Tutorial · Scripting foundations

How to script in Roblox Studio: a beginner's guide

Scripting, or coding, in Roblox Studio means writing Luau, Roblox's version of the Lua language, in scripts that you add to your place. This guide starts from an empty Baseplate: you open the Output window, write a first script, change a part from code, react to a player stepping on a pad and try a LocalScript, learning variables, functions, if statements, loops and events on the way.

Updated 15 October 202621 min readBeginnerLuau

In short

To script in Roblox Studio, hover over ServerScriptService in the Explorer, click + and insert a Script. Studio opens it in the Script Editor. Type Luau, such as print("Hello"), press Play (F5) and read the result in the Output window (Window menu or Script tab). A Script runs on the server and changes things for everyone; a LocalScript in StarterPlayerScripts runs on one player's device.

  • Learn four ideas first: variables (local coins = 3), functions (local function name() ... end), if statements and events (part.Touched:Connect(...)). The four scripts in this guide are built from those, plus loops and tables.
  • Use task.wait(), not wait(). Roblox's reference marks the global wait() deprecated and superseded by task.wait().
  • In the Output window's display options, turn on Show Context so each line says whether it came from the Server or a Client.
On this page
  1. Before you start
  2. 1. First script
  3. 2. Change a part
  4. 3. Events
  5. 4. First LocalScript
  6. 5. Test it
  7. Where scripts go
  8. Read errors
  9. Older tutorials
  10. Practice
  11. What next
  12. Common errors
  13. With RoCode
  14. Questions
  15. Sources

Before you start: Studio, a Baseplate and the Output window

IllustrationThe four scripts in one playtest: the ColourChanger part changes colour every second, stepping on the Pad turns it yellow for 2 seconds for every player and puts your name in Output, and E fades the Pad on this screen only.

You need Roblox Studio and a Roblox account, and nothing else: no code editor and no plugin. Every script in this guide is typed into Studio's own Script Editor.

  1. Install Roblox Studio, Roblox's free app for Windows and Mac, and sign in with your Roblox account.
  2. Open Studio. Its start page lists templates: pick Baseplate. You get a floor with a 4x4 grid texture and a SpawnLocation, the spot where your avatar appears when you play.
  3. If the Explorer and Properties windows are not showing, open them from the Window menu or the Home tab. The Explorer lists every object in your place; Properties shows the settings of whatever you select.
  4. Open Output from the Window menu or the Script tab. This is where your scripts' messages and errors appear.
  5. In the Output window's display options, turn on Show Context, which labels each message Client or Server, and Show Source, which shows the script and line number that produced it.
The four scripts you will write
ScriptTypeWhere it goesWhat it teaches
FirstScriptScriptServerScriptServiceVariables, a function, an if statement, loops and a table
ColourChangerScriptInside a Part in WorkspaceChanging properties, script.Parent and a loop that waits
TouchPadScriptInside a Part named PadEvents, finding the player who touched a part, and a debounce
MyFirstLocalScriptLocalScriptStarterPlayerScripts, inside StarterPlayerCode that runs on one player's device, key presses, and what stays on that device
Explorer when you finish (only the objects this guide uses)
Workspace
  Baseplate Part
  SpawnLocation SpawnLocation
  Part Part new
    ColourChanger Script new
  Pad Part new
    TouchPad Script new
ServerScriptService
  FirstScript Script new
StarterPlayer
  StarterPlayerScripts
    MyFirstLocalScript LocalScript new

Step 1: Write your first script

  1. In the Explorer, hover over ServerScriptService, click the + button and pick Script (the shortcut is Ctrl+I, or ⌘I on Mac). Studio creates the script and opens it in the Script Editor.
  2. Right-click the new script, choose Rename and name it FirstScript. The name does not change what the script does, but it tells you which script printed what.
  3. New scripts start with one line, print("Hello world!"). Delete it and paste in the code below.
  4. Press Play (F5), with Test chosen in the dropdown to its left. Studio starts a playtest and puts your avatar at the SpawnLocation.
  5. Read the lines in Output, then press Stop (Shift+F5). Stop also puts every object back the way it was before you pressed Play, so anything you moved or recoloured while playing goes back.
Script in ServerScriptService named FirstScript
-- Script in ServerScriptService named FirstScript.
-- Your first Luau: variables, a function, an if statement, a loop and a table.
-- Press Play (F5) and read the results in the Output window.

-- A variable is a name that holds a value
local gameName = "Coin Run"
local coinsToWin = 3

-- A function is a named block of code you can run as often as you like.
-- name and goal are its parameters; return hands a value back to the caller.
local function describe(name: string, goal: number): string
	return `{name}: collect {goal} coins to win`
end

print(describe(gameName, coinsToWin)) --> Coin Run: collect 3 coins to win

-- An if statement runs code only when its condition is true
if coinsToWin > 5 then
	print("That is a long game")
elseif coinsToWin > 1 then
	print("That is a short game")
else
	print("One coin and you win")
end

-- A for loop repeats code a set number of times
for count = 1, coinsToWin do
	print("Coin number", count)
end

-- A table holds a list of values; this loop visits each one in order
local colours = { "Red", "Green", "Blue" }
for position, colour in colours do
	print(position, colour) --> 1 Red, then 2 Green, then 3 Blue
end

Anything after -- on a line is a comment: Luau skips it, so you can leave notes for yourself. The --> comments show what that line prints.

Output should show these eight lines, mixed in with any messages from Studio itself. When print gets more than one value, it puts a space between them. With Show Context and Show Source on, each line is also labelled Server and FirstScript with a line number.

Output (expected)
Coin Run: collect 3 coins to win
That is a short game
Coin number 1
Coin number 2
Coin number 3
1 Red
2 Green
3 Blue

Match each line to the code that printed it. You will do the same with error messages later, so it is worth the habit now.

What each part of FirstScript does
CodeIdeaWhat it means
local gameName = "Coin Run"VariableA name that holds a value. local means only this script, or the block it sits in, can use it. Text in quotes is a string; 3 is a number. Names are case-sensitive, so coinsToWin and CoinsToWin are two different variables.
local function describe(name: string, goal: number): stringFunctionA named block of code you can run as often as you like. name and goal are its parameters: values handed in each time it is called. : string and : number are optional type annotations. Luau uses them to warn you about mistakes in the Script Editor; the code runs the same without them.
returnReturn valueHands a value back to the code that called the function. print(describe(gameName, coinsToWin)) prints whatever describe returns.
`{name}: collect {goal} coins to win`String interpolationText in backticks can hold values: Luau replaces {name} and {goal} with their current values.
if, elseif, else, endIf statementLuau tests the conditions from top to bottom and runs only the first one that is true. coinsToWin is 3, which is not more than 5 but is more than 1, so only "That is a short game" prints.
for count = 1, coinsToWin doNumeric for loopRuns the code inside once for each number from 1 to coinsToWin, with count set to 1, then 2, then 3.
{ "Red", "Green", "Blue" } and for position, colour in colours doTable and loopA table used as a list, which Luau calls an array. Positions start at 1, not 0. The loop visits each item and gives you its position and its value.

Every block that opens with function, if, for or while closes with end. One missing end stops the whole script from running; reading errors shows the message you get.

Step 2: Change a part from a script

Scripts become useful when they change things in the world. The settings you see in the Properties window, such as a part's Color, Transparency or Anchored, are properties, and a script can set them too.

  1. On the Home tab, click Part. Studio adds a block to the Workspace. Its name does not matter.
  2. In the Explorer, hover over the new part, click + and insert a Script. Rename it ColourChanger and replace its contents with the code below.
  3. Press Play. The part turns red, then blue, then green, changing once a second, and starts again.
Script in a Part in Workspace named ColourChanger
-- Script inside a Part in Workspace, named ColourChanger.
-- Scripts change the same properties you see in the Properties window.
-- This one gives its part a new colour every second, for every player.

local part = script.Parent :: BasePart -- the part this script sits inside

local colours = {
	Color3.fromRGB(255, 85, 85), -- red
	Color3.fromRGB(85, 170, 255), -- blue
	Color3.fromRGB(85, 255, 127), -- green
}

part.Anchored = true -- an anchored part stays where you put it

local index = 1
while true do
	part.Color = colours[index]
	index = index % #colours + 1 -- 1, 2, 3, then back to 1
	task.wait(1) -- pause for one second (the old wait() is deprecated)
end
  • script.Parent is the object the script sits inside, here the part. Drag the script into another part and it changes that part instead.
  • :: BasePart is a type cast. It tells the Script Editor that the parent is a part, so it can check the properties you use on it. Luau uses types only for warnings and suggestions, so the cast does not change what the line does.
  • part.Color and part.Anchored are the same properties you see in the Properties window, with the same names. Roblox uses American spelling, so the property is Color even though this script is called ColourChanger.
  • Anchored = true keeps the part still: Roblox's reference says an anchored part never moves because of gravity, collisions or any other physics.
  • colours[index] reads one item from the list. #colours is the length of the list, 3, and % gives the remainder after dividing, so index % #colours + 1 counts 1, 2, 3, 1, 2, 3.
  • while true do repeats forever, which is why the task.wait(1) inside it matters. Roblox's docs say to always put a delay such as task.wait() in an infinite loop: without one, the game freezes and Studio crashes.

ColourChanger is a Script, so it runs on the server, and every player in the game sees the same colour at the same time. Step 4 shows the other kind of script.

Step 3: React to a player with an event

Most game code waits for something to happen: a player joins, a part is touched, a button is clicked. Roblox calls these events. To run code when one fires, you connect a function to it.

  1. Insert another Part and rename it exactly Pad, with a capital P. Leave it directly in the Workspace, not inside a folder or a model, because the LocalScript in Step 4 looks for it there.
  2. Make it a flat pad you can walk onto, for example by setting its Size to 6, 1, 6 in the Properties window. Move it onto the floor near the SpawnLocation and tick Anchored so it stays put.
  3. Hover over Pad, click +, insert a Script, rename it TouchPad and paste in the code below.
  4. Press Play and walk onto the pad. It turns yellow for 2 seconds, and Output names you.
Script in the Pad part in Workspace named TouchPad
-- Script inside a Part in Workspace named Pad, script named TouchPad.
-- Events: when a player steps on the pad, it glows yellow and Output says who it was.
-- A debounce stops it running many times a second while they stand on it.

local Players = game:GetService("Players")

local pad = script.Parent :: BasePart
local COOLDOWN_SECONDS = 2

local normalColour = pad.Color
local busy = false

local function onTouched(otherPart: BasePart)
	if busy then
		return -- still cooling down from the last touch
	end
	-- The character is the Model that holds the body part (or hat) that touched the pad
	local character = otherPart:FindFirstAncestorOfClass("Model")
	local player = character and Players:GetPlayerFromCharacter(character)
	if not player then
		return -- a loose part or an NPC touched it, not a player
	end

	busy = true
	print(`{player.Name} stepped on the pad`)
	pad.Color = Color3.fromRGB(255, 220, 0)
	task.wait(COOLDOWN_SECONDS)
	pad.Color = normalColour
	busy = false
end

pad.Touched:Connect(onTouched)
How TouchPad gets from a touch to a player
CodeWhat it does
pad.Touched:Connect(onTouched)Connects the function to the pad's Touched event, so Roblox runs onTouched each time something touches the pad, and passes in the part that touched it.
otherPartThe part that touched the pad: a foot, a leg, the handle of a hat, or a tool the player is holding. It is never the player, so the next two lines work out who it belongs to.
otherPart:FindFirstAncestorOfClass("Model")Climbs up from that part to the first ancestor whose class is exactly Model, which is the character. Because the class name must match exactly, it passes over a hat (class Accessory) and a held tool (class Tool).
Players:GetPlayerFromCharacter(character)Returns the Player whose character that model is, or nil if it is nobody's character, such as an NPC. The character and in front skips the call when no model was found, which leaves player as nil.
if not player then return endStops here for anything that is not a player. return leaves the function early.

Why the pad needs a debounce

Roblox's debounce page warns that Touched "fires multiple times in quick succession" as parts make contact, and a walking character has several body parts. Without a check, one step onto the pad could print many lines and restart the yellow glow again and again.

The busy variable is the debounce. The first touch sets it to true, and every touch during the next 2 seconds reaches if busy then return end and stops. After task.wait(COOLDOWN_SECONDS) the pad changes back and busy returns to false. COOLDOWN_SECONDS is written in capitals because it is a setting that does not change while the game runs, the naming Roblox suggests for constants.

This pad has one debounce for everyone, so a second player who steps on within those 2 seconds is ignored. That is fine for a pad that glows. A pad that gives rewards should keep a cooldown for each player instead, as the coin pad in the leaderboard guide does.

Step 4: Your first LocalScript, and why it is different

A running game is one server plus one client for each player. Everything so far was a Script, which runs on the server, so its changes reach every player. A LocalScript runs on one player's device instead. Key presses, the camera and on-screen menus are handled there, because only that device knows about them.

  1. In the Explorer, expand StarterPlayer, hover over StarterPlayerScripts, click + and insert a LocalScript. Rename it MyFirstLocalScript and paste in the code below.
  2. Press Play. Output shows Hello, and your name, labelled Client.
  3. Click into the game view and press E. The pad fades. Press E again to bring it back.
  4. While the playtest is still running, click the Client/Server toggle in Studio's testing controls to switch to the server's copy of the game. The pad is solid there: the server never heard about the change.
LocalScript in StarterPlayerScripts named MyFirstLocalScript
-- LocalScript in StarterPlayer > StarterPlayerScripts named MyFirstLocalScript.
-- A LocalScript runs on one player's own device. Press E: the Pad fades on your
-- screen only, because a change to a part made here does not reach the server or anyone else.

local Players = game:GetService("Players")
local UserInputService = game:GetService("UserInputService")

local player = Players.LocalPlayer
print(`Hello, {player.Name}`) -- shows in Output, marked as Client

UserInputService.InputBegan:Connect(function(input: InputObject, gameProcessed: boolean)
	if gameProcessed then
		return -- the key was used for something else, such as typing in chat
	end
	if input.KeyCode == Enum.KeyCode.E then
		local pad = workspace:FindFirstChild("Pad")
		if pad and pad:IsA("BasePart") then
			pad.Transparency = if pad.Transparency == 0 then 0.6 else 0
		end
	end
end)
  • Players.LocalPlayer is the player whose device is running the script. Roblox defines it only for LocalScripts and the ModuleScripts they require, so server code cannot use it.
  • UserInputService.InputBegan fires when the player starts a key press, a click or a touch. gameProcessed is true when the engine has already used that input, for example a click on a button or a key typed into the chat bar, so the script ignores it.
  • workspace:FindFirstChild("Pad") returns the child named Pad, or nil if there is none. pad:IsA("BasePart") checks that it really is a part before the script changes its Transparency.
  • if pad.Transparency == 0 then 0.6 else 0 is an if-expression: it picks one of two values. A Transparency of 0 is fully visible and 1 is invisible.
Script, LocalScript and ModuleScript
TypeRuns onIts changes reachUse it forUsually goes in
ScriptThe serverEvery playerGame rules: coins, damage, doors, rounds, savingServerScriptService, or inside a part while you learn
LocalScriptOne player's deviceThat device only, apart from its own character's movementInput, the camera, screen menus, effects for one playerStarterPlayerScripts or StarterGui
ModuleScriptWhichever side calls require() on itThe same as the script that required itCode that several scripts shareReplicatedStorage for both sides, ServerScriptService for server only

What a cheater can change

Assume a cheater controls everything on their own device. They can run their own LocalScripts and change yours, so they can fade the pad, or anything else, on their own screen. Here that is harmless: the fade is only for show and stays on their device. It is also the reason anything that matters is decided by a Script on the server.

A server Script is not automatically safe either. TouchPad runs on the server, but each player's device controls the physics of its own character, and Roblox's security docs list manipulating when Touched fires, or stopping it firing at all, among the things a client can do with the parts it controls. For a pad that glows, that does not matter. For a pad that pays out, also check something the server keeps track of itself, like the obby guide's rule that checkpoints only count in order.

Step 5: Test all four scripts together

  1. Clear Output with Ctrl+K (⌘K on Mac) and press Play (F5). Output shows FirstScript's eight lines labelled Server, and your Hello line labelled Client. The ColourChanger part changes colour every second.
  2. Walk onto the pad. It turns yellow for 2 seconds and Output shows your name and "stepped on the pad" once. Keep walking around on it: a new line appears at most once every 2 seconds, not every time Touched fires.
  3. Press E. The pad fades to a Transparency of 0.6. Press E again and it is solid.
  4. Press Stop. In the testing dropdown choose Server & Clients, set 2 clients and press Play (or F7). Studio opens a server window and two client windows. In one client, press E: the pad fades there, while the other client and the server still show it solid. Press End Session when you are done.
  5. Break something on purpose. Rename Pad to Pad2 and play. Walking onto it still turns it yellow, because TouchPad finds its part with script.Parent, not by name. Pressing E now does nothing, and there is no error: FindFirstChild("Pad") returned nil, and the if pad and ... check quietly skipped the rest. Add print(pad) on the line after FindFirstChild, play and press E: Output shows nil. A print like that is the quickest way to find out why a script does nothing. Stop, delete the print line and rename the part back to Pad.

Where scripts go

Where a script sits decides whether it runs at all, and Studio does not warn you when it never will. For the scripts you will write next:

Where to put each kind of script
ContainerPut hereWhy
ServerScriptServiceScripts with most of your game's rules: rewards, rounds, savingThey run on the server, and nothing in ServerScriptService is sent to players.
Inside a part in WorkspaceA Script that belongs to that one part, like ColourChanger and TouchPadFine while you learn: the part is script.Parent. For real projects, Roblox advises tagging the parts instead (see below).
StarterPlayerScripts, inside StarterPlayerMost LocalScripts: input, the camera, effects for one playerEach player gets their own copy when they join.
StarterGuiLocalScripts inside a ScreenGui that run an on-screen menuEach player gets their own copy of the interface.
ReplicatedStorageModuleScripts that both server and client code requireBoth sides can see it. A LocalScript, or a Script with the default settings, placed here never runs.

Roblox's script locations page recommends not putting scripts directly inside parts in Workspace at all: tag the parts instead and work with them from a single ModuleScript using CollectionService. A script inside a part is still the easiest way to start, and it is fine for one or two objects while you learn. The door guide shows the tagged pattern, with one script for every door, and the client and server guide has the full table of which containers run which scripts.

When something goes wrong: read the Output

Errors show in Output in red. Each one starts with where it happened, the script's full name and the line number, and then says what went wrong. Click the error and Studio opens that script at that line. For example, if you deleted the if not player check from TouchPad and a loose part landed on the pad, Output would show:

Output (example)
Workspace.Pad.TouchPad:22: attempt to index nil with 'Name'

Mistakes in how the code is written, such as a missing end, show up before you press Play: the Script Editor underlines them in red, and the Script Analysis window (the Analysis button on the Script tab) lists them. A script with one of these mistakes does not run at all, not even the lines above it.

Three errors to recognise
MessageWhat it meansFix
Colour is not a valid member of Part "Workspace.Part"Nothing with that exact name exists on that object. Here, the property is spelled Color.Match the spelling and capitals in the Properties window or the Explorer. More on this error.
attempt to index nil with 'Name'The code read something, here .Name, from a value that was nil. In the example above, player was nil because a loose part touched the pad.Find out why the value is nil, and check it with if before using it. More on this error.
Expected 'end' (to close 'then' at line 2), got <eof>The if on line 2 has no matching end. For a function the message says to close 'function', and <eof> means the end of the file.Add the missing end, looking at the line named in the brackets rather than the last line. Sometimes the message ends with "did you forget to close ... at line N?". That part is Luau's guess from your indentation and can point at the wrong block, so check the line in the brackets first. More on syntax errors.

When a script does nothing and Output shows nothing either, it is usually somewhere it never runs, or waiting for an event that never fires. The script errors guide has a checklist for silent scripts, and goes deeper into reading Output.

What older scripting tutorials do differently

If you also learn from videos and forum posts, you will meet older patterns. These are the ones that matter, with the reason each one is a problem.

Patterns in older tutorials, and what this guide does instead
The tutorialThe problemThis guide
Pauses with wait(1)Roblox's reference marks the global wait() deprecated and says task.wait() has superseded it.task.wait(1)
Finds the character with otherPart.Parent, as Roblox's own lava lesson doesWhen a hat or a held tool touches the part, otherPart.Parent is the Accessory or the Tool, not the character, so no Humanoid is found and that touch is missed.FindFirstAncestorOfClass("Model"), then GetPlayerFromCharacter
Uses Touched with no debounceTouched fires several times in quick succession for one step, so the code runs again and again.A busy flag and a cooldown
Puts a LocalScript inside a part in WorkspaceA LocalScript never runs there. It only runs from places that belong to one player.LocalScripts in StarterPlayerScripts (why)
Writes part.Touched:connect(...) or table.getn(list)Roblox's naming guide says camelCase APIs are mostly deprecated, and the reference lists only Connect. table.getn is deprecated in favour of #list.:Connect(...) and #list
Changes coins or deals damage in a LocalScriptThe change stays on that player's device, so nobody else sees it and the server never counts it.Game rules in Scripts on the server

Practice: three changes to try

Changing code teaches more than reading it. Try these in your own place, one at a time, and press Play after each.

  • Make the pad give a point. Add the Leaderstats script from Step 1 of the leaderboard guide. Then in TouchPad, after busy = true, find the player's leaderstats folder and add 1 to its Coins value. Hint: player:FindFirstChild("leaderstats"), then leaderstats:FindFirstChild("Coins"), then coins.Value += 1. The leaderboard guide's coin pad is a finished version, with a cooldown for each player.
  • Fade the colour changer too. Make ColourChanger change the part's Transparency every second as well. Hint: add a second table of numbers between 0 and 1, such as { 0, 0.3, 0.6 }, and set part.Transparency from it on the line after part.Color, using the same index.
  • Print the pad's colour. Make MyFirstLocalScript print the pad's Color when you press E. Hint: print(pad.Color) inside the if pad and pad:IsA("BasePart") block. Press E while the pad is yellow: the client sees the colour the server set, because changes made on the server reach every client.

What to learn next

You have now used the pieces most game scripts are built from. A good order for what comes next:

  1. LocalScript vs Script vs ModuleScript: where each script type runs and what it can change, in more depth than Step 4.
  2. RemoteEvents: how a LocalScript asks the server to do something, and how the server checks the request.
  3. A leaderboard: your first stats, created and changed on the server.
  4. Your first game: a short coin course with lava, coins and a finish pad, run by two server scripts, then published.
  5. Then pick a system to add: a shop GUI, a round system or obby checkpoints. When something breaks, the script errors guide helps you read the message.

Roblox's own Coding fundamentals tutorials make a good companion: six series that go from variables and functions through conditionals, loops, and arrays and dictionaries to organising code with ModuleScripts, with small projects to build in Studio.

Common errors and fixes

Most first-script problems are a name that does not match, a script in the wrong place, or a loop with no wait. Keep Output open while you test.

Studio freezes or stops responding when I press Play

A while true do loop has no wait inside it, so nothing else ever gets to run. Roblox's docs say an infinite loop without a delay such as task.wait() freezes the game and crashes Studio. Put a task.wait() inside every loop that runs forever, as ColourChanger does.

Nothing happens when I step on the pad

Check that TouchPad is a Script, not a LocalScript, directly inside the Pad part, that it is not disabled, and that the pad's CanTouch property is ticked. Then make print("touched", otherPart.Name) the first line inside onTouched. If it never prints, the event is not firing; if it prints, the problem is further down.

Pressing E does nothing

MyFirstLocalScript must be a LocalScript inside StarterPlayerScripts: a LocalScript in Workspace or ServerScriptService never runs. The part must be named exactly Pad and sit directly in the Workspace. Click into the game view first, and make sure you are not typing in the chat, because the script ignores keys the game has already used.

The part changes on my screen but not for other players

The change was made in a LocalScript, so it stayed on your device. Make it in a server Script instead, or have the LocalScript ask the server with a RemoteEvent.

ColourChanger works inside a part but breaks in ServerScriptService

It uses script.Parent as its part. In ServerScriptService the parent is ServerScriptService, which has no Anchored or Color, so Output shows a "not a valid member" error. Keep it inside the part, or give the part a name and find it by that name instead, for example local part = workspace:WaitForChild("ColourPart") :: BasePart.

Output shows nothing at all

Check that the Output window is open (Window menu or Script tab) and that no filter is set: Output can be filtered by message type, by Client or Server, and by text. If it is open and still empty, the script probably never ran. See the checklist for scripts that do nothing.

Getting unstuck with RoCode

If you get stuck on a script in your own place, RoCode can read it with you. RoCode is an independent AI agent for Roblox Studio, not made by Roblox: you type in a web chat, and its Studio plugin creates and edits the scripts in your Explorer.

While you are learning, Ask mode is the useful one: you still write the scripts, and RoCode reads what is already there and answers your questions about it.

You type

Explain what the TouchPad script inside the Pad part does, line by line, and tell me why it uses a debounce.

RoCode does
  • In Ask mode, uses only reading tools such as Search Scripts and Read Script, and changes nothing in the place
  • If something needs fixing, says what it would change and where, and suggests switching to Build
  • Switch to Build and it edits the scripts in place, then compile-checks each one with Check Script. That is a compile check, not a type check or a playtest
  • Reads Studio's Output with its Check Output tool, including Server and Client lines from your last playtest, even after you press Stop

In Build mode with plugin 3.9 or newer, RoCode can run a short playtest and read the errors, but it does not move a character or take screenshots, so you still walk onto the pad yourself. How RoCode connects to Studio.

Questions

Where do I write scripts in Roblox Studio?

In the Explorer, hover over a container such as ServerScriptService, click the + button and pick Script. Studio opens it in the Script Editor, where you type Luau. Server scripts usually go in ServerScriptService; LocalScripts go in StarterPlayerScripts or StarterGui.

How do I run a script in Roblox Studio?

Press Play (F5). Studio starts a playtest, and each enabled Script in ServerScriptService or Workspace runs as soon as the game starts; LocalScripts in StarterPlayerScripts run once you join the playtest. Run (choose it in the dropdown next to Play, or press F8) starts the game without your avatar, so use Play for this guide. Press Stop (Shift+F5) to end the test. To open a script you already have, double-click it in the Explorer.

What programming language does Roblox use?

Luau. Roblox describes it as a fast, small, safe, gradually typed scripting language derived from Lua 5.1, so most Lua tutorials still help. Luau adds features such as string interpolation with backticks and optional type annotations, and Roblox adds its own libraries and objects, such as task.wait.

What is the difference between a Script and a LocalScript?

A Script runs on the server, and its changes reach every player. A LocalScript runs on one player's device, for things like input, the camera and screen menus, and its changes to parts, values and the interface stay on that device. The client and server guide covers both, plus ModuleScripts.

Can I script in Roblox Studio on a phone or iPad?

Roblox's setup page describes Studio as a free app for Windows and Mac and lists no phone or tablet version, so you need a computer to write scripts.

Why does my script do nothing and show no error?

It is usually somewhere that kind of script does not run (a LocalScript in Workspace, or a Script in StarterPlayerScripts), it is disabled, or the event it waits for never fires. The script errors guide has a checklist.

How long does it take to learn Roblox scripting?

Nobody can give you an honest number: it depends on how much you build. What helps most is writing small scripts in your own place often. Change the four scripts here, try the practice tasks, then follow the first game guide and add one system at a time.

Sources and further reading

How the code was checked: every script on this page passes Luau's strict type checker against Roblox's API definitions (luau-lsp, 15 October 2026). A type check catches misspelt APIs and wrong types, not game logic, so playtest in Studio before you publish.

Try RoCode on your own place.

Free every day, no card required. Install the plugin, describe the feature, and review what lands in Studio.