Scripting HelpersARCHIVE
A little piece of Roblox history. Preserved for everyone, one question at a time.Read about the archive →
✓ ANSWER ACCEPTED

Is my Lua Table changing values on me?

I was working on a script to be able to call a module to create a Model (like a building or something) that is saved as a table in the Module.

local module = {}

function _Create(data) --Creates an object from a Table. Originally by Merely
	local obj
	if type(data[1]) == "string" then --first value in the table is always ClassName
		obj = Instance.new(data[1])
	else --Not ever used for my purposes (I believe)
		obj = data[1]
	end
	for k, v in pairs(data) do
		if k ~= 1 then --First Value is the ClassName
			if type(k) == "number" then --The Create functions don't have a named index
				v.Parent = obj --Whatever the function creates has a parent of obj
			else
				obj[k] = v --obj["Material"] = "Neon"
			end
		end
	end
	return obj
end

function module:Create(object) --What you can call the module with
	_Create(object)
end

module.Model1 = {"Model",
	Parent = game.Workspace,
	Name = "Model1",
		_Create({
			"Part",
			Name = "Brick1",
			Position = Vector3.new(0,0,0),
			Anchored = true,
			CanCollide = true,
			BottomSurface = "Smooth",
			TopSurface = "Smooth",
			BrickColor = BrickColor.new("Lime green"),
			Material = "Neon"}),
		
		_Create({
			"Part",
			Name = "Brick2",
			Anchored = true,
			CanCollide = true,
			BottomSurface = "Smooth",
			Position = Vector3.new(10,10,10),
			TopSurface = "Smooth",
			BrickColor = BrickColor.new("Earth green"),
			Material = "Neon"
			  })
}

return module

I then call it in a different test script with:

local Module = require(game:GetService("ServerScriptService").CreatorModule)

local M1 = Module:Create(Module.Model1)
wait(1)
local M2 = Module:Create(Module.Model1)
wait(1)
local M3 = Module:Create(Module.Model1)

What happens is, the script creates the first Model (a Model in the Workspace with two parts named Brick1 and Brick2 inside). Then it waits 1 second, then creates another Model, but without the parts inside it. Then waits and creates another model (correctly named), but without parts inside it again.

I believe the problem has something to do with this part of the script:

if type(k) == "number" then --The Create functions don't have a named index
	v.Parent = obj --Whatever the function creates has a parent of obj

Anything you can think of that might be the problem is greatly appreciated.

1 answer

✓ Accepted answer

The way this module is set up doesn't make any sense:

module:Create doesn't return any object.

That means the feature of creating children is wasted in _Create, since only the module definition can take advantage of it.

You should instead make it return a value. At the same time, you shouldn't construct children using _Create at all -- you should use the same table format that you're using, and let _Create take care of that.

There's no real reason at all to make module:Create and _Create be different.

That might look something like this:

function module:Create(description)
	local instance = Instance.new(description[1])
	for i = 2, #description do
		local child = module:Create(description[i])
		child.Parent = instance
	end
	for key, value in pairs(description) do
		if type(key) == "string" then
			instance[key] = value
		end
	end
	return instance
end

Using it would then look like this:

templateModel = {
	"Model";
	{ "Part";
		Name = "Brick1",
		Anchored = true,
		-- etc
	},
	{ "Part",
		Name = "Brick2",
		Anchored = true,
		-- etc
	},
	Name = "MyModel",
}

local m1 = module:Create(templateModel)
wait(1)
local m2 = module:Create(templateModel)
wait(2)
local m3 = module:Create(templateModel)

This template can be safely reused because nothing about it is actually used -- all information is copied.

2 comments

0

It makes me laugh that I stared at this code that was complex-looking to me and you rewrote the function and it's like reading normal English almost. One question though, if I had put a return value on "module:Create," would it have worked the same (just with unnecessary amounts of work)?

0

It would have made more sense to return from module:Create, but you still wouldn't have been able to make a template that has children -- because you'd refer to the same object that was returned, and what you really want is a new object (with the same properties) each time

This discussion is preserved as it was. New answers, comments, and votes are closed.