Thread Tools Display Modes
06-14-12, 01:08 PM   #1
Haleth
This Space For Rent
 
Haleth's Avatar
Featured
Join Date: Sep 2008
Posts: 1,173
Strange behaviour with ColorPickerFrame

Hello.

I'm working on some options for my addon, Aurora, to let people toggle whether or not they want to use class colours, and if not, let them pick a custom colour.

As soon as ADDON_LOADED fires, the saved variables are copied into local ones (prefixed with 'old'). As soon as an option changes, the saved variable changes, but they are only copied back to the local vars when the user clicks 'Okay' on the GUI. If the user clicks 'Cancel', then the saved vars are replaced with the local vars which still contain the previous value.

This works for everything, except for the colour picker. As soon as the user selects a new colour, the saved var is updated as intended. However, despite not being coded to do so, the 'old' var is updated as well, so when the user clicks Cancel (on the GUI - the colour picker cancel works fine), the saved var is replaced with the same value as it already contained.

This is my code, I've highlighted the problematic part:

Code:
local F, C = unpack(Aurora)

-- these variables are loaded on init and updated only on gui.okay. Calling gui.cancel resets the saved vars to these
local oldAlpha, oldEnableFont, oldUseCustomColour, oldCustomColour

-- create frames/widgets

local gui = CreateFrame("Frame", "AuroraConfig", UIParent)
gui.name = "Aurora"
InterfaceOptions_AddCategory(gui)

local title = gui:CreateFontString(nil, "ARTWORK", "GameFontNormalLarge")
title:SetPoint("TOP", 0, -26)
title:SetText("Aurora v."..GetAddOnMetadata("Aurora", "Version"))

local credits = gui:CreateFontString(nil, "ARTWORK", "GameFontHighlight")
credits:SetText("Aurora by Freethinker @ Steamwheedle Cartel - EU / Haleth on wowinterface.com")
credits:SetPoint("TOP", 0, -300)

local fontBox = CreateFrame("CheckButton", "AuroraConfigEnableFont", gui, "InterfaceOptionsCheckButtonTemplate")
fontBox:SetPoint("TOPLEFT", 16, -80)

local fontBoxText = fontBox:CreateFontString(nil, "ARTWORK", "GameFontHighlight")
fontBoxText:SetPoint("LEFT", fontBox, "RIGHT", 1, 1)
fontBoxText:SetText("Replace default game fonts (requires UI reload)")

local reloadButton = CreateFrame("Button", "AuroraConfigReloadUI", gui, "UIPanelButtonTemplate")
reloadButton:SetPoint("LEFT", fontBoxText, "RIGHT", 20, 0)
reloadButton:SetSize(128, 25)
reloadButton:SetText("Reload UI")

local colourBox = CreateFrame("CheckButton", "AuroraConfigUseClassColours", gui, "InterfaceOptionsCheckButtonTemplate")
colourBox:SetPoint("TOPLEFT", 16, -120)

local colourBoxText = colourBox:CreateFontString(nil, "ARTWORK", "GameFontHighlight")
colourBoxText:SetPoint("LEFT", colourBox, "RIGHT", 1, 1)
colourBoxText:SetText("Use custom colour rather than class as highlight")

local colourButton = CreateFrame("Button", "AuroraConfigCustomColour", gui, "UIPanelButtonTemplate")
colourButton:SetPoint("LEFT", colourBoxText, "RIGHT", 20, 0)
colourButton:SetSize(128, 25)
colourButton:SetText("Change...")

local alphaSlider = CreateFrame("Slider", "AuroraConfigAlpha", gui, "OptionsSliderTemplate")
alphaSlider:SetPoint("TOPLEFT", 16, -200)
BlizzardOptionsPanel_Slider_Enable(alphaSlider)
alphaSlider:SetMinMaxValues(0, 1)
alphaSlider:SetValueStep(0.1)
AuroraConfigAlphaText:SetText("Alpha")

-- add event handlers

gui.refresh = function()
	alphaSlider:SetValue(oldAlpha)
	fontBox:SetChecked(oldEnableFont)
	colourBox:SetChecked(oldUseCustomColour)
	if not colourBox:GetChecked() then
		colourButton:Disable()
	end
end

gui:RegisterEvent("ADDON_LOADED")
gui:SetScript("OnEvent", function(self, _, addon)
	if addon ~= "Aurora" then return end

	oldAlpha = AuroraConfig.alpha
	oldEnableFont = AuroraConfig.enableFont
	oldUseCustomColour = AuroraConfig.useCustomColour
	oldCustomColour = AuroraConfig.customColour
	
	gui.refresh()
	
	F.Reskin(reloadButton)
	F.Reskin(colourButton)
	F.ReskinCheck(fontBox)
	F.ReskinCheck(colourBox)
	F.ReskinSlider(alphaSlider)
	
	self:UnregisterEvent("ADDON_LOADED")
end)

local function updateFrames()
	for i = 1, #C.frames do
		F.CreateBD(C.frames[i], AuroraConfig.alpha)
	end
end

gui.okay = function()
	oldAlpha = AuroraConfig.alpha
	oldEnableFont = AuroraConfig.enableFont
	oldUseCustomColour = AuroraConfig.useCustomColour
	oldCustomColour = AuroraConfig.customColour
end

gui.cancel = function()
	AuroraConfig.alpha = oldAlpha
	AuroraConfig.enableFont = oldEnableFont
	AuroraConfig.useCustomColour = oldUseCustomColour
	AuroraConfig.customColour = oldCustomColour
	
	updateFrames()
	gui.refresh()
end

gui.default = function()
	oldAlpha = C.defaults.alpha
	oldEnableFont = C.defaults.enableFont
	AuroraConfig.alpha = oldAlpha
	AuroraConfig.enableFont = oldEnableFont
	
	olduseCustomColour = C.defaults.useCustomColour
	oldCustomColour = C.defaults.customColour
	AuroraConfig.useCustomColour = olduseCustomColour
	AuroraConfig.customColour = oldCustomColour
	
	updateFrames()
	gui.refresh()
end

reloadButton:SetScript("OnClick", ReloadUI)

alphaSlider:SetScript("OnValueChanged", function(_, value)
	AuroraConfig.alpha = value
	updateFrames()
end)

fontBox:SetScript("OnClick", function(self)
	if self:GetChecked() then
		AuroraConfig.enableFont = true
	else
		AuroraConfig.enableFont = false
	end
end)

colourBox:SetScript("OnClick", function(self)
	if self:GetChecked() then
		AuroraConfig.useCustomColour = true
		colourButton:Enable()
	else
		AuroraConfig.useCustomColour = false
		colourButton:Disable()
	end
end)

local function setColour()
	local r, g, b = ColorPickerFrame:GetColorRGB()
	AuroraConfig.customColour.r, AuroraConfig.customColour.g, AuroraConfig.customColour.b = r, g, b
	-- why is this the same?
	print(AuroraConfig.customColour.r.." "..AuroraConfig.customColour.g.." "..AuroraConfig.customColour.b)
	print(oldCustomColour.r.." "..oldCustomColour.g.." "..oldCustomColour.b)
end

local function resetColour(restore)
	AuroraConfig.customColour.r, AuroraConfig.customColour.g, AuroraConfig.customColour.b = restore.r, restore.g, restore.b
end

colourButton:SetScript("OnClick", function()
	local r, g, b = AuroraConfig.customColour.r, AuroraConfig.customColour.g, AuroraConfig.customColour.b
	ColorPickerFrame:SetColorRGB(r, g, b)
	ColorPickerFrame.previousValues = {r = r, g = g, b = b}
	ColorPickerFrame.func = setColour
	ColorPickerFrame.cancelFunc = resetColour
	ColorPickerFrame:Hide()
	ColorPickerFrame:Show()
end)
I might've made an obvious oversight here, but I've been looking for about two hours now and I can't find it.

Any help would be appreciated.
  Reply With Quote
06-14-12, 02:07 PM   #2
Rilgamon
Premium Member
 
Rilgamon's Avatar
Premium Member
AddOn Author - Click to view addons
Join Date: Sep 2009
Posts: 822
When setting a table you copy only a reference. So if you change one you change both.
If you want it to be different copy it using CopyTable.
__________________
The cataclysm broke the world ... and the pandas could not fix it!
  Reply With Quote
06-14-12, 02:13 PM   #3
Haleth
This Space For Rent
 
Haleth's Avatar
Featured
Join Date: Sep 2008
Posts: 1,173
Oh. It took me 6 weeks of studying C programming and call by value/call by reference to remember that much of it. Wonderful.

Thanks for the quick reply.
  Reply With Quote

WoWInterface » Developer Discussions » Lua/XML Help » Strange behaviour with ColorPickerFrame


Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

vB code is On
Smilies are On
[IMG] code is On
HTML code is Off