====== Lab 2: Picking Up "Home Made" Objects ====== ===== Goal ===== The goal of this lab is to create an interactive scene where you can walk around and pick up various "home made" textured objects you have created with Blender 3D. ===== Preparation ===== - **Install Blender** You need to install Blender 3D on your own machine before you start. You get the latest version from the [[http://www.blender.org/|Blender 3D Home Page]]. - **Install Gimp** (or similar) It is also good to have an image editing program ready, such as Photoshop or the powerful but free [[http://gimp.org|Gimp]] image editor. - **Set Up Unity Folder** In Unity it may be a good idea to organize all of your VIEN work inside a dedicated ''VIEN'' folder under the **Project** panel. To do that, **right-click** on ''Assets'' and select ''Create->Folder'' and type ''VIEN'' as the name. Under the VIEN folder, create three more folders: ''Scenes'', ''Scripts'' and ''Props''. ===== Procedure ===== - **Basic Scene** In Unity, start with an empty scene. Add a floor (as a ''Plane'' game object) and replace the ''Main Camera'' with a ''First Person Controller''. Make sure you can walk around your plane. Feel free to embelish this scene with other visuals (e.g. skybox or fog). Save your scene in your "VIEN/Scenes" folder. - **Create a Textured Object** In Blender, create a new object from scratch with some texturing, export it from there in the Autodesk FBX format and add to your scene in Unity. For this step follow the instructions on the [[public:t-vien-14-1:blendertexturing|Blender Model Export and UV Texturing]] - **Make Object Instance Sense Collision** Once you have instanced your new textured object as a **GameObject** in the scene, click on it in the **Hierarchy** tab and in the **Inspector** panel click on **Add Component** and use the search box to search for a ''Sphere Collider''. Add this collider component to your game object. In the ''Sphere Collider'' check the ''Is Trigger'' check box. You have now created an invisible sphere around your object, which generates a trigger event if something collides with it. You can control the radius of this sphere directly from the ''Radius'' property in the **Inspector** panel. - **Create a Pickable Behavior** You now have to add code to the object to tell it what to do when a collision is detected. In Unity, such behavior code is really just another component that can be added to game objects. We first have to create that compenent as an Asset, before we can attach it. So, in the **Project** panel, navigate to your ''Scripts'' folder (or create one under ''VIEN'' if you haven't already). Right-click inside that folder and select ''Create->C# Script''. Name the new script ''Pickable'', double-click it to open the editor and add the following method to the class that appears: void OnTriggerEnter(Collider col) { if (col.gameObject.tag == "Player") { col.gameObject.SendMessage ("Pickup"); Destroy (gameObject); } } Save the code (Ctrl-S) and back in the scene, select your object and in the **Inspector** press **Add Component** where you can use the search to find the ''Pickable'' script. Add it. - **Tag the Player** To be able to identify the ''First Person Controller'' game object as the player, you have to give it a named tag. Select this game object in the scene and in the **Inspector** find the ''Tag'' property near the top. Select ''Player'' from a drop-down list of available tags. Now it is easy to "ask" this game object whether it's actually the player. - **Test Collision** Hit **Play**, you should be able to walk around and when you collide with the object it should get destroyed. However, you will see an error stating that "SendMessage Pickup has no receiver". This is because your object has sent a message to the player, expecting a method there with a matching name. We will add this method next. - **Create Inventory Behavior** In the same way you created the new ''Pickable'' script, create another C# script in your script folder called ''Inventory''. Edit this script in the following way: - Add a public member variable to hold a sound: public AudioClip pickupSound; - Add a method, with the name of the pickup message, to play the sound when called: void Pickup() { AudioSource.PlayClipAtPoint (pickupSound, transform.position); }Save the code (Ctrl-S) and back in the scene, select your ''First Person Controller'' game object and in the **Inspector** press **Add Component** where you can use the search to find the ''Inventory'' script. Add it. - **Test Inventory Behavior** Once you have added the ''Inventory'' behavior to your player, you have to associate the ''pickupSound'' variable of the ''Inventory'' component in the **Inspector** panel with a sound asset. You can use whatever sound effect you like. You just have to make sure that the sound file is somewhere under the Unity ''Assets'' folder so that you can browse to it. You can either fill in the value for the sound file by pressing the litle target circle next to the edit box of the ''Pickup Sound'' property, or you can drag a sound from the **Project** panel right into the edit box. After you have provided the sound, you should play the scene and make sure you hear it when the player runs into the objet. - **Make a Pickable Object Prefab** In order to create multiple instances of your object, that now includes a behavior for being picked up, you can turn it into a **Prefab**. In the **Project** panel, navigate to your ''VIEN'' folder and create a new sub-folder called ''Prefabs''. Open that empty folder. Now drag the working instance of your object in the scene into this ''Prefabs'' folder (you are essentially storing the complete configuration of your game object into a template kind of structure that Unity calls a **Prefab**). Change the name of your new prefab object in the **Projects** panel into ''PickableObject'' or something like that (notice that the name also changes up in the scene). Now you can drag this prefab into your scene as many times as you want to make multiple copies of it. If you wish to change any properties in all of them simultaneously, you can select the prefab instead of an object instance and use the **Inspector** to edit a property that then gets propagated to all instances of that prefab. - **Add a Counter to Inventory** You should do this on your own. Maintain a state in the ''Inventory'' class that knows how many objects have been picked up. Display this number on the screen. To have a class write something onto the GUI, you override the ''void OnGUI()'' method of that class (inherited from ''MonoBehavior''. This method gets called whenever the GUI gets updated by Unity. Here is an example of that method being used to write a sample number on the GUI: void OnGUI() { int number = 2; GUI.Label(new Rect(0,0,Screen.width, Screen.height),"Number:"+number.ToString()); } - **Extend your Scene** From here you can go wild with making your scene interesting!