- Main Page
- Classes
- Files

- File List

# C:/Users/Andreas Schiffler/Desktop/SVN/NewGamePhysics/MontyHallGame/Screens/MontyHallGameplayScreen.cs

    00001 //-----------------------------------------------------------------------------
    00002 // MontyHallGameplayScreen.cs
    00003 // (C) A. Schiffler, 2009-2011
    00004 //-----------------------------------------------------------------------------
    00005
    00006 namespace MontyHallGame
    00007 {
    00008     using System;
    00009     using System.Threading;
    00010
    00011     using Microsoft.Xna.Framework;
    00012     using Microsoft.Xna.Framework.Content;
    00013     using Microsoft.Xna.Framework.Graphics;
    00014     using Microsoft.Xna.Framework.Input;
    00015
    00016     using NewGamePhysics.StateManager;
    00017     using NewGamePhysics.Utilities;
    00018     using NewGamePhysics.GraphicalElements;
    00019     using NewGamePhysics.PhysicalElements;
    00020
    00026     class MontyHallGameplayScreen : GameScreen
    00027     {
    00028         #region Fields
    00029
    00033         private ContentManager contentManager;
    00034
    00038         private ScrollingText scrollingInfoText;
    00039
    00043         private int[] doorState;
    00044
    00052         private int gamePhase;
    00053
    00057         private int selectorPosition;
    00058
    00062         private int preselectedDoor;
    00063
    00067         private int prizePosition;
    00068
    00072         private long waitTicks;
    00073
    00074         #endregion
    00075
    00076         #region Initialization
    00077
    00081         public MontyHallGameplayScreen()
    00082         {
    00083             TransitionOnTime = TimeSpan.FromSeconds(1.5);
    00084             TransitionOffTime = TimeSpan.FromSeconds(1.5);
    00085         }
    00086
    00090         public override void LoadContent()
    00091         {
    00092             if (this.contentManager == null)
    00093             {
    00094                 this.contentManager = new ContentManager(ScreenManager.Game.Services, "Content");
    00095             }
    00096
    00097             // Reset doors
    00098             doorState = new int[3];
    00099             doorState[0] = 0;
    00100             doorState[1] = 0;
    00101             doorState[2] = 0;
    00102
    00103             // Reset state
    00104             gamePhase = 1;
    00105             preselectedDoor = -1; // none
    00106             selectorPosition = 1; // middle
    00107
    00108             // Randomly selecy a prize position
    00109             prizePosition = MontyHallGame.state.Rng.Next(0, 2);
    00110
    00111             // Reset delay
    00112             waitTicks = 0;
    00113
    00114             // Reset game time
    00115             ScreenManager.Game.ResetElapsedTime();
    00116
    00117             // Reset play accumulator
    00118             MontyHallGame.state.playTime = 0.0;
    00119
    00120             // Create scrollers
    00121             SpriteFont font = ScreenManager.Fonts["menu"];
    00122             MontyHallGame game = (MontyHallGame)ScreenManager.Game;
    00123             int width = game.GraphicsDevice.Viewport.Width;
    00124             scrollingInfoText = new ScrollingText("", font, width, 30);
    00125             scrollingInfoText.TextColor = Color.Black;
    00126
    00127             // Play sound
    00128             ScreenManager.Sounds["show"].Play();
    00129
    00130             // Set initial text
    00131             scrollingInfoText.Text = "Press [Left] or [Right], then [Space] to pre-select a door to Open later.";
    00132         }
    00133
    00137         public override void UnloadContent()
    00138         {
    00139             this.contentManager.Unload();
    00140         }
    00141
    00142         #endregion
    00143
    00144         #region Update and Draw
    00145
    00151         public override void Update(GameTime gameTime, bool otherScreenHasFocus,
    00152                                                        bool coveredByOtherScreen)
    00153         {
    00154             base.Update(gameTime, otherScreenHasFocus, coveredByOtherScreen);
    00155
    00156             if (IsActive)
    00157             {
    00158                 // Accumulate active game time
    00159                 MontyHallGame.state.playTime += gameTime.ElapsedRealTime.TotalSeconds;
    00160
    00161                 // Handle game phases
    00162                 switch (gamePhase)
    00163                 {
    00164                     case 1:
    00165                         // Nothing to do here, we just wait for the
    00166                         // game phase to change based on user input.
    00167                         break;
    00168                     case 2:
    00169                         // Switch the doors around, hidden to the user
    00170                         NextDoor();
    00171                         break;
    00172                     case 3:
    00173                         // Nothing to do here, we just wait for the
    00174                         // game phase to change based on user input.
    00175                         break;
    00176                     case 4:
    00177                         if (waitTicks == 0)
    00178                         {
    00179                             // Add a 1 sec delay to see the gold.
    00180                             waitTicks = gameTime.TotalRealTime.Ticks + 1 * (1000000000/100);
    00181                         }
    00182                         else if (gameTime.TotalRealTime.Ticks > waitTicks)
    00183                         {
    00184                             // Determine if there was a winner and end game
    00185                             if (doorState[prizePosition] == 1)
    00186                             {
    00187                                 MontyHallGame.state.Wins++;
    00188
    00189                                 // Show game over screen
    00190                                 ScreenManager.AddScreen(
    00191                                     new MontyHallGameOverScreen("*** Winner ***"), null);
    00192
    00193                                 // Play sound
    00194                                 ScreenManager.Sounds["money"].Play();
    00195                             }
    00196                             else
    00197                             {
    00198                                 MontyHallGame.state.Losses++;
    00199
    00200                                 // Show game over screen
    00201                                 ScreenManager.AddScreen(
    00202                                     new MontyHallGameOverScreen("Sorry - You Lost!"), null);
    00203
    00204                                 // Play sound
    00205                                 ScreenManager.Sounds["loser"].Play();
    00206                             }
    00207                         }
    00208                         break;
    00209                 }
    00210
    00211                 // Update scrollers
    00212                 scrollingInfoText.Update(gameTime);
    00213             }
    00214         }
    00215
    00220         public override void HandleInput(InputState input)
    00221         {
    00222             if (input == null)
    00223             {
    00224                 throw new ArgumentNullException("input");
    00225             }
    00226
    00227             // Look up inputs for the active player profile.
    00228             int playerIndex = (int)ControllingPlayer.Value;
    00229
    00230             KeyboardState keyboardState = input.CurrentKeyboardStates[playerIndex];
    00231             GamePadState gamePadState = input.CurrentGamePadStates[playerIndex];
    00232
    00233             // The game pauses either if the user presses the pause button, or if
    00234             // they unplug the active gamepad. This requires us to keep track of
    00235             // whether a gamepad was ever plugged in, because we don't want to pause
    00236             // on PC if they are playing with a keyboard and have no gamepad at all!
    00237             bool gamePadDisconnected = !gamePadState.IsConnected &&
    00238                                        input.GamePadWasConnected[playerIndex];
    00239
    00240             if (input.IsInputCancel(ControllingPlayer) || gamePadDisconnected)
    00241             {
    00242                 ScreenManager.AddScreen(new MontyHallPauseMenuScreen(), ControllingPlayer);
    00243             }
    00244             else
    00245             {
    00246
    00247                 // Do doors
    00248                 if (input.IsNewInputRight(ControllingPlayer))
    00249                 {
    00250                     // Play sound
    00251                     ScreenManager.Sounds["click"].Play();
    00252
    00253                     // Switc doors
    00254                     NextDoor();
    00255                 }
    00256                 else if (input.IsNewInputLeft(ControllingPlayer))
    00257                 {
    00258                     // Play sound
    00259                     ScreenManager.Sounds["click"].Play();
    00260
    00261                     // Switch doors
    00262                     PreviousDoor();
    00263                 }
    00264
    00265                 // Open or select a door
    00266                 if (input.IsInputSelect(ControllingPlayer))
    00267                 {
    00268                     switch (gamePhase)
    00269                     {
    00270                         case 1:
    00271                             // Lock in the preselected position
    00272                             preselectedDoor = selectorPosition;
    00273
    00274                             // Switch Doors
    00275                             NextDoor();
    00276
    00277                             // Update Text
    00278                             scrollingInfoText.Text = "Press [Space] and Monty will help by opening loosing door for you.";
    00279
    00280                             // Play sound
    00281                             ScreenManager.Sounds["crowd"].Play(0.33f, 0.0f, 0.0f);
    00282
    00283                             // Next Game Phase
    00284                             gamePhase++;
    00285                             break;
    00286                         case 2:
    00287                             // Update selector so we do not reveal the prize
    00288                             if (selectorPosition == prizePosition)
    00289                             {
    00290                                 NextDoor();
    00291                             }
    00292
    00293                             // Open the door where the selector is placed
    00294                             doorState[selectorPosition] = 1;
    00295
    00296                             // Play sound
    00297                             ScreenManager.Sounds["door"].Play();
    00298
    00299                             // Set next door to the preselected one
    00300                             selectorPosition = preselectedDoor;
    00301
    00302                             // Update Text
    00303                             scrollingInfoText.Text = "Stay or switch doors? Use [Left] or [Right] to select another door, then press [Space] try to get your prize.";
    00304
    00305                             // Next Game Phase
    00306                             gamePhase++;
    00307                             break;
    00308                         case 3:
    00309                             // Open the door where the selector is placed
    00310                             doorState[selectorPosition] = 1;
    00311
    00312                             // Update number of door-switches
    00313                             if (selectorPosition != preselectedDoor)
    00314                             {
    00315                                 MontyHallGame.state.Switches++;
    00316                             }
    00317
    00318                             // Clear text
    00319                             scrollingInfoText.Text = "";
    00320
    00321                             // Play sound
    00322                             ScreenManager.Sounds["door"].Play();
    00323
    00324                             // Next Game Phase
    00325                             gamePhase++;
    00326                             break;
    00327                     }
    00328                 }
    00329             }
    00330         }
    00331
    00335         public override void Draw(GameTime gameTime)
    00336         {
    00337             // Get drawing helpers and textures
    00338             PrimitiveBatch primitiveBatch = ScreenManager.PrimitiveBatch;
    00339             SpriteBatch spriteBatch = ScreenManager.SpriteBatch;
    00340             Viewport viewport = ScreenManager.GraphicsDevice.Viewport;
    00341
    00342             // Determine door texture
    00343             string doorTextureName = "mdoor_";
    00344             doorTextureName += (doorState[0] == 0) ? "c" : "o";
    00345             doorTextureName += (doorState[1] == 0) ? "c" : "o";
    00346             doorTextureName += (doorState[2] == 0) ? "c" : "o";
    00347             Texture2D doorTexture = ScreenManager.Textures[doorTextureName];
    00348
    00349             // Draw doors
    00350             double aspectRatio = 1024.0 / 768.0;
    00351             int displayWidth = (int)Math.Truncate((double)viewport.Height * aspectRatio);
    00352             Rectangle dest = new Rectangle(
    00353                 (viewport.Width - displayWidth) / 2, 0,
    00354                 displayWidth, viewport.Height);
    00355             spriteBatch.Begin(SpriteBlendMode.AlphaBlend);
    00356             spriteBatch.Draw(doorTexture, dest, Color.White);
    00357             spriteBatch.End();
    00358
    00359             // Draw selector
    00360             if ((gameTime.TotalRealTime.Milliseconds % 500) < 400)
    00361             {
    00362                 switch (gamePhase)
    00363                 {
    00364                     case 1:
    00365                         dest = new Rectangle(
    00366                         viewport.Width / 2 +
    00367                             (int)((float)displayWidth * 0.29f * (float)(selectorPosition - 1))
    00368                             - 60,
    00369                         viewport.Height - 100,
    00370                         100, 50);
    00371                         spriteBatch.Begin(SpriteBlendMode.AlphaBlend);
    00372                         spriteBatch.Draw(ScreenManager.Textures["opensign"], dest, Color.White);
    00373                         spriteBatch.End();
    00374                         break;
    00375                     case 2:
    00376                         for (int i = 0; i < 3; i++)
    00377                         {
    00378                             if (i != preselectedDoor)
    00379                             {
    00380                                 dest = new Rectangle(
    00381                                 viewport.Width / 2 +
    00382                                     (int)((float)displayWidth * 0.29f * (float)(i - 1))
    00383                                     - 55,
    00384                                 viewport.Height - 100,
    00385                                 90, 90);
    00386                                 spriteBatch.Begin(SpriteBlendMode.AlphaBlend);
    00387                                 spriteBatch.Draw(ScreenManager.Textures["monty"], dest, Color.White);
    00388                                 spriteBatch.End();
    00389                             }
    00390                         }
    00391                         break;
    00392                     case 3:
    00393                         dest = new Rectangle(
    00394                         viewport.Width / 2 +
    00395                             (int)((float)displayWidth * 0.29f * (float)(selectorPosition - 1))
    00396                             - 60,
    00397                         viewport.Height - 100,
    00398                         100, 100);
    00399                         spriteBatch.Begin(SpriteBlendMode.AlphaBlend);
    00400                         spriteBatch.Draw(ScreenManager.Textures["key"], dest, Color.White);
    00401                         spriteBatch.End();
    00402                         break;
    00403                 }
    00404             }
    00405
    00406             // Draw pre-selection if set
    00407             if (preselectedDoor >= 0)
    00408             {
    00409                 dest = new Rectangle(
    00410                 viewport.Width / 2 +
    00411                     (int)((float)displayWidth * 0.29f * (float)(preselectedDoor - 1))
    00412                     - 30,
    00413                 (int)((float)viewport.Height * 0.25f),
    00414                 50, 25);
    00415                 spriteBatch.Begin(SpriteBlendMode.AlphaBlend);
    00416                 spriteBatch.Draw(ScreenManager.Textures["opensign"], dest, Color.White);
    00417                 spriteBatch.End();
    00418             }
    00419
    00420             // Draw prize if won
    00421             if ((gamePhase == 4) && (doorState[prizePosition] != 0))
    00422             {
    00423                 dest = new Rectangle(
    00424                 viewport.Width / 2 +
    00425                     (int)((float)displayWidth * 0.29f * (float)(prizePosition - 1))
    00426                     - 35,
    00427                 viewport.Height - 190,
    00428                 80, 80);
    00429                 spriteBatch.Begin(SpriteBlendMode.AlphaBlend);
    00430                 spriteBatch.Draw(ScreenManager.Textures["potogold"], dest, Color.White);
    00431                 spriteBatch.End();
    00432             }
    00433
    00434             // Draw scroller
    00435             scrollingInfoText.Draw(gameTime, spriteBatch);
    00436
    00437             // If the game is transitioning on or off, fade it out to black.
    00438             if (TransitionPosition > 0)
    00439             {
    00440                 ScreenManager.FadeBackBufferToBlack(255 - TransitionAlpha);
    00441             }
    00442         }
    00443
    00444         #endregion
    00445
    00450         private void NextDoor()
    00451         {
    00452             do
    00453             {
    00454                 selectorPosition = (selectorPosition + 1);
    00455                 if (selectorPosition > 2)
    00456                 {
    00457                     selectorPosition = 0;
    00458                 }
    00459             } while (((selectorPosition == preselectedDoor) && (gamePhase < 3)) ||
    00460                 (doorState[selectorPosition] != 0));
    00461         }
    00462
    00467         private void PreviousDoor()
    00468         {
    00469             do
    00470             {
    00471                 selectorPosition = (selectorPosition - 1);
    00472                 if (selectorPosition < 0)
    00473                 {
    00474                     selectorPosition = 2;
    00475                 }
    00476             } while (((selectorPosition == preselectedDoor) && (gamePhase < 3)) ||
    00477                 (doorState[selectorPosition] != 0));
    00478         }
    00479     }
    00480 }