Simple 3rd Person Camera Controller in Unity




Someone in the Unity Forums asked for help with a 3rd person camera controller. I decided to post my code there for him/her, and so I'm going to post it here, too. This is a javascript that will track an object in the world and move the camera towards it if the object gets too far away.

I like code examples that are simple and easy to read, and while this code could be even more stripped down, it's pretty simple. I included comments for every line.

// Put this script on a GameObject with your camera and a character controller on it.

var target: GameObject;  // Assign this to your player
var maxDist = 20.0; // distance before triggering follow
var minDist = 10.0; // distance before untriggering follow
var speed = 6.0;  // Should be set to the same speed as your character
private var acc = 0.0; // Amount of movement on the camera. this starts at 0 and builds until it reaches speed. 

function LateUpdate () // Had to be late update becuase it was studdering otherwise.  
	{
	var myDist = 0; // This variable is a (changing) threshhold to determine whether or not our camera should be moving or not. 
	// when the camera is not moving (acc==0), it is asigned to maxDist. 
	// Once the camera starts moving, we set myDist to minDist. This means the camera needs to get even CLOSER to the player before it stops
	// moving than it took to trigger it in the first place. this behavior does 2 things: 
	// When the camera is stopped, it lets the character walk around a bit before the cam starts to move. 
	// When the camera is moving, it prevents studdering as the character walks in-and-out of threshold. 
	
	if (acc == 0) // If the camera	 is not moving
		{
		myDist = maxDist; // Set our threshhold to Max
		}
	else // else the camera IS moving
		{
		myDist = minDist; // set threshold to min
		}
	transform.LookAt(target.transform);  // Aim at the character 
	
	var idist = Vector3.Distance(transform.position, target.transform.position); // Get distance between the cam and the player
	
	if (idist > myDist) // If distance beyond our current threshold 
		{
		acc = Mathf.Min(acc + 2, speed); // accelerate by a fixed amount (+2) until we're at max speed (speed)
		}
	else  // Else the distance is inside our threshold 
		{
		acc = Mathf.Max(acc - 2, 0);  // deacclerate by (-2) until we're at stopped (0).
		}

if (acc > 0) // If we're moving
		{
	    //transform.Translate(0, 0,  acc	 * Time.deltaTime); // Old way without collision; 
		
		//--VV-- This turns the local angle into a world coord that can be passed to the Move command 
		var iangle = transform.TransformDirection(Vector3(0,0, acc * Time.deltaTime));  
		//--AA--
		var controller : CharacterController = GetComponent(CharacterController); // Get controller 
		var flags = controller.Move(iangle);// Move with collision but without gravity. 
		}
	}


And that's all!

Creating elevators in Unity




Unity's Character Controller is an example of what makes Unity great. It's a part of Unity's engine that is specifically designed for creating moving characters in video games. It has built-in support handling slopes, walls, and steps, all rolled into a single component so that you don't have to (re)write this for every game, like you would in most general purpose 3d engines. But all that built-in functionality comes at a price: if you want to make your character do something that the built-in stuff doesn't support, then you gotta roll it yourself. Still, it's better than having to roll everything yourself. Continued

More Lightwave and Unity




Unity logo[see all of my Unity posts] I'm past the point of the Unity trial, and it was simple enough, powerful enough, and (most importantly) fun enough for me to buy it, with the goal of eventually making a commercial game with it. Although, for the time being, I'm just using it as hobby -- that is, using it for fun to learn it, as opposed to diving in and methodically developing a commercial game with it.

Importing models and animations from NewTek Lightwave 3D to Unity

I've been using LightWave 3D version 9.3.1 for all my modeling, and so far it's been going fine -- with one little problem: the models import into Unity rotated so that the object is laying on it's side. It's odd because when the model is dragged into the scene, it appears right side up, but Unity sets the object's rotation to 270,270,0 -- as if Unity knows the object is rotated incorrectly, and fixes it for me (I assume that in a normal situation, an object with rotation set to 0,0,0 should appear right-side-up in the world). It all seems like a minor detail until I went to use something like LookAt to point the object towards a destination, and the object returns to it's un-normal sideways position.

The solution was to create an empty game object that the object is a child of, set the Parent to [0,0,0], and fix the child's rotation [270,270,0]. It means all the scripts get attached to the parent GameObject instead of the model itself, and that meant I had to rewrite all the little scripts I had written to target the child object. No big deal at this point, but I'm glad I discovered this early. I hadn't noticed it earlier since all my scripting tests were done with primitives.

I have yet to see if you can use this same trick for objects (trees) in the Terrain engine. I wonder how much processing overhead there is in adding a GameObject to an object, esp. if it's going to be mass-populated via the Terrain engine. I hope to have some more to report on soon.


Dean Utian's Director Survey




If you're a Adobe Director user, head over to Dean Untian's Director/Shockwave Survey and fill it out. The information goes directly back to the developers at Adobe. Remember, Director is still very much alive, and your input counts. There's only a few more days to fill it out.


Unity day 11: Terrain overview and Scripting




Unity logoNOTE: If you've not seen my posts on testing out Unity, check them out here. It's been a lot more than 11 days since I started my Unity test, but most of those days I didn't get a chance to play around with it.

Executive Summary

Here's my executive summary of my most recent Unity exploits.

Terrain: I've messed with the Terrain engine a bit and found it pretty easy to use. Feature-wise it's a bit on the simple side; but overall I cannot imagine trying to build a game world solely in a 3D modeling tool, and this is much simpler and more interactive. It seems to feel a lot like the terrain in Oblivion (which is a good thing!).

Scripting: I also took a stab at scripting. So far I've been able to write my own 3rd person camera system (total time: one evening), a Diablo-style point-and-click character controller (total time: another one evening), and try my hand with Unity's coroutines.

I found scripting to be pretty straightforward and it was easy to do just about everything I tried. The point-and-click character controller had me a bit daunted at first, but I was able to get it working in a single evening. The scripting reference came in pretty handy.

Coming from Director, coroutines are definitely the most exciting aspect of Unity scripting. It seems to simply all the problems of execute-over-time scripting without having to do complex case statements. I'll try to explain more about this in a later blog post if anyone is interested.

More on terrain

After reading up on the terrain engine in Unity I got pretty excited, since it appears to handle large maps and vegetation built right in. In an evening I was able to create a height map in Photoshop based on a scan of an island I designed in a previous game, and import it into the editor. It took me several attempts to get it right, which is to be expected, since heightmaps are always trial-and-error process. a few things I learned: use 16bit-per-channel images for heightmaps, and blur the hell out of them, otherwise you'll get major jaggies in your import and (on my wimpy G4) the terrain will grind to a halt. This makes me wonder how graceful it would scale -- the world seems to render quite nicely when it's all smooth hills but after adding ridges and rough edges Unity appears to not LOD them as aggressively when they're far away, which is why initial heightmap tests choked the framerate. Is it possible to make the terrain too detailed? From my initial tests I feel that it's something that I could work around. I took a new approach. My strategy was to use the heightmap as a rough guide and fill in the details with Unity's built in terrain editor. This seemed to work pretty well.

Unity's terrain engine is impressive and automates a lot for you. It has built in tools for modifying land height, adding trees and grass, and texturing the terrain; not to mention rendering them with LODs, billboards, and clipping automatically. In some other engines, you'd need to write all this yourself, but you get it all for free in Unity. Of course that's a double edged sword: the terrain editing tools, while acceptable, are pretty basic. For example, it's very tricky to use the tools to build controlled sloped paths. I keep bouncing between pits and bumps when trying to create slopes. In one evening I felt like I had gotten a lot better at it though, and started to find some tricks for building terrain conducive to gameplay.

Current wishes

While overall I am quite excited about Unity's performance in my tests, I do have my own set of wishes, which currently are:

More examples in the scripting reference: There's still some things I'm trying to wrap my head around conceptually, and often times I use examples to help with that, but the Unity scripting reference is missing examples in some areas. I was able to find Scroll Wheel support in the documentation, but can't actually figure out how to use it yet. There's no example, and I'm still learning the ropes of Unity, and I was not able to get the syntax correct.

Script editor: The Unitron script editor that comes with Unity doesn't work on my old PPC PC (but they're aware of it) so I don't get any color-coding, etc. On top of that, I'm not 100% sure there's a way to do step-by-step debugging. I really have come to rely on having IDEs with built in editors that are "aware" of your project.

Capitalization: This is less of an issue with Unity as it is an issue with Javascript, but I really am frustrated with having case sensitive parsing, and the capitalization standards functions and classes use. I'm going to bitch about it because it causes a lot of stupid errors. It's easy to remember names, but tricky to remember when they're capitalized and when they're not. "camera" isn't. "ScreenPointToRay" is. But here's the thing that irks me the most: it would be considered bad design to have an object named "Max" that did one thing, and an object named "max" that did something different, so why allow it? What I'd love to see is a script editor that automatically capitalizes, so I don't have to.

Overall Game Techniques: I'm also interested in seeing high-level descriptions of how to do common game-related scripting architecture. I'm not looking for pre-written code; just concepts. I am sure some of this may be covered on the Unity site, but I've not found them yet. Topics I've love to see addressed:
  • Save Game/Load game: a quick writeup on how to crawl the hierarchy and save off gamedata for instantiation later. Techniques for making this scalable so that you're not going back and changing the savegame code every time you change properties of the world.
  • Building large worlds: the terrain engine has built in support for clipping trees and grass, but what about all the other objects you want to stick in your world? Can you just add objects to your world without worrying about it? or are there tricks that need to be used?
  • Writing core functions: I want to write some functions that can be called from any script. How do I do that?

More to come soon ...






iPhone: Why won't you let me type my name?




Are you a long time user of the iPhone? Do you feel like you're pretty proficient at typing on it, but not quite 100% adept at it yet? Don't worry, it's probably not you. It's Apple.

After a year of using my iPhone, I discovered that on both 1.0 and 2.0, it's impossible to type my name into my iPhone correctly the first time, even if you consider accepting or rejecting the auto-suggest as part of the normal process. You simply have to use the backspace key to type "hanford" -- it's impossible to type without it. Go ahead, try it. Go into Notepad and type "h a n f o r d" on your iPhone keyboard on your first try (without ever correcting using the backspace key), and reject the auto-suggest when it pops up. It will probably come out as "Handord".

But let's take a closer look. Go ahead and type a few more various words to reset the iPhone suggestion buffer (more on this later). Then try this:

  • Type h a n but when going for the f, press and hold down. Don't release.
  • You'll see that either the d or the g pop up instead.
  • Now slide your finger over a little bit to hit the f.
See what happens? The iPhone skips over the f and pops up the letter next to it. At this point, it is impossible to type hanf.

Now continue:
  • Type a d or a g instead. Then hit the backspace key.
  • Now try and type an f again.
Presto! You'll probably hit it immediately.

In short: You have to use the backspace key in order to type Hanford on the iPhone. You cannot type it without making a mistake.

And if this is not obvious to you: it's not just my name. There's lots of words that you've tried to type: shorthand, other people's names, abbreviations, that the iPhone simply won't let you type without making a mistake. You've probably just never noticed that it was the iPhone's fault, and not yours.

So what's going on with the iPhone keyboard?

In addition to the iPhone's auto-correct suggestions, the keyboard apparently has multiple "smart" modes, one of which is triggered when you type han. It's thinking there's no possible way you'd ever want to type the f next, and so it's mapping it out of the keyboard temporarily to make it easier to hit other keys. Except, in this "smart" case, it's actually making it impossible to type what you mean to, which means you're forced to make a mistake, no matter how accurate your typing is.

Pressing the backspace key will turn off this smart keyboard mode and allow you to type any key on the keyboard. But as soon as you complete your word by pressing space, the iPhone's system is reset, and trying to type hanford will again result in handord or hangord.

This is maddening. To fix it I had to add a dummy entry into my Contacts list.

Predictability and Smart Systems

I typically don't like "smart" systems (engines that have complex rules in order to try to do the right thing for the user) because more often than not they're not smart enough and therefore lack predictability. Predictability in a UI is extremely important; If a user can't consistently get their predicted results -- to be able to think a few steps ahead to mentally target where they're going -- they start to feel like they're not in control of the system.

The iPhone is even worse than others because its system forces advanced users who are adept at typing accurately on the iPhone into guaranteed mistakes that require the backspace to use. That's right: the iPhone punishes the expert user. It's why even after using the iPhone's keyboard for over a year I still don't feel completely adept at using it: because Apple has designed it in such a way that it is impossible to be.

NOTE: sometimes this smart keyboard is disabled; like in website fields. But in SMS and Notepad the smart option is always on.

iTunes Genius UI: Who designed this?




This is the login for the new Genuis feature in iTunes:

Genius login
It took me 10 minutes to figure out that the AOL radio button was not associated with the text field next to it. I was assuming it was a separate login if you wanted to use an AOL ID instead of an Apple ID, and leaving it blank. I never even saw "password"; the logos are so dominating. Anyone else run into this?

Seriously Apple, do some user testing on your products before releasing them.



Unity: Day 5




Unity logo I've now spent a few days with Unity (see my initial reactions here). I'm still only about 1/2 way through the Lerpz tutorial, but I have an update:

Unity Support

As I mentioned in my previous post, I had experienced a few crashes. Let me provide you on a few details about them. Every time Unity crashes, a simple Bug Report app fires up which encourages you to submit a bug. The app is so easy to use, I've filed bug reports every time the app crashed on me. I'm happy to report that every bug I submitted was replied to by a Unity representative. In both cases, I was able to narrow down the crashing to two known bugs that Unity is aware of. Additionally, both bugs are pretty easy to work around.

While crash bugs are never welcome, it's nice to know that the bug reports didn't fall into a black hole, and that the developers were aware of them.

Unity and Lightwave: first results

One of my biggest questions about Unity, not to mention every other 3d engine I've messed with, is how well does it play with Lightwave. Lightwave is a great modeler but not quite the industry standard, and I never had great success importing Lightwave scenes into Director, which ultimately kept me from ever using Director's 3D capabilities for a project. When I started to test Unity, Tom Higgins (Unity Product Evangelist) told me it should work just fine, but I still like to qualify my tools via testing before truly sinking my teeth into them. The executive summary of my initial Lightwave testing is everything's working great so far. Here's a bit more detail, though:

Importing models from Lightwave into Unity First off, I had to install the FBX exporter to Lightwave 9.3. Pretty straightforward, and it was covered in the Unity documentation. I loaded up a character from my previous game development follies, and exported him.

This is where I learned that the Lightwave FBX exporter requires all texturing to be done with the UV projection, as opposed to other projections. I normally don't apply UVs when modeling in Lightwave since all my models are pretty basic, designed for pre-rendering, and using UVs in Modeler adds extra steps.

For this first test, I exported the model anyway. the FBX exporter still worked, it just left off the textures. Additionally, the FBX model froze the subdivision cages that the model had, and turned them into triangles. Pretty cool.

The model imported into Unity and showed up in the game world just fine, outside of it's missing textures.

Importing animation from Lightwave to Unity
My next test was to import a walk cycle from Lightwave and see how it showed up in Unity. I exported a character with a bone-enabled walk cycle to FBX and pulled it into Unity. Again, it worked great. Here I ran into a bit of short-lasting confusion: It appeared that with Lightwave models you only get one animation per model. After a bit of playing around I discovered the "Settings" button in the Project pane. In Settings it allows you to manually break the imported animation into pieces, specifying a name, beginning frame, ending frame, and whether or not it loops. So the process is to do all your character's animations in a single timeline, export it, then break them up in Unity using the Settings panel. Once I figured that out, I was very happy.

TexturesI then soldiered forward and decided to import a model with proper UV maps. I quickly made a crate and textured it on all sides, and exported it. The import into Unity looked great.

To Do: animation with texturesSo my next test will be to combine the above: import a character animation with textures and see if it looks right in Unity. At this point I feel like it's just a formality, but I still want to make sure it all works during this trial process.

Hanford's Unity FAQs

Here's a running list of open questions I have about Unity. As I find the answers, I hope to update this.

Q: Does Unity have native SaveGame and LoadGame support or do you have to hand-roll this?
A: Unity has support for saving and loading data, but as far as tying that data to the state of the world, you'll need to roll your own. Specifically, you’ll want to use the PlayerPrefs class which works both in standalone and Unity Web Player targets. (Source: blog comments).

Q: Does Unity have native PathFinding built into it's terrain? If not, is it easy to implement given an A* routine?
A: No native pathfinding built in. It is possible to create your own, and there are third party implementations. Specifically, there's an article in issue 1 of Unity Developer Magazine in how to do so, and a free A* implementation by Angry Ant. (Source: blog comments)

Q: How much support is there for permanently modifying a scene via scripting? Can I write my own level editor tools that change the Scene permanently?
A: Via scripting it's possible to edit the scene realtime, and using this with a combination of saving the worldstate (like a saveGame script would do) would give you the results you'd want.

However, there's also support for using Editor commands via scripting described in the Editor section of the Unity Manual. However, the strategy for using these classes to modify the scene is still unclear to me. (Source: blog comments)


Checking out Unity




Unity logoYesterday I dusted off my old G4 and set it up in order to mess around with Unity. Unity is a high-level 3d game creation engine that many ex-Director users have switched over to. Games made in Unity can play on Mac or Windows, but the authoring environment is Mac only.

I hope to be able to post my thoughts here on Unity as I explore it's capabilities.

Day 1: Installing the trial

I downloaded and installed Unity 2.1, and immediately ran into a problem: the app was booting to a completely blank dialog box with just an OK button on it, then freezing. OTEE (the makers of Unity) support was quick, but their best suggestion was to re-install. The next day however I solved the problem: it turned out my date/time on my old Mac was not set correctly, and this was playing havoc with the DRM. I set up my date correctly and now Unity is working fine.

First Impressions

LerpzSo far Unity looks pretty cool. It's apparent that it is optimized for making games compared to Director (which takes a more general approach). That is, there's a lot of primitives and built-in game-oriented options that don't require scripting, or even using pre-written scripts. That's a breath of fresh air compared to Director, which pretty much requires you write your own systems for just about everything. The way the editor interacts with scripts reminds me a lot of Leia, which was LucasArt's in-house level editor originally written for Jedi Knight (which I did level design for).

I'm about 1/3 through the Lerpz tutorial, which is a combo PDF and Unity project file that takes you though the basics of creating a 3rd person platformer using pre-written component scripts. It all seems pretty straightforward so far. My first few nitpicks: I've had a few crashes when switching viewport layouts, and the undo/redo seems a bit sketchy. Still, I'm impressed.

More to come here as I continue to play with it ....





Col. Sander's Paradox




Col. Sander's Paradox: The act of realizing that eating KFC is a bad idea and will lead to future trouble -- while actually consuming KFC -- but not able to stop, nor understand why you'd want to.

PS Don't forget my favorite tattoo.



      
 

This site is mostly about

Video Game Design

User Interface Design

Creative & fun stuff

 

Your Host

I'm Hanford Lemoore. My parking skills are unparalleled.

I make things. From consumer electronics, to video games, to theme park attractions. Perhaps I can make things for you! Check out my portfolio.

When I'm not making things for other people, I'm usually experimenting.

 

Contact

Follow me on Twitter.

Message me on Facebook.

Email me using my contact form.

 

RSS 2.0

 

maquettegame.com

tikiroom.com

junkyardclubhouse.com

monolux.com

 

   


Copyright 2025 Hanford Lemoore | Blog | About | Portfolio | Contact
Powered by Olark