1
Fork 0
mirror of https://bitbucket.org/Ioncannon/project-meteor-server.git synced 2025-04-20 19:57:46 +00:00

Merge remote-tracking branch 'origin/ioncannon/quest_system' into Jorge/quest_system

# Conflicts:
#	Data/scripts/commands/EmoteSitCommand.lua  - Resolved using Theirs
This commit is contained in:
CuriousJorge 2022-03-11 19:21:42 -05:00
commit e94c037fb5
73 changed files with 1096 additions and 212 deletions

View file

@ -1,17 +1,37 @@
function init(npc)
require("global");
--[[
PrivateAreaPastExit
This object contains the player inside a PrivateAreaPast, stopping them from escaping it's bounds. It is the
object that generates the circle graphic on the minimap. This object always has two push triggers, an inner
and outer inverted circle. The inner one is named "caution" and the outer one is named "exit". When the player
leaves the inner circle a warning is shown and when they leave the outer circle they either leave the instance
or get warped back to the center.
]]
function init(privAreaExit)
return false, false, 0, 0;
end
function onEventStarted(player, npc, eventType, eventName)
function onEventStarted(player, privAreaExit, eventType, eventName)
player:EndEvent();
if (eventName == "caution") then
player:SendGameMessage(player, GetWorldMaster(), 34109, 0x20);
player:SendGameMessage(player, GetWorldMaster(), 34109, MESSAGE_TYPE_SYSTEM); -- You are about to leave the instance.
elseif (eventName == "exit") then
local activeQuests = player:GetQuestsForNpc(npc);
print(tostring(#activeQuests));
if (#activeQuests >= 1) then
activeQuests[1]:OnPush(player, npc, eventName);
local area = privAreaExit.CurrentArea;
if (area.IsPrivate()) then
-- If you can leave, warp to public zone and show message.
if (area.CanExitPrivateArea()) then
player:SendGameMessage(player, GetWorldMaster(), 34110, MESSAGE_TYPE_SYSTEM); -- You have left the instance.
GetWorldManager():WarpToPublicArea(player);
-- Otherwise warp back to the center of the zone.
else
GetWorldManager():WarpToCharaPosition(player, privAreaExit);
end
end
end
end

View file

@ -13,7 +13,7 @@ local attackMagicHandlers = {
}
function onEventStarted(player, command, triggerName, arg1, arg2, arg3, arg4, targetActor, arg5, arg6, arg7, arg8)
function onEventStarted(player, command, eventType, eventName, arg1, arg2, arg3, arg4, targetActor, arg5, arg6, arg7, arg8)
player.Ability(command.Id, targetActor);
player:endEvent();
end

View file

@ -1,5 +1,5 @@
require("global")
function onEventStarted(player, command, triggerName, arg1, arg2, arg3, arg4, targetActor, arg5, arg6, arg7, arg8)
function onEventStarted(player, command, eventType, eventName, arg1, arg2, arg3, arg4, targetActor, arg5, arg6, arg7, arg8)
end

View file

@ -13,7 +13,7 @@ local attackMagicHandlers = {
}
function onEventStarted(player, command, triggerName, arg1, arg2, arg3, arg4, targetActor, arg5, arg6, arg7, arg8)
function onEventStarted(player, command, eventType, eventName, arg1, arg2, arg3, arg4, targetActor, arg5, arg6, arg7, arg8)
player.Ability(command.Id, targetActor);
player:endEvent();

View file

@ -13,7 +13,7 @@ local attackMagicHandlers = {
}
function onEventStarted(player, command, triggerName, arg1, arg2, arg3, arg4, targetActor, arg5, arg6, arg7, arg8)
function onEventStarted(player, command, eventType, eventName, arg1, arg2, arg3, arg4, targetActor, arg5, arg6, arg7, arg8)
player.Cast(command.Id, targetActor);
player:endEvent();
end;

View file

@ -9,7 +9,7 @@ Finds the correct weaponskill subscript to fire when a weaponskill actor is acti
--]]
function onEventStarted(player, command, triggerName, arg1, arg2, arg3, arg4, targetActor, arg5, arg6, arg7, arg8)
function onEventStarted(player, command, eventType, eventName, arg1, arg2, arg3, arg4, targetActor, arg5, arg6, arg7, arg8)
--Are they in active mode?
if (player:GetState() != 2) then

View file

@ -8,7 +8,7 @@ Handles what happens when you examine a player's bazaar
require ("global")
function onEventStarted(player, actor, triggerName, name, arg1, arg2, arg3, bazaarActorId)
function onEventStarted(player, actor, eventType, eventName, name, arg1, arg2, arg3, bazaarActorId)
local bazaarActor = nil;

View file

@ -20,7 +20,7 @@ seekAmount: The amount of seekItem we want.
require ("global")
function onEventStarted(player, actor, triggerName, rewardItem, seekItem, bazaarMode, arg1, bazaarActor, rewardAmount, seekAmount, arg2, arg3, type9ItemIds)
function onEventStarted(player, actor, eventType, eventName, rewardItem, seekItem, bazaarMode, arg1, bazaarActor, rewardAmount, seekAmount, arg2, arg3, type9ItemIds)
local rewarding = nil;
local seeking = nil;

View file

@ -10,7 +10,7 @@ All bazaar args have a Reward (The item the person who fufills the request gets)
--TODO REFACTOR
function onEventStarted(player, actor, triggerName, rewardItem, seekItemOrCost, seekAmount, arg1, bazaarActorId, rewardAmount, rewardItemId, nameIndex, arg2, type9ItemIds)
function onEventStarted(player, actor, eventType, eventName, rewardItem, seekItemOrCost, seekAmount, arg1, bazaarActorId, rewardAmount, rewardItemId, nameIndex, arg2, type9ItemIds)
local originalReward = nil;
local originalSeek = nil;

View file

@ -13,7 +13,7 @@ Handles canceling bazaar items
--]]
function onEventStarted(player, actor, triggerName, rewardItem, seekItem, bazaarType, narg, bazaarActor, rewardAmount, seekAmount, narg, narg, type9ItemIds)
function onEventStarted(player, actor, eventType, eventName, rewardItem, seekItem, bazaarType, narg, bazaarActor, rewardAmount, seekAmount, narg, narg, type9ItemIds)
GetWorldManager():RemoveFromBazaar(player, player:GetItem(rewardItem));

View file

@ -10,7 +10,7 @@ operateUI(pointsAvailable, pointsLimit, str, vit, dex, int, min, pie)
require ("global")
function onEventStarted(player, actor, triggerName)
function onEventStarted(player, actor, eventType, eventName)
--local points = player:GetAttributePoints();
--player:RunEventFunction("delegateCommand", actor, "operateUI", points.available, points.limit, points.inSTR, points.inVIT, points.inDEX, points.inINT, points.inMIN, points.inPIT);
result = callClientFunction(player, "delegateCommand", actor, "operateUI", 100, 100, 10, 10, 10, 10, 10, 10);

View file

@ -1,4 +1,4 @@
function onEventStarted(player, caller, commandRequest, arg1, arg2, arg3, arg4, arg5, arg6, arg7, arg8)
function onEventStarted(player, caller, eventType, eventName, arg1, arg2, arg3, arg4, arg5, arg6, arg7, arg8)
player:SetCurrentJob(17);

View file

@ -6,7 +6,7 @@ Handles player examining someone
--]]
function onEventStarted(player, commandactor, triggerName, arg1, arg2, arg3, arg4, checkedActorId)
function onEventStarted(player, commandactor, eventType, eventName, arg1, arg2, arg3, arg4, checkedActorId)
actor = player:GetActorInInstance(checkedActorId);

View file

@ -8,9 +8,7 @@ Handles mounting and dismounting the Chocobo and Goobbue
require ("global")
function onEventStarted(player, actor, triggerName, isGoobbue)
<<<<<<< HEAD
function onEventStarted(player, actor, eventType, eventName, isGoobbue)
if (player:GetState() == 0) then
worldMaster = GetWorldMaster();
@ -45,48 +43,6 @@ function onEventStarted(player, actor, triggerName, isGoobbue)
player:SetMountState(0);
player:ChangeSpeed(0.0, 2.0, 5.0, 5.0)
player:ChangeState(0);
end
end
player:EndEvent();
=======
if (player:GetState() == 0) then
worldMaster = GetWorldMaster();
if (isGoobbue ~= true) then
player:ChangeMusic(83);
player:SendGameMessage(player, worldMaster, 26001, 0x20);
player:SetMountState(1);
else
player:ChangeMusic(98);
player:SendGameMessage(player, worldMaster, 26019, 0x20);
player:SetMountState(2);
end
player:ChangeSpeed(0.0, 5.0, 10.0, 10.0);
player:ChangeState(15);
else
player:ChangeMusic(player.CurrentArea.bgmDay);
worldMaster = GetWorldMaster();
if (player.rentalExpireTime != 0) then
player:SendGameMessage(player, worldMaster, 26004, 0x20); --You dismount.
else
if (player:GetMountState() == 1) then
player:SendGameMessage(player, worldMaster, 26003, 0x20); --You dismount X.
else
player:SendGameMessage(player, worldMaster, 26021, 0x20); --You dismount your Gobbue.
end
end
player:SetMountState(0);
player:ChangeSpeed(0.0, 2.0, 5.0, 5.0)
player:ChangeState(0);
end
player:EndEvent();
>>>>>>> ioncannon/quest_system
end

View file

@ -124,7 +124,7 @@ local weaponskillHandlers = {
[0xA0F070EA] = nil
}
function onEventStarted(player, command, triggerName)
function onEventStarted(player, command, eventType, eventName)
--Are they in active mode?
if (player:GetState() != 2) then

View file

@ -6,7 +6,7 @@ Handles what happens when you resolve an invite to a group
--]]
function onEventStarted(player, actor, triggerName, groupType, result)
function onEventStarted(player, actor, eventType, eventName, groupType, result)
--Accept/Refuse happened, else just close the window
if (result == 1 or result == 2) then

View file

@ -6,7 +6,7 @@ Handles what happens when you accept/refuse a trade
--]]
function onEventStarted(player, actor, triggerName, groupType, result)
function onEventStarted(player, actor, eventType, eventName, groupType, result)
--Accept
if (result == 1) then

View file

@ -156,7 +156,7 @@ local skillAnim = {
local craftStartWidgetOpen = false;
function onEventStarted(player, commandactor, triggerName, arg1, arg2, arg3, arg4, checkedActorId)
function onEventStarted(player, commandactor, eventType, eventName, arg1, arg2, arg3, arg4, checkedActorId)
local MENU_CANCEL, MENU_MAINHAND, MENU_OFFHAND, MENU_REQUEST = 0, 1, 2, 3;
local MENU_RECENT, MENU_AWARDED, MENU_RECENT_DETAILED, MENU_AWARDED_DETAILED = 7, 8, 9, 10;

View file

@ -1,4 +1,4 @@
function onEventStarted(player, command, triggerName, arg1, arg2, arg3, arg4, targetActor, arg5, arg6, arg7, arg8)
function onEventStarted(player, command, eventType, eventName, arg1, arg2, arg3, arg4, targetActor, arg5, arg6, arg7, arg8)
player.Cast(command.Id, targetActor);
player:endEvent();

View file

@ -1,4 +1,4 @@
function onEventStarted(player, command, triggerName, arg1, arg2, arg3, arg4, targetActor, arg5, arg6, arg7, arg8)
function onEventStarted(player, command, eventType, eventName, arg1, arg2, arg3, arg4, targetActor, arg5, arg6, arg7, arg8)
player.Cast(command.Id, targetActor);
player:endEvent();

View file

@ -9,7 +9,7 @@ Finds the correct weaponskill subscript to fire when a weaponskill actor is acti
--]]
function onEventStarted(player, command, triggerName, arg1, arg2, arg3, arg4, targetActor, arg5, arg6, arg7, arg8)
function onEventStarted(player, command, eventType, eventName, arg1, arg2, arg3, arg4, targetActor, arg5, arg6, arg7, arg8)
--Are they in active mode?
if (player:GetState() != 2) then

View file

@ -4,7 +4,7 @@ DiceCommand Script
--]]
function onEventStarted(player, actor, triggerName, maxNumber)
function onEventStarted(player, actor, eventType, eventName, maxNumber)
if (maxNumber == nil or maxNumber > 1000 or maxNumber < 1) then
maxNumber = 100;

View file

@ -99,7 +99,7 @@ nodeItems = {
require ("global")
function onEventStarted(player, commandActor, triggerName, arg1, arg2, arg3, arg4, checkedActorId)
function onEventStarted(player, commandActor, eventType, eventName, arg1, arg2, arg3, arg4, checkedActorId)
debugMsg = false;

View file

@ -1,4 +1,4 @@
function onEventStarted(player, command, triggerName, arg1, arg2, arg3, arg4, targetActor, arg5, arg6, arg7, arg8)
function onEventStarted(player, command, eventType, eventName, arg1, arg2, arg3, arg4, targetActor, arg5, arg6, arg7, arg8)
player.Cast(command.Id, targetActor);
player:endEvent();

View file

@ -4,7 +4,7 @@ EmoteSitCommand Script
--]]
function onEventStarted(player, actor, eventType, triggerName, emoteId)
function onEventStarted(player, actor, eventType, eventName, emoteId)
if (player:GetState() == 0) then
if (emoteId == 0x2712) then

View file

@ -6,7 +6,7 @@ require ("global")
--commandid: command being equipped
function onEventStarted(player, equipAbilityWidget, triggername, slot, commandid, unkown, arg1, arg2, arg3, arg4, arg5, arg6)
function onEventStarted(player, equipAbilityWidget, eventType, eventName, slot, commandid, unkown, arg1, arg2, arg3, arg4, arg5, arg6)
local worldManager = GetWorldManager();
local ability = worldManager:GetBattleCommand(commandid);

View file

@ -53,7 +53,7 @@ GRAPHICSLOT_L_RINGFINGER = 24;
GRAPHICSLOT_R_INDEXFINGER = 25;
GRAPHICSLOT_L_INDEXFINGER = 26;
function onEventStarted(player, actor, triggerName, equippedItem, param1, param2, param3, param4, param5, param6, param7, equipSlot, itemDBIds)
function onEventStarted(player, actor, eventType, eventName, equippedItem, param1, param2, param3, param4, param5, param6, param7, equipSlot, itemDBIds)
equipSlot = equipSlot-1;
--Equip Item

View file

@ -1,4 +1,4 @@
function onEventStarted(player, command, triggerName, arg1, arg2, arg3, arg4, targetActor, arg5, arg6, arg7, arg8)
function onEventStarted(player, command, eventType, eventName, arg1, arg2, arg3, arg4, targetActor, arg5, arg6, arg7, arg8)
player.Cast(command.Id, targetActor);
player:endEvent();

View file

@ -6,7 +6,7 @@ Handles moving items across item packages (IE: Taking loot)
--]]
function onEventStarted(player, actor, triggerName, itemReference, targetPackage, sourcePackage, arg1, arg2, unknown, arg3, arg4, arg5, type9ItemIds)
function onEventStarted(player, actor, eventType, eventName, itemReference, targetPackage, sourcePackage, arg1, arg2, unknown, arg3, arg4, arg5, type9ItemIds)
player:EndEvent();

View file

@ -6,7 +6,7 @@ Handles giving an item to another party member.
--]]
function onEventStarted(player, actor, triggerName, itemReference, targetPackage, sourcePackage, arg1, targetPlayer, arg2, arg3, arg4, arg5, type9ItemIds)
function onEventStarted(player, actor, eventType, eventName, itemReference, targetPackage, sourcePackage, arg1, targetPlayer, arg2, arg3, arg4, arg5, type9ItemIds)
player:EndEvent();

View file

@ -9,7 +9,7 @@ The param "itemDBIds" has the vars: item1 and item2.
--]]
function onEventStarted(player, actor, triggerName, itemReference, targetPackage, sourcePackage, arg1, arg2, unknown, arg3, arg4, arg5, type9ItemIds)
function onEventStarted(player, actor, eventType, eventName, itemReference, targetPackage, sourcePackage, arg1, arg2, unknown, arg3, arg4, arg5, type9ItemIds)
player:GetItemPackage(itemReference.itemPackage):RemoveItemAtSlot(itemReference.slot);
player:EndEvent();
end

View file

@ -4,7 +4,7 @@ LinkshellAppointCommand Script
--]]
function onEventStarted(player, actor, triggerName, linkshellName, memberName, rank)
function onEventStarted(player, actor, eventType, eventName, linkshellName, memberName, rank)
GetWorldManager():RequestWorldLinkshellRankChange(player, linkshellName, memberName, rank);
player:EndEvent();

View file

@ -4,7 +4,7 @@ LinkshellChangeCommand Script
--]]
function onEventStarted(player, actor, triggerName, linkshellName, arg1, arg2)
function onEventStarted(player, actor, eventType, eventName, linkshellName, arg1, arg2)
if (linkshellName == nil) then
linkshellName = "";

View file

@ -6,7 +6,7 @@ Handles what happens when you cancel an invite to a linkshell
--]]
function onEventStarted(player, actor, triggerName, arg1, arg2, arg3, arg4, actorId)
function onEventStarted(player, actor, eventType, eventName, arg1, arg2, arg3, arg4, actorId)
GetWorldManager():RequestWorldLinkshellCancelInvite(player);
player:EndEvent();

View file

@ -6,7 +6,7 @@ Handles what happens when you invite a player to a linkshell
--]]
function onEventStarted(player, actor, triggerName, linkshellName, arg1, arg2, arg3, actorId)
function onEventStarted(player, actor, eventType, eventName, linkshellName, arg1, arg2, arg3, actorId)
GetWorldManager():RequestWorldLinkshellInviteMember(player, linkshellName, actorId);
player:EndEvent();

View file

@ -4,7 +4,7 @@ LinkshellKickCommand Script
--]]
function onEventStarted(player, actor, triggerName, linkshellName, kickedName)
function onEventStarted(player, actor, eventType, eventName, linkshellName, kickedName)
GetWorldManager():RequestWorldLinkshellKick(player, linkshellName, kickedName);
player:EndEvent();

View file

@ -4,7 +4,7 @@ LinkshellLeaveCommand Script
--]]
function onEventStarted(player, actor, triggerName, linkshellName)
function onEventStarted(player, actor, eventType, eventName, linkshellName)
GetWorldManager():RequestWorldLinkshellLeave(player, linkshellName);
player:EndEvent();

View file

@ -8,7 +8,7 @@ Handles post-dream events.
require ("global")
function onEventStarted(player, actor, triggerName, dreamCode, innCode, narg1, narg2, bedActor)
function onEventStarted(player, actor, eventType, eventName, dreamCode, innCode, narg1, narg2, bedActor)
--In Plain Sight
if (dreamCode == 1) then

View file

@ -12,7 +12,7 @@ eventLogoutFade()
require ("global")
function onEventStarted(player, command, triggerName)
function onEventStarted(player, command, eventType, eventName)
choice = callClientFunction(player, "delegateCommand", command, "eventConfirm");

View file

@ -40,7 +40,7 @@ updateNegotiationWidget(player, gridIndex, key, itemIconId, pointValue, ?, ?) -
require ("global")
function onEventStarted(player, commandactor, triggerName, arg1, arg2, arg3, arg4, arg5)
function onEventStarted(player, commandactor, eventType, eventName, arg1, arg2, arg3, arg4, arg5)
negotiationJudge = GetStaticActor("NegotiationJudge");

View file

@ -4,13 +4,14 @@ require ("global")
NpcLinkshellChatCommand Script
Handler for when a player clicks a npc ls to talk to. If adding new linkshells to the handle, make sure to add
it to the handler table (with correct offset), and that your function is above the handler. If padding is needed
to hit some ID, add "nils".
Player class will go through all quests and see if there are active msgs for one. If there was, it will
return true and that quest must end the event (if needed). Otherwise if nothing caught the event, the
event is ended here.
--]]
function onEventStarted(player, command, eventType, eventName, npcLsId)
player:HandleNpcLS(npcLsId);
player:EndEvent();
if (player:HandleNpcLs(npcLsId) == false) then
player:EndEvent();
end
end

View file

@ -6,7 +6,7 @@ Handles disbanding the party.
--]]
function onEventStarted(player, actor, triggerName)
function onEventStarted(player, actor, eventType, eventName)
worldMaster = GetWorldMaster();
if (player:IsPartyLeader()) then

View file

@ -15,7 +15,7 @@ TextIds:
--]]
function onEventStarted(player, actor, name)
function onEventStarted(player, actor, eventType, eventName, name)
worldMaster = GetWorldMaster();
if (player:IsPartyLeader()) then

View file

@ -6,7 +6,7 @@ Handles what happens when you invite
--]]
function onEventStarted(player, actor, triggerName, name, arg1, arg2, arg3, actorId)
function onEventStarted(player, actor, eventType, eventName, name, arg1, arg2, arg3, actorId)
if (name ~= nil) then
GetWorldManager():CreateInvitePartyGroup(player, name);

View file

@ -15,7 +15,7 @@ TextIds:
--]]
function onEventStarted(player, actor, triggerName, name, arg2, arg3, arg4, actorId)
function onEventStarted(player, actor, eventType, eventName, name, arg2, arg3, arg4, actorId)
worldMaster = GetWorldMaster();
if (player:IsPartyLeader()) then

View file

@ -6,7 +6,7 @@ Handles requesting to change party leader and various errors.
--]]
function onEventStarted(player, actor, triggerName, name, arg2, arg3, arg4, actorId)
function onEventStarted(player, actor, eventType, eventName, name, arg2, arg3, arg4, actorId)
worldMaster = GetWorldMaster();
if (player:IsPartyLeader()) then

View file

@ -6,7 +6,7 @@ Handles leaving a party
--]]
function onEventStarted(player, actor, triggerName)
function onEventStarted(player, actor, eventType, eventName)
player:PartyLeave(name);
player:EndEvent();
end

View file

@ -27,7 +27,7 @@ markers = { -- [id] = {overheadIcon, textIcon}
}
function onEventStarted(player, actor, triggerName, commandValue, category, unk1, unk2, targetActor, unk3, unk4, unk5, unk6)
function onEventStarted(player, actor, eventType, eventName, commandValue, category, unk1, unk2, targetActor, unk3, unk4, unk5, unk6)
workName = "charaWork.parameterTemp.targetInformation";
uiFunc = "charaWork/stateForAll";

View file

@ -1,5 +1,5 @@
function onEventStarted(player, command, triggerName, arg1, arg2, arg3, arg4, targetActor, arg5, arg6, arg7, arg8)
function onEventStarted(player, command, eventType, eventName, arg1, arg2, arg3, arg4, targetActor, arg5, arg6, arg7, arg8)
player.Cast(command.Id, targetActor);

View file

@ -1,4 +1,4 @@
function onEventStarted(player, command, triggerName, arg1, arg2, arg3, arg4, targetActor, arg5, arg6, arg7, arg8)
function onEventStarted(player, command, eventType, eventName, arg1, arg2, arg3, arg4, targetActor, arg5, arg6, arg7, arg8)
player.Cast(command.Id, targetActor);
player:endEvent();

View file

@ -3,7 +3,7 @@
--]]
function onEventStarted(player, actor, questId)
function onEventStarted(player, actor, eventType, eventName, questId)
player:SendDataPacket("requestedData", "activegl", 7, nil, nil, nil, nil, nil, nil, nil);
-- player:SendRequestedInfo("requestedData", "glHist", 10, 0x1D4F2, 1009, 12464, 11727, 12485, 12526);
end

View file

@ -9,7 +9,7 @@ Finds the correct weaponskill subscript to fire when a weaponskill actor is acti
--]]
function onEventStarted(player, command, triggerName, arg1, arg2, arg3, arg4, targetActor, arg5, arg6, arg7, arg8)
function onEventStarted(player, command, eventType, eventName, arg1, arg2, arg3, arg4, targetActor, arg5, arg6, arg7, arg8)
player.Ability(command.Id, targetActor);
player:endEvent();
end;

View file

@ -13,7 +13,7 @@ local attackMagicHandlers = {
}
function onEventStarted(player, command, triggerName, arg1, arg2, arg3, arg4, targetActor, arg5, arg6, arg7, arg8)
function onEventStarted(player, command, eventType, eventName, arg1, arg2, arg3, arg4, targetActor, arg5, arg6, arg7, arg8)
player.Cast(command.Id, targetActor);
player:endEvent();
end;

View file

@ -24,7 +24,7 @@ reedit: Target has canceled their accept.
require ("global")
function onEventStarted(player, actor, triggerName)
function onEventStarted(player, actor, eventType, eventName)
callClientFunction(player, "delegateCommand", GetStaticActor("TradeExecuteCommand"), "processTradeCommandOpenTray");

View file

@ -6,7 +6,7 @@ Handles what happens a player cancels a trade
--]]
function onEventStarted(player, actor, triggerName, commandId, result)
function onEventStarted(player, actor, eventType, eventName, commandId, result)
GetWorldManager():CancelTrade(player);
player:EndEvent();

View file

@ -6,7 +6,7 @@ Handles what happens when you invite to trade
--]]
function onEventStarted(player, actor, triggerName, name, arg1, arg2, arg3, actorId)
function onEventStarted(player, actor, eventType, eventName, name, arg1, arg2, arg3, actorId)
local otherActor = nil;

View file

@ -24,6 +24,21 @@ vertical = {
["DESCEND"] = -1,
}
horizontal = {
["RIGHT"] = 2,
["R"] = 2,
["+"] = 2,
["LEFT"] = -2,
["L"] = -2,
["0"] = -2
}
rotation = {
["ROTATE"] = 3,
["ORIENTATION"] = 3,
["O"] = 3
}
function onTrigger(player, argc, arg1, arg2)
local pos = player:GetPos();
local x = pos[1];
@ -54,16 +69,24 @@ function onTrigger(player, argc, arg1, arg2)
distance = checkArg1;
elseif checkArg1 and not checkArg2 then -- If first is number and second is string
distance = checkArg1;
if vertical[string.upper(arg2)] then -- Check vertical direction on string, otherwise throw param error
if vertical[string.upper(arg2)] then -- Check vertical direction on string
direction = vertical[string.upper(arg2)];
elseif horizontal[string.upper(arg2)] then -- Check horizontal direction on string
direction = horizontal[string.upper(arg2)];
elseif rotation[string.upper(arg2)] then -- Check rotation on string, otherwise throw param error
direction = rotation[string.upper(arg2)];
else
player:SendMessage(messageID, sender, "Unknown parameters! Usage: \n"..properties.description);
return;
end
elseif (not checkArg1) and checkArg2 then -- If first is string and second is number
distance = checkArg2;
if vertical[string.upper(arg1)] then -- Check vertical direction on string, otherwise throw param error
if vertical[string.upper(arg1)] then -- Check vertical direction on string
direction = vertical[string.upper(arg1)];
elseif horizontal[string.upper(arg1)] then -- Check horizontal direction on string
direction = horizontal[string.upper(arg1)];
elseif rotation[string.upper(arg1)] then -- Check rotation on string, otherwise throw param error
direction = rotation[string.upper(arg1)];
else
player:SendMessage(messageID, sender, "Unknown parameters! Usage: \n"..properties.description);
return;
@ -86,6 +109,19 @@ function onTrigger(player, argc, arg1, arg2)
y = y - distance;
message = string.format("Positioning down %s yalms.", distance);
worldManager:DoPlayerMoveInZone(player, x, y, z, rot, 0x0);
elseif direction == 2 then
local px = x - distance * math.cos(angle - math.pi/2);
local pz = z + distance * math.sin(angle - math.pi/2);
message = string.format("Positioning right %s yalms.", distance);
worldManager:DoPlayerMoveInZone(player, px, y, pz, rot, 0x0);
elseif direction == -2 then
local px = x - distance * math.cos(angle + math.pi/2);
local pz = z + distance * math.sin(angle + math.pi/2);
message = string.format("Positioning left %s yalms.", distance);
worldManager:DoPlayerMoveInZone(player, px, y, pz, rot, 0x0);
elseif direction == 3 then
message = string.format("ROTATE down %s yalms.", distance);
worldManager:DoPlayerMoveInZone(player, x, y, z, distance, 0x0);
else
local px = x - distance * math.cos(angle);
local pz = z + distance * math.sin(angle);

View file

@ -0,0 +1,140 @@
require("global");
properties = {
permissions = 0,
parameters = "ss",
description =
[[
Positions a targeted npc by some <distance>, defaults to 5 yalms.
!nudge |
!nudge <distance> |
!nudge <distance> <up/down> |
!nudge <distance> <left/right> |
!nudge <distance> <rotate> |
]],
}
vertical = {
["UP"] = 1,
["U"] = 1,
["+"] = 1,
["ASCEND"] = 1,
["DOWN"] = -1,
["D"] = -1,
["-"] = -1,
["DESCEND"] = -1,
}
horizontal = {
["RIGHT"] = 2,
["R"] = 2,
["+"] = 2,
["LEFT"] = -2,
["L"] = -2,
["0"] = -2
}
rotation = {
["ROTATE"] = 3,
["ORIENTATION"] = 3,
["O"] = 3
}
function onTrigger(player, argc, arg1, arg2)
local messageID = MESSAGE_TYPE_SYSTEM;
local sender = "[nudge] ";
local targetActor = player.CurrentArea.FindActorInArea(player.currentTarget) or nil;
if (targetActor == nil) then
player:SendMessage(MESSAGE_TYPE_SYSTEM, sender, "No target was selected.\n");
return;
end
local pos = targetActor:GetPos();
local x = pos[1];
local y = pos[2];
local z = pos[3];
local rot = pos[4];
local zone = pos[5];
local angle = rot + (math.pi/2);
local worldManager = GetWorldManager();
local distance = 5;
local direction = 0;
local checkArg1 = tonumber(arg1);
local checkArg2 = tonumber(arg2);
if argc == 1 then
if checkArg1 then
distance = checkArg1;
else
player:SendMessage(messageID, sender, "Unknown parameters! Usage: \n"..properties.description);
return;
end
elseif argc == 2 then
if checkArg1 and checkArg2 then -- If both are numbers, just ignore second argument
distance = checkArg1;
elseif checkArg1 and not checkArg2 then -- If first is number and second is string
distance = checkArg1;
if vertical[string.upper(arg2)] then -- Check vertical direction on string
direction = vertical[string.upper(arg2)];
elseif horizontal[string.upper(arg2)] then -- Check horizontal direction on string
direction = horizontal[string.upper(arg2)];
elseif rotation[string.upper(arg2)] then -- Check rotation on string, otherwise throw param error
direction = rotation[string.upper(arg2)];
else
player:SendMessage(messageID, sender, "Unknown parameters! Usage: \n"..properties.description);
return;
end
elseif (not checkArg1) and checkArg2 then -- If first is string and second is number
distance = checkArg2;
if vertical[string.upper(arg1)] then -- Check vertical direction on string
direction = vertical[string.upper(arg1)];
elseif horizontal[string.upper(arg1)] then -- Check horizontal direction on string
direction = horizontal[string.upper(arg1)];
elseif rotation[string.upper(arg1)] then -- Check rotation on string, otherwise throw param error
direction = rotation[string.upper(arg1)];
else
player:SendMessage(messageID, sender, "Unknown parameters! Usage: \n"..properties.description);
return;
end
else
player:SendMessage(messageID, sender, "Unknown parameters! Usage: \n"..properties.description);
return;
end
end
if direction == 1 then
y = y + distance;
targetActor:SetPos(x,y,z,rot,true, player);
message = string.format("Moved %s @ %f, %f, %f, %f", targetActor:GetUniqueId(), x, y, z, rot);
elseif direction == -1 then
y = y - distance;
targetActor:SetPos(x,y,z,rot,true, player);
message = string.format("Moved %s @ %f, %f, %f, %f", targetActor:GetUniqueId(), x, y, z, rot);
elseif direction == 2 then
local px = x - distance * math.cos(angle - math.pi/2);
local pz = z + distance * math.sin(angle - math.pi/2);
targetActor:SetPos(px, y, pz, rot, true, player);
message = string.format("Moved %s @ %f, %f, %f, %f", targetActor:GetUniqueId(), px, y, pz, rot);
elseif direction == -2 then
local px = x - distance * math.cos(angle + math.pi/2);
local pz = z + distance * math.sin(angle + math.pi/2);
targetActor:SetPos(px, y, pz, rot, true, player);
message = string.format("Moved %s @ %f, %f, %f, %f", targetActor:GetUniqueId(), px, y, pz, rot);
elseif direction == 3 then
targetActor:SetPos(x, y, z, distance, true, player);
message = string.format("Moved %s @ %f, %f, %f, %f", targetActor:GetUniqueId(), x, y, z, distance);
else
local px = x - distance * math.cos(angle);
local pz = z + distance * math.sin(angle);
targetActor:SetPos(px, y, pz, rot, true, player);
message = string.format("Moved %s @ %f, %f, %f, %f", targetActor:GetUniqueId(), px, y, pz, rot);
end
player:SendMessage(messageID, sender, message);
end

View file

@ -0,0 +1,16 @@
require("global");
properties = {
permissions = 0,
parameters = "d",
description = "Simulates killing a bnpc. Used for quest testing.",
}
function onTrigger(player, argc, actorClassId)
if (argc == 1) then
player:HandleBNpcKill(actorClassId);
player:SendMessage(0x20, "", "Simulating BNpc kill for actor class id: " .. tostring(actorClassId));
else
player:SendMessage(0x20, "", "No actor class id provided.");
end
end

View file

@ -40,6 +40,7 @@ MESSAGE_TYPE_URGENT_MESSAGE = 28;
MESSAGE_TYPE_GENERAL_INFO = 29;
MESSAGE_TYPE_SYSTEM = 32;
MESSAGE_TYPE_SYSTEM_ERROR = 33;
MESSAGE_TYPE_NPC_LINKSHELL = 39;
-- INVENTORY
INVENTORY_NORMAL = 0x0000; --Max 0xC8

View file

@ -28,7 +28,7 @@ SEQ_065 = 65; -- Return to FSH Guild
SEQ_070 = 70; -- Contact Baderon on LS
SEQ_075 = 75; -- Go to the ARM and BSM Guilds. Talk to Bodenolf.
SEQ_080 = 80; -- Speak with H'naanza
SEQ_085 = 85; -- Speak with Bodenolf
SEQ_085 = 85; -- Walk into push trigger
SEQ_090 = 90; -- Contact Baderon on LS
SEQ_092 = 92; -- Return to Baderon.
@ -56,7 +56,7 @@ ISANDOREL = 1000152;
MERLZIRN = 1000472;
MSK_TRIGGER = 1090001;
-- Echo in Mrd Guild
-- Echo in MSK Guild
NERVOUS_BARRACUDA = 1000096;
INTIMIDATING_BARRACUDA = 1000097;
OVEREAGER_BARRACUDA = 1000107;
@ -91,14 +91,23 @@ JOELLAUT = 1000163;
WERNER = 1000247;
HIHINE = 1000267;
TRINNE = 1000268;
ECHO_EXIT_TRIGGER2 = 1090001;
ECHO_EXIT_TRIGGER2 = 1090007;
-- Quest Markers
-- Quest Data
CNTR_SEQ7_CUL = 1;
CNTR_SEQ7_MRD = 2;
CNTR_SEQ7_MSK = 2;
CNTR_SEQ40_FSH = 3;
CNTR_LS_MSG = 4;
-- Msg packs for the Npc LS
NPCLS_MSGS = {
{339},
{80, 81, 82},
{131, 326, 132},
{161, 162, 163, 164}
};
function onStart(player, quest)
quest:StartSequence(SEQ_000);
@ -137,21 +146,17 @@ function onStateChange(player, quest, sequence)
quest:SetENpc(BADERON, QFLAG_PLATE);
elseif (sequence == SEQ_007) then
local subseqCUL = data:GetCounter(CNTR_SEQ7_CUL);
local subseqMRD = data:GetCounter(CNTR_SEQ7_MRD);
local subseqMSK = data:GetCounter(CNTR_SEQ7_MSK);
-- Always active in this seqence
quest:SetENpc(BADERON);
quest:SetENpc(CHARLYS, subseqCUL == 0 and QFLAG_PLATE or QFLAG_NONE);
-- Down and Up the MSK guild
quest:SetENpc(ISANDOREL, (subseqMRD == 0 or subseqMRD == 2) and QFLAG_PLATE or QFLAG_NONE);
if (subseqMRD == 1) then
quest:SetENpc(ISANDOREL, (subseqMSK == 0 or subseqMSK == 2) and QFLAG_PLATE or QFLAG_NONE);
if (subseqMSK == 1) then
quest:SetENpc(MSK_TRIGGER, QFLAG_MAP, false, true);
elseif (subseqMRD == 2) then
elseif (subseqMSK == 2) then
quest:SetENpc(MERLZIRN);
end
-- In Echo
quest:SetENpc(NERVOUS_BARRACUDA);
quest:SetENpc(INTIMIDATING_BARRACUDA);
@ -163,11 +168,7 @@ function onStateChange(player, quest, sequence)
quest:SetENpc(ADVENTURER1);
quest:SetENpc(ADVENTURER2);
quest:SetENpc(ADVENTURER3);
quest:SetENpc(ECHO_EXIT_TRIGGER, subseqMRD == 3 and QFLAG_MAP or QFLAG_NONE, false, subseqMRD == 3);
if (subseqCUL == 1 and subseqMRD == 4) then
player:SetNpcLS(1, 1);
end
quest:SetENpc(ECHO_EXIT_TRIGGER, subseqMSK == 3 and QFLAG_MAP or QFLAG_NONE, false, subseqMSK == 3);
elseif (sequence == SEQ_035) then
quest:SetENpc(NNMULIKA, QFLAG_PLATE);
elseif (sequence == SEQ_040) then
@ -363,7 +364,7 @@ function seq000_onTalk(player, quest, npc, classId)
callClientFunction(player, "delegateEvent", player, quest, "processEvent010_8");
elseif (classId == BADERON) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent020");
player:SetNpcLS(1, 3);
quest:NewNpcLsMsg(1);
quest:StartSequence(SEQ_003);
player:EndEvent();
@ -392,12 +393,12 @@ end
function seq007_onTalk(player, quest, npc, classId)
local data = quest:GetData();
local subseqCUL = data:GetCounter(CNTR_SEQ7_CUL);
local subseqMRD = data:GetCounter(CNTR_SEQ7_MRD);
local subseqMSK = data:GetCounter(CNTR_SEQ7_MSK);
if (classId == BADERON) then
if (subseqCUL == 1) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent027_3");
elseif (subseqMRD == 4) then
elseif (subseqMSK == 4) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent027_4");
else
callClientFunction(player, "delegateEvent", player, quest, "processEvent027_2");
@ -405,20 +406,23 @@ function seq007_onTalk(player, quest, npc, classId)
elseif (classId == CHARLYS) then
if (subseqCUL == 0) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent030");
data:IncCounter(CNTR_SEQ7_CUL);
data:IncCounter(CNTR_SEQ7_CUL);
if (data:GetCounter(CNTR_SEQ7_MSK) == 4) then
seq007_endSequence(player, quest);
end
--give 1000g
else
callClientFunction(player, "delegateEvent", player, quest, "processEvent030_2");
end
elseif (classId == ISANDOREL) then
if (subseqMRD == 2) then
if (subseqMSK == 2) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent050");
data:IncCounter(CNTR_SEQ7_MRD);
data:IncCounter(CNTR_SEQ7_MSK);
GetWorldManager():WarpToPrivateArea(player, "PrivateAreaMasterPast", 3);
elseif (subseqMRD == 0) then
elseif (subseqMSK == 0) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent035");
data:IncCounter(CNTR_SEQ7_MRD);
elseif (subseqMRD == 1) then
data:IncCounter(CNTR_SEQ7_MSK);
elseif (subseqMSK == 1) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent035_2");
end
elseif (classId == MERLZIRN) then
@ -448,6 +452,11 @@ function seq007_onTalk(player, quest, npc, classId)
player:EndEvent();
end
function seq007_endSequence(player, quest)
callClientFunction(player, "delegateEvent", player, quest, "processEvent033");
quest:NewNpcLsMsg(1);
end
function seq080_085_onTalk(player, quest, npc, classId)
if (classId == IOFA) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent630_2");
@ -477,13 +486,16 @@ function onPush(player, quest, npc)
if (sequence == SEQ_007) then
if (classId == MSK_TRIGGER) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent040");
data:IncCounter(CNTR_SEQ7_MRD);
data:IncCounter(CNTR_SEQ7_MSK);
player:EndEvent();
quest:UpdateENPCs();
GetWorldManager():DoZoneChange(player, 230, nil, 0, 15, -620.0, 29.476, -70.050, 0.791);
elseif (classId == ECHO_EXIT_TRIGGER) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent060");
data:IncCounter(CNTR_SEQ7_MRD);
data:IncCounter(CNTR_SEQ7_MSK);
if (data:GetCounter(CNTR_SEQ7_CUL) == 1) then
seq007_endSequence(player, quest);
end
player:EndEvent();
quest:UpdateENPCs();
GetWorldManager():WarpToPublicArea(player);
@ -509,12 +521,15 @@ function onPush(player, quest, npc)
callClientFunction(player, "delegateEvent", player, quest, "processEvent620");
-- Give 3000 gil
player:EndEvent();
quest:StartSequence(SEQ_075);
quest:NewNpcLsMsg(1);
quest:StartSequence(SEQ_070);
end
elseif (sequence == SEQ_085) then
if (classId == ECHO_EXIT_TRIGGER2) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent635");
player:EndEvent();
player:EndEvent();
quest:NewNpcLsMsg(1);
quest:StartSequence(SEQ_090);
quest:UpdateENPCs();
GetWorldManager():WarpToPublicArea(player);
end
@ -632,29 +647,43 @@ function onNotice(player, quest, target)
quest:UpdateENPCs();
end
function onNpcLS(player, quest, npcLSId)
function onNpcLS(player, quest, from, msgStep)
local sequence = quest:getSequence();
if (npcLSId == 1) then
player:SetNpcLS(1, 1);
if (sequence == SEQ_003) then
player:SendGameMessageLocalizedDisplayName(quest, 298, 39, 1000015, nil);
local msgPack;
if (from == 1) then
-- Get the right msg pack
if (sequence == SEQ_003) then
msgPack = 1;
elseif (sequence == SEQ_007 or sequence == SEQ_035) then
msgPack = 2;
elseif (sequence == SEQ_070 or sequence == SEQ_075) then
msgPack = 3;
elseif (sequence == SEQ_090 or sequence == SEQ_092) then
msgPack = 4;
end
-- Quick way to handle all msgs nicely.
player:SendGameMessageLocalizedDisplayName(quest, NPCLS_MSGS[msgPack][msgStep], MESSAGE_TYPE_NPC_LINKSHELL, 1000015);
if (msgStep >= #NPCLS_MSGS[msgPack]) then
quest:EndOfNpcLsMsgs();
else
quest:ReadNpcLsMsg();
end
-- Handle anything else
if (sequence == SEQ_003) then
endTutorialMode(player);
elseif (sequence == SEQ_007) then
player:SendGameMessageLocalizedDisplayName(quest, 80, 39, 1000015, nil);
player:SendGameMessageLocalizedDisplayName(quest, 81, 39, 1000015, nil);
player:SendGameMessageLocalizedDisplayName(quest, 82, 39, 1000015, nil);
quest:StartSequence(SEQ_035);
quest:StartSequenceForNpcLs(SEQ_035);
elseif (sequence == SEQ_070) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent625");
player:EndEvent();
quest:StartSequence(SEQ_075);
quest:StartSequenceForNpcLs(SEQ_075);
elseif (sequence == SEQ_090) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent637");
player:EndEvent();
quest:StartSequence(SEQ_092);
quest:StartSequenceForNpcLs(SEQ_092);
end
end
player:EndEvent();
end
function startMan0l1Content(player, quest)
@ -675,7 +704,7 @@ function startMan0l1Content(player, quest)
end
function getJournalInformation(player, quest)
return 0, quest:GetData():GetCounter(CNTR_SEQ7_CUL) * 5, quest:GetData():GetCounter(CNTR_SEQ7_MRD) * 5;
return 0, quest:GetData():GetCounter(CNTR_SEQ7_CUL) * 5, quest:GetData():GetCounter(CNTR_SEQ7_MSK) * 5;
end
function getJournalMapMarkerList(player, quest)

View file

@ -168,8 +168,6 @@ function onNotice(player, quest, target)
quest:UpdateENPCs();
end
function seq000_onTalk(player, quest, npc, classId)
if (classId == MOMODI) then

View file

@ -0,0 +1,398 @@
require("global");
--[[
Quest Script
Name: Legends Adrift
Code: Man1l0
Id: 110003
Prereq: Treasures of the Main (Man0l1 - 110002)
]]
-- Sequence Numbers
SEQ_000 = 0; -- Echo intance with Y'shtola, Baderon, Etc. Talk to Y'shtola.
SEQ_010 = 10; -- Echo instance, talk with Baderon.
SEQ_020 = 20; -- Head to MRD guild and talk to Waekbyrt.
SEQ_030 = 30; -- Head down the Astalicia to the push trigger.
SEQ_040 = 40; -- Head up the Astalicia to the push trigger.
SEQ_050 = 50; -- Contact Baderon on the Link Pearl.
SEQ_060 = 60; -- Head to the FSH guild and push the trigger.
SEQ_070 = 70; -- Head to a spot in Lower La Noscea.
SEQ_080 = 80; -- Contact Baderon on the Link Pearl.
SEQ_090 = 90; -- Speak to P'tahjha at the ACN guild.
SEQ_100 = 100; -- Echo instance, head downstairs to push a trigger and cutscene.
SEQ_110 = 110; -- Echo instance still, head upstairs to trigger a cutscene.
SEQ_120 = 120; -- Contact Baderon on the Link Pearl.
SEQ_122 = 122; -- Head back to Baderon to finish the quest.
-- Quest Actors
BADERON = 1000137;
YSHTOLA = 1000001;
-- ADV Guild Echo
ADVENTURER = 1000101;
WHISPERING_ADVENTURER = 1000102;
UNAPPROACHABLE_ADVENTURER = 1000103;
FISH_SMELLING_ADVENTURER = 1000104;
SPEAR_WIELDING_ADVENTURER = 1000105;
TRIGGER_ADVGUILD = 1090080;
-- MRD Guild Echo
WAEKBYRT = 1000003;
HULKING_CUDA_KNIGHT = 1000182;
SOPHISTICATED_CUDA_KNIGHT = 1000108;
FRIGHTENED_CUDA_KNIGHT = 1000110;
ZEALOUS_PIRATE = 1000112;
ENRAGED_PIRATE = 1000113;
TRIGGER_MRD = 1090081;
-- MRD Guild Echo 2
DISGRUNTLED_PIRATE = 1000087;
PINE_SCENTED_PIRATE = 1000088;
BARITONE_PIRATE = 1000089;
BAYARD = 1000190;
-- FSH Guild Sequences
NNMULIKA = 1000153;
SISIPU = 1000156;
TRIGGER_FSH = 1090006;
TRIGGER_SEAFLD = 1090082;
-- ACN Guild Echo
ASSESSOR = 1000121;
PTAHJHA = 1000150;
HALDBERK = 1000160;
LILINA = 1000178;
DODOROBA = 1000196;
IVAN = 1000197;
MERODAULYN = 1000008;
COQUETTISH_PIRATE = 1000868;
VOLUPTUOUS_PIRATE = 1000115;
PEACOCKISH_PIRATE = 1000118;
TRIGGER_ACN_LOWER = 1090083;
TRIGGER_ACN_UPPER = 1090084;
-- Quest Markers
MRKR_TRIGGER_FSH = 11000306;
MRKR_TRIGGER_SEAFLD = 11000307;
MRKR_TRIGGER_ANC_LOWER = 11000308;
-- Msg packs for the Npc LS
NPCLS_MSGS = {
{57, 58, 59}, -- SEQ_050
{92, 93, 94}, -- SEQ_070
{140, 141} -- SEQ_120
};
function onStart(player, quest)
quest:StartSequence(SEQ_000);
GetWorldManager():WarpToPrivateArea(player, "PrivateAreaMasterPast", 3, -430.55, 40.2, 185.41, 1.89);
end
function onFinish(player, quest)
end
function onStateChange(player, quest, sequence)
local data = quest:GetData();
if (sequence == SEQ_ACCEPT) then
quest:SetENpc(BADERON, QFLAG_PLATE);
elseif (sequence == SEQ_000) then
quest:SetENpc(BADERON);
quest:SetENpc(ADVENTURER);
quest:SetENpc(WHISPERING_ADVENTURER);
quest:SetENpc(UNAPPROACHABLE_ADVENTURER);
quest:SetENpc(FISH_SMELLING_ADVENTURER);
quest:SetENpc(SPEAR_WIELDING_ADVENTURER);
quest:SetENpc(TRIGGER_ADVGUILD, QFLAG_MAP, false, true);
elseif (sequence == SEQ_010) then
quest:SetENpc(BADERON, QFLAG_PLATE);
quest:SetENpc(ADVENTURER);
quest:SetENpc(WHISPERING_ADVENTURER);
quest:SetENpc(UNAPPROACHABLE_ADVENTURER);
quest:SetENpc(FISH_SMELLING_ADVENTURER);
quest:SetENpc(SPEAR_WIELDING_ADVENTURER);
quest:SetENpc(YSHTOLA);
elseif (sequence == SEQ_020) then
quest:SetENpc(WAEKBYRT, QFLAG_PLATE);
quest:SetENpc(BADERON);
elseif (sequence == SEQ_030) then
quest:SetENpc(TRIGGER_MRD, QFLAG_MAP, false, true);
quest:SetENpc(HULKING_CUDA_KNIGHT);
quest:SetENpc(SOPHISTICATED_CUDA_KNIGHT);
quest:SetENpc(FRIGHTENED_CUDA_KNIGHT);
quest:SetENpc(ZEALOUS_PIRATE);
quest:SetENpc(ENRAGED_PIRATE);
quest:SetENpc(WAEKBYRT);
elseif (sequence == SEQ_040) then
quest:SetENpc(TRIGGER_MRD, QFLAG_MAP, false, true);
quest:SetENpc(PINE_SCENTED_PIRATE);
quest:SetENpc(BARITONE_PIRATE);
quest:SetENpc(BAYARD);
quest:SetENpc(DISGRUNTLED_PIRATE);
elseif (sequence == SEQ_060) then
quest:SetENpc(TRIGGER_FSH, QFLAG_MAP, false, true);
quest:SetENpc(BADERON);
elseif (sequence == SEQ_070) then
quest:SetENpc(TRIGGER_SEAFLD, QFLAG_MAP, false, true);
quest:SetENpc(NNMULIKA);
elseif (sequence == SEQ_090) then
quest:SetENpc(PTAHJHA, QFLAG_PLATE);
elseif (sequence == SEQ_100) then
quest:SetENpc(TRIGGER_ACN_LOWER, QFLAG_MAP, false, true);
quest:SetENpc(ASSESSOR);
quest:SetENpc(HALDBERK);
quest:SetENpc(LILINA);
quest:SetENpc(VOLUPTUOUS_PIRATE);
quest:SetENpc(PEACOCKISH_PIRATE);
quest:SetENpc(MERODAULYN);
quest:SetENpc(COQUETTISH_PIRATE);
quest:SetENpc(IVAN);
elseif (sequence == SEQ_110) then
quest:SetENpc(TRIGGER_ACN_UPPER, QFLAG_MAP, false, true);
elseif (sequence == SEQ_122) then
quest:SetENpc(BADERON, QFLAG_REWARD);
end
end
function onTalk(player, quest, npc)
local sequence = quest:getSequence();
local classId = npc:GetActorClassId();
if (sequence == SEQ_ACCEPT) then
if (classId == BADERON) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent200");
player:EndEvent();
player:AcceptQuest(quest, true);
return;
end
elseif (sequence == SEQ_000) then
seq000_010_onTalk(player, quest, npc, classId);
elseif (sequence == SEQ_010) then
if (classId == BADERON) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent215");
player:EndEvent();
quest:StartSequence(SEQ_020);
GetWorldManager():WarpToPublicArea(player);
return;
elseif (classId == YSHTOLA) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent200_8");
else
seq000_010_onTalk(player, quest, npc, classId);
end
elseif (sequence == SEQ_020) then
if (classId == WAEKBYRT) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent400");
quest:StartSequence(SEQ_030);
player:EndEvent();
GetWorldManager():WarpToPrivateArea(player, "PrivateAreaMasterPast", 6, -754.03, 7.352, 382.872, 3.133);
return;
elseif (classId == BADERON) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent215_2");
end
elseif (sequence == SEQ_030 or sequence == SEQ_040) then
seq000_030_040_onTalk(player, quest, npc, classId)
elseif (sequence == SEQ_060) then
if (classId == NNMULIKA) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent600");
elseif (classId == BADERON) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent420_2");
end
elseif (sequence == SEQ_070) then
if (classId == NNMULIKA) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent600_2");
end
elseif (sequence == SEQ_090) then
if (classId == PTAHJHA) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent2000");
quest:StartSequence(SEQ_100);
player:EndEvent();
GetWorldManager():WarpToPrivateArea(player, "PrivateAreaMasterPast", 7);
elseif (classId == BADERON) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent610_2");
end
elseif (sequence == SEQ_100) then
seq000_100_onTalk(player, quest, npc, classId)
elseif (sequence == SEQ_110) then
elseif (sequence == SEQ_122) then
if (classId == BADERON) then
callClientFunction(player, "delegateEvent", player, quest, "processEventComplete");
callClientFunction(player, "delegateEvent", player, quest, "sqrwa", 300, 1, 1, 2);
player:EndEvent();
player:CompleteQuest(quest);
return;
end
end
player:EndEvent();
quest:UpdateENPCs();
end
function seq000_010_onTalk(player, quest, npc, classId)
if (classId == ADVENTURER) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent200_2");
elseif (classId == WHISPERING_ADVENTURER) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent200_3");
elseif (classId == UNAPPROACHABLE_ADVENTURER) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent200_4");
elseif (classId == FISH_SMELLING_ADVENTURER) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent200_5");
elseif (classId == SPEAR_WIELDING_ADVENTURER) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent200_6");
elseif (classId == BADERON) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent200_7");
end
end
function seq000_030_040_onTalk(player, quest, npc, classId)
if (classId == HULKING_CUDA_KNIGHT) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent400_2");
elseif (classId == SOPHISTICATED_CUDA_KNIGHT) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent400_3");
elseif (classId == FRIGHTENED_CUDA_KNIGHT) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent400_4");
elseif (classId == ZEALOUS_PIRATE) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent400_5");
elseif (classId == ENRAGED_PIRATE) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent400_6");
elseif (classId == WAEKBYRT) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent400_7");
elseif (classId == PINE_SCENTED_PIRATE) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent410_2");
elseif (classId == BARITONE_PIRATE) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent410_3");
elseif (classId == BAYARD) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent410_4");
elseif (classId == DISGRUNTLED_PIRATE) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent410_5");
end
end
function seq000_100_onTalk(player, quest, npc, classId)
if (classId == ASSESSOR) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent2000_2");
elseif (classId == 0) then -- !!!MISSING DIALOG OWNER!!!
callClientFunction(player, "delegateEvent", player, quest, "processEvent2000_3");
elseif (classId == HALDBERK) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent2000_4");
elseif (classId == LILINA) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent2000_5");
elseif (classId == VOLUPTUOUS_PIRATE) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent2000_6");
elseif (classId == PEACOCKISH_PIRATE) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent2000_7");
elseif (classId == MERODAULYN) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent2000_8");
elseif (classId == COQUETTISH_PIRATE) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent2000_9");
elseif (classId == 0) then -- !!!MISSING DIALOG OWNER!!!
callClientFunction(player, "delegateEvent", player, quest, "processEvent2000_10");
elseif (classId == 0) then -- !!!MISSING DIALOG OWNER!!!
callClientFunction(player, "delegateEvent", player, quest, "processEvent2000_11");
elseif (classId == IVAN) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent2000_12");
end
end
function onPush(player, quest, npc)
local data = quest:GetData();
local sequence = quest:getSequence();
local classId = npc:GetActorClassId();
if (sequence == SEQ_000) then
if (classId == TRIGGER_ADVGUILD) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent210");
quest:StartSequence(SEQ_010);
end
elseif (sequence == SEQ_030) then
if (classId == TRIGGER_MRD) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent410");
quest:StartSequence(SEQ_040);
player:EndEvent();
GetWorldManager():WarpToPosition(player, -764.519, -3.146, 384.154, 1.575);
return;
end
elseif (sequence == SEQ_040) then
if (classId == TRIGGER_MRD) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent420");
quest:NewNpcLsMsg(1);
quest:StartSequence(SEQ_050);
player:EndEvent();
GetWorldManager():WarpToPublicArea(player);
return;
end
elseif (sequence == SEQ_060) then
if (classId == TRIGGER_FSH) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent600");
quest:StartSequence(SEQ_070);
end
elseif (sequence == SEQ_070) then
if (classId == TRIGGER_SEAFLD) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent610");
quest:NewNpcLsMsg(1);
quest:StartSequence(SEQ_080);
end
elseif (sequence == SEQ_100) then
if (classId == TRIGGER_ACN_LOWER) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent2001");
quest:StartSequence(SEQ_110);
player:EndEvent();
GetWorldManager():WarpToPosition(player, -785.938, -0.62, 189.044, 3.09);
return;
end
elseif (sequence == SEQ_110) then
if (classId == TRIGGER_ACN_UPPER) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent2002");
quest:NewNpcLsMsg(1);
quest:StartSequence(SEQ_120);
player:EndEvent();
GetWorldManager():WarpToPublicArea(player);
return;
end
end
player:EndEvent();
quest:UpdateENPCs();
end
function onNpcLS(player, quest, from, msgStep)
local sequence = quest:getSequence();
local msgPack;
if (from == 1) then
-- Get the right msg pack
if (sequence == SEQ_050 or sequence == SEQ_060) then
msgPack = 1;
elseif (sequence == SEQ_080 or sequence == SEQ_090) then
msgPack = 2;
elseif (sequence == SEQ_120 or sequence == SEQ_122) then
msgPack = 3;
end
-- Quick way to handle all msgs nicely.
player:SendGameMessageLocalizedDisplayName(quest, NPCLS_MSGS[msgPack][msgStep], MESSAGE_TYPE_NPC_LINKSHELL, 1000015);
if (msgStep >= #NPCLS_MSGS[msgPack]) then
quest:EndOfNpcLsMsgs();
else
quest:ReadNpcLsMsg();
end
-- Handle anything else
if (sequence == SEQ_050) then
quest:StartSequenceForNpcLs(SEQ_060);
elseif (sequence == SEQ_080) then
quest:StartSequenceForNpcLs(SEQ_090);
elseif (sequence == SEQ_120) then
quest:StartSequenceForNpcLs(SEQ_122);
end
end
player:EndEvent();
end
function getJournalMapMarkerList(player, quest)
local sequence = quest:getSequence();
end

View file

@ -1,4 +1,52 @@
require("global")
require("global");
--[[
Quest Script
Name: Never the Twain Shall Meet
Code: Man2l0
Id: 110004
Prereq: Legends Adrift (Man1l0 - 110003)
]]
-- Sequence Numbers
SEQ_000 = 0; -- Talk to Captain Hob.
SEQ_010 = 10; -- Ship instance, enter the hold.
SEQ_015 = 15; -- Exit the hold, go back upstairs.
SEQ_020 = 20; -- Duty, fight Emerick and Merodaulyn
SEQ_035 = 35; -- Head to Baderon and chat.
SEQ_037 = 37; -- Head to outcrop in La Noscea.
SEQ_040 = 40; -- Talk to Baderon on the Link Pearl
SEQ_042 = 42; -- Enter and push at the MSK guild.
SEQ_045 = 45; -- Talk to Isaudorel
SEQ_050 = 50; -- Head to God's Grip push, talk with Blackburn.
SEQ_055 = 55; -- Continue to the other push with Y'shtola in the subecho.
SEQ_060 = 60; -- Unused? Talks about spying Stahlmann, Emerick, and Merod scheming.
SEQ_065 = 65; -- Unused? Talks about the meteor shower and the Ascian stealing the key.
SEQ_070 = 70; -- Unused? Talks about heading to Ul'dah
-- Quest Actors
BADERON = 1000137;
YSHTOLA = 1000001;
HOB = 1000151;
ISAUDOREL = 1000152;
BARRACUDA_KNIGHT1 = 1000183;
BARRACUDA_KNIGHT2 = 1000184;
TRIGGER_SHIP1 = 1090003;
TRIGGER_SHIP2 = 1090003;
TRIGGER_MSK = 1090003;
TRIGGER_SEAFLD1 = 1090003;
TRIGGER_SEAFLD2 = 1090003;
TRIGGER_SEAFLD3 = 1090003;
-- Quest Markers
-- Msg packs for the Npc LS
NPCLS_MSGS = {
{40, 41} -- SEQ_040
};
function onStart(player, quest)
quest:StartSequence(SEQ_000);
@ -7,29 +55,169 @@ end
function onFinish(player, quest)
end
function onStateChange(player, quest, seqNum)
function onStateChange(player, quest, sequence)
local data = quest:GetData();
if (sequence == SEQ_ACCEPT) then
quest:SetENpc(BADERON, QFLAG_PLATE);
elseif (sequence == SEQ_000) then
quest:SetENpc(HOB, QFLAG_PLATE);
quest:SetENpc(BADERON);
elseif (sequence == SEQ_010) then
quest:SetENpc(HOB);
quest:SetENpc(BARRACUDA_KNIGHT1);
quest:SetENpc(BARRACUDA_KNIGHT2);
elseif (sequence == SEQ_015) then
quest:SetENpc(HOB);
quest:SetENpc(BARRACUDA_KNIGHT1);
quest:SetENpc(BARRACUDA_KNIGHT2);
elseif (sequence == SEQ_020) then
-- DUTY HAPPENS HERE
elseif (sequence == SEQ_035) then
quest:SetENpc(BADERON, QFLAG_PLATE);
elseif (sequence == SEQ_037) then
quest:SetENpc(BADERON);
elseif (sequence == SEQ_040) then
elseif (sequence == SEQ_042) then
quest:SetENpc(BADERON);
elseif (sequence == SEQ_045) then
quest:SetENpc(ISAUDOREL, QFLAG_PLATE);
elseif (sequence == SEQ_050) then
elseif (sequence == SEQ_055) then
quest:SetENpc(YSHTOLA);
end
end
function onTalk(player, quest, npc)
local sequence = quest:getSequence();
local classId = npc:GetActorClassId();
end
function onEmote(player, quest, npc, emote)
if (sequence == SEQ_ACCEPT) then
if (classId == BADERON) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent000");
end
elseif (sequence == SEQ_000) then
if (classId == HOB) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent010");
quest:StartSequence(SEQ_010);
elseif (classId == BADERON) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent000_2");
end
elseif (sequence == SEQ_010) then
if (classId == HOB) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent011_2");
elseif (classId == BARRACUDA_KNIGHT1) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent011_3");
elseif (classId == BARRACUDA_KNIGHT2) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent011_4");
end
elseif (sequence == SEQ_015) then
if (classId == HOB) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent011_2");
elseif (classId == BARRACUDA_KNIGHT1) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent011_3");
elseif (classId == BARRACUDA_KNIGHT2) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent011_4");
end
elseif (sequence == SEQ_035) then
if (classId == BADERON) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent050");
quest:StartSequence(SEQ_037);
end
elseif (sequence == SEQ_037) then
if (classId == BADERON) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent050_2");
end
elseif (sequence == SEQ_042) then
if (classId == BADERON) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent060_2");
end
elseif (sequence == SEQ_045) then
if (classId == ISAUDOREL) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent075");
quest:StartSequence(SEQ_050);
end
elseif (sequence == SEQ_055) then
if (classId == YSHTOLA) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent080_2");
end
end
player:EndEvent();
quest:UpdateENPCs();
end
function onPush(player, quest, npc)
local data = quest:GetData();
local sequence = quest:getSequence();
local classId = npc:GetActorClassId();
if (sequence == SEQ_037) then
if (classId == TRIGGER_SEAFLD1) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent060");
quest:StartSequence(SEQ_040);
end
elseif (sequence == SEQ_042) then
if (classId == TRIGGER_MSK) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent070");
quest:StartSequence(SEQ_045);
end
elseif (sequence == SEQ_050) then
if (classId == TRIGGER_SEAFLD2) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent080");
quest:StartSequence(SEQ_055);
end
elseif (sequence == SEQ_055) then
if (classId == TRIGGER_SEAFLD3) then
callClientFunction(player, "delegateEvent", player, quest, "processEvent081");
end
end
player:EndEvent();
quest:UpdateENPCs();
end
function onNotice(player, quest, npc)
function onNotice(player, quest, target)
callClientFunction(player, "delegateEvent", player, quest, "sqrwa", 300, 1, 1, 2);
player:CompleteQuest(quest);
callClientFunction(player, "delegateEvent", player, quest, "processEvent081_2", 1);
player:EndEvent();
quest:UpdateENPCs();
end
function onNpcLS(player, quest, from, msgStep)
local sequence = quest:getSequence();
local msgPack;
if (from == 1) then
-- Get the right msg pack
if (sequence == SEQ_040 or sequence == SEQ_042) then
msgPack = 1;
end
-- Quick way to handle all msgs nicely.
player:SendGameMessageLocalizedDisplayName(quest, NPCLS_MSGS[msgPack][msgStep], MESSAGE_TYPE_NPC_LINKSHELL, 1000015);
if (msgStep >= #NPCLS_MSGS[msgPack]) then
quest:EndOfNpcLsMsgs();
else
quest:ReadNpcLsMsg();
end
-- Handle anything else
if (sequence == SEQ_040) then
quest:StartSequenceForNpcLs(SEQ_042);
end
end
player:EndEvent();
end
function getJournalInformation(player, quest)
return {};
return 40, 40, 40;
end
function getJournalMapMarkerList(player, quest)
return 11000105, 11000106;
local sequence = quest:getSequence();
end

View file

@ -642,7 +642,7 @@ namespace Meteor.Map.Actors
return new Vector3(positionX, positionY, positionZ);
}
public void SetPos(float x, float y, float z, float rot = 0, bool instant = false)
public void SetPos(float x, float y, float z, float rot = 0, bool instant = false, Player player = null)
{
oldPositionX = positionX;
oldPositionY = positionY;
@ -657,8 +657,9 @@ namespace Meteor.Map.Actors
// todo: handle zone?
if (instant)
{
CurrentArea.BroadcastPacketAroundPoint(oldPositionX, oldPositionY, CreateSpawnTeleportPacket(0));
CurrentArea.BroadcastPacketAroundPoint(positionX, positionY, CreateSpawnTeleportPacket(0));
player.QueuePacket(CreateSpawnTeleportPacket(0));
//CurrentArea.BroadcastPacketAroundPoint(oldPositionX, oldPositionY, CreateSpawnTeleportPacket(0));
//CurrentArea.BroadcastPacketAroundPoint(positionX, positionY, CreateSpawnTeleportPacket(0));
}
else
CurrentArea.BroadcastPacketAroundActor(this, MoveActorToPositionPacket.BuildPacket(Id, x, y, z, rot, moveState));

View file

@ -33,9 +33,10 @@ namespace Meteor.Map.actors.area
private readonly Zone ParentZone;
private readonly string PrivateAreaName;
private readonly int PrivateAreaType;
private readonly bool CanExitArea;
public PrivateArea(Zone parent, string classPath, string privateAreaName, int privateAreaType, ushort bgmDay, ushort bgmNight, ushort bgmBattle)
: base(parent.ZoneId, parent.ZoneName, parent.RegionId, classPath, bgmDay, bgmNight, bgmBattle, parent.isIsolated, parent.isInn, parent.canRideChocobo, parent.canStealth, true)
public PrivateArea(Zone parent, string classPath, string privateAreaName, int privateAreaType, bool canExitArea, ushort music)
: base(parent.ZoneId, parent.ZoneName, parent.RegionId, classPath, music, music, music, parent.isIsolated, parent.isInn, parent.canRideChocobo, parent.canStealth, true)
{
this.ParentZone = parent;
this.PrivateAreaName = privateAreaName;
@ -52,6 +53,11 @@ namespace Meteor.Map.actors.area
return PrivateAreaType;
}
public bool CanExitPrivateArea()
{
return CanExitArea;
}
public override bool IsPublic()
{
return false;

View file

@ -38,7 +38,7 @@ namespace Meteor.Map.actors.area
}
public PrivateAreaContent(Zone parent, string classPath, string privateAreaName, int privateAreaType, Director director, Player contentStarter) //TODO: Make it a list
: base(parent, classPath, privateAreaName, privateAreaType, 0, 0, 0)
: base(parent, classPath, privateAreaName, privateAreaType, false, 0)
{
currentDirector = director;
LuaEngine.GetInstance().CallLuaFunction(contentStarter, this, "onCreate", false, currentDirector);

View file

@ -1840,21 +1840,34 @@ namespace Meteor.Map.Actors
public Quest[] GetQuestsForNpc(Npc npc)
{
Quest[] quests = questStateManager.GetQuestsForNpc(npc);
Quest[] quests = questStateManager.GetQuestsForNpc(npc, CurrentArea.IsPrivate());
Array.Sort(quests, (q1, q2) => (q1.HasData() ? 1 : 0) - (q2.HasData() ? 1 : 0));
return quests;
}
public void HandleNpcLS(uint id)
public void HandleBNpcKill(uint bnpcClassId)
{
foreach (Quest quest in questScenario)
{
if (quest != null)
quest.OnNpcLS(this, id);
quest.OnKillBNpc(this, bnpcClassId);
}
}
public void SetNpcLS(uint npcLSId, uint state)
public bool HandleNpcLs(uint id)
{
foreach (Quest quest in questScenario)
{
if (quest != null && quest.HasNpcLsMsgs(id))
{
quest.OnNpcLs(this);
return true;
}
}
return false;
}
public void SetNpcLs(uint npcLSId, uint state)
{
bool isCalling, isExtra;
isCalling = isExtra = false;

View file

@ -35,6 +35,7 @@ namespace Meteor.Map.Actors.QuestNS
private QuestState questState = null;
private QuestData data = null;
// Creates a Static Quest for the StaticActors list.
public Quest(uint actorID, string className, string classPath)
: base(actorID)
@ -59,11 +60,11 @@ namespace Meteor.Map.Actors.QuestNS
}
// Creates a Instance Quest that has been started with data.
public Quest(Player owner, Quest staticQuest, ushort sequence, uint flags, ushort counter1, ushort counter2, ushort counter3, ushort counter4) : this(staticQuest)
public Quest(Player owner, Quest staticQuest, ushort sequence, uint flags, ushort counter1, ushort counter2, ushort counter3, ushort counter4, uint npcLsFrom, byte npcLsMsgStep) : this(staticQuest)
{
this.owner = owner;
currentSequence = sequence;
data = new QuestData(owner, this, flags, counter1, counter2, counter3, counter4);
data = new QuestData(owner, this, flags, counter1, counter2, counter3, counter4, npcLsFrom, npcLsMsgStep);
questState = new QuestState(owner, this);
questState.UpdateState();
}
@ -137,6 +138,35 @@ namespace Meteor.Map.Actors.QuestNS
}
}
public void NewNpcLsMsg(uint from)
{
data.SetNpcLsFrom(from);
owner.SetNpcLs(from, Player.NPCLS_ALERT);
owner.SendGameMessage(Server.GetWorldManager().GetActor(), 25119, 0x20, (object)from); // A glow emanates from the <NpcLs> linkpearl.
}
public void ReadNpcLsMsg()
{
data.IncrementNpcLsMsgStep();
owner.SetNpcLs(data.GetNpcLsFrom(), Player.NPCLS_ACTIVE);
}
public void EndOfNpcLsMsgs()
{
owner.SetNpcLs(data.GetNpcLsFrom(), Player.NPCLS_INACTIVE);
data.ClearNpcLs();
}
public bool HasNpcLsMsgs(uint from)
{
return data.GetNpcLsFrom() == from;
}
public int GetNpcLsMsgStep()
{
return data.GetMsgStep();
}
public QuestState GetQuestState()
{
return questState;
@ -164,9 +194,14 @@ namespace Meteor.Map.Actors.QuestNS
LuaEngine.GetInstance().CallLuaFunction(caller, this, "onNotice", true, triggerName);
}
public void OnNpcLS(Player caller, uint npcLSId)
public void OnKillBNpc(Player caller, uint classId)
{
LuaEngine.GetInstance().CallLuaFunction(caller, this, "onNpcLS", true, npcLSId);
LuaEngine.GetInstance().CallLuaFunction(caller, this, "onKillBNpc", true, classId);
}
public void OnNpcLs(Player caller)
{
LuaEngine.GetInstance().CallLuaFunction(caller, this, "onNpcLS", true, data.GetNpcLsFrom(), data.GetMsgStep());
}
public object[] GetJournalInformation()
@ -213,6 +248,12 @@ namespace Meteor.Map.Actors.QuestNS
questState.UpdateState();
}
public void StartSequenceForNpcLs(ushort sequence)
{
currentSequence = sequence;
questState.UpdateState();
}
public void OnAccept()
{
data = new QuestData(owner, this);
@ -237,6 +278,5 @@ namespace Meteor.Map.Actors.QuestNS
data = null;
questState.UpdateState();
}
}
}

View file

@ -17,9 +17,12 @@ namespace Meteor.Map.Actors.QuestNS
private ushort counter3;
private ushort counter4;
private uint npcLsFrom = 0;
private byte npcLsMessageStep = 0;
public bool Dirty { get; private set; } = false;
public QuestData(Player owner, Quest parent, uint flags, ushort counter1, ushort counter2, ushort counter3, ushort counter4)
public QuestData(Player owner, Quest parent, uint flags, ushort counter1, ushort counter2, ushort counter3, ushort counter4, uint npcLsFrom, byte npcLsMessageStep)
{
this.owner = owner;
this.parent = parent;
@ -28,6 +31,8 @@ namespace Meteor.Map.Actors.QuestNS
this.counter2 = counter2;
this.counter3 = counter3;
this.counter4 = counter4;
this.npcLsFrom = npcLsFrom;
this.npcLsMessageStep = npcLsMessageStep;
}
public QuestData(Player owner, Quest parent)
@ -160,6 +165,34 @@ namespace Meteor.Map.Actors.QuestNS
return 0;
}
public void SetNpcLsFrom(uint from)
{
npcLsFrom = from;
npcLsMessageStep = 1;
Dirty = true;
}
public void IncrementNpcLsMsgStep()
{
npcLsMessageStep++;
Dirty = true;
}
public uint GetNpcLsFrom()
{
return npcLsFrom;
}
public byte GetMsgStep()
{
return npcLsMessageStep;
}
public void ClearNpcLs()
{
npcLsFrom = 0;
}
public void ClearDirty()
{
Dirty = false;

View file

@ -151,9 +151,12 @@ namespace Meteor.Map.Actors.QuestNS
return ActiveQuests.Find(quest => quest.GetQuestId() == id);
}
public Quest[] GetQuestsForNpc(Npc npc)
public Quest[] GetQuestsForNpc(Npc npc, bool isPrivateArea)
{
return ActiveQuests.FindAll(quest => quest.IsQuestENPC(player, npc)).ToArray();
if (isPrivateArea)
return ActiveQuests.FindAll(quest => quest.IsQuestENPC(player, npc) && quest.GetSequence() != Quest.SEQ_NOT_STARTED).ToArray();
else
return ActiveQuests.FindAll(quest => quest.IsQuestENPC(player, npc)).ToArray();
}
public byte[] GetCompletionSliceBytes(ushort from, ushort to)

View file

@ -591,7 +591,7 @@ namespace Meteor.Map
query = @"
UPDATE characters_quest_scenario
SET sequence = @sequence, flags = @flags, counter1 = @counter1, counter2 = @counter2, counter3 = @counter3
SET sequence = @sequence, flags = @flags, counter1 = @counter1, counter2 = @counter2, counter3 = @counter3, counter4 = @counter4, npcLsFrom = @npcLsFrom, npcLsMsgStep = @npcLsMsgStep
WHERE characterId = @charaId and questId = @questId
";
@ -600,14 +600,14 @@ namespace Meteor.Map
cmd.Parameters.AddWithValue("@questId", 0xFFFFF & quest.Id);
cmd.Parameters.AddWithValue("@sequence", quest.GetSequence());
if (qData != null)
{
cmd.Parameters.AddWithValue("@flags", qData.GetFlags());
cmd.Parameters.AddWithValue("@counter1", qData.GetCounter(1));
cmd.Parameters.AddWithValue("@counter2", qData.GetCounter(2));
cmd.Parameters.AddWithValue("@counter3", qData.GetCounter(3));
}
cmd.Parameters.AddWithValue("@flags", qData.GetFlags());
cmd.Parameters.AddWithValue("@counter1", qData.GetCounter(1));
cmd.Parameters.AddWithValue("@counter2", qData.GetCounter(2));
cmd.Parameters.AddWithValue("@counter3", qData.GetCounter(3));
cmd.Parameters.AddWithValue("@counter4", qData.GetCounter(4));
cmd.Parameters.AddWithValue("@npcLsFrom", qData.GetNpcLsFrom());
cmd.Parameters.AddWithValue("@npcLsMsgStep", qData.GetMsgStep());
cmd.ExecuteNonQuery();
}
catch (MySqlException e)
@ -1216,7 +1216,10 @@ namespace Meteor.Map
flags,
counter1,
counter2,
counter3
counter3,
counter4,
npcLsFrom,
npcLsMsgStep
FROM characters_quest_scenario WHERE characterId = @charId";
cmd = new MySqlCommand(query, conn);
@ -1232,11 +1235,13 @@ namespace Meteor.Map
ushort counter1 = reader.GetUInt16("counter1");
ushort counter2 = reader.GetUInt16("counter2");
ushort counter3 = reader.GetUInt16("counter3");
//ushort counter4 = reader.GetUInt16("counter4");
ushort counter4 = reader.GetUInt16("counter4");
ushort npsLsFrom = reader.GetUInt16("npcLsFrom");
byte npcLsMsgStep = reader.GetByte("npcLsMsgStep");
Quest baseQuest = (Quest) Server.GetStaticActors(questId);
player.playerWork.questScenario[index] = questId;
player.questScenario[index] = new Quest(player, baseQuest, sequence, flags, counter1, counter2, counter3, 0);
player.questScenario[index] = new Quest(player, baseQuest, sequence, flags, counter1, counter2, counter3, counter4, npsLsFrom, npcLsMsgStep);
}
}

View file

@ -144,9 +144,8 @@ namespace Meteor.Map
privateAreaName,
privateAreaType,
className,
dayMusic,
nightMusic,
battleMusic
canExitArea,
music
FROM server_zones_privateareas
WHERE privateAreaName IS NOT NULL";
@ -161,7 +160,7 @@ namespace Meteor.Map
if (zoneList.ContainsKey(parentZoneId))
{
Zone parent = zoneList[parentZoneId];
PrivateArea privArea = new PrivateArea(parent, reader.GetString("className"), reader.GetString("privateAreaName"), reader.GetInt32("privateAreaType"), reader.GetUInt16("dayMusic"), reader.GetUInt16("nightMusic"), reader.GetUInt16("battleMusic"));
PrivateArea privArea = new PrivateArea(parent, reader.GetString("className"), reader.GetString("privateAreaName"), reader.GetInt32("privateAreaType"), reader.GetBoolean("canExitArea"), reader.GetUInt16("music"));
parent.AddPrivateArea(privArea);
}
else
@ -884,10 +883,6 @@ namespace Meteor.Map
player.playerSession.LockUpdates(false);
//Send "You have left the instance" if old area is a Private Area
if (oldArea is PrivateArea)
player.SendGameMessage(GetActor(), 34110, 0x20);
//Send "You have entered an instance" if it's a Private Area
if (newArea is PrivateArea)
player.SendGameMessage(GetActor(), 34108, 0x20);
@ -943,7 +938,7 @@ namespace Meteor.Map
DoZoneChange(player, player.CurrentArea.ZoneId, null, 0, 15, x, y, z, rotation);
}
public void WarpToPosition(Player player, float x, float y, float z, float rotation)
public void WarpToPosition(Player player, float x, float y, float z, float rotation, bool debugInstant = false)
{
//Remove player from currentZone if transfer else it's login
if (player.CurrentArea != null)
@ -960,13 +955,18 @@ namespace Meteor.Map
//Send packets
player.playerSession.QueuePacket(_0xE2Packet.BuildPacket(player.Id, 0x10));
player.playerSession.QueuePacket(player.CreateSpawnTeleportPacket(0));
player.playerSession.QueuePacket(player.CreateSpawnTeleportPacket(debugInstant ? (ushort) 0x0 : (ushort) 0xF));
player.playerSession.LockUpdates(false);
player.SendInstanceUpdate();
}
}
public void WarpToCharaPosition(Player player, Character target)
{
WarpToPosition(player, target.positionX, target.positionY, target.positionZ, target.rotation);
}
//Moves actor to new zone, and sends packets to spawn at the given coords.
public void DoZoneChangeContent(Player player, PrivateAreaContent contentArea, float spawnX, float spawnY, float spawnZ, float spawnRotation, ushort spawnType = SetActorPositionPacket.SPAWNTYPE_WARP_DUTY)
{