| Home Page | Recent Changes | Preferences

Coding Guidelines

Introduction

It can be very useful and safe a lot of time when all coders who are working on the same project use the same style of coding. This document is meant to be a good guideline.

Get yourself a decent text editor. Notepad rarely crashes, but that's about the only thing to be said in its favor. A decent text editor (in coding terms) supports

Auto-indention
After pressing Enter, the inserted paragraph has the same indention as the paragraph you're coming from.
Hard tabs
Pressing the Tab key (optionally) doesn't insert an actual tab character but simply enough spaces to jump to the next tab position. Conversely, if there is nothing but tab-equivalent spaces before the cursor position on the line, Backspace will remove the equivalent of one tab. See below.
Powerful search
Some means to search the open document for strings; that's one of your primary means for navigation in your source code. Some text editors even provide "inline search", which searches the document as you type in your search string – that's probably the most efficient way to implement a document search from a user's point of view.

Syntax highlighting is frequently mentioned as a crucial feature too, but it's more a nice-to-have (or even a very nice-to-have) than a feature that actually enhances your productivity.

General Advice

Indentation

Indent code that's in a block. Whether you indent it using tabs or spaces is a matter of personal preference to a degree, but here are some pointers:

  • Tabs are a logical way of indenting code. In theory, everybody who's reading your code could just set their favorite tab width in their text editor and view your code as they like to. In practice, tabs are used as a physical means of indentation and happily mixed and merged with regular spaces though, which completely messes up the source code layout if the reader doesn't happen to use exactly the same tab width as the writer. (Epic uses four characters, for instance, while most text editors default to eight characters.)
  • A decent text editor allows you to enter tabs either as an actual tab character or as a row of spaces automatically after a single stroke on the Tab key.

Expression Syntax

Make expressions readable:

  • Put spaces around operators.
  • Don't use more parentheses than necessary to understand the expression. Operator precedences aren't always obvious to everyone (if they aren't obvious to you, look them up on the Operators page), but it's at least commonly known that comparison operators have a higher precedence than binary boolean operators, for instance.
  • If your parentheses are complex, consider marking the nesting with line breaks and indentation.

Comments

If the code and the comments disagree, then both are probably wrong.

Norm Schryer

Everybody has a different notion on how much commenting is "just enough," but no comments at all are universally considered too sparse. At the very least, give your classes and its methods comment headers that explain what the class and its methods do. It's also good practice to put a comment at the end of a public object property declaration that's exposed in UnrealEd's Actor Properties Window – that might even be directly supported by future versions of UnrealEd that might display those comments as tooltips for mappers' guidance.

When creating comment headers for classes and methods it's generally easier to use comment blocks than single line comments – as there is less editing to do should you need to update the comment block at a later date.

/*
    This function is called whenever a player collides with the flag.
    The function performs the following operations: ...
*/

function FlagCollision ()

EntropicLqd: Sometimes the what in a comment is self evident from the code. The why however may be far less obvious. It's also easier to comment small blocks of code so it's worth creating reasonably atomic functions. I'll dig out Code Complete tonight – that had some good thoughts on commenting code.

Mychaeel: Concise code and variable names that are well thought out will help a great deal already (both readers and the writer of the code), but there's a natural limit to that. That's why I'm emphasizing class and function comment headers – they allow the writer to summarize what hundreds of lines of code do in a few comprehensible natural-language sentences, and they serve to define a class's or a function's interface (which would be the "why" you mentioned, I suppose).

EntropicLqd: I would agree with that. I rarely add comment blocks within a given function or method (unless I'm up to something particularly tortuous) but my function and class headers are generally detailed works of art (well, detailed anyway).

Class Declaration

If you use modifiers in your class declaration (see Class Syntax) place each modifier on an indented new line.

class Child extends Parent
    abstract
    config
    native;

[BWF]GrimReaper: Beware of using the word 'class' in preceding comments. The compiler will error.

El Muerte TDS: that is not completely true, multi-line comments are not ignored in the initial class parsing, so:

/* this class won't compile */
class Child extends Parent abstract config;

The initial parses recognizes this as a class called "won", there's an easy work around for this at the moment:

/* 
  class Child extends Parent
  this does compile, all it needs are the class and extends, the class modifiers are not needed
*/
class Child extends Parent abstract config;

Foxpaw: I believe you can also use single-line comments, like so:

// This Class does some junk.
// I guess.
// I never use comments anyway.
class AClass extends ASuperClass;

El Muerte TDS: that's what I implicated, only multi-line comments have problems (also in defaultproperties)

Names

See [Ottinger's Rules for Variable and Class Naming] for a few very valuable guidelines on naming.

Name Capitalization

Stick to the conventions used in UnrealScript for naming your class, function, state and variable names.

  • Write all UnrealScript keywords in lowercase.
  • Write all symbol names (variable, state, class names) using the capitalization used in their declaration, even though UnrealScript is case-insensitive.
  • Name your functions, variables with the Pascal notation (HelpMe, MyInteger, DoSomething()).

Names are Documentation

Always, always, always use good, unabbreviated, correctly-spelled meaningful names.

"I don't like typing that much!"
You're really just admitting that you don't know how to type, which is really not acceptable these days. Good editors help. Copy and paste if you have to. It's not really that much to do. Typically, in a narrow system, a given symbol won't be referenced more than 20 times anyway.
"It's difficult to come up with meaningful names!"
Agreed. Lambda functions are nice but aren't always available. Perhaps you can more something more generic, or maybe you can scope a name. Usually, though, if you can't come up with a good name for a thing, you probably don't have a good idea what the thing is supposed to do.

Taken from Wiki logo MeaningfulNames

Make sure you give your functions and variables names that match their purpose (even if it's more typing). Avoid the use of abbreviations unless they're immediately clear to everyone who's likely to read your code (including yourself).

Negatives

Avoid double negatives. Make boolean variable names positive statements. Here's an example of what not to do from DynamicAmbientSound:

  bDontRepeat

Care to work out what that is interpreted as when "False"? Now try it at 02:00 with no coffee.

Hungarian Notation

Hungarian notation uses a prefix to indicate the data type of a variable. Epic use Hungarian notation for boolean variables (bStatic, for example), but extending the usage to other simple variables can greatly improve the readability and maintainability of your code. In the example below the lower variable declaration uses hungarian notation to indicate that the variable is an int.

int Count; // No hungarian notation here
int iCount; // Note the i prefix - that's hungarian notation

The prefixes you use within your code are purely a matter of choice.

  • Some coders use the first character of the built-in data types as variable name prefixes; but you can also use multi-letter prefixes and mark variables for their intended use (for instance, IndexFoo or idxFoo for integer variables used as array indices, CountBar or cntBar or nBar for integers that hold a counter of something, and so on).
  • For object references, you could use the referenced object's class name (or a reasonable abbreviation of it) as the variable name prefix, for example PawnPlayer or EffectExplosion.

The aim of hungarian notation is to improve code comprehension. You're not only doing that for other people reading your code but mainly for yourself. It's much easier to write bugfree code if you don't constantly have to remember what your variables are supposed to contain.

Braces

Where to put the braces that surround blocks of statements is largely a matter of personal preference. There are a couple of different variants around.

The only thing that's universally agreed on is that you should by all means indent all statements of a block. (Whether to indent them with blanks or tabs and how many of them is a matter for an entirely different discussion.)

  • Note that block statements (like if, for and so on) don't require braces if the code block they apply to consists of a single statement. Without braces, it's customary to put that single statement in a line of its own anyway and indent it as if it were a block – just the opening and closing brace are missing.
if(foo)
  bar;

Epic's programmers put opening and closing braces in separate lines, indented as much as the surrounding code, with the block within the braces indented one more level.

if(foo)
{
  bar
}

You can also put the opening brace in the same line as the statement starting the block; that makes the code more compact (which may or may not be a good thing) and emphasizes the relation of the block itself and the block statement it belongs to.

if(foo) {
  bar
}

And you can indent the closing brace with the interior block, so the whole thing looks like a single paragraph with a hanging indent:

if(foo) {
  bar; 
  }

Discussion

Wormbo: A little discussion from my page:

EntropicLqd - I saw you sneak in and change the formatting of the Relics page to not use the subheadings :P. I bet you put your curly braces on the same line as your if statement too! :P :) ;) - I'll make my stuff consistent at some point if you don't beat me to it.

What's wrong with the brace on the same line? Everything! ;P I always put them there except for function, state, replication and defaultproperties. ;-)Wormbo
(Hey, this reminds me! We could make a page about good coding style...)

Uh yeah. Please, let's have a good, fun, utterly pointless discussion about coding style – where to put braces and how to indent. I have some pretty unorthodox notions of my own there. ;-)Mychaeel

That would rock - I've not had a decent flame war (aka religious discussion) about coding style for ages. The problem with coding-style discussions is that there is no right answer. In reality, consistency is more important than form - but I'll save the rest for the discussion – EntropicLqd

That, indeed, is something I heartily agree on. Consistency is important, not where braces are located and how indention is done (obviously everybody has grown attached to what he/she's doing him/herself, because I doubt doing it otherwise simply didn't occur to anyone). :-)Mychaeel

If only that were true. I've probably tried hundreds of different combinations of styles in an attempt to find the "perfect" style. In practice I've simply found a set of conventions for code that I find easiest to read. The really ironic thing is that these conventions have changed over time (i.e the last million years) and so the style I use now is very slightly different to the style I was using a year ago. What I also find even worse is that some elements of my coding style are influenced by whatever language I am developing most in at the time.

Actually, I don't find that to be a problem... you can hardly keep a consistent style across different languages simply due to the very different syntax of theirs. My source code style in Delphi is very different from my source code style in UnrealScript, but then again it's hard to compare because the languages simply have different syntax. Then again, the way I indent braces and stuff like that is consistent among languages that use braces. As for symbol naming and capitalization conventions I've always found it most convenient to stick with the conventions given by the language used, more or less at least. —Mychaeel

I agree about the indentation thing - that's something that is completely consistent aross all languages - as is my bracing (for those that use braces). Spacing after/before brackets is something I'm almost (sigh) always consistent in, and my function declarations (when needed) and commenting style is pretty much identical across all languages. Symbol naming and capitalisation is something I prefer to be consistent with but in most cases someone else has generally written the coding style guide before me. It irritates me that I find symbol naming and capitalisation pretty much transparent to code comprehension - I feel it should be more important than it actually is in practice.


Mychaeel: The problem with such a page on a Wiki is that you will hardly be able to find something less than ultra-generic that all people agree on. I, for instance, completely disagree with the notion of using tabs instead of blanks for indentation, ironically for precisely the reasons you're mentioning (non-standardized tab widths, above all – and a decent text editor will let you use the Tab key for inserting spaces to jump to the next tab position, so convenience of use is not an issue).

So brace yourself for a heated discussion on what "good coding style" is, as everybody has a different notion of it. (And at the end of it, there's nothing wrong with that – as long as, like you say, a whole team agrees on a given set of conventions, it's pretty irrelevant what conventions those are.)

Tarquin: we could outline the different styles. You're right about tabs... they can look great in UnrealEd's script window and then like dross in a different editor. :( Going beyond typographical layout, we could mention conventions such as bSomething for booleans, EOPtions for enumerations.

2COOL4-U: Well I really am pro-tabs. No one has ever set a standard about how many spaces to use. And all the editors I use(except 1st page 2000 for HTML editing) have a nice good way of handling tabs. Also a good editor has an option to change the number of spaces used for a tab.

I am also trying to write coding guidelines about how the classes coded by Epic Games are written. They use tabs for example.

Mychaeel: Well... the lack of a common standard for the number of characters per tabstop is, as I wrote, something that's in my opinion the best argument against the usage of tabs for indentation – Epic is apparently using four character widths per tabstop, while normal text terminals and text editors default to eight. Looking at Epic's code with a text editor that isn't set to those exact four characters makes it look pretty messed up and incomprehensible.

That's especially true since coders are tempted to use tabs not only for indentation but also for horizontal alignment of subsequent lines; and mixing lines with tabs and blanks is pure horror. I can't see any of these disadvantages in using blanks and a decent text editor that enters them when you press Tab.

Incidentally, every full-fledged programming environment like Microsoft Visual C++ or Delphi makes either behavior optional and configurable. At the end of the day that just proves once more that this is an item of personal preference (even though everybody might have strong reasons for doing it this or another way), and nobody is in the position to publicly claim that using tabs or not using tabs is the one way to go. If anything we could, Wiki-like, list pros and cons for both notions and be done with that.

EntropicLqd Ironically the very reason cited by Mychaeel for using spaces instead of tabs is the reason I prefer to use tabs. I tend to use tab stops of either 2 or 4 depending on what language I am programming in. The text editor I use has a configurable setting for the tab stops. This means that if I pick up some code from someone who thinks a tab stop of 8 is great, if they have used tabs, it will get displayed to my preference. If spaces are used I either have to remember to also use spaces (so as not to break the indentation scheme when viewed by the original author), or reformat all the code to use tabs (which would also irritate the original author).

TaoPaiPai: The last thing I want is someone to tell me how to indent my code :/ :p

Birelli: My attempt at a generic statement: "Projects in which there are going to be multiple editors used essentially require the use of spaces only and not tabs. However, if there is no doubt at all that every member of the team working on the project and every member that 'will ever work on it' is going to use the same text editor then, if everyone agrees, tabs can be permissible to use as a time-saver and an efficient way of lining up consecutive lines, something that anyone who has made a block of slightly varying function calls can attest to as critical." Ok, so it's a bit lengthy, but I think it satisfies all the arguments presented. Personally, I always use tabs in my programming, but if I was ever going to work with someone using a different editor, I think it would be worth it to use spaces. </riding the fence> ;-)

Mychaeel: The "time saver" argument really doesn't apply, unless you're using a very simple text editor that doesn't allow you to use the Tab key to jump to the next tab position with spaces. I wouldn't like to have to hit the Space key either twice (or more) each time I add an indentation level. (By the way: I'm implying the presence of auto-indent in a decent text editor: When pressing Enter, the new line is indented just as much as the one you were previously in.)

Tarquin: absolutely. I used to think "spaces... urg!" until I switched to TextPad. Spaces make sense for the saved document; using the tab key makes sense for the actual coder. Auto-indent brings the two together :)

Birelli: Aaaah, /me understands Mych now. I guess that does satisfy everything involved.

Mychaeel: To my utter delight I just found the following quote on [How To Write Unmaintainable Code: Coding Obfuscation] (also linked from UnrealScript, though not by me, I might add): "Tabs From Hell – Never underestimate how much havoc you can create by indenting with tabs instead of spaces, especially when there is no corporate standard on how much indenting a tab represents."

Trystan: Nothing to do with tabs; everything to do with Hungarian notation. I've always disagreed with it - in my mind your variable name and an idea of what the code is doing, along with context, should be enough of a clue to a programmer as to what your variable contains. I use bVariableName myself because I like to know that a variable should only be compared to true/false, but I never saw the point of lpszPointerToAString. I'm also a fan of CamelCase notation, but not camelCase. Why not capitalize the first letter? It keeps things more "standard"; you could either "capitalize the first letter of every word except the first" or "capitalize the first letter of every word." Anything with an exception in it makes me think "not standard." As further proof of Hungarian notation's uselessness the .NET Framework - the framework of the future (?) - discourages it's use and Microsoft has officially stopped usage of the notation in it's corporate programming.

As for tabs - I'm a tab fanatic. I hate spaces. I hate spaces because we live in a mostly WYSIWYG world and when you open up code inside an editor that defaults to a proportional font spacing just gives up the ghost. I'm willing to wager that's why most people use tabs: a tab will always take you a half inch in, or whatever you have yours set to. (Should you use an editor that doesn't default to a proportional font? Probably not. How many times have you been on a machine who's only text editor is Wordpad when you want to take a gander at someone else's code? My personal machine is tweaked out to my specifications, but the other 325 machines at my company aren't. :P)

Mychaeel: "Hungarian notation" isn't what I'm personally using for my variable names, but I do use a prefix-based naming convention (that is thus "reversed" compared to normal talking). Boolean values are prefixed with "b", counters with "n", indices with "i". After that, a top-down list of terms describing what the variable holds – for instance "nPlayersJailed", which would be a variable that holds the number of jailed players. And "nPlayersFree" would be the number of free players. When those two variable names are neatly horizontally aligned (something you cannot do with proportional fonts), it's easy to see at the first glance what's the same about them (count players) and what's different (jailed/free). What's more important for anybody having to maintain your code, you can pull all this information from the very variable name itself at any time.

Tabs in source code are something I, for very practical reasons, loathe. They're neat in concept as you describe, but I have yet to see anybody who actually uses them along their conceptual beauty. Most people use them in a very thoughtless "layout" sense which breaks beyond recognition as soon as somebody else looks at their code with another tab setting, or another font, or just another editor. Especially if you're dealing with 325 computers with 325 different editor preferences, that should be important to you. If people only used tabs for block indention, everything would be fine and even I would use them; but people also use tabs to horizontally align corresponding items on subsequent lines, or comments at the end of lines, and so on. What's even worse is if people use spaces and tabs in the same source code, maybe even in the same block (just look at Epic's code).

Using spaces for indention and horizontal alignment avoids all of those problems at the small expense of indentions not being as wide as with tabs when used with proportional fonts; but at least they're still recognizable. (And you can scratch the entire notion of horizontal alignment anyway beyond mere block indention if you're using a proportional font to start with, which is one more reason not to do that.)

Trystan: True. I use tabs to line my code up underneath brackets and had never considered it before. Eep. I may have to use that tabs to spaces option after all.. tab once, logic block. Tab twice, code under logic block. Someone opens it up.. sigh.. time to go update our project's coding notes. (Ironically it's never been a problem because I'm the only coder at my company.. heh.)

Tarquin: best of both worlds is TextPad, which has Hard Tabs – you hit TAB, but it inserts spaces :D

Mychaeel: I believe that's a feature every decent text editor has (or ought to have, anyway) – mine can even convert tabs to spaces on the fly when loading files or pasting text.

Trystan: WOTGreal has it. Notepad doesn't.. :) Wait, wait, that doesn't qualify as a decent editor. I found another reason I enjoy tabs though - if you've tabbed most editors will only require one cursor key movement to go over the entire length of the tab. If you've used spaces you've got to hit it that many times. Nothing serious, just trying to find stable ground to stand on in tabs vs spaces. :P

Mychaeel: Of course you would rather press Ctrl+LeftArrow or Ctrl+RightArrow to move from word to word instead of pressing the same arrow key repeatedly. (Even Notepad supports that.)

Trystan: BAH! I give up! /me putters off to code rather than argue. :D

The Unreal Engine Documentation Site

Wiki Community

Topic Categories

Image Uploads

Random Page

Recent Changes

Offline Wiki

Unreal Engine

Console Commands

Terminology

Mapping Topics

Mapping Lessons

UnrealEd Interface

Questions&Answers

Scripting Topics

Scripting Lessons

Making Mods

Class Tree

Questions&Answers

Modeling Topics

Questions&Answers

Log In