Introduction
As a game developer, we all love to make our games compatible to all devices, Including mobile!
If you have any mobile buttons in your game, they probably look like this which is good enough…
The crouch button is stretched out, isn’t similar to the jump button, and varies on distance from jump button (ex. different screen sizes can make it closer or further away from the jump button.) However, it displays as an icon and not some text making it a bit more easier to see.
This one easy to reach, and doesn’t vary on distance from the jump button, however it uses the legacy mobile button design and uses text instead of an icon. This is fine and it works but the legacy design contradicts the modern Roblox UI.
(no hate to Piggy or FE2 they’re very goated games)
This is what we are going for in this tutorial; a user friendly mobile button relative to the jump button that is easy to use.
Overview:
The way Roblox designs its mobile controls are made to be simple to understand. The jump button doesn’t say ‘jump’, it just has a self-explanatory up arrow. The joystick doesn’t say ‘walk’, that is also self-explanatory. UI doesn’t need to be that complicated, especially for people using a phone… As developers have full control over this, you can even ditch the default controls by disabling GuiService.TouchControlsEnabled
and code your own from scratch if you’re looking for more customizable options and such. This tutorial is for making an “addon” to the default ones, as Roblox probably intended for its developers. so that the user has a familiar experience and gets the hang of the controls easily.
According to Roblox Docs, there’s 2 spots for mobile buttons. Here we have the Thumbstick Zone and the Jump Button Zone
Now, Mobile buttons should never be at the Thumbstick Zone! It’s just a very bad idea, as the left thumb should always be used for the thumbstick and it’s very inconvenient to stop moving your character just to press a button. This also can create issues where you try to move your character with the dynamic thumbstick and end up pressing a button instead.
There is something you should be aware of while doing this!
The jump button can change size and position depending on the screen size (ex. phones and tablets)
Phone
Tablet
Notice how the jump button’s size and position has changed when the screen size has changed! More specifically, there’s 2 presets of size and position for the controls. The preset changes when any of the screen dimensions reach over 500 pixels.
Getting Started
In StarterGUI, Create a frame. That resembles where the jump button is. A good spot would be {1, -95},{1, -90}
with a size of {0, 70},{0, 70}
. This is only for editing purposes as it will be changed in a script later on.
Then insert an ImageButton and set it’s position relative to its parent. A good spot for it can be {-1.1, 0},{0, 0}
and set its size to {1, 0},{1, 0}
* (don’t place it on the right as it won’t be fully visible on the screen.
*Assuming you haven’t modified the anchor point.
Scripting
Insert a script inside the Frame
The often-made mistake that just makes me feel disgusted for some reason is this:
local isMobile = game:GetService('UserInputService').TouchEnabled
This is a very bad idea, since Roblox’s core scripts don’t even use this method. If the user happens to have a touch screen PC, they will see mobile controls without even touching the screen.
You should do this instead:
local UIS = game:GetService("UserInputService") --UserInputService
local Frame = script.Parent
function updateInput()
local lastInput = UIS:GetLastInputType()
if lastInput == Enum.UserInputType.Focus then return end -- ignore if the player focuses on the app
Frame.Visible = lastInput == Enum.UserInputType.Touch -- makes the frame visible if the user touched the screen
end
updateInput() -- Detect input on Startup
UIS.LastInputTypeChanged:Connect(updateInput)
What this does is detect if last UserInputType was Touch, instead of just checking if you can touch the screen. Then it makes the frame visible.
We’re almost done! We just need to make sure that the mobile buttons are in the right place!
For this part, we can take a peek at some of Roblox’s PlayerScripts. More specifically, TouchJump which was written by @jmargh.
In this chunk of code, we have exactly what we need to place our jump button.
To explain this code in words, if the absolute length or width of the device safe insets is less than 500, The jump button changes size and position to a value. Otherwise, it changes size and position to another value.
Let’s find a way to replicate this into a LocalScript the easiest way possible!
Adjusting Setup
A way to detect the absolute size of the screen is super simple!
First, Insert a GUI Inside of the frame. It sounds odd, I know. But it will be all worth it
For demonstration purposes, we will be naming this Screen
Set Screen’s insets to DeviceSafeInsets
Mainly, Screen has the Absolute Size of the device!
Scripting (again)
With credit to @jmargh, update the script to this to support the screen sizes.
local UIS = game:GetService("UserInputService")
local RS = game:GetService("RunService")
local Frame = script.Parent
function updateInput()
-- Detecting if Buttons should show
local lastInput = UIS:GetLastInputType()
if lastInput == Enum.UserInputType.Focus then return end -- ignore if the player focuses on the app
Frame.Visible = lastInput == Enum.UserInputType.Touch -- makes the frame visible if the user touched the screen
end
updateInput() -- Run this anyway at first.
UIS.LastInputTypeChanged:Connect(updateInput) -- Now you can run only if you need to.
-- Positioning the mobile buttons.
RS.RenderStepped:Connect(function() -- This should always be running
if Frame.Visible then -- Are mobile buttons enabled?
local screenSize = Frame.Screen.AbsoluteSize -- Absolute Size of the screen.
local minAxis = math.min(screenSize.X, screenSize.Y)
local isSmallScreen = minAxis <= 500 -- Is the screen to small for big mobile buttons?
local jumpButtonSize = isSmallScreen and 70 or 120 -- Gets the size of the jump button.
Frame.Size = UDim2.new(0, jumpButtonSize, 0, jumpButtonSize)
Frame.Position = isSmallScreen and UDim2.new(1, -(jumpButtonSize*1.5-10), 1, -jumpButtonSize - 20) or UDim2.new(1, -(jumpButtonSize*1.5-10), 1, -jumpButtonSize * 1.75)
end
end)
Review
Now you have reached the point where you can now create and place the mobile buttons Easily! If your screen looks like this while emulating a mobile device (using only mouse inputs) You are sooooo close to finishing. Now we need to do the last part: designing the mobile buttons to look like the original.
Designing
Resources required:
- paint.net - Free
After installing paint.net, go in Roblox’s files and open ControlsSheetV2 using paint.net
Save a copy and get started.
So first thing we are going to do is get a blank version of TouchControlsSheetV2. I already made an image of this here so you don’t have to. (don’t open it yet)
Now we need to find an icon for the mobile button. You can find these on Google very easily, or create your own. Then, in a new layer on top of the original one, paste that in and make it a solid color if it isn’t already. Then place it on top of the jump button, with relative size to the arrow.
For demonstration purposes, I didn’t center the image relative to the button. Sometimes, you don’t have to. It’s mostly dependent on the icon you are using. If you are, you’re gonna need to use some math (size of the icon, etc). For reference, in ControlsSheetV2 each button is 144 pixels long and wide
Now use the Magic Wand and the Fill Tool to remove those transparent pixels. Those will cause problems later on.
If you wish to keep your eyes intact and working, I recommend making a background that isn’t white in another layer
Now do what I did here to paste that onto the Jump button
Make a hole where the Jump Button is on the button
Using a little but of math, get the icon on both buttons with the same position relative to their buttons. Here the left of the icon was 44 pixels away from the left of the button (yes the buttons are 1 pixel away from each other, and the left is 1 pixel away from the left side of the image. Use this information, I copied the icon, then used arrow keys/CTRL + arrow keys to move it to perfectly align its left side to the left side of the button, then moved it right 44 pixels
After that, do what you just did coloring the first icon, but with the second one.
There you have it! A modified mobile button sheet for you to use! Now just delete the background layer then merge all layers. Then just cut out parts to export (remember, each button is 144 x 144 pixels
Now just go back to Studio, edit the ImageButton that’s used as a mobile button, then simply upload the images to Image and ImagePressed!
Finished
That was probably a long process. Well, now you’re done! The product should look something like this.
Just like on a keyboard, the input should register when you start pressing the button. Not using the average click functions which require you to hold the button down then up. Use MouseButton1Down, or if you’re that type of guy, use InputBegan.
Also note that the “Active” property can be useful at times, because it doesn’t sink input and allows you to press the button while moving the camera at the same time. This is most used in games where movement really matters like first person shooters, and you probably shouldn’t be using the
Activated
event if the button isn’t activated.
Resources
Gui Used In This Tutorial|attachment (6.7 KB .rbxm)
Your welcome!
@Micamaster100