fix: Adds safety to corpses and cleans up quests (#1685)
### Summary - Adds some more checks in case a corpse's owner is somehow null. Would like to eventually allow null owner corpses, but more work is needed. - Cleans up variable unboxing and reassignment in quests. Also flattens quest logic. Still more work needs to be done. - Codegens more quest items/mobiles.
This commit is contained in:
parent
0d5aa1d022
commit
e994505ad0
90 changed files with 2623 additions and 3168 deletions
|
|
@ -136,7 +136,7 @@ namespace Server.Engines.Harvest
|
|||
|
||||
if (qs is CollectorQuest)
|
||||
{
|
||||
QuestObjective obj = qs.FindObjective<FishPearlsObjective>();
|
||||
var obj = qs.FindObjective<FishPearlsObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -41,7 +41,7 @@ public abstract partial class BaseAmbitiousSolenQueen : BaseQuester
|
|||
}
|
||||
else
|
||||
{
|
||||
QuestObjective obj = qs.FindObjective<ReturnAfterKillsObjective>();
|
||||
var obj = qs.FindObjective<ReturnAfterKillsObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
|
|
@ -88,7 +88,7 @@ public abstract partial class BaseAmbitiousSolenQueen : BaseQuester
|
|||
}
|
||||
else
|
||||
{
|
||||
QuestSystem newQuest = new AmbitiousQueenQuest(player, RedSolen);
|
||||
var newQuest = new AmbitiousQueenQuest(player, RedSolen);
|
||||
|
||||
if (player.Quest == null && QuestSystem.CanOfferQuest(player, typeof(AmbitiousQueenQuest)))
|
||||
{
|
||||
|
|
@ -110,7 +110,7 @@ public abstract partial class BaseAmbitiousSolenQueen : BaseQuester
|
|||
return base.OnDragDrop(from, dropped);
|
||||
}
|
||||
|
||||
QuestObjective obj = qs.FindObjective<GatherFungiObjective>();
|
||||
var obj = qs.FindObjective<GatherFungiObjective>();
|
||||
|
||||
if (obj?.Completed != false || dropped is not ZoogiFungus fungi)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -36,19 +36,10 @@ public partial class AlbertaGiacco : BaseQuester
|
|||
HairHue = 0x457;
|
||||
}
|
||||
|
||||
public override bool CanTalkTo(PlayerMobile to)
|
||||
{
|
||||
QuestSystem qs = to.Quest as CollectorQuest;
|
||||
|
||||
if (qs == null)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
return qs.IsObjectiveInProgress(typeof(FindAlbertaObjective))
|
||||
|| qs.IsObjectiveInProgress(typeof(SitOnTheStoolObjective))
|
||||
|| qs.IsObjectiveInProgress(typeof(ReturnPaintingObjective));
|
||||
}
|
||||
public override bool CanTalkTo(PlayerMobile to) =>
|
||||
to.Quest is CollectorQuest qs && (qs.IsObjectiveInProgress(typeof(FindAlbertaObjective))
|
||||
|| qs.IsObjectiveInProgress(typeof(SitOnTheStoolObjective))
|
||||
|| qs.IsObjectiveInProgress(typeof(ReturnPaintingObjective)));
|
||||
|
||||
public override void OnTalk(PlayerMobile player, bool contextMenu)
|
||||
{
|
||||
|
|
@ -58,7 +49,7 @@ public partial class AlbertaGiacco : BaseQuester
|
|||
{
|
||||
Direction = GetDirectionTo(player);
|
||||
|
||||
QuestObjective obj = qs.FindObjective<FindAlbertaObjective>();
|
||||
var obj = qs.FindObjective<FindAlbertaObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -45,110 +45,9 @@ public partial class ElwoodMcCarrin : BaseQuester
|
|||
|
||||
var qs = player.Quest;
|
||||
|
||||
if (qs is CollectorQuest)
|
||||
if (qs is not CollectorQuest)
|
||||
{
|
||||
if (qs.IsObjectiveInProgress(typeof(FishPearlsObjective)))
|
||||
{
|
||||
qs.AddConversation(new ElwoodDuringFishConversation());
|
||||
}
|
||||
else
|
||||
{
|
||||
QuestObjective obj = qs.FindObjective<ReturnPearlsObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
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<ReturnPaintingObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
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<ReturnAutographObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
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<ReturnToysObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
obj.Complete();
|
||||
|
||||
if (GiveReward(player))
|
||||
{
|
||||
qs.AddConversation(new EndConversation());
|
||||
}
|
||||
else
|
||||
{
|
||||
qs.AddConversation(new FullEndConversation(true));
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
obj = qs.FindObjective<MakeRoomObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
if (GiveReward(player))
|
||||
{
|
||||
obj.Complete();
|
||||
qs.AddConversation(new EndConversation());
|
||||
}
|
||||
else
|
||||
{
|
||||
qs.AddConversation(new FullEndConversation(false));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
QuestSystem newQuest = new CollectorQuest(player);
|
||||
var newQuest = new CollectorQuest(player);
|
||||
|
||||
if (qs == null && QuestSystem.CanOfferQuest(player, typeof(CollectorQuest)))
|
||||
{
|
||||
|
|
@ -158,10 +57,113 @@ public partial class ElwoodMcCarrin : BaseQuester
|
|||
{
|
||||
newQuest.AddConversation(new DontOfferConversation());
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.IsObjectiveInProgress(typeof(FishPearlsObjective)))
|
||||
{
|
||||
qs.AddConversation(new ElwoodDuringFishConversation());
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.FindObjective<ReturnPearlsObjective>() is { Completed: false } obj1)
|
||||
{
|
||||
obj1.Complete();
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.IsObjectiveInProgress(typeof(FindAlbertaObjective)))
|
||||
{
|
||||
qs.AddConversation(new ElwoodDuringPainting1Conversation());
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.IsObjectiveInProgress(typeof(SitOnTheStoolObjective)))
|
||||
{
|
||||
qs.AddConversation(new ElwoodDuringPainting2Conversation());
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.FindObjective<ReturnPaintingObjective>() is { Completed: false } obj2)
|
||||
{
|
||||
obj2.Complete();
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.IsObjectiveInProgress(typeof(FindGabrielObjective)))
|
||||
{
|
||||
qs.AddConversation(new ElwoodDuringAutograph1Conversation());
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.IsObjectiveInProgress(typeof(FindSheetMusicObjective)))
|
||||
{
|
||||
qs.AddConversation(new ElwoodDuringAutograph2Conversation());
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.IsObjectiveInProgress(typeof(ReturnSheetMusicObjective)))
|
||||
{
|
||||
qs.AddConversation(new ElwoodDuringAutograph3Conversation());
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.FindObjective<ReturnAutographObjective>() is { Completed: false } obj3)
|
||||
{
|
||||
obj3.Complete();
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.IsObjectiveInProgress(typeof(FindTomasObjective)))
|
||||
{
|
||||
qs.AddConversation(new ElwoodDuringToys1Conversation());
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.IsObjectiveInProgress(typeof(CaptureImagesObjective)))
|
||||
{
|
||||
qs.AddConversation(new ElwoodDuringToys2Conversation());
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.IsObjectiveInProgress(typeof(ReturnImagesObjective)))
|
||||
{
|
||||
qs.AddConversation(new ElwoodDuringToys3Conversation());
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.FindObjective<ReturnToysObjective>() is { Completed: false } obj4)
|
||||
{
|
||||
obj4.Complete();
|
||||
|
||||
if (GiveReward(player))
|
||||
{
|
||||
qs.AddConversation(new EndConversation());
|
||||
}
|
||||
else
|
||||
{
|
||||
qs.AddConversation(new FullEndConversation(true));
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.FindObjective<MakeRoomObjective>() is { Completed: false } obj5)
|
||||
{
|
||||
if (GiveReward(player))
|
||||
{
|
||||
obj5.Complete();
|
||||
qs.AddConversation(new EndConversation());
|
||||
}
|
||||
else
|
||||
{
|
||||
qs.AddConversation(new FullEndConversation(false));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public bool GiveReward(Mobile to)
|
||||
public static bool GiveReward(Mobile to)
|
||||
{
|
||||
var bag = new Bag();
|
||||
|
||||
|
|
|
|||
|
|
@ -37,52 +37,44 @@ public partial class GabrielPiete : BaseQuester
|
|||
FacialHairHue = 0x460;
|
||||
}
|
||||
|
||||
public override bool CanTalkTo(PlayerMobile to)
|
||||
{
|
||||
QuestSystem qs = to.Quest as CollectorQuest;
|
||||
|
||||
if (qs == null)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
return qs.IsObjectiveInProgress(typeof(FindGabrielObjective))
|
||||
|| qs.IsObjectiveInProgress(typeof(FindSheetMusicObjective))
|
||||
|| qs.IsObjectiveInProgress(typeof(ReturnSheetMusicObjective))
|
||||
|| qs.IsObjectiveInProgress(typeof(ReturnAutographObjective));
|
||||
}
|
||||
public override bool CanTalkTo(PlayerMobile to) =>
|
||||
to.Quest is CollectorQuest qs && (qs.IsObjectiveInProgress(typeof(FindGabrielObjective))
|
||||
|| qs.IsObjectiveInProgress(typeof(FindSheetMusicObjective))
|
||||
|| qs.IsObjectiveInProgress(typeof(ReturnSheetMusicObjective))
|
||||
|| qs.IsObjectiveInProgress(typeof(ReturnAutographObjective)));
|
||||
|
||||
public override void OnTalk(PlayerMobile player, bool contextMenu)
|
||||
{
|
||||
var qs = player.Quest;
|
||||
|
||||
if (qs is CollectorQuest)
|
||||
if (qs is not CollectorQuest)
|
||||
{
|
||||
Direction = GetDirectionTo(player);
|
||||
return;
|
||||
}
|
||||
|
||||
QuestObjective obj = qs.FindObjective<FindGabrielObjective>();
|
||||
Direction = GetDirectionTo(player);
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
obj.Complete();
|
||||
}
|
||||
else if (qs.IsObjectiveInProgress(typeof(FindSheetMusicObjective)))
|
||||
{
|
||||
qs.AddConversation(new GabrielNoSheetMusicConversation());
|
||||
}
|
||||
else
|
||||
{
|
||||
obj = qs.FindObjective<ReturnSheetMusicObjective>();
|
||||
if (qs.FindObjective<FindGabrielObjective>() is { Completed: false } obj1)
|
||||
{
|
||||
obj1.Complete();
|
||||
return;
|
||||
}
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
obj.Complete();
|
||||
}
|
||||
else if (qs.IsObjectiveInProgress(typeof(ReturnAutographObjective)))
|
||||
{
|
||||
qs.AddConversation(new GabrielIgnoreConversation());
|
||||
}
|
||||
}
|
||||
if (qs.IsObjectiveInProgress(typeof(FindSheetMusicObjective)))
|
||||
{
|
||||
qs.AddConversation(new GabrielNoSheetMusicConversation());
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.FindObjective<ReturnSheetMusicObjective>() is { Completed: false } obj2)
|
||||
{
|
||||
obj2.Complete();
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.IsObjectiveInProgress(typeof(ReturnAutographObjective)))
|
||||
{
|
||||
qs.AddConversation(new GabrielIgnoreConversation());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -35,17 +35,8 @@ public partial class Impresario : BaseQuester
|
|||
Utility.AssignRandomFacialHair(this);
|
||||
}
|
||||
|
||||
public override bool CanTalkTo(PlayerMobile to)
|
||||
{
|
||||
QuestSystem qs = to.Quest as CollectorQuest;
|
||||
|
||||
if (qs == null)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
return qs.IsObjectiveInProgress(typeof(FindSheetMusicObjective));
|
||||
}
|
||||
public override bool CanTalkTo(PlayerMobile to) =>
|
||||
to.Quest is CollectorQuest qs && qs.IsObjectiveInProgress(typeof(FindSheetMusicObjective));
|
||||
|
||||
public override void OnTalk(PlayerMobile player, bool contextMenu)
|
||||
{
|
||||
|
|
@ -119,34 +110,38 @@ public class SheetMusicOfferGump : BaseQuestGump
|
|||
|
||||
public override void OnResponse(NetState sender, RelayInfo info)
|
||||
{
|
||||
if (info.ButtonID == 1 && info.IsSwitched(1))
|
||||
if (info.ButtonID != 1 || !info.IsSwitched(1))
|
||||
{
|
||||
if (sender.Mobile is PlayerMobile player)
|
||||
{
|
||||
var qs = player.Quest;
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs is not CollectorQuest)
|
||||
{
|
||||
return;
|
||||
}
|
||||
if (sender.Mobile is not PlayerMobile player)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
var obj = qs.FindObjective<FindSheetMusicObjective>();
|
||||
var qs = player.Quest;
|
||||
|
||||
if (obj?.Completed != false)
|
||||
{
|
||||
return;
|
||||
}
|
||||
if (qs is not CollectorQuest)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
if (player.Backpack?.ConsumeTotal(typeof(Gold), 10) == true || Banker.Withdraw(player, 10))
|
||||
{
|
||||
obj.Complete();
|
||||
}
|
||||
else
|
||||
{
|
||||
// You don't have enough gold to buy the sheet music.
|
||||
player.SendLocalizedMessage(1055108);
|
||||
}
|
||||
}
|
||||
var obj = qs.FindObjective<FindSheetMusicObjective>();
|
||||
|
||||
if (obj?.Completed != false)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
if (player.Backpack?.ConsumeTotal(typeof(Gold), 10) == true || Banker.Withdraw(player, 10))
|
||||
{
|
||||
obj.Complete();
|
||||
}
|
||||
else
|
||||
{
|
||||
// You don't have enough gold to buy the sheet music.
|
||||
player.SendLocalizedMessage(1055108);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -35,60 +35,50 @@ public partial class TomasONeerlan : BaseQuester
|
|||
HairHue = 0x455;
|
||||
}
|
||||
|
||||
public override bool CanTalkTo(PlayerMobile to)
|
||||
{
|
||||
QuestSystem qs = to.Quest as CollectorQuest;
|
||||
|
||||
if (qs == null)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
return qs.IsObjectiveInProgress(typeof(FindTomasObjective))
|
||||
|| qs.IsObjectiveInProgress(typeof(CaptureImagesObjective))
|
||||
|| qs.IsObjectiveInProgress(typeof(ReturnImagesObjective));
|
||||
}
|
||||
public override bool CanTalkTo(PlayerMobile to) =>
|
||||
to.Quest is CollectorQuest qs && (qs.IsObjectiveInProgress(typeof(FindTomasObjective))
|
||||
|| qs.IsObjectiveInProgress(typeof(CaptureImagesObjective))
|
||||
|| qs.IsObjectiveInProgress(typeof(ReturnImagesObjective)));
|
||||
|
||||
public override void OnTalk(PlayerMobile player, bool contextMenu)
|
||||
{
|
||||
var qs = player.Quest;
|
||||
|
||||
if (qs is CollectorQuest)
|
||||
if (qs is not CollectorQuest)
|
||||
{
|
||||
Direction = GetDirectionTo(player);
|
||||
return;
|
||||
}
|
||||
|
||||
QuestObjective obj = qs.FindObjective<FindTomasObjective>();
|
||||
Direction = GetDirectionTo(player);
|
||||
|
||||
if (obj?.Completed == false)
|
||||
if (qs.FindObjective<FindTomasObjective>() is { Completed: false } obj1) {
|
||||
var paints = new EnchantedPaints();
|
||||
|
||||
if (!player.PlaceInBackpack(paints))
|
||||
{
|
||||
Item paints = new EnchantedPaints();
|
||||
|
||||
if (!player.PlaceInBackpack(paints))
|
||||
{
|
||||
paints.Delete();
|
||||
// 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.
|
||||
player.SendLocalizedMessage(1046260);
|
||||
}
|
||||
else
|
||||
{
|
||||
obj.Complete();
|
||||
}
|
||||
}
|
||||
else if (qs.IsObjectiveInProgress(typeof(CaptureImagesObjective)))
|
||||
{
|
||||
qs.AddConversation(new TomasDuringCollectingConversation());
|
||||
paints.Delete();
|
||||
// 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.
|
||||
player.SendLocalizedMessage(1046260);
|
||||
}
|
||||
else
|
||||
{
|
||||
obj = qs.FindObjective<ReturnImagesObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
player.Backpack?.ConsumeUpTo(typeof(EnchantedPaints), 1);
|
||||
|
||||
obj.Complete();
|
||||
}
|
||||
obj1.Complete();
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.IsObjectiveInProgress(typeof(CaptureImagesObjective)))
|
||||
{
|
||||
qs.AddConversation(new TomasDuringCollectingConversation());
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.FindObjective<ReturnImagesObjective>() is { Completed: false } obj2)
|
||||
{
|
||||
player.Backpack?.ConsumeUpTo(typeof(EnchantedPaints), 1);
|
||||
|
||||
obj2.Complete();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -446,8 +446,8 @@ namespace Server.Engines.Quests
|
|||
return false;
|
||||
}
|
||||
|
||||
if (questType == typeof(UzeraanTurmoilQuest) && pm.Profession != 1 && pm.Profession != 2 && pm.Profession != 5
|
||||
) // warrior / magician / paladin
|
||||
// warrior / magician / paladin
|
||||
if (questType == typeof(UzeraanTurmoilQuest) && pm.Profession != 1 && pm.Profession != 2 && pm.Profession != 5)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -32,7 +32,7 @@ public partial class CrystalCaveBarrier : Item
|
|||
|
||||
if (qs is DarkTidesQuest)
|
||||
{
|
||||
QuestObjective obj = qs.FindObjective<SpeakCavePasswordObjective>();
|
||||
var obj = qs.FindObjective<SpeakCavePasswordObjective>();
|
||||
|
||||
if (obj?.Completed == true)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -52,7 +52,7 @@ public partial class KronusScroll : QuestItem
|
|||
{
|
||||
if (pm.Map == m_WellOfTearsMap && m_WellOfTearsArea.Contains(pm.Location))
|
||||
{
|
||||
QuestObjective obj = qs.FindObjective<UseCallingScrollObjective>();
|
||||
var obj = qs.FindObjective<UseCallingScrollObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -29,7 +29,7 @@ public partial class KronusScrollBox : MetalBox
|
|||
|
||||
if (qs is DarkTidesQuest)
|
||||
{
|
||||
QuestObjective obj = qs.FindObjective<FindCallingScrollObjective>();
|
||||
var obj = qs.FindObjective<FindCallingScrollObjective>();
|
||||
|
||||
if (obj?.Completed == false || DarkTidesQuest.HasLostCallingScroll(from))
|
||||
{
|
||||
|
|
|
|||
|
|
@ -24,7 +24,7 @@ public partial class ScrollOfAbraxus : QuestItem
|
|||
|
||||
if (qs is DarkTidesQuest)
|
||||
{
|
||||
QuestObjective obj = qs.FindObjective<RetrieveAbraxusScrollObjective>();
|
||||
var obj = qs.FindObjective<RetrieveAbraxusScrollObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
|
|
@ -46,7 +46,7 @@ public partial class ScrollOfAbraxus : QuestItem
|
|||
|
||||
if (qs is DarkTidesQuest)
|
||||
{
|
||||
QuestObjective obj = qs.FindObjective<ReadAbraxusScrollObjective>();
|
||||
var obj = qs.FindObjective<ReadAbraxusScrollObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -57,7 +57,7 @@ public partial class Horus : BaseQuester
|
|||
|
||||
if (qs is DarkTidesQuest)
|
||||
{
|
||||
QuestObjective obj = qs.FindObjective<FindCrystalCaveObjective>();
|
||||
var obj = qs.FindObjective<FindCrystalCaveObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
|
|
@ -70,48 +70,47 @@ public partial class Horus : BaseQuester
|
|||
{
|
||||
base.OnMovement(m, oldLocation);
|
||||
|
||||
if (InRange(m.Location, 2) && !InRange(oldLocation, 2) && m is PlayerMobile pm)
|
||||
if (!InRange(m.Location, 2) || InRange(oldLocation, 2) || m is not PlayerMobile pm)
|
||||
{
|
||||
var qs = pm.Quest;
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs is DarkTidesQuest)
|
||||
var qs = pm.Quest;
|
||||
|
||||
if (qs is not DarkTidesQuest)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.FindObjective<ReturnToCrystalCaveObjective>() is { Completed: false } obj1)
|
||||
{
|
||||
obj1.Complete();
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.FindObjective<FindHorusAboutRewardObjective>() is { Completed: false } obj2)
|
||||
{
|
||||
var cont = GetNewContainer();
|
||||
|
||||
cont.DropItem(new Gold(500));
|
||||
|
||||
BaseJewel jewel = new GoldBracelet();
|
||||
if (Core.AOS)
|
||||
{
|
||||
QuestObjective obj = qs.FindObjective<ReturnToCrystalCaveObjective>();
|
||||
BaseRunicTool.ApplyAttributesTo(jewel, 3, 20, 40);
|
||||
}
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
obj.Complete();
|
||||
}
|
||||
else
|
||||
{
|
||||
obj = qs.FindObjective<FindHorusAboutRewardObjective>();
|
||||
cont.DropItem(jewel);
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
var cont = GetNewContainer();
|
||||
|
||||
cont.DropItem(new Gold(500));
|
||||
|
||||
BaseJewel jewel = new GoldBracelet();
|
||||
if (Core.AOS)
|
||||
{
|
||||
BaseRunicTool.ApplyAttributesTo(jewel, 3, 20, 40);
|
||||
}
|
||||
|
||||
cont.DropItem(jewel);
|
||||
|
||||
if (!pm.PlaceInBackpack(cont))
|
||||
{
|
||||
cont.Delete();
|
||||
// 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.
|
||||
pm.SendLocalizedMessage(1046260);
|
||||
}
|
||||
else
|
||||
{
|
||||
obj.Complete();
|
||||
}
|
||||
}
|
||||
}
|
||||
if (pm.PlaceInBackpack(cont))
|
||||
{
|
||||
obj2.Complete();
|
||||
}
|
||||
else
|
||||
{
|
||||
cont.Delete();
|
||||
// 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.
|
||||
pm.SendLocalizedMessage(1046260);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -120,36 +119,30 @@ public partial class Horus : BaseQuester
|
|||
{
|
||||
base.GetContextMenuEntries(from, list);
|
||||
|
||||
if (from.Alive)
|
||||
if (!from.Alive || from is not PlayerMobile pm)
|
||||
{
|
||||
if (from is PlayerMobile pm)
|
||||
{
|
||||
var qs = pm.Quest;
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs is DarkTidesQuest)
|
||||
{
|
||||
QuestObjective obj = qs.FindObjective<SpeakCavePasswordObjective>();
|
||||
var enabled = obj?.Completed == false;
|
||||
var qs = pm.Quest;
|
||||
|
||||
list.Add(new SpeakPasswordEntry(this, pm, enabled));
|
||||
}
|
||||
}
|
||||
if (qs is DarkTidesQuest)
|
||||
{
|
||||
var obj = qs.FindObjective<SpeakCavePasswordObjective>();
|
||||
var enabled = obj?.Completed == false;
|
||||
|
||||
list.Add(new SpeakPasswordEntry(this, pm, enabled));
|
||||
}
|
||||
}
|
||||
|
||||
public virtual void OnPasswordSpoken(PlayerMobile from)
|
||||
{
|
||||
var qs = from.Quest;
|
||||
var obj = (from.Quest as DarkTidesQuest)?.FindObjective<SpeakCavePasswordObjective>();
|
||||
|
||||
if (qs is DarkTidesQuest)
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
QuestObjective obj = qs.FindObjective<SpeakCavePasswordObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
obj.Complete();
|
||||
return;
|
||||
}
|
||||
obj.Complete();
|
||||
return;
|
||||
}
|
||||
|
||||
from.SendLocalizedMessage(1060185); // Horus ignores you.
|
||||
|
|
|
|||
|
|
@ -89,86 +89,80 @@ public partial class Mardoth : BaseQuester
|
|||
{
|
||||
var qs = player.Quest;
|
||||
|
||||
if (qs is DarkTidesQuest)
|
||||
if (qs == null && QuestSystem.CanOfferQuest(player, typeof(DarkTidesQuest)))
|
||||
{
|
||||
if (DarkTidesQuest.HasLostCallingScroll(player))
|
||||
new DarkTidesQuest(player).SendOffer();
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs is not DarkTidesQuest)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
if (DarkTidesQuest.HasLostCallingScroll(player))
|
||||
{
|
||||
qs.AddConversation(new LostCallingScrollConversation(true));
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.FindObjective<FindMardothAboutVaultObjective>() is { Completed: false } obj1)
|
||||
{
|
||||
obj1.Complete();
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.FindObjective<FindMardothAboutKronusObjective>() is { Completed: false } obj2)
|
||||
{
|
||||
obj2.Complete();
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.FindObjective<FindMardothEndObjective>() is { Completed: false } obj3)
|
||||
{
|
||||
var cont = GetNewContainer();
|
||||
|
||||
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));
|
||||
|
||||
BaseWeapon weapon = new BoneHarvester();
|
||||
|
||||
weapon.Slayer = SlayerName.OrcSlaying;
|
||||
|
||||
if (Core.AOS)
|
||||
{
|
||||
qs.AddConversation(new LostCallingScrollConversation(true));
|
||||
BaseRunicTool.ApplyAttributesTo(weapon, 3, 20, 40);
|
||||
}
|
||||
else
|
||||
{
|
||||
QuestObjective obj = qs.FindObjective<FindMardothAboutVaultObjective>();
|
||||
weapon.DamageLevel = (WeaponDamageLevel)RandomMinMaxScaled(2, 4);
|
||||
weapon.AccuracyLevel = (WeaponAccuracyLevel)RandomMinMaxScaled(2, 4);
|
||||
weapon.DurabilityLevel = (WeaponDurabilityLevel)RandomMinMaxScaled(2, 4);
|
||||
}
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
obj.Complete();
|
||||
}
|
||||
else
|
||||
{
|
||||
obj = qs.FindObjective<FindMardothAboutKronusObjective>();
|
||||
cont.DropItem(weapon);
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
obj.Complete();
|
||||
}
|
||||
else
|
||||
{
|
||||
obj = qs.FindObjective<FindMardothEndObjective>();
|
||||
cont.DropItem(new BankCheck(2000));
|
||||
cont.DropItem(new EnchantedSextant());
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
var cont = GetNewContainer();
|
||||
|
||||
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));
|
||||
|
||||
BaseWeapon weapon = new BoneHarvester();
|
||||
|
||||
weapon.Slayer = SlayerName.OrcSlaying;
|
||||
|
||||
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(weapon);
|
||||
|
||||
cont.DropItem(new BankCheck(2000));
|
||||
cont.DropItem(new EnchantedSextant());
|
||||
|
||||
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.
|
||||
}
|
||||
}
|
||||
}
|
||||
if (!player.PlaceInBackpack(cont))
|
||||
{
|
||||
cont.Delete();
|
||||
// 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.
|
||||
player.SendLocalizedMessage(1046260);
|
||||
}
|
||||
else
|
||||
{
|
||||
obj3.Complete();
|
||||
}
|
||||
}
|
||||
else if (qs == null && QuestSystem.CanOfferQuest(player, typeof(DarkTidesQuest)))
|
||||
else if (contextMenu)
|
||||
{
|
||||
new DarkTidesQuest(player).SendOffer();
|
||||
FocusTo(player);
|
||||
player.SendLocalizedMessage(1061821); // Mardoth has nothing more for you at this time.
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -176,22 +170,24 @@ public partial class Mardoth : BaseQuester
|
|||
{
|
||||
base.OnMovement(m, oldLocation);
|
||||
|
||||
if (m is PlayerMobile && !m.Frozen && !m.Alive && InRange(m, 4) && !InRange(oldLocation, 4) && InLOS(m))
|
||||
if (m is not PlayerMobile || m.Frozen || m.Alive || !InRange(m, 4) || InRange(oldLocation, 4) || !InLOS(m))
|
||||
{
|
||||
if (m.Map?.CanFit(m.Location, 16, false, false) != true)
|
||||
{
|
||||
m.SendLocalizedMessage(502391); // Thou can not be resurrected there!
|
||||
}
|
||||
else
|
||||
{
|
||||
Direction = GetDirectionTo(m);
|
||||
return;
|
||||
}
|
||||
|
||||
m.PlaySound(0x214);
|
||||
m.FixedEffect(0x376A, 10, 16);
|
||||
if (m.Map?.CanFit(m.Location, 16, false, false) != true)
|
||||
{
|
||||
m.SendLocalizedMessage(502391); // Thou can not be resurrected there!
|
||||
}
|
||||
else
|
||||
{
|
||||
Direction = GetDirectionTo(m);
|
||||
|
||||
m.CloseGump<ResurrectGump>();
|
||||
m.SendGump(new ResurrectGump(m, ResurrectMessage.Healer));
|
||||
}
|
||||
m.PlaySound(0x214);
|
||||
m.FixedEffect(0x376A, 10, 16);
|
||||
|
||||
m.CloseGump<ResurrectGump>();
|
||||
m.SendGump(new ResurrectGump(m, ResurrectMessage.Healer));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -60,7 +60,7 @@ public partial class EminosKatanaChest : WoodenChest
|
|||
}
|
||||
else
|
||||
{
|
||||
QuestObjective obj = qs.FindObjective<HallwayWalkObjective>();
|
||||
var obj = qs.FindObjective<HallwayWalkObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -21,7 +21,7 @@ public partial class WhiteNinjaQuestTeleporter : DynamicTeleporter
|
|||
|
||||
if (qs is EminosUndertakingQuest)
|
||||
{
|
||||
QuestObjective obj = qs.FindObjective<SearchForSwordObjective>();
|
||||
var obj = qs.FindObjective<SearchForSwordObjective>();
|
||||
|
||||
if (obj != null)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -80,23 +80,19 @@ public partial class Emino : BaseQuester
|
|||
return;
|
||||
}
|
||||
|
||||
QuestObjective obj = qs.FindObjective<FindEminoBeginObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
if (qs.FindObjective<FindEminoBeginObjective>() is { Completed: false } obj1)
|
||||
{
|
||||
obj.Complete();
|
||||
obj1.Complete();
|
||||
return;
|
||||
}
|
||||
|
||||
obj = qs.FindObjective<UseTeleporterObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
if (qs.FindObjective<UseTeleporterObjective>() is { Completed: false } obj2)
|
||||
{
|
||||
Item note = new NoteForZoel();
|
||||
var note = new NoteForZoel();
|
||||
|
||||
if (player.PlaceInBackpack(note))
|
||||
{
|
||||
obj.Complete();
|
||||
obj2.Complete();
|
||||
|
||||
player.AddToBackpack(new LeatherNinjaPants());
|
||||
player.AddToBackpack(new LeatherNinjaMitts());
|
||||
|
|
@ -111,9 +107,7 @@ public partial class Emino : BaseQuester
|
|||
return;
|
||||
}
|
||||
|
||||
obj = qs.FindObjective<ReturnFromInnObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
if (qs.FindObjective<ReturnFromInnObjective>() is { Completed: false } obj3)
|
||||
{
|
||||
var cont = GetNewContainer();
|
||||
|
||||
|
|
@ -127,7 +121,7 @@ public partial class Emino : BaseQuester
|
|||
|
||||
if (player.PlaceInBackpack(cont))
|
||||
{
|
||||
obj.Complete();
|
||||
obj3.Complete();
|
||||
}
|
||||
else
|
||||
{
|
||||
|
|
@ -145,60 +139,47 @@ public partial class Emino : BaseQuester
|
|||
return;
|
||||
}
|
||||
|
||||
obj = qs.FindObjective<GiveEminoSwordObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
if (qs.FindObjective<GiveEminoSwordObjective>() is { Completed: false } obj4)
|
||||
{
|
||||
Item katana = null;
|
||||
var katana = player.Backpack?.FindItemByType<EminosKatana>();
|
||||
|
||||
if (player.Backpack != null)
|
||||
if (katana == null)
|
||||
{
|
||||
katana = player.Backpack.FindItemByType<EminosKatana>();
|
||||
return;
|
||||
}
|
||||
|
||||
if (katana != null)
|
||||
var stolenTreasure = false;
|
||||
|
||||
var walk = qs.FindObjective<HallwayWalkObjective>();
|
||||
|
||||
if (walk != null)
|
||||
{
|
||||
var stolenTreasure = false;
|
||||
stolenTreasure = walk.StolenTreasure;
|
||||
}
|
||||
|
||||
var walk = qs.FindObjective<HallwayWalkObjective>();
|
||||
var kama = new Kama();
|
||||
BaseRunicTool.ApplyAttributesTo(kama, 1, 10, stolenTreasure ? 20 : 30);
|
||||
|
||||
if (walk != null)
|
||||
{
|
||||
stolenTreasure = walk.StolenTreasure;
|
||||
}
|
||||
|
||||
var kama = new Kama();
|
||||
if (player.PlaceInBackpack(kama))
|
||||
{
|
||||
katana.Delete();
|
||||
obj4.Complete();
|
||||
|
||||
if (stolenTreasure)
|
||||
{
|
||||
BaseRunicTool.ApplyAttributesTo(kama, 1, 10, 20);
|
||||
qs.AddConversation(new EarnLessGiftsConversation());
|
||||
}
|
||||
else
|
||||
{
|
||||
BaseRunicTool.ApplyAttributesTo(kama, 1, 10, 30);
|
||||
}
|
||||
|
||||
if (player.PlaceInBackpack(kama))
|
||||
{
|
||||
katana.Delete();
|
||||
obj.Complete();
|
||||
|
||||
if (stolenTreasure)
|
||||
{
|
||||
qs.AddConversation(new EarnLessGiftsConversation());
|
||||
}
|
||||
else
|
||||
{
|
||||
qs.AddConversation(new EarnGiftsConversation());
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
kama.Delete();
|
||||
// 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.
|
||||
player.SendLocalizedMessage(1046260);
|
||||
qs.AddConversation(new EarnGiftsConversation());
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
kama.Delete();
|
||||
// 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.
|
||||
player.SendLocalizedMessage(1046260);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -206,22 +187,24 @@ public partial class Emino : BaseQuester
|
|||
{
|
||||
base.OnMovement(m, oldLocation);
|
||||
|
||||
if (!m.Frozen && !m.Alive && InRange(m, 4) && !InRange(oldLocation, 4) && InLOS(m))
|
||||
if (m.Frozen || m.Alive || !InRange(m, 4) || InRange(oldLocation, 4) || !InLOS(m))
|
||||
{
|
||||
if (m.Map?.CanFit(m.Location, 16, false, false) != true)
|
||||
{
|
||||
m.SendLocalizedMessage(502391); // Thou can not be resurrected there!
|
||||
}
|
||||
else
|
||||
{
|
||||
Direction = GetDirectionTo(m);
|
||||
return;
|
||||
}
|
||||
|
||||
m.PlaySound(0x214);
|
||||
m.FixedEffect(0x376A, 10, 16);
|
||||
if (m.Map?.CanFit(m.Location, 16, false, false) != true)
|
||||
{
|
||||
m.SendLocalizedMessage(502391); // Thou can not be resurrected there!
|
||||
}
|
||||
else
|
||||
{
|
||||
Direction = GetDirectionTo(m);
|
||||
|
||||
m.CloseGump<ResurrectGump>();
|
||||
m.SendGump(new ResurrectGump(m, ResurrectMessage.Healer));
|
||||
}
|
||||
m.PlaySound(0x214);
|
||||
m.FixedEffect(0x376A, 10, 16);
|
||||
|
||||
m.CloseGump<ResurrectGump>();
|
||||
m.SendGump(new ResurrectGump(m, ResurrectMessage.Healer));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -54,7 +54,7 @@ public partial class Zoel : BaseQuester
|
|||
|
||||
if (qs is EminosUndertakingQuest)
|
||||
{
|
||||
QuestObjective obj = qs.FindObjective<FindZoelObjective>();
|
||||
var obj = qs.FindObjective<FindZoelObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
|
|
@ -73,7 +73,7 @@ public partial class Zoel : BaseQuester
|
|||
{
|
||||
if (dropped is NoteForZoel)
|
||||
{
|
||||
QuestObjective obj = qs.FindObjective<GiveZoelNoteObjective>();
|
||||
var obj = qs.FindObjective<GiveZoelNoteObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -42,7 +42,7 @@ public partial class HaochisKatanaGenerator : Item
|
|||
}
|
||||
else
|
||||
{
|
||||
QuestObjective obj = qs.FindObjective<FifthTrialIntroObjective>();
|
||||
var obj = qs.FindObjective<FifthTrialIntroObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -37,7 +37,7 @@ public partial class HonorCandle : CandleLong
|
|||
|
||||
if (qs is HaochisTrialsQuest)
|
||||
{
|
||||
QuestObjective obj = qs.FindObjective<SixthTrialIntroObjective>();
|
||||
var obj = qs.FindObjective<SixthTrialIntroObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -50,7 +50,7 @@ public partial class DeadlyImp : BaseCreature
|
|||
var qs = player.Quest;
|
||||
if (qs is HaochisTrialsQuest)
|
||||
{
|
||||
QuestObjective obj = qs.FindObjective<SecondTrialAttackObjective>();
|
||||
var obj = qs.FindObjective<SecondTrialAttackObjective>();
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
obj.Complete();
|
||||
|
|
|
|||
|
|
@ -57,7 +57,7 @@ public partial class FierceDragon : BaseCreature
|
|||
var qs = player.Quest;
|
||||
if (qs is HaochisTrialsQuest)
|
||||
{
|
||||
QuestObjective obj = qs.FindObjective<SecondTrialAttackObjective>();
|
||||
var obj = qs.FindObjective<SecondTrialAttackObjective>();
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
obj.Complete();
|
||||
|
|
|
|||
|
|
@ -47,115 +47,95 @@ public partial class Haochi : BaseQuester
|
|||
{
|
||||
var qs = player.Quest;
|
||||
|
||||
if (qs is HaochisTrialsQuest)
|
||||
if (qs is not HaochisTrialsQuest)
|
||||
{
|
||||
if (HaochisTrialsQuest.HasLostHaochisKatana(player))
|
||||
return;
|
||||
}
|
||||
|
||||
if (HaochisTrialsQuest.HasLostHaochisKatana(player))
|
||||
{
|
||||
qs.AddConversation(new LostSwordConversation());
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.FindObjective<FindHaochiObjective>() is { Completed: false } obj1)
|
||||
{
|
||||
obj1.Complete();
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.FindObjective<FirstTrialReturnObjective>() is { Completed: false } obj2)
|
||||
{
|
||||
player.AddToBackpack(new LeatherDo());
|
||||
obj2.Complete();
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.FindObjective<SecondTrialReturnObjective>() is { Completed: false } obj3)
|
||||
{
|
||||
if (obj3.Dragon)
|
||||
{
|
||||
player.AddToBackpack(new LeatherSuneate());
|
||||
}
|
||||
|
||||
obj3.Complete();
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.FindObjective<ThirdTrialReturnObjective>() is { Completed: false } obj4)
|
||||
{
|
||||
player.AddToBackpack(new LeatherHaidate());
|
||||
obj4.Complete();
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.FindObjective<FourthTrialReturnObjective>() is { Completed: false } obj5)
|
||||
{
|
||||
if (!obj5.KilledCat)
|
||||
{
|
||||
var cont = GetNewContainer();
|
||||
cont.DropItem(new LeatherHiroSode());
|
||||
cont.DropItem(new JinBaori());
|
||||
player.AddToBackpack(cont);
|
||||
}
|
||||
|
||||
obj5.Complete();
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.FindObjective<FifthTrialReturnObjective>() is { Completed: false } obj6)
|
||||
{
|
||||
var katana = player.Backpack?.FindItemByType<HaochisKatana>();
|
||||
if (katana == null)
|
||||
{
|
||||
qs.AddConversation(new LostSwordConversation());
|
||||
return;
|
||||
}
|
||||
|
||||
QuestObjective obj = qs.FindObjective<FindHaochiObjective>();
|
||||
katana.Delete();
|
||||
obj6.Complete();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
obj.Complete();
|
||||
return;
|
||||
}
|
||||
qs.AddConversation(
|
||||
new SixthTrialIntroConversation(qs.FindObjective<FifthTrialIntroObjective>()?.StolenTreasure == true)
|
||||
);
|
||||
}
|
||||
|
||||
obj = qs.FindObjective<FirstTrialReturnObjective>();
|
||||
if (qs.FindObjective<SixthTrialReturnObjective>() is { Completed: false } obj7)
|
||||
{
|
||||
obj7.Complete();
|
||||
return;
|
||||
}
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
player.AddToBackpack(new LeatherDo());
|
||||
obj.Complete();
|
||||
return;
|
||||
}
|
||||
if (qs.FindObjective<SeventhTrialReturnObjective>() is { Completed: false } obj8)
|
||||
{
|
||||
BaseWeapon weapon = new Daisho();
|
||||
BaseRunicTool.ApplyAttributesTo(weapon, Utility.Random(1, 3), 10, 30);
|
||||
player.AddToBackpack(weapon);
|
||||
|
||||
obj = qs.FindObjective<SecondTrialReturnObjective>();
|
||||
BaseArmor armor = new LeatherDo();
|
||||
BaseRunicTool.ApplyAttributesTo(armor, Utility.Random(1, 3), 10, 20);
|
||||
player.AddToBackpack(armor);
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
if (((SecondTrialReturnObjective)obj).Dragon)
|
||||
{
|
||||
player.AddToBackpack(new LeatherSuneate());
|
||||
}
|
||||
|
||||
obj.Complete();
|
||||
return;
|
||||
}
|
||||
|
||||
obj = qs.FindObjective<ThirdTrialReturnObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
player.AddToBackpack(new LeatherHiroSode());
|
||||
obj.Complete();
|
||||
return;
|
||||
}
|
||||
|
||||
obj = qs.FindObjective<FourthTrialReturnObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
if (!((FourthTrialReturnObjective)obj).KilledCat)
|
||||
{
|
||||
var cont = GetNewContainer();
|
||||
cont.DropItem(new LeatherHiroSode());
|
||||
cont.DropItem(new JinBaori());
|
||||
player.AddToBackpack(cont);
|
||||
}
|
||||
|
||||
obj.Complete();
|
||||
return;
|
||||
}
|
||||
|
||||
obj = qs.FindObjective<FifthTrialReturnObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
var katana = player.Backpack?.FindItemByType<HaochisKatana>();
|
||||
if (katana == null)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
katana.Delete();
|
||||
obj.Complete();
|
||||
|
||||
obj = qs.FindObjective<FifthTrialIntroObjective>();
|
||||
if (((FifthTrialIntroObjective)obj)?.StolenTreasure == true)
|
||||
{
|
||||
qs.AddConversation(new SixthTrialIntroConversation(true));
|
||||
}
|
||||
else
|
||||
{
|
||||
qs.AddConversation(new SixthTrialIntroConversation(false));
|
||||
}
|
||||
}
|
||||
|
||||
obj = qs.FindObjective<SixthTrialReturnObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
obj.Complete();
|
||||
return;
|
||||
}
|
||||
|
||||
obj = qs.FindObjective<SeventhTrialReturnObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
BaseWeapon weapon = new Daisho();
|
||||
BaseRunicTool.ApplyAttributesTo(weapon, Utility.Random(1, 3), 10, 30);
|
||||
player.AddToBackpack(weapon);
|
||||
|
||||
BaseArmor armor = new LeatherDo();
|
||||
BaseRunicTool.ApplyAttributesTo(armor, Utility.Random(1, 3), 10, 20);
|
||||
player.AddToBackpack(armor);
|
||||
|
||||
obj.Complete();
|
||||
}
|
||||
obj8.Complete();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -49,7 +49,7 @@ public partial class Relnia : BaseQuester
|
|||
|
||||
if (qs is HaochisTrialsQuest)
|
||||
{
|
||||
QuestObjective obj = qs.FindObjective<FourthTrialCatsObjective>();
|
||||
var obj = qs.FindObjective<FourthTrialCatsObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -25,7 +25,7 @@ public class QuestCompleteObjectiveRegion : BaseRegion
|
|||
{
|
||||
if (m is PlayerMobile player && player?.Quest != null && player.Quest.GetType() == Quest)
|
||||
{
|
||||
QuestObjective obj = player.Quest.FindObjective(Objective);
|
||||
var obj = player.Quest.FindObjective(Objective);
|
||||
|
||||
if (obj is { Completed: false })
|
||||
{
|
||||
|
|
|
|||
|
|
@ -1,102 +1,46 @@
|
|||
using System.Collections.Generic;
|
||||
using ModernUO.Serialization;
|
||||
using Server.ContextMenus;
|
||||
using Server.Engines.Plants;
|
||||
using Server.Items;
|
||||
using Server.Mobiles;
|
||||
using Server.Targeting;
|
||||
|
||||
namespace Server.Engines.Quests.Matriarch
|
||||
namespace Server.Engines.Quests.Matriarch;
|
||||
|
||||
[SerializationGenerator(0)]
|
||||
public abstract partial class BaseSolenMatriarch : BaseQuester
|
||||
{
|
||||
public abstract class BaseSolenMatriarch : BaseQuester
|
||||
public BaseSolenMatriarch()
|
||||
{
|
||||
public BaseSolenMatriarch()
|
||||
Body = 0x328;
|
||||
|
||||
if (!RedSolen)
|
||||
{
|
||||
Body = 0x328;
|
||||
|
||||
if (!RedSolen)
|
||||
{
|
||||
Hue = 0x44E;
|
||||
}
|
||||
|
||||
SpeechHue = 0;
|
||||
Hue = 0x44E;
|
||||
}
|
||||
|
||||
public BaseSolenMatriarch(Serial serial) : base(serial)
|
||||
SpeechHue = 0;
|
||||
}
|
||||
|
||||
public abstract bool RedSolen { get; }
|
||||
public override string DefaultName => "the solen matriarch";
|
||||
public override bool DisallowAllMoves => false;
|
||||
|
||||
public override int GetIdleSound() => 0x10D;
|
||||
|
||||
public override bool CanTalkTo(PlayerMobile to) =>
|
||||
SolenMatriarchQuest.IsFriend(to, RedSolen) || to.Quest is SolenMatriarchQuest qs && qs.RedSolen == RedSolen;
|
||||
|
||||
public override void OnTalk(PlayerMobile player, bool contextMenu)
|
||||
{
|
||||
Direction = GetDirectionTo(player);
|
||||
|
||||
if (player.Quest is not SolenMatriarchQuest qs || qs.RedSolen != RedSolen)
|
||||
{
|
||||
}
|
||||
|
||||
public abstract bool RedSolen { get; }
|
||||
public override string DefaultName => "the solen matriarch";
|
||||
public override bool DisallowAllMoves => false;
|
||||
|
||||
public override int GetIdleSound() => 0x10D;
|
||||
|
||||
public override bool CanTalkTo(PlayerMobile to)
|
||||
{
|
||||
if (SolenMatriarchQuest.IsFriend(to, RedSolen))
|
||||
if (SolenMatriarchQuest.IsFriend(player, RedSolen))
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
||||
return to.Quest is SolenMatriarchQuest qs && qs.RedSolen == RedSolen;
|
||||
}
|
||||
|
||||
public override void OnTalk(PlayerMobile player, bool contextMenu)
|
||||
{
|
||||
Direction = GetDirectionTo(player);
|
||||
|
||||
if (player.Quest is SolenMatriarchQuest qs && qs.RedSolen == RedSolen)
|
||||
{
|
||||
if (qs.IsObjectiveInProgress(typeof(KillInfiltratorsObjective)))
|
||||
{
|
||||
qs.AddConversation(new DuringKillInfiltratorsConversation());
|
||||
}
|
||||
else
|
||||
{
|
||||
QuestObjective obj = qs.FindObjective<ReturnAfterKillsObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
obj.Complete();
|
||||
}
|
||||
else if (qs.IsObjectiveInProgress(typeof(GatherWaterObjective)))
|
||||
{
|
||||
qs.AddConversation(new DuringWaterGatheringConversation());
|
||||
}
|
||||
else
|
||||
{
|
||||
obj = qs.FindObjective<ReturnAfterWaterObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
obj.Complete();
|
||||
}
|
||||
else if (qs.IsObjectiveInProgress(typeof(ProcessFungiObjective)))
|
||||
{
|
||||
qs.AddConversation(new DuringFungiProcessConversation());
|
||||
}
|
||||
else
|
||||
{
|
||||
obj = qs.FindObjective<GetRewardObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
if (SolenMatriarchQuest.GiveRewardTo(player))
|
||||
{
|
||||
obj.Complete();
|
||||
}
|
||||
else
|
||||
{
|
||||
qs.AddConversation(new FullBackpackConversation(false));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
else if (SolenMatriarchQuest.IsFriend(player, RedSolen))
|
||||
{
|
||||
QuestSystem newQuest = new SolenMatriarchQuest(player, RedSolen);
|
||||
var newQuest = new SolenMatriarchQuest(player, RedSolen);
|
||||
|
||||
if (player.Quest == null && QuestSystem.CanOfferQuest(player, typeof(SolenMatriarchQuest)))
|
||||
{
|
||||
|
|
@ -107,227 +51,221 @@ namespace Server.Engines.Quests.Matriarch
|
|||
newQuest.AddConversation(new DontOfferConversation(true));
|
||||
}
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
public override bool OnDragDrop(Mobile from, Item dropped)
|
||||
if (qs.IsObjectiveInProgress(typeof(KillInfiltratorsObjective)))
|
||||
{
|
||||
if (from is PlayerMobile player)
|
||||
qs.AddConversation(new DuringKillInfiltratorsConversation());
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.FindObjective<ReturnAfterKillsObjective>() is { Completed: false } obj1)
|
||||
{
|
||||
obj1.Complete();
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.IsObjectiveInProgress(typeof(GatherWaterObjective)))
|
||||
{
|
||||
qs.AddConversation(new DuringWaterGatheringConversation());
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.FindObjective<ReturnAfterWaterObjective>() is { Completed: false } obj2)
|
||||
{
|
||||
obj2.Complete();
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.IsObjectiveInProgress(typeof(ProcessFungiObjective)))
|
||||
{
|
||||
qs.AddConversation(new DuringFungiProcessConversation());
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.FindObjective<GetRewardObjective>() is { Completed: false } obj3)
|
||||
{
|
||||
if (SolenMatriarchQuest.GiveRewardTo(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);
|
||||
obj3.Complete();
|
||||
}
|
||||
else
|
||||
{
|
||||
qs.AddConversation(new FullBackpackConversation(false));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
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 not PlayerMobile player)
|
||||
{
|
||||
return base.OnDragDrop(from, dropped);
|
||||
}
|
||||
|
||||
dropped.Delete();
|
||||
return true;
|
||||
}
|
||||
if (dropped is not Seed)
|
||||
{
|
||||
if (dropped is ZoogiFungus fungus)
|
||||
{
|
||||
OnGivenFungi(player, fungus);
|
||||
|
||||
if (dropped is ZoogiFungus fungus)
|
||||
{
|
||||
OnGivenFungi(player, fungus);
|
||||
|
||||
return fungus.Deleted;
|
||||
}
|
||||
return fungus.Deleted;
|
||||
}
|
||||
|
||||
return base.OnDragDrop(from, dropped);
|
||||
}
|
||||
|
||||
public override void GetContextMenuEntries(Mobile from, List<ContextMenuEntry> list)
|
||||
if (player.Quest is SolenMatriarchQuest qs && qs.RedSolen == RedSolen)
|
||||
{
|
||||
base.GetContextMenuEntries(from, list);
|
||||
SayTo(player, 1054080); // Thank you for that plant seed. Those have such wonderful flavor.
|
||||
}
|
||||
else
|
||||
{
|
||||
var newQuest = new SolenMatriarchQuest(player, RedSolen);
|
||||
|
||||
if (from.Alive)
|
||||
if (player.Quest == null && QuestSystem.CanOfferQuest(player, typeof(SolenMatriarchQuest)))
|
||||
{
|
||||
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));
|
||||
}
|
||||
}
|
||||
}
|
||||
newQuest.SendOffer();
|
||||
}
|
||||
else
|
||||
{
|
||||
newQuest.AddConversation(
|
||||
new DontOfferConversation(SolenMatriarchQuest.IsFriend(player, RedSolen))
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
public void OnGivenFungi(PlayerMobile player, ZoogiFungus fungi)
|
||||
dropped.Delete();
|
||||
return true;
|
||||
}
|
||||
|
||||
public override void GetContextMenuEntries(Mobile from, List<ContextMenuEntry> list)
|
||||
{
|
||||
base.GetContextMenuEntries(from, list);
|
||||
|
||||
if (from.Alive && from is PlayerMobile pm && pm.Quest is SolenMatriarchQuest qs && qs.RedSolen == RedSolen &&
|
||||
qs.IsObjectiveInProgress(typeof(ProcessFungiObjective)))
|
||||
{
|
||||
Direction = GetDirectionTo(player);
|
||||
list.Add(new ProcessZoogiFungusEntry(this, pm));
|
||||
}
|
||||
}
|
||||
|
||||
if (player.Quest is SolenMatriarchQuest qs && qs.RedSolen == RedSolen)
|
||||
{
|
||||
QuestObjective obj = qs.FindObjective<ProcessFungiObjective>();
|
||||
public void OnGivenFungi(PlayerMobile player, ZoogiFungus fungi)
|
||||
{
|
||||
Direction = GetDirectionTo(player);
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
var amount = fungi.Amount / 2;
|
||||
|
||||
if (amount > 100)
|
||||
{
|
||||
amount = 100;
|
||||
}
|
||||
|
||||
if (amount > 0)
|
||||
{
|
||||
if (amount * 2 >= fungi.Amount)
|
||||
{
|
||||
fungi.Delete();
|
||||
}
|
||||
else
|
||||
{
|
||||
fungi.Amount -= amount * 2;
|
||||
}
|
||||
|
||||
var powder = new PowderOfTranslocation(amount);
|
||||
player.AddToBackpack(powder);
|
||||
|
||||
player.SendLocalizedMessage(1054100); // You receive some powder of translocation.
|
||||
|
||||
obj.Complete();
|
||||
}
|
||||
}
|
||||
}
|
||||
if (player.Quest is not SolenMatriarchQuest qs || qs.RedSolen != RedSolen)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
public override void Serialize(IGenericWriter writer)
|
||||
{
|
||||
base.Serialize(writer);
|
||||
var obj = qs.FindObjective<ProcessFungiObjective>();
|
||||
|
||||
writer.WriteEncodedInt(0); // version
|
||||
if (obj?.Completed != false)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
public override void Deserialize(IGenericReader reader)
|
||||
{
|
||||
base.Deserialize(reader);
|
||||
var amount = fungi.Amount / 2;
|
||||
|
||||
var version = reader.ReadEncodedInt();
|
||||
if (amount > 100)
|
||||
{
|
||||
amount = 100;
|
||||
}
|
||||
|
||||
private class ProcessZoogiFungusEntry : ContextMenuEntry
|
||||
if (amount > 0)
|
||||
{
|
||||
private readonly PlayerMobile m_From;
|
||||
private readonly BaseSolenMatriarch m_Matriarch;
|
||||
|
||||
public ProcessZoogiFungusEntry(BaseSolenMatriarch matriarch, PlayerMobile from) : base(6184)
|
||||
if (amount * 2 >= fungi.Amount)
|
||||
{
|
||||
m_Matriarch = matriarch;
|
||||
m_From = from;
|
||||
fungi.Delete();
|
||||
}
|
||||
else
|
||||
{
|
||||
fungi.Amount -= amount * 2;
|
||||
}
|
||||
|
||||
public override void OnClick()
|
||||
{
|
||||
if (m_From.Alive)
|
||||
{
|
||||
m_From.Target = new ProcessFungiTarget(m_Matriarch, m_From);
|
||||
}
|
||||
}
|
||||
var powder = new PowderOfTranslocation(amount);
|
||||
player.AddToBackpack(powder);
|
||||
|
||||
player.SendLocalizedMessage(1054100); // You receive some powder of translocation.
|
||||
|
||||
obj.Complete();
|
||||
}
|
||||
}
|
||||
|
||||
private class ProcessZoogiFungusEntry : ContextMenuEntry
|
||||
{
|
||||
private readonly PlayerMobile _from;
|
||||
private readonly BaseSolenMatriarch _matriarch;
|
||||
|
||||
public ProcessZoogiFungusEntry(BaseSolenMatriarch matriarch, PlayerMobile from) : base(6184)
|
||||
{
|
||||
_matriarch = matriarch;
|
||||
_from = from;
|
||||
}
|
||||
|
||||
private class ProcessFungiTarget : Target
|
||||
public override void OnClick()
|
||||
{
|
||||
private readonly PlayerMobile m_From;
|
||||
private readonly BaseSolenMatriarch m_Matriarch;
|
||||
|
||||
public ProcessFungiTarget(BaseSolenMatriarch matriarch, PlayerMobile from) : base(-1, false, TargetFlags.None)
|
||||
if (_from.Alive)
|
||||
{
|
||||
m_Matriarch = matriarch;
|
||||
m_From = from;
|
||||
}
|
||||
|
||||
protected override void OnTargetCancel(Mobile from, TargetCancelType cancelType)
|
||||
{
|
||||
from.SendLocalizedMessage(1042021, "", 0x59); // Cancelled.
|
||||
}
|
||||
|
||||
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.
|
||||
}
|
||||
}
|
||||
_from.Target = new ProcessFungiTarget(_matriarch, _from);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public class RedSolenMatriarch : BaseSolenMatriarch
|
||||
private class ProcessFungiTarget : Target
|
||||
{
|
||||
[Constructible]
|
||||
public RedSolenMatriarch()
|
||||
private readonly PlayerMobile _from;
|
||||
private readonly BaseSolenMatriarch _matriarch;
|
||||
|
||||
public ProcessFungiTarget(BaseSolenMatriarch matriarch, PlayerMobile from) : base(-1, false, TargetFlags.None)
|
||||
{
|
||||
_matriarch = matriarch;
|
||||
_from = from;
|
||||
}
|
||||
|
||||
public RedSolenMatriarch(Serial serial) : base(serial)
|
||||
protected override void OnTargetCancel(Mobile from, TargetCancelType cancelType)
|
||||
{
|
||||
from.SendLocalizedMessage(1042021, "", 0x59); // Cancelled.
|
||||
}
|
||||
|
||||
public override bool RedSolen => true;
|
||||
|
||||
public override void Serialize(IGenericWriter writer)
|
||||
protected override void OnTarget(Mobile from, object targeted)
|
||||
{
|
||||
base.Serialize(writer);
|
||||
|
||||
writer.WriteEncodedInt(0); // version
|
||||
}
|
||||
|
||||
public override void Deserialize(IGenericReader reader)
|
||||
{
|
||||
base.Deserialize(reader);
|
||||
|
||||
var version = reader.ReadEncodedInt();
|
||||
}
|
||||
}
|
||||
|
||||
public class BlackSolenMatriarch : BaseSolenMatriarch
|
||||
{
|
||||
[Constructible]
|
||||
public BlackSolenMatriarch()
|
||||
{
|
||||
}
|
||||
|
||||
public BlackSolenMatriarch(Serial serial) : base(serial)
|
||||
{
|
||||
}
|
||||
|
||||
public override bool RedSolen => false;
|
||||
|
||||
public override void Serialize(IGenericWriter writer)
|
||||
{
|
||||
base.Serialize(writer);
|
||||
|
||||
writer.WriteEncodedInt(0); // version
|
||||
}
|
||||
|
||||
public override void Deserialize(IGenericReader reader)
|
||||
{
|
||||
base.Deserialize(reader);
|
||||
|
||||
var version = reader.ReadEncodedInt();
|
||||
if (targeted is ZoogiFungus fungus)
|
||||
{
|
||||
if (fungus.IsChildOf(_from.Backpack))
|
||||
{
|
||||
_matriarch.OnGivenFungi(_from, fungus);
|
||||
}
|
||||
else
|
||||
{
|
||||
_from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it.
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
[SerializationGenerator(0)]
|
||||
public partial class RedSolenMatriarch : BaseSolenMatriarch
|
||||
{
|
||||
[Constructible]
|
||||
public RedSolenMatriarch()
|
||||
{
|
||||
}
|
||||
|
||||
public override bool RedSolen => true;
|
||||
}
|
||||
|
||||
[SerializationGenerator(0)]
|
||||
public partial class BlackSolenMatriarch : BaseSolenMatriarch
|
||||
{
|
||||
[Constructible]
|
||||
public BlackSolenMatriarch()
|
||||
{
|
||||
}
|
||||
|
||||
public override bool RedSolen => false;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,154 +1,137 @@
|
|||
using ModernUO.Serialization;
|
||||
using Server.Engines.Plants;
|
||||
using Server.Items;
|
||||
using Server.Mobiles;
|
||||
|
||||
namespace Server.Engines.Quests.Naturalist
|
||||
namespace Server.Engines.Quests.Naturalist;
|
||||
|
||||
[SerializationGenerator(0)]
|
||||
public partial class Naturalist : BaseQuester
|
||||
{
|
||||
public class Naturalist : BaseQuester
|
||||
[Constructible]
|
||||
public Naturalist() : base("the Naturalist")
|
||||
{
|
||||
[Constructible]
|
||||
public Naturalist() : base("the Naturalist")
|
||||
}
|
||||
|
||||
public override void InitBody()
|
||||
{
|
||||
InitStats(100, 100, 25);
|
||||
|
||||
Hue = Race.Human.RandomSkinHue();
|
||||
|
||||
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);
|
||||
}
|
||||
|
||||
public override void OnTalk(PlayerMobile player, bool contextMenu)
|
||||
{
|
||||
if (player.Quest is StudyOfSolenQuest qs && qs.Naturalist == this)
|
||||
{
|
||||
}
|
||||
|
||||
public Naturalist(Serial serial) : base(serial)
|
||||
{
|
||||
}
|
||||
|
||||
public override void InitBody()
|
||||
{
|
||||
InitStats(100, 100, 25);
|
||||
|
||||
Hue = Race.Human.RandomSkinHue();
|
||||
|
||||
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);
|
||||
}
|
||||
|
||||
public override void OnTalk(PlayerMobile player, bool contextMenu)
|
||||
{
|
||||
if (player.Quest is StudyOfSolenQuest qs && qs.Naturalist == this)
|
||||
var study = qs.FindObjective<StudyNestsObjective>();
|
||||
if (study == null)
|
||||
{
|
||||
var study = qs.FindObjective<StudyNestsObjective>();
|
||||
if (study == null)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
if (!study.Completed)
|
||||
{
|
||||
PlaySound(0x41F);
|
||||
qs.AddConversation(new NaturalistDuringStudyConversation());
|
||||
return;
|
||||
}
|
||||
|
||||
QuestObjective obj = qs.FindObjective<ReturnToNaturalistObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
Seed reward;
|
||||
|
||||
var type = Utility.Random(17) switch
|
||||
{
|
||||
0 => PlantType.CampionFlowers,
|
||||
1 => PlantType.Poppies,
|
||||
2 => PlantType.Snowdrops,
|
||||
3 => PlantType.Bulrushes,
|
||||
4 => PlantType.Lilies,
|
||||
5 => PlantType.PampasGrass,
|
||||
6 => PlantType.Rushes,
|
||||
7 => PlantType.ElephantEarPlant,
|
||||
8 => PlantType.Fern,
|
||||
9 => PlantType.PonytailPalm,
|
||||
10 => PlantType.SmallPalm,
|
||||
11 => PlantType.CenturyPlant,
|
||||
12 => PlantType.WaterPlant,
|
||||
13 => PlantType.SnakePlant,
|
||||
14 => PlantType.PricklyPearCactus,
|
||||
15 => PlantType.BarrelCactus,
|
||||
_ => PlantType.TribarrelCactus
|
||||
};
|
||||
|
||||
if (study.StudiedSpecialNest)
|
||||
{
|
||||
reward = new Seed(type, PlantHue.FireRed);
|
||||
}
|
||||
else
|
||||
{
|
||||
var hue = Utility.Random(3) switch
|
||||
{
|
||||
0 => PlantHue.Pink,
|
||||
1 => PlantHue.Magenta,
|
||||
_ => PlantHue.Aqua
|
||||
};
|
||||
|
||||
reward = new Seed(type, hue);
|
||||
}
|
||||
|
||||
if (player.PlaceInBackpack(reward))
|
||||
{
|
||||
obj.Complete();
|
||||
|
||||
PlaySound(0x449);
|
||||
PlaySound(0x41B);
|
||||
|
||||
if (study.StudiedSpecialNest)
|
||||
{
|
||||
qs.AddConversation(new SpecialEndConversation());
|
||||
}
|
||||
else
|
||||
{
|
||||
qs.AddConversation(new EndConversation());
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
reward.Delete();
|
||||
|
||||
qs.AddConversation(new FullBackpackConversation());
|
||||
}
|
||||
}
|
||||
return;
|
||||
}
|
||||
else
|
||||
{
|
||||
QuestSystem newQuest = new StudyOfSolenQuest(player, this);
|
||||
|
||||
if (player.Quest == null && QuestSystem.CanOfferQuest(player, typeof(StudyOfSolenQuest)))
|
||||
if (!study.Completed)
|
||||
{
|
||||
PlaySound(0x41F);
|
||||
qs.AddConversation(new NaturalistDuringStudyConversation());
|
||||
return;
|
||||
}
|
||||
|
||||
var obj = qs.FindObjective<ReturnToNaturalistObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
Seed reward;
|
||||
|
||||
var type = Utility.Random(17) switch
|
||||
{
|
||||
PlaySound(0x42F);
|
||||
newQuest.SendOffer();
|
||||
0 => PlantType.CampionFlowers,
|
||||
1 => PlantType.Poppies,
|
||||
2 => PlantType.Snowdrops,
|
||||
3 => PlantType.Bulrushes,
|
||||
4 => PlantType.Lilies,
|
||||
5 => PlantType.PampasGrass,
|
||||
6 => PlantType.Rushes,
|
||||
7 => PlantType.ElephantEarPlant,
|
||||
8 => PlantType.Fern,
|
||||
9 => PlantType.PonytailPalm,
|
||||
10 => PlantType.SmallPalm,
|
||||
11 => PlantType.CenturyPlant,
|
||||
12 => PlantType.WaterPlant,
|
||||
13 => PlantType.SnakePlant,
|
||||
14 => PlantType.PricklyPearCactus,
|
||||
15 => PlantType.BarrelCactus,
|
||||
_ => PlantType.TribarrelCactus
|
||||
};
|
||||
|
||||
if (study.StudiedSpecialNest)
|
||||
{
|
||||
reward = new Seed(type, PlantHue.FireRed);
|
||||
}
|
||||
else
|
||||
{
|
||||
PlaySound(0x448);
|
||||
newQuest.AddConversation(new DontOfferConversation());
|
||||
var hue = Utility.Random(3) switch
|
||||
{
|
||||
0 => PlantHue.Pink,
|
||||
1 => PlantHue.Magenta,
|
||||
_ => PlantHue.Aqua
|
||||
};
|
||||
|
||||
reward = new Seed(type, hue);
|
||||
}
|
||||
|
||||
if (player.PlaceInBackpack(reward))
|
||||
{
|
||||
obj.Complete();
|
||||
|
||||
PlaySound(0x449);
|
||||
PlaySound(0x41B);
|
||||
|
||||
if (study.StudiedSpecialNest)
|
||||
{
|
||||
qs.AddConversation(new SpecialEndConversation());
|
||||
}
|
||||
else
|
||||
{
|
||||
qs.AddConversation(new EndConversation());
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
reward.Delete();
|
||||
|
||||
qs.AddConversation(new FullBackpackConversation());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public override void Serialize(IGenericWriter writer)
|
||||
else
|
||||
{
|
||||
base.Serialize(writer);
|
||||
var newQuest = new StudyOfSolenQuest(player, this);
|
||||
|
||||
writer.WriteEncodedInt(0); // version
|
||||
}
|
||||
|
||||
public override void Deserialize(IGenericReader reader)
|
||||
{
|
||||
base.Deserialize(reader);
|
||||
|
||||
var version = reader.ReadEncodedInt();
|
||||
if (player.Quest == null && QuestSystem.CanOfferQuest(player, typeof(StudyOfSolenQuest)))
|
||||
{
|
||||
PlaySound(0x42F);
|
||||
newQuest.SendOffer();
|
||||
}
|
||||
else
|
||||
{
|
||||
PlaySound(0x448);
|
||||
newQuest.AddConversation(new DontOfferConversation());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,150 +1,120 @@
|
|||
using ModernUO.Serialization;
|
||||
using Server.Items;
|
||||
using Server.Mobiles;
|
||||
|
||||
namespace Server.Engines.Quests.Zento
|
||||
namespace Server.Engines.Quests.Zento;
|
||||
|
||||
[SerializationGenerator(0)]
|
||||
public partial class AnsellaGryen : BaseQuester
|
||||
{
|
||||
public class AnsellaGryen : BaseQuester
|
||||
[Constructible]
|
||||
public AnsellaGryen()
|
||||
{
|
||||
[Constructible]
|
||||
public AnsellaGryen()
|
||||
}
|
||||
|
||||
public override string DefaultName => "Ansella Gryen";
|
||||
|
||||
public override void InitBody()
|
||||
{
|
||||
InitStats(100, 100, 25);
|
||||
|
||||
Hue = 0x83EA;
|
||||
|
||||
Female = true;
|
||||
Body = 0x191;
|
||||
}
|
||||
|
||||
public override void InitOutfit()
|
||||
{
|
||||
HairItemID = 0x203B;
|
||||
HairHue = 0x1BB;
|
||||
|
||||
AddItem(new SamuraiTabi(0x8FD));
|
||||
AddItem(new FemaleKimono(0x4B6));
|
||||
AddItem(new Obi(0x526));
|
||||
|
||||
AddItem(new GoldBracelet());
|
||||
}
|
||||
|
||||
public override int GetAutoTalkRange(PlayerMobile m) => m.Quest == null ? 3 : -1;
|
||||
|
||||
public override void OnTalk(PlayerMobile player, bool contextMenu)
|
||||
{
|
||||
var qs = player.Quest;
|
||||
|
||||
if (qs is TerribleHatchlingsQuest)
|
||||
{
|
||||
}
|
||||
|
||||
public AnsellaGryen(Serial serial) : base(serial)
|
||||
{
|
||||
}
|
||||
|
||||
public override string DefaultName => "Ansella Gryen";
|
||||
|
||||
public override void InitBody()
|
||||
{
|
||||
InitStats(100, 100, 25);
|
||||
|
||||
Hue = 0x83EA;
|
||||
|
||||
Female = true;
|
||||
Body = 0x191;
|
||||
}
|
||||
|
||||
public override void InitOutfit()
|
||||
{
|
||||
HairItemID = 0x203B;
|
||||
HairHue = 0x1BB;
|
||||
|
||||
AddItem(new SamuraiTabi(0x8FD));
|
||||
AddItem(new FemaleKimono(0x4B6));
|
||||
AddItem(new Obi(0x526));
|
||||
|
||||
AddItem(new GoldBracelet());
|
||||
}
|
||||
|
||||
public override int GetAutoTalkRange(PlayerMobile m)
|
||||
{
|
||||
if (m.Quest == null)
|
||||
if (qs.IsObjectiveInProgress(typeof(FirstKillObjective)))
|
||||
{
|
||||
return 3;
|
||||
qs.AddConversation(new DirectionConversation());
|
||||
return;
|
||||
}
|
||||
|
||||
return -1;
|
||||
}
|
||||
|
||||
public override void OnTalk(PlayerMobile player, bool contextMenu)
|
||||
{
|
||||
var qs = player.Quest;
|
||||
|
||||
if (qs is TerribleHatchlingsQuest)
|
||||
if (qs.IsObjectiveInProgress(typeof(SecondKillObjective))
|
||||
|| qs.IsObjectiveInProgress(typeof(ThirdKillObjective)))
|
||||
{
|
||||
if (qs.IsObjectiveInProgress(typeof(FirstKillObjective)))
|
||||
qs.AddConversation(new TakeCareConversation());
|
||||
return;
|
||||
}
|
||||
|
||||
var obj = qs.FindObjective<ReturnObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
var cont = GetNewContainer();
|
||||
|
||||
cont.DropItem(new Gold(Utility.RandomMinMax(100, 200)));
|
||||
|
||||
if (Utility.RandomBool())
|
||||
{
|
||||
qs.AddConversation(new DirectionConversation());
|
||||
if (Loot.Construct(Loot.SEWeaponTypes) is BaseWeapon weapon)
|
||||
{
|
||||
BaseRunicTool.ApplyAttributesTo(weapon, 3, 10, 30);
|
||||
cont.DropItem(weapon);
|
||||
}
|
||||
}
|
||||
else if (qs.IsObjectiveInProgress(typeof(SecondKillObjective))
|
||||
|| qs.IsObjectiveInProgress(typeof(ThirdKillObjective)))
|
||||
else if (Loot.Construct(Loot.SEArmorTypes) is BaseArmor armor)
|
||||
{
|
||||
qs.AddConversation(new TakeCareConversation());
|
||||
BaseRunicTool.ApplyAttributesTo(armor, 1, 10, 20);
|
||||
cont.DropItem(armor);
|
||||
}
|
||||
|
||||
if (player.PlaceInBackpack(cont))
|
||||
{
|
||||
obj.Complete();
|
||||
}
|
||||
else
|
||||
{
|
||||
QuestObjective obj = qs.FindObjective<ReturnObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
var cont = GetNewContainer();
|
||||
|
||||
cont.DropItem(new Gold(Utility.RandomMinMax(100, 200)));
|
||||
|
||||
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 (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.
|
||||
}
|
||||
}
|
||||
cont.Delete();
|
||||
// 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.
|
||||
player.SendLocalizedMessage(1046260);
|
||||
}
|
||||
}
|
||||
else
|
||||
}
|
||||
else
|
||||
{
|
||||
var newQuest = new TerribleHatchlingsQuest(player);
|
||||
|
||||
if (qs != null)
|
||||
{
|
||||
var newQuest = new TerribleHatchlingsQuest(player);
|
||||
|
||||
if (qs != null)
|
||||
if (contextMenu)
|
||||
{
|
||||
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 var inRestartPeriod))
|
||||
{
|
||||
newQuest.SendOffer();
|
||||
}
|
||||
else if (inRestartPeriod && contextMenu)
|
||||
{
|
||||
SayTo(player, 1049357); // I have nothing more for you at this time.
|
||||
// Before you can help me with the Terrible Hatchlings, you'll need to finish the quest you've already taken!
|
||||
SayTo(player, 1063322);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public override void Serialize(IGenericWriter writer)
|
||||
{
|
||||
base.Serialize(writer);
|
||||
|
||||
writer.WriteEncodedInt(0); // version
|
||||
}
|
||||
|
||||
public override void Deserialize(IGenericReader reader)
|
||||
{
|
||||
base.Deserialize(reader);
|
||||
|
||||
var version = reader.ReadEncodedInt();
|
||||
}
|
||||
|
||||
public override void TurnToTokuno()
|
||||
{
|
||||
else if (QuestSystem.CanOfferQuest(player, typeof(TerribleHatchlingsQuest), out var inRestartPeriod))
|
||||
{
|
||||
newQuest.SendOffer();
|
||||
}
|
||||
else if (inRestartPeriod && contextMenu)
|
||||
{
|
||||
SayTo(player, 1049357); // I have nothing more for you at this time.
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public override void TurnToTokuno()
|
||||
{
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -84,7 +84,7 @@ public partial class Victoria : BaseQuester
|
|||
return base.OnDragDrop(from, dropped);
|
||||
}
|
||||
|
||||
QuestObjective obj = qs.FindObjective<CollectBonesObjective>();
|
||||
var obj = qs.FindObjective<CollectBonesObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -82,7 +82,7 @@ namespace Server.Engines.Quests.Doom
|
|||
{
|
||||
base.Cancel();
|
||||
|
||||
QuestObjective obj = FindObjective<CollectBonesObjective>();
|
||||
var obj = FindObjective<CollectBonesObjective>();
|
||||
|
||||
if (obj?.CurProgress > 0)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -1,177 +1,134 @@
|
|||
using ModernUO.Serialization;
|
||||
using Server.Items;
|
||||
|
||||
namespace Server.Engines.Quests.Haven
|
||||
namespace Server.Engines.Quests.Haven;
|
||||
|
||||
public enum CannonDirection
|
||||
{
|
||||
public enum CannonDirection
|
||||
North,
|
||||
East,
|
||||
South,
|
||||
West
|
||||
}
|
||||
|
||||
[SerializationGenerator(0, false)]
|
||||
public partial class Cannon : BaseAddon
|
||||
{
|
||||
[SerializableField(0, setter: "private")]
|
||||
[SerializedCommandProperty(AccessLevel.GameMaster)]
|
||||
private CannonDirection _cannonDirection;
|
||||
|
||||
[SerializableField(1)]
|
||||
[SerializedCommandProperty(AccessLevel.GameMaster)]
|
||||
private MilitiaCanoneer _canoneer;
|
||||
|
||||
[Constructible]
|
||||
public Cannon(CannonDirection direction)
|
||||
{
|
||||
North,
|
||||
East,
|
||||
South,
|
||||
West
|
||||
}
|
||||
CannonDirection = direction;
|
||||
|
||||
public class Cannon : BaseAddon
|
||||
{
|
||||
[Constructible]
|
||||
public Cannon(CannonDirection direction)
|
||||
switch (direction)
|
||||
{
|
||||
CannonDirection = direction;
|
||||
|
||||
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.East:
|
||||
{
|
||||
AddComponent(new CannonComponent(0xE96), 0, 0, 0);
|
||||
AddComponent(new CannonComponent(0xE95), -1, 0, 0);
|
||||
AddComponent(new CannonComponent(0xE94), -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;
|
||||
}
|
||||
default:
|
||||
{
|
||||
AddComponent(new CannonComponent(0xE8E), 0, 0, 0);
|
||||
AddComponent(new CannonComponent(0xE8F), 1, 0, 0);
|
||||
AddComponent(new CannonComponent(0xE90), 2, 0, 0);
|
||||
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public Cannon(Serial serial) : base(serial)
|
||||
{
|
||||
}
|
||||
|
||||
[CommandProperty(AccessLevel.GameMaster)]
|
||||
public CannonDirection CannonDirection { get; private set; }
|
||||
|
||||
[CommandProperty(AccessLevel.GameMaster)]
|
||||
public MilitiaCanoneer Canoneer { get; set; }
|
||||
|
||||
public override bool HandlesOnMovement => Canoneer?.Deleted == false && Canoneer.Active;
|
||||
|
||||
public void DoFireEffect(Point3D target)
|
||||
{
|
||||
var from = CannonDirection switch
|
||||
{
|
||||
CannonDirection.North => new Point3D(X, Y - 1, Z),
|
||||
CannonDirection.East => new Point3D(X + 1, Y, Z),
|
||||
CannonDirection.South => new Point3D(X, Y + 1, Z),
|
||||
_ => new Point3D(X - 1, Y, Z)
|
||||
};
|
||||
|
||||
Effects.SendLocationEffect(from, Map, 0x36B0, 16, 1);
|
||||
Effects.PlaySound(from, Map, 0x11D);
|
||||
|
||||
Effects.SendLocationEffect(target, Map, 0x36B0, 16, 1);
|
||||
Effects.PlaySound(target, Map, 0x11D);
|
||||
}
|
||||
|
||||
public void Fire(Mobile from, Mobile target)
|
||||
{
|
||||
DoFireEffect(target.Location);
|
||||
|
||||
target.Damage(9999, from);
|
||||
}
|
||||
|
||||
public override void OnMovement(Mobile m, Point3D oldLocation)
|
||||
{
|
||||
if (!(Canoneer?.Deleted == false && Canoneer.Active))
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
var canFire = CannonDirection switch
|
||||
{
|
||||
CannonDirection.North => m.X >= X - 7 && m.X <= X + 7 && m.Y == Y - 7 && oldLocation.Y < Y - 7,
|
||||
CannonDirection.East => m.Y >= Y - 7 && m.Y <= Y + 7 && m.X == X + 7 && oldLocation.X > X + 7,
|
||||
CannonDirection.South => m.X >= X - 7 && m.X <= X + 7 && m.Y == Y + 7 && oldLocation.Y > Y + 7,
|
||||
_ => m.Y >= Y - 7 && m.Y <= Y + 7 && m.X == X - 7 && oldLocation.X < X - 7
|
||||
};
|
||||
|
||||
if (canFire && Canoneer.WillFire(this, m))
|
||||
{
|
||||
Fire(Canoneer, m);
|
||||
}
|
||||
}
|
||||
|
||||
public override void Serialize(IGenericWriter writer)
|
||||
{
|
||||
if (Canoneer?.Deleted == true)
|
||||
{
|
||||
Canoneer = null;
|
||||
}
|
||||
|
||||
base.Serialize(writer);
|
||||
|
||||
writer.Write(0); // version
|
||||
|
||||
writer.WriteEncodedInt((int)CannonDirection);
|
||||
writer.Write(Canoneer);
|
||||
}
|
||||
|
||||
public override void Deserialize(IGenericReader reader)
|
||||
{
|
||||
base.Deserialize(reader);
|
||||
|
||||
var version = reader.ReadInt();
|
||||
|
||||
CannonDirection = (CannonDirection)reader.ReadEncodedInt();
|
||||
Canoneer = (MilitiaCanoneer)reader.ReadEntity<Mobile>();
|
||||
}
|
||||
}
|
||||
|
||||
public class CannonComponent : AddonComponent
|
||||
{
|
||||
public CannonComponent(int itemID) : base(itemID)
|
||||
{
|
||||
}
|
||||
|
||||
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)
|
||||
case CannonDirection.North:
|
||||
{
|
||||
cannon.Canoneer = value;
|
||||
AddComponent(new CannonComponent(0xE8D), 0, 0, 0);
|
||||
AddComponent(new CannonComponent(0xE8C), 0, 1, 0);
|
||||
AddComponent(new CannonComponent(0xE8B), 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;
|
||||
}
|
||||
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;
|
||||
}
|
||||
default:
|
||||
{
|
||||
AddComponent(new CannonComponent(0xE8E), 0, 0, 0);
|
||||
AddComponent(new CannonComponent(0xE8F), 1, 0, 0);
|
||||
AddComponent(new CannonComponent(0xE90), 2, 0, 0);
|
||||
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public override bool HandlesOnMovement => _canoneer?.Deleted == false && _canoneer.Active;
|
||||
|
||||
public void DoFireEffect(Point3D target)
|
||||
{
|
||||
var from = _cannonDirection switch
|
||||
{
|
||||
CannonDirection.North => new Point3D(X, Y - 1, Z),
|
||||
CannonDirection.East => new Point3D(X + 1, Y, Z),
|
||||
CannonDirection.South => new Point3D(X, Y + 1, Z),
|
||||
_ => new Point3D(X - 1, Y, Z)
|
||||
};
|
||||
|
||||
Effects.SendLocationEffect(from, Map, 0x36B0, 16, 1);
|
||||
Effects.PlaySound(from, Map, 0x11D);
|
||||
|
||||
Effects.SendLocationEffect(target, Map, 0x36B0, 16, 1);
|
||||
Effects.PlaySound(target, Map, 0x11D);
|
||||
}
|
||||
|
||||
public void Fire(Mobile from, Mobile target)
|
||||
{
|
||||
DoFireEffect(target.Location);
|
||||
|
||||
target.Damage(9999, from);
|
||||
}
|
||||
|
||||
public override void OnMovement(Mobile m, Point3D oldLocation)
|
||||
{
|
||||
if (!(Canoneer?.Deleted == false && Canoneer.Active))
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
public override void Serialize(IGenericWriter writer)
|
||||
var canFire = CannonDirection switch
|
||||
{
|
||||
base.Serialize(writer);
|
||||
CannonDirection.North => m.X >= X - 7 && m.X <= X + 7 && m.Y == Y - 7 && oldLocation.Y < Y - 7,
|
||||
CannonDirection.East => m.Y >= Y - 7 && m.Y <= Y + 7 && m.X == X + 7 && oldLocation.X > X + 7,
|
||||
CannonDirection.South => m.X >= X - 7 && m.X <= X + 7 && m.Y == Y + 7 && oldLocation.Y > Y + 7,
|
||||
_ => m.Y >= Y - 7 && m.Y <= Y + 7 && m.X == X - 7 && oldLocation.X < X - 7
|
||||
};
|
||||
|
||||
writer.Write(0); // version
|
||||
}
|
||||
|
||||
public override void Deserialize(IGenericReader reader)
|
||||
if (canFire && Canoneer.WillFire(this, m))
|
||||
{
|
||||
base.Deserialize(reader);
|
||||
|
||||
var version = reader.ReadInt();
|
||||
Fire(Canoneer, m);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
[SerializationGenerator(0, false)]
|
||||
public partial class CannonComponent : AddonComponent
|
||||
{
|
||||
public CannonComponent(int itemID) : base(itemID)
|
||||
{
|
||||
}
|
||||
|
||||
[CommandProperty(AccessLevel.GameMaster)]
|
||||
public MilitiaCanoneer Canoneer
|
||||
{
|
||||
get => (Addon as Cannon)?.Canoneer;
|
||||
set
|
||||
{
|
||||
if (Addon is Cannon cannon)
|
||||
{
|
||||
cannon.Canoneer = value;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,74 +1,56 @@
|
|||
using ModernUO.Serialization;
|
||||
using Server.Items;
|
||||
using Server.Mobiles;
|
||||
|
||||
namespace Server.Engines.Quests.Haven
|
||||
namespace Server.Engines.Quests.Haven;
|
||||
|
||||
[SerializationGenerator(0, false)]
|
||||
public partial class DaemonBloodChest : MetalChest
|
||||
{
|
||||
public class DaemonBloodChest : MetalChest
|
||||
[Constructible]
|
||||
public DaemonBloodChest() => Movable = false;
|
||||
|
||||
public override void OnDoubleClick(Mobile from)
|
||||
{
|
||||
[Constructible]
|
||||
public DaemonBloodChest() => Movable = false;
|
||||
|
||||
public DaemonBloodChest(Serial serial) : base(serial)
|
||||
if (from is not PlayerMobile player || !player.InRange(GetWorldLocation(), 2))
|
||||
{
|
||||
}
|
||||
|
||||
public override void OnDoubleClick(Mobile from)
|
||||
{
|
||||
if (from is PlayerMobile player && player.InRange(GetWorldLocation(), 2))
|
||||
{
|
||||
var qs = player.Quest;
|
||||
|
||||
if (qs is UzeraanTurmoilQuest)
|
||||
{
|
||||
QuestObjective obj = qs.FindObjective<GetDaemonBloodObjective>();
|
||||
|
||||
if (obj?.Completed == false || 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 (obj?.Completed == false)
|
||||
{
|
||||
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;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
base.OnDoubleClick(from);
|
||||
return;
|
||||
}
|
||||
|
||||
public override void Serialize(IGenericWriter writer)
|
||||
{
|
||||
base.Serialize(writer);
|
||||
var qs = player.Quest;
|
||||
|
||||
writer.Write(0); // version
|
||||
if (qs is not UzeraanTurmoilQuest)
|
||||
{
|
||||
base.OnDoubleClick(from);
|
||||
return;
|
||||
}
|
||||
|
||||
public override void Deserialize(IGenericReader reader)
|
||||
{
|
||||
base.Deserialize(reader);
|
||||
var obj = qs.FindObjective<GetDaemonBloodObjective>();
|
||||
|
||||
var version = reader.ReadInt();
|
||||
if (obj?.Completed != false && !UzeraanTurmoilQuest.HasLostDaemonBlood(player))
|
||||
{
|
||||
base.OnDoubleClick(from);
|
||||
return;
|
||||
}
|
||||
|
||||
Item vial = new QuestDaemonBlood();
|
||||
|
||||
if (player.PlaceInBackpack(vial))
|
||||
{
|
||||
// You take a vial of blood from the chest and put it in your pack.
|
||||
player.SendLocalizedMessage(1049331, "", 0x22);
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
obj.Complete();
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
// 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.
|
||||
player.SendLocalizedMessage(1049338, "", 0x22);
|
||||
vial.Delete();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,30 +1,13 @@
|
|||
using ModernUO.Serialization;
|
||||
using Server.Mobiles;
|
||||
|
||||
namespace Server.Engines.Quests.Haven
|
||||
namespace Server.Engines.Quests.Haven;
|
||||
|
||||
[SerializationGenerator(0, false)]
|
||||
public partial class QuestDaemonBlood : QuestItem
|
||||
{
|
||||
public class QuestDaemonBlood : QuestItem
|
||||
{
|
||||
[Constructible]
|
||||
public QuestDaemonBlood() : base(0xF7D) => Weight = 1.0;
|
||||
[Constructible]
|
||||
public QuestDaemonBlood() : base(0xF7D) => Weight = 1.0;
|
||||
|
||||
public QuestDaemonBlood(Serial serial) : base(serial)
|
||||
{
|
||||
}
|
||||
|
||||
public override bool CanDrop(PlayerMobile player) => player.Quest is not UzeraanTurmoilQuest;
|
||||
|
||||
public override void Serialize(IGenericWriter writer)
|
||||
{
|
||||
base.Serialize(writer);
|
||||
|
||||
writer.Write(0); // version
|
||||
}
|
||||
|
||||
public override void Deserialize(IGenericReader reader)
|
||||
{
|
||||
base.Deserialize(reader);
|
||||
|
||||
var version = reader.ReadInt();
|
||||
}
|
||||
}
|
||||
public override bool CanDrop(PlayerMobile player) => player.Quest is not UzeraanTurmoilQuest;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,30 +1,13 @@
|
|||
using ModernUO.Serialization;
|
||||
using Server.Mobiles;
|
||||
|
||||
namespace Server.Engines.Quests.Haven
|
||||
namespace Server.Engines.Quests.Haven;
|
||||
|
||||
[SerializationGenerator(0, false)]
|
||||
public partial class QuestDaemonBone : QuestItem
|
||||
{
|
||||
public class QuestDaemonBone : QuestItem
|
||||
{
|
||||
[Constructible]
|
||||
public QuestDaemonBone() : base(0xF80) => Weight = 1.0;
|
||||
[Constructible]
|
||||
public QuestDaemonBone() : base(0xF80) => Weight = 1.0;
|
||||
|
||||
public QuestDaemonBone(Serial serial) : base(serial)
|
||||
{
|
||||
}
|
||||
|
||||
public override bool CanDrop(PlayerMobile player) => player.Quest is not UzeraanTurmoilQuest;
|
||||
|
||||
public override void Serialize(IGenericWriter writer)
|
||||
{
|
||||
base.Serialize(writer);
|
||||
|
||||
writer.Write(0); // version
|
||||
}
|
||||
|
||||
public override void Deserialize(IGenericReader reader)
|
||||
{
|
||||
base.Deserialize(reader);
|
||||
|
||||
var version = reader.ReadInt();
|
||||
}
|
||||
}
|
||||
public override bool CanDrop(PlayerMobile player) => player.Quest is not UzeraanTurmoilQuest;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,30 +1,13 @@
|
|||
using ModernUO.Serialization;
|
||||
using Server.Mobiles;
|
||||
|
||||
namespace Server.Engines.Quests.Haven
|
||||
namespace Server.Engines.Quests.Haven;
|
||||
|
||||
[SerializationGenerator(0, false)]
|
||||
public partial class QuestFertileDirt : QuestItem
|
||||
{
|
||||
public class QuestFertileDirt : QuestItem
|
||||
{
|
||||
[Constructible]
|
||||
public QuestFertileDirt() : base(0xF81) => Weight = 1.0;
|
||||
[Constructible]
|
||||
public QuestFertileDirt() : base(0xF81) => Weight = 1.0;
|
||||
|
||||
public QuestFertileDirt(Serial serial) : base(serial)
|
||||
{
|
||||
}
|
||||
|
||||
public override bool CanDrop(PlayerMobile player) => player.Quest is not UzeraanTurmoilQuest;
|
||||
|
||||
public override void Serialize(IGenericWriter writer)
|
||||
{
|
||||
base.Serialize(writer);
|
||||
|
||||
writer.Write(0); // version
|
||||
}
|
||||
|
||||
public override void Deserialize(IGenericReader reader)
|
||||
{
|
||||
base.Deserialize(reader);
|
||||
|
||||
var version = reader.ReadInt();
|
||||
}
|
||||
}
|
||||
public override bool CanDrop(PlayerMobile player) => player.Quest is not UzeraanTurmoilQuest;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,211 +1,156 @@
|
|||
using System.Collections.Generic;
|
||||
using ModernUO.Serialization;
|
||||
using Server.Items;
|
||||
using Server.Misc;
|
||||
using Server.Mobiles;
|
||||
using Server.Network;
|
||||
|
||||
namespace Server.Engines.Quests.Haven
|
||||
namespace Server.Engines.Quests.Haven;
|
||||
|
||||
[SerializationGenerator(0, false)]
|
||||
public partial class SchmendrickApprenticeCorpse : Corpse
|
||||
{
|
||||
public class SchmendrickApprenticeCorpse : Corpse
|
||||
private static int _hairHue;
|
||||
|
||||
[SerializableField(0, setter: "private")]
|
||||
private Lantern _lantern;
|
||||
|
||||
[Constructible]
|
||||
public SchmendrickApprenticeCorpse() : base(GetOwner(), GetHair(), GetFacialHair(), GetEquipment())
|
||||
{
|
||||
private static int m_HairHue;
|
||||
Direction = Direction.West;
|
||||
|
||||
private Lantern m_Lantern;
|
||||
|
||||
[Constructible]
|
||||
public SchmendrickApprenticeCorpse() : base(GetOwner(), GetHair(), GetFacialHair(), GetEquipment())
|
||||
foreach (var item in EquipItems)
|
||||
{
|
||||
Direction = Direction.West;
|
||||
|
||||
foreach (var item in EquipItems)
|
||||
{
|
||||
DropItem(item);
|
||||
}
|
||||
|
||||
m_Lantern = new Lantern { Movable = false, Protected = true };
|
||||
m_Lantern.Ignite();
|
||||
DropItem(item);
|
||||
}
|
||||
|
||||
public SchmendrickApprenticeCorpse(Serial serial) : base(serial)
|
||||
_lantern = new Lantern { Movable = false, Protected = true };
|
||||
_lantern.Ignite();
|
||||
}
|
||||
|
||||
private static Mobile GetOwner()
|
||||
{
|
||||
var apprentice = new Mobile
|
||||
{
|
||||
Hue = Race.Human.RandomSkinHue(),
|
||||
Female = false,
|
||||
Body = 0x190,
|
||||
Name = NameList.RandomName("male")
|
||||
};
|
||||
|
||||
apprentice.Delete();
|
||||
return apprentice;
|
||||
}
|
||||
|
||||
private static List<Item> GetEquipment() =>
|
||||
[
|
||||
new Robe(QuestSystem.RandomBrightHue()),
|
||||
new WizardsHat(Utility.RandomNeutralHue()),
|
||||
new Shoes(Utility.RandomNeutralHue()),
|
||||
new Spellbook()
|
||||
];
|
||||
|
||||
private static HairInfo GetHair()
|
||||
{
|
||||
_hairHue = Race.Human.RandomHairHue();
|
||||
return new HairInfo(Race.Human.RandomHair(false), _hairHue);
|
||||
}
|
||||
|
||||
private static FacialHairInfo GetFacialHair()
|
||||
{
|
||||
_hairHue = Race.Human.RandomHairHue();
|
||||
|
||||
return new FacialHairInfo(Race.Human.RandomFacialHair(false), _hairHue);
|
||||
}
|
||||
|
||||
public override void AddNameProperty(IPropertyList 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
|
||||
}
|
||||
}
|
||||
|
||||
public override void OnSingleClick(Mobile from)
|
||||
{
|
||||
var hue = Notoriety.GetHue(NotorietyHandlers.CorpseNotoriety(from, this));
|
||||
|
||||
if (ItemID == 0x2006) // Corpse form
|
||||
{
|
||||
// the remains of ~1_NAME~ the apprentice
|
||||
from.NetState.SendMessageLocalized(Serial, ItemID, MessageType.Label, hue, 3, 1049144, "", Name);
|
||||
}
|
||||
else
|
||||
{
|
||||
// the remains of a wizard's apprentice
|
||||
from.NetState.SendMessageLocalized(Serial, ItemID, MessageType.Label, hue, 3, 1049145);
|
||||
}
|
||||
}
|
||||
|
||||
public override void Open(Mobile from, bool checkSelfLoot)
|
||||
{
|
||||
if (!from.InRange(GetWorldLocation(), 2))
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
// TODO: What is this? Why are we creating and deleting a mobile?
|
||||
private static Mobile GetOwner()
|
||||
if (from is not PlayerMobile player)
|
||||
{
|
||||
var apprentice = new Mobile();
|
||||
|
||||
apprentice.Hue = Race.Human.RandomSkinHue();
|
||||
apprentice.Female = false;
|
||||
apprentice.Body = 0x190;
|
||||
apprentice.Name = NameList.RandomName("male");
|
||||
|
||||
apprentice.Delete();
|
||||
|
||||
return apprentice;
|
||||
return;
|
||||
}
|
||||
|
||||
private static List<Item> GetEquipment()
|
||||
if (player.Quest is not UzeraanTurmoilQuest qs || qs.FindObjective<FindApprenticeObjective>() is not
|
||||
{ Completed: false } obj)
|
||||
{
|
||||
var list = new List<Item>();
|
||||
|
||||
list.Add(new Robe(QuestSystem.RandomBrightHue()));
|
||||
list.Add(new WizardsHat(Utility.RandomNeutralHue()));
|
||||
list.Add(new Shoes(Utility.RandomNeutralHue()));
|
||||
list.Add(new Spellbook());
|
||||
|
||||
return list;
|
||||
// This is the corpse of a wizard's apprentice. You can't bring yourself to search it without a good reason.
|
||||
from.SendLocalizedMessage(1049143, "", 0x22);
|
||||
return;
|
||||
}
|
||||
|
||||
private static HairInfo GetHair()
|
||||
var scroll = new SchmendrickScrollOfPower();
|
||||
|
||||
if (player.PlaceInBackpack(scroll))
|
||||
{
|
||||
m_HairHue = Race.Human.RandomHairHue();
|
||||
return new HairInfo(Race.Human.RandomHair(false), m_HairHue);
|
||||
player.SendLocalizedMessage(1049147, "", 0x22); // You find the scroll and put it in your pack.
|
||||
obj.Complete();
|
||||
}
|
||||
|
||||
private static FacialHairInfo GetFacialHair()
|
||||
else
|
||||
{
|
||||
m_HairHue = Race.Human.RandomHairHue();
|
||||
|
||||
return new FacialHairInfo(Race.Human.RandomFacialHair(false), m_HairHue);
|
||||
// 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.
|
||||
player.SendLocalizedMessage(1049146, "", 0x22);
|
||||
scroll.Delete();
|
||||
}
|
||||
}
|
||||
|
||||
public override void AddNameProperty(IPropertyList list)
|
||||
public override void OnLocationChange(Point3D oldLoc)
|
||||
{
|
||||
if (_lantern?.Deleted == false)
|
||||
{
|
||||
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
|
||||
}
|
||||
_lantern.Location = new Point3D(X, Y + 1, Z);
|
||||
}
|
||||
}
|
||||
|
||||
public override void OnSingleClick(Mobile from)
|
||||
public override void OnMapChange()
|
||||
{
|
||||
if (_lantern?.Deleted == false)
|
||||
{
|
||||
var hue = Notoriety.GetHue(NotorietyHandlers.CorpseNotoriety(from, this));
|
||||
|
||||
if (ItemID == 0x2006) // Corpse form
|
||||
{
|
||||
from.NetState.SendMessageLocalized(
|
||||
Serial,
|
||||
ItemID,
|
||||
MessageType.Label,
|
||||
hue,
|
||||
3,
|
||||
1049144,
|
||||
"",
|
||||
Name
|
||||
); // the remains of ~1_NAME~ the apprentice
|
||||
}
|
||||
else
|
||||
{
|
||||
from.NetState.SendMessageLocalized(
|
||||
Serial,
|
||||
ItemID,
|
||||
MessageType.Label,
|
||||
hue,
|
||||
3,
|
||||
1049145
|
||||
); // the remains of a wizard's apprentice
|
||||
}
|
||||
_lantern.Map = Map;
|
||||
}
|
||||
}
|
||||
|
||||
public override void Open(Mobile from, bool checkSelfLoot)
|
||||
public override void OnAfterDelete()
|
||||
{
|
||||
base.OnAfterDelete();
|
||||
|
||||
if (_lantern?.Deleted == false)
|
||||
{
|
||||
if (!from.InRange(GetWorldLocation(), 2))
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
if (from is PlayerMobile player)
|
||||
{
|
||||
var qs = player.Quest;
|
||||
|
||||
if (qs is UzeraanTurmoilQuest)
|
||||
{
|
||||
QuestObjective obj = qs.FindObjective<FindApprenticeObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
Item scroll = new SchmendrickScrollOfPower();
|
||||
|
||||
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();
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
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 OnLocationChange(Point3D oldLoc)
|
||||
{
|
||||
if (m_Lantern?.Deleted == false)
|
||||
{
|
||||
m_Lantern.Location = new Point3D(X, Y + 1, Z);
|
||||
}
|
||||
}
|
||||
|
||||
public override void OnMapChange()
|
||||
{
|
||||
if (m_Lantern?.Deleted == false)
|
||||
{
|
||||
m_Lantern.Map = Map;
|
||||
}
|
||||
}
|
||||
|
||||
public override void OnAfterDelete()
|
||||
{
|
||||
base.OnAfterDelete();
|
||||
|
||||
if (m_Lantern?.Deleted == false)
|
||||
{
|
||||
m_Lantern.Delete();
|
||||
}
|
||||
}
|
||||
|
||||
public override void Serialize(IGenericWriter writer)
|
||||
{
|
||||
if (m_Lantern?.Deleted == true)
|
||||
{
|
||||
m_Lantern = null;
|
||||
}
|
||||
|
||||
base.Serialize(writer);
|
||||
|
||||
writer.Write(0); // version
|
||||
|
||||
writer.Write(m_Lantern);
|
||||
}
|
||||
|
||||
public override void Deserialize(IGenericReader reader)
|
||||
{
|
||||
base.Deserialize(reader);
|
||||
|
||||
var version = reader.ReadInt();
|
||||
|
||||
m_Lantern = (Lantern)reader.ReadEntity<Item>();
|
||||
_lantern.Delete();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,37 +1,20 @@
|
|||
using ModernUO.Serialization;
|
||||
using Server.Mobiles;
|
||||
|
||||
namespace Server.Engines.Quests.Haven
|
||||
namespace Server.Engines.Quests.Haven;
|
||||
|
||||
[SerializationGenerator(0, false)]
|
||||
public partial class SchmendrickScrollOfPower : QuestItem
|
||||
{
|
||||
public class SchmendrickScrollOfPower : QuestItem
|
||||
public SchmendrickScrollOfPower() : base(0xE34)
|
||||
{
|
||||
public SchmendrickScrollOfPower() : base(0xE34)
|
||||
{
|
||||
Weight = 1.0;
|
||||
Hue = 0x34D;
|
||||
}
|
||||
|
||||
public SchmendrickScrollOfPower(Serial serial) : base(serial)
|
||||
{
|
||||
}
|
||||
|
||||
public override int LabelNumber => 1049118; // a scroll with ancient markings
|
||||
|
||||
public override bool CanDrop(PlayerMobile player) =>
|
||||
!(player.Quest is UzeraanTurmoilQuest qs &&
|
||||
qs.IsObjectiveInProgress(typeof(ReturnScrollOfPowerObjective)));
|
||||
|
||||
public override void Serialize(IGenericWriter writer)
|
||||
{
|
||||
base.Serialize(writer);
|
||||
|
||||
writer.Write(0); // version
|
||||
}
|
||||
|
||||
public override void Deserialize(IGenericReader reader)
|
||||
{
|
||||
base.Deserialize(reader);
|
||||
|
||||
var version = reader.ReadInt();
|
||||
}
|
||||
Weight = 1.0;
|
||||
Hue = 0x34D;
|
||||
}
|
||||
|
||||
public override int LabelNumber => 1049118; // a scroll with ancient markings
|
||||
|
||||
public override bool CanDrop(PlayerMobile player) =>
|
||||
!(player.Quest is UzeraanTurmoilQuest qs &&
|
||||
qs.IsObjectiveInProgress(typeof(ReturnScrollOfPowerObjective)));
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,34 +1,17 @@
|
|||
using ModernUO.Serialization;
|
||||
using Server.Mobiles;
|
||||
|
||||
namespace Server.Engines.Quests.Haven
|
||||
namespace Server.Engines.Quests.Haven;
|
||||
|
||||
[SerializationGenerator(0, false)]
|
||||
public partial class UzeraanTurmoilHorn : HornOfRetreat
|
||||
{
|
||||
public class UzeraanTurmoilHorn : HornOfRetreat
|
||||
[Constructible]
|
||||
public UzeraanTurmoilHorn()
|
||||
{
|
||||
[Constructible]
|
||||
public UzeraanTurmoilHorn()
|
||||
{
|
||||
DestLoc = new Point3D(3597, 2582, 0);
|
||||
DestMap = Map.Trammel;
|
||||
}
|
||||
|
||||
public UzeraanTurmoilHorn(Serial serial) : base(serial)
|
||||
{
|
||||
}
|
||||
|
||||
public override bool ValidateUse(Mobile from) => from is PlayerMobile pm && pm.Quest is UzeraanTurmoilQuest;
|
||||
|
||||
public override void Serialize(IGenericWriter writer)
|
||||
{
|
||||
base.Serialize(writer);
|
||||
|
||||
writer.Write(0); // version
|
||||
}
|
||||
|
||||
public override void Deserialize(IGenericReader reader)
|
||||
{
|
||||
base.Deserialize(reader);
|
||||
|
||||
var version = reader.ReadInt();
|
||||
}
|
||||
DestLoc = new Point3D(3597, 2582, 0);
|
||||
DestMap = Map.Trammel;
|
||||
}
|
||||
|
||||
public override bool ValidateUse(Mobile from) => from is PlayerMobile pm && pm.Quest is UzeraanTurmoilQuest;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,73 +1,58 @@
|
|||
using ModernUO.Serialization;
|
||||
using Server.Mobiles;
|
||||
|
||||
namespace Server.Engines.Quests.Haven
|
||||
namespace Server.Engines.Quests.Haven;
|
||||
|
||||
[SerializationGenerator(0, false)]
|
||||
public partial class UzeraanTurmoilTeleporter : DynamicTeleporter
|
||||
{
|
||||
public class UzeraanTurmoilTeleporter : DynamicTeleporter
|
||||
[Constructible]
|
||||
public UzeraanTurmoilTeleporter()
|
||||
{
|
||||
[Constructible]
|
||||
public UzeraanTurmoilTeleporter()
|
||||
}
|
||||
|
||||
public override bool GetDestination(PlayerMobile player, ref Point3D loc, ref Map map)
|
||||
{
|
||||
var qs = player.Quest;
|
||||
|
||||
if (qs is not UzeraanTurmoilQuest)
|
||||
{
|
||||
}
|
||||
|
||||
public UzeraanTurmoilTeleporter(Serial serial) : base(serial)
|
||||
{
|
||||
}
|
||||
|
||||
public override bool GetDestination(PlayerMobile player, ref Point3D loc, ref Map map)
|
||||
{
|
||||
var qs = player.Quest;
|
||||
|
||||
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;
|
||||
}
|
||||
|
||||
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;
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
public override void Serialize(IGenericWriter writer)
|
||||
if (qs.IsObjectiveInProgress(typeof(FindSchmendrickObjective))
|
||||
|| qs.IsObjectiveInProgress(typeof(FindApprenticeObjective))
|
||||
|| UzeraanTurmoilQuest.HasLostScrollOfPower(player))
|
||||
{
|
||||
base.Serialize(writer);
|
||||
|
||||
writer.Write(0); // version
|
||||
loc = new Point3D(5222, 1858, 0);
|
||||
map = Map.Trammel;
|
||||
return true;
|
||||
}
|
||||
|
||||
public override void Deserialize(IGenericReader reader)
|
||||
if (qs.IsObjectiveInProgress(typeof(FindDryadObjective))
|
||||
|| UzeraanTurmoilQuest.HasLostFertileDirt(player))
|
||||
{
|
||||
base.Deserialize(reader);
|
||||
|
||||
var version = reader.ReadInt();
|
||||
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;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,116 +1,82 @@
|
|||
using System.Collections.Generic;
|
||||
using ModernUO.Serialization;
|
||||
using Server.Items;
|
||||
using Server.Mobiles;
|
||||
|
||||
namespace Server.Engines.Quests.Haven
|
||||
namespace Server.Engines.Quests.Haven;
|
||||
|
||||
[SerializationGenerator(0, false)]
|
||||
public partial class Dryad : BaseQuester
|
||||
{
|
||||
public class Dryad : BaseQuester
|
||||
[Constructible]
|
||||
public Dryad() : base("the Dryad")
|
||||
{
|
||||
[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 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);
|
||||
|
||||
Hue = 0x85A7;
|
||||
|
||||
Female = true;
|
||||
Body = 0x191;
|
||||
}
|
||||
|
||||
public override void InitOutfit()
|
||||
{
|
||||
AddItem(new Kilt(0x301));
|
||||
AddItem(new FancyShirt(0x300));
|
||||
|
||||
HairItemID = 0x203D; // Pony Tail
|
||||
HairHue = 0x22;
|
||||
|
||||
var bow = new Bow();
|
||||
bow.Movable = false;
|
||||
AddItem(bow);
|
||||
}
|
||||
|
||||
public override void InitSBInfo()
|
||||
{
|
||||
_sbInfos.Add(new SBDryad());
|
||||
}
|
||||
|
||||
public override int GetAutoTalkRange(PlayerMobile pm) => 4;
|
||||
|
||||
public override bool CanTalkTo(PlayerMobile to) =>
|
||||
to.Quest is UzeraanTurmoilQuest qs && qs.FindObjective<FindDryadObjective>() != null;
|
||||
|
||||
public override void OnTalk(PlayerMobile player, bool contextMenu)
|
||||
{
|
||||
var qs = player.Quest;
|
||||
|
||||
if (qs is UzeraanTurmoilQuest)
|
||||
{
|
||||
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 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);
|
||||
|
||||
Hue = 0x85A7;
|
||||
|
||||
Female = true;
|
||||
Body = 0x191;
|
||||
}
|
||||
|
||||
public override void InitOutfit()
|
||||
{
|
||||
AddItem(new Kilt(0x301));
|
||||
AddItem(new FancyShirt(0x300));
|
||||
|
||||
HairItemID = 0x203D; // Pony Tail
|
||||
HairHue = 0x22;
|
||||
|
||||
var bow = new Bow();
|
||||
bow.Movable = false;
|
||||
AddItem(bow);
|
||||
}
|
||||
|
||||
public override void InitSBInfo()
|
||||
{
|
||||
_sbInfos.Add(new SBDryad());
|
||||
}
|
||||
|
||||
public override int GetAutoTalkRange(PlayerMobile pm) => 4;
|
||||
|
||||
public override bool CanTalkTo(PlayerMobile to) =>
|
||||
to.Quest is UzeraanTurmoilQuest qs && qs.FindObjective<FindDryadObjective>() != null;
|
||||
|
||||
public override void OnTalk(PlayerMobile player, bool contextMenu)
|
||||
{
|
||||
var qs = player.Quest;
|
||||
|
||||
if (qs is UzeraanTurmoilQuest)
|
||||
if (UzeraanTurmoilQuest.HasLostFertileDirt(player))
|
||||
{
|
||||
if (UzeraanTurmoilQuest.HasLostFertileDirt(player))
|
||||
FocusTo(player);
|
||||
qs.AddConversation(new LostFertileDirtConversation(false));
|
||||
}
|
||||
else
|
||||
{
|
||||
var obj = qs.FindObjective<FindDryadObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
FocusTo(player);
|
||||
qs.AddConversation(new LostFertileDirtConversation(false));
|
||||
}
|
||||
else
|
||||
{
|
||||
QuestObjective obj = qs.FindObjective<FindDryadObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
FocusTo(player);
|
||||
|
||||
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.
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
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();
|
||||
|
||||
|
|
@ -120,65 +86,78 @@ namespace Server.Engines.Quests.Haven
|
|||
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;
|
||||
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 not PlayerMobile { Quest: UzeraanTurmoilQuest qs } player || dropped is not Apple ||
|
||||
!UzeraanTurmoilQuest.HasLostFertileDirt(from))
|
||||
{
|
||||
return base.OnDragDrop(from, dropped);
|
||||
}
|
||||
|
||||
public override void Serialize(IGenericWriter writer)
|
||||
{
|
||||
base.Serialize(writer);
|
||||
FocusTo(from);
|
||||
|
||||
writer.Write(0); // version
|
||||
Item fertileDirt = new QuestFertileDirt();
|
||||
|
||||
if (!player.PlaceInBackpack(fertileDirt))
|
||||
{
|
||||
fertileDirt.Delete();
|
||||
// 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.
|
||||
player.SendLocalizedMessage(1046260);
|
||||
return false;
|
||||
}
|
||||
|
||||
public override void Deserialize(IGenericReader reader)
|
||||
{
|
||||
base.Deserialize(reader);
|
||||
dropped.Consume();
|
||||
qs.AddConversation(new DryadAppleConversation());
|
||||
return dropped.Deleted;
|
||||
}
|
||||
}
|
||||
|
||||
var version = reader.ReadInt();
|
||||
public class SBDryad : SBInfo
|
||||
{
|
||||
public override IShopSellInfo SellInfo { get; } = new InternalSellInfo();
|
||||
|
||||
public override List<GenericBuyInfo> BuyInfo { get; } = new InternalBuyInfo();
|
||||
|
||||
public class InternalBuyInfo : List<GenericBuyInfo>
|
||||
{
|
||||
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 SBDryad : SBInfo
|
||||
public class InternalSellInfo : GenericSellInfo
|
||||
{
|
||||
public override IShopSellInfo SellInfo { get; } = new InternalSellInfo();
|
||||
|
||||
public override List<GenericBuyInfo> BuyInfo { get; } = new InternalBuyInfo();
|
||||
|
||||
public class InternalBuyInfo : List<GenericBuyInfo>
|
||||
public InternalSellInfo()
|
||||
{
|
||||
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);
|
||||
}
|
||||
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);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,72 +1,55 @@
|
|||
using ModernUO.Serialization;
|
||||
using Server.Items;
|
||||
using Server.Mobiles;
|
||||
|
||||
namespace Server.Engines.Quests.Haven
|
||||
namespace Server.Engines.Quests.Haven;
|
||||
|
||||
[SerializationGenerator(0, false)]
|
||||
public partial class MansionGuard : BaseQuester
|
||||
{
|
||||
public class MansionGuard : BaseQuester
|
||||
[Constructible]
|
||||
public MansionGuard() : base("the Mansion Guard")
|
||||
{
|
||||
[Constructible]
|
||||
public MansionGuard() : base("the Mansion Guard")
|
||||
}
|
||||
|
||||
public override void InitBody()
|
||||
{
|
||||
InitStats(100, 100, 25);
|
||||
|
||||
Hue = Race.Human.RandomSkinHue();
|
||||
|
||||
Female = false;
|
||||
Body = 0x190;
|
||||
Name = NameList.RandomName("male");
|
||||
}
|
||||
|
||||
public override void InitOutfit()
|
||||
{
|
||||
AddItem(new PlateChest());
|
||||
AddItem(new PlateArms());
|
||||
AddItem(new PlateGloves());
|
||||
AddItem(new PlateLegs());
|
||||
|
||||
Utility.AssignRandomHair(this);
|
||||
Utility.AssignRandomFacialHair(this, HairHue);
|
||||
|
||||
var weapon = new Bardiche();
|
||||
weapon.Movable = false;
|
||||
AddItem(weapon);
|
||||
}
|
||||
|
||||
public override int GetAutoTalkRange(PlayerMobile pm) => 3;
|
||||
|
||||
public override bool CanTalkTo(PlayerMobile to) =>
|
||||
to.Quest == null && QuestSystem.CanOfferQuest(to, typeof(UzeraanTurmoilQuest));
|
||||
|
||||
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)
|
||||
{
|
||||
}
|
||||
|
||||
public override void InitBody()
|
||||
{
|
||||
InitStats(100, 100, 25);
|
||||
|
||||
Hue = Race.Human.RandomSkinHue();
|
||||
|
||||
Female = false;
|
||||
Body = 0x190;
|
||||
Name = NameList.RandomName("male");
|
||||
}
|
||||
|
||||
public override void InitOutfit()
|
||||
{
|
||||
AddItem(new PlateChest());
|
||||
AddItem(new PlateArms());
|
||||
AddItem(new PlateGloves());
|
||||
AddItem(new PlateLegs());
|
||||
|
||||
Utility.AssignRandomHair(this);
|
||||
Utility.AssignRandomFacialHair(this, HairHue);
|
||||
|
||||
var weapon = new Bardiche();
|
||||
weapon.Movable = false;
|
||||
AddItem(weapon);
|
||||
}
|
||||
|
||||
public override int GetAutoTalkRange(PlayerMobile pm) => 3;
|
||||
|
||||
public override bool CanTalkTo(PlayerMobile to) =>
|
||||
to.Quest == null && QuestSystem.CanOfferQuest(to, typeof(UzeraanTurmoilQuest));
|
||||
|
||||
public override void OnTalk(PlayerMobile player, bool contextMenu)
|
||||
{
|
||||
if (player.Quest == null && QuestSystem.CanOfferQuest(player, typeof(UzeraanTurmoilQuest)))
|
||||
{
|
||||
Direction = GetDirectionTo(player);
|
||||
|
||||
new UzeraanTurmoilQuest(player).SendOffer();
|
||||
}
|
||||
}
|
||||
|
||||
public override void Serialize(IGenericWriter writer)
|
||||
{
|
||||
base.Serialize(writer);
|
||||
|
||||
writer.Write(0); // version
|
||||
}
|
||||
|
||||
public override void Deserialize(IGenericReader reader)
|
||||
{
|
||||
base.Deserialize(reader);
|
||||
|
||||
var version = reader.ReadInt();
|
||||
new UzeraanTurmoilQuest(player).SendOffer();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,100 +1,91 @@
|
|||
using ModernUO.Serialization;
|
||||
using Server.Items;
|
||||
using Server.Mobiles;
|
||||
|
||||
namespace Server.Engines.Quests.Haven
|
||||
namespace Server.Engines.Quests.Haven;
|
||||
|
||||
[SerializationGenerator(0, false)]
|
||||
public partial class MilitiaCanoneer : BaseQuester
|
||||
{
|
||||
public class MilitiaCanoneer : BaseQuester
|
||||
private static readonly int[] _cannonFireClilocs = [
|
||||
500651, // You're evil, and must die!
|
||||
1049098, // I shall make short work of thee.
|
||||
1049320, // FIRE!
|
||||
1043149 // Thou deservest to die!
|
||||
];
|
||||
|
||||
[SerializableField(0)]
|
||||
[SerializedCommandProperty(AccessLevel.GameMaster)]
|
||||
private bool _active;
|
||||
|
||||
[Constructible]
|
||||
public MilitiaCanoneer() : base("the Militia Canoneer") => _active = true;
|
||||
|
||||
public override void InitBody()
|
||||
{
|
||||
[Constructible]
|
||||
public MilitiaCanoneer() : base("the Militia Canoneer") => Active = true;
|
||||
InitStats(100, 125, 25);
|
||||
|
||||
public MilitiaCanoneer(Serial serial) : base(serial)
|
||||
Hue = Race.Human.RandomSkinHue();
|
||||
|
||||
Female = false;
|
||||
Body = 0x190;
|
||||
Name = NameList.RandomName("male");
|
||||
}
|
||||
|
||||
public override void InitOutfit()
|
||||
{
|
||||
Utility.AssignRandomHair(this);
|
||||
Utility.AssignRandomFacialHair(this, HairHue);
|
||||
|
||||
AddItem(new PlateChest());
|
||||
AddItem(new PlateArms());
|
||||
AddItem(new PlateGloves());
|
||||
AddItem(new PlateLegs());
|
||||
|
||||
var torch = new Torch
|
||||
{
|
||||
}
|
||||
Movable = false
|
||||
};
|
||||
|
||||
[CommandProperty(AccessLevel.GameMaster)]
|
||||
public bool Active { get; set; }
|
||||
AddItem(torch);
|
||||
torch.Ignite();
|
||||
}
|
||||
|
||||
public override void InitBody()
|
||||
public override bool CanTalkTo(PlayerMobile to) => false;
|
||||
|
||||
public override void OnTalk(PlayerMobile player, bool contextMenu)
|
||||
{
|
||||
}
|
||||
|
||||
public override bool IsEnemy(Mobile m)
|
||||
{
|
||||
while (!m.Player && m is not BaseVendor)
|
||||
{
|
||||
InitStats(100, 125, 25);
|
||||
|
||||
Hue = Race.Human.RandomSkinHue();
|
||||
|
||||
Female = false;
|
||||
Body = 0x190;
|
||||
Name = NameList.RandomName("male");
|
||||
}
|
||||
|
||||
public override void InitOutfit()
|
||||
{
|
||||
Utility.AssignRandomHair(this);
|
||||
Utility.AssignRandomFacialHair(this, HairHue);
|
||||
|
||||
AddItem(new PlateChest());
|
||||
AddItem(new PlateArms());
|
||||
AddItem(new PlateGloves());
|
||||
AddItem(new PlateLegs());
|
||||
|
||||
var torch = new Torch();
|
||||
torch.Movable = false;
|
||||
AddItem(torch);
|
||||
torch.Ignite();
|
||||
}
|
||||
|
||||
public override bool CanTalkTo(PlayerMobile to) => false;
|
||||
|
||||
public override void OnTalk(PlayerMobile player, bool contextMenu)
|
||||
{
|
||||
}
|
||||
|
||||
public override bool IsEnemy(Mobile m)
|
||||
{
|
||||
if (m.Player || m is BaseVendor)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
if (m is BaseCreature bc)
|
||||
{
|
||||
var master = bc.GetMaster();
|
||||
if (master != null)
|
||||
{
|
||||
return IsEnemy(master);
|
||||
m = master;
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
return m.Karma < 0;
|
||||
}
|
||||
|
||||
public bool WillFire(Cannon cannon, Mobile target)
|
||||
{
|
||||
if (Active && IsEnemy(target))
|
||||
{
|
||||
Direction = GetDirectionTo(target);
|
||||
Say(Utility.RandomList(500651, 1049098, 1049320, 1043149));
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
return false;
|
||||
public bool WillFire(Cannon cannon, Mobile target)
|
||||
{
|
||||
if (_active && IsEnemy(target))
|
||||
{
|
||||
Direction = GetDirectionTo(target);
|
||||
Say(_cannonFireClilocs.RandomElement());
|
||||
return true;
|
||||
}
|
||||
|
||||
public override void Serialize(IGenericWriter writer)
|
||||
{
|
||||
base.Serialize(writer);
|
||||
|
||||
writer.Write(0); // version
|
||||
|
||||
writer.Write(Active);
|
||||
}
|
||||
|
||||
public override void Deserialize(IGenericReader reader)
|
||||
{
|
||||
base.Deserialize(reader);
|
||||
|
||||
var version = reader.ReadInt();
|
||||
|
||||
Active = reader.ReadBool();
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,180 +1,133 @@
|
|||
using System.Collections.Generic;
|
||||
using ModernUO.Serialization;
|
||||
using Server.Items;
|
||||
using Server.Misc;
|
||||
using Server.Mobiles;
|
||||
using Server.Network;
|
||||
|
||||
namespace Server.Engines.Quests.Haven
|
||||
namespace Server.Engines.Quests.Haven;
|
||||
|
||||
[SerializationGenerator(0, false)]
|
||||
public partial class MilitiaFighter : BaseCreature
|
||||
{
|
||||
public class MilitiaFighter : BaseCreature
|
||||
[Constructible]
|
||||
public MilitiaFighter() : base(AIType.AI_Melee)
|
||||
{
|
||||
[Constructible]
|
||||
public MilitiaFighter() : base(AIType.AI_Melee)
|
||||
InitStats(40, 30, 5);
|
||||
Title = "the Militia Fighter";
|
||||
|
||||
SpeechHue = Utility.RandomDyedHue();
|
||||
|
||||
Hue = Race.Human.RandomSkinHue();
|
||||
|
||||
Female = false;
|
||||
Body = 0x190;
|
||||
Name = NameList.RandomName("male");
|
||||
|
||||
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());
|
||||
|
||||
var weapon = Utility.Random(6) switch
|
||||
{
|
||||
InitStats(40, 30, 5);
|
||||
Title = "the Militia Fighter";
|
||||
0 => (Item)new Broadsword(),
|
||||
1 => new Cutlass(),
|
||||
2 => new Katana(),
|
||||
3 => new Longsword(),
|
||||
4 => new Scimitar(),
|
||||
_ => new VikingSword()
|
||||
};
|
||||
|
||||
SpeechHue = Utility.RandomDyedHue();
|
||||
weapon.Movable = false;
|
||||
AddItem(weapon);
|
||||
|
||||
Hue = Race.Human.RandomSkinHue();
|
||||
|
||||
Female = false;
|
||||
Body = 0x190;
|
||||
Name = NameList.RandomName("male");
|
||||
|
||||
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());
|
||||
|
||||
var weapon = Utility.Random(6) switch
|
||||
{
|
||||
0 => (Item)new Broadsword(),
|
||||
1 => new Cutlass(),
|
||||
2 => new Katana(),
|
||||
3 => new Longsword(),
|
||||
4 => new Scimitar(),
|
||||
_ => new VikingSword()
|
||||
};
|
||||
|
||||
weapon.Movable = false;
|
||||
AddItem(weapon);
|
||||
|
||||
Item shield = new BronzeShield();
|
||||
shield.Movable = false;
|
||||
AddItem(shield);
|
||||
|
||||
SetSkill(SkillName.Swords, 20.0);
|
||||
}
|
||||
|
||||
public MilitiaFighter(Serial serial) : base(serial)
|
||||
Item shield = new BronzeShield
|
||||
{
|
||||
}
|
||||
Movable = false
|
||||
};
|
||||
|
||||
public override bool ClickTitle => false;
|
||||
AddItem(shield);
|
||||
|
||||
public override bool IsEnemy(Mobile m)
|
||||
SetSkill(SkillName.Swords, 20.0);
|
||||
}
|
||||
|
||||
public override bool ClickTitle => false;
|
||||
|
||||
public override bool IsEnemy(Mobile m)
|
||||
{
|
||||
while (!m.Player && m is not BaseVendor)
|
||||
{
|
||||
if (m.Player || m is BaseVendor)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
if (m is BaseCreature bc)
|
||||
{
|
||||
var master = bc.GetMaster();
|
||||
if (master != null)
|
||||
{
|
||||
return IsEnemy(master);
|
||||
m = master;
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
return m.Karma < 0;
|
||||
}
|
||||
|
||||
public override void Serialize(IGenericWriter writer)
|
||||
{
|
||||
base.Serialize(writer);
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
writer.Write(0); // version
|
||||
[SerializationGenerator(0, false)]
|
||||
public partial class MilitiaFighterCorpse : Corpse
|
||||
{
|
||||
public MilitiaFighterCorpse(Mobile owner, HairInfo hair, FacialHairInfo facialhair, List<Item> equipItems) : base(
|
||||
owner,
|
||||
hair,
|
||||
facialhair,
|
||||
equipItems
|
||||
)
|
||||
{
|
||||
}
|
||||
|
||||
public override void AddNameProperty(IPropertyList list)
|
||||
{
|
||||
if (ItemID == 0x2006) // Corpse form
|
||||
{
|
||||
list.Add("a human corpse");
|
||||
list.Add(1049318, Name); // the remains of ~1_NAME~ the militia fighter
|
||||
}
|
||||
|
||||
public override void Deserialize(IGenericReader reader)
|
||||
else
|
||||
{
|
||||
base.Deserialize(reader);
|
||||
|
||||
var version = reader.ReadInt();
|
||||
list.Add(1049319); // the remains of a militia fighter
|
||||
}
|
||||
}
|
||||
|
||||
public class MilitiaFighterCorpse : Corpse
|
||||
public override void OnSingleClick(Mobile from)
|
||||
{
|
||||
public MilitiaFighterCorpse(Mobile owner, HairInfo hair, FacialHairInfo facialhair, List<Item> equipItems) : base(
|
||||
owner,
|
||||
hair,
|
||||
facialhair,
|
||||
equipItems
|
||||
)
|
||||
var hue = Notoriety.GetHue(NotorietyHandlers.CorpseNotoriety(from, this));
|
||||
|
||||
if (ItemID == 0x2006) // Corpse form
|
||||
{
|
||||
// the remains of ~1_NAME~ the militia fighter
|
||||
from.NetState.SendMessageLocalized(Serial, ItemID, MessageType.Label, hue, 3, 1049318, "", Name);
|
||||
}
|
||||
|
||||
public MilitiaFighterCorpse(Serial serial) : base(serial)
|
||||
else
|
||||
{
|
||||
// the remains of a militia fighter
|
||||
from.NetState.SendMessageLocalized(Serial, ItemID, MessageType.Label, hue, 3, 1049319);
|
||||
}
|
||||
}
|
||||
|
||||
public override void AddNameProperty(IPropertyList list)
|
||||
public override void Open(Mobile from, bool checkSelfLoot)
|
||||
{
|
||||
if (from.InRange(GetWorldLocation(), 2))
|
||||
{
|
||||
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 OnSingleClick(Mobile from)
|
||||
{
|
||||
var hue = Notoriety.GetHue(NotorietyHandlers.CorpseNotoriety(from, this));
|
||||
|
||||
if (ItemID == 0x2006) // Corpse form
|
||||
{
|
||||
from.NetState.SendMessageLocalized(
|
||||
Serial,
|
||||
ItemID,
|
||||
MessageType.Label,
|
||||
hue,
|
||||
3,
|
||||
1049318,
|
||||
"",
|
||||
Name
|
||||
); // the remains of ~1_NAME~ the militia fighter
|
||||
}
|
||||
else
|
||||
{
|
||||
from.NetState.SendMessageLocalized(
|
||||
Serial,
|
||||
ItemID,
|
||||
MessageType.Label,
|
||||
hue,
|
||||
3,
|
||||
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 Serialize(IGenericWriter writer)
|
||||
{
|
||||
base.Serialize(writer);
|
||||
|
||||
writer.Write(0); // version
|
||||
}
|
||||
|
||||
public override void Deserialize(IGenericReader reader)
|
||||
{
|
||||
base.Deserialize(reader);
|
||||
|
||||
var version = reader.ReadInt();
|
||||
// Thinking about his sacrifice, you can't bring yourself to loot the body of this militia fighter.
|
||||
from.SendLocalizedMessage(1049661, "", 0x22);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,149 +1,136 @@
|
|||
using ModernUO.Serialization;
|
||||
using Server.Gumps;
|
||||
using Server.Items;
|
||||
using Server.Mobiles;
|
||||
|
||||
namespace Server.Engines.Quests.Haven
|
||||
namespace Server.Engines.Quests.Haven;
|
||||
|
||||
[SerializationGenerator(0, false)]
|
||||
public partial class Schmendrick : BaseQuester
|
||||
{
|
||||
public class Schmendrick : BaseQuester
|
||||
[Constructible]
|
||||
public Schmendrick() : base("the High Mage")
|
||||
{
|
||||
[Constructible]
|
||||
public Schmendrick() : base("the High Mage")
|
||||
}
|
||||
|
||||
public override string DefaultName => "Schmendrick";
|
||||
|
||||
public override void InitBody()
|
||||
{
|
||||
InitStats(100, 100, 25);
|
||||
|
||||
Hue = 0x83F3;
|
||||
|
||||
Female = false;
|
||||
Body = 0x190;
|
||||
}
|
||||
|
||||
public override void InitOutfit()
|
||||
{
|
||||
AddItem(new Robe(0x4DD));
|
||||
AddItem(new WizardsHat(0x482));
|
||||
AddItem(new Shoes(0x482));
|
||||
|
||||
HairItemID = 0x203C;
|
||||
HairHue = 0x455;
|
||||
|
||||
FacialHairItemID = 0x203E;
|
||||
FacialHairHue = 0x455;
|
||||
|
||||
var staff = new GlacialStaff
|
||||
{
|
||||
Movable = false
|
||||
};
|
||||
AddItem(staff);
|
||||
|
||||
var pack = new Backpack
|
||||
{
|
||||
Movable = false
|
||||
};
|
||||
AddItem(pack);
|
||||
}
|
||||
|
||||
public override int GetAutoTalkRange(PlayerMobile pm) => 7;
|
||||
|
||||
public override bool CanTalkTo(PlayerMobile to) =>
|
||||
to.Quest is UzeraanTurmoilQuest qs && qs.FindObjective<FindSchmendrickObjective>() != null;
|
||||
|
||||
public override void OnTalk(PlayerMobile player, bool contextMenu)
|
||||
{
|
||||
var qs = player.Quest;
|
||||
|
||||
if (qs is not UzeraanTurmoilQuest)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
public Schmendrick(Serial serial) : base(serial)
|
||||
if (UzeraanTurmoilQuest.HasLostScrollOfPower(player))
|
||||
{
|
||||
FocusTo(player);
|
||||
qs.AddConversation(new LostScrollOfPowerConversation(false));
|
||||
return;
|
||||
}
|
||||
|
||||
public override string DefaultName => "Schmendrick";
|
||||
var obj = qs.FindObjective<FindSchmendrickObjective>();
|
||||
|
||||
public override void InitBody()
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
InitStats(100, 100, 25);
|
||||
|
||||
Hue = 0x83F3;
|
||||
|
||||
Female = false;
|
||||
Body = 0x190;
|
||||
FocusTo(player);
|
||||
obj.Complete();
|
||||
}
|
||||
|
||||
public override void InitOutfit()
|
||||
else if (contextMenu)
|
||||
{
|
||||
AddItem(new Robe(0x4DD));
|
||||
AddItem(new WizardsHat(0x482));
|
||||
AddItem(new Shoes(0x482));
|
||||
|
||||
HairItemID = 0x203C;
|
||||
HairHue = 0x455;
|
||||
|
||||
FacialHairItemID = 0x203E;
|
||||
FacialHairHue = 0x455;
|
||||
|
||||
var staff = new GlacialStaff();
|
||||
staff.Movable = false;
|
||||
AddItem(staff);
|
||||
|
||||
var pack = new Backpack();
|
||||
pack.Movable = false;
|
||||
AddItem(pack);
|
||||
FocusTo(player);
|
||||
SayTo(player, 1049357); // I have nothing more for you at this time.
|
||||
}
|
||||
}
|
||||
|
||||
public override int GetAutoTalkRange(PlayerMobile pm) => 7;
|
||||
|
||||
public override bool CanTalkTo(PlayerMobile to) =>
|
||||
to.Quest is UzeraanTurmoilQuest qs && qs.FindObjective<FindSchmendrickObjective>() != null;
|
||||
|
||||
public override void OnTalk(PlayerMobile player, bool contextMenu)
|
||||
public override bool OnDragDrop(Mobile from, Item dropped)
|
||||
{
|
||||
if (dropped is not BlankScroll || !UzeraanTurmoilQuest.HasLostScrollOfPower(from))
|
||||
{
|
||||
var qs = player.Quest;
|
||||
|
||||
if (qs is UzeraanTurmoilQuest)
|
||||
{
|
||||
if (UzeraanTurmoilQuest.HasLostScrollOfPower(player))
|
||||
{
|
||||
FocusTo(player);
|
||||
qs.AddConversation(new LostScrollOfPowerConversation(false));
|
||||
}
|
||||
else
|
||||
{
|
||||
QuestObjective obj = qs.FindObjective<FindSchmendrickObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
FocusTo(player);
|
||||
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 (dropped is BlankScroll && UzeraanTurmoilQuest.HasLostScrollOfPower(from))
|
||||
{
|
||||
FocusTo(from);
|
||||
|
||||
Item scroll = new SchmendrickScrollOfPower();
|
||||
|
||||
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;
|
||||
}
|
||||
|
||||
dropped.Consume();
|
||||
from.SendLocalizedMessage(
|
||||
1049346
|
||||
); // Schmendrick scribbles on the scroll for a few moments and hands you the finished product.
|
||||
return dropped.Deleted;
|
||||
}
|
||||
|
||||
return base.OnDragDrop(from, dropped);
|
||||
}
|
||||
|
||||
public override void OnMovement(Mobile m, Point3D oldLocation)
|
||||
FocusTo(from);
|
||||
var scroll = new SchmendrickScrollOfPower();
|
||||
|
||||
if (!from.PlaceInBackpack(scroll))
|
||||
{
|
||||
base.OnMovement(m, oldLocation);
|
||||
|
||||
if (m is PlayerMobile && !m.Frozen && !m.Alive && InRange(m, 4) && !InRange(oldLocation, 4) && InLOS(m))
|
||||
{
|
||||
if (m.Map?.CanFit(m.Location, 16, false, false) != true)
|
||||
{
|
||||
m.SendLocalizedMessage(502391); // Thou can not be resurrected there!
|
||||
}
|
||||
else
|
||||
{
|
||||
Direction = GetDirectionTo(m);
|
||||
|
||||
m.PlaySound(0x214);
|
||||
m.FixedEffect(0x376A, 10, 16);
|
||||
|
||||
m.CloseGump<ResurrectGump>();
|
||||
m.SendGump(new ResurrectGump(m, ResurrectMessage.Healer));
|
||||
}
|
||||
}
|
||||
scroll.Delete();
|
||||
// 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.
|
||||
from.SendLocalizedMessage(1046260);
|
||||
return false;
|
||||
}
|
||||
|
||||
public override void Serialize(IGenericWriter writer)
|
||||
{
|
||||
base.Serialize(writer);
|
||||
dropped.Consume();
|
||||
|
||||
writer.Write(0); // version
|
||||
// Schmendrick scribbles on the scroll for a few moments and hands you the finished product.
|
||||
from.SendLocalizedMessage(1049346);
|
||||
return dropped.Deleted;
|
||||
}
|
||||
|
||||
public override void OnMovement(Mobile m, Point3D oldLocation)
|
||||
{
|
||||
base.OnMovement(m, oldLocation);
|
||||
|
||||
if (m is not PlayerMobile || m.Frozen || m.Alive || !InRange(m, 4) || InRange(oldLocation, 4) || !InLOS(m))
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
public override void Deserialize(IGenericReader reader)
|
||||
if (m.Map?.CanFit(m.Location, 16, false, false) != true)
|
||||
{
|
||||
base.Deserialize(reader);
|
||||
|
||||
var version = reader.ReadInt();
|
||||
m.SendLocalizedMessage(502391); // Thou can not be resurrected there!
|
||||
return;
|
||||
}
|
||||
|
||||
Direction = GetDirectionTo(m);
|
||||
|
||||
m.PlaySound(0x214);
|
||||
m.FixedEffect(0x376A, 10, 16);
|
||||
|
||||
m.CloseGump<ResurrectGump>();
|
||||
m.SendGump(new ResurrectGump(m, ResurrectMessage.Healer));
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,427 +1,399 @@
|
|||
using ModernUO.Serialization;
|
||||
using Server.Gumps;
|
||||
using Server.Items;
|
||||
using Server.Mobiles;
|
||||
|
||||
namespace Server.Engines.Quests.Haven
|
||||
namespace Server.Engines.Quests.Haven;
|
||||
|
||||
[SerializationGenerator(0, false)]
|
||||
public partial class Uzeraan : BaseQuester
|
||||
{
|
||||
public class Uzeraan : BaseQuester
|
||||
[Constructible]
|
||||
public Uzeraan() : base("the Conjurer")
|
||||
{
|
||||
[Constructible]
|
||||
public Uzeraan() : base("the Conjurer")
|
||||
}
|
||||
|
||||
public override string DefaultName => "Uzeraan";
|
||||
|
||||
public override void InitBody()
|
||||
{
|
||||
InitStats(100, 100, 25);
|
||||
|
||||
Hue = 0x83F3;
|
||||
|
||||
Female = false;
|
||||
Body = 0x190;
|
||||
}
|
||||
|
||||
public override void InitOutfit()
|
||||
{
|
||||
AddItem(new Robe(0x4DD));
|
||||
AddItem(new WizardsHat(0x8A5));
|
||||
AddItem(new Shoes(0x8A5));
|
||||
|
||||
HairItemID = 0x203C;
|
||||
HairHue = 0x455;
|
||||
|
||||
FacialHairItemID = 0x203E;
|
||||
FacialHairHue = 0x455;
|
||||
|
||||
var staff = new BlackStaff
|
||||
{
|
||||
Movable = false
|
||||
};
|
||||
|
||||
AddItem(staff);
|
||||
}
|
||||
|
||||
public override int GetAutoTalkRange(PlayerMobile pm) => 3;
|
||||
|
||||
public override bool CanTalkTo(PlayerMobile to) => to.Quest is UzeraanTurmoilQuest;
|
||||
|
||||
public override void OnTalk(PlayerMobile player, bool contextMenu)
|
||||
{
|
||||
var qs = player.Quest;
|
||||
|
||||
if (qs is not UzeraanTurmoilQuest)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
public Uzeraan(Serial serial) : base(serial)
|
||||
if (UzeraanTurmoilQuest.HasLostScrollOfPower(player))
|
||||
{
|
||||
qs.AddConversation(new LostScrollOfPowerConversation(true));
|
||||
return;
|
||||
}
|
||||
|
||||
public override string DefaultName => "Uzeraan";
|
||||
|
||||
public override void InitBody()
|
||||
if (UzeraanTurmoilQuest.HasLostFertileDirt(player))
|
||||
{
|
||||
InitStats(100, 100, 25);
|
||||
|
||||
Hue = 0x83F3;
|
||||
|
||||
Female = false;
|
||||
Body = 0x190;
|
||||
qs.AddConversation(new LostFertileDirtConversation(true));
|
||||
return;
|
||||
}
|
||||
|
||||
public override void InitOutfit()
|
||||
if (UzeraanTurmoilQuest.HasLostDaemonBlood(player))
|
||||
{
|
||||
AddItem(new Robe(0x4DD));
|
||||
AddItem(new WizardsHat(0x8A5));
|
||||
AddItem(new Shoes(0x8A5));
|
||||
|
||||
HairItemID = 0x203C;
|
||||
HairHue = 0x455;
|
||||
|
||||
FacialHairItemID = 0x203E;
|
||||
FacialHairHue = 0x455;
|
||||
|
||||
var staff = new BlackStaff();
|
||||
staff.Movable = false;
|
||||
AddItem(staff);
|
||||
qs.AddConversation(new LostDaemonBloodConversation());
|
||||
return;
|
||||
}
|
||||
|
||||
public override int GetAutoTalkRange(PlayerMobile pm) => 3;
|
||||
|
||||
public override bool CanTalkTo(PlayerMobile to) => to.Quest is UzeraanTurmoilQuest;
|
||||
|
||||
public override void OnTalk(PlayerMobile player, bool contextMenu)
|
||||
if (UzeraanTurmoilQuest.HasLostDaemonBone(player))
|
||||
{
|
||||
var qs = player.Quest;
|
||||
qs.AddConversation(new LostDaemonBoneConversation());
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs is UzeraanTurmoilQuest)
|
||||
if (player.Profession == 2) // magician
|
||||
{
|
||||
var backpack = player.Backpack;
|
||||
|
||||
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)
|
||||
{
|
||||
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
|
||||
{
|
||||
var backpack = player.Backpack;
|
||||
|
||||
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());
|
||||
}
|
||||
}
|
||||
|
||||
QuestObjective obj = qs.FindObjective<FindUzeraanBeginObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
obj.Complete();
|
||||
}
|
||||
else
|
||||
{
|
||||
obj = qs.FindObjective<FindUzeraanFirstTaskObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
obj.Complete();
|
||||
}
|
||||
else
|
||||
{
|
||||
obj = qs.FindObjective<FindUzeraanAboutReportObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
var cont = GetNewContainer();
|
||||
|
||||
if (player.Profession == 2) // magician
|
||||
{
|
||||
cont.DropItem(new MarkScroll(5));
|
||||
cont.DropItem(new RecallScroll(5));
|
||||
for (var i = 0; i < 5; i++)
|
||||
{
|
||||
cont.DropItem(new RecallRune());
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
cont.DropItem(new Gold(300));
|
||||
for (var i = 0; i < 6; i++)
|
||||
{
|
||||
cont.DropItem(new NightSightPotion());
|
||||
cont.DropItem(new LesserHealPotion());
|
||||
}
|
||||
}
|
||||
|
||||
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<ReturnScrollOfPowerObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
FocusTo(player);
|
||||
SayTo(player, 1049378); // Hand me the scroll, if you have it.
|
||||
}
|
||||
else
|
||||
{
|
||||
obj = qs.FindObjective<ReturnFertileDirtObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
FocusTo(player);
|
||||
SayTo(player, 1049381); // Hand me the Fertile Dirt, if you have it.
|
||||
}
|
||||
else
|
||||
{
|
||||
obj = qs.FindObjective<ReturnDaemonBloodObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
FocusTo(player);
|
||||
SayTo(player, 1049379); // Hand me the Vial of Blood, if you have it.
|
||||
}
|
||||
else
|
||||
{
|
||||
obj = qs.FindObjective<ReturnDaemonBoneObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
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.
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
qs.AddConversation(new FewReagentsConversation());
|
||||
}
|
||||
}
|
||||
|
||||
public override bool OnDragDrop(Mobile from, Item dropped)
|
||||
if (qs.FindObjective<FindUzeraanBeginObjective>() is { Completed: false } obj1)
|
||||
{
|
||||
if (from is PlayerMobile player)
|
||||
obj1.Complete();
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.FindObjective<FindUzeraanFirstTaskObjective>() is { Completed: false } obj2)
|
||||
{
|
||||
obj2.Complete();
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.FindObjective<FindUzeraanAboutReportObjective>() is { Completed: false } obj3)
|
||||
{
|
||||
var cont = GetNewContainer();
|
||||
|
||||
if (player.Profession == 2) // magician
|
||||
{
|
||||
var qs = player.Quest;
|
||||
|
||||
if (qs is UzeraanTurmoilQuest)
|
||||
cont.DropItem(new MarkScroll(5));
|
||||
cont.DropItem(new RecallScroll(5));
|
||||
for (var i = 0; i < 5; i++)
|
||||
{
|
||||
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.
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
if (dropped is SchmendrickScrollOfPower)
|
||||
{
|
||||
QuestObjective obj = qs.FindObjective<ReturnScrollOfPowerObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
var cont = GetNewContainer();
|
||||
|
||||
cont.DropItem(new TreasureMap(player.Young ? 0 : 1, Map.Trammel));
|
||||
cont.DropItem(new Shovel());
|
||||
cont.DropItem(new UzeraanTurmoilHorn());
|
||||
|
||||
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;
|
||||
}
|
||||
|
||||
dropped.Delete();
|
||||
obj.Complete();
|
||||
return true;
|
||||
}
|
||||
}
|
||||
else if (dropped is QuestFertileDirt)
|
||||
{
|
||||
QuestObjective obj = qs.FindObjective<ReturnFertileDirtObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
var cont = GetNewContainer();
|
||||
|
||||
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 (var i = 0; i < 3; i++)
|
||||
{
|
||||
cont.DropItem(Loot.RandomScroll(0, 23, SpellbookType.Regular));
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
cont.DropItem(new Gold(300));
|
||||
cont.DropItem(new Bandage(25));
|
||||
|
||||
for (var i = 0; i < 5; i++)
|
||||
{
|
||||
cont.DropItem(new LesserHealPotion());
|
||||
}
|
||||
}
|
||||
|
||||
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;
|
||||
}
|
||||
|
||||
dropped.Delete();
|
||||
obj.Complete();
|
||||
return true;
|
||||
}
|
||||
}
|
||||
else if (dropped is QuestDaemonBlood)
|
||||
{
|
||||
QuestObjective obj = qs.FindObjective<ReturnDaemonBloodObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
Item reward;
|
||||
|
||||
if (player.Profession == 2) // magician
|
||||
{
|
||||
var cont = GetNewContainer();
|
||||
|
||||
cont.DropItem(new ExplosionScroll(4));
|
||||
cont.DropItem(new MagicWizardsHat());
|
||||
|
||||
reward = cont;
|
||||
}
|
||||
else
|
||||
{
|
||||
var weapon = Utility.Random(6) switch
|
||||
{
|
||||
0 => (BaseWeapon)new Broadsword(),
|
||||
1 => new Cutlass(),
|
||||
2 => new Katana(),
|
||||
3 => new Longsword(),
|
||||
4 => new Scimitar(),
|
||||
_ => new VikingSword()
|
||||
};
|
||||
|
||||
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.Silver;
|
||||
|
||||
reward = weapon;
|
||||
}
|
||||
|
||||
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;
|
||||
}
|
||||
|
||||
dropped.Delete();
|
||||
obj.Complete();
|
||||
return true;
|
||||
}
|
||||
}
|
||||
else if (dropped is QuestDaemonBone)
|
||||
{
|
||||
QuestObjective obj = qs.FindObjective<ReturnDaemonBoneObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
var cont = GetNewContainer();
|
||||
cont.DropItem(new BankCheck(2000));
|
||||
cont.DropItem(new EnchantedSextant());
|
||||
|
||||
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;
|
||||
}
|
||||
|
||||
dropped.Delete();
|
||||
obj.Complete();
|
||||
return true;
|
||||
}
|
||||
}
|
||||
cont.DropItem(new RecallRune());
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
cont.DropItem(new Gold(300));
|
||||
for (var i = 0; i < 6; i++)
|
||||
{
|
||||
cont.DropItem(new NightSightPotion());
|
||||
cont.DropItem(new LesserHealPotion());
|
||||
}
|
||||
}
|
||||
|
||||
if (!player.PlaceInBackpack(cont))
|
||||
{
|
||||
cont.Delete();
|
||||
// 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.
|
||||
player.SendLocalizedMessage(1046260);
|
||||
}
|
||||
else
|
||||
{
|
||||
obj3.Complete();
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.FindObjective<ReturnScrollOfPowerObjective>()?.Completed == false)
|
||||
{
|
||||
FocusTo(player);
|
||||
SayTo(player, 1049378); // Hand me the scroll, if you have it.
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.FindObjective<ReturnFertileDirtObjective>()?.Completed == false)
|
||||
{
|
||||
FocusTo(player);
|
||||
SayTo(player, 1049381); // Hand me the Fertile Dirt, if you have it.
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.FindObjective<ReturnDaemonBloodObjective>()?.Completed == false)
|
||||
{
|
||||
FocusTo(player);
|
||||
SayTo(player, 1049379); // Hand me the Vial of Blood, if you have it.
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.FindObjective<ReturnDaemonBoneObjective>()?.Completed == false)
|
||||
{
|
||||
FocusTo(player);
|
||||
SayTo(player, 1049380); // Hand me the Daemon Bone, if you have it.
|
||||
return;
|
||||
}
|
||||
|
||||
SayTo(player, 1049357); // I have nothing more for you at this time.
|
||||
}
|
||||
|
||||
public override bool OnDragDrop(Mobile from, Item dropped)
|
||||
{
|
||||
if (from is not PlayerMobile player)
|
||||
{
|
||||
return base.OnDragDrop(from, dropped);
|
||||
}
|
||||
|
||||
public override void OnMovement(Mobile m, Point3D oldLocation)
|
||||
{
|
||||
base.OnMovement(m, oldLocation);
|
||||
var qs = player.Quest;
|
||||
|
||||
if (m is PlayerMobile && !m.Frozen && !m.Alive && InRange(m, 4) && !InRange(oldLocation, 4) && InLOS(m))
|
||||
if (qs is not UzeraanTurmoilQuest)
|
||||
{
|
||||
return base.OnDragDrop(from, dropped);
|
||||
}
|
||||
|
||||
if (dropped is UzeraanTurmoilHorn horn)
|
||||
{
|
||||
if (player.Young)
|
||||
{
|
||||
if (m.Map?.CanFit(m.Location, 16, false, false) != true)
|
||||
if (horn.Charges < 10)
|
||||
{
|
||||
m.SendLocalizedMessage(502391); // Thou can not be resurrected there!
|
||||
SayTo(from, 1049384); // I have recharged the item for you.
|
||||
horn.Charges = 10;
|
||||
}
|
||||
else
|
||||
{
|
||||
Direction = GetDirectionTo(m);
|
||||
|
||||
m.PlaySound(0x214);
|
||||
m.FixedEffect(0x376A, 10, 16);
|
||||
|
||||
m.CloseGump<ResurrectGump>();
|
||||
m.SendGump(new ResurrectGump(m, ResurrectMessage.Healer));
|
||||
SayTo(from, 1049385); // That doesn't need recharging yet.
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
player.SendLocalizedMessage(1114333); // You must be young to have this item recharged.
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
if (dropped is SchmendrickScrollOfPower)
|
||||
{
|
||||
var obj = qs.FindObjective<ReturnScrollOfPowerObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
var cont = GetNewContainer();
|
||||
|
||||
cont.DropItem(new TreasureMap(player.Young ? 0 : 1, Map.Trammel));
|
||||
cont.DropItem(new Shovel());
|
||||
cont.DropItem(new UzeraanTurmoilHorn());
|
||||
|
||||
if (!player.PlaceInBackpack(cont))
|
||||
{
|
||||
cont.Delete();
|
||||
// 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.
|
||||
player.SendLocalizedMessage(1046260);
|
||||
return false;
|
||||
}
|
||||
|
||||
dropped.Delete();
|
||||
obj.Complete();
|
||||
return true;
|
||||
}
|
||||
}
|
||||
else if (dropped is QuestFertileDirt)
|
||||
{
|
||||
var obj = qs.FindObjective<ReturnFertileDirtObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
var cont = GetNewContainer();
|
||||
|
||||
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 (var i = 0; i < 3; i++)
|
||||
{
|
||||
cont.DropItem(Loot.RandomScroll(0, 23, SpellbookType.Regular));
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
cont.DropItem(new Gold(300));
|
||||
cont.DropItem(new Bandage(25));
|
||||
|
||||
for (var i = 0; i < 5; i++)
|
||||
{
|
||||
cont.DropItem(new LesserHealPotion());
|
||||
}
|
||||
}
|
||||
|
||||
if (!player.PlaceInBackpack(cont))
|
||||
{
|
||||
cont.Delete();
|
||||
// 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.
|
||||
player.SendLocalizedMessage(1046260);
|
||||
return false;
|
||||
}
|
||||
|
||||
dropped.Delete();
|
||||
obj.Complete();
|
||||
return true;
|
||||
}
|
||||
}
|
||||
else if (dropped is QuestDaemonBlood)
|
||||
{
|
||||
var obj = qs.FindObjective<ReturnDaemonBloodObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
Item reward;
|
||||
|
||||
if (player.Profession == 2) // magician
|
||||
{
|
||||
var cont = GetNewContainer();
|
||||
|
||||
cont.DropItem(new ExplosionScroll(4));
|
||||
cont.DropItem(new MagicWizardsHat());
|
||||
|
||||
reward = cont;
|
||||
}
|
||||
else
|
||||
{
|
||||
var weapon = Utility.Random(6) switch
|
||||
{
|
||||
0 => (BaseWeapon)new Broadsword(),
|
||||
1 => new Cutlass(),
|
||||
2 => new Katana(),
|
||||
3 => new Longsword(),
|
||||
4 => new Scimitar(),
|
||||
_ => new VikingSword()
|
||||
};
|
||||
|
||||
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.Silver;
|
||||
|
||||
reward = weapon;
|
||||
}
|
||||
|
||||
if (!player.PlaceInBackpack(reward))
|
||||
{
|
||||
reward.Delete();
|
||||
// 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.
|
||||
player.SendLocalizedMessage(1046260);
|
||||
return false;
|
||||
}
|
||||
|
||||
dropped.Delete();
|
||||
obj.Complete();
|
||||
return true;
|
||||
}
|
||||
}
|
||||
else if (dropped is QuestDaemonBone)
|
||||
{
|
||||
var obj = qs.FindObjective<ReturnDaemonBoneObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
var cont = GetNewContainer();
|
||||
cont.DropItem(new BankCheck(2000));
|
||||
cont.DropItem(new EnchantedSextant());
|
||||
|
||||
if (!player.PlaceInBackpack(cont))
|
||||
{
|
||||
cont.Delete();
|
||||
// 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.
|
||||
player.SendLocalizedMessage(1046260);
|
||||
return false;
|
||||
}
|
||||
|
||||
dropped.Delete();
|
||||
obj.Complete();
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
public override void Serialize(IGenericWriter writer)
|
||||
return base.OnDragDrop(from, dropped);
|
||||
}
|
||||
|
||||
public override void OnMovement(Mobile m, Point3D oldLocation)
|
||||
{
|
||||
base.OnMovement(m, oldLocation);
|
||||
|
||||
if (m is PlayerMobile && !m.Frozen && !m.Alive && InRange(m, 4) && !InRange(oldLocation, 4) && InLOS(m))
|
||||
{
|
||||
base.Serialize(writer);
|
||||
if (m.Map?.CanFit(m.Location, 16, false, false) != true)
|
||||
{
|
||||
m.SendLocalizedMessage(502391); // Thou can not be resurrected there!
|
||||
}
|
||||
else
|
||||
{
|
||||
Direction = GetDirectionTo(m);
|
||||
|
||||
writer.Write(0); // version
|
||||
}
|
||||
m.PlaySound(0x214);
|
||||
m.FixedEffect(0x376A, 10, 16);
|
||||
|
||||
public override void Deserialize(IGenericReader reader)
|
||||
{
|
||||
base.Deserialize(reader);
|
||||
|
||||
var version = reader.ReadInt();
|
||||
m.CloseGump<ResurrectGump>();
|
||||
m.SendGump(new ResurrectGump(m, ResurrectMessage.Healer));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -190,14 +190,14 @@ namespace Server.Engines.Quests.Haven
|
|||
{
|
||||
case KillHordeMinionsStep.First:
|
||||
{
|
||||
QuestObjective obj = new KillHordeMinionsObjective(KillHordeMinionsStep.LearnKarma);
|
||||
var obj = new KillHordeMinionsObjective(KillHordeMinionsStep.LearnKarma);
|
||||
System.AddObjective(obj);
|
||||
obj.CurProgress = CurProgress;
|
||||
break;
|
||||
}
|
||||
case KillHordeMinionsStep.LearnKarma:
|
||||
{
|
||||
QuestObjective obj = new KillHordeMinionsObjective(KillHordeMinionsStep.Others);
|
||||
var obj = new KillHordeMinionsObjective(KillHordeMinionsStep.Others);
|
||||
System.AddObjective(obj);
|
||||
obj.CurProgress = CurProgress;
|
||||
break;
|
||||
|
|
|
|||
|
|
@ -1,28 +1,12 @@
|
|||
namespace Server.Items
|
||||
using ModernUO.Serialization;
|
||||
|
||||
namespace Server.Items;
|
||||
|
||||
[SerializationGenerator(0, false)]
|
||||
public partial class Cauldron : Item
|
||||
{
|
||||
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 override string DefaultName => "a cauldron";
|
||||
|
||||
public override void Serialize(IGenericWriter writer)
|
||||
{
|
||||
base.Serialize(writer);
|
||||
|
||||
writer.Write(0); // version
|
||||
}
|
||||
|
||||
public override void Deserialize(IGenericReader reader)
|
||||
{
|
||||
base.Deserialize(reader);
|
||||
|
||||
var version = reader.ReadInt();
|
||||
}
|
||||
}
|
||||
public override string DefaultName => "a cauldron";
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,105 +1,75 @@
|
|||
using System.Collections.Generic;
|
||||
using ModernUO.Serialization;
|
||||
using Server.Items;
|
||||
using Server.Misc;
|
||||
using Server.Mobiles;
|
||||
using Server.Network;
|
||||
|
||||
namespace Server.Engines.Quests.Hag
|
||||
namespace Server.Engines.Quests.Hag;
|
||||
|
||||
[SerializationGenerator(0, false)]
|
||||
public partial class HagApprenticeCorpse : Corpse
|
||||
{
|
||||
public class HagApprenticeCorpse : Corpse
|
||||
[Constructible]
|
||||
public HagApprenticeCorpse() : base(GetOwner(), []) => Direction = Direction.South;
|
||||
|
||||
private static Mobile GetOwner()
|
||||
{
|
||||
[Constructible]
|
||||
public HagApprenticeCorpse() : base(GetOwner(), GetEquipment())
|
||||
var apprentice = new Mobile
|
||||
{
|
||||
Direction = Direction.South;
|
||||
Hue = Race.Human.RandomSkinHue(),
|
||||
Female = false,
|
||||
Body = 0x190
|
||||
};
|
||||
|
||||
foreach (var item in EquipItems)
|
||||
apprentice.Delete();
|
||||
|
||||
return apprentice;
|
||||
}
|
||||
|
||||
public override void AddNameProperty(IPropertyList list)
|
||||
{
|
||||
list.Add("a charred corpse");
|
||||
}
|
||||
|
||||
public override void OnSingleClick(Mobile from)
|
||||
{
|
||||
var hue = Notoriety.GetHue(NotorietyHandlers.CorpseNotoriety(from, this));
|
||||
|
||||
from.NetState.SendMessage(Serial, ItemID, MessageType.Label, hue, 3, true, null, "", "a charred corpse");
|
||||
}
|
||||
|
||||
public override void Open(Mobile from, bool checkSelfLoot)
|
||||
{
|
||||
if (!from.InRange(GetWorldLocation(), 2))
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
if (from is PlayerMobile player)
|
||||
{
|
||||
var qs = player.Quest;
|
||||
|
||||
if (qs is WitchApprenticeQuest)
|
||||
{
|
||||
DropItem(item);
|
||||
}
|
||||
}
|
||||
|
||||
public HagApprenticeCorpse(Serial serial) : base(serial)
|
||||
{
|
||||
}
|
||||
|
||||
// TODO: What is this? Why are we creating a mobile and deleting it?
|
||||
private static Mobile GetOwner()
|
||||
{
|
||||
var apprentice = new Mobile();
|
||||
|
||||
apprentice.Hue = Race.Human.RandomSkinHue();
|
||||
apprentice.Female = false;
|
||||
apprentice.Body = 0x190;
|
||||
|
||||
apprentice.Delete();
|
||||
|
||||
return apprentice;
|
||||
}
|
||||
|
||||
private static List<Item> GetEquipment() => new();
|
||||
|
||||
public override void AddNameProperty(IPropertyList list)
|
||||
{
|
||||
list.Add("a charred corpse");
|
||||
}
|
||||
|
||||
public override void OnSingleClick(Mobile from)
|
||||
{
|
||||
var hue = Notoriety.GetHue(NotorietyHandlers.CorpseNotoriety(from, this));
|
||||
|
||||
from.NetState.SendMessage(Serial, ItemID, MessageType.Label, hue, 3, true, null, "", "a charred corpse");
|
||||
}
|
||||
|
||||
public override void Open(Mobile from, bool checkSelfLoot)
|
||||
{
|
||||
if (!from.InRange(GetWorldLocation(), 2))
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
if (from is PlayerMobile player)
|
||||
{
|
||||
var qs = player.Quest;
|
||||
|
||||
if (qs is WitchApprenticeQuest)
|
||||
var obj = qs.FindObjective<FindApprenticeObjective>();
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
var obj = qs.FindObjective<FindApprenticeObjective>();
|
||||
if (obj?.Completed == false)
|
||||
if (obj.Corpse == this)
|
||||
{
|
||||
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;
|
||||
obj.Complete();
|
||||
Delete();
|
||||
}
|
||||
else
|
||||
{
|
||||
// You examine the corpse, but it doesn't fit the description of the particular apprentice the Hag tasked you with finding.
|
||||
SendLocalizedMessageTo(from, 1055047);
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
SendLocalizedMessageTo(from, 1055048); // You examine the corpse, but find nothing of interest.
|
||||
}
|
||||
|
||||
public override void Serialize(IGenericWriter writer)
|
||||
{
|
||||
base.Serialize(writer);
|
||||
|
||||
writer.Write(0); // version
|
||||
}
|
||||
|
||||
public override void Deserialize(IGenericReader reader)
|
||||
{
|
||||
base.Deserialize(reader);
|
||||
|
||||
var version = reader.ReadInt();
|
||||
}
|
||||
SendLocalizedMessageTo(from, 1055048); // You examine the corpse, but find nothing of interest.
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,36 +1,20 @@
|
|||
namespace Server.Items
|
||||
using ModernUO.Serialization;
|
||||
|
||||
namespace Server.Items;
|
||||
|
||||
[SerializationGenerator(0, false)]
|
||||
public partial class HagCauldron : BaseAddon
|
||||
{
|
||||
public class HagCauldron : BaseAddon
|
||||
[Constructible]
|
||||
public HagCauldron()
|
||||
{
|
||||
[Constructible]
|
||||
public HagCauldron()
|
||||
{
|
||||
AddonComponent pot;
|
||||
pot = new AddonComponent(2420);
|
||||
AddComponent(pot, 0, 0, 0); // pot w/ support
|
||||
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);
|
||||
}
|
||||
|
||||
public HagCauldron(Serial serial) : base(serial)
|
||||
{
|
||||
}
|
||||
|
||||
public override void Serialize(IGenericWriter writer)
|
||||
{
|
||||
base.Serialize(writer);
|
||||
|
||||
writer.Write(0); // version
|
||||
}
|
||||
|
||||
public override void Deserialize(IGenericReader reader)
|
||||
{
|
||||
base.Deserialize(reader);
|
||||
|
||||
var version = reader.ReadInt();
|
||||
}
|
||||
AddonComponent fire;
|
||||
fire = new AddonComponent(4012); // fire pit
|
||||
fire.Light = LightType.Circle150;
|
||||
AddComponent(fire, 0, 0, 0);
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,71 +1,52 @@
|
|||
using System;
|
||||
using ModernUO.Serialization;
|
||||
|
||||
namespace Server.Items
|
||||
namespace Server.Items;
|
||||
|
||||
[SerializationGenerator(0, false)]
|
||||
public partial class HagStew : BaseAddon
|
||||
{
|
||||
public class HagStew : BaseAddon
|
||||
[Constructible]
|
||||
public HagStew()
|
||||
{
|
||||
[Constructible]
|
||||
public HagStew()
|
||||
// stew
|
||||
AddComponent(new AddonComponent(2416)
|
||||
{
|
||||
AddonComponent stew;
|
||||
stew = new AddonComponent(2416);
|
||||
stew.Name = "stew";
|
||||
stew.Visible = true;
|
||||
AddComponent(stew, 0, 0, -7); // stew
|
||||
}
|
||||
Name = "stew",
|
||||
Visible = true
|
||||
}, 0, 0, -7);
|
||||
}
|
||||
|
||||
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.");
|
||||
}
|
||||
|
||||
public override void OnComponentUsed(AddonComponent stew, Mobile from)
|
||||
else
|
||||
{
|
||||
if (!from.InRange(GetWorldLocation(), 2))
|
||||
stew.Visible = false;
|
||||
|
||||
var hagstew = new BreadLoaf(); // this decides your fillrate
|
||||
hagstew.Eat(from);
|
||||
|
||||
Timer timer = new ShowStew(stew);
|
||||
timer.Start();
|
||||
}
|
||||
}
|
||||
|
||||
public class ShowStew : Timer
|
||||
{
|
||||
private readonly AddonComponent _stew;
|
||||
|
||||
public ShowStew(AddonComponent ac) : base(TimeSpan.FromSeconds(30)) => _stew = ac;
|
||||
|
||||
protected override void OnTick()
|
||||
{
|
||||
if (_stew.Visible == false)
|
||||
{
|
||||
from.SendMessage("You are too far away.");
|
||||
}
|
||||
else
|
||||
{
|
||||
stew.Visible = false;
|
||||
|
||||
var hagstew = new BreadLoaf(); // this decides your fillrate
|
||||
hagstew.Eat(from);
|
||||
|
||||
Timer m_timer = new ShowStew(stew);
|
||||
m_timer.Start();
|
||||
}
|
||||
}
|
||||
|
||||
public override void Serialize(IGenericWriter writer)
|
||||
{
|
||||
base.Serialize(writer);
|
||||
|
||||
writer.Write(0); // version
|
||||
}
|
||||
|
||||
public override void Deserialize(IGenericReader reader)
|
||||
{
|
||||
base.Deserialize(reader);
|
||||
|
||||
var version = reader.ReadInt();
|
||||
}
|
||||
|
||||
public class ShowStew : Timer
|
||||
{
|
||||
private readonly AddonComponent stew;
|
||||
|
||||
public ShowStew(AddonComponent ac) : base(TimeSpan.FromSeconds(30))
|
||||
{
|
||||
stew = ac;
|
||||
}
|
||||
|
||||
protected override void OnTick()
|
||||
{
|
||||
if (stew.Visible == false)
|
||||
{
|
||||
Stop();
|
||||
stew.Visible = true;
|
||||
}
|
||||
Stop();
|
||||
_stew.Visible = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,81 +1,51 @@
|
|||
namespace Server.Engines.Quests.Hag
|
||||
using ModernUO.Serialization;
|
||||
|
||||
namespace Server.Engines.Quests.Hag;
|
||||
|
||||
[SerializationGenerator(0, false)]
|
||||
public partial class HangoverCure : Item
|
||||
{
|
||||
public class HangoverCure : Item
|
||||
[EncodedInt]
|
||||
[SerializableField(0)]
|
||||
[SerializedCommandProperty(AccessLevel.GameMaster)]
|
||||
private int _uses;
|
||||
|
||||
[Constructible]
|
||||
public HangoverCure() : base(0xE2B)
|
||||
{
|
||||
[Constructible]
|
||||
public HangoverCure() : base(0xE2B)
|
||||
{
|
||||
Weight = 1.0;
|
||||
Hue = 0x2D;
|
||||
Weight = 1.0;
|
||||
Hue = 0x2D;
|
||||
|
||||
Uses = 20;
|
||||
_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;
|
||||
}
|
||||
|
||||
public HangoverCure(Serial serial) : base(serial)
|
||||
if (Uses > 0)
|
||||
{
|
||||
from.PlaySound(0x2D6);
|
||||
from.SendLocalizedMessage(501206); // An awful taste fills your mouth.
|
||||
|
||||
if (from.BAC > 0)
|
||||
{
|
||||
from.BAC = 0;
|
||||
from.SendLocalizedMessage(501204); // You are now sober!
|
||||
}
|
||||
|
||||
Uses--;
|
||||
}
|
||||
|
||||
public override int LabelNumber => 1055060; // Grizelda's Extra Strength Hangover Cure
|
||||
|
||||
[CommandProperty(AccessLevel.GameMaster)]
|
||||
public int Uses { get; set; }
|
||||
|
||||
public override void OnDoubleClick(Mobile from)
|
||||
else
|
||||
{
|
||||
if (!IsChildOf(from.Backpack))
|
||||
{
|
||||
SendLocalizedMessageTo(from, 1042038); // You must have the object in your backpack to use it.
|
||||
return;
|
||||
}
|
||||
|
||||
if (Uses > 0)
|
||||
{
|
||||
from.PlaySound(0x2D6);
|
||||
from.SendLocalizedMessage(501206); // An awful taste fills your mouth.
|
||||
|
||||
if (from.BAC > 0)
|
||||
{
|
||||
from.BAC = 0;
|
||||
from.SendLocalizedMessage(501204); // You are now sober!
|
||||
}
|
||||
|
||||
Uses--;
|
||||
}
|
||||
else
|
||||
{
|
||||
Delete();
|
||||
from.SendLocalizedMessage(501201); // There wasn't enough left to have any effect.
|
||||
}
|
||||
}
|
||||
|
||||
public override void Serialize(IGenericWriter writer)
|
||||
{
|
||||
base.Serialize(writer);
|
||||
|
||||
writer.Write(1); // version
|
||||
|
||||
writer.WriteEncodedInt(Uses);
|
||||
}
|
||||
|
||||
public override void Deserialize(IGenericReader reader)
|
||||
{
|
||||
base.Deserialize(reader);
|
||||
|
||||
var version = reader.ReadInt();
|
||||
|
||||
switch (version)
|
||||
{
|
||||
case 1:
|
||||
{
|
||||
Uses = reader.ReadEncodedInt();
|
||||
break;
|
||||
}
|
||||
case 0:
|
||||
{
|
||||
Uses = 20;
|
||||
break;
|
||||
}
|
||||
}
|
||||
Delete();
|
||||
from.SendLocalizedMessage(501201); // There wasn't enough left to have any effect.
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,72 +1,59 @@
|
|||
using ModernUO.Serialization;
|
||||
using Server.Mobiles;
|
||||
|
||||
namespace Server.Engines.Quests.Hag
|
||||
namespace Server.Engines.Quests.Hag;
|
||||
|
||||
[SerializationGenerator(0, false)]
|
||||
public partial class MagicFlute : Item
|
||||
{
|
||||
public class MagicFlute : Item
|
||||
[Constructible]
|
||||
public MagicFlute() : base(0x1421) => Hue = 0x8AB;
|
||||
|
||||
public override int LabelNumber => 1055051; // magic flute
|
||||
|
||||
public override void OnDoubleClick(Mobile from)
|
||||
{
|
||||
[Constructible]
|
||||
public MagicFlute() : base(0x1421) => Hue = 0x8AB;
|
||||
|
||||
public MagicFlute(Serial serial) : base(serial)
|
||||
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 (from is not PlayerMobile player)
|
||||
{
|
||||
if (!IsChildOf(from.Backpack))
|
||||
{
|
||||
SendLocalizedMessageTo(from, 1042292); // You must have the object in your backpack to use it.
|
||||
return;
|
||||
}
|
||||
|
||||
from.PlaySound(0x3D);
|
||||
|
||||
if (from is PlayerMobile player)
|
||||
{
|
||||
var qs = player.Quest;
|
||||
|
||||
if (qs is WitchApprenticeQuest)
|
||||
{
|
||||
var obj = qs.FindObjective<FindZeefzorpulObjective>();
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
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();
|
||||
|
||||
obj.Complete();
|
||||
}
|
||||
else
|
||||
{
|
||||
player.SendLocalizedMessage(
|
||||
1055052
|
||||
); // The flute sparkles. Zeefzorpul must be in a good hiding place nearby.
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
public override void Serialize(IGenericWriter writer)
|
||||
{
|
||||
base.Serialize(writer);
|
||||
var qs = player.Quest;
|
||||
|
||||
writer.Write(0); // version
|
||||
if (qs is not WitchApprenticeQuest)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
public override void Deserialize(IGenericReader reader)
|
||||
var obj = qs.FindObjective<FindZeefzorpulObjective>();
|
||||
if (obj?.Completed != false)
|
||||
{
|
||||
base.Deserialize(reader);
|
||||
|
||||
var version = reader.ReadInt();
|
||||
return;
|
||||
}
|
||||
|
||||
if (player.Map != Map.Trammel && player.Map != Map.Felucca || !player.InRange(obj.ImpLocation, 8))
|
||||
{
|
||||
// Nothing happens. Zeefzorpul must not be hiding in this area.
|
||||
player.SendLocalizedMessage(1055053);
|
||||
return;
|
||||
}
|
||||
|
||||
if (player.InRange(obj.ImpLocation, 4))
|
||||
{
|
||||
Delete();
|
||||
obj.Complete();
|
||||
return;
|
||||
}
|
||||
|
||||
// The flute sparkles. Zeefzorpul must be in a good hiding place nearby.
|
||||
player.SendLocalizedMessage(1055052);
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,28 +1,12 @@
|
|||
namespace Server.Engines.Quests.Hag
|
||||
using ModernUO.Serialization;
|
||||
|
||||
namespace Server.Engines.Quests.Hag;
|
||||
|
||||
[SerializationGenerator(0, false)]
|
||||
public partial class MoonfireBrew : Item
|
||||
{
|
||||
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 override int LabelNumber => 1055065; // a bottle of magical moonfire brew
|
||||
|
||||
public override void Serialize(IGenericWriter writer)
|
||||
{
|
||||
base.Serialize(writer);
|
||||
|
||||
writer.Write(0); // version
|
||||
}
|
||||
|
||||
public override void Deserialize(IGenericReader reader)
|
||||
{
|
||||
base.Deserialize(reader);
|
||||
|
||||
var version = reader.ReadInt();
|
||||
}
|
||||
}
|
||||
public override int LabelNumber => 1055065; // a bottle of magical moonfire brew
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,232 +1,205 @@
|
|||
using ModernUO.Serialization;
|
||||
using Server.Engines.Virtues;
|
||||
using Server.Items;
|
||||
using Server.Mobiles;
|
||||
|
||||
namespace Server.Engines.Quests.Hag
|
||||
namespace Server.Engines.Quests.Hag;
|
||||
|
||||
[SerializationGenerator(0, false)]
|
||||
public partial class Grizelda : BaseQuester
|
||||
{
|
||||
public class Grizelda : BaseQuester
|
||||
[Constructible]
|
||||
public Grizelda() : base("the Hag")
|
||||
{
|
||||
[Constructible]
|
||||
public Grizelda() : base("the Hag")
|
||||
}
|
||||
|
||||
public override bool ClickTitle => true;
|
||||
public override string DefaultName => "Grizelda";
|
||||
|
||||
public override void InitBody()
|
||||
{
|
||||
InitStats(100, 100, 25);
|
||||
|
||||
Hue = 0x83EA;
|
||||
|
||||
Female = true;
|
||||
Body = 0x191;
|
||||
}
|
||||
|
||||
public override void InitOutfit()
|
||||
{
|
||||
AddItem(new Robe(0x1));
|
||||
AddItem(new Sandals());
|
||||
AddItem(new WizardsHat(0x1));
|
||||
AddItem(new GoldBracelet());
|
||||
|
||||
HairItemID = 0x203C;
|
||||
|
||||
Item staff = new GnarledStaff();
|
||||
staff.Movable = false;
|
||||
AddItem(staff);
|
||||
}
|
||||
|
||||
public override void OnTalk(PlayerMobile player, bool contextMenu)
|
||||
{
|
||||
Direction = GetDirectionTo(player);
|
||||
|
||||
var qs = player.Quest;
|
||||
|
||||
if (qs is not WitchApprenticeQuest)
|
||||
{
|
||||
}
|
||||
var newQuest = new WitchApprenticeQuest(player);
|
||||
|
||||
public Grizelda(Serial serial) : base(serial)
|
||||
{
|
||||
}
|
||||
|
||||
public override bool ClickTitle => true;
|
||||
public override string DefaultName => "Grizelda";
|
||||
|
||||
public override void InitBody()
|
||||
{
|
||||
InitStats(100, 100, 25);
|
||||
|
||||
Hue = 0x83EA;
|
||||
|
||||
Female = true;
|
||||
Body = 0x191;
|
||||
}
|
||||
|
||||
public override void InitOutfit()
|
||||
{
|
||||
AddItem(new Robe(0x1));
|
||||
AddItem(new Sandals());
|
||||
AddItem(new WizardsHat(0x1));
|
||||
AddItem(new GoldBracelet());
|
||||
|
||||
HairItemID = 0x203C;
|
||||
|
||||
Item staff = new GnarledStaff();
|
||||
staff.Movable = false;
|
||||
AddItem(staff);
|
||||
}
|
||||
|
||||
public override void OnTalk(PlayerMobile player, bool contextMenu)
|
||||
{
|
||||
Direction = GetDirectionTo(player);
|
||||
|
||||
var qs = player.Quest;
|
||||
|
||||
if (qs is WitchApprenticeQuest)
|
||||
if (qs != null)
|
||||
{
|
||||
if (qs.IsObjectiveInProgress(typeof(FindApprenticeObjective)))
|
||||
newQuest.AddConversation(new DontOfferConversation());
|
||||
}
|
||||
else if (QuestSystem.CanOfferQuest(player, typeof(WitchApprenticeQuest), out var inRestartPeriod))
|
||||
{
|
||||
PlaySound(0x20);
|
||||
PlaySound(0x206);
|
||||
newQuest.SendOffer();
|
||||
}
|
||||
else if (inRestartPeriod)
|
||||
{
|
||||
PlaySound(0x259);
|
||||
PlaySound(0x206);
|
||||
newQuest.AddConversation(new RecentlyFinishedConversation());
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.IsObjectiveInProgress(typeof(FindApprenticeObjective)))
|
||||
{
|
||||
PlaySound(0x259);
|
||||
PlaySound(0x206);
|
||||
qs.AddConversation(new HagDuringCorpseSearchConversation());
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.FindObjective<FindGrizeldaAboutMurderObjective>() is { Completed: false } obj1)
|
||||
{
|
||||
PlaySound(0x420);
|
||||
PlaySound(0x20);
|
||||
obj1.Complete();
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.IsObjectiveInProgress(typeof(KillImpsObjective))
|
||||
|| qs.IsObjectiveInProgress(typeof(FindZeefzorpulObjective)))
|
||||
{
|
||||
PlaySound(0x259);
|
||||
PlaySound(0x206);
|
||||
qs.AddConversation(new HagDuringImpSearchConversation());
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.FindObjective<ReturnRecipeObjective>() is { Completed: false } obj2)
|
||||
{
|
||||
PlaySound(0x258);
|
||||
PlaySound(0x41B);
|
||||
obj2.Complete();
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.IsObjectiveInProgress(typeof(FindIngredientObjective)))
|
||||
{
|
||||
PlaySound(0x259);
|
||||
PlaySound(0x206);
|
||||
qs.AddConversation(new HagDuringIngredientsConversation());
|
||||
return;
|
||||
}
|
||||
|
||||
if (qs.FindObjective<ReturnIngredientsObjective>() is { Completed: false } obj3)
|
||||
{
|
||||
var 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 Cauldron());
|
||||
cont.DropItem(new MoonfireBrew());
|
||||
cont.DropItem(new TreasureMap(Utility.RandomMinMax(1, 4), Map));
|
||||
cont.DropItem(new Gold(2000, 2200));
|
||||
|
||||
if (Utility.RandomBool())
|
||||
{
|
||||
var weapon = Loot.RandomWeapon();
|
||||
|
||||
if (Core.AOS)
|
||||
{
|
||||
PlaySound(0x259);
|
||||
PlaySound(0x206);
|
||||
qs.AddConversation(new HagDuringCorpseSearchConversation());
|
||||
BaseRunicTool.ApplyAttributesTo(weapon, 2, 20, 30);
|
||||
}
|
||||
else
|
||||
{
|
||||
QuestObjective obj = qs.FindObjective<FindGrizeldaAboutMurderObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
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<ReturnRecipeObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
PlaySound(0x258);
|
||||
PlaySound(0x41B);
|
||||
obj.Complete();
|
||||
}
|
||||
else if (qs.IsObjectiveInProgress(typeof(FindIngredientObjective)))
|
||||
{
|
||||
PlaySound(0x259);
|
||||
PlaySound(0x206);
|
||||
qs.AddConversation(new HagDuringIngredientsConversation());
|
||||
}
|
||||
else
|
||||
{
|
||||
obj = qs.FindObjective<ReturnIngredientsObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
var 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 Cauldron());
|
||||
cont.DropItem(new MoonfireBrew());
|
||||
cont.DropItem(new TreasureMap(Utility.RandomMinMax(1, 4), Map));
|
||||
cont.DropItem(new Gold(2000, 2200));
|
||||
|
||||
if (Utility.RandomBool())
|
||||
{
|
||||
var 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);
|
||||
}
|
||||
|
||||
cont.DropItem(weapon);
|
||||
}
|
||||
else
|
||||
{
|
||||
Item item;
|
||||
|
||||
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
|
||||
{
|
||||
var armor = Loot.RandomArmorOrShield();
|
||||
item = armor;
|
||||
|
||||
armor.ProtectionLevel = (ArmorProtectionLevel)RandomMinMaxScaled(2, 3);
|
||||
armor.Durability = (ArmorDurabilityLevel)RandomMinMaxScaled(2, 3);
|
||||
}
|
||||
|
||||
cont.DropItem(item);
|
||||
}
|
||||
|
||||
if (player.BAC > 0)
|
||||
{
|
||||
cont.DropItem(new HangoverCure());
|
||||
}
|
||||
|
||||
if (player.PlaceInBackpack(cont))
|
||||
{
|
||||
var gainedPath = false;
|
||||
|
||||
if (VirtueSystem.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.
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
weapon.DamageLevel = (WeaponDamageLevel)RandomMinMaxScaled(2, 3);
|
||||
weapon.AccuracyLevel = (WeaponAccuracyLevel)RandomMinMaxScaled(2, 3);
|
||||
weapon.DurabilityLevel = (WeaponDurabilityLevel)RandomMinMaxScaled(2, 3);
|
||||
}
|
||||
|
||||
cont.DropItem(weapon);
|
||||
}
|
||||
else
|
||||
{
|
||||
QuestSystem newQuest = new WitchApprenticeQuest(player);
|
||||
Item item;
|
||||
|
||||
if (qs != null)
|
||||
if (Core.AOS)
|
||||
{
|
||||
newQuest.AddConversation(new DontOfferConversation());
|
||||
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 if (QuestSystem.CanOfferQuest(player, typeof(WitchApprenticeQuest), out var inRestartPeriod))
|
||||
else
|
||||
{
|
||||
PlaySound(0x20);
|
||||
PlaySound(0x206);
|
||||
newQuest.SendOffer();
|
||||
}
|
||||
else if (inRestartPeriod)
|
||||
{
|
||||
PlaySound(0x259);
|
||||
PlaySound(0x206);
|
||||
newQuest.AddConversation(new RecentlyFinishedConversation());
|
||||
var armor = Loot.RandomArmorOrShield();
|
||||
item = armor;
|
||||
|
||||
armor.ProtectionLevel = (ArmorProtectionLevel)RandomMinMaxScaled(2, 3);
|
||||
armor.Durability = (ArmorDurabilityLevel)RandomMinMaxScaled(2, 3);
|
||||
}
|
||||
|
||||
cont.DropItem(item);
|
||||
}
|
||||
}
|
||||
|
||||
public override void Serialize(IGenericWriter writer)
|
||||
{
|
||||
base.Serialize(writer);
|
||||
if (player.BAC > 0)
|
||||
{
|
||||
cont.DropItem(new HangoverCure());
|
||||
}
|
||||
|
||||
writer.Write(0); // version
|
||||
}
|
||||
if (player.PlaceInBackpack(cont))
|
||||
{
|
||||
var gainedPath = false;
|
||||
|
||||
public override void Deserialize(IGenericReader reader)
|
||||
{
|
||||
base.Deserialize(reader);
|
||||
// TODO: Check amount on OSI.
|
||||
if (VirtueSystem.Award(player, VirtueName.Sacrifice, 250, ref gainedPath))
|
||||
{
|
||||
player.SendLocalizedMessage(1054160); // You have gained in sacrifice.
|
||||
}
|
||||
|
||||
var version = reader.ReadInt();
|
||||
PlaySound(0x253);
|
||||
PlaySound(0x20);
|
||||
obj3.Complete();
|
||||
}
|
||||
else
|
||||
{
|
||||
cont.Delete();
|
||||
// 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.
|
||||
player.SendLocalizedMessage(1046260);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -61,7 +61,7 @@ namespace Server.Engines.Quests.Hag
|
|||
Timer.StartTimer(TimeSpan.FromSeconds(3.0), () => DeleteImp(imp));
|
||||
}
|
||||
|
||||
private void DeleteImp(Mobile m)
|
||||
private static void DeleteImp(Mobile m)
|
||||
{
|
||||
if (m?.Deleted == false)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -608,7 +608,7 @@ public abstract partial class BaseBeverage : Item, IHasQuantity
|
|||
{
|
||||
if (from is PlayerMobile { Quest: SolenMatriarchQuest qs })
|
||||
{
|
||||
QuestObjective obj = qs.FindObjective<GatherWaterObjective>();
|
||||
var obj = qs.FindObjective<GatherWaterObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -183,7 +183,7 @@ public partial class BankCheck : Item
|
|||
|
||||
if (qs is DarkTidesQuest)
|
||||
{
|
||||
QuestObjective obj = qs.FindObjective<CashBankCheckObjective>();
|
||||
var obj = qs.FindObjective<CashBankCheckObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -47,16 +47,19 @@ public static class CorpsePackets
|
|||
}
|
||||
}
|
||||
|
||||
if (beheld.Hair?.ItemID > 0)
|
||||
if (beheld.Owner != null)
|
||||
{
|
||||
writer.Write((byte)(Layer.Hair + 1));
|
||||
writer.Write(HairInfo.FakeSerial(beheld.Owner.Serial) - 2);
|
||||
}
|
||||
if (beheld.Hair?.ItemID > 0)
|
||||
{
|
||||
writer.Write((byte)(Layer.Hair + 1));
|
||||
writer.Write(HairInfo.FakeSerial(beheld.Owner.Serial) - 2);
|
||||
}
|
||||
|
||||
if (beheld.FacialHair?.ItemID > 0)
|
||||
{
|
||||
writer.Write((byte)(Layer.FacialHair + 1));
|
||||
writer.Write(FacialHairInfo.FakeSerial(beheld.Owner.Serial) - 2);
|
||||
if (beheld.FacialHair?.ItemID > 0)
|
||||
{
|
||||
writer.Write((byte)(Layer.FacialHair + 1));
|
||||
writer.Write(FacialHairInfo.FakeSerial(beheld.Owner.Serial) - 2);
|
||||
}
|
||||
}
|
||||
|
||||
writer.Write((byte)Layer.Invalid);
|
||||
|
|
@ -115,38 +118,41 @@ public static class CorpsePackets
|
|||
}
|
||||
}
|
||||
|
||||
if (hairItemID > 0)
|
||||
if (beheld.Owner != null)
|
||||
{
|
||||
writer.Write(HairInfo.FakeSerial(beheld.Owner.Serial) - 2);
|
||||
writer.Write((ushort)hairItemID);
|
||||
writer.Write((byte)0); // signed, itemID offset
|
||||
writer.Write((ushort)1);
|
||||
writer.Write(0); // X/Y
|
||||
if (ns.ContainerGridLines)
|
||||
if (hairItemID > 0)
|
||||
{
|
||||
writer.Write((byte)0); // Grid Location?
|
||||
writer.Write(HairInfo.FakeSerial(beheld.Owner.Serial) - 2);
|
||||
writer.Write((ushort)hairItemID);
|
||||
writer.Write((byte)0); // signed, itemID offset
|
||||
writer.Write((ushort)1);
|
||||
writer.Write(0); // X/Y
|
||||
if (ns.ContainerGridLines)
|
||||
{
|
||||
writer.Write((byte)0); // Grid Location?
|
||||
}
|
||||
writer.Write(beheld.Serial);
|
||||
writer.Write((ushort)beheld.Hair!.Hue);
|
||||
|
||||
++written;
|
||||
}
|
||||
writer.Write(beheld.Serial);
|
||||
writer.Write((ushort)beheld.Hair!.Hue);
|
||||
|
||||
++written;
|
||||
}
|
||||
|
||||
if (facialHairItemID > 0)
|
||||
{
|
||||
writer.Write(FacialHairInfo.FakeSerial(beheld.Owner.Serial) - 2);
|
||||
writer.Write((ushort)facialHairItemID);
|
||||
writer.Write((byte)0); // signed, itemID offset
|
||||
writer.Write((ushort)1);
|
||||
writer.Write(0); // X/Y
|
||||
if (ns.ContainerGridLines)
|
||||
if (facialHairItemID > 0)
|
||||
{
|
||||
writer.Write((byte)0); // Grid Location?
|
||||
}
|
||||
writer.Write(beheld.Serial);
|
||||
writer.Write((ushort)beheld.FacialHair!.Hue);
|
||||
writer.Write(FacialHairInfo.FakeSerial(beheld.Owner.Serial) - 2);
|
||||
writer.Write((ushort)facialHairItemID);
|
||||
writer.Write((byte)0); // signed, itemID offset
|
||||
writer.Write((ushort)1);
|
||||
writer.Write(0); // X/Y
|
||||
if (ns.ContainerGridLines)
|
||||
{
|
||||
writer.Write((byte)0); // Grid Location?
|
||||
}
|
||||
writer.Write(beheld.Serial);
|
||||
writer.Write((ushort)beheld.FacialHair!.Hue);
|
||||
|
||||
++written;
|
||||
++written;
|
||||
}
|
||||
}
|
||||
|
||||
writer.Seek(1, SeekOrigin.Begin);
|
||||
|
|
|
|||
4
Projects/UOContent/Migrations/Server.Engines.Quests.Hag.Grizelda.v0.json
generated
Normal file
4
Projects/UOContent/Migrations/Server.Engines.Quests.Hag.Grizelda.v0.json
generated
Normal file
|
|
@ -0,0 +1,4 @@
|
|||
{
|
||||
"version": 0,
|
||||
"type": "Server.Engines.Quests.Hag.Grizelda"
|
||||
}
|
||||
4
Projects/UOContent/Migrations/Server.Engines.Quests.Hag.HagApprenticeCorpse.v0.json
generated
Normal file
4
Projects/UOContent/Migrations/Server.Engines.Quests.Hag.HagApprenticeCorpse.v0.json
generated
Normal file
|
|
@ -0,0 +1,4 @@
|
|||
{
|
||||
"version": 0,
|
||||
"type": "Server.Engines.Quests.Hag.HagApprenticeCorpse"
|
||||
}
|
||||
14
Projects/UOContent/Migrations/Server.Engines.Quests.Hag.HangoverCure.v0.json
generated
Normal file
14
Projects/UOContent/Migrations/Server.Engines.Quests.Hag.HangoverCure.v0.json
generated
Normal file
|
|
@ -0,0 +1,14 @@
|
|||
{
|
||||
"version": 0,
|
||||
"type": "Server.Engines.Quests.Hag.HangoverCure",
|
||||
"properties": [
|
||||
{
|
||||
"name": "Uses",
|
||||
"type": "int",
|
||||
"rule": "PrimitiveTypeMigrationRule",
|
||||
"ruleArguments": [
|
||||
"EncodedInt"
|
||||
]
|
||||
}
|
||||
]
|
||||
}
|
||||
4
Projects/UOContent/Migrations/Server.Engines.Quests.Hag.MagicFlute.v0.json
generated
Normal file
4
Projects/UOContent/Migrations/Server.Engines.Quests.Hag.MagicFlute.v0.json
generated
Normal file
|
|
@ -0,0 +1,4 @@
|
|||
{
|
||||
"version": 0,
|
||||
"type": "Server.Engines.Quests.Hag.MagicFlute"
|
||||
}
|
||||
4
Projects/UOContent/Migrations/Server.Engines.Quests.Hag.MoonfireBrew.v0.json
generated
Normal file
4
Projects/UOContent/Migrations/Server.Engines.Quests.Hag.MoonfireBrew.v0.json
generated
Normal file
|
|
@ -0,0 +1,4 @@
|
|||
{
|
||||
"version": 0,
|
||||
"type": "Server.Engines.Quests.Hag.MoonfireBrew"
|
||||
}
|
||||
16
Projects/UOContent/Migrations/Server.Engines.Quests.Haven.Cannon.v0.json
generated
Normal file
16
Projects/UOContent/Migrations/Server.Engines.Quests.Haven.Cannon.v0.json
generated
Normal file
|
|
@ -0,0 +1,16 @@
|
|||
{
|
||||
"version": 0,
|
||||
"type": "Server.Engines.Quests.Haven.Cannon",
|
||||
"properties": [
|
||||
{
|
||||
"name": "CannonDirection",
|
||||
"type": "Server.Engines.Quests.Haven.CannonDirection",
|
||||
"rule": "EnumMigrationRule"
|
||||
},
|
||||
{
|
||||
"name": "Canoneer",
|
||||
"type": "Server.Engines.Quests.Haven.MilitiaCanoneer",
|
||||
"rule": "SerializableInterfaceMigrationRule"
|
||||
}
|
||||
]
|
||||
}
|
||||
4
Projects/UOContent/Migrations/Server.Engines.Quests.Haven.CannonComponent.v0.json
generated
Normal file
4
Projects/UOContent/Migrations/Server.Engines.Quests.Haven.CannonComponent.v0.json
generated
Normal file
|
|
@ -0,0 +1,4 @@
|
|||
{
|
||||
"version": 0,
|
||||
"type": "Server.Engines.Quests.Haven.CannonComponent"
|
||||
}
|
||||
4
Projects/UOContent/Migrations/Server.Engines.Quests.Haven.DaemonBloodChest.v0.json
generated
Normal file
4
Projects/UOContent/Migrations/Server.Engines.Quests.Haven.DaemonBloodChest.v0.json
generated
Normal file
|
|
@ -0,0 +1,4 @@
|
|||
{
|
||||
"version": 0,
|
||||
"type": "Server.Engines.Quests.Haven.DaemonBloodChest"
|
||||
}
|
||||
4
Projects/UOContent/Migrations/Server.Engines.Quests.Haven.Dryad.v0.json
generated
Normal file
4
Projects/UOContent/Migrations/Server.Engines.Quests.Haven.Dryad.v0.json
generated
Normal file
|
|
@ -0,0 +1,4 @@
|
|||
{
|
||||
"version": 0,
|
||||
"type": "Server.Engines.Quests.Haven.Dryad"
|
||||
}
|
||||
4
Projects/UOContent/Migrations/Server.Engines.Quests.Haven.MansionGuard.v0.json
generated
Normal file
4
Projects/UOContent/Migrations/Server.Engines.Quests.Haven.MansionGuard.v0.json
generated
Normal file
|
|
@ -0,0 +1,4 @@
|
|||
{
|
||||
"version": 0,
|
||||
"type": "Server.Engines.Quests.Haven.MansionGuard"
|
||||
}
|
||||
14
Projects/UOContent/Migrations/Server.Engines.Quests.Haven.MilitiaCanoneer.v0.json
generated
Normal file
14
Projects/UOContent/Migrations/Server.Engines.Quests.Haven.MilitiaCanoneer.v0.json
generated
Normal file
|
|
@ -0,0 +1,14 @@
|
|||
{
|
||||
"version": 0,
|
||||
"type": "Server.Engines.Quests.Haven.MilitiaCanoneer",
|
||||
"properties": [
|
||||
{
|
||||
"name": "Active",
|
||||
"type": "bool",
|
||||
"rule": "PrimitiveTypeMigrationRule",
|
||||
"ruleArguments": [
|
||||
""
|
||||
]
|
||||
}
|
||||
]
|
||||
}
|
||||
4
Projects/UOContent/Migrations/Server.Engines.Quests.Haven.MilitiaFighter.v0.json
generated
Normal file
4
Projects/UOContent/Migrations/Server.Engines.Quests.Haven.MilitiaFighter.v0.json
generated
Normal file
|
|
@ -0,0 +1,4 @@
|
|||
{
|
||||
"version": 0,
|
||||
"type": "Server.Engines.Quests.Haven.MilitiaFighter"
|
||||
}
|
||||
4
Projects/UOContent/Migrations/Server.Engines.Quests.Haven.MilitiaFighterCorpse.v0.json
generated
Normal file
4
Projects/UOContent/Migrations/Server.Engines.Quests.Haven.MilitiaFighterCorpse.v0.json
generated
Normal file
|
|
@ -0,0 +1,4 @@
|
|||
{
|
||||
"version": 0,
|
||||
"type": "Server.Engines.Quests.Haven.MilitiaFighterCorpse"
|
||||
}
|
||||
4
Projects/UOContent/Migrations/Server.Engines.Quests.Haven.QuestDaemonBlood.v0.json
generated
Normal file
4
Projects/UOContent/Migrations/Server.Engines.Quests.Haven.QuestDaemonBlood.v0.json
generated
Normal file
|
|
@ -0,0 +1,4 @@
|
|||
{
|
||||
"version": 0,
|
||||
"type": "Server.Engines.Quests.Haven.QuestDaemonBlood"
|
||||
}
|
||||
4
Projects/UOContent/Migrations/Server.Engines.Quests.Haven.QuestDaemonBone.v0.json
generated
Normal file
4
Projects/UOContent/Migrations/Server.Engines.Quests.Haven.QuestDaemonBone.v0.json
generated
Normal file
|
|
@ -0,0 +1,4 @@
|
|||
{
|
||||
"version": 0,
|
||||
"type": "Server.Engines.Quests.Haven.QuestDaemonBone"
|
||||
}
|
||||
4
Projects/UOContent/Migrations/Server.Engines.Quests.Haven.QuestFertileDirt.v0.json
generated
Normal file
4
Projects/UOContent/Migrations/Server.Engines.Quests.Haven.QuestFertileDirt.v0.json
generated
Normal file
|
|
@ -0,0 +1,4 @@
|
|||
{
|
||||
"version": 0,
|
||||
"type": "Server.Engines.Quests.Haven.QuestFertileDirt"
|
||||
}
|
||||
4
Projects/UOContent/Migrations/Server.Engines.Quests.Haven.Schmendrick.v0.json
generated
Normal file
4
Projects/UOContent/Migrations/Server.Engines.Quests.Haven.Schmendrick.v0.json
generated
Normal file
|
|
@ -0,0 +1,4 @@
|
|||
{
|
||||
"version": 0,
|
||||
"type": "Server.Engines.Quests.Haven.Schmendrick"
|
||||
}
|
||||
11
Projects/UOContent/Migrations/Server.Engines.Quests.Haven.SchmendrickApprenticeCorpse.v0.json
generated
Normal file
11
Projects/UOContent/Migrations/Server.Engines.Quests.Haven.SchmendrickApprenticeCorpse.v0.json
generated
Normal file
|
|
@ -0,0 +1,11 @@
|
|||
{
|
||||
"version": 0,
|
||||
"type": "Server.Engines.Quests.Haven.SchmendrickApprenticeCorpse",
|
||||
"properties": [
|
||||
{
|
||||
"name": "Lantern",
|
||||
"type": "Server.Items.Lantern",
|
||||
"rule": "SerializableInterfaceMigrationRule"
|
||||
}
|
||||
]
|
||||
}
|
||||
4
Projects/UOContent/Migrations/Server.Engines.Quests.Haven.SchmendrickScrollOfPower.v0.json
generated
Normal file
4
Projects/UOContent/Migrations/Server.Engines.Quests.Haven.SchmendrickScrollOfPower.v0.json
generated
Normal file
|
|
@ -0,0 +1,4 @@
|
|||
{
|
||||
"version": 0,
|
||||
"type": "Server.Engines.Quests.Haven.SchmendrickScrollOfPower"
|
||||
}
|
||||
4
Projects/UOContent/Migrations/Server.Engines.Quests.Haven.Uzeraan.v0.json
generated
Normal file
4
Projects/UOContent/Migrations/Server.Engines.Quests.Haven.Uzeraan.v0.json
generated
Normal file
|
|
@ -0,0 +1,4 @@
|
|||
{
|
||||
"version": 0,
|
||||
"type": "Server.Engines.Quests.Haven.Uzeraan"
|
||||
}
|
||||
4
Projects/UOContent/Migrations/Server.Engines.Quests.Haven.UzeraanTurmoilHorn.v0.json
generated
Normal file
4
Projects/UOContent/Migrations/Server.Engines.Quests.Haven.UzeraanTurmoilHorn.v0.json
generated
Normal file
|
|
@ -0,0 +1,4 @@
|
|||
{
|
||||
"version": 0,
|
||||
"type": "Server.Engines.Quests.Haven.UzeraanTurmoilHorn"
|
||||
}
|
||||
4
Projects/UOContent/Migrations/Server.Engines.Quests.Haven.UzeraanTurmoilTeleporter.v0.json
generated
Normal file
4
Projects/UOContent/Migrations/Server.Engines.Quests.Haven.UzeraanTurmoilTeleporter.v0.json
generated
Normal file
|
|
@ -0,0 +1,4 @@
|
|||
{
|
||||
"version": 0,
|
||||
"type": "Server.Engines.Quests.Haven.UzeraanTurmoilTeleporter"
|
||||
}
|
||||
4
Projects/UOContent/Migrations/Server.Engines.Quests.Matriarch.BaseSolenMatriarch.v0.json
generated
Normal file
4
Projects/UOContent/Migrations/Server.Engines.Quests.Matriarch.BaseSolenMatriarch.v0.json
generated
Normal file
|
|
@ -0,0 +1,4 @@
|
|||
{
|
||||
"version": 0,
|
||||
"type": "Server.Engines.Quests.Matriarch.BaseSolenMatriarch"
|
||||
}
|
||||
4
Projects/UOContent/Migrations/Server.Engines.Quests.Matriarch.BlackSolenMatriarch.v0.json
generated
Normal file
4
Projects/UOContent/Migrations/Server.Engines.Quests.Matriarch.BlackSolenMatriarch.v0.json
generated
Normal file
|
|
@ -0,0 +1,4 @@
|
|||
{
|
||||
"version": 0,
|
||||
"type": "Server.Engines.Quests.Matriarch.BlackSolenMatriarch"
|
||||
}
|
||||
4
Projects/UOContent/Migrations/Server.Engines.Quests.Matriarch.RedSolenMatriarch.v0.json
generated
Normal file
4
Projects/UOContent/Migrations/Server.Engines.Quests.Matriarch.RedSolenMatriarch.v0.json
generated
Normal file
|
|
@ -0,0 +1,4 @@
|
|||
{
|
||||
"version": 0,
|
||||
"type": "Server.Engines.Quests.Matriarch.RedSolenMatriarch"
|
||||
}
|
||||
4
Projects/UOContent/Migrations/Server.Engines.Quests.Naturalist.Naturalist.v0.json
generated
Normal file
4
Projects/UOContent/Migrations/Server.Engines.Quests.Naturalist.Naturalist.v0.json
generated
Normal file
|
|
@ -0,0 +1,4 @@
|
|||
{
|
||||
"version": 0,
|
||||
"type": "Server.Engines.Quests.Naturalist.Naturalist"
|
||||
}
|
||||
4
Projects/UOContent/Migrations/Server.Engines.Quests.Zento.AnsellaGryen.v0.json
generated
Normal file
4
Projects/UOContent/Migrations/Server.Engines.Quests.Zento.AnsellaGryen.v0.json
generated
Normal file
|
|
@ -0,0 +1,4 @@
|
|||
{
|
||||
"version": 0,
|
||||
"type": "Server.Engines.Quests.Zento.AnsellaGryen"
|
||||
}
|
||||
4
Projects/UOContent/Migrations/Server.Items.Cauldron.v0.json
generated
Normal file
4
Projects/UOContent/Migrations/Server.Items.Cauldron.v0.json
generated
Normal file
|
|
@ -0,0 +1,4 @@
|
|||
{
|
||||
"version": 0,
|
||||
"type": "Server.Items.Cauldron"
|
||||
}
|
||||
4
Projects/UOContent/Migrations/Server.Items.HagCauldron.v0.json
generated
Normal file
4
Projects/UOContent/Migrations/Server.Items.HagCauldron.v0.json
generated
Normal file
|
|
@ -0,0 +1,4 @@
|
|||
{
|
||||
"version": 0,
|
||||
"type": "Server.Items.HagCauldron"
|
||||
}
|
||||
4
Projects/UOContent/Migrations/Server.Items.HagStew.v0.json
generated
Normal file
4
Projects/UOContent/Migrations/Server.Items.HagStew.v0.json
generated
Normal file
|
|
@ -0,0 +1,4 @@
|
|||
{
|
||||
"version": 0,
|
||||
"type": "Server.Items.HagStew"
|
||||
}
|
||||
|
|
@ -1373,7 +1373,7 @@ public abstract class BaseAI
|
|||
|
||||
if (qs is DarkTidesQuest)
|
||||
{
|
||||
QuestObjective obj = qs.FindObjective<FetchAbraxusScrollObjective>();
|
||||
var obj = qs.FindObjective<FetchAbraxusScrollObjective>();
|
||||
|
||||
if (obj?.Completed == false)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -148,12 +148,7 @@ namespace Server.Spells.Necromancy
|
|||
}
|
||||
else
|
||||
{
|
||||
Type type = null;
|
||||
|
||||
if (c.Owner != null)
|
||||
{
|
||||
type = c.Owner.GetType();
|
||||
}
|
||||
Type type = c.Owner?.GetType();
|
||||
|
||||
if (c.ItemID != 0x2006 || c.Animated || type == typeof(PlayerMobile) || type == null ||
|
||||
c.Owner?.Fame < 100 ||
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue