CanvasGroups - Instantly Change Transparency of Multiple UI Objects!

About

I just created my first public module, and I find it kind of useful. It’s not a very complicated module, but it can really change your UIs.

How To Use

To insert a CanvasGroup into an object, use Module:Create().
This function takes 3 arguments: (Object, transparency, bool)
The object is where you would like to place the CanvasGroup. I recommend doing this in your main frame. The bool is used for Strokes. Personally I don’t want there to be a TextStroke on my object, so I’ll write false. I can of course change the transparency at all times, using tweens or just changing the value.

Examples:

Tweening

local CanvasGroup = Module:Create(script.Parent.Frame)
local TS = game:GetService("TweenService")
local TI = TweenInfo.new(4)

local Tween = TS:Create(CanvasGroup, TI, {Value = 0.5})
Tween:Play()

Changing the Value

local CanvasGroup = Module:Create(script.Parent.Frame)

CanvasGroup.Value = 0.5

https://gyazo.com/54387c3b3bbcb76a05bbac6a811dd92e (Example)

API

Module:Create(object parent, float transparency, bool doStrokes)

Get It

Id: 7719600381
Link: CanvasGroup Module - Roblox

Feel free to request any changes :slight_smile:

14 Likes

This is a godsend, I have always wished Roblox would add a feature that allows descendants to inherit the transparency of their parent. Was going to implement it myself but you saved me, thanks :slight_smile:

2 Likes

Thank you for the feedback! I did some digging, and found out that Roblox actually added a CanvasGroup object in Release 494 (Added Class CanvasGroup : GuiObject). It’s not actually working yet though.

3 Likes

Came across this, and despite it being over 2 years old and there now being an Instance for this (albeit still in Beta), I’m here with some modifications to accommodate for pre-existing Transparency.

Updated Source
local module = {}

local function calculateTransparency(orig, factor)
	return orig + (1 - orig) * factor
end

local function set(inst: Instance, prop: string, factor: number)
	inst[prop] = calculateTransparency(inst:GetAttribute(`CG_{prop}`), factor)
end

local function fixDescendants(canvasGroup, bool)
	local doStrokes = false
	
	if bool then
		doStrokes = true
	end
	
	set(canvasGroup.Parent, 'BackgroundTransparency', canvasGroup.Value)

	for canvas, descendant in pairs(canvasGroup.Parent:GetDescendants()) do
		if descendant:IsA("GuiObject") then
			set(descendant, 'BackgroundTransparency', canvasGroup.Value)
			
			if descendant:IsA("TextLabel") or descendant:IsA("TextButton") or descendant:IsA("TextBox") then
				set(descendant, 'TextTransparency', canvasGroup.Value)
				if doStrokes then
					set(descendant, 'TextStrokeTransparency', canvasGroup.Value)
				end
				
			elseif descendant:IsA("ImageButton") or descendant:IsA("ImageLabel") then
				set(descendant, 'ImageTransparency', canvasGroup.Value)
			end
		end
	end
	
	return nil
	
	--[[
	
	Test Cases:
	[
    	[ 1, 0.5, 1 ],
    	[ 0, 0.5, 0.5 ],
    	[ 0.5, 0.5, 0.75 ],
    	[ 1, 0, 1 ],
    	[ 0, 0, 0 ],
    	[ 0.5, 0, 0.5 ],
    	[ 1, 1, 1 ],
    	[ 0, 1, 1 ],
    	[ 0.5, 1, 1 ],
    	[ 1, 0.25, 1 ],
    	[ 0, 0.25, 0.25 ],
    	[ 0.5, 0.25, 0.625],
	]
	
	]]
end


function module:Create(parent, value, bool)
	local numberVal = Instance.new("NumberValue")
	
	local key = "CanvasGroup"
	numberVal.Name = key
	numberVal.Value = value
	numberVal.Parent = parent
		
	numberVal.Parent:SetAttribute("CG_BackgroundTransparency", numberVal.Parent.BackgroundTransparency)
	for _, descendant in ipairs(numberVal.Parent:GetDescendants()) do
		if descendant:IsA("GuiObject") then
			descendant:SetAttribute("CG_BackgroundTransparency", descendant.BackgroundTransparency)
			if descendant:IsA("TextLabel") or descendant:IsA("TextButton") or descendant:IsA("TextBox") then
				descendant:SetAttribute("CG_TextTransparency", descendant.TextTransparency)
				descendant:SetAttribute("CG_TextStrokeTransparency", descendant.TextStrokeTransparency)
			elseif descendant:IsA("ImageButton") or descendant:IsA("ImageLabel") then
				descendant:SetAttribute("CG_ImageTransparency", descendant.ImageTransparency)
			end
		end
	end
	
	numberVal:GetPropertyChangedSignal("Value"):Connect(function()
		fixDescendants(numberVal, bool)
	end)
	
	numberVal.Parent.ChildAdded:Connect(function()
		fixDescendants(numberVal, bool)
	end)
	
	fixDescendants(numberVal, bool)
	
	return numberVal
end

return module
2 Likes

I still rather use this instead of Roblox’s CanvasGroup object since it’s performance is really bad