Lesson 16 - Code Syntax vs. Style

Tutorial Series: Introduction to Unity with C# Series

Previous Article  |  Next Article


Before we move on to discussing variable scope, which leads us into the heart of C#, and object-oriented principles, which in turns re-focuses on back onto Unity, I want to quickly go over some basics in regards to code structure versus strictly-enforced code syntax. This relates to something that you will become intimately familiar with when coding: that is dealing with errors. You may have already experienced a few weird errors when you were following along. Perhaps you missed a semicolon or you misspelled a word. Errors are a normal part of coding, and I want to quickly go over the topic before we go deeper into C#.

The first thing you should know is that everything in C# is case-sensitive. A variable named "Message" with a capital M is completely different from a variable named "message" with a lower-case m. Many errors or unexpected output often result from a simple spelling mistake, so definitely be on the lookout for that when you are first tracking down issues. Speaking of tracking down issues, one of the great things about using an IDE like Visual Studio is that it is pretty good about helping you figure out problems in your code. You will often get hints about errors and potential problems in your code by looking out for those squiggly lines in your code. I will show you right here. In our code here, if I take out… If I create a simple error like taking out the semicolon, pretty quickly there we see a red squiggly underline, and when we hover over it, it gives us a hint. In this case it is pretty explicit and obvious, it says a semicolon is expected, so we will fix that right away. That red squiggly line, that indicates an error. If we try to run the program, or we try to build it, it just won't work.

Sometimes you will see a green squiggly line, such as in the case when you create a variable that you end up not doing anything with, so let's make a variable that we don't do anything in the code, in the rest of our code we don't reference it. There you go, we got a green squiggly line this time, which is more like a warning in Visual Studio. When we hover over it it says, "The variable nothing is declared but never used." We never even assign it is never used anywhere else in our code. It is just declared, and then it just sits there, and that is our warning. The green squiggly line is just a warning, which is in contrast to the red squiggly line, which indicates an error. When we produce an actual error that was caught by the compiler, the script execution stops entirely, and it prevents the game from running. When you try to run your script and it has an error in it, this is called a compile time error, which is basically a fundamental error in your code, usually syntax-related, that is basically saying, "This doesn't make sense. How am I supposed to run this?" Sometimes, we get a very cryptic message that tries to provide a clue to us into the error, but usually the most important clue is the line number being reported with the error, so we can go back and check what the error might be.

I will show you what I mean, let me just… Actually I will just type in some gibberish, that definitely shouldn't result in a compilation, in a successful compilation. Down here in our error list, it gives us some error messages. It correctly identifies there is no semicolon. That is pretty obvious, but even more obvious than that is that as this error message says, the name whatever gibberish I typed in does not exist in the current context. It is basically saying that there is no variable that has been defined with this name. It basically means nothing to the compiler. If we had a variable with that name that we had previously declared, it actually might make somewhat sense, and this error may not at least appear, not this one. What we really want to look at is over here on the end of our error list, we see the line number in which it appears. The red squiggly line gives us the indicator, but sometimes you actually end up with a lot of errors, or several errors on different lines. In that case it is often very useful to hunt it down by first looking at the line numbers here on the right-hand side. Error messages can be very obtuse, even to experienced coders,so don't freak out it. It seems like total gibberish or to be speaking a totally different language. Another error you may see when you are naming variables and methods is if you use an invalid character. I am not going to go over all the symbols you shouldn't be using when naming your variables and methods, and instead I will just generalize it with a basic rule, a rule of thumb. That is to use only alphabetical characters, and if you feel you have to include a number, like we did with our different method names, we post-fix with a number. Post-fix it, don't prefix it, it just won't work. Alphabetical characters only for our names, and post-fix with a number if you absolutely feel like that is necessary.

Here is an example if you want a variable to store a winning percentage. Name is something like this. Let's get rid of this gibberish. Name is something like, it doesn't matter, it is going to be a winning percentage, so it is going to be a float. Name it winningPercentage. That is valid, there again we see the green squiggly line because we're not doing anything with that variable just yet. That is a valid variable name. Don't do something like this. That is not valid, because the percent sign is not alphabetical character or a number at the end of this variable name. Also if you have a multi-word name like winning percentage, avoid using an underscore between the words, and instead rely on camelCasing, what is called camelCasing or PascalCasing to separate the words. That makes it a little bit more visually appealing and easier for you to understand. This would be camelCasing. Alright. That is camelCasing because it sort of resembles the humps on a camel's back. The first letter is lower-case, and then we also have PascalCasing, like that, where you capitalize the first letter of each word. In both cases, you wouldn't separate the words, because that would actually be basically creating the name or identifier for two variables. That is strictly forbidden. And a general tip for you, especially as a beginner, you may have seen some people who write code using very cryptic and short variable names. I would say err on the side of being descriptive, even if the names start getting a bit long. It is much more important to be able to look at your code and quickly see what is going on, especially when a lot of time has passed since you first wrote it.

I guess the last thing to keep in mind with regards to creating custom variable and method names is that you can't use what is called reserved words. The C# language has many reserved words, which will show up in blue font, just like you have seen with the types we have been using, like Int, String, etc. Whenever you see this special color-coding, just know that you can't use that as your custom identifier for a variable or a method's name. Next thing I want to talk about is code formatting. C# as a language relies on explicit characters to designate where code blocks begin and end, which is curly braces, and where statements end, which would be semicolons. Because of this, the practice of indentation and whitespace is pretty much purely for readability. In principle, you could put all of your code on one long line. It would be terrible for readability, but it would not result in errors, since the compiler is able to properly understand where code blocks and statements begin and end just in the syntax alone. The guideline is to indent a single tab for all lines within the immediate code block. As you have been seeing in our code so far, that's been the case. Actually you have probably noticed that Visual Studio defaults to naturally implementing this indentation structure.

When I make up a method, it just ... I press enter, and create the curly braces, and it creates the indentation for me. Create an if statement, same thing, it creates this natural indentation structure. You should just go along with that, no need to create your own, that is just a general rule of thumb when coding, for readability's sake. When it comes to empty code lines, to more clearly visually separate variables or visually group elements together, this also comes down to personal taste. For example, when we grouped these variables here in our method called stateHandler(), maybe it would have been a little move visually easy for me, especially if I have a lot of variables,to separate my ints from my bools just by adding some whitespace. But it makes no difference to the compiler whatsoever. Visual Studio is an invaluable tool to help keep our code neat and tidy, but it also helps us reduce the chance of producing errors in the first place. One of the first lines of defense in Visual Studio is its built-in code completion feature called IntelliSense. You may have already stumbled across this, where elements that have been already declared in your code can be automatically detected when you start typing, and allow for quick and flawless auto-completion. Here in my code, we have already declared damageRating. If I start typing damageRating, just a couple of characters in it already pops up. It anticipates with IntelliSense that I am going to want to reference this variable.

When IntelliSense pops up, all I have to do is hit Tab, and it automatically completes that variable name. Really handy feature. IntelliSense is really great, not only for reducing errors caused by stuff like misspelled variable names and whatnot, but also for giving you a hint as to what is available to you in certain contexts in your code. It really helps when you are coding and are accessing the Unity API as a real-time list of options available to you. IntelliSense is something we will be using quite often from this point forward. But that is all I want to say about that. We will go more into this and show you the beauty of Intellisense as we cross the Unity API, as we cross that path. All in all, we have looked at how to keep your code tidy, hopefully error-free, and how to go about fixing errors if you do get them. But in the end, probably the bet tip I can give you is simply this: to not write a lot of code before you send it off to the compiler, before you build the code or press the play button in Unity. In fact, you should get used to building your script to check for errors almost without thinking about it, almost automatically. Sometimes nothing more than a few lines of code, you should just be hitting the build button or else the shortcut, which is Control+Shift+B.

Here when I go to my code, if I hit Control+Shift+B, shows 'build started' down at the bottom, and it shows the build details. Again, you can go to the error list if you get errors, which we didn't. It says 'build succeeded.' But if we do have an error, such as, again I will take out that semicolon, and Control+Shift+B to build it, before even pressing Play in Unity, this is a quick and simple way of testing my script. If you check for errors often, it will just be a lot easier to track down the errors without having to systematically dismantle your code in order to isolate where the error might be coming from. It is just a good general tip to keep in mind. That is about all I want to say about these topics for now. We will certainly keep referring to suggested coding standards, error handling, IntelliSense, debugging and all that as we move along. But for now I just want to get the basics out of the way, and in the next video, we will be going back to coding and get a look at variable scope. See you there.

Related Articles in this Tutorial:

Lesson 1 - Who This Course is For

Lesson 2 - What to Expect from this Course

Lesson 3 - Installation and Getting Started

Lesson 4 - Starting the First Project

Lesson 5 - Prototype Workflow

Lesson 6 - Basic Code Review

Lesson 7 - Game Loop Primer

Lesson 8 - Prototyping Continued

Lesson 9 - C# Fundamentals and Hello World

Lesson 10 - Variables and Operations

Lesson 11 - Variables and Operations Continued

Lesson 12 - Floats, Bools and Casting

Lesson 13 - If Statement Conditionals

Lesson 14 - If Statements Continued

Lesson 15 - Complex Evaluations and States

Lesson 16 - Code Syntax vs. Style

Lesson 17 - Variable Scope

Lesson 18 - Object-Oriented Programming Intro

Lesson 19 - OOP, Access Modifiers, Instantiation

Lesson 20 - Object Containment and Method Returns

Lesson 21 - "Has-A" Object Containment

Lesson 22 - "Is-A" Inheritance Containment

Lesson 23 - Static Fields and Methods

Lesson 24 - Method Inputs and Returns

Lesson 25 - Reference vs. Value Types

Lesson 26 - Introduction to Polymorphism

Lesson 27 - Navigating the Unity API

Lesson 28 - Applying What You've Learned and Refactoring

Lesson 29 - Constructors, Local Variables in the Update Method

Lesson 30 - Collecting Collectibles, Items and Powerups

Lesson 31 - Spawning and Managing Prefab Powerups

Lesson 32 - Implementing Powerup State Logic

Lesson 33 - Displaying Text, OnGUI, Method Overloading

Lesson 34 - Referencing Instantiated GameObjects, Parenting

Lesson 35 - Understanding the Lerp Method

Lesson 36 - Creating Pseudo Animations in Code

Lesson 37 - Understanding Generic Classes and Methods

Lesson 38 - Animations Using SpriteSheets and Animator

Lesson 39 - Working with Arrays and Loops

Lesson 40 - Debugging Unity Projects with Visual Studio

Lesson 41 - Camera Movement and LateUpdate

Lesson 42 - Playing Audio Clips

Lesson 43 - Routing Audio, Mixers and Effects

Lesson 44 - Adding Scoring Mechanics and Enhancements

Lesson 45 - Scene Loading and Game Over Manager

Lesson 46 - Understanding Properties

Lesson 47 - Controller Mapping and Input Manager

Lesson 48 - Understanding Enums

Lesson 49 - Dealing with Null References

Lesson 50 - Handling Variable Framerates with time.DeltaTime

Lesson 51 - Preparing the Project for Final Build

Lesson 52 - Final Build and Project Settings

Lesson 53 - Introduction to the Unity Physics Engine

Lesson 54 - Understanding FixedUpdate vs. Update

Lesson 55 - Movement Using Physics

Lesson 56 - Attack Script and Collision Events with OnCollisionEnter2D

Lesson 57 - Projectiles and Stomping Attack

Lesson 58 - Parallax Background and Scrolling Camera

Lesson 59 - Infinitely Tiling Background Sprites

Lesson 60 - OOP Enemy Classes

Lesson 61 - OOP Enemy Classes Continued

Lesson 62 - Trigger Colliders and Causing Damage

Lesson 63 - Multi-Dimensional Arrays and Procedural Platforms

Lesson 64 - Finishing Touches

Lesson 65 - Series Wrap


Please login or register to add a comment