This content has been archived.

Archive

Older content from our site that still has value for lots of developers!

Beginning Unity 3D for iOS: Part 2/3

In this second tutorial,, you’ll add functionality to enrich the project, including better player movement and better game scenery. You’ll also learn how to use Unity Remote for debugging.

Version

  • Other, Other, Other
Learn how to use Unity to make a simple 3D iOS game!

Learn how to use Unity to make a simple 3D iOS game!

Welcome to the second part of the tutorial series on Beginning Unity 3D for iOS!

In the first part of this series, you learned the basics of Unity by building a very simple project and deploying it to an iOS device. You’ll want to be sure to go through that part of the tutorial before moving on to this one.

Now in this second part, you’ll add functionality to enrich the project, including better player movement and better game scenery. You’ll also learn how to use Unity Remote for debugging.

Once again, game on!

Getting Started: A Change of Scenery

Open your Unity project from Part 1 of the tutorial. If you don’t have it already, here are the download links: Unity Project, Xcode Project.

You’ll make your changes for this part of the tutorial in a new scene, so you can easily have the old one for reference later if you’d like.

Select File\Save Scene as… and name your new scene Level_2. The new Level_2 scene should show up in the Project View.

All the assets you had in the previous scene, such as scripts, are now available for use in your new scene. You can make changes to the GameObjects present in the Level_2 scene without affecting the same objects in the Level_1 scene.

Gettin’ Jiggy With It

First you’ll enhance the player’s movement. Currently your Heroic Cube always moves forward and rotates right. That’s not very smooth or exciting.

A Character Controller is a Unity component that you can attach to a GameObject to help create more realistic movement. You manipulate the Character Controller through script functions.

For example, you can call a pre-defined SimpleMove function to move the character. The SimpleMove function takes in a Vector3 input representing the speed with which to perform the move. The character’s movements automatically account for gravity, allowing it to move up slopes and down stairs.

The character also slides around any obstacles it finds in its path without your having to write code to take care of that.

To see what this means, select the Cube GameObject (the player) in the Hierarchy View and select Component\Physics\Character Controller. You’ll see a dialog asking for confirmation to replace the Box Collider with a CharacterController.

Adding CharacterController component warning.

Click Replace.

You should see a new component in the Inspector for the Character Controller. You’re going to create a brand-new script to control the player’s movement, so you no longer need to attach the MoveSimple script to the Heroic Cube in this scene.

Character Controller added.

Click on the gear icon to the right of the MoveSimple script component in the Inspector and select Remove Component. The script should no longer show up in the Inspector.

Remove Move Simple script.

Create a new JavaScript asset by selecting Assets\Create\JavaScript and name it MoveAround. Double-click the new script to open it in the MonoDevelop Editor. Delete the stubbed out functions and add the following code:

var speed : float = 3.0;
var rotateSpeed : float = 3.0;

function Update () {
    var controller : CharacterController = GetComponent(CharacterController);

    // Rotate around y - axis
    transform.Rotate(0, Input.GetAxis ("Horizontal") * rotateSpeed, 0);
    
    // Move forward / backward
    var forward : Vector3 = transform.TransformDirection(Vector3.forward);
    var curSpeed : float = speed * Input.GetAxis ("Vertical");
    controller.SimpleMove(forward * curSpeed);
}

@script RequireComponent(CharacterController)

Save your changes.

The last line in the script specifies that this script can only be attached to a GameObject that has a Character Controller component.

The Update() function gets a handle to the Character Controller component. It then rotates the transform around the y-axis based on inputs representing left/right movements. By default, the left/right movement is controlled by both the left/right arrows and the A/D keys.

The Input.GetAxis() value ranges from -1 to +1. A negative value will result in an anti-clockwise rotation and a positive value a clockwise rotation around the y-axis.

The SimpleMove function moves the character forward or backward, depending on the input obtained from Input.GetAxis(“Vertical”). This input is triggered by either the up/down arrows or the W/S keys. As with the horizontal input, the Input.GetAxis() value ranges from -1 to +1, and negative and positive values will result in backward and forward movement, respectively. You use a speed multiplier to control the rotation angle or the move distance.

Attach the new script to your Heroic Cube. By now you should know the drill.

(Hint: If you don’t remember, it’s Components\Scripts\Move Around. :])

When you’re done, you should see the new Move Around script component in the player’s Inspector.

Move Around script added.

Why don’t you take your Heroic Cube for a spin using the Unity Editor? Click the Play button and experience your newfound freedom – oh, the joy of being able to rotate left and right, and move forwards and backwards!

Use the left/right/up/down arrow keys to move around, and also test out the W/A/S/D keys. The player movements are much smoother now, thanks to the Character Controller component and your scripting genius.

Give yourself a pat on the back before continuing. :]

Debugging with Unity Remote

You might have noticed in the last tutorial that testing your project on your iOS device was a bit cumbersome. The entire process of exporting to an Xcode project and building and running on your device can take quite a bit of time, which really adds up during development.

The good news is there’s a better way! The fastest way to debug your game on iOS is using an app called Unity Remote. This allows you to skip the steps of building your project for iOS, launching Xcode and deploying on your device.

With the Unity Remote iOS app, you can link your iOS device to the Unity Editor and control your Unity Editor from the iOS device. This allows you to quickly debug your game inside the Unity Editor.

Unity Remote is available for free via the App Store. Download and install the app on your device.

Note: To use Unity Remote, your iOS device and your computer should both be on the same Wi-Fi network. In addition, the Unity Editor window must be in the foreground in order for this to work. If you send the Unity Editor window to the background, you’ll get a “Waiting for game view. Press ‘Play'” message on the iOS app.

Click Play in the Unity Editor. On your iOS device, launch the Unity Remote app. Select your computer from the list that appears. If your computer is not listed, try entering your computer’s IP address in the Unity Remote’s IP setting.

Unity Remote

When Unity Remote has paired with your computer, your iOS device should be able to control the game running in the Unity Editor. The resolution of the display on the device won’t be ideal, but it’s a great way to quickly prototype your game. However, you’ll want to occasionally build the project for iOS and launch it from Xcode so you can properly test game physics under more realistic conditions.

Test the game on iOS. You’ll find that there’s no way to move the player on your device because your left/right/up/down inputs do not exist on iOS (however, you can still control it on your Mac). Next up, you’ll implement some joystick controls to fix this.

Double the Joysticks, Double the Fun

Lucky for you, Unity’s Standard Assets (Mobile) package includes assets that implement joystick functionality. Select Assets\Import Package\Standard Assets (Mobile) to import the relevant items (as showing below) from the package.

Importing package assets for joystick functionality.

Select the indicated items that relate to joystick functionality. Click Import. When the import is complete, the Project View will contain a new folder called Standard Assets (Mobile). You may see a warning in Unity 4 with the imported joystick script, similar to this (in yellow at the bottom):

Script warning.

To resolve this, double-click on the warning. That should open the Joystick script file. Put your cursor on the line with the warning:

    gameObject.active = false;

Modify the statement to:

    gameObject.SetActive(false);

Now when you switch back to the Unity Editor, the warning should vanish. Take that!

First add the Dual Joysticks prefab to your scene. A prefab is a reusable and often customized GameObject. You can add a prefab to a scene by either dragging it from the Project View or adding it programmatically via a script. For example, you could build a prefab that represents a player and programmatically add multiple players to a scene.

In your Project View, open the Standard Assets (Mobile)\Prefabs folder. Drag the Dual Joysticks prefab into your Hierarchy View.

Dual joysticks added to scene.

You can see the joysticks by clicking the Game tab to go to the Game View:

Joysticks in Game View.

Go back to the Scene View.

Click on the triangle next to the Dual Joysticks GameObject in the Hierarchy View. Notice that the Dual Joysticks GameObject is actually composed of two child GameObjects.

A procedure called parenting was used to set up the joystick parent/child GameObject relationship. Parenting is useful if you want to create a composite GameObject that has linked GameObjects. For example, you may want the left and right joysticks to be enabled or disabled at the same time, and it’s much easier to do this via script if they can be treated as a single object.

Select the LeftJoystick GameObject and note that it has the Joystick script component attached to it. Select the RightJoystick GameObject and verify the same.

The Joystick script detects touch events on the GUI Texture (the graphic) attached to it and repositions it with certain constraints. For example, the graphics only move inside a given boundary. The script also normalizes the position output so that it’s within the -1 to +1 range. This allows you to use the joystick in an iOS environment as a substitute for Input.GetAxis().

At this point you’ve placed the two joysticks in the scene, but they’re not yet connected to your Heroic Cube to drive input. You’ll modify the script to assign the right joystick the task of rotating the player, while the left joystick will move the player back and forth.

Modify the MoveAround script to handle joystick input. Open the script for editing and add two public variables representing the move and rotate joysticks (at the top where the other variables are):

var moveJoystick : Joystick;
var rotateJoystick : Joystick;

Then add a new function that looks at the joystick position and returns an output between -1 and +1. Add it right after the Update() function:

function joyStickInput (joystick : Joystick) {
    var absJoyPos = Vector2 (Mathf.Abs(joystick.position.x),
                                   Mathf.Abs(joystick.position.y));
    var xDirection = (joystick.position.x > 0) ? 1 : -1;
    var yDirection = (joystick.position.y > 0) ? 1 : -1;
    return ( ( absJoyPos.x > absJoyPos.y) ? absJoyPos.x * xDirection : absJoyPos.y * yDirection);
}

The joystick input is a Vector2 input, having x and y components. You use the larger, absolute value of x or y to set the output. You use the direction of the joystick as a multiplier to denote a negative or positive value. This results in an output value between -1 and +1.

Modify the Update() function to handle input from the Unity Editor or from an iOS device:

function Update () {
    var controller : CharacterController = GetComponent(CharacterController);

    // Rotate around y - axis
    var rotatePos = Input.GetAxis ("Horizontal") ? 
                       Input.GetAxis ("Horizontal") : joyStickInput(rotateJoystick);
    transform.Rotate(0, rotatePos * rotateSpeed, 0);
    
    // Move forward / backward
    var forward = transform.TransformDirection(Vector3.forward);
    var movePos = Input.GetAxis ("Vertical") ? 
                     Input.GetAxis ("Vertical") : joyStickInput(moveJoystick);
    var curSpeed = speed * movePos;
    controller.SimpleMove(forward * curSpeed);
}

The transform’s Rotate() function gets input from either the left/right arrow (or A/D) keys or from the rotate joystick input. The Character Controller’s SimpleMove function gets input from either the up/down arrow (or W/S) keys or from the left joystick input.

Save your script changes. Select the player GameObject (the cube) and note that the Move Around script component has two new public variables for Move Joystick and Rotate Joystick.

Joystick-related variables for Move Around script.

These variables are not currently assigned. With the player GameObject still selected, drag the LeftJoystick GameObject to the Move Joystick variable. Drag the RightJoystick GameObject to the Rotate Joystick variable. (Or instead of dragging, you can used the selector next to each variable, as indicated before.)

Move Around joystick variables assigned.

Click Play in Unity Editor. Start Unity Remote on your iOS device.

Test the joystick functionality and verify that you can move forward and backward using the left joystick and rotate left and right using the right joystick. As you move the joysticks on your iOS device, you should see the joysticks moving in the Unity Editor.

App running with Unity Remote

Note: The joystick images might appear stretched like you see here. Don’t worry, they won’t show up like that on the actual device.

A Clear, Bright Skybox

Now that you’ve improved your Heroic Cube’s movements, how about improving the scenery? So far the player’s been occupying a dull, grey world. Time to do some landscaping. :]

Thankfully, this is fairly simple. Unity includes assets in the Standard Assets package that you can use to create a sky, add vegetation and vary the height of the terrain.

In this section, you’ll add a sky by means of a skybox component. The skybox is a big cube object that’s added to the Main Camera in your game. Once you add the component, you can dress it up by adding a material that covers the cube and is rendered to create the skybox effect.

Select Assets\Import Package\Skyboxes to begin the import process. Select Sunny2 Skybox.mat, then click Import.

Importing package assets for the skybox.

When the import is complete, your Project View should have a new Standard Assets\Skyboxes folder that contains the newly imported asset.

Skybox assets imported.

Select the Main Camera object, then select Component\Rendering\Skybox.

Skybox component added to Main Camera.

The new component shows up in the Inspector. Notice that it has a variable representing the material. This is where the skybox material you imported earlier comes into play.

Click on the little circular icon next to the Custom Skybox variable. The Select Material dialog should pop up listing any material assets that are available for your project’s use.

Selecting skybox material.

Click on the Sunny2 Skybox material, then close the Select Material dialog. The Custom Skybox material should now have the Sunny2 Skybox material assigned to it.

Skybox material assigned.

Your Scene View will now magically change to display the sunny sky you’ve just added. You can click on the Game tab to view the sky in the Game View, or click the Play button.

Game View after skybox added.

The sun has come out! And even though it may appear overcast, that’s encouragement to add some green life to your world.

Don’t Forget Your Veggies

Switch back to the Scene View. You can create vegetation by first adding a terrain GameObject, then adding material (e.g., grass) and objects (e.g., trees).

You no longer need the plane GameObject, as the terrain will take over flooring responsibilities. Right-click on the plane GameObject in the Hierarchy View and select Delete.

Select Assets\Import Package\Terrain Assets.

Importing package assets for the terrain.

Click Import to import all the selections. The Terrain Assets should show up under your Standard Assets folder. You can use the imported assets to modify the behavior of a terrain GameObject.

Select Terrain\Create Terrain to add a terrain GameObject to your scene. Select the terrain object and change its transform position to -1000,0,-1000 using the Inspector. This stretches the terrain out far enough to give your player room to move.

Terrain GameObject transform adjusted.

The Terrain (Script) section contains tools that you can use to dress up your terrain:

Terrain tools.

Select the Paint tool to bring up the brushes you can work with:

Terrain paint tool.

You’ll be painting your terrain with grass. Click Edit Textures\Add Texture:

Terrain paint texture selection.

In the Add Terrain Texture dialog, click Select in the Texture area, select the Grass (Hill) texture, close the Select Texture2D pop up, then click Add:

Grass texture added.

Click around in your scene to paint the grass. To check out your artwork, click on the Game tab:

Game View after grass added.

If only landscaping could always be so easy!

Switch back to the Scene View – now you’re going to plant some palm trees! Select the Place Trees tool in the Terrain (Script) section:

Terrain place trees tool.

Click Edit Trees\Add Tree:

Tree selection.

In the Add Tree dialog, click the circular icon next to the Tree entry, select the Palm GameObject, then click Add:

Tree available to add to scene.

Set the Brush Size to 20:

Place trees tool settings.

Start adding trees to your scene by clicking where you want the trees to be. Hint: Zoom into the scene and pan around as you place the trees. Try adjusting the Point light range and height to see more of the scene as you add trees.

Point light adjustments to place trees.

When done, your scene should look something like this:

Scene View after trees added.

Wow, that’s much better! It’s starting to look like a real world down there. But your terrain’s still looking a bit flat, isn’t it?

You can easily add some height variation to your terrain. In the Terrain (Script) section, select the leftmost tool to raise and lower the terrain height:

Terrain height adjustment tool.

Set the Brush Size to 20, then in the Scene View, click on two to three spots around the player (not too near, though) to vary the terrain height.

Scene View after height adjusted.

Preview the game and move around the scene. Tweak the number of trees in the scene as you see fit but remember to stop the game before making any changes you wish to keep.

Game after scene enhancement done.

Save your scene.

Test your project using Unity Remote and when satisfied, build it as an Xcode project. Select File\Build Settings and in the Build Settings dialog, click Add Current to add the Level_2 scene. The new scene will show up in the Scenes In Build list. Deselect the Level_1 scene to build only Level_2.

Build Settings changes for new scene deployment.

Click Build, choose to replace the previous project if asked and then launch the Xcode project. Deploy and test on your iOS device.

Game on iOS.

Not bad, eh? Imagine how long it would have taken to do all this with raw OpenGL ;]

Where to Go From Here?

Well done! You’ve taken another big stride forward in developing your Unity skills. :] Soon, your Heroic Cube will be closing in on the finish line, too.

Here are some downloads with all of the code from the project up until this point: Unity Project, Xcode Project.

In the final part of the tutorial, you’ll build on the project by adding gameplay. Then you’ll polish it up by adding all the bells and whistles that players expect.

How do you like Unity so far? We’d love to hear about your experiences in the forums!

Add a rating for this content

Contributors

Comments