Quantcast
--[[
##############################################################################
_____/\\\\\\\\\\\____/\\\________/\\\__/\\\________/\\\__/\\\\\\\\\\\_       #
 ___/\\\/////////\\\_\/\\\_______\/\\\_\/\\\_______\/\\\_\/////\\\///__      #
  __\//\\\______\///__\//\\\______/\\\__\/\\\_______\/\\\_____\/\\\_____     #
   ___\////\\\__________\//\\\____/\\\___\/\\\_______\/\\\_____\/\\\_____    #
    ______\////\\\________\//\\\__/\\\____\/\\\_______\/\\\_____\/\\\_____   #
     _________\////\\\______\//\\\/\\\_____\/\\\_______\/\\\_____\/\\\_____  #
      __/\\\______\//\\\______\//\\\\\______\//\\\______/\\\______\/\\\_____ #
       _\///\\\\\\\\\\\/________\//\\\________\///\\\\\\\\\/____/\\\\\\\\\\\_#
        ___\///////////___________\///___________\/////////_____\///////////_#
##############################################################################
S U P E R - V I L L A I N - U I   By: Munglunch                              #
##############################################################################
##########################################################
LOCALIZED LUA FUNCTIONS
##########################################################
]]--
--[[ GLOBALS ]]--
local _G = _G;
local unpack 	= _G.unpack;
local select 	= _G.select;
local pairs 	= _G.pairs;
local type 		= _G.type;
local tinsert 	= _G.tinsert;
local string 	= _G.string;
local math 		= _G.math;
local table 	= _G.table;
--[[ STRING METHODS ]]--
local format,find = string.format, string.find;
--[[ MATH METHODS ]]--
local floor = math.floor;
--[[ TABLE METHODS ]]--
local twipe, tcopy = table.wipe, table.copy;
--[[
##########################################################
GET ADDON DATA
##########################################################
]]--
local SuperVillain, L = unpack(SVUI);
local SVUIAddOnName, SVUIAddOn = ...;
local StyleVillain = SVUI_LIB:SetObject(SVUIAddOnName);

SVUIAddOn = StyleVillain;

_G["StyleVillain"] = SVUIAddOn;

local DOCK = SuperVillain.Registry:Expose('SVDock');
local SuperDockWindow = _G["SuperDockWindow"];
local SuperDockletMain = _G["SuperDockletMain"];
local SuperDockletExtra = _G["SuperDockletExtra"];
local NewHook = hooksecurefunc;
local SVUIAddonEventHandler = CreateFrame("Frame", "SVUIAddonEventHandler")
--[[
##########################################################
CORE DATA
##########################################################
]]--
StyleVillain.DockedParent = {}
StyleVillain.AddOnQueue = {};
StyleVillain.AddOnEvents = {};
StyleVillain.BlizzardQueue = {};
StyleVillain.CustomQueue = {};
StyleVillain.EventListeners = {};
StyleVillain.PassiveAddons = {};
StyleVillain.OptionsCache = {
	order = 4,
	type = "group",
	name = "Addon Styling",
	get = function(a)return SuperVillain.db.SVStyle.addons[a[#a]] end,
	set = function(a,b)SuperVillain.db.SVStyle.addons[a[#a]] = b;SuperVillain:StaticPopup_Show("RL_CLIENT")end,
	disabled = function()return not SuperVillain.db.SVStyle.addons.enable end,
	guiInline = true,
	args = {
		ace3 = {
			type = "toggle",
			order = 1,
			name = "Ace3"
		},
	}
};
--[[
##########################################################
CORE FUNCTIONS
##########################################################
]]--
function StyleVillain:LoadAlert(MainText, Function)
	self.Alert.Text:SetText(MainText)
	self.Alert.Accept:SetScript('OnClick', Function)
	self.Alert:Show()
end

function StyleVillain:IsAddonReady(this, ...)
	for i = 1, select('#', ...) do
		local a = select(i, ...)
		if not a then break end
		if not IsAddOnLoaded(a) then return false end
	end
	return SuperVillain.db.SVStyle.addons[this]
end

function StyleVillain:SaveAddonStyle(addon, fn, force, passive, ...)
	local args,hasEvent = {},false;
	for i=1, select("#",...) do
		local event = select(i,...)
		if event then
			args[event] = true
			hasEvent = true;
		end;
	end;
	if passive then self.PassiveAddons[addon] = true end;
	if not self.AddOnEvents[addon] then
		self.AddOnEvents[addon] = {};
		self.AddOnEvents[addon]["complete"] = false;
		if hasEvent then
			self.AddOnEvents[addon]["events"] = args;
		end
	end
	if force then
		fn()
		self.AddOnQueue[addon] = nil
	else
		self.AddOnQueue[addon] = fn
	end
end;

function StyleVillain:SaveBlizzardStyle(addon, fn, force, passive, preload)
	if passive then self.PassiveAddons[addon] = true end;
	if force then
		if(preload and not IsAddOnLoaded(addon)) then
			LoadAddOn(addon)
		end
		fn()
		self.BlizzardQueue[addon] = nil
	else
		self.BlizzardQueue[addon] = fn
	end
end;

function StyleVillain:SaveCustomStyle(fn)
	tinsert(StyleVillain.CustomQueue, fn)
end;

function StyleVillain:DefineEventFunction(addonEvent, addon)
	if(not self.EventListeners[addonEvent]) then
		self.EventListeners[addonEvent] = {}
	end
	if(addon) then
		self.EventListeners[addonEvent][addon] = true
	end
	if(not self[addonEvent]) then
		self[addonEvent] = function(self, event, ...)
			for addon,fn in pairs(self.AddOnQueue)do
				if self:IsAddonReady(addon) and self.EventListeners[event] and self.EventListeners[event][addon] then
					local _,error = pcall(fn, event, ...)
				end
			end
		end;
		SVUIAddonEventHandler:RegisterEvent(addonEvent);
	end
end

function StyleVillain:SafeEventRemoval(addon, event)
	if not self.EventListeners[event] then return end;
	if not self.EventListeners[event][addon] then return end;
	self.EventListeners[event][addon] = nil;
	local defined = false;
	for name,_ in pairs(self.EventListeners[event]) do
		if name then
			defined = true;
			break
		end
	end;
	if not defined then
		SVUIAddonEventHandler:UnregisterEvent(event)
	end
end;

function StyleVillain:RefreshAddonStyles()
	for addon,fn in pairs(self.AddOnQueue) do
		if(SuperVillain.db.SVStyle.addons[addon] == true) then
			if IsAddOnLoaded(addon) then
				local _,error = pcall(fn, "PLAYER_ENTERING_WORLD")
			end
		end
	end
end

function StyleVillain:LoadStyles()
	for addon,fn in pairs(self.BlizzardQueue) do
		if IsAddOnLoaded(addon) then
			fn()
			self.BlizzardQueue[addon]=nil
		end
	end;
	for _,fn in pairs(self.CustomQueue)do
		fn()
	end;
	twipe(self.CustomQueue)
	for addon,fn in pairs(self.AddOnQueue)do
		StyleVillain:AppendAddonOption(addon)
		if IsAddOnLoaded(addon) then
			if(SuperVillain.db.SVStyle.addons[addon] == nil) then
				SuperVillain.db.SVStyle.addons[addon] = true
			end
			if(SuperVillain.db.SVStyle.addons[addon] == true) then
				if(not self.AddOnEvents[addon]["complete"]) then
					if self.AddOnEvents[addon]["events"] then
						for event,_ in pairs(self.AddOnEvents[addon]["events"]) do
							self:DefineEventFunction(event, addon)
						end
					end
					self.AddOnEvents[addon]["complete"] = true
				end
			end
		end
	end;
	self:RefreshAddonStyles()
end

function StyleVillain:ToggleStyle(addon, value)
	SuperVillain.db.SVStyle.addons[addon] = value
end;
--[[
##########################################################
OPTIONS CREATION
##########################################################
]]--
function StyleVillain:AppendAddonOption(addon)
	StyleVillain.OptionsCache.args[addon] = {
		type = "toggle",
		name = addon,
		desc = L["Addon Styling"],
		get=function(a)return StyleVillain:IsAddonReady(a[#a])end,
		set=function(a,b)SuperVillain.db.SVStyle.addons[a[#a]] = b;SuperVillain:StaticPopup_Show("RL_CLIENT")end,
		disabled = function()
			if addon then
				 return not IsAddOnLoaded(addon)
			else
				 return false
			end
		end
	}
end;

function StyleVillain:SetConfigOptions()
	SuperVillain.Options.args.SVStyle={
		type = "group",
		name = L["UI Styling"],
		childGroups = "tree",
		args = {
			intro = {
				order = 1,
				type = "description",
				name = L["ART_DESC"]
			},
			blizzardEnable = {
				order = 2,
				type = "toggle",
				name = "Standard UI Styling",
				get = function(a)return SuperVillain.db.SVStyle.blizzard.enable end,
				set = function(a,b)SuperVillain.db.SVStyle.blizzard.enable = b;SuperVillain:StaticPopup_Show("RL_CLIENT")end
			},
			addonEnable = {
				order = 3,
				type = "toggle",
				name = "Addon Styling",
				get = function(a)return SuperVillain.db.SVStyle.addons.enable end,
				set = function(a,b)SuperVillain.db.SVStyle.addons.enable = b;SuperVillain:StaticPopup_Show("RL_CLIENT")end
			},
			blizzard = {
				order = 300,
				type = "group",
				name = "Individual Mods",
				get = function(a)return SuperVillain.db.SVStyle.blizzard[a[#a]]end,
				set = function(a,b)SuperVillain.db.SVStyle.blizzard[a[#a]] = b;SuperVillain:StaticPopup_Show("RL_CLIENT")end,
				disabled = function()return not SuperVillain.db.SVStyle.blizzard.enable end,
				guiInline = true,
				args = {
					bmah = {
						type = "toggle",
						name = L["Black Market AH"],
						desc = L["TOGGLEART_DESC"]
					},
						transmogrify = {
						type = "toggle",
						name = L["Transmogrify Frame"],
						desc = L["TOGGLEART_DESC"]
					},
						encounterjournal = {
						type = "toggle",
						name = L["Encounter Journal"],
						desc = L["TOGGLEART_DESC"]
					},
						reforge = {
						type = "toggle",
						name = L["Reforge Frame"],
						desc = L["TOGGLEART_DESC"]
					},
						calendar = {
						type = "toggle",
						name = L["Calendar Frame"],
						desc = L["TOGGLEART_DESC"]
					},
						achievement = {
						type = "toggle",
						name = L["Achievement Frame"],
						desc = L["TOGGLEART_DESC"]
					},
						lfguild = {
						type = "toggle",
						name = L["LF Guild Frame"],
						desc = L["TOGGLEART_DESC"]
					},
						inspect = {
						type = "toggle",
						name = L["Inspect Frame"],
						desc = L["TOGGLEART_DESC"]
					},
						binding = {
						type = "toggle",
						name = L["KeyBinding Frame"],
						desc = L["TOGGLEART_DESC"]
					},
						gbank = {
						type = "toggle",
						name = L["Guild Bank"],
						desc = L["TOGGLEART_DESC"]
					},
						archaeology = {
						type = "toggle",
						name = L["Archaeology Frame"],
						desc = L["TOGGLEART_DESC"]
					},
						guildcontrol = {
						type = "toggle",
						name = L["Guild Control Frame"],
						desc = L["TOGGLEART_DESC"]
					},
						guild = {
						type = "toggle",
						name = L["Guild Frame"],
						desc = L["TOGGLEART_DESC"]
					},
						tradeskill = {
						type = "toggle",
						name = L["TradeSkill Frame"],
						desc = L["TOGGLEART_DESC"]
					},
						raid = {
						type = "toggle",
						name = L["Raid Frame"],
						desc = L["TOGGLEART_DESC"]
					},
						talent = {
						type = "toggle",
						name = L["Talent Frame"],
						desc = L["TOGGLEART_DESC"]
					},
						auctionhouse = {
						type = "toggle",
						name = L["Auction Frame"],
						desc = L["TOGGLEART_DESC"]
					},
						timemanager = {
						type = "toggle",
						name = L["Time Manager"],
						desc = L["TOGGLEART_DESC"]
					},
						barber = {
						type = "toggle",
						name = L["Barbershop Frame"],
						desc = L["TOGGLEART_DESC"]
					},
						macro = {
						type = "toggle",
						name = L["Macro Frame"],
						desc = L["TOGGLEART_DESC"]
					},
						debug = {
						type = "toggle",
						name = L["Debug Tools"],
						desc = L["TOGGLEART_DESC"]
					},
						trainer = {
						type = "toggle",
						name = L["Trainer Frame"],
						desc = L["TOGGLEART_DESC"]
					},
						socket = {
						type = "toggle",
						name = L["Socket Frame"],
						desc = L["TOGGLEART_DESC"]
					},
						alertframes = {
						type = "toggle",
						name = L["Alert Frames"],
						desc = L["TOGGLEART_DESC"]
					},
						loot = {
						type = "toggle",
						name = L["Loot Frames"],
						desc = L["TOGGLEART_DESC"]
					},
						bgscore = {
						type = "toggle",
						name = L["BG Score"],
						desc = L["TOGGLEART_DESC"]
					},
						merchant = {
						type = "toggle",
						name = L["Merchant Frame"],
						desc = L["TOGGLEART_DESC"]
					},
						mail = {
						type = "toggle",
						name = L["Mail Frame"],
						desc = L["TOGGLEART_DESC"]
					},
						help = {
						type = "toggle",
						name = L["Help Frame"],
						desc = L["TOGGLEART_DESC"]
					},
						trade = {
						type = "toggle",
						name = L["Trade Frame"],
						desc = L["TOGGLEART_DESC"]
					},
						gossip = {
						type = "toggle",
						name = L["Gossip Frame"],
						desc = L["TOGGLEART_DESC"]
					},
						greeting = {
						type = "toggle",
						name = L["Greeting Frame"],
						desc = L["TOGGLEART_DESC"]
					},
						worldmap = {
						type = "toggle",
						name = L["World Map"],
						desc = L["TOGGLEART_DESC"]
					},
						taxi = {
						type = "toggle",
						name = L["Taxi Frame"],
						desc = L["TOGGLEART_DESC"]
					},
						lfg = {
						type = "toggle",
						name = L["LFG Frame"],
						desc = L["TOGGLEART_DESC"]
					},
						mounts = {
						type = "toggle",
						name = L["Mounts & Pets"],
						desc = L["TOGGLEART_DESC"]
					},
						quest = {
						type = "toggle",
						name = L["Quest Frames"],
						desc = L["TOGGLEART_DESC"]
					},
						petition = {
						type = "toggle",
						name = L["Petition Frame"],
						desc = L["TOGGLEART_DESC"]
					},
						dressingroom = {
						type = "toggle",
						name = L["Dressing Room"],
						desc = L["TOGGLEART_DESC"]
					},
						pvp = {
						type = "toggle",
						name = L["PvP Frames"],
						desc = L["TOGGLEART_DESC"]
					},
						nonraid = {
						type = "toggle",
						name = L["Non-Raid Frame"],
						desc = L["TOGGLEART_DESC"]
					},
						friends = {
						type = "toggle",
						name = L["Friends"],
						desc = L["TOGGLEART_DESC"]
					},
						spellbook = {
						type = "toggle",
						name = L["Spellbook"],
						desc = L["TOGGLEART_DESC"]
					},
						character = {
						type = "toggle",
						name = L["Character Frame"],
						desc = L["TOGGLEART_DESC"]
					},
						misc = {
						type = "toggle",
						name = L["Misc Frames"],
						desc = L["TOGGLEART_DESC"]
					},
						tabard = {
						type = "toggle",
						name = L["Tabard Frame"],
						desc = L["TOGGLEART_DESC"]
					},
						guildregistrar = {
						type = "toggle",
						name = L["Guild Registrar"],
						desc = L["TOGGLEART_DESC"]
					},
						bags = {
						type = "toggle",
						name = L["Bags"],
						desc = L["TOGGLEART_DESC"]
					},
						stable = {
						type = "toggle",
						name = L["Stable"],
						desc = L["TOGGLEART_DESC"]
					},
						bgmap = {
						type = "toggle",
						name = L["BG Map"],
						desc = L["TOGGLEART_DESC"]
					},
						petbattleui = {
						type = "toggle",
						name = L["Pet Battle"],
						desc = L["TOGGLEART_DESC"]
					},
						losscontrol = {
						type = "toggle",
						name = L["Loss Control"],
						desc = L["TOGGLEART_DESC"]
					},
						voidstorage = {
						type = "toggle",
						name = L["Void Storage"],
						desc = L["TOGGLEART_DESC"]
					},
						itemUpgrade = {
						type = "toggle",
						name = L["Item Upgrade"],
						desc = L["TOGGLEART_DESC"]
					}
				}
			},
			addons = StyleVillain.OptionsCache
		}
	}
end;

local RegisterAddonDocklets = function()
	local main = SuperVillain.db.SVDock.docklets.DockletMain;
  	local alternate = SuperVillain.db.SVDock.docklets.enableExtra and SuperVillain.db.SVDock.docklets.DockletExtra or "";

  	if main == nil or main == "None" then return end;

	if find(main, "Skada") or find(alternate, "Skada") then
		if DOCK:IsDockletReady("Skada") then
			StyleVillain:Docklet_Skada()
			if find(alternate, "Skada") and SuperDockletExtra.FrameName  ~= "SkadaHolder2" then
				DOCK.ExtraToolTip = "Skada";
				DOCK:RegisterExtraDocklet("SkadaHolder2")
				--StyleVillain.DockedParent["Skada"] = SuperDockletExtra
			end
			if find(main, "Skada") and SuperDockletMain.FrameName  ~= "SkadaHolder" then
				DOCK.MainToolTip = "Skada";
				DOCK:RegisterMainDocklet("SkadaHolder")
				--StyleVillain.DockedParent["Skada"] = SuperDockletMain
			end
		end;
	end;
	if main == "Omen" or alternate == "Omen" then
		if DOCK:IsDockletReady("Omen") then
			if alternate == "Omen" and SuperDockletExtra.FrameName ~= "OmenAnchor" then
				DOCK.ExtraToolTip = "Omen";
				DOCK:RegisterExtraDocklet("OmenAnchor")
				StyleVillain:Docklet_Omen(SuperDockletExtra)
				StyleVillain.DockedParent["Omen"] = SuperDockletExtra
			elseif SuperDockletMain.FrameName ~= "OmenAnchor" then
				DOCK.MainToolTip = "Omen";
				DOCK:RegisterMainDocklet("OmenAnchor")
				StyleVillain:Docklet_Omen(SuperDockletMain)
				StyleVillain.DockedParent["Omen"] = SuperDockletMain
			end
		end;
	end;
	if main == "Recount" or alternate == "Recount" then
		if DOCK:IsDockletReady("Recount") then
			if alternate == "Recount" and SuperDockletExtra.FrameName ~= "Recount_MainWindow" then
				DOCK.ExtraToolTip = "Recount";
				DOCK:RegisterExtraDocklet("Recount_MainWindow")
				StyleVillain:Docklet_Recount(SuperDockletExtra)
				StyleVillain.DockedParent["Recount"] = SuperDockletExtra
			elseif SuperDockletMain.FrameName ~= "Recount_MainWindow" then
				DOCK.MainToolTip = "Recount";
				DOCK:RegisterMainDocklet("Recount_MainWindow")
				StyleVillain:Docklet_Recount(SuperDockletMain)
				StyleVillain.DockedParent["Recount"] = SuperDockletMain
			end
		end;
	end;
	if main == "TinyDPS" or alternate == "TinyDPS" then
		if DOCK:IsDockletReady("TinyDPS") then
			if alternate == "TinyDPS" and SuperDockletExtra.FrameName ~= "tdpsFrame" then
				DOCK.ExtraToolTip = "TinyDPS";
				DOCK:RegisterExtraDocklet("tdpsFrame")
				StyleVillain:Docklet_TinyDPS(SuperDockletExtra)
				StyleVillain.DockedParent["TinyDPS"] = SuperDockletExtra
			elseif SuperDockletMain.FrameName ~= "tdpsFrame" then
				DOCK.MainToolTip = "TinyDPS";
				DOCK:RegisterMainDocklet("tdpsFrame")
				StyleVillain:Docklet_TinyDPS(SuperDockletMain)
				StyleVillain.DockedParent["TinyDPS"] = SuperDockletMain
			end
		end;
	end;
	if main == "alDamageMeter" or alternate == "alDamageMeter" then
		if DOCK:IsDockletReady("alDamageMeter") then
			if alternate == "alDamageMeter" and SuperDockletExtra.FrameName ~= "alDamagerMeterFrame" then
				DOCK.ExtraToolTip = "alDamageMeter";
				DOCK:RegisterExtraDocklet("alDamagerMeterFrame")
				StyleVillain:Docklet_alDamageMeter(SuperDockletExtra)
				StyleVillain.DockedParent["alDamageMeter"] = SuperDockletExtra
			elseif SuperDockletMain.FrameName ~= "alDamagerMeterFrame" then
				DOCK.MainToolTip = "alDamageMeter";
				DOCK:RegisterMainDocklet("alDamagerMeterFrame")
				StyleVillain:Docklet_alDamageMeter(SuperDockletMain)
				StyleVillain.DockedParent["alDamageMeter"] = SuperDockletMain
			end
		end;
	end;
end;
--[[
##########################################################
BUILD FUNCTION
##########################################################
]]--
local function LoadStyleOMatic()
	local alert = CreateFrame('Frame', nil, UIParent);
	alert:SetFixedPanelTemplate('Transparent');
	alert:SetSize(250, 70);
	alert:SetPoint('CENTER', UIParent, 'CENTER');
	alert:SetFrameStrata('DIALOG');
	alert.Text = alert:CreateFontString(nil, "OVERLAY");
	alert.Text:SetFont(SuperVillain.Media.font.default, 12);
	alert.Text:SetPoint('TOP', alert, 'TOP', 0, -10);
	alert.Accept = CreateFrame('Button', nil, alert);
	alert.Accept:SetSize(70, 25);
	alert.Accept:SetPoint('RIGHT', alert, 'BOTTOM', -10, 20);
	alert.Accept.Text = alert.Accept:CreateFontString(nil, "OVERLAY");
	alert.Accept.Text:SetFont(SuperVillain.Media.font.default, 10);
	alert.Accept.Text:SetPoint('CENTER');
	alert.Accept.Text:SetText(YES);
	alert.Close = CreateFrame('Button', nil, alert);
	alert.Close:SetSize(70, 25);
	alert.Close:SetPoint('LEFT', alert, 'BOTTOM', 10, 20);
	alert.Close:SetScript('OnClick', function(self) self:GetParent():Hide() end);
	alert.Close.Text = alert.Close:CreateFontString(nil, "OVERLAY");
	alert.Close.Text:SetFont(SuperVillain.Media.font.default, 10);
	alert.Close.Text:SetPoint('CENTER');
	alert.Close.Text:SetText(NO);
	alert.Accept:SetButtonTemplate();
	alert.Close:SetButtonTemplate();
	alert:Hide();
	StyleVillain.Alert = alert;

	StyleVillain:LoadStyles();
	NewHook(DOCK, "ReloadDocklets", RegisterAddonDocklets);
	DOCK:ReloadDocklets();
	SuperVillain.DynamicOptions["SVStyle"] = {key = "addons", data = StyleVillain.OptionsCache};
	SVUIAddonEventHandler:RegisterEvent('ADDON_LOADED');
end

SuperVillain.Registry:NewScript(LoadStyleOMatic)
SuperVillain.Registry:NewPlugin(SVUIAddOnName, StyleVillain.SetConfigOptions)

local Registry_OnEvent = function(self, event, ...)
	-- print("--------------------------------------")
	-- print("Registered Event Fired: ")
	-- print(event)
	-- print("--------------------------------------")
	if(event == "ADDON_LOADED") then
		local addon = select(1, ...)
		if StyleVillain.PassiveAddons[addon] then
			StyleVillain.BlizzardQueue[addon]()
			StyleVillain.BlizzardQueue[addon] = nil;
			return
		end;
		if not SuperVillain.CoreEnabled or not StyleVillain.BlizzardQueue[addon] then return end;
		StyleVillain.BlizzardQueue[addon]()
		StyleVillain.BlizzardQueue[addon] = nil
	elseif(StyleVillain[event]) then
		StyleVillain[event](StyleVillain, event, ...)
	end
end
SVUIAddonEventHandler:SetScript("OnEvent", Registry_OnEvent)