Setting colors in Lua

So SetColorTexture (among others) uses values between 0-1 for each of the RGB values. eg: Druid orange is apparently SetColorTexture(1.0, 0.49, 0.04). I was under the impression that to get these values you take the hex RGB values and divide them by 255. So druids are effectively 255, 124, 10 which translates to #FF7C0A.

So, I’d have expected to be able to take a hex color like Charcoal Grey (#36454F) convert it to RGB (54, 69, 79) divide by 255 (0.21, 0.27, 0.31) and be able to use it in SetColorTexture and have a nice charcoal grey background texture.

However, when I do that it often produces a colour completely different from the original. Is this because of rounding errors? In the above charcoal grey example it’s actually more like (0.211764706, 0.270588235, 0.309803922) so I’ve rounded to two decimal places.

Is there some other “gotcha” that I haven’t seen in the API for SetColorTexture?

Define or better yet, show the original.

The colours look the same to me using #36454F (painting program) and Texture:SetVertexColor(54/255, 69/255, 79/255) (WoW)

WoW Screenshot:
https://imgur.com/tzgZmTb

Painting program:
https://imgur.com/jfPLc8j

Well here’s a simple one from another question I asked and you helped with. I attached a texture to my addon frame and set the colour to grey. That seems ok. I added another texture to a fontstring to give it a white background. Added another texture to a second fontstring that should have a green background.

MyAddonFS1:SetColorTexture(1.0,1.0,1.0); – Should be white
MyAddonFS2:SetColorTexture(0.67,0.83,0.45); – Hunter green

The green works, the white just doesn’t appear. It’s the same gray as the background. If I change it to;

MyAddonFS1:SetColorTexture(1.0,0.49,0.04); – Druid orange

That works and displays as orange. So I know I’m setting the colour properly but sometimes it doesn’t seem to apply the colour.

Here is the literal example we’ve been talking about in another thread; https://half-assed.net/images/colour_weirdness.jpg

The fontstring “Testing fontstring” literally has the code up above that should make it white yet it’s gray (or transparent).

Oof, just to add to the weirdness. I added a Close button to my addon and now the fontstring background texture shows up as white. If I cut out the button code the texture goes back to being grey (or transparent).

This makes my brain hurt.

edit: And just to make it even more painful. I pasted the code back in and the texture is grey (or transparent) again.

It’s imposible to tell without seeing the code but I’m guessing whatever widget your close button is hiding, it’s not the one you think it is.

Using the code from the other thread, a grey frame with randomly class coloured backgrounds to fontstrings/texture combinations with a close button and a show/hide slash command (/ca)

And a print of the class colors including hex.

local Units = {}
local topOnLine

local classes = {
	"DRUID",
	"HUNTER",
	"PRIEST",
}

for k, v in pairs(classes) do
	local color = C_ClassColor.GetClassColor(v)
	print(v, color.r, color.g, color.b, color:GenerateHexColor())
end

local function CreateUnit(parent, id)
	local f = parent:CreateTexture()
	Units[id] = f
	f:SetSize(75, 18)
	f:SetTexture("Interface/BUTTONS/WHITE8X8")
	local class = random(1, #classes)
	local color = C_ClassColor.GetClassColor(classes[class])
	f:SetVertexColor(color.r, color.g, color.b)
	f.Text = parent:CreateFontString()
	f.Text:SetFont("Fonts\\FRIZQT__.TTF", 16)
	f.Text:SetTextColor(54/255, 69/255, 79/255)
	f.Text:SetPoint("CENTER", f)
	if id == 1 then
		f:SetPoint("TOPLEFT", 5, -5)
		topOnLine = f
	elseif mod(id-1, 5) == 0 then
                f:SetPoint("LEFT", topOnLine, "RIGHT", 5, 0)
                topOnLine = f
	else
		f:SetPoint("TOP", Units[id-1], "BOTTOM", 0, -5)
	end
	f.Text:SetText("Raid"..id)
end

local f = CreateFrame("Frame", "CanackiAddonFrame", UIParent)
f:SetSize(560, 120)
f:SetPoint("TOPLEFT", 20, -20)
f.Texture = f:CreateTexture()
f.Texture:SetAllPoints()
f.Texture:SetTexture("Interface/BUTTONS/WHITE8X8")
--f.Texture:SetVertexColor(54/255, 69/255, 79/255)
f.Texture:SetBlendMode("DISABLE")
f.Texture:SetVertexColor(0.5, 0.5, 0.5)

f.Close = CreateFrame("Button", "$parentClose", f, "UIPanelButtonTemplate")
f.Close:SetSize(60, 25)
f.Close:SetText("Close")
f.Close:SetPoint("TOPRIGHT")
f.Close:SetScript("OnClick", function(self)
	self:GetParent():Hide()
end)

for i=1, 25 do -- add 25 "units"
	CreateUnit(CanackiAddonFrame, i)
end

Units[25].Text:SetText("Last Unit") -- change the name of the last unit
CreateUnit(CanackiAddonFrame, #Units + 1)
Units[#Units].Text:SetText("No I am") -- change the name of the last unit

_G["SLASH_CanackiAddon1"] = "/ca"
SlashCmdList.CanackiAddon = function(msg)
	CanackiAddonFrame:SetShown(not CanackiAddonFrame:IsShown())
end

In that screenshot above where it says “Testing fontstring” that is MyAddonFS1.

When I say adding a close button changed the background colour of MyAddonFS1 I mean literally just by adding a button, not the onclick event. But that only seemed to affect the colour once, and now it’s no longer affecting the colour.

Similarly, I can change JUST the one entry:

MyAddonFS1:SetColorTexture(1.0,1.0,1.0);

to

MyAddonFS1:SetColorTexture(1.0,0.49,0.04);

And the expected colour (orange) appears where it’s supposed to (around the words “Testing fontstring”). But change it back to

MyAddonFS1:SetColorTexture(1.0,1.0,1.0);

And the colour is either set to the same gray as the background or it’s rendered transparently.

It’s blowing my mind because there’s no doubt it’s the right object that I’m working on (otherwise setting it to orange wouldn’t work). But white just refuses to work, and several shades of grey created weird colours too.

I’ve looked up the colour codes (https://wowpedia.fandom.com/wiki/Class_colors) before I even asked this question because I was sure I was doing it right. I thought maybe with the button there was a naming collision so the fontstring was getting assigned the colour that way, but I’ve double checked and it’s definitely not.

I thought widget names (in the code block you did post) with the suffix of …FSn where n is the number were FontStrings and not the background textures, but once again, the full code might help determining where the problem(s) are.

If you haven’t yet, install:
https://www.curseforge.com/wow/addons/bugsack

and:
https://www.curseforge.com/wow/addons/bug-grabber

to makie detecting/finding errors easier.

I must admit I half-assed the names because this is just me trying to get the addon doing what I want it to. My intention was once I get my head around the weird quirks I’d start clean and use better naming conventions. I should have named them texMyAddon1 or MyAddonTex1.

Already running bugsack and buggrabber. There are no errors with either scenario (using white or orange). And I haven’t got as far as adding error-handling to the test addon so it’s not like there is something getting caught there either.

Names can matter depending on scope, all addons share the same global table including the entire Blizzard UI so you want to avoid clashes there and use unique global variable/frame names.

Outside of that, there’s nothing else I can do to help being completely blind as to what you are actually doing.

Good luck and have fun.

I have literally culled everything but the problem areas and hopefully clearer names. And I’m still having the same problem (white just flat out refuses to work).

This is literally the entire LUA file
local CarnackiTestAddon = CreateFrame(“Frame”, nil, UIParent);
local CarnackiTestAddonTexBG = CarnackiTestAddon:CreateTexture();
local CarnackiTestAddonTexTitle = CarnackiTestAddon:CreateTexture();
local CarnackiTestAddonTexDetails = CarnackiTestAddon:CreateTexture();

CarnackiTestAddon:SetFrameStrata("MEDIUM");
CarnackiTestAddon:SetWidth(300);
CarnackiTestAddon:SetHeight(300);
CarnackiTestAddon:SetPoint("CENTER");
CarnackiTestAddon:SetMovable(true);
CarnackiTestAddon:EnableMouse(true);

-- Main window background
CarnackiTestAddon.texture = CarnackiTestAddonTexBG
CarnackiTestAddonTexBG:SetAllPoints();
CarnackiTestAddonTexBG:SetColorTexture(0.21,0.27,0.31);
CarnackiTestAddonTexBG:SetAlpha(1.0);

-- Title background
CarnackiTestAddon.texture = CarnackiTestAddonTexTitle
CarnackiTestAddonTexTitle:SetAllPoints();
CarnackiTestAddonTexTitle:SetColorTexture(1,1,0.5);
CarnackiTestAddonTexTitle:SetAlpha(1.0);

-- Create the title fontstring
CarnackiTestAddon.font = CarnackiTestAddonFSTitle
CarnackiTestAddonFSTitle = CarnackiTestAddon:CreateFontString();
CarnackiTestAddonFSTitle:SetFont("Fonts\\FRIZQT__.TTF", 24);
CarnackiTestAddonFSTitle:SetPoint("TOP", 0 , -10);
CarnackiTestAddonFSTitle:SetTextColor(0,0,0);
CarnackiTestAddonFSTitle:SetText("TEST");
CarnackiTestAddonTexTitle:SetAllPoints(CarnackiTestAddonFSTitle);

-- Add details background
CarnackiTestAddon.texture = CarnackiTestAddonTexDetails
CarnackiTestAddonTexDetails:SetAllPoints();
CarnackiTestAddonTexDetails:SetColorTexture(1.0,1.0,1.0);
--CarnackiTestAddonTexDetails:SetColorTexture(1.0,0.49,0.04);
CarnackiTestAddonTexDetails:SetAlpha(1.0);

-- Create the details fontstring
CarnackiTestAddon.font = CarnackiTestAddonFSDetails
CarnackiTestAddonFSDetails = CarnackiTestAddon:CreateFontString();
CarnackiTestAddonFSDetails:SetFont("Fonts\\FRIZQT__.TTF", 16);
CarnackiTestAddonFSDetails:SetPoint("TOP", 0 , -40);
CarnackiTestAddonFSDetails:SetTextColor(0,0,0);
CarnackiTestAddonFSDetails:SetText("Testing fontstring");
CarnackiTestAddonTexDetails:SetAllPoints(CarnackiTestAddonFSDetails);

-- Display the addon
CarnackiTestAddon:Show()

This is literally the entire TOC

## Title: Test
## Notes: Testing weird texture colour behaviour
## Version: 1.0
## Author: Carnacki
## Interface: 90105

test.lua

The texture colour in the details background works perfectly if I change it to orange (the commented line) but not when it’s white. I can’t imagine any of the current addons have globals that match the names used in my test file.

I’m using Notepad++ for the coding so I can select a variable and it instantly highlights everywhere in the lua where it’s used. And it all looks good to me.

The details fontstring and texture were on the same default drawlayer as the background texture so the white was being blended in and lost. I’ve moved them to the ARTWORK layer and 1, 2 sub-levels (see the layer link in the SetBlendMode page linked below to get a better understanding of frame stratas and layeredregion draw layers).

I’ve commented out some uneeded lines and the last CarnackiTestAddon:Show() isn’t required as frames are shown by default.

local CarnackiTestAddon = CreateFrame("Frame", nil, UIParent);
local CarnackiTestAddonTexBG = CarnackiTestAddon:CreateTexture();
local CarnackiTestAddonTexTitle = CarnackiTestAddon:CreateTexture();
local CarnackiTestAddonTexDetails = CarnackiTestAddon:CreateTexture();

CarnackiTestAddon:SetFrameStrata("MEDIUM");
CarnackiTestAddon:SetWidth(300);
CarnackiTestAddon:SetHeight(300);
CarnackiTestAddon:SetPoint("CENTER");
CarnackiTestAddon:SetMovable(true);
CarnackiTestAddon:EnableMouse(true);

-- Main window background
--CarnackiTestAddon.texture = CarnackiTestAddonTexBG
CarnackiTestAddonTexBG:SetAllPoints();
CarnackiTestAddonTexBG:SetColorTexture(0.21,0.27,0.31);
CarnackiTestAddonTexBG:SetAlpha(1.0);

-- Title background
--CarnackiTestAddon.texture = CarnackiTestAddonTexTitle
CarnackiTestAddonTexTitle:SetAllPoints();
CarnackiTestAddonTexTitle:SetColorTexture(1,1,0.5);
CarnackiTestAddonTexTitle:SetAlpha(1.0);

-- Create the title fontstring
--CarnackiTestAddon.font = CarnackiTestAddonFSTitle
CarnackiTestAddonFSTitle = CarnackiTestAddon:CreateFontString();
CarnackiTestAddonFSTitle:SetFont("Fonts\\FRIZQT__.TTF", 24);
CarnackiTestAddonFSTitle:SetPoint("TOP", 0 , -10);
CarnackiTestAddonFSTitle:SetTextColor(0,0,0);
CarnackiTestAddonFSTitle:SetText("TEST");
CarnackiTestAddonTexTitle:SetAllPoints(CarnackiTestAddonFSTitle);

-- Add details background
--CarnackiTestAddon.texture = CarnackiTestAddonTexDetails
--CarnackiTestAddonTexDetails:SetAllPoints();
CarnackiTestAddonTexDetails:SetDrawLayer("ARTWORK", 1)
CarnackiTestAddonTexDetails:SetColorTexture(1.0,1.0,1.0);
--CarnackiTestAddonTexDetails:SetColorTexture(1.0,0.49,0.04);
CarnackiTestAddonTexDetails:SetAlpha(1.0);

-- Create the details fontstring
--CarnackiTestAddon.font = CarnackiTestAddonFSDetails
CarnackiTestAddonFSDetails = CarnackiTestAddon:CreateFontString();
CarnackiTestAddonFSDetails:SetFont("Fonts\\FRIZQT__.TTF", 16);
CarnackiTestAddonFSDetails:SetDrawLayer("ARTWORK", 2)
CarnackiTestAddonFSDetails:SetPoint("TOP", 0 , -40);
CarnackiTestAddonFSDetails:SetTextColor(0,0,0);
CarnackiTestAddonFSDetails:SetText("Testing fontstring");
CarnackiTestAddonTexDetails:SetAllPoints(CarnackiTestAddonFSDetails);
1 Like

You’re a genius. Thanks so much. I’d have never realized the drawlayer was the problem.

So I’m guessing the orange is a strong enough colour that even though it was blending it still looked orange. That would also explain why some of the greys I tested looked weird - they were being blended and wound up unusual colours.

So a couple more questions about the code.

  1. On the details background texture you’ve set the layer to 1 and on the details fontstring you’ve set it to 2. I assume based on that the higher values are “above” the lower ones. So if you draw two textures the one with the higher number will overlap the one with the lower?

  2. I noticed that you commented out the SetAllPoints for the Details texture but not the Title texture. Is there a reason you didn’t remove the SetAllPoints from the Title texture as well?

Thanks again. You’ve been amazingly helpful.

The commented out SetAllPoints was because you later did the same ac tion with the associated FontStrring as the anchor region, (the last line before where you had the CarnackiTestAddon:Show()).

The SetAlpha calls also aren’t required as 1 it the default for those but I assumed you were using those to try and fix the problem.

While it’s ok with consecutive SetAllPoints, the SetPoint() method is addative without first using ClearAllPoints() (Each SetPoint will move a point without resetting any others you have anchored)

Frames use stratas/levels do define where they sit in the stack in relation to other frames and layered regions use drawlayer/sub-levels to set where they sit in relation to other regions attached to a frame. The image on the following page link shows it pretty well. It’s not so different to a drawing program.

There is also a SetBlendMode method so it can all get complicated or configurable depending on your outlook :slight_smile:

The notes explain the all blend methods might not be available these days but…?

1 Like

I’m not sure. Even I’m still trying to blend in these days. :smirk: