mirror of
https://github.com/islehorse/HISP.git
synced 2025-04-06 05:05:40 +12:00
395 lines
13 KiB
C#
Executable file
395 lines
13 KiB
C#
Executable file
using System;
|
|
using System.Collections.Generic;
|
|
using System.Linq;
|
|
|
|
using HISP.Game.Inventory;
|
|
using HISP.Player;
|
|
using HISP.Server;
|
|
using HISP.Game.Items;
|
|
|
|
namespace HISP.Game
|
|
{
|
|
public class Quest
|
|
{
|
|
public const string Shovel = "SHOVEL";
|
|
public const string Binoculars = "BINOCS";
|
|
public const string Rake = "RAKE";
|
|
public const string MagnifyingGlass = "MAGNIFY";
|
|
public const int CloudIslesQuest = 1373;
|
|
public struct QuestItemInfo
|
|
{
|
|
public int ItemId;
|
|
public int Quantity;
|
|
}
|
|
public struct QuestAltActivation
|
|
{
|
|
public string Type;
|
|
public int ActivateX;
|
|
public int ActivateY;
|
|
}
|
|
public struct QuestEntry
|
|
{
|
|
public int Id;
|
|
public string Notes;
|
|
public string Title;
|
|
|
|
public int[] RequiresQuestIdCompleteStatsMenu; // Not sure what this is for.
|
|
public QuestAltActivation AltActivation;
|
|
public bool Tracked; // Should we track how many times the player has completed this quest.
|
|
// Fail Settings
|
|
public int MaxRepeats;
|
|
public int MoneyCost;
|
|
public QuestItemInfo[] ItemsRequired;
|
|
public string FailNpcChat;
|
|
public int AwardRequired;
|
|
public int[] RequiresQuestIdCompleted;
|
|
public int[] RequiresQuestIdNotCompleted;
|
|
|
|
// Success Settings
|
|
public int MoneyEarned;
|
|
public QuestItemInfo[] ItemsEarned;
|
|
public int QuestPointsEarned;
|
|
public int SetNpcChatpoint;
|
|
public int GotoNpcChatpoint;
|
|
public int WarpX;
|
|
public int WarpY;
|
|
public string SuccessMessage;
|
|
public string SuccessNpcChat;
|
|
|
|
public bool HideReplyOnFail;
|
|
public string Difficulty;
|
|
public string Author;
|
|
public int ChainedQuestId;
|
|
public bool Minigame;
|
|
}
|
|
|
|
private static List<QuestEntry> questList = new List<QuestEntry>();
|
|
public static void AddQuestEntry(QuestEntry quest)
|
|
{
|
|
questList.Add(quest);
|
|
}
|
|
private static QuestEntry[] QuestList
|
|
{
|
|
get
|
|
{
|
|
return questList.ToArray();
|
|
}
|
|
}
|
|
public static int GetTotalQuestPoints()
|
|
{
|
|
int totalQp = 0;
|
|
QuestEntry[] quests = GetPublicQuestList();
|
|
foreach (QuestEntry quest in quests)
|
|
{
|
|
totalQp += quest.QuestPointsEarned;
|
|
}
|
|
return totalQp;
|
|
}
|
|
|
|
|
|
public static int GetTotalQuestsComplete(User user)
|
|
{
|
|
QuestEntry[] questList = GetPublicQuestList();
|
|
int totalComplete = 0;
|
|
foreach (QuestEntry quest in questList)
|
|
{
|
|
if (user.Quests.GetTrackedQuestAmount(quest.Id) > 0)
|
|
totalComplete++;
|
|
}
|
|
return totalComplete;
|
|
}
|
|
|
|
|
|
public static QuestEntry[] GetPublicQuestList()
|
|
{
|
|
QuestEntry[] quests = QuestList.OrderBy(o => o.Title).ToArray();
|
|
List<QuestEntry> sortedQuests = new List<QuestEntry>();
|
|
foreach (QuestEntry quest in quests)
|
|
{
|
|
if (quest.Title != null)
|
|
sortedQuests.Add(quest);
|
|
|
|
}
|
|
return sortedQuests.ToArray();
|
|
}
|
|
|
|
public class QuestResult
|
|
{
|
|
public QuestResult()
|
|
{
|
|
NpcChat = null;
|
|
SetChatpoint = -1;
|
|
GotoChatpoint = -1;
|
|
HideRepliesOnFail = false;
|
|
QuestCompleted = false;
|
|
}
|
|
public string NpcChat;
|
|
public int SetChatpoint;
|
|
public int GotoChatpoint;
|
|
public bool HideRepliesOnFail;
|
|
public bool QuestCompleted;
|
|
}
|
|
|
|
public static bool CanComplete(User user, QuestEntry quest)
|
|
{
|
|
// Has completed other required quests?
|
|
foreach (int questId in quest.RequiresQuestIdCompleted)
|
|
if (user.Quests.GetTrackedQuestAmount(questId) < 1)
|
|
return false;
|
|
|
|
// Has NOT competed other MUST NOT BE required quests
|
|
foreach (int questId in quest.RequiresQuestIdNotCompleted)
|
|
if (user.Quests.GetTrackedQuestAmount(questId) > 1)
|
|
return false;
|
|
|
|
if (quest.Tracked)
|
|
{
|
|
|
|
// Has allready tracked this quest?
|
|
if (user.Quests.GetTrackedQuestAmount(quest.Id) >= quest.MaxRepeats)
|
|
return false;
|
|
|
|
}
|
|
|
|
// Check if user has award unlocked
|
|
if (quest.AwardRequired != 0)
|
|
if (!user.Awards.HasAward(Award.GetAwardById(quest.AwardRequired)))
|
|
return false;
|
|
|
|
// Check if i have required items
|
|
foreach (QuestItemInfo itemInfo in quest.ItemsRequired)
|
|
{
|
|
bool hasThisItem = false;
|
|
InventoryItem[] items = user.Inventory.GetItemList();
|
|
foreach (InventoryItem item in items)
|
|
{
|
|
if (item.ItemId == itemInfo.ItemId && item.ItemInstances.Length >= itemInfo.Quantity)
|
|
{
|
|
hasThisItem = true;
|
|
break;
|
|
}
|
|
}
|
|
if (!hasThisItem)
|
|
return false;
|
|
}
|
|
|
|
// Have enough money?
|
|
if (user.Money < quest.MoneyCost)
|
|
return false;
|
|
|
|
|
|
return true;
|
|
}
|
|
|
|
public static QuestResult CompleteQuest(User user, QuestEntry quest, bool npcActivation = false, QuestResult res=null)
|
|
{
|
|
if(res == null)
|
|
res = new QuestResult();
|
|
// Take Items
|
|
foreach (QuestItemInfo itemInfo in quest.ItemsRequired)
|
|
{
|
|
InventoryItem itm = user.Inventory.GetItemByItemId(itemInfo.ItemId);
|
|
for (int i = 0; i < itemInfo.Quantity; i++)
|
|
user.Inventory.Remove(itm.ItemInstances[0]);
|
|
|
|
}
|
|
// Take Money
|
|
user.TakeMoney(quest.MoneyCost);
|
|
// Give money
|
|
user.AddMoney(quest.MoneyEarned);
|
|
// Give items
|
|
foreach (QuestItemInfo itemInfo in quest.ItemsEarned)
|
|
{
|
|
for (int i = 0; i < itemInfo.Quantity; i++)
|
|
{
|
|
ItemInstance itm = new ItemInstance(itemInfo.ItemId);
|
|
Item.ItemInformation itemInformation = itm.GetItemInfo();
|
|
if (itemInformation.Type == "CONCEPTUAL")
|
|
Item.ConsumeItem(user, itemInformation);
|
|
else
|
|
user.Inventory.AddIgnoringFull(itm);
|
|
}
|
|
}
|
|
if (quest.WarpX != 0 && quest.WarpY != 0)
|
|
user.Teleport(quest.WarpX, quest.WarpY);
|
|
|
|
// Give quest points
|
|
user.QuestPoints += quest.QuestPointsEarned;
|
|
|
|
res.QuestCompleted = true;
|
|
if (npcActivation)
|
|
{
|
|
if (quest.SuccessNpcChat != null && quest.SuccessNpcChat.Trim() != "")
|
|
res.NpcChat = quest.SuccessNpcChat;
|
|
|
|
if(quest.SetNpcChatpoint != -1)
|
|
res.SetChatpoint = quest.SetNpcChatpoint;
|
|
|
|
if(quest.GotoNpcChatpoint != -1)
|
|
res.GotoChatpoint = quest.GotoNpcChatpoint;
|
|
}
|
|
|
|
if (quest.Tracked)
|
|
user.Quests.TrackQuest(quest.Id);
|
|
|
|
if (quest.ChainedQuestId != 0)
|
|
res = ActivateQuest(user, Quest.GetQuestById(quest.ChainedQuestId), npcActivation, res);
|
|
|
|
if (quest.SuccessMessage != null)
|
|
{
|
|
byte[] ChatPacket = PacketBuilder.CreateChat(quest.SuccessMessage, PacketBuilder.CHAT_BOTTOM_RIGHT);
|
|
user.Client.SendPacket(ChatPacket);
|
|
}
|
|
|
|
if (quest.SuccessNpcChat != null)
|
|
{
|
|
if (!npcActivation)
|
|
{
|
|
byte[] ChatPacket = PacketBuilder.CreateChat(quest.SuccessNpcChat, PacketBuilder.CHAT_BOTTOM_RIGHT);
|
|
user.Client.SendPacket(ChatPacket);
|
|
}
|
|
}
|
|
|
|
// Check if award unlocked
|
|
int questPointsPercent = Convert.ToInt32(Math.Floor(((decimal)user.QuestPoints / (decimal)GetTotalQuestPoints()) * (decimal)100.0));
|
|
if (questPointsPercent >= 25)
|
|
user.Awards.AddAward(Award.GetAwardById(1)); // 25% Quest Completion Award.
|
|
if (questPointsPercent >= 50)
|
|
user.Awards.AddAward(Award.GetAwardById(2)); // 50% Quest Completion Award.
|
|
if (questPointsPercent >= 75)
|
|
user.Awards.AddAward(Award.GetAwardById(3)); // 75% Quest Completion Award.
|
|
if (questPointsPercent >= 100)
|
|
user.Awards.AddAward(Award.GetAwardById(4)); // 100% Quest Completion Award.
|
|
|
|
// Is cloud isles quest?
|
|
if (quest.Id == CloudIslesQuest)
|
|
{
|
|
byte[] swfLoadPacket = PacketBuilder.CreateSwfModule("ballooncutscene", PacketBuilder.PACKET_SWF_MODULE_CUTSCENE);
|
|
user.Client.SendPacket(swfLoadPacket);
|
|
}
|
|
|
|
return res;
|
|
}
|
|
public static QuestResult FailQuest(User user, QuestEntry quest, bool npcActivation = false, QuestResult res=null)
|
|
{
|
|
if(res == null)
|
|
res = new QuestResult();
|
|
res.QuestCompleted = false;
|
|
|
|
if(npcActivation)
|
|
{
|
|
if(quest.GotoNpcChatpoint != -1)
|
|
res.GotoChatpoint = quest.GotoNpcChatpoint;
|
|
if(quest.HideReplyOnFail != false)
|
|
res.HideRepliesOnFail = quest.HideReplyOnFail;
|
|
if(res.SetChatpoint != -1)
|
|
res.SetChatpoint = quest.SetNpcChatpoint;
|
|
}
|
|
if (quest.FailNpcChat != null)
|
|
{
|
|
if (!npcActivation)
|
|
{
|
|
byte[] ChatPacket = PacketBuilder.CreateChat(quest.FailNpcChat, PacketBuilder.CHAT_BOTTOM_RIGHT);
|
|
user.Client.SendPacket(ChatPacket);
|
|
}
|
|
else
|
|
{
|
|
if(quest.FailNpcChat != null)
|
|
{
|
|
if(npcActivation)
|
|
{
|
|
if (quest.FailNpcChat != "")
|
|
{
|
|
res.NpcChat = quest.FailNpcChat;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
return res;
|
|
}
|
|
public static QuestResult ActivateQuest(User user, QuestEntry quest, bool npcActivation = false, QuestResult res=null)
|
|
{
|
|
|
|
if (CanComplete(user, quest))
|
|
{
|
|
return CompleteQuest(user, quest, npcActivation, res);
|
|
}
|
|
else
|
|
{
|
|
return FailQuest(user, quest, npcActivation, res);
|
|
}
|
|
|
|
}
|
|
public static bool DoesQuestExist(int id)
|
|
{
|
|
try
|
|
{
|
|
GetQuestById(id);
|
|
return true;
|
|
}
|
|
catch(KeyNotFoundException)
|
|
{
|
|
return false;
|
|
}
|
|
}
|
|
public static QuestEntry GetQuestById(int id)
|
|
{
|
|
foreach(QuestEntry quest in QuestList)
|
|
{
|
|
if(quest.Id == id)
|
|
{
|
|
return quest;
|
|
}
|
|
}
|
|
throw new KeyNotFoundException("Quest Id: " + id + " Dont exist.");
|
|
}
|
|
public static bool UseTool(User user, string tool, int x, int y)
|
|
{
|
|
if (tool == Quest.Shovel)
|
|
{
|
|
// check Treasures
|
|
if (Treasure.IsTileTreasure(x, y))
|
|
{
|
|
Treasure treasure = Treasure.GetTreasureAt(x, y);
|
|
if(treasure.Type == "BURIED")
|
|
treasure.CollectTreasure(user);
|
|
return true;
|
|
}
|
|
}
|
|
|
|
QuestResult result = null;
|
|
|
|
foreach (QuestEntry quest in QuestList)
|
|
{
|
|
|
|
if (quest.AltActivation.Type == tool && quest.AltActivation.ActivateX == x && quest.AltActivation.ActivateY == y)
|
|
{
|
|
result = ActivateQuest(user, quest, true, result);
|
|
if(result.QuestCompleted)
|
|
{
|
|
if(result.NpcChat != null)
|
|
{
|
|
byte[] ChatPacket = PacketBuilder.CreateChat(result.NpcChat, PacketBuilder.CHAT_BOTTOM_RIGHT);
|
|
user.Client.SendPacket(ChatPacket);
|
|
}
|
|
return true;
|
|
}
|
|
}
|
|
}
|
|
|
|
if(result != null)
|
|
{
|
|
if (result.NpcChat != null)
|
|
{
|
|
byte[] ChatPacket = PacketBuilder.CreateChat(result.NpcChat, PacketBuilder.CHAT_BOTTOM_RIGHT);
|
|
user.Client.SendPacket(ChatPacket);
|
|
}
|
|
return true;
|
|
}
|
|
|
|
|
|
return false;
|
|
}
|
|
}
|
|
}
|