XNA Game-Themed CS1 Examples (XGC1) Release 2.0 (XNA V3.1) 2/8/2010
Topic: Topic.4.DecisionStructures
Example: Ex_6.NestedConditional

# Decision Statements: Nested Conditionals

References:

• Pre-requisite: it is assumed that you have read through the prior tutorials, and are familiar with the concepts covered in those tutorials.

Goals:

• Throughout this chapter, we will work towards a simple game, with each tutorial adding a little bit more to what we've already done.  In this tutorial, we're going to
1. Examine a slightly different format for nested conditionals, which are sometimes referred to as if...else if statements.  One could also describe these using a phrase like 'chained' conditionals.

1. Obtain the example code

Download and unzip the zip file and you will see an ExampleProgram folder. Open the ExampleProgram folder, the EXE folder contains the compiled program and you can double click on the .sln file to work with the source code.

When the game starts, you'll see a screen that looks similar to this:

The game behaves in a manner that is identical to the what was described for the previous tutorial.  In this tutorial, we will be examining a different way of accomplishing the same effects as we had done in the previous tutorial.

3. Ball Bouncing Off The Paddles, Using Nested Conditionals:

As we look at the code from the previous tutorial for making the ball bounce off of the paddles, we can observe something useful: the ball can't touch both the left and the right paddles at the same time.  Therefore, if the ball is bouncing off the right paddle, there's no need to check if the ball is also bouncing off the left paddle.  We can do this efficiently, using a nested if statement, like so:

• BounceOffPaddles(), Version #1 private void BounceOffPaddles(){     if (m_RightPaddle.Collided(m_TheSoccer))     {         m_TheSoccer.VelocityX = -m_TheSoccer.VelocityX;         PlayACue("Bounce");         m_NumBounces = m_NumBounces + 1;     }     else     {         if (m_LeftPaddle.Collided(m_TheSoccer))         {             m_TheSoccer.VelocityX = -m_TheSoccer.VelocityX;             PlayACue("Bounce");             m_NumBounces = m_NumBounces + 1;         }     } }
• You'll notice that the function is exactly the same, except for the addition of the else clause, which ensures that if m_RightPaddle.Collided(m_TheSoccer) is true, then we'll do all the work inside the first curly-brace block, and then SKIP everything in the else clause.
• While this works well, you'll notice something interesting: there's really only 1 statement inside the 'else' clause (the if, plus the stuff in the curly braces, counts as 1 statement), meaning that we don't really need the curly braces for the else clause.  Instead, we could write it as is shown in Version #2, below.
• BounceOffPaddles(), Version #2 private void BounceOffPaddles(){     if (m_RightPaddle.Collided(m_TheSoccer))     {         m_TheSoccer.VelocityX = -m_TheSoccer.VelocityX;         PlayACue("Bounce");         m_NumBounces = m_NumBounces + 1;     }     else         if (m_LeftPaddle.Collided(m_TheSoccer))         {             m_TheSoccer.VelocityX = -m_TheSoccer.VelocityX;             PlayACue("Bounce");             m_NumBounces = m_NumBounces + 1;         } }
• Functionally, this is identical to the prior version, except that we don't have the curly braces around the else's if.
• While this works ok, you'll notice that if we had another else clause at the end, and another if inside that, and if we kept indenting things as we have been, the code would slowly creep towards the right:

{

}

else

{

}

else

if ( ... )

{

}

else

if ( ... )

{

}

// etc

Furthermore, since we're basically looking at making one of a series of mutually exclusive choices, it makes sense to keep everything at the same level of indentation, as shown in our third and final version:

• BounceOffPaddles(), Version #3 private void BounceOffPaddles(){     if (m_RightPaddle.Collided(m_TheSoccer))     {         m_TheSoccer.VelocityX = -m_TheSoccer.VelocityX;         PlayACue("Bounce");         m_NumBounces = m_NumBounces + 1;     }     else if (m_LeftPaddle.Collided(m_TheSoccer))     {         m_TheSoccer.VelocityX = -m_TheSoccer.VelocityX;         PlayACue("Bounce");         m_NumBounces = m_NumBounces + 1;     } }
• The only things that have changed are that the second if is now on the same line as the else (don't forget the required blank space between the else and the if!!!), and that the second curly-brace block is now at the same level of indentation as the previous two.
• Otherwise, this version behaves in the exact same fashion as the prior two.
• This particular style of indentation is very common in programming, and you should make sure to get comfortable with it.
• Indeed, while it's technically a specialized type of nesting, it often gets it's own name/description: if...else if statements, or maybe something like chained conditionals (note that this last term is more of a description than a well-established technical term)

FURTHER EXERCISES::

1. Start from a blank starter project (1000.201, if you need it), and re-do the code from memory as much as possible.  On your first try, do what you can, and keep the above code open so that when you get stuck, you can quickly look up what you forgot (and that after you finish a line, so that you can compare your line to the 'correct' line).  On the next try, do the same thing, but try to use the finished code less.  Repeat this until you can type everything, without refering the tutorial's code.
• Repeat this exercise daily for several days, so that you really get the hang of this.  As you go on, periodically review this by re-doing this exercise.
2. Nested/Chained Conditionals: Practice
For this exercise, you should use the same project that was explained in the above tutorial.
If you haven't done so yet, go through the CheckForWorldBound, and make sure that you can nest/chain the statements in that function in a correct and efficient manner.
• If you're looking for hints, there is a similar exercise in the previous tutorial that you may find helpful.
3. Nested Conditionals: Decorating Your Game
For this exercise, you should use the same project that was explained in the above tutorial.
Mechanically, a nested conditional allows you make a second decision, but only after the test for the first decision is true (or false).  For example, in the previous tutorial, we asked "Did the player get enough bounces to be in expert mode?", and if that was true, we decided to both move the player to expert mode, and then also ask a second question "Is this the first time that the player's in expert mode?"  If that second question was true, we played a sound, and made the ball speed up.
In other words, the nested if allowed us to make a much more complex decision ("Put the game in expert mode AND maybe play a sound/adjust the speed"), instead of a simple decision ("Put the game in expert mode").  So one way of describing what nested if statements do is to say that nested if statements (nested conditional statements) allow us to complicate, or 'complex-ify' a decision.
Another way of describing what nested conditional statements do is to say that nested conditional statementsallow us to decorate a decision.  Instead of just deciding to put the game in expert mode, we also play a sound, and speed up the ball - the "decoration" is the extra decision about whether or not to play the sound and boost the speed.
For this exercise, you should decorate some of the decisions that your game is already making:
1.  For this exercise, you should decorate the actions that happen when the ball bounces the edge of the screen.  When the ball bounces off a wall, if the game is in expert mode, then you should play the sound "Bounce4".  If the player is NOT in expert mode, then you do not need to play any sounds whatsoever.
• Hint: After you've found the code that is responsible for bouncing the ball off the walls, you'll need to add your code in.  Make sure that you think carefully about the syntax here, especially about curly braces.
2. For this project, we've added several new sounds - "Bounce2", "Bounce3", and "Bounce4".  Currently, when the ball bounces of a paddle, we play the sound "Bounce".  This exercise will focus on 'decorating' the actions the game does, in response to the ball bouncing.
You should first change the program to simply play the sound "Bounce2", so that you know what it sounds like, and so you can make sure that you can get it to work.
Next, you should decorate the actions that happen when the ball bounces off a paddle.  Specifically, if the player is in novice mode, you should keep playing the "Bounce" sound, but if the player is in expert mode, you should play the "Bounce2" sound.  You will need to use an if/else statement, nested inside the existing if statement(s) to do this.  Make sure that this behavior happens no matter which paddle the ball bounces off of.
3.  For this exercise, you should further decorate the actions that happen when the ball bounces off a paddle.  When the player is in expert mode, and has bounced the ball more than 5 extra times than was needed to get to expert mode, play the sound "Bounce3" instead of "Bounce" or "Bounce2".  In other words, if the player needed to get 5 bounces to go to expert mode (where we started playing "Bounce2"), then when the player gets more than 10 bounces, the game should play the "Bounce3" sound instead.
You may need to make sure of the 'chained' if...else if pattern here.