PageRenderTime 16ms CodeModel.GetById 8ms app.highlight 6ms RepoModel.GetById 1ms app.codeStats 0ms

/truck/TankA/Screens/LoadingScreen.cs

https://bitbucket.org/kenzoix/tanka
C# | 162 lines | 79 code | 30 blank | 53 comment | 7 complexity | 68e1b35db169fcf1899a954d8896beb1 MD5 | raw file
  1#region File Description
  2//-----------------------------------------------------------------------------
  3// LoadingScreen.cs
  4//
  5// Microsoft XNA Community Game Platform
  6// Copyright (C) Microsoft Corporation. All rights reserved.
  7//-----------------------------------------------------------------------------
  8#endregion
  9
 10#region Using Statements
 11using System;
 12using Microsoft.Xna.Framework;
 13using Microsoft.Xna.Framework.Graphics;
 14#endregion
 15
 16namespace TankA
 17{
 18    /// <summary>
 19    /// The loading screen coordinates transitions between the menu system and the
 20    /// game itself. Normally one screen will transition off at the same time as
 21    /// the next screen is transitioning on, but for larger transitions that can
 22    /// take a longer time to load their data, we want the menu system to be entirely
 23    /// gone before we start loading the game. This is done as follows:
 24    /// 
 25    /// - Tell all the existing screens to transition off.
 26    /// - Activate a loading screen, which will transition on at the same time.
 27    /// - The loading screen watches the state of the previous screens.
 28    /// - When it sees they have finished transitioning off, it activates the real
 29    ///   next screen, which may take a long time to load its data. The loading
 30    ///   screen will be the only thing displayed while this load is taking place.
 31    /// </summary>
 32    class LoadingScreen : GameScreen
 33    {
 34        #region Fields
 35
 36        bool loadingIsSlow;
 37        bool otherScreensAreGone;
 38
 39        GameScreen[] screensToLoad;
 40
 41        #endregion
 42
 43        #region Initialization
 44
 45
 46        /// <summary>
 47        /// The constructor is private: loading screens should
 48        /// be activated via the static Load method instead.
 49        /// </summary>
 50        private LoadingScreen(ScreenManager screenManager, bool loadingIsSlow,
 51                              GameScreen[] screensToLoad)
 52        {
 53            this.loadingIsSlow = loadingIsSlow;
 54            this.screensToLoad = screensToLoad;
 55
 56            TransitionOnTime = TimeSpan.FromSeconds(0.5);
 57        }
 58
 59
 60        /// <summary>
 61        /// Activates the loading screen.
 62        /// </summary>
 63        public static void Load(ScreenManager screenManager, bool loadingIsSlow,
 64                                PlayerIndex? controllingPlayer,
 65                                params GameScreen[] screensToLoad)
 66        {
 67            // Tell all the current screens to transition off.
 68            foreach (GameScreen screen in screenManager.GetScreens())
 69                screen.ExitScreen();
 70
 71            // Create and activate the loading screen.
 72            LoadingScreen loadingScreen = new LoadingScreen(screenManager,
 73                                                            loadingIsSlow,
 74                                                            screensToLoad);
 75
 76            screenManager.AddScreen(loadingScreen, controllingPlayer);
 77        }
 78
 79
 80        #endregion
 81
 82        #region Update and Draw
 83
 84
 85        /// <summary>
 86        /// Updates the loading screen.
 87        /// </summary>
 88        public override void Update(GameTime gameTime, bool otherScreenHasFocus,
 89                                                       bool coveredByOtherScreen)
 90        {
 91            base.Update(gameTime, otherScreenHasFocus, coveredByOtherScreen);
 92
 93            // If all the previous screens have finished transitioning
 94            // off, it is time to actually perform the load.
 95            if (otherScreensAreGone)
 96            {
 97                ScreenManager.RemoveScreen(this);
 98
 99                foreach (GameScreen screen in screensToLoad)
100                {
101                    if (screen != null)
102                    {
103                        ScreenManager.AddScreen(screen, ControllingPlayer);
104                    }
105                }
106
107                // Once the load has finished, we use ResetElapsedTime to tell
108                // the  game timing mechanism that we have just finished a very
109                // long frame, and that it should not try to catch up.
110                ScreenManager.Game.ResetElapsedTime();
111            }
112        }
113
114
115        /// <summary>
116        /// Draws the loading screen.
117        /// </summary>
118        public override void Draw(GameTime gameTime)
119        {
120            // If we are the only active screen, that means all the previous screens
121            // must have finished transitioning off. We check for this in the Draw
122            // method, rather than in Update, because it isn't enough just for the
123            // screens to be gone: in order for the transition to look good we must
124            // have actually drawn a frame without them before we perform the load.
125            if ((ScreenState == ScreenState.Active) &&
126                (ScreenManager.GetScreens().Length == 1))
127            {
128                otherScreensAreGone = true;
129            }
130
131            // The gameplay screen takes a while to load, so we display a loading
132            // message while that is going on, but the menus load very quickly, and
133            // it would look silly if we flashed this up for just a fraction of a
134            // second while returning from the game to the menus. This parameter
135            // tells us how long the loading is going to take, so we know whether
136            // to bother drawing the message.
137            if (loadingIsSlow)
138            {
139                SpriteBatch spriteBatch = ScreenManager.SpriteBatch;
140                SpriteFont font = ScreenManager.Font;
141
142                const string message = "Loading...";
143
144                // Center the text in the viewport.
145                Viewport viewport = ScreenManager.GraphicsDevice.Viewport;
146                Vector2 viewportSize = new Vector2(viewport.Width, viewport.Height);
147                Vector2 textSize = font.MeasureString(message);
148                Vector2 textPosition = (viewportSize - textSize) / 2;
149
150                Color color = new Color(255, 255, 255, TransitionAlpha);
151
152                // Draw the text.
153                spriteBatch.Begin();
154                spriteBatch.DrawString(font, message, textPosition, color);
155                spriteBatch.End();
156            }
157        }
158
159
160        #endregion
161    }
162}