Unity’s Touch system for mobile development can monitor several properties of touches, allowing a wide variety of control systems for both games and applications. Touches are tracked individually, each associated with the finger that made it, and carry with them several data elements. In this tutorial, you will learn about Unity's Touch system and how to use it in mobile development.
If you are using Unity 2019.2 or higher, click here.
Unity’s Touch system for mobile development can monitor several properties of touches, allowing a wide variety of control systems for both games and applications. Touches are tracked individually, each associated with the finger that made it, and carry with them several data elements. For our purposes, we are concerned primarily with the phase and screen position of the touch, though the touch radius, tap count, and finger ID may also be useful. In the exercises that follow, we will process this data, beginning with the touch phase.
There are five possible touch phases:
Began: A finger has just begun touching the screen
Moved: The finger has moved position, without breaking contact with the screen, since it was last polled
Stationary: The finger has remained in position without breaking contact with the screen since it was last polled (not used in this workflow)
Ended: The finger is no longer touching the screen
Cancelled: Tracking for this touch has been cancelled (not used in this workflow)
For this first demonstration, we are concerned only with the phase of a single touch. Create a new script called TouchPhaseDisplay. Delete Start, as we won’t be using that method.
For this demonstration, we’ll need to use Unity’s UI. This isn’t a requirement to use mobile touch, but we’re using it for our purposes in displaying the touch phase. On line 4, type:
usingUnityEngine.UI;
Now we’ll declare our data members. Beginning on line 7, type:
public Text phaseDisplayText;
private Touch theTouch;
privatefloat timeTouchEnded;
privatefloat displayTime = .5f;
TouchPhaseDisplay is now complete. (Figure 01) Save changes and return to the Unity Editor.
Select image to expand
Figure 01: The completed TouchPhaseDisplay script
Back in the Unity Editor, from the GameObject dropdown, select Create Empty, name it TouchDisplay, and attach the Touch Phase Display component.
From the GameObject dropdown select UI > Text, making sure that it clearly displays the following test phrase with the Game display resolution set to that of your mobile device:
Stationary
Drag the newly created UI Text object into the slot marked Debug Text in the Touch Phase Display component of TouchDisplay. (Figure 02)
Select image to expand
Figure 02: The name will change with each exercise, but all three will use the display text.
Build and run your project on your physical or emulated mobile device. Tap the screen and note the status display. Try moving your finger while touching the screen, or just holding it in one place.
For this exercise, we will use the change in phase and position of a single touch to act as a simple, virtual 4-way directional pad (D-pad). We’ll reuse the UI Text object from Exercise 1 to display the D-pad’s direction. Create a new script called VirtualDPad and delete the Start method. The Update method uses a few levels of nesting, so be sure to pair each opening brace { with a closing }.
On line 4, type:
usingUnityEngine.UI;
Beginning on line 7, type:
public Text directionText;
private Touch theTouch;
private Vector2 touchStartPosition, touchEndPosition;
privatestring direction;
In Update, beginning on line 17, type:
if (Input.touchCount > 0)
{
theTouch = Input.GetTouch(0);
if (theTouch.phase == TouchPhase.Began)
{
touchStartPosition = theTouch.position;
}
elseif (theTouch.phase == TouchPhase.Moved || theTouch.phase == TouchPhase.Ended)
{
touchEndPosition = theTouch.position;
float x = touchEndPosition.x - touchStartPosition.x;
float y = touchEndPosition.y - touchStartPosition.y;
if (Mathf.Abs(x) == 0 && Mathf.Abs(y) == 0)
{
direction = “Tapped”;
}
elseif (Mathf.Abs(x) > Mathf.Abs(y))
{
direction = x > 0 ? “Right” : “Left”;
}
else
{
direction = y > 0 ? “Up” : “Down”;
}
}
}
directionText.text = direction;
VirtualDPad is now complete. (Figure 03) Save changes and return to the Unity Editor.
Select image to expand
Figure 03: The completed VirtualDPad script
In the hierarchy window, right click TouchDisplay and select Rename. Type DpadTester. In the Inspector, click the gear in the upper right corner of the Touch Phase Display component, or right click Touch Phase Display (Script), and select Remove Component. (Figure 04)
Select image to expand
Figure 04
Add the Virtual D Pad component and drag the UI text into the Direction Text slot.
Build and run your project on your physical or emulated mobile device. Try tapping the screen and lifting your finger or stylus without moving it. Swipe in different directions and notice how even the smallest movement in any direction registers a direction. In an actual game, you would probably want to have a minimum change in touch position before movement is registered, and/or scale movement by how far the virtual D-pad is moved.
This exercise shows a few data members of the Touch class that we haven’t explored yet. Of note is the max tap count, which could be useful for tracking personal bests in a clicker game. We also track the radius (but not the shape) of the touch, which (when compared with the maximum possible radius) could translate to pressure in a tactile physics puzzler or natural media painting app. Pressure is tracked separately, as is the orientation of a stylus, but we have omitted those here as they’re not available on every device. We’ll reuse the UI Text and scene object from earlier exercises. Create a new script called MultiTouchDisplay and delete Start.
On line 4, type:
usingUnityEngine.UI;
Beginning on line 7, type:
public Text multiTouchInfoDisplay;
privateint maxTapCount = 0;
privatestring multiTouchInfo;
private touch theTouch;
In Update, beginning on line 15, type:
multiTouchInfo = string.Format(“Max tap count: {0}\n”, maxTapCount);
if (Input.touchCount > 0)
{
for (int i = 0; i < Input.touchCount; i++)
{
theTouch = Input.GetTouch(i);
multiTouchInfo +=
string.Format(“Touch {0} - Position {1} - Tap Count: {2} - Finger ID: {3}\nRadius: {4} ({5}%)\n”,
i, theTouch.position, theTouch.tapCount, theTouch.fingerId, theTouch.radius,
((theTouch.radius/(theTouch.radius + theTouch.radiusVariance)) * 100f).ToString(“F1”));
if (theTouch.tapCount > maxTapCount)
{
maxTapCount = theTouch.tapCount;
}
}
}
multiTouchInfoDisplay.text = multiTouchInfo;
MultiTouchDisplay is now complete. (Figure 05) Rename DPadTester to MultiTouch as in earlier exercises. Remove the Virtual D Pad component and add Multi Touch Display. Finally, add the Multi Touch Display component to MultiTouch and drag the UI text object into the Multi Touch Info Display slot.
Select image to expand
Figure 05: the completed MultiTouchDisplay script
Build and run your project on your physical or emulated Android device. Using as many fingers as you can, experiment with mixing the order in which you touch and lift fingers. Try holding three or more fingers on the screen, then temporarily lifting one of the middle (in the sequence of touches) fingers. Watch how the position coordinates jump, but Unity is able to tell which finger was lifted, indicated by the finger ID. Try getting the tap count past 100. Notice how each finger contributes only to its own tap count. Using just a single touch, the tap count times out and resets to zero briefly after a touch ends. What strategy can you use with multiple touches to keep it from resetting? Try rolling your fingertip on the screen as if you were being fingerprinted, or just barely tapping the screen and monitoring how the radius changes.
When you’re ready, exit the exercise application.
Touch input for mobile is full of possibilities. How you apply the information provided by the touch system can significantly shape your players’ experience. Though we didn’t cover everything that the Touch Input system offers, we did cover what is most useful for games. For more information on what Touch has to offer, check out Touch in the Unity script reference.