Skip to main content

Blog Archive

Advanced Scripting: Gui Tutorial 1

September 28, 2009

by John Shedletsky


Hello everyone, Madrak here with the first blog post in our series on building your own GUIs using Lua.  This is a post for advanced script writers only, so don’t worry if some of this goes over your head.

In this lesson, I’ll be explaining the first steps to set up a 2D GUI, and some basics about our coordinate system.frame

 (Here’s a simple GUI dialog that consists of mostly frames and labels)

The first step to creating your GUI is to create a GuiMain and insert it into the player’s PlayerGui object.


local tool = script.Parent;

local character = script.Parent.Parent

local player = game.Players:GetPlayerFromCharacter(character)

local guiMain =“GuiMain”)

guiMain.Parent = player.PlayerGui


A GuiMain object is an invisible overlay that fills the entire screen.  If you add Frames or Labels and Buttons to it, they will be drawn.  But they have to be put into a GuiMain object.

So now that we’ve created out GuiMain object, we can start adding Frames to it.  A Frame is a container object, with a BackgroundColor and BorderColor, that can hold other objects (other Frames, in addition to Buttons and Labels).  It also will fire events when the mouse either enters and leaves, allowing you to script all kinds of cool stuff.  Lastly, it contains a Visible property which can be set to false if you want it (and all of its children) to stop rendering.  This is useful if you want to hide a Frame temporarily. 


–This sample code will create and position a new Frame

local mainFrame ="Frame")

mainFrame.Position =, 0, 0.88, -300)

mainFrame.Size =, 240, 0.0, 300)

mainFrame.Parent = guiMain;


Hold up.  What are all these UDim2 objects?  Well, they are new.  UDim stands for Universal Dimension, and is a compact way to specify both relative and absolute positioning at the same time.  When laying out a GUI, it is often necessary to have some positions/sizes change when a parent container’s size changes.  Other times, you might want to have a fixed offset that is a specific number of pixels.  A UDim lets you do both at the same time.

A UDim object consists of a Scale and an OffsetScale is specified as a number between 0.0 and 1.0 that represents the percentage of your parent’s size.  Offset is specified as an integer number, either positive or negative.  The final result is the combination of the two: Scale * Parent’s Size + Offset.  With the combination of these two values, almost anything is possible.  A UDim2 is just two UDim objects, referenced by X and Y. Here is the exact definition of the function:, xOffset, yScale, yOffset)

Now I’ll run through a few examples of using UDim2’s to make Gui objects stick to various parts of the screen.  Remember, Position is defined as the top left corner of the Frame.


–A 50×50 frame 5 pixels from the top, 10 pixels from the left mainFrame.Position =, 10, 0.0, 5)

mainFrame.Size =, 50, 0.0, 50)

–A frame that is half the size of the main screen, in the center

mainFrame.Position =, 0, 0.25, 0)

mainFrame.Size =, 0, 0.5, 0)

–A 50×50 frame in the top right corner

mainFrame.Position =, -50, 0.0, 0)

mainFrame.Size =, 50, 0, 50)

–A frame that is 1/4 the size of the screen,

–in the bottom right corner

–(For position I took the corner’s position (1.0) – the

— size (0.25) to get the position (0.75))

mainFrame.Position =, 0, 0.75, 0)

mainFrame.Size =, 0, 0.25, 0)


So that’s what a UDim2 object is all about, and how our relative positioning works.  Take a look at my sample PaintBrush tool, hopefully it makes a bit more sense now.

One last tip:  If you’d like to try playing around with Positions and Sizes, open up a level in edit mode and drop a GuiMain (and some Frames)  into the StarterGui. Start playing with the numbers to get a feel for how it changes, and try resizing Roblox to see how using Scales changes your GUI.  Note that StarterGui has a ShowDevelopmentGui flag that you can use to hide it while you are working on your level.  Make sure its checked or nothing will show up.

If you’d like to discuss this blog post, please visit this thread.

Next time: Buttons