How to use module script?

Hi, I want to make a module script to store all the variables and then call them in a local script. One tiny problem though, I have no idea how to use module scripts. I started experimenting with them using the Roblox API but I am pretty sure this is not the way to go about it. Can someone help?

-- // Module in StarterGUI \\

local module = {}

function module.Storefunc(stagetrans,steps)
	if stagetrans.Text == "1" then
		steps.Text = "100"
	elseif stagetrans.Text == "2" then
		steps.Text = "125"
	elseif stagetrans.Text == "3" then
		steps.Text = "125"
	elseif stagetrans.Text == "4" then
		steps.Text = "25"
	elseif stagetrans.Text == "5" then
		steps.Text = "200"
	elseif stagetrans.Text == "6" then
		steps.Text = "250"
	elseif stagetrans.Text == "7" then
		steps.Text = "110"
	elseif stagetrans.Text == "8" then
		steps.Text = "75"
	elseif stagetrans.Text == "9" then
		steps.Text = "75"
	elseif stagetrans.Text == "10" then
		steps.Text = "75"
	elseif stagetrans.Text == "11" then
		steps.Text = "125"
	elseif stagetrans.Text == "12" then
		steps.Text = "450"
	elseif stagetrans.Text == "13" then
		steps.Text = "200"
	elseif stagetrans.Text == "14" then
		steps.Text = "150"
	elseif stagetrans.Text == "15" then
		steps.Text = "200"
	end
end

return module


-- // Local script in StarterGUI \\

local player = game.Players.LocalPlayer
local character = player.Character
local Humanoid = player.Character:WaitForChild("Humanoid")
local steps = player.PlayerGui.StepsGUI.Frame.TextLabel
local stagetrans = player.PlayerGui.StageTransfer.CurrentStage
local leaderstats = player.leaderstats.Stage
local mod = script.Parent.ModuleScript
local RunService = game:GetService("RunService")
print(steps.Text)

local info = require(mod,stagetrans,steps)
local info2 = info.Storefunc() --Get the module script values or something idk

stagetrans:GetPropertyChangedSignal("Text"):Connect(function()
--Store the variables in here (Like copy pasting the entire module script function
end)
2 Likes

You can find info about it here:

They are mainly used to Store Objects, Animations, functions, etc

A cool thing about them is that you can get access to them with an AssetId

require(12345) -- Random Number for Example

Example of a ModuleScript:

local module = {
TweenService = game:GetService("TweenService");
MaxSpawns = 10;
Animation = "rbxassetid//:1234567890";
}


return module -- returns the contents of the ModuleScript (or in this case, a table)

In most cases can be only fired once.

2 Likes

In the module, you have to return a value at the end of the script. This will be your module variable for your case. When you use require(modulescript), you run the script and get the return value.
(meant to reply to @Earthraphobic2)

The easiest way I can explain it is it essentially lets you reuse code which is pretty useful in programming. Personally, I exclusively use module scripts and I like having one for each behavior/system in my game as it’s easy to debug since I know where everything is being handled and if I need systems to interact with each other I can do that by requiring the module.

I have a pretty simple module that has some UI related functions

function UI:ChangeMenu(menuName : string)
	if typeof(menuName) ~= "string" then return end
	if CurrentMenu == menuName then return end
	if not (script:FindFirstChild(menuName)) then return end
	-- print("Changing Menu:",newMenu,"Previous Menu:",PreviousMenu)
	PreviousMenu = CurrentMenu
	CurrentMenu = menuName
	require(script[menuName])()
end

function UI:Transition(number)
	local Info = TweenInfo.new(1,Enum.EasingStyle.Quart,Enum.EasingDirection.Out,0,false,0)
	local Tween = TweenService:Create(ScreenGui.Transition,Info,{Transparency = number})

	Tween:Play()

	return Tween
end

function UI:GetCurrentMenu()
	return CurrentMenu
end

function UI:GetPreviousMenu()
	return PreviousMenu
end

Now in another module if I wanted to change the menu on a button press I can just require this module and call the ChangeMenu() function.

So in my case, would I put my if statements in the table and then return it?

Thank you, but I have one question,
image
At this, how can you use “:” key. Do module scripts have different behaivours and allow that?

1 Like

yes, but when you want to call them, you can do this in another script:

Example:

local Module = require(game.ReplicatedStorage.ModuleScript)


TextLabel.Text = Module.MaxSpawns

1 Like

But when I do that, it gives me an error:
image

Specify what stagetrans is inside the ModuleScript, otherwise it wont work

Oh, but in order for me to do that, I have to specify local player. Will it still work with that?

Specified, still gives error:
image

local module = {
Player = game.Players.LocalPlayer;
stagetrans = "Wherever stagetrans is";
}


return module

On another script:

local MS = require(game.replicatedStorage.ModuleScript)

if MS.stagetrans.Text = "1" then
-- rest of your script

If you were to write a function normally you wouldn’t be able to access it

local module = {}

local function MyFunction()
	print("Hello!")
end

return module

So this code below wouldn’t work

local module = require(path)
module:MyFunction() 

However, if you wrote the function like this the code above would work

local module = {}

function module:MyFunction()
	print("Hello!")
end

return module

Basically, all your doing is adding that function to the table which is what a module returns.

Edit: You could do a similar thing with variables

local module = {}

module.MyVariable = "Goodbye"

function module:MyFunction()
	print("Hello!")
end

return module
local module = require(path)

print(module.MyVariable)

Wait, then wouldn’t module script become useless then? If i want to store the if statements in the Module script then I would have to keep it in module script; then I can access it to my scripts when I need to keeping it cleaner and more organized.

I see, thanks! But would the function also work if you replaced the : with a . ?

Yes it would work, but it depends on what you need to do since using : and . gives different results which I actually don’t remember besides the fact it has something to do about passing itself as the first argument.

1 Like

Oh yeah, I think I saw a video explaining what : is but I didn’t really pay attention and forgot xD. But thanks for clarifying! Also why would there ever be a need to pass itself as the first arg?

Unfortunately, I’m not 100% sure, but it has its use cases which you’ll probably come across at some point.

1 Like

You would need to pass itself as the first argument in some cases where your working with custom objects where data tied to that object isn’t available in the modulescript itself, but the object created by the modulescript. It is also known as the self variable, commonly used in object oriented programming.

For example:

local DSS = game:GetService("DataStoreService")
local Datastor = DSS:GetDataStore()
print(DataStore:GetAsync())

see how it’s not DSS:GetAsync()? Because data in a datastore is only tied to the Datastor object made by DSS, and not actually in DSS itself. Which is also why DSS doesn’t have the datastore object functions to begin with.

If I’m to interject here, here’s a quick easy tutorial on ModuleScripts:


Think of ModuleScripts as libraries for Lua, or little Lego blocks that you can use in your code to easily refactor or reuse code without spending too much time.

For example, you can have a ModuleScript with two properties and functions (Foo, Bar, Fizz, Buzz), that you can use in your code easily:

-- modulescript @ game.ServerStorage.ModuleScript
local module = {}
module.foo = "Foo!"
module.bar = "Bar!"

-- THIS FUNCTION IS LOCAL! 
-- It can only be accessed by the ModuleScript, and is not returned in the Require()
local function modulator(m,n)
  return n % m == 0
end

function module:Fizz(n)
  -- using the local function
  if  modulator(n,3) then return "fizz" end
  return n
end

function module:Buzz(n)
  -- not using the local function
  if n % 5 == 0 then return "buzz" end
  return n
end

You can then reuse these functions in your other scripts in your game, calling the properties from the module.

-- Random Script
local exampleModule = require(game.ServerStorage.ModuleScript)

print(exampleModule.foo) -- Foo!
print(exampleModule.bar) -- Foo!

print(exampleModule:fizz(6)) -- fizz
print(exampleModule:fizz(5)) -- 5
print(exampleModule:fizz(5)) -- buzz

That way, by just changing the code in the ModuleScript, you can use the same reused code everywhere; you can require it in multiple scripts.

For real usage examples, I commonly use ModuleScripts for things like tool code, for example harvesting, raycasting, hitboxes, and such. They’re also commonly used as config files so you don’t have to dive into a bunch of code to change some variables.

Happy Scripting! Oh, and also, please reply if you need some other stuff about these to be explained.

4 Likes