local me, ns = ... ns.Configure() local addon=addon --#addon local shipyard local _G=_G local GMF=GMF local GSF=GSF local GMFMissions=GarrisonMissionFrameMissions local GSFMissions=GarrisonMissionFrameMissions local GARRISON_CURRENCY=GARRISON_CURRENCY local GARRISON_SHIP_OIL_CURRENCY=_G.GARRISON_SHIP_OIL_CURRENCY local SEAL_CURRENCY=994 local LE_FOLLOWER_TYPE_GARRISON_6_0=_G.LE_FOLLOWER_TYPE_GARRISON_6_0 -- 1 local LE_FOLLOWER_TYPE_SHIPYARD_6_2=_G.LE_FOLLOWER_TYPE_SHIPYARD_6_2 -- 2 local pairs=pairs local format=format local strsplit=strsplit local generated local shipsnumber=0 local salvages={ 114120,114119,114116} local module=addon:NewSubClass('MissionCompletion') --#Module function module:GenerateMissionCompleteList(title,anchor) local w=AceGUI:Create("GCMCList") --@debug@ title=format("%s %s %s",title,w.frame:GetName(),GetTime()*1000) --@end-debug@ w:SetTitle(title) w:SetCallback("OnClose",function(widget) widget:Release() return module:MissionsCleanup() end) --report:SetPoint("TOPLEFT",GMFMissions.CompleteDialog.BorderFrame) --report:SetPoint("BOTTOMRIGHT",GMFMissions.CompleteDialog.BorderFrame) w:ClearAllPoints() w:SetPoint("TOP",anchor) w:SetPoint("BOTTOM",anchor) w:SetWidth(500) w:SetParent(anchor) w.frame:SetFrameStrata("HIGH") return w end --@debug@ function addon.ShowRewards() module:GenerateMissionCompleteList("Test",UIParent) end --@end-debug@ local cappedCurrencies={ GARRISON_CURRENCY, GARRISON_SHIP_OIL_CURRENCY } local missions={} local followerType=LE_FOLLOWER_TYPE_GARRISON_6_0 local missionsFrame local panel local states={} local rewards={ items={}, followerBase={}, followerXP=setmetatable({},{__index=function() return 0 end}), currencies=setmetatable({},{__index=function(t,k) rawset(t,k,{icon="",qt=0}) return t[k] end}), } local scroller local report local timer local function stopTimer() if (timer) then module:CancelTimer(timer) timer=nil end end local function startTimer(delay,event,...) delay=delay or 0.2 event=event or "LOOP" stopTimer() timer=module:ScheduleRepeatingTimer("MissionAutoComplete",delay,event,...) --@debug@ print("Timer rearmed for",event,delay) --@end-debug@ end function module:MissionsCleanup() local f=panel local fmissions=missionsFrame local module=followerType==LE_FOLLOWER_TYPE_GARRISON_6_0 and addon or addon:GetModule(LE_FOLLOWER_TYPE_SHIPYARD_6_2 and "ShipYard" or "OrderHall") self:Events(false) stopTimer() f.MissionTab.MissionList.CompleteDialog:Hide() f.MissionComplete:Hide() f.MissionCompleteBackground:Hide() f.MissionComplete.currentIndex = nil f.MissionTab:Show() -- Re-enable "view" button fmissions.CompleteDialog.BorderFrame.ViewButton:SetEnabled(true) module:OpenLastTab() f:UpdateMissions() f:CheckCompleteMissions() end function module:Events(on) if (on) then self:RegisterEvent("GARRISON_MISSION_BONUS_ROLL_LOOT","MissionAutoComplete") self:RegisterEvent("GARRISON_MISSION_BONUS_ROLL_COMPLETE","MissionAutoComplete") self:RegisterEvent("GARRISON_MISSION_COMPLETE_RESPONSE","MissionAutoComplete") self:RegisterEvent("GARRISON_FOLLOWER_XP_CHANGED","MissionAutoComplete") self:RegisterEvent("GARRISON_FOLLOWER_REMOVED","MissionAutoComplete") else self:UnregisterAllEvents() end end function module:CloseReport() if report then pcall(report.Close,report) report=nil end if GSF and GSF:IsVisible() then --@debug@ print "Ship close mission" --@end-debug@ GSF:CloseMissionComplete() elseif GMF and GMF:IsVisible() then --@debug@ print "Garr close mission" --@end-debug@ GMF:CloseMissionComplete() end addon:OpenMissionsTab() addon:RefreshParties() addon:RefreshMissions() end function module:MissionComplete(this,button,skiprescheck) followerType=this.missionType missions=G.GetCompleteMissions(followerType) shipyard=addon:GetModule("ShipYard") shipsnumber=shipyard:GetTotFollowers() local module=self:GetMissionModule(followerType) missionsFrame=module:GetMissions() panel=module:GetMain() if (missions and #missions > 0) then this:SetEnabled(false) missionsFrame.CompleteDialog.BorderFrame.ViewButton:SetEnabled(false) -- Disabling standard Blizzard Completion wipe(rewards.followerBase) wipe(rewards.followerXP) wipe(rewards.currencies) wipe(rewards.items) local message=C("WARNING",'red') local wasted={} for i=1,#missions do for k,v in pairs(missions[i].followers) do -- rewards.followerBase[v]=self:GetAnyData(followerType,v,'qLevel',0) rewards.followerBase[v]=self:GetAnyData(followerType,v) end for k,v in pairs(missions[i].rewards) do if v.itemID then GetItemInfo(v.itemID) end -- tickling server if v.currencyID and tContains(cappedCurrencies,v.currencyID) then wasted[v.currencyID]=(wasted[v.currencyID] or 0) + v.quantity end end local m=missions[i] --totalTimeString, totalTimeSeconds, isMissionTimeImproved, successChance, partyBuffs, isEnvMechanicCountered, xpBonus, materialMultiplier, goldMultiplier = C_Garrison.GetPartyMissionInfo(MISSION_PAGE_FRAME.missionInfo.missionID); local _ _,_,m.isMissionTimeImproved,m.successChance,_,_,m.xpBonus,m.resourceMultiplier,m.goldMultiplier=G.GetPartyMissionInfo(m.missionID) end local stop for id,qt in pairs(wasted) do local name,current,_,_,_,cap=GetCurrencyInfo(id) --@debug@ print(name,current,qt,cap) --@end-debug@ current=current+qt if current+qt > cap then message=message.."\n"..format(L["Capped %1$s. Spend at least %2$d of them"],name,current+qt-cap) stop =true end end if stop and not skiprescheck then self:Popup(message.."\n" ..format(L["If you %s, you will lose them\nClick on %s to abort"],ACCEPT,CANCEL),0, function() StaticPopup_Hide("LIBINIT_POPUP") module:MissionComplete(this,button,true) end, function() StaticPopup_Hide("LIBINIT_POPUP") this:SetEnabled(true) missionsFrame.CompleteDialog.BorderFrame.ViewButton:SetEnabled(true) panel:Hide() ns.quick=false end ) return end report=self:GenerateMissionCompleteList("Missions' results",panel) report:SetUserData('missions',missions) report:SetUserData('current',1) self:Events(true) self:MissionAutoComplete("INIT") this:SetEnabled(true) end end function module:GetMission(missionID) if not report then return end local missions=report:GetUserData('missions') if missions then for i=1,#missions do if missions[i].missionID==missionID then return missions[i] end end end end function module:MissionAutoComplete(event,ID,arg1,arg2,arg3,arg4,...) -- C_Garrison.MarkMissionComplete Mark mission as complete and prepare it for bonus roll, da chiamare solo in caso di successo -- C_Garrison.MissionBonusRoll --@debug@ print("evt",event,ID,arg1 or'',arg2 or '',arg3 or '',...) --@end-debug@ if event=="LOOT" then return self:MissionsPrintResults() end local current=report:GetUserData('current') local currentMission=report:GetUserData('missions')[current] local missionID=currentMission and currentMission.missionID or 0 -- GARRISON_FOLLOWER_XP_CHANGED: followerID, xpGained, actualXp, newLevel, quality if (event=="GARRISON_FOLLOWER_XP_CHANGED") then ID=arg1 arg1=arg2 if tonumber(arg1,0) then --report:AddFollower(ID,arg1,arg2) rewards.followerXP[ID]=rewards.followerXP[ID]+tonumber(arg1) or 0 end return -- GARRISON_MISSION_BONUS_ROLL_LOOT: itemID elseif (event=="GARRISON_MISSION_BONUS_ROLL_LOOT") then if (missionID) then rewards.items[format("%d:%s",missionID,ID)]=1 else rewards.items[format("%d:%s",0,ID)]=1 end return -- GARRISON_FOLLOWER_REMOVED elseif (event=="GARRISON_FOLLOWER_REMOVED") then -- gestire la distruzione di un follower... senza il follower -- GARRISON_MISSION_COMPLETE_RESPONSE: missionID, requestCompleted, succeeded elseif (event=="GARRISON_MISSION_COMPLETE_RESPONSE") then if (not arg1) then -- We need to call server again currentMission.state=0 elseif (arg2) then -- success, we need to roll currentMission.state=1 else -- failure, just print results currentMission.state=2 end startTimer(0.1) return -- GARRISON_MISSION_BONUS_ROLL_COMPLETE: missionID, requestCompleted; happens after C_Garrison.MissionBonusRoll elseif (event=="GARRISON_MISSION_BONUS_ROLL_COMPLETE") then if (not arg1) then -- We need to call server again currentMission.state=1 else currentMission.state=3 end startTimer(0.1) return else -- event == LOOP or INIT if (currentMission) then local step=currentMission.state or -1 if (step<1) then step=0 currentMission.state=0 currentMission.goldMultiplier=currentMission.goldMultiplier or 1 currentMission.xp=select(2,G.GetMissionInfo(currentMission.missionID)) report:AddMissionButton(currentMission,addon:GetParty(currentMission.missionID),currentMission.successChance,"report") end if (step==0) then --@debug@ print("Fired mission complete for",currentMission.missionID) --@end-debug@ G.MarkMissionComplete(currentMission.missionID) startTimer(2) elseif (step==1) then --@debug@ print("Fired bonus roll complete for",currentMission.missionID) --@end-debug@ G.MissionBonusRoll(currentMission.missionID) startTimer(2) elseif (step>=2) then self:GetMissionResults(step==3,currentMission) addon:RefreshFollowerStatus() shipyard:RefreshFollowerStatus() local current=report:GetUserData('current') report:SetUserData('current',current+1) startTimer() return end currentMission.state=step else report:AddButton(L["Building Final report"]) startTimer(1,"LOOT") end end end function module:GetMissionResults(success,currentMission) stopTimer() if (success) then report:AddMissionResult(currentMission.missionID,true) PlaySound(SOUNDKIT.UI_GARRISON_MISSION_COMPLETE_MISSION_SUCCESS) else report:AddMissionResult(currentMission.missionID,false) PlaySound(SOUNDKIT.UI_GARRISON_MISSION_COMPLETE_MISSION_FAIL_STINGER) end if success then local resourceMultiplier=currentMission.resourceMultiplier or {} local goldMultiplier=currentMission.goldMultiplier or 1 for k,v in pairs(currentMission.rewards) do v.quantity=v.quantity or 0 if v.currencyID then rewards.currencies[v.currencyID].icon=v.icon local multi=resourceMultiplier[v.currencyID] if v.currencyID == 0 then rewards.currencies[v.currencyID].qt=rewards.currencies[v.currencyID].qt+v.quantity * goldMultiplier elseif resourceMultiplier[v.currencyID] then rewards.currencies[v.currencyID].qt=rewards.currencies[v.currencyID].qt+v.quantity * multi else rewards.currencies[v.currencyID].qt=rewards.currencies[v.currencyID].qt+v.quantity end elseif v.itemID then rewards.items[format("%d:%s",currentMission.missionID,v.itemID)]=1 end end end end function module:MissionsPrintResults(success) stopTimer() if ns.quick then self:CloseReport() local qm=addon:GetModule("Quick") addon.ScheduleTimer(qm,"RunQuick",0.2) return end local reported local followers for k,v in pairs(rewards.currencies) do reported=true if k == 0 then -- Money reward report:AddIconText(v.icon,GetMoneyString(v.qt)) else -- Other currency reward report:AddIconText(v.icon,GetCurrencyLink(k,v.qt)) end end local items=new() for k,v in pairs(rewards.items) do local missionid,itemid=strsplit(":",k) if (not items[itemid]) then items[itemid]=1 else items[itemid]=items[itemid]+1 end end for itemid,qt in pairs(items) do reported=true report:AddItem(itemid,qt) end del(items) for k,v in pairs(rewards.followerXP) do reported=true followers=true report:AddFollower(self:GetAnyData(followerType,k),v,self:GetAnyData(followerType,k,'qLevel',0) > tonumber(rewards.followerBase[k].qLevel,0)) end if not reported then report:AddRow(L["Nothing to report"]) end if not followers then report:AddRow(L["No follower gained xp"]) end if followerType==LE_FOLLOWER_TYPE_SHIPYARD_6_2 then local shipyard=addon:GetModule("ShipYard") local newshipsnumber=shipyard:GetTotFollowers() if shipsnumber ~= newshipsnumber then report:AddRow(C(format(L["You lost %d ships"],shipsnumber - newshipsnumber),"red")) for k,v in pairs(rewards.followerBase) do if not self:GetAnyData(followerType,k) then report:AddFollower(v,-1) end end end local fogFrames = GSF.MissionTab.MissionList.FogFrames for j=1, #fogFrames do fogFrames[j]:Hide() end GarrisonShipyardMap_UpdateMissions() addon:ScheduleTimer(GarrisonShipyardMap_UpdateMissions,0.1) end report:AddRow(DONE) end function addon:MissionComplete(...) return module:MissionComplete(...) end function addon:CloseMissionComplete() return module:CloseReport() end