Roblox scripting with Lua
Learning Roblox scripting with Lua is a lot of fun. Once you understand the basics you’ll be able to use these skills to build your creative ideas in Roblox.
This starter guide is for the absolute beginner that has never written any code. Understanding each of these topics will help you become a better programmer.
Let me know in the comments if there’s anything that’s confusing or needs more explanation.
Before we start, visit this online Lua interpreter to try out the examples.
Let’s get started!
How to create a script in Roblox
- Install Roblox Studio if it’s not already installed
- To download Roblox Studio, visit the Create section
- Click the green “Create New Experience” button
- Open Roblox Studio
- Start a new project by selecting a template or theme
- From the toolbox add a model to your scene such as a sword
- Move the sword to your workspace
- From the explorer, expand the sword to reveal its properties
- Double click the SwordScript
This is a quick way to get started with Roblox scripting. You can of course create your own object and add a script for it using the same steps.
Lua variables
Types and values
Lua is a dynamically-typed language. Dynamic typing means that a variable can store any type of data.
Types
- Text
- Numbers
- Boolean (true or false)
- Class
- Function
- Nil
Nil type
A variable uses the nil type when it should have no value. You might think this is zero but it’s not. The best way to think of nil is that the value does not exist.
Scopes
A scope determines how long a variable exists in memory while the script is running. You can have variables in a local or global scope. Scopes help organize your variables and help to control allocated memory.
Local scope
Variables with a local scope only exist until the function or script finishes. Once the script finishes, these variables get cleaned up by releasing the memory used. If this doesn’t happen then our programs will use up all the available memory and eventually crash your computer or device.
Example:
local a = 5
function multiplyByFive (num)
local multiplier = 5
return num * multiplier
end
local p = multiplyByFive(a)
In this example, the variable ‘a’ exists in memory until the script finishes. Within the function multiplyByFive(), the multiplier variable exists until the function finishes and does not exist outside of it.
Adding this to the end of the script would fail.
local product = a * multiplier
Global scope
Variables in a global scope exist until the entire program finishes. It is important to carefully use global variables since any other script can access them. Mis-using global variables may lead to confusing behavior in your script.
Example:
local a = 5
multiplier = 5
function multiplyByFive (num)
return num * multiplier
end
local p = multiplyByFive(a)
In this instance, the multiplier variable becomes a global by defining it without the local keyword.
Adding this to the end of the script executes just fine.
local product = a * multiplier
To avoid any confusing issues or bugs in your code, it’s always best to declare your variables with local. Use global scope sparingly.
Operators
Operators allow us to define code that changes a variable’s value.
Arithmetic Operators
There are mathematical operators for addition, subtraction, multiplication, and division.
Addition uses the + symbol.
Example: 1 + 1
Subtraction uses the – symbol.
Example: 2 – 1
Multiplication uses the * symbol.
Example: 2 * 1
Division uses the / symbol.
Example: 2 / 1
These mathematical operators only work with variables holding numeric values. You will get an error if it’s used with non-numeric values.
Example of code that will fail:
local x = 10
local y = "red25"
local z = x + y
print("Sum of x+y =",z)
To test if a variable equals another, you’ll use the == operator.
To test if a variable does NOT equal another, you’ll use the ~= operator.
To test if a variable is greater than another, you’ll use the > operator or >= operator.
To test if a variable is less than another, you’ll use the < operator or <= operator.
Logic Operators
Logic operators include the and keyword, such as when you want to test if two expressions are true.
Example:
local a = 5
local b = 100
local aGreaterThanZero = a > 0
local aLessThanB = a < b
local someNumberIsInRange = aGreaterThanZero and aLessThanB
This example shows that the someNumberIsInRange variable is true when a is greater than zero and less than 100.
The or operator is a bit similar to the and keyword except either expression can be true.
Code comments
Commenting your code is good for explaining the purpose of a block of code. To add a comment in Lua you can use — symbols. Lua will not execute anything within the comment.
Example:
-- this is a comment
You can add multiple line comments by starting with –[[ and closing your comments with –]]
Example:
--[[
This is
a multiple line comment block
--]]
Logic statements
Assigning values
You assign a value to a variable by using the = symbol.
You can also assign multiple variables in a single statement.
Example:
local someNumber, someWord = 5, "hello"
When using multiple variables, you must assign a value for each one.
local someNumber, someNil = 5, nil
Condition statements
An if-then-else
statement defines a condition for a block of code to execute.
Example:
local playerHasWeapon = player.weapon ~= nil
if playerHasWeapon then
player.weapon.shoot()
else
player.hand.punch()
end
Here we’re testing if a player has a weapon and then running its shoot() function, otherwise we execute the punch() function of the player’s hand.
Lua loops
Loops use the for and while language keywords. We use for loops to iterate or run a piece of code on a list. We use while loops to run a block of code until the while loop condition becomes false.
Example:
local gameIsRunning = true
while gameIsRunning do
local inputKey = inputHandler.run()
physicsEngine.run()
renderer.run()
if inputKey == “q” then
gameIsRunning = false
end
end
In this basic game loop, we run each step from our input handler (in this case a keyboard), the physics engine, and then the renderer. When the inputKey variable becomes “q” we stop the while loop and end the game.
local allGameObjects = []
for i, gameObject in allGameObjects do
print(gameObject.name)
end
In this for loop, we’re going through each game object in the allGameObjects list and printing its name.
When you need to stop your loop for any condition you can use the break or return keywords.
Example:
local allGameObjects = []
for i, gameObject in allGameObjects do
print(gameObject.name)
if gameObject.name == “Tandem Coder” then break end
end
end
Lua functions
Functions are great for organizing our code into logical pieces. Instead of putting everything into a single function, we can reuse code with simpler functions.
Example:
function render(gameObject)
gameObject.render()
end
function renderAllGameObjects(gameObjects)
for i,gameObject in gameObjects do
render(gameObject)
end
end
Working with strings
Lua has a string library or a set of functions used just for working with strings.
Functions
- string.lower(“ALL UPPERCASE”)
- Returns the input with all lowercase characters
- string.upper(“all lowercase”)
- Returns the input with all uppercase characters
- string.sub(input, startIndex, endIndex)
- Returns a sub string of input
- Example:
local s = “test”
local t = string.sub(s, 0, 2)
– returns “te”
- local startIndex, endIndex = string.find(input, sub string)
- Returns start and end position for sub string within the input string
Tables demystified
In Lua, tables are used for all data structures such as lists, queues, and sets.
To define a table, we use curly brackets such as {}.
Arrays
Arrays is a type of data structure for holding a list of data. Lua uses integers (a whole number) as the index of a table to hold an array value.
Example:
local someArray = {}
for i=1, 10 do
someArray[i] = 0
end
A script that creates an array filled with ten zeros.
The typical convention is to start arrays from index = 1, unlike other languages that start with 0. Starting with index = 1 allows us to use other lua libraries.
An example of creating a array in one line.
local anotherArray = {2, 5, 7, 9, 20, 55}
Linked lists
A linked list is an efficient data structure for lists when inserting or removing items in a list. In contrast, an array is more memory efficient since it does not need to hold a reference to an item’s value.
Example:
-- linked list root
local root = nil
root = { next = root, value = someValue }
-- add another value
root.next = { next = nil, value = anotherValue }
Object Oriented Programming with Lua
With Object-Oriented programming (OOP for short) we treat everything as an object that has its own functions and structure. With OOP we have literal types and object types. Literal types include actual numbers and strings while objects include additional functions.
Classes
For example you can have an Animal object that has functions for eating, walking, and sleeping. We can reuse the basic definition of Animal to then create a more specific object such as Cat or Dog. These object definitions are called classes.
Example:
Animal = { energy = 10 }
-- creates a new Animal object
function Animal:new (o)
o = o or {}
setmetatable(o, self)
self.__index = self
return o
end
function Animal:eat()
-- increase energy by 10
self.energy = self.energy + 10
end
local someAnimal = Animal:new()
someAnimal:eat()
print(someAnimal.energy) -- prints out 20
Cat = Animal:new() -- starts out with energy of 10
function Cat:eat()
self.energy = self.energy + 20 -- cat gets more energy when it eats
end
local someCat = Cat:new()
someCat:eat()
print(someCat.energy) -- prints 30
The self keyword that you see in these functions refers to the unique object that it’s being called with. These class definitions are a blueprint for your object and do not create an object. The new function is used to create an object with these functions and properties.
You can call the new function again to create more individual cats that have their own energy level.
Example:
local anotherCat = Cat:new()
local specialCat = Cat:new()
-- now we have 3 cats in our script
Types of Roblox scripts
Roblox scripting uses many types of scripts for different purposes.
- LocalScript is used for code that runs on the player’s device.
- PlayerScripts contain all LocalScripts to set up a player when they join the game.
- Script is a type of script that runs on Roblox servers.
- CoreScript is used within the Roblox system and can not be changed by a game or player.
- ModuleScript provides developers a way of reusing code.
Since Roblox is a multiplayer game, it’s important to have the server keep the game state consistent. Having the server do all the heavy lifting keeps your game secure and reduces the possibility of other player’s cheating.
There will be a separate Roblox scripting post that goes into more depth on Roblox client-server communication and which types of scripts to use.
Tips for learning Roblox scripting & Lua
There’s a lot to digest here and I hope you’ve learned a lot from this post!
As a Roblox scripting beginner, I would focus on simple and basic concepts to get a better grasp of how Lua works. I’d suggest creating a starter world in Roblox and create a script for a model that you like. You can learn a lot about how to manipulate that model’s properties such as its position and orientation. You can also try animating the model by changing its position within a loop.
Remember, always ask questions!
There will be more beginner level Roblox scripting examples coming soon!
Continue your Roblox scripting journey by learning the fundamentals of programming and learn how Roblox games work.
Want more?
Learn more about Roblox CFrames or how to make a Roblox Cutscene.
Please consider joining my email newsletter for more Roblox guides and updates!
Thank you for reading Tandem Coder, stay curious!.