[Unity UI - Introduction for the business developer Series - Part 5] Unity UI 101



Jim Mc̮̑̑̑͒G
  ·  
10 March 2020  
  ·  
 13 min read

This is part five of a beginner-level series about Unity, aimed at existing .NET business developers, who are interested in dipping a toe into something different.

In Part 1 - Getting started, we explore how a business developer could make a start using Unity, look at the Editor and overview some of the common words that you’ll encounter.

In Part 2 - Scripting, we learn about some coding concepts that are applicable to Unity.

In Part 3 - A prototype mobile app, we work through the steps needed to make a super-simple application and deploy it to a mobile device.

In Part 4 -Logging and debugging with Android , we look at how we can attach the debugger and use logging - basic tools for any developer.

In Part 5 - Unity UI 101 , we take a first look at Unity UI and interact with a basic button control.

In Part 6 - Unity UI Scrolling List - Creating the Scene , we take on a slightly more complex project, by creating a scrolling list of items using Unity UI.

In Part 7 - Unity UI Scrolling List - Adding the Code , we finish the project started in Part 6, by writing a script to call a REST service and populate items in our UI.



Overview

As a business developer, you may have looked at other tutorials and found that you have difficulty correlating the development world that you are accustomed to (e.g. results of a database query) to a man in a space-suit, moving around a virtual room with a game controller.

Space-monsters rendered with stunning graphics and realistic physics is pretty cool - but how do we go about displaying a collection of records from an API call?

In this article, we’ll introduce Unity UI - a fully-featured, out-of-the-box toolset for creating an interface that is suitable for virtually any application.

As a reminder, this series is not intended to be an in-depth beginner guide to Unity. Instead, this is meant to be a birds-eye overview, orientated towards existing business developers. You’ll probably be the sort of person who already has a good feel for how software is created, but just wants an overview of the main features and semantics of how a Unity project hangs-together.

As we mentioned back in part 2 of this series, if you are accustomed to working with markup languages (such as HTML or XAML) to describe the UI, you may find Unity UI a slightly alien way of working. However, if you have a history of using older MS technologies such as WinForms or WebForms, the notion of visually creating and manipulating controls in an editor will be more familiar territory.



Learn how to work with a basic UI Element

We’re going to start by keeping things really simple, by looking at how to work with a simple button; how to create one, how to position it and how to attach events.

  • We need to start with a fresh Unity app and configure it for mobile deployment, just like we did in part 2 of this series.



Add a basic button

To get the ball rolling we’ll create and play around with a simple UI building block. We’ll create a button, position it using the UI and show how we can set its text in code. If you can see how that works, you’ll probably feel comfortable enough to figure out how the other UI elements work.

  • With an empty Unity project, right-click in the Hierarchy and select “UI” → “Button”
  • A couple of things happen:
    • A GameObject called “EventSystem” is added to the hierarchy. It’s relevant to what we are doing, but we don’t need to become involved with it, so just ignore for now. Importantly, just make a point of not deleting it. You can read more at Unity Documentation : Event System
    • A GameObject called “Canvas” has been added. As the name suggests, this is an object onto which other UI elements appear. We’ll use it to define how the UI presents itself to the user. We can read more at Unity Documentation : Canvas.
    • Finally, the thing we actually started off asking for is a “Button” GameObject

screenshot unity UI adding button



If we look more closely at the “Button” GameObject in the Hierarchy, we’ll see that it has a caret indicating that it has children. If we expand this, we can find a child GameObject called “Text”.

The significance of separating the button object directly from things like the text of its label means that we have the option to combine other elements to create more complex controls.

For example, we could choose to leave the button as we see it now - but alternatively, we could instead combine other elements together if we wanted. For example, a common choice could be a button with both text and an image (e.g. an icon).


That’s great, but what does my new UI look like?

Adding elements to the Hierarchy is all good and well, but it’s a little bit like writing HTML markup without having access to a web browser to actually see what the rendered version looks like.

Our view into the game world, including our UI, should all be conveyed by the Unity Editors Scene View. However, at the moment there’s a good chance that all we can see is a bit of blue sky and maybe some lines. We’ll sort this all out now.

Because we’re intending for this to be viewed on a mobile device, we’ll take some additional steps to make our App work better in a typical portrait mode.

  • Start by highlighting the “Canvas” GameObject in the Hierarchy View.
  • In the Inspector View, locate the Component called “Canvas Scalar”.
    • In the “Canvas Scalar” component, locate the field “UI Scale Mode” and change the dropdown to “Scale with Screen Size”.
    • Also in the “Canvas Scalar” component, locate the field “Reference Resolution” and change the X value to “640” and the Y to “960”. This approximates a common mobile phone screen ratio.
  • Looking at the buttons across the top of the Scene View panel, find a button labelled “2D” and press it. This will flatten our view into the scene.
  • We want to position the view so that we can see the entire “Canvas” - it’s marked as a rectangular outline. Before progressing further with this guide, make sure that we can see the outline of the “Canvas” (so it looks like the screenshot below).
    • If we can’t see the outline, try zooming the view out (using the mouse wheel) and/or panning the view about (holding the middle button and moving mouse).

screenshot adjusting canvas for a phone size



Positioning elements

As business developers, we are probably familiar with positioning UI elements using a coordinate system. In HTML+CSS you may be accustomed to a coordinate system whereby “0,0” is in the top-left corner of the parent, with increasing values of X taking us further to the right, and increasing values of Y taking us further down.

Unity has similarities but is not quite the same.
* Incrementing the Y axis moves an object upwards (not downwards, as with HTML) * The relative origin of the parent can be chosen, rather than always being top-left (as with HTML)

Let’s quickly experiment with this:

  • In the Hierarchy View select the “Button” GameObject and look at its “Transform” Component in the Inspector View.
  • We should find a control that looks a bit like a bunch of nested squares. This is called the “Anchor Preset Button” This control lets us set the GameObject Anchor.
  • Before we start, the Anchor will default so that it is centred in the parent. We can visually check this by looking for a “target-like icon” (it’s difficult to describe in words, so just check out the screenshot below).
    • We want to check that we’re starting at the same default, so make sure the Anchor is centred and that the X/Y positions are both “0”.
    • We can also describe the Anchor positon as a decimal number in the range from 0 to 1. Currently, we should see values of “0.5” in “Anchors” values for both the X/Y axis - meaning “the anchor is centred horizontally and vertically”. Leave these values untouched for the moment.

screenshot centred anchor



  • Next, press the “Anchor Preset Button” - a grid of other buttons is displayed.
  • Click the button that corresponds to the top-left position.
    • We should see the anchor-icon reposition so that it appears in the top-left corner of the parent “Canvas” GameObject
    • We should see that the “Button” GameObject itself hasn’t actually repositioned.
    • However, we should see that the X/Y position coordinates of the “Button” have changed.

screenshot anchor top-left



With the Anchor set to be top-left, the origin of the relative coordinate system is now centred on the top-left corner of the canvas. To finish demonstrating how this works, we should now:

  • Modify the X/Y position values of the button to both be “0”.
  • With this change made, we should now see the “Button” itself now repositioned to the top-left corner of the canvas:

It may be helpful if we spend a few more minutes experimenting with different anchor positions and different values for position, but we’ve pretty much covered the absolute basics of positioning.



Make the button a bit bigger

The button is a bit too small to see or read the label, so let’s reposition it again and make everything a bit larger.

  • Return the “Button” back to the centre of the “Canvas” using the “Anchor Preset Button”. Reset the X/Y positions to “0” so the button sits in the middle.
  • Continuing to work in the “Transform” Component of the the “Button”, increase the size of the “Button” by setting the width and height to “400” and “100” respectively.
  • In the Hierarchy View, select the child “Text” Component. Over in the Inspector View, locate the Component called “Text”
  • Within the “Text” Component, locate the attribute “Font Size” and set it to “48”
  • The UI element should now be much larger and look like the following screenshot:

screenshot making button element larger



Changing the button text in code.

We can of course manually use the Inspector View to modify the text of the button at design-time, but there is every chance that we will want our project to be able to change values of UI elements procedurally.

Back in part 2 of this series, we looked at a couple of ways that we could reference GameObjects in code. If you haven’t been following along, we should go back and read this article, as we’re going to be building on concepts that you need to be familiar with.

  • In the Hierarchy View, right-click and create a new empty GameObject and rename it to “ButtonManager”
  • In the Project View, right-click in the “Scripts” folder and create a new C# script also called “ButtonManager”.
  • Drag and drop the “ButtonManager” script (from the Project View) directly onto the “ButtonManager” GameObject (in the hierarchy).
    • As a reminder, we create and add the script in this two-step approach, rather than simply using the “Add Component” button in the Inspector. This is so that we can choose the folder we want the script added to - otherwise, it gets dumped into the root of the “Assets” folder.

screenshot added ButtonManger object



  • Next, open up the script file “ButtonManager” in our code editor.
using UnityEngine;
using UnityEngine.UI;

public class ButtonManager : MonoBehaviour
{
    private Text buttonText;

    void Start()
    {
        buttonText = GameObject.Find("/Canvas/Button/Text").GetComponent<Text>();
        buttonText.text = "Hello World";
    }
}

Let’s pause a moment to talk about the above code.

  • Don’t forget to include using UnityEngine.UI.
  • We use private Text buttonText; to store a reference to a Unity UI “Text” Component
  • We hopefully recognise the use of GameObject.Find from part 2 of this series - along with the use of a path to locate the GameObject that we’re specifically interested in.
  • What’s new in this code, is that we are not interested a reference to the “Text” GameObject, but rather the Component of the GameObject, which is also called “Text”. We use the generic method GetComponent<Text>() to access the Component specifically.

The duplicate naming does get a little confusing here, it feels like it should be called something like “TextComponent”, but that’s the way it is in Unity.

Putting that aside, both GameObject.Find and GetComponent<type> are really useful pieces of code that we are likely to use all of the time, so they are really worth taking note of.

As a performance consideration, avoid using these methods in the Update() loop as they are relatively expensive operations.

  • Save the changes to the script and run the project in the editor. If things are working, we should see the button now displaying the message “hello world”.

screenshot button showing hello world



Make the button do something when clicked

A final basic ingredient to any UI cookbook, is the ability to create events - we’re going to add a “ButtonClick” handler to our button.

  • Return back to the code editor and make the following change to the “ButtonManager” script:
  • Pay attention to the fact that the new ButtonClicked() method needs to be public.
  • Don’t forget to save the changes (Unity needs to detect a file save in order to recompile).
using UnityEngine;
using UnityEngine.UI;

public class ButtonManager : MonoBehaviour
{
    private Text buttonText;

    void Start()
    {
        buttonText = GameObject.Find("/Canvas/Button/Text").GetComponent< Text>();
        buttonText.text = "Hello World";
    }

    public void ButtonClicked()
    {
        buttonText.text = "Clicked!";
    }
}


Adding the code above was straightforward.

Next, we need to wire up that code to the Click handler of the button.

This next bit is a little fiddly, so take care to read the instructions carefully:

  • Return back to the Unity Editor
  • In the Hierarchy, locate and highlight the “Button” GameObject. Over in the Inspector locate the Component called “Button”.
  • Within the “Button” Component locate the “OnClick” control - it’s located near the bottom of the Component and appears as a larger box than the other fields.
  • Locate and click the small “+” (plus symbol) button found on the bottom-right.
  • When we click this button, a new item is added to the list of click events.
  • There is a drop-down with the value “Runtime only” which we can ignore - what we need to find is a box immediately below this, which will contain the value “None (Object)” by default. Make sure we can find this box before progressing.
  • Taking care not to single-click in the Hierarchy (so as to change the highlighted selection), drag the “ButtonManger” GameObject from the Hierarchy and across to the Inspector and drop it onto the box in the ClickHandler that we identified a moment ago.
  • Next, in the dropdown that currently says “No Function”, change this so that it first highlights “ButtonManager”.
  • A flyout-menu will then appear, listing methods that are available in the “ButtonManager” to select - we should go ahead and select the “ButtonClicked()” method (that we wrote earlier).
  • Go ahead and run the project - click the button and be amazed ;-)

screenshot attaching button click handler



Making a more attractive UI

The default cosmetic for Unity UI elements is really basic - but then, so is the basic look of things like HTML form controls!

However, just like HTML and other UI systems, UnityUI has plenty of options for modifying the look and appearance of controls.

Along with basic options, such as being able to change colours and fonts, we can also add images to UI elements. When we start using custom graphics like this, the UI can look vastly more professional.

As a business developer, there is a good chance that you work alongside colleagues whose role is to specialise in cosmetic design (e.g. the front-end web designer), so this may be an area to defer to their talent if you have access to people like this.

Alternatively, have a look through the Unity Asset Store, searching for “UI Pack”, as there are literally hundreds of free and premium packs available to download.



Wrapping up

As a beginner to Unity, we’ve actually covered a fair bit of ground learning about some of the basic building blocks and seeing how various parts of a Unity project all hang together.

In particular, the correlation between script files and Unity objects is an important concept to understand well - so if you’re feeling comfortable with what you’ve learned so far in this series, you’ll probably not face any real challenges with Unity moving forward.



In the next part of this series, we’ll expand upon what we have learned in this article, to create a more advanced interface using Unity UI.

NEXT: Read Part 6 - Unity UI Scrolling List - Creating the Scene

If you find my content helpful, please consider sharing the love with a GitHub Sponsorship - equivalent to a cup of coffee every other week.





Archives

2020 (23)
2019 (27)