Game Design Tips #16 – [Unity + C#] Linear Interpolation

It’s been an awfully long time since my last post – blame coursework! I have a few weeks to get a couple of posts in before I have more coursework and then exams, so enjoy me while I’m here.

If you’ve coded at all with Unity, you’ve probably noticed its API has a lot of methods called ‘lerp’. Mathf.Lerp(), Vector3.Lerp(), Color.Lerp(); all of these are very helpful methods. But what exactly do they do, and how should we be using them properly? First of all, I’m gonna go ahead and show you how they’re meant to be used, then I’m gonna break them horribly to show you cheap ways of doing cool stuff.

How to use Lerp without being hacky

‘Linear Interpolation’ is a lot of syllables to get your head around, so first of all, let me explain what it means. Let’s say we have a thing. We want the thing to change into another thing at a constant (linear) rate. This is what linear interpolation does – it takes a vector, colour, float, you name it, and changes it into a new one.

tip-16_img01

This is the lerp method for Vector3. We pass in startPos, endPos (both Vector3s) and a float parameter; this parameter should be between 0.0 and 1.0. When time = 0.0, the object’s position will be 100% at startPos and 0% at endPos, and when time = 1.0, it will be placed at 0% startPos and 100% endPos. It’s easiest to demonstrate what lerp is doing when talking about Color.Lerp(), so we can use a pretty diagram:

tip-16_img02

Here, the square represents the RGB colour scale found in Unity’s colour picker (well, flipped horizontally). When we use Color.Lerp() in this way, when the third parameter is 0, the method returns a red colour (#ff0000 in hexadecimal RGB colour representation) and when the parameter is 1, we get full white (#ffffff). At any point in between, we blend between the two linearly – at 0.5, we’ll get a pink-ish colour exactly halfway between red and white on the RGB scale (#ff7f7f roughly) and at 0.75, we get something mostly white but retaining a tiny bit of red (about #ffbfbf).

Once we understand what lerp is doing when we pass in certain numbers, we can pull everything together cleanly into a coroutine.

tip-16_img03

We pass in the sprite renderer whose colour will change, the colour it will change to and how long it will take to change. The coroutine automatically works out all of the needed variables for the user, so we don’t need to pass in the start colour. Every frame, we set the new colour of the renderer based on what percentage the current time is between the start and end times. Simple! The final step is to ensure the colour gets set to the end colour exactly, since the loop might have exited only 99.9% through the lerp (it’s never going to be noticeable to the human eye, but I’m doing this for the sake of completeness and to avoid triggering anyone’s OCD).

How to use Lerp badly

Now that we know how to use lerp properly, it’s time to be a terrible person! I’ll show you one popular way of using lerp badly. Assume, for the following example, that the ‘speed’ variable is set to 0.1f.

tip-16_img04

tip-16_img05

I’ve tried to illustrate what happens on each frame here. At the start (on the first time interval), the sprite colour is at its original colour. At the second time interval (0.1s after starting), we have moved 10% from the original position towards the final position. This is easy to understand – we move 10% of the way between full red and full white (assuming the original colour was red and targetCol is white). On the next interval, we have travelled another 10%. However, the starting point was not the original red – it was 10% towards white. This means the current colour is 10% between the last colour and full white; it is now 19% towards full white. This process continues; rather than moving linearly between red and white, the end result is a curve.

The reason this works is because the time parameter we pass in is always a fraction between 0 and 1, but the start colour is always changing too. It’s not exact, but roughly every 0.1s, the colour will change 10%. The numbers above won’t be precise since the lerp is running every frame, not every 0.1s, but hopefully this gives you an idea of how this blasphemy is working behind the scenes. This isn’t how lerp is intended to be used, but it is a cheap way of moving between vectors, colours or floats on a curve. It’s disgustingly amazing – dismazing, if you will.

It’s also worth noting that if the parameter passed to lerp is set to below 0 or above 1, it will snap up or down to those boundary values. Now you should be a certified lerp expert! I’ve put both versions of the linear interpolation script online for you to download if you’re too lazy to copy them (which is only a problem because I’m too lazy to make them look nice without resorting to taking screenshots. My bad).

Advertisements

Game Design Tips #15 – [General] Staying Sane While Making Games

You have a great idea. This is the one. The one that’s gonna thrust you into the limelight; the one that promises to turn you from a nobody to an auteur overnight. You’ve jotted all your ideas down on paper, got a plan together and you’re ready to get rolling on this massive project. Great! However, the most important thing here is to be realistic. This project probably isn’t going to bring around world peace, and you’re not going to be able to work on it all day and all night. I’ve put together this list of ways you can keep the motivation strong by pacing yourself, in the hope it’ll prevent people from burning themselves out halfway through the project.

Be open to changing your original plan

So you have this 400-page whopper of a plan. Not everything in it is going to be pure gold; odds are, you’ll show it to a friend and they’ll poke out a few holes in your story. I’ve been there (not with 400 pages of stuff though!), and it sure sucks to be told you were wrong, but don’t fret. Your friends are also your customers. More often than not, asking your friends, family or colleagues for feedback will give you valuable insight into what they’re looking for, and it’s crucial to make sure your game idea is viable at an early stage. After all, if your friends are iffy about playing it, then what would the average random person think? Either that, or your plan is perfect, everyone else is wrong, and you should get new friends that appreciate you.

Don’t stay up ridiculous hours to get your game done

I’ve broken this rule at pretty much every game jam I’ve ever gone to, but I’m allowed to be a hypocrite. Really, I mean don’t stay up if you don’t want to. There may come a point where you’re falling behind your schedule and you feel as if just a few more hours would let you get back on track, but that’s not always the case. It’s a trap! Staying up those few hours will likely make you feel tired the next day, which is only going to subtract from your productivity later.

tip_15-01

When you get frustrated, leave it for a while

When you have a bug in your code that just doesn’t want to go away, or there’s a graphical glitch that makes everyone turn purple for no good reason, it’s not a bad idea to leave your desk for an hour or two and come back with a fresh mind. In that time, why not go for a walk? Go get a glass of water, and a snack too. Keeping yourself hydrated and cutting off the cycle of frustration will make development much more pleasant. In any case, if you’re really stuck with your problem, there’s every chance someone else has run into the same problems; the solution can probably be found on a game design forum somewhere.

tip_15-02

If it stops being fun, stop working on it

This point is of the utmost importance. Many times, there will come a point where game development stops being fun; if you have no obligation to continue the project (say, if it’s a personal project and you don’t have legions of fans expecting something of you), then there’s no shame in shelving your progress so far. That said, planning your game in the first place to be a good length is important to avoid this – if you know you’re prone to quitting when development hits the end stages, perhaps your next game should be much shorter. You should always try to avoid circumstances where development isn’t fun, but if it happens, you always have the choice to move on. You can always come back later, but the worst thing that can happen is getting creator’s block – you want to avoid that at all costs.

Game Design Tips #14 – [Unity + C#] Persistent Data

Today I’m gonna talk about how you can save data to disk and read it back later. Unity has a utility built-in for this – they’re called PlayerPrefs – but for anything more than perhaps options and preferences, you’re going to want a more robust system for saving data between scenes within your game or separate game sessions. This is where I jump in and throw a bunch of fancy C# things at you! Note – this system should work on standalone platforms such as Windows, Mac and Linux and mobile platforms, but it won’t work on Web Player builds or platforms such as Samsung TV. I’m not sure if it works on console platforms since I don’t have the resources to develop for any of them and the internet has been unhelpful in this regard, but oh well. Time to get started!

There is a lot of motivation for wanting to save data to disk; high scores, player progress, and player-customised assets are all types of data we want to make persistent. I’ll be showing you how to achieve this in Unity using C#. To do this, we need to package up the data we’re going to save into its own class.

tip_14-01

We’re going to put this portion of code right below the SaveStuff script, which we’ll be writing next. For the SavableObject class, we’ve made a bunch of variables that we want saving to disk. In this example, imagine there’s a guy named Bob, and that he wants to remember his own name, how many bananas he’s holding, how long he’s been dancing (measured in hours – he’s an active bloke) and whether he’s made of wood. From this, we can only assume the following: he’s forgetful, probably a fan of potassium, potentially flexible, and doesn’t remember if he’s a real boy. But my game doesn’t know that! That’s why I’m going to save all this crucial information to disk.

tip_14-02

THIS is my all-knowing, all-powerful SaveStuff script. Let’s gloss over all the important things this script is doing – I’m sure you’ll be able to fill in the rest. It may get a tad boring, but bear with me, because saving things is actually really fun. Honest.

First of all, you can see a small snippet of the SavableObject class at the bottom of the file to show you where I’d place it. It has a [Serializable] attribute (line 36) – in order to use this, we need to import the System namespace (line 2). In the Start() method, we make our new SavableObject and specify Bob’s name as “John” (turns out he’s really forgetful) and his body’s wood status to “true”. The constructor for SavableObject already specified default values for numberOfBananas and danceTimer, so we won’t have to worry about those. Oh, and System.IO is imported for use of FileStream and File, whereas System.Every.Bloody.Word.In.The.English.Language is used for BinaryFormatter. Now let’s save Bob’s status.

Here’s the part where I attempt to make C# exciting! SaveMyStuff() is now going to do a bunch of fabulous things. We make a fun little BinaryFormatter we’ll be using shortly and then create a wonderful, happy file called “myThings.dat”. One thing to note here – I was dumb when writing this example, so it should actually be “/myThings.dat” to ensure the file goes inside the folder at Application.persistentDataPath. We serialise the data from the SavableObject we made earlier (using rainbows), turning it into a binary string that an ordinary user wouldn’t be able to comprehend if they opened the file manually. We then close the file up and wait a second before calling LoadMyStuff() on our loader object (in practice, this second’s worth of waiting may be replaced by an arbitrary amount of time, perhaps even including closing the game and reopening it). Closing the file is a very important step, since C# places a ‘lock’ on the file while it’s being accessed, and trying to access it from elsewhere at the same time – while it’s locked – would be reeeeally bad. Got all that? Good! I told you C# was fun! Now let’s introduce the LoadStuff class and go over its features.

Oh, by the way, Application.persistentDataPath is a ‘default’ filepath that varies by export platform. Most games that use Unity will probably use this default path plus a bit of extra filename appended to it (as I have here). The filepath also contains the company name and game name, both determined in the PlayerSettings in the Editor (found at Edit/Project Settings/Player).

tip_14-03

This script happens to be pretty similar to SaveStuff, but does things backwards. In LoadMyStuff(), which happened to be called by SaveStuff (it doesn’t matter what called this method in practice, I just did that for convenience), I first check if the file “myThings.dat” exist. If it does, I create all the necessary things, as with SaveMyStuff(), but this time I’m opening the file instead of creating it. That’s why it was necessary to check that the file exists, because trying to open it if it didn’t would make things cry/crash/explode. Now that the file’s open, I can deserialise its contents, un-binary format it and stick it back into a SavableObject. Then all there is to do is grab the variables out of that object, plonk them all into a horrible example of how not to concatenate strings together, and watch the Console output all our data with no errors whatsoever.

tip_14-04

Congratulations, you’ve just saved to disk and loaded up that data back from disk! It’s a very useful feature you’ll find yourself using in a variety of places; from remembering player’s preferred options to keeping track of game progress, the possible uses of saving to disk are endless.

 

Game Design Tips #13 – [Unity] ScriptableObjects and Custom Project Gizmos

It’s been a while since my last Game Design Tip, but I’m back and ready to show off some cool things I started using very recently. Ever wanted to save data as an asset in Unity? Turns out, there’s a dead easy way to do that. I’d heard of ScriptableObjects before, but not used them; they’re a godsend for any task where you just care about keeping hold of static data for something – weapons, enemies, item drops, you name it.

I’ll take an example I was working on the other day. I have a load of guns that the player may own, each with their own cooldown rates, damage, clip size and whatnot. My strategy at the time would have been to create a MonoBehaviour script that holds a bunch of public variables, stick that script on a bunch of GameObjects and tweak their variables individually, then save them all as prefabs. Upon needing to read the data, I’d instantiate one of those objects (or have them all instantiated at level start), then read off all the variables. In doing so, I’d waste a bunch of memory loading up GameObjects whose sole purpose was to hold data, clogging up the RAM with redundant data and making the garbage collector mad.

tip_13-01

That was dumb.

Instead, I should have used ScriptableObjects, something Unity provides for this exact purpose. Instead of extending MonoBehaviour, we’re first of all going to extend ScriptableObject. That’s going to tell Unity that this script is special, just like every one of my readers. That’s my flattery quota for the day met!

tip_13-02

You’ll also notice we gave the entire class the [Serializable] attribute. This is provided by the System namespace (hence, that’s included on line 2) and tells Unity we’ll want it to do stuff to it to make it visible in the Inspector. In reality, it’s a lot more complex than that, but we don’t care for now, do we? We just want our data saved. Oh, and I’ve stuck this class in the WeaponClasses namespace for the hell of it, but you can ignore that if you so wish. In my example, WeaponType is just an enum to deduce which class the weapon falls under.

Now that we’ve gone about making our data serializable, we need a way to make these new Weapon objects. There’s probably many ways to do this, but I’ve used a bit of Editor scripting to get the job done. It might look a bit alien at first, but it’ll all start to come together soon.

tip_13-03

This is a brand-new script which doesn’t extend Monobehaviour, ScriptableObject etc. It just needs to import UnityEngine and UnityEditor, and the script must be placed under Assets/Editor. We use the [MenuItem] attribute to add a lovely menu entry for making new weapons – now, we’ll be able to click ‘Assets’ on the toolbar, hover over ‘Create’ and find ‘Weapon’ listed underneath all the usual entries. Clicking this places a brand-spanking-new Weapon under the path defined in the script (line 14) and focuses Unity on the new Weapon in the Project Window (lines 16 and 17). Just a word of warning – it’ll replace anything called NewWeapon.asset in that directory, so I’d rename it straight away! Now you’ll have an awesome new Weapon instance you can reference in your scripts without having to attach it to some empty GameObject.

tip_13-04

Not a typo, just a really fun thing for gunning people down.

I did a little more processing with mine using an additional, more complex Editor script to hide certain variables based on the type of weapon, but this is basically what you get when you click on one of your Weapon instances in the Project window. We’re done with ScriptableObjects now, but let’s go one step further and make a cool gizmo for our Weapons.

Weapon icon

This is the icon I’ll be using. It’s dead easy to tell Unity to use this for our Weapons; just save this under the exact name “Weapon icon.png” or “Weapon icon.tif” – only .png and .tif files are allowed. The syntax is [Class Name] [single space] [the word “icon”] [.png/.tif]. Super simple stuff!

tip_13-05

Now we have pretty-looking icons for our Weapons and a clean way to save data for each Weapon. Unfortunately, it doesn’t make them look different in the Inspector, but at least they have an icon in the Project view that makes them easier to find. I hope this has been helpful, and I’ll be back soon with more tips.

Game Design Tips #12 – Object Pooling

I’ve given up all hope of this being a daily series, but fret not! I’ll still be posting tips whenever I get the chance. Obviously being back at uni will probably mean I’m a little less frequent with updates, but I’ll try and keep up my usual blog regime of posting whenever I’ve done any interesting game development. On that note, the first Warwick Game Design Society two-week challenge just finished, and the theme was ‘Retro’. I opted for a 2D kind-of-platformer starring an edgy 90’s hipster kid. Obviously. You can read about it in my previous post. Enough of that though, it’s time for today’s tip!

What is Object Pooling?

Object pooling is a common technique used by developers to make their games a bit more efficient. On desktop and console platforms, it’s not exactly necessary but it’s still a good habit to get into; mobile platforms will be much slower without it. The technique isn’t bound to any one platform, engine or language though, so you non-Unity people out there can breathe a sigh of relief. I’ll still be using good ‘ol Unity and C# for my examples though.

tip_12-03

These are not the pools you’re looking for.

Instantiation and destruction of objects can be expensive processes, since they involve a lot of memory allocation and garbage collection respectively. A system where we just had a bunch of one item already instantiated at start (enemies, projectiles, you name it) and we only make them active when needed would alleviate this problem; object pools do just this. By setting up a list of an item and populating the list with instantiated, inactive objects, we’ve taken all of the instantiation overhead at level load and never destroy anything until the level ends. As we all know, destruction is bad because it rouses the garbage collector.

Why use it?

By removing the overhead of instantiating and destroying objects and instead activating and deactivating them, our game is now much faster at stuff like spawning and removing things. It’s significant on mobile platforms when we can’t really be affording to waste CPU cycles. There is of course a RAM overhead as all the objects in the pool (and the list storing the pool itself) need to stay live in memory, so on platforms especially restricted by memory, another approach may work better for you.

Another reason to use pooling is that it gives more control to the game programmer. Who the hell knows what instantiation and destruction might be doing in the background? If you, the programmer, create your own object pooling system, then you more fully know the finer details of how the pool operates. You can also tweak it to your exact, bespoke needs rather than relying on a general-purpose method that probably carries redundant overhead with it.

How do I implement one?

Simple! I’ll be creating an ObjectPool class that will constitute the pool itself, and a PoolController that handles putting items into the pool and taking items out of the pool. Note, the ObjectPool class doesn’t inherit MonoBehaviour, so we can’t just stick this as a Component onto a GameObject – we’ll have to create ObjectPool objects inside a PoolController (which does inherit MonoBehaviour, and should be a component on some GameObject). I’ll explain the theory behind various types of pool, but I’ll only show an example of the last type.

Bounded-size non-generic ObjectPool

The concept behind a fixed-size pool is simple – we construct a list and fill it with a specified number of objects at level load – this number does not change during the program’s lifespan. The advantage is that we always know exactly how many objects are floating around. However, we may run out of objects when we try and get one from the pool. Most implementations of this will define what type they’re holding hard-coded into the pool (for example, in Unity, I’d make my pool hold GameObjects, e.g. List<GameObject>, and all methods will take GameObjects as parameters or return GameObjects). The problem with this is that we can’t guarantee type safety – at level start, we might be able to add an enemy game object, then add a particle game object, then a player game object, and so on all to the same pool. That means we can’t guarantee the items we receive from the pool are of any one type, because we might have added in any random type of object.

It’s also worth noting that this version actually works better if implemented with an array holding the GameObjects rather than a list. I won’t delve too far into why, but it’s to do with asymptotic running times of certain operations (specifically, you can either add and remove items with an array quicker than with a list, or you can implement an array in less space than a list – it’s hard to explain here). Look up Big O notation for more information. The next example will assume you’ve used a list though, as the next two versions work better with lists than arrays.

Bounded-size generic ObjectPool

We can modify this approach to use generic types.  Using generics prohibits adding anything that does not match the original type definition –  we’d define our list internally in the ObjectPool class as a List<T> instead of a List<GameObject>, and define our class as public class ObjectPool<T> where T : MonoBehaviour, then we can only add one type of object at runtime to any one pool in the PoolController class. This means:

  • public class ObjectPool<T> where T : MonoBehaviour means this pool can hold any kind of GameObject, but can only hold one type of GameObject at a time. We instantiate the ObjectPool with new ObjectPool<YourObjectType>().
  • List<T> means the object pool’s internal list holds that same type of object.

It’s hard to explain, but you should see what I mean in the examples below.

If you’ve never touched on generic programming before and you’re confused or would like to know more, check out the C# reference if you’re using Unity, or the Java reference for other uses. Those are the languages I’ve used with generics, but your choice of language or engine may also support generic programming. Generics can turn nasty runtime bugs into compile-time hiccups, so I’d recommend using them where it’s sensible to.

Unbounded generic ObjectPool

I’ll show an example of one of these below. The other examples of ObjectPools have had the problem of possibly running out of objects. To avoid this, we can make our object pool have a variable length; by allowing us to add another object to the pool if we’ve run out, we suffer the overhead of instantiation, but we still avoid garbage collection since it’s not destroyed. This too has drawbacks – if we have a spike in the middle of the game where we need, say, 500 enemies, we’ll end up creating more enemies dynamically and once used and deactivated, they’ll stay in the pool forever. For platforms bounded by RAM size, it’s not exactly ideal, and you’d be best off sticking with the previous version. We could improve this solution by creating some kind of way of destroying objects when the game is idle, and possible framerate drops are acceptable (say, when a menu is open), however that can get very complicated so I won’t go into it here.

ObjectPool.cs

tip_12_01

PoolController.cs

tip_12_02

This example assumes you have some sort of Enemy type already defined. We set up an ObjectPool in PoolController for every type of object we want to pool – in this example, enemies and particles. We have also assigned which objects we’ll be adding to the pool (the enemy and particle variables). At start, we instantiate a given number of objects for each pool (I’ve only shown this for the enemy pool though; you’d have a for-loop for every pool) – this number is defined in Unity’s Inspector. When we want to retrieve an object from a given pool from some other script (I’ve provided the poolController variable for this purpose, so we can type PoolController.poolController to reference the singular PoolController we’ll have in the scene), we use the GetEnemy() method (or GetParticle(), but I’ve not written it since it’s mostly the same as GetEnemy()). When we’ve finished using an object and would usually destroy it, we call DeactivateObject() instead, causing it to stay in the pool but be inactive in the scene.

I hope this has given you a deeper understanding of object pools. If you have any questions, feel free to leave a comment below.

A Game Design Tip a Day #11 – [Unity Physics] 2D Physics Effectors

This series is quite obviously no longer daily, since I’ve not updated my blog since the start of September. However, now that I actually have free time (Metal Gear Solid V came out, then I moved into my new flat ready for the second year of uni, hence the lack of blog time), I’ll try my best to continue the series. That is, until term starts and assignments start hitting me at Mach 3 speed.

2D Physics Effectors are pretty new in Unity. You could be forgiven for not really knowing much about them, since they came out with little fanfare back when Unity 5 launched and got largely drowned out by all the hype about physically-based rendering, global illumination and whatnot. For you guys still using Unity for your 2D games, these effectors will probably be a godsend to you. I’ll be covering all four of them, and to accompany this post, I’ve made a neat little demo scene just below for you to visually see what each effector does. Oh how I spoil you lot! I’ll also include the entire source project in case you want to tinker around with it.

Gimme the demo scene!

I tried using Unity’s WebGL export option to make it easier for people to view the demo scene, but it’s slow as hell to compile and only really works if you just happen to have a server ready to host it on. Instead, I’ll have to put up a series of download links, but hopefully I can manifest an easier way to do it next time. All the images below are from the demo, because there’s no real way to show the effectors in action unless they’re animated.

Area Effectors

tip_a_day_11_01

This type of effector is handy if you have something like wind in your game and you want objects to be forced in some direction while they’re inside an area. It uses a trigger collider to detect Rigidbody2D objects and then adds whatever force you’ve specified (you provide a magnitude and an angle, since this is in 2D). You can also supply both regular and angular drag to objects in the area effector, and you can specify where the force is applied with the ‘Force Target’ option; choose the rigidbody and the force is applied to the centre of mass and no torque (turning effect) will result, or choose the collider and it’ll be applied to the collider’s centre point, which results in a torque if the collider centre happens to be different to the centre of mass’ position.

Point Effectors

tip_a_day_11_02

Even wanted a magnet in your game? Then this is the effector for you. This one works by defining a point in 2D space (either the rigidbody position or collider position) and providing an outward force from that point to whatever objects are inside the trigger. You can even provide a negative magnitude and your Point Effector will act like a tiny planet. Most of the other options are straightforward, but ‘Force Mode’ is pretty important – set it to ‘Constant’ and the same force is applied to objects, no matter how far away they are from the effector. Set it to ‘Inverse Linear’ or ‘Inverse Squared’, and the attraction/repulsion will get weaker the further an object is from the Point Effector. ‘Inverse Squared’ will most accurately represent real-life gravity.

Surface Effectors

tip_a_day_11_03

These ones may as well be called Conveyor Belt Effectors. Plonk one of these on a surface and change the ‘Speed’ parameter to change how fast these things move, with negative speeds causing a change in direction. You can add a bit of variation to the speed too, in case you want a conveyor belt that jerks when it moves.

Platform Effectors

tip_a_day_11_04

Platform Effectors are a simple way of adding one-way collision to platforms, or you can turn off the one-way collision and have it act as a platform without friction or bounce on the sides. You can also set the maximum angle for what is considered a ‘side’ for the friction and bounce properties.

A Game Design Tip a Day #10 – [Unity Editor] Preferences

This fledgling little series of mine has reached 10 tips already! I’ve still got heaps more to throw at you, so stay tuned! If you’re liking the series so far, then go tell your friends, tell your neighbours, tell your cat. If Mr. Snuggles doesn’t start reading these tips, I’ll be mad! Today’s tip is a bit on the short side, but covers a few useful options you’ll likely end up using.

For some people that like to customise everything to their liking, this menu is the first place you’ll go as soon as you’ve downloaded Unity. But others probably don’t realise how useful some of the features are, or don’t know where to find the goddamn thing (hint: it’s buried in Edit -> Preferences…). I’ll now go over the various tabs on the left-hand side, ignoring General, GI Cache and Cache Server because they’re not where the juicy stuff hides.

External Tools

tip_a_day_10

One thing I completely neglected to mention in the previous tip (the one where I called MonoDevelop terrible a lot) was how to set a different IDE as your preferred one. This is where you can do so – in the External Script Editor drop-down, by default you’ll see MonoDevelop and Browse; the latter allows you to check for a real IDE. Editor Attaching sets whether the external IDE is responsible for debugging, so you’ll want to check this box if you’re using Visual Studio. You can also set which application opens up images – it may be helpful to set this as Photoshop or GIMP to allow for quick image editing, since the default program on your system for opening images is probably just a photo viewer of some kind. Finally, this is where you point Unity to your system’s Android SDK if you’re developing for mobile.

Colors

tip_a_day_10_02

You can safely ignore most of the colours on here, unless you really want to customise everything. What I want to highlight here is the topmost colour option – Playmode tint. Often while working in the editor, you’ll forget that you’re currently in play mode and modify a bunch of variables on all your components, only to realise you’re not in edit mode and those changes will be reverted. Then you’ll curse loudly, grumble and tweak them all over again. If you changed Playmode tint to something strikingly obvious, like red, then you’ll definitely notice much more often when you’re in play mode, because the entire editor changes to that colour. It’s much more obvious than the slightly different grey used by default. It’s only a shame you can’t also change the spelling of the header to “Colours”, the correct way of spelling it. Sigh.

Keys

tip_a_day_10_03

The last thing doesn’t require much of an explanation, but you can rebind all the keys used to navigate the editor. It’s very handy if there’s a specific key you’d rather use for a given task.