WoWInterface

WoWInterface (http://www.wowinterface.com/forums/index.php)
-   Lua/XML Help (http://www.wowinterface.com/forums/forumdisplay.php?f=16)
-   -   SavedVariablesPerCharacter (http://www.wowinterface.com/forums/showthread.php?t=45410)

Benalish 12-09-12 11:41 AM

SavedVariablesPerCharacter
 
I was able to successfully create the file to save the variables of my addon.

Code:

## SavedVariablesPerCharacter: MyAddon_Settings
But if I want call these variables every time I load the addon, what should I do?

Tim 12-09-12 11:57 AM

This should help you.
http://www.wowpedia.org/Saving_varia..._game_sessions

Phanx 12-09-12 10:56 PM

I cleaned up that wiki page some to remove some really outdated information, so it should be relevant again now. If you read it before now, I'd suggest going back to re-read it, and then removing any references to the VARIABLES_LOADED event from your addon (use ADDON_LOADED where arg1 is the folder name of your addon instead) and probably removing PLAYER_LOGOUT (it's completely unnecessary for the vast majority of addons).

Also, if you want to use a table to hold multiple variables, here is a simple function you can use to initialize your default values. It works no matter how many levels of sub-tables are in your defaults.

Code:

-- Define your default table:
local MyDefaults = {
        enable = true,
        showTheThing = false,
        x = 47,
        foo = "bar",
        t = {
                [12] = "twelve",
                [68] = true,
                cats = "meow",
        }
}

-- This function will make sure your saved table contains all the same
-- keys as your table, and that each key's value is of the same type
-- as the value of the same key in the default table.
local function CopyDefaults(src, dst)
        if type(src) ~= "table" then return {} end
        if type(dst) ~= "table" then dst = {} end
        for k, v in pairs(src) do
                if type(v) == "table" then
                        dst[k] = CopyDefaults(v, dst[k])
                elseif type(v) ~= type(dst[k]) then
                        dst[k] = v
                end
        end
        return dst
end

local addon = CreateFrame("Frame", "MyAddon")
addon:RegisterEvent("ADDON_LOADED")
addon:SetScript("OnEvent", function(self, event, arg1)
        if event == "ADDON_LOADED" and arg1 == "MyAddon" then
                -- Call the function to update your saved table:
                MyAddonSavedVariables = CopyDefaults(MyDefaults, MyAddonSavedVariables)
                -- Unregister this event, since there is no further use for it:
                self:UnregisterEvent("ADDON_LOADED")
        end
end)


Benalish 12-10-12 06:43 PM

MyAddonSavedVariables is the file specified in line ## SavedVariablesPerCharacter:?

SDPhantom 12-10-12 07:26 PM

There is no control over the actual file it writes to or where it's located, just what global variables WoW stores in it. To shorten Phanx's explanation, the SavedVariablesPerCharacter directive just tells WoW what globals to save for your addon. These globals will be available when ADDON_LOADED fires for your addon.

Benalish 12-10-12 10:39 PM

Code:

local addon = CreateFrame("Frame", "MyAddon")
addon:RegisterEvent("ADDON_LOADED")
addon:SetScript("OnEvent", function(self, event, arg1)
        if event == "ADDON_LOADED" and arg1 == "MyAddon" then
                -- Call the function to update your saved table:
                MyAddonSavedVariables = CopyDefaults(MyDefaults, MyAddonSavedVariables)
                print(MyAddonSavedVariables)
                -- Unregister this event, since there is no further use for it:
                self:UnregisterEvent("ADDON_LOADED")
        end
end)

This code print the valor (?) of MyAddonSavedVariables. But if I write the print function outside this, the code doesn't work

Code:

local addon = CreateFrame("Frame", "MyAddon")
addon:RegisterEvent("ADDON_LOADED")
addon:SetScript("OnEvent", function(self, event, arg1)
        if event == "ADDON_LOADED" and arg1 == "MyAddon" then
                -- Call the function to update your saved table:
                MyAddonSavedVariables = CopyDefaults(MyDefaults, MyAddonSavedVariables)
                -- Unregister this event, since there is no further use for it:
                self:UnregisterEvent("ADDON_LOADED")
        end
end)

print(MyAddonSavedVariables)


Phanx 12-10-12 10:39 PM

Quote:

Originally Posted by Benalish (Post 270522)
MyAddonSavedVariables is the file specified in line ## SavedVariablesPerCharacter:?

Yes, though "MyAddonSavedVariables" is a variable name, not a file name, and you can specify it in either the SavedVariables field or the SavedVariablesPerCharacter field, depending on whether you want all of the user's characters to share a single copy of the variable (so changes made on one character would apply to all characters) or each have their own copy (so changes made on one would not affect any others).

SDPhantom 12-11-12 01:49 PM

Quote:

Originally Posted by Benalish (Post 270542)
... if I write the print function outside this, the code doesn't work

Code:

local addon = CreateFrame("Frame", "MyAddon")
addon:RegisterEvent("ADDON_LOADED")
addon:SetScript("OnEvent", function(self, event, arg1)
        if event == "ADDON_LOADED" and arg1 == "MyAddon" then
                -- Call the function to update your saved table:
                MyAddonSavedVariables = CopyDefaults(MyDefaults, MyAddonSavedVariables)
                -- Unregister this event, since there is no further use for it:
                self:UnregisterEvent("ADDON_LOADED")
        end
end)

print(MyAddonSavedVariables)


This is because the script you registered in addon:SetScript() hasn't run yet. Look at the function there as a callback. It only runs when the frame receives any event that is registered to it. Since it's running the callback function when ADDON_LOADED fires, it's running long after your print() call. Try loading your addon, then typing /dump MyAddonSavedVariables into chat.

Phanx 12-11-12 09:33 PM

Code outside of a function runs immediately when WoW reads your file.

Code inside of a function does not run until that function is called. In your example, the code inside the function you set as your frame's OnEvent script does not run until the game fires the ADDON_LOADED event with your addon's name as the first argument. That happens after all of your addon's files and saved variables have been read.

gmarco 12-12-12 06:33 AM

Quote:

Originally Posted by SDPhantom (Post 270528)
These globals will be available when ADDON_LOADED fires for your addon.

Is the use of:

PLAYER_LOGIN

similar ?

So I can save to check with ADDON_LOADED the arg1 ...

gmarco 12-12-12 06:38 AM

I did something like this to check if the addon db was in an old format and eventually convert.

Lua Code:
  1. frame_cleu:RegisterEvent("ZONE_CHANGED_NEW_AREA")
  2. frame_cleu:RegisterEvent("PLAYER_ENTERING_WORLD")
  3. frame_cleu:RegisterEvent("PLAYER_LOGIN")
  4.  
  5. frame_cleu:SetScript("OnEvent", function(self, event, ...)
  6.  
  7.     if event == "PLAYER_LOGIN" then    
  8.        
  9.         if RemGankCFG["newdbver"] == nil then RemGank_DB_Convert() end
  10.        
  11.         if RemGankCFG["enabled"] == true then
  12.             print(string_format("%s: enabled", prgname))
  13.         else
  14.             print(string_format("%s: disabled. Type /remgank enable to start", prgname))           
  15.         end
  16.        
  17.     end
  18.  
  19.     if event == "ZONE_CHANGED_NEW_AREA" or event == "PLAYER_ENTERING_WORLD" then   
  20.  
  21.               -- blabla

SDPhantom 12-12-12 03:01 PM

Quote:

Originally Posted by gmarco (Post 270599)
Is the use of:

PLAYER_LOGIN

similar ?

So I can save to check with ADDON_LOADED the arg1 ...

It's not recommended to use PLAYER_LOGIN in replacement of ADDON_LOADED. For major reasons, PLAYER_LOGIN is not guaranteed to fire in all circumstances. Firing at inappropriate times or not at all is a side effect of picking a wrong and irrelevant event to register.

The purpose of PLAYER_LOGIN is to tell addons that all unit-specific data for the player is now available, like UnitName(). This fires only once and might not fire when the UI is reloaded. If an addon is LoD, it may never see this event at all.

ADDON_LOADED is specifically meant for this procedure. It signals the entire environment that an addon has finished loading and all global API and saved data provided by said addon is now available.

gmarco 12-12-12 04:55 PM

Understood :-)


All times are GMT -6. The time now is 10:48 AM.

vBulletin © 2017, Jelsoft Enterprises Ltd
© 2004 - 2017 MMOUI