Proper Unity Programming Procedures C#

Hello everyone!
I am a relatively experienced programmer. When I started using unity, I coded like I was coding a typical c# program. I would have one main script that would initialize the actual game class which would handle and instantiate other classes on start, etc. It followed your standard OOP structure. Then I started switching to a more scripting approach instead of looking at each script as your typical c# class if that makes sense. That being said I think the more I take a “scripting” approach the sloppier my code gets and the harder it is for someone who comes behind me to figure out what’s going on. Is there somewhere I can see a uml diagram or project demonstrating appropriate code structure in Unity? Is there a set of industry standard guidelines for Unity code? Thank you all for your time!

I’m not aware of a formal set of guidelines. Someone else might be able to point to them. But here are some things that will help for coding inside of Unity.

  • Unity itself takes care of the Main function, and provides you with hooks into the main game loop.
  • Unity is very component based. It favours composition over inheritance. Build many small components, with a shallow inheritance structure. Each component should be relatively modular and take care of a single job. You should be able to modify each component individually, without touching other code.
  • Assign data to components via serialised fields in the inspector. For bigger projects this can be impractical, instead load data from a file.

That’s a starting place for people to tell me I’m wrong, but hopefully by the end of the thread you’ll get something useable.

3 Likes

If you’re accustomed to starting from a Main and going from there one thing you can do in Unity is start from one Update function in one game object and have all of your game logic going from there. I tend to do most of my Unity work that way, actually.That being said, there isn’t any one solid right or wrong way to write stuff in Unity. What is “right” really depends on what you’re trying to accomplish. I’d say just start to work and keep in mind code organization while you’re writing.

Unless you are very good with design patterns I would suggest avoiding this. You’ll manually need to keep track of each game entity and modify its state every frame. Essentially duplicating work Unity is already doing.

That said there are some games where I could see this being a useful technique. Its also worth noting I’ve never tried this technique.

Oh man, Callski, I had the same problem when I first came to game engines like Unity and the sort that use the ‘component pattern’ for developing purposes.

I too tried the very same thing as you and was frustrated at how ‘hackish’ it felt to hook into the main start loop of the game and do all my work.

I’m still working out the kinks of various aspects, and sort of just accept the oddities of it. I wish I had more help for any direction, but I have yet to find any community guidelines really… and just roll with what works best for me.

I do know that the componet pattern is just an extension of the “composite design pattern”. So just approach it with that in mind. I still have my own classes separate from the components, but everything hooks off of the components in some way.

Oh and I avoid any of the magic string bs in the engine. I wrote my own collection of functions and utils (some of which have deprecated as Unity adds them as well to the official API) to avoid using strings to invoke methods, or start coroutines.

You can see what I give away free here:
https://code.google.com/p/spacepuppy-unity-framework/source/browse/#svn/trunk/SpacepuppyBase

Check out my ‘utils’ namespace, primarily the ComponentUtil, CoroutineUtil, and GameObjectUtil, as well as the RadicalCoroutine in the base namespace.

Really it depends on how tightly you want to control everything and how much stuff you want to program yourself. I came to Unity from XNA so I got accustomed to just doing everything myself. It’s also an optimization thing, in its way; if you do everything yourself you can ensure that only the stuff that needs to happen actually does.

Apples and oranges, really. Which approach one uses ultimately depends on the project as well as preference. I generally do stuff with just one scene and cobble together prefabs that are instantiated and tracked in code.

Stick with the approach you started with, other than implementing component based approaches where appropriate. Technically, you’re just scripting with C#, but it’s a full-on high level programming language. Take a bit more of a distributed, event-driven approach, because a game is essentially event-driven. Thus the lack of an equivalent to main().

Unfortunately, the community has a lot of lazy programmers that fail to treat it like it’s an object oriented language, and ignore proper encapsulation and other basics. Don’t let the community set your standards, because most of the code I see is sloppy. Set standards for the community, because lord knows we could use some.

2 Likes

I wouldn’t be so quick to call people lazy or say they have no standards. Unity’s accessibility means that anyone can get involved, so there experience level here varies hugely, and a lot of available learning materials are designed to get people up and running quickly (or, ick, are made by people who really shouldn’t be trying to teach others).

3 Likes

It’s also worth noting that Unity itself doesn’t always play nice with standards. Sometimes you can end up fighting the engine.

Serialising interfaces comes to mind.

I think Unity being such a hybrid interface makes good programming a bit difficult too. Call me old fashioned, but initializing variables by dropping objects onto the inspector never seems right to me. I’m sure when I get to the stage (in the tutorials I"m making) of creating actual games I’ll be loading all resources through script. Convenience is for experts, not for beginners.

If that’s the only way you’re doing it then I’d have to agree. I’m pretty selective about what I expose to the Inspector. It’s always done as a deliberate choice, and with a deliberate interface designm and with appropriate error checking. Also, my code interfaces and my Inspector interfaces are individually and explicitly designed - something is never in one just because it happens to be in the other (though I’ll admit it’s super rare that I want something in the Inspector and not also available by code).

Also remember that Inspector value initialization isn’t magic. It’s just as code driven as anything else, it just doesn’t happen to be code that we write in script land.

I like everything to be or to be as close as can be to being able to use them over again in another project.
So if one part didn’t fit I don’t have to edit much to carry it over.

I like being able to initialise via the inspector. It’s a pretty powerful feature that allows very quick iteration. It also allows a lot of data driven behaviour. I would only recommend initialising via code if you plan to load data from a text or XML file.

What is annoying, and probably leads to a lot of the bad coding practice mentioned, is the coupling of public and serialised. This leads to beginners making everything public. Which leads to accessing everything by script. Which leads to massive dependencies. Which leads to the dark side.

So maybe another best practice should be

  • Separate your public API from your inspector serialisation. Use public only for variables you want to access from other scripts. Use [SerialiseField] to expose a variable to the inspector.
1 Like

I’s good to hear I’m not alone regarding [SerialiseField]
After I posted this http://forum.unity3d.com/threads/need-help-to-spawn-objects-not-too-close-to-eachother.290404/#post-1918533 I wondered if I’d be jumped on from a great height … still waiting to find out :slight_smile:

Not at all. When I introduce people to Unity now I teach that as “the right way”. The whole “make everything public” approach breaks too many basic rules to be considered a long term approach. And it’s not that I’m a stickler for rules for the sake of rules, it’s that there are many practical benefits to following best practices.

The trouble is make a variable public is in every beginners tutorial that Unity has produced. I coded like that fine for the first few months. Till I tried to change a couple classes. I didn’t know the technical word then, but I learned to hate dependencies pretty quickly. Its such a simple concept that learning it the right way first would cost almost no effort. Learning the hard way sucks.

1 Like

So many people don’t even consider that this is something that can be improved, though. They think it’s just the nature of the beast, and every time a client asks them to change something they just knuckle down and commence with the radical code changes.

I’m a chemical engineer by day. The idea of reusable unit operations with narrow interfaces come pretty naturally once I’d discovered it on google.

Then again I still miss the second equals sign just about every time I write an if statement. And I occasionally catch myself writing it with two fs.

And yet at the top of the official documentation for [SerializeField] it states “You will almost never need this”…

Sometimes I feel like Unity tries to enforce impractical coding habits (like promoting the constant use of public variables). For my first Unity project I had all the assets I needed in the resources folder and loaded everything through code. I could code the entire project exactly how had done other stand alone applications. This had to change the moment I was integrated into a bigger team. Then I had to work alongside designers, programmers (guys who just vomit code on screen until it works and have no educational background in the field), and sound etc and a lot of my approach had to change. UI is now set up using tools like NGUI and UGUI. Now I approach things a bit differently but I’m still somewhat happy with how I’m able to code.

I basically have overarching view classes. So in perspective of a simple UI program, you’d have the view class which would handle all logic for the UI and fires off number of events (delegates). All this class knows is when something has been “clicked” and handles UI animations, just aesthetic stuff. Then you have other classes which function exactly like a regular c# class. They’re usually a child to the global gameobject, onstart they gameobject.find the gameobject containing the view script and listen for those events to fire. Keeps everything nice and separate and you don’t have to worry about crazy dependencies. Artists can just switch out their stuff in the view classes and all other logic is completely unaffected. Also if you’re dealing with a number of coders on one project everyone can work on their task without worrying about their code screwing up everyone else’s.