Have you ever wondered how do games localize their games? what do we mean by localization? Localization is when you add multiple language support in your game. What if a player does not understand English but rather Arabic? Can we make a game that can run with multiple languages? With Unity, the answer is simply YES! Here are the simplest way you can make your game support multiple languages.
Once you import the localization package from Unity’s Package Manager you need to start setting up Unity’s Localization system by going to the Project Settings and then Localization. From there, click on Locale Generator. This where you will be presented with all the languages that Unity supports and all what you have to do is to check the languages that you want to support and press Generate Locales.
Figure 1: Arabic and English support are the selected Locales
Once you do that you will see the following two locales appearing in the available locales windows in the project settings:
Figure 2: Arabic and English appearing as the available locales
From there, all what you have to do is to create your Localization Table. Go to Window, Asset Management and then Localization Tables. From there Click on New Table Collection
Figure 3: The creation of localization tables
Give you table a name and click on Create String Table Collection. The table will be created and now you are ready to start creating your text and translations.
Lets say you have a UI Button that starts the game, the text on the button says “Start Game” and you want the player to switch the language and once the language is switched is should display “ابدأ اللعبة” in arabic. All what you need to do is to add a key and the sentence in the languages you support as shown in figure 4.
Figure 4: Localizing “Start Game” in the Localization Table
As you can see in figure 4. the key is a unique identifier for that translation and then under each column that corresponds to a language the translation is mentioned appropriately.
Now, how do we link that to the UI Text of the button? It is really simple to do that. All what you have to do is you need to add a component to the UI Text that is childed to the UI Button called “Localize String Event”. In that component, you need to do three things:
In the String Reference, select from the table the key corresponding to the text you want to have in that button.
In Element 0, Reference the Text component existing on that game object.
In the Update String Event, add an event and reference the Text Component and then in the functions select the text property of the Text Component. This will allow the localization table to add the appropriate text depending on the selected language to the Text component.
Figure 5: the setup of the Localize String Event
Once you do that, it should work out of the box; and here is how it looks like this:
One of the things that fascinate me about video games is the ability to tell stories and allow the player to be part of it. These immersive experiences are what make video games epic. I remember the tears I shed when General Shepard killed Ghost and Roach in cold blood after having a very tough time in the mission titled “Loose Ends” in Call of Duty: Modern Warfare 2. I was too mad at Shepard and I remember that I cried a lot when that cutscene was playing. Since that moment, my dream of creating a video game that tells an epic story has started. Today, that dream is in progress and I am finally ready to tell a story of mine
This is where Project Osiris comes in!
Yes, Project Osiris is a code name of a video game that I started developing on April 2nd, 2021 that tells an epic story about the ancient Egyptian civilization. I don’t want to get into details about the game in order not to spoil the idea but through the game the player will take a role of an Egyptian god who tries to restore balance in Egypt. The player will engage in epic battles, fight big monsters from the Egyptian Mythology and spar 1:1 with Egypt’s greatest gods.
I started with working on a high concept document that lays out the game in terms of functionality, enemy types and powers that each will poses. I have to say designing a game from scratch is challenging but fun. At the moment, I am working on the Game Design Document (GDD). I should be able to complete the full design of the game by the end of April 2021.
However, being a geek and someone who cant stop writing code, I jumped into unity and I started prototyping a basic third person controller. Yes, the game will provide the player with a third person view of the player. To make the game easy to port into other platforms, I used Unity’s new Input System in order to layout the controls for the keyboard. This is how the basic layout that I started with looks like:
Figure 1: The player input layout
The use of Unity’s new input system will allow me in the future to enable control use with ease and without doing any changes to the code. I have future plans into building the game for consoles, but it is too early to decide now on this. As you can see in figure 1, the player can move using the WASD buttons and can jump using the space bar and look around using the mouse. the MouseLook action is then liked to the Virtual Camera that is responsible for tracking the player. I did this by adding a Cinemachine Input provider component into the virtual camera, this will override the needs for the standard input.
Figure 2: Cinmachine Input Provider component
With this setup, I created a player character with the most complex graphics that any GPU can ever handle!
Figure 3: The player character
At this point I was ready to start coding a simple third person controller. For this case, I wanted to use Unity’s character controller to handle the movement and the ground check for me. I started with creating the below variables:
Figure 4: The controller’s variables
Afterwards, I initialized the input system for player controls and some other variables in the start and awake functions
Figure 5: The unity functions and initializations
You may have noticed that I tend to comment my code a lot. I do this because it is very important to make your code understandable by other people who may review you code or even be working with you. Also, a great man once said:
Always comment your code as if the one reviewing it is a serial killer who knows where you live!
Let’s get back to the code and examine the Move() function This is where the magic is happening. this function is divided into to major parts. The part where the player moves and we align the player forward vector with the camera’s direction and the other is to handle the jump. Here is the code that makes the player move in the direction of the camera:
Figure 6: The player movement section with respect to the camera’s direction
The code looks straight forward but I want to explain a bit the lie where I calculate the target angle. Imagine the the player is looking at a direction, call it x, now put a point at that line, then imagine that the camera is looking at another direction and plot a point on that line and call it y. These two line will intersect at some point and you want to calculate the angle between those two lines because this is the angle in which the player should turn in order to be aligned with the camera’s forward direction. The function that can calculate the angle for us is an Atan2 function.
Figure 7: Atan2 Function
As you can see in figure 7, the angle can be calculated by the function atan2(y, x). However, in our case the atan2 function will look like this atan2(x,y). The reason behind this is that we are facing the forward direction and according to tan part in sohcahtoa, the tan of theta is calculated by the opposite/Adjacent. Since we are looking forward (the direction of the positive Y axis) The opposite of the angle is a line parallel to the X-axis and the Adjacent is the Y-axis as shown in the diagram below.
Figure 8: the calculation of the the new theta
After calculating the target angle, I used the SmoothDampAngle function offered by Unity to smoothen the angle. Without the use of this function the player will snap to the new rotation, instead I wanted the player to have a smooth transition when rotating the desired direction.
The final thing that I did is to code the functionality for jumping which is straight forward.
Figure 9: The jumping code
The reason why I am caching the value of the yVelocity in a global variable is that I don’t want the y position to be overwritten every frame when the movement direction is calculated otherwise the player will jump in the current frame and will snap to the group in the frame right after it.
With this, I was able to create a basic third person controller that works like a charm. There are so many other things that I am planning on implementing but these are for a later blog post. Here is how it looks like:
One of the things that make video games amazing is the ability to tell and experience stories. You can make the player engage with the game’s protagonist; or have compassion on the game’s antagonist. Back in the days of PlayStation 1, I was fascinated by the idea of having cut scenes in the game. It never came into my mind that you can actually play some kind of movies in a game. I used to call those cartoons 🙂 For many years, the idea of telling epic stories in games has haunted my thought. The Call of Duty Modern Warfare trilogy were just brilliant in the way they tell the story during the loading screen. The amazing story of God of War and how you feel bad for Kratos and so many other games that tell breath taking stories. All of these experiences and stories are told during cutscenes! Back in school I used to make short films and visual effects using Adobe After Effects and I always dreamed of being able to do something like this but in video games. Today I am telling you that this dream came true, and I finally was able to create my first cutscene and story in a video game using Unity3D.
Making cutscenes in Unity has been an absolute thrill and it is all thanks to GameDevHQ’s amazing Cinematography course offer to its Pro members. For this project I used GDHQ’s Filebase. If you don’t know what Filebase is, then you are missing alot. Filebase is this insane library of assets for Unity that you can use to make games. They have everything that you can imagine, in AAA quality.
To start with, you have to have some kind of imagination to how the scenes will look like, what the environment is and how you want your camera’s to pan through the scene. This can be all found in the director’s note. Usually these notes imagine the scene through simple sketches along with camera movement guides. They put you on a starting position to getting the correct shots of you scene.
Figure 1: Director’s Notes of the entry scene
In the above image you can see that the director is plotting the entry scene of the level. The director wants the player character to glide down the rope and you can see in the notes and in the arrow that the camera should pan downwards. Then there should be a shot from a far showing the player dropping down in the dark corner of the room. From that point, the animators should start animating the scene a 3D software, export it to a format that Unity can understand and then it is time to import that animation clip into Unity. This is where the all the magic happens.
After importing the animation clip, you want to plan your shots, how do you know what shots to take and for how long? You guessed it, from the director’s notes. You want to do exactly as the director has intended. The first thing I did here is that I started planning for the shots. I creating multiple Virtual Cameras that are scattered across the scene.
Figure 2: Virtual Camera’s scattered in the scene
In figure 2 you can see the “CM” icons, these are all virtual camera positioned at a starting place where I want the camera to start panning from. The one that is selected above is the camera that pans down while the player character is gliding down the rope.
Figure 3: A director’s note of another shot
Figure 4: Another Virtual Camera for another shot in the same scene
Figure 4 is another shot taken from a different angle of the entry scene. Now when this shot is active, the player should be already on the ground and according to the director’s notes in figure 3. This is basically the approach that you want to take when planning out your shots before you start composing them. For each shot, I had a camera ready to be animated to give the panning effect desired by the director as shown in figure 5.
Figure 5: How the hierarchy looks like after adding all the camera for a scene
Now, Here comes the million dollar question; how do I compose the shot? How do I get all of these shots together and pan the camera. The first thought is that this has to be a very complex way and it would take days to compose only one shot in Unity. This is not the case in Unity. Unity has this module called Timeline which is an amazing tool to compose your shots, just like Adobe Premiere or Final Cut. IT IS THAT SIMPLE!
In figure 5, you can see a game object called Into_Cutscene. This object I added a Playable Director component. This component holds the timeline. From here, I referenced all the virtual cameras in the timeline and starting animating them just like any professional video editing software. You can see in figure 6 how the timeline looks like, and if you are a video editor, you will be able to relate to it alot!
Figure 6: Unity’s Timeline in action
In figure 6, you can see that we can control the camera movement through animation, we can control the audio as in music of voice over. I can also control other game objects in the scene! How awesome is that! After a scene is over, the game is triggered and the user can start controlling the player character.
Another thing that I did was to trigger cutscenes to play when the player reaches a certain point. I used a box collider, as demonstrated in figure 7, that I positioned in a scene and when the player enters that collider, it triggers the cutscene.
Figure 7: A box collider that triggers a scene.
The code to trigger the scene is the following:
public class GrabKeyCardActivation : MonoBehaviour
{
public GameObject sleepingGuardCutScene;
private void OnTriggerEnter(Collider other)
{
if(other.tag.Equals("Player"))
{
if (sleepingGuardCutScene != null)
sleepingGuardCutScene.SetActive(true);
GameManager.Instance.HasCard = true;
}
}
}
This is the approach that I used in creating cutscenes in the game. At the end, this is what I came up with:
Figure 8: The cutscene with the level
I have to say, working on this mini game has been an absolute thrill to me and I cant wait to start working on the stories that I want to tell!