Checking if variable has changed

I am creating a module that handles settings for games. I am adding signals to it using the Signals module that fire whenever a setting is changed.

However, it’s not working. Not the signal, but detecting if the setting has changed.

local function heartbeat()
	for name, setting in pairs(settingsModule.Settings) do
		local oldSetting = oldSettings[name]
		
		if oldSetting then
			if oldSetting.Value ~= setting.Value then
				settingsModule.SettingChanged:Fire(setting)
				setting.Changed:Fire(setting.Value)
			end
		else
			settingsModule.SettingAdded:Fire(setting)
		end
	end
	
	oldSettings = settingsModule.Settings
end

runService.Heartbeat:Connect(heartbeat)

This is what I have for it right now. Unfortunately, the signal doesn’t fire, and if I add a print, it won’t do that either.

I thought it might be oldSettings = settingsModule.Settings, so I made it individually set each setting, but that didn’t work either.

I’m thinking the oldSettings variable could just be referencing the settingsModule.Settings table so it’s always the same, but I don’t know how I can get around that.

Any thoughts?

(Don’t be fooled by the Value “property”! The settings are not objects, they are tables!)

is setting a value in workspace? if so then you could use setting.Changed and connect a function to fire everytime that happens

1 Like

They are not objects. I would rather not resort to using objects to accomplish this. I’m sure what I’m trying to do is possible but I’m not sure how.

2 Likes

First of all the Signal module you use is unlisted and none of the devs ik seems to use it (not saying that you shouldn’t but these are top devs), a better pick would be stravants GoodSignal which afaik is the industry standard as it has already been benchmarked and is already proved to be superior to the competition.

1 Like

The problem is not the Signal module. I’m attempting to detect when a variable within a table, or a “setting”, has changed.

1 Like

Yep, here’s the stats to back it up: Lua Signal Class Comparison & Optimal `GoodSignal` Class
GoodSignal is the industry standard as you say.
Your code looks good and should work as intended from what I can see.
Try disconnecting it from the RS loop, and instead run it every X seconds. Print out the oldSettings and the currentSettings → are they what you expect?

1 Like

Value is always the same when I print them both out. I think this is because I’m changing oldSettings to reference settingsModule.Settings- and not actually changing oldSettings to the value of settingsModule.Settings. How can I work around this?

New code if it's useful
local function changedLoop()
	while task.wait(0.1) do
		print(oldSettings)
		print(settingsModule.Settings)
		
		for name, setting in pairs(settingsModule.Settings) do
			local oldSetting = oldSettings[name]

			if oldSetting then
				if oldSetting.Value ~= setting.Value then
					settingsModule.SettingChanged:Fire(setting)
					setting.Changed:Fire(setting.Value)
				end
			else
				settingsModule.SettingAdded:Fire(setting)
			end
		end

		oldSettings = settingsModule.Settings
	end
end

task.spawn(changedLoop)

I’m not sure how your module looks, but for barebone explaining and suggesting it should do:

local module = {}
module.Settings = {
	VFX = false
}

function module:getSettingsMetatable()
	return setmetatable({}, {__newindex = function(t, index, value)
		print(self.Settings)
		self.Settings[index] = value
		print(self.Settings)
	end})
end

return module
------Running
local Settings = require(game.ReplicatedStorage.ModuleScript)
local SettingsMeta = Settings:getSettingsMetatable()
SettingsMeta["VFX"] = true
----- Output
{
   ["VFX"] = false
}  -  Client - ModuleScript:7

{
   ["VFX"] = true
}  -  Client - ModuleScript:9

__newindex metamethod looks like the best option to me. Hope this will help you out!

I have solved this problem using a more advanced table.clone() function. Turns out I was referencing the new Settings table.

This topic was automatically closed 14 days after the last reply. New replies are no longer allowed.