Add Promise delayed calls

Sasky [06-21-14 - 12:27]
Add Promise delayed calls
Filename
LAddMin.lua
diff --git a/LAddMin.lua b/LAddMin.lua
index a72b602..897da76 100644
--- a/LAddMin.lua
+++ b/LAddMin.lua
@@ -45,10 +45,76 @@ local invalidAddons = {
 -- local missedPanelIDs = {}
 -- local lastID = 1000

+-------------------------------------------------------------------------------
+-- Delayed calls object, author Sasky (http://www.esoui.com/forums/member.php?u=2586)
+-------------------------------------------------------------------------------
+local Promise = {}
+setmetatable(Promise, {
+   __index = function(self, key)
+      self:__preSave(key)
+      return (self.__save)
+   end,
+   __call = function (cls, ...)
+      return cls.__new(...)
+   end
+})
+function Promise:__new()
+   local o = setmetatable({}, {
+      __index = Promise,
+      __call = function (cls, ...)
+         return cls:__execute(...)
+      end
+   })
+   o.callList = {}
+   o.nextKey = nil
+
+   return o
+end
+
+function Promise:__preSave(key)
+   self.nextKey = key
+end
+
+function Promise:__save(...)
+   if self.nextKey == nil then return end
+
+   table.insert(self.callList, {
+      func = self.nextKey,
+      narg = select('#', ...),
+      varargs = {...}
+   })
+   self.nextKey = nil
+end
+
+MISSED_CALLS = {}
+function Promise:__execute(obj)
+   for k,v in ipairs(self.callList) do
+      table.insert(MISSED_CALLS, k .. ":" .. v.func .. "(" .. table.concat(v.varargs,",") .. ")")
+      obj[v.func](v.func, unpack(v.varargs))
+   end
+end

 -------------------------------------------------------------------------------
 -- Library replacement --------------------------------------------------------
 -------------------------------------------------------------------------------
+--catch calls from addons which creates menu before saved variables are available (Rainbow Reticle)
+-- local MissedLamCalls = Promise()
+-- LibStub.libs["LibAddonMenu-1.0"] = setmetatable({}, { __index = MissedLamCalls })
+-- local LAM = LibStub:NewLibrary("LibAddonMenu-1.0", 999)
+-- function LAM:CreateControlPanel(controlPanelID, controlPanelName)
+--    local name = controlPanelName:gsub("|[cC]%w%w%w%w%w%w",""):gsub("|[rR]","")
+--
+--    if missedPanelIDs[name] ~= nil then
+--       return missedPanelIDs[name]
+--    end
+--
+--    lastID = lastID + 1
+--    missedPanelIDs[name] = lastID
+--
+--    MissedLamCalls:CreateControlPanel(controlPanelID, controlPanelName)
+--
+--    return lastID
+-- end

 --LAM 1.0 to 2.0 interface
 FAKE_LAM1 = setmetatable ({}, { __index = LAM1 })
@@ -101,13 +167,16 @@ function FAKE_LAM1:AddHeader(panelID, controlName, text)
    local controlTable = {
       type = "header",
       name = text,
-      reference = controlName,
+      reference = controlName .. "_LAddMin",
+      controlName = controlName,
    }
-
+
    local tab = type(panelID) == "table" and panelID or settingsTable[panelID - 1000].controls
    table.insert(tab, controlTable)

-   return tab[#tab]
+   _G[controlName] = Promise()
+
+   return _G[controlName]
 end
 -- LAM1:AddSlider(panelID, controlName, text, tooltip, minValue, maxValue, step, getFunc, setFunc, warning, warningText)
 function FAKE_LAM1:AddSlider(panelID, controlName, text, tooltip, minValue, maxValue, step, getFunc, setFunc, warning, warningText)
@@ -125,13 +194,16 @@ function FAKE_LAM1:AddSlider(panelID, controlName, text, tooltip, minValue, maxV
       getFunc = getFunc,
       setFunc = setFunc,
       warning = warningText,
-      reference = controlName,
+      reference = controlName .. "_LAddMin",
+      controlName = controlName,
    }

    local tab = type(panelID) == "table" and panelID or settingsTable[panelID - 1000].controls
    table.insert(tab, controlTable)

-   return tab[#tab]
+   _G[controlName] = Promise()
+
+   return _G[controlName]
 end
 -- LAM1:AddDropdown(panelID, controlName, text, tooltip, validChoices, getFunc, setFunc, warning, warningText)
 function FAKE_LAM1:AddDropdown(panelID, controlName, text, tooltip, validChoices, getFunc, setFunc, warning, warningText)
@@ -147,13 +219,16 @@ function FAKE_LAM1:AddDropdown(panelID, controlName, text, tooltip, validChoices
       getFunc = getFunc,
       setFunc = setFunc,
       warning = warningText,
-      reference = controlName,
+      reference = controlName .. "_LAddMin",
+      controlName = controlName,
    }

    local tab = type(panelID) == "table" and panelID or settingsTable[panelID - 1000].controls
    table.insert(tab, controlTable)

-   return tab[#tab]
+   _G[controlName] = Promise()
+
+   return _G[controlName]
 end
 -- LAM1:AddCheckbox(panelID, controlName, text, tooltip, getFunc, setFunc, warning, warningText)
 function FAKE_LAM1:AddCheckbox(panelID, controlName, text, tooltip, getFunc, setFunc, warning, warningText)
@@ -168,13 +243,16 @@ function FAKE_LAM1:AddCheckbox(panelID, controlName, text, tooltip, getFunc, set
       getFunc = getFunc,
       setFunc = setFunc,
       warning = warningText,
-      reference = controlName,
+      reference = controlName .. "_LAddMin",
+      controlName = controlName,
    }

    local tab = type(panelID) == "table" and panelID or settingsTable[panelID - 1000].controls
    table.insert(tab, controlTable)

-   return tab[#tab]
+   _G[controlName] = Promise()
+
+   return _G[controlName]
 end
 -- LAM1:AddColorPicker(panelID, controlName, text, tooltip, getFunc, setFunc, warning, warningText)
 function FAKE_LAM1:AddColorPicker(panelID, controlName, text, tooltip, getFunc, setFunc, warning, warningText)
@@ -189,13 +267,16 @@ function FAKE_LAM1:AddColorPicker(panelID, controlName, text, tooltip, getFunc,
       getFunc = getFunc,
       setFunc = setFunc,
       warning = warningText,
-      reference = controlName,
+      reference = controlName .. "_LAddMin",
+      controlName = controlName,
    }

    local tab = type(panelID) == "table" and panelID or settingsTable[panelID - 1000].controls
    table.insert(tab, controlTable)

-   return tab[#tab]
+   _G[controlName] = Promise()
+
+   return _G[controlName]
 end
 -- LAM1:AddEditBox(panelID, controlName, text, tooltip, isMultiLine, getFunc, setFunc, warning, warningText)
 function FAKE_LAM1:AddEditBox(panelID, controlName, text, tooltip, isMultiLine, getFunc, setFunc, warning, warningText)
@@ -211,13 +292,20 @@ function FAKE_LAM1:AddEditBox(panelID, controlName, text, tooltip, isMultiLine,
       setFunc = setFunc,
       isMultiline = isMultiLine,
       warning = warningText,
-      reference = controlName,
+      reference = controlName .. "_LAddMin",
+      controlName = controlName,
    }

    local tab = type(panelID) == "table" and panelID or settingsTable[panelID - 1000].controls
    table.insert(tab, controlTable)

-   return tab[#tab]
+   local missedCalls = Promise()
+   _G[controlName] = missedCalls
+   missedCalls.additionalObjects = {}
+   _G[controlName].edit = Promise()
+   table.insert(missedCalls.additionalObjects, { edit = _G[controlName].edit })
+
+   return _G[controlName]
 end
 -- LAM1:AddButton(panelID, controlName, text, tooltip, onClick, warning, warningText)
 function FAKE_LAM1:AddButton(panelID, controlName, text, tooltip, onClick, warning, warningText)
@@ -231,13 +319,16 @@ function FAKE_LAM1:AddButton(panelID, controlName, text, tooltip, onClick, warni
       tooltip = tooltip,
       func = onClick,
       warning = warningText,
-      reference = controlName,
+      reference = controlName .. "_LAddMin",
+      controlName = controlName,
    }

    local tab = type(panelID) == "table" and panelID or settingsTable[panelID - 1000].controls
    table.insert(tab, controlTable)

-   return tab[#tab]
+   _G[controlName] = Promise()
+
+   return _G[controlName]
 end
 -- LAM1:AddDescription(panelID, controlName, text, titleText)
 function FAKE_LAM1:AddDescription(panelID, controlName, text, titleText)
@@ -249,13 +340,16 @@ function FAKE_LAM1:AddDescription(panelID, controlName, text, titleText)
       type = "description",
       title = titleText,
       text = text,
-      reference = controlName,
+      reference = controlName .. "_LAddMin",
+      controlName = controlName,
    }

    local tab = type(panelID) == "table" and panelID or settingsTable[panelID - 1000].controls
    table.insert(tab, controlTable)

-   return tab[#tab]
+   _G[controlName] = Promise()
+
+   return _G[controlName]
 end
 -- LAM1:AddSubMenu(panelID, controlName, text, tooltip)
 function FAKE_LAM1:AddSubMenu(panelID, controlName, text, tooltip)
@@ -267,20 +361,47 @@ function FAKE_LAM1:AddSubMenu(panelID, controlName, text, tooltip)
       type = "submenu",
       name = text,
       tooltip = tooltip,
-      reference = controlName,
+      reference = controlName .. "_LAddMin",
+      controlName = controlName,
       controls = {},
    }
+
+   _G[controlName] = controlTable.controls

    local tab = type(panelID) == "table" and panelID or settingsTable[panelID - 1000].controls
    table.insert(tab, controlTable)

-   return tab[#tab].controls
+   return _G[controlName]
 end


 -------------------------------------------------------------------------------
 -- Local functions ------------------------------------------------------------
 -------------------------------------------------------------------------------
+local function DelayedCalls(panel)
+   local panelID = panelIDs[panel:GetName()]
+   if panelID then
+      for i,controlTable in ipairs(settingsTable[panelID - 1000].controls) do
+         local missedCalls = _G[controlTable.controlName]
+         _G[controlTable.controlName] = _G[controlTable.reference]
+
+         missedCalls(_G[controlTable.controlName])
+
+         for key, missedCall in pairs(missedCalls.additionalObjects) do
+            if key == "edit" then
+               _G[controlTable.controlName][key] = _G[controlTable.controlName].editbox
+               missedCall(_G[controlTable.controlName][key])
+            else
+               missedCall(_G[controlTable.controlName][key])
+            end
+         end
+
+         _G[controlTable.reference] = nil
+         missedCalls = nil
+      end
+   end
+end
+
 local function CreateSettingsMenu()
    local panel = {
       name = "L'AddonMinder",
@@ -327,6 +448,9 @@ local function OnAddonLoaded(code, addon)
    if addon ~= "LAddMin" then return end

    sv = ZO_SavedVars:NewAccountWide("LAddMin_SavedVariables", 1, "Addons", { enabled = {} })
+
+--    LibStub.libs["LibAddonMenu-1.0"] = FAKE_LAM1
+--    MissedLamCalls(FAKE_LAM1)

    CreateSettingsMenu()