- Main Page
- Classes
- Files

- File List

# C:/Users/Andreas Schiffler/Desktop/SVN/NewGamePhysics/NewGamePhysics/GraphicalElements/GravitySelector.cs

    00001 ﻿// DrawableGravitySelector.cs
    00002 //
    00003
    00004 namespace NewGamePhysics.GraphicalElements
    00005 {
    00006     using System;
    00007     using System.Collections.Generic;
    00008     using System.Linq;
    00009     using System.Text;
    00010     using Microsoft.Xna.Framework;
    00011     using Microsoft.Xna.Framework.Content;
    00012     using Microsoft.Xna.Framework.Graphics;
    00013     using Microsoft.Xna.Framework.Input;
    00014
    00015     using NewGamePhysics.StateManager;
    00016     using NewGamePhysics.Utilities;
    00017     using NewGamePhysics.PhysicalElements;
    00018     using NewGamePhysics.Mathematics;
    00019     using NewGamePhysics.Physics;
    00020
    00024     public class GravitySelector
    00025     {
    00029         private ScreenManager screenManager;
    00030
    00034         private static Vector3 cameraReferenceVector = new Vector3(0.0f, 0.0f, -1.0f);
    00035
    00039         private static Vector3 cameraUpVector = new Vector3(0.0f, 1.0f, 0.0f);
    00040
    00044         private TexturedSphere planetSphere;
    00045
    00049         private Matrix projectionMatrix;
    00050
    00054         private Matrix viewMatrix;
    00055
    00059         private ValueIndicator gravityIndicator;
    00060
    00064         private ValueIndicator latitudeIndicator;
    00065
    00069         private ValueIndicator longitudeIndicator;
    00070
    00074         private ScrollingText scrollingInfoText;
    00075
    00079         private double latitude;
    00080
    00084         private double longitude;
    00085
    00090         private float displaySize;
    00091
    00095         private Vector2 screenCenter;
    00096
    00100         private Color drawColor;
    00101
    00105         private CelestialBody celestialBody;
    00106
    00110         private GravityCalculator gravityCalculator;
    00111
    00115         private Texture2D surfaceTexture;
    00116
    00120         private double gravity;
    00121
    00125         public double Gravity
    00126         {
    00127             get { return this.gravity; }
    00128         }
    00129
    00134         public float DisplaySize
    00135         {
    00136             get { return this.displaySize; }
    00137             set
    00138             {
    00139                 this.displaySize = value;
    00140
    00141                 // Lock to valid range
    00142                 if (this.displaySize < 0.0f)
    00143                 {
    00144                     this.displaySize = 0.0f;
    00145                 }
    00146                 else if (this.displaySize > 2.0f)
    00147                 {
    00148                     this.displaySize = 2.0f;
    00149                 }
    00150
    00151                 // Change display
    00152                 UpdateViewMatrix();
    00153             }
    00154         }
    00155
    00162         public GravitySelector(
    00163             ScreenManager manager,
    00164             CelestialObject celestialObject,
    00165             GravityCalculator gravityCalculator)
    00166         {
    00167             // Keep reference to screen manager for drawing
    00168             this.screenManager = manager;
    00169
    00170             // Initialize body
    00171             this.celestialBody = new CelestialBody(celestialObject);
    00172
    00173             // Load texture (default variation)
    00174             this.surfaceTexture = screenManager.Game.Content.Load<Texture2D>(
    00175                 this.celestialBody.GetTextureName(0));
    00176
    00177             // Initialize gravity calculator and value
    00178             this.gravityCalculator = gravityCalculator;
    00179             this.gravity = this.gravityCalculator.Value;
    00180
    00181             // Create textured sphere object
    00182             this.planetSphere = new TexturedSphere(
    00183                 screenManager.GraphicsDevice,
    00184                 36,
    00185                 36,
    00186                 1.0f,
    00187                 this.surfaceTexture);
    00188
    00189             // Center of screen
    00190             this.screenCenter = new Vector2(
    00191                 (float)(screenManager.GraphicsDevice.Viewport.Width / 2),
    00192                 (float)(screenManager.GraphicsDevice.Viewport.Height / 2));
    00193
    00194             // Aspect ratio of screen
    00195             float aspectRatio =
    00196                 (float)screenManager.GraphicsDevice.Viewport.Width /
    00197                 (float)screenManager.GraphicsDevice.Viewport.Height;
    00198
    00199             // Set projection matrix for view
    00200             this.projectionMatrix = Matrix.CreatePerspectiveFieldOfView(
    00201                 0.1f * MathHelper.PiOver4,
    00202                 aspectRatio,
    00203                 5.0f,
    00204                 10000.0f);
    00205
    00206             // Create a view matrix for the camera
    00207             this.displaySize = 1.0f;
    00208             UpdateViewMatrix();
    00209
    00210             // Reset values
    00211             this.latitude = 0.0;
    00212             this.longitude = 0.0;
    00213
    00214             // Create indicators and set initial value which will autoset ranges
    00215             this.latitudeIndicator = new ValueIndicator(
    00216                 this.screenManager, "Latitude", "{0,20:####.##} deg", -90.0, 90.0);
    00217             this.latitudeIndicator.SetPosition(new Vector2(20.0f, 20.0f));
    00218             this.latitudeIndicator.SetValueInRange(this.latitude);
    00219
    00220             this.longitudeIndicator = new ValueIndicator(
    00221                 this.screenManager, "Longitude", "{0,20:####.##} deg", 0.0, 360.0);
    00222             this.longitudeIndicator.SetPosition(new Vector2(20.0f, 80.0f));
    00223             this.longitudeIndicator.LowHighColoring = false;
    00224             this.longitudeIndicator.SetValueInRange(this.longitude);
    00225
    00226             this.gravityIndicator = new ValueIndicator(
    00227                 this.screenManager, "Gravity", "{0,20:###.######} N");
    00228             this.gravityIndicator.SetPosition(new Vector2((float)screenManager.GraphicsDevice.Viewport.Width - 20.0f - ValueIndicator.Width, 20.0f));
    00229             this.latitudeIndicator.LowHighColoring = false;
    00230             this.gravityIndicator.SetValue(this.gravity);
    00231
    00232             // Load fonts
    00233             this.screenManager.AddFont("retro", "Fonts/retroMedium");
    00234
    00235             // Create scrollers
    00236             SpriteFont font = this.screenManager.Fonts["game"];
    00237             int width = this.screenManager.GraphicsDevice.Viewport.Width;
    00238             int yPos = this.screenManager.GraphicsDevice.Viewport.Height - 32;
    00239             string infoText =
    00240                 "Model Info: " +
    00241                 gravityCalculator.GetModelInfo() +
    00242                 " --- Texture Info: " +
    00243                 celestialBody.GetTextureInfo() +
    00244                 "  ";
    00245             infoText = infoText.Replace("\n", "  *  ");
    00246             scrollingInfoText = new ScrollingText(infoText, font, width, yPos);
    00247             scrollingInfoText.TextScale = 0.5f;
    00248
    00249             // Set draw color
    00250             this.drawColor = new Color(1.0f, 0.25f, 0.25f);
    00251         }
    00252
    00257         public double Latitude
    00258         {
    00259             get
    00260             {
    00261                 return this.latitude;
    00262             }
    00263
    00264             set
    00265             {
    00266                 this.latitude = value;
    00267
    00268                 // Fit into range
    00269                 while (this.latitude < -90.0)
    00270                 {
    00271                     this.latitude = -90.0;
    00272                 }
    00273
    00274                 while (this.latitude > 90.0)
    00275                 {
    00276                     this.latitude = 90.0;
    00277                 }
    00278
    00279                 // Set latitude and recalculate gravity
    00280                 this.gravityCalculator.Latitude = this.latitude;
    00281                 this.gravity = this.gravityCalculator.Value;
    00282
    00283                 // Update indicators
    00284                 this.latitudeIndicator.SetValueInRange(this.latitude);
    00285                 this.gravityIndicator.SetValue(this.gravity);
    00286             }
    00287         }
    00288
    00293         public double Longitude
    00294         {
    00295             get
    00296             {
    00297                 return this.longitude;
    00298             }
    00299
    00300             set
    00301             {
    00302                 this.longitude = value;
    00303
    00304                 // Fit into range
    00305                 while (this.longitude < 0.0)
    00306                 {
    00307                     this.longitude += 360.0;
    00308                 }
    00309
    00310                 while (this.longitude > 360.0)
    00311                 {
    00312                     this.longitude -= 360.0;
    00313                 }
    00314
    00315                 // Set longitude to recalculate gravity
    00316                 this.gravityCalculator.Longitude = this.longitude;
    00317                 this.gravity = this.gravityCalculator.Value;
    00318
    00319                 // Update indicators
    00320                 this.longitudeIndicator.SetValueInRange(this.longitude);
    00321                 this.gravityIndicator.SetValue(this.gravity);
    00322             }
    00323         }
    00324
    00328         public void Update(GameTime gameTime)
    00329         {
    00330             scrollingInfoText.Update(gameTime);
    00331         }
    00332
    00337         public void Draw(GameTime gameTime)
    00338         {
    00339             // Earth is rotated by longitude and latitude
    00340             Matrix sphereRollingMatrix = Matrix.CreateRotationY((float)(this.longitude * Math.PI / 180.0))
    00341                                        * Matrix.CreateRotationX((float)(this.latitude * Math.PI / 180.0));
    00342             planetSphere.Render(
    00343                 this.screenManager.GraphicsDevice,
    00344                 this.viewMatrix,
    00345                 this.projectionMatrix,
    00346                 sphereRollingMatrix,
    00347                 this.DisplaySize);
    00348
    00349             // Overlay cross-hair
    00350             PrimitiveBatch primitiveBatch = screenManager.PrimitiveBatch;
    00351             float offset = (float)Math.Abs(Math.Sin(Math.PI * gameTime.TotalRealTime.TotalSeconds));
    00352             offset = 4.0f * MathHelper.SmoothStep(0.0f, 1.0f, offset);
    00353             float max_size = 12.0f + offset;
    00354             float min_size =  1.0f + offset;
    00355
    00356             // Lines
    00357             primitiveBatch.Begin(PrimitiveType.LineList);
    00358
    00359             primitiveBatch.AddVertex(screenCenter + new Vector2( max_size, 0.0f), this.drawColor);
    00360             primitiveBatch.AddVertex(screenCenter + new Vector2( min_size, 0.0f), this.drawColor);
    00361
    00362             primitiveBatch.AddVertex(screenCenter + new Vector2(-max_size, 0.0f), this.drawColor);
    00363             primitiveBatch.AddVertex(screenCenter + new Vector2(-min_size, 0.0f), this.drawColor);
    00364
    00365             primitiveBatch.AddVertex(screenCenter + new Vector2(0.0f,  max_size), this.drawColor);
    00366             primitiveBatch.AddVertex(screenCenter + new Vector2(0.0f,  min_size), this.drawColor);
    00367
    00368             primitiveBatch.AddVertex(screenCenter + new Vector2(0.0f, -max_size), this.drawColor);
    00369             primitiveBatch.AddVertex(screenCenter + new Vector2(0.0f, -min_size), this.drawColor);
    00370
    00371             primitiveBatch.End();
    00372
    00373             // Draw indicators and scroller
    00374             if (this.displaySize > 0.99f)
    00375             {
    00376                 longitudeIndicator.Draw(gameTime);
    00377                 latitudeIndicator.Draw(gameTime);
    00378                 gravityIndicator.Draw(gameTime);
    00379
    00380                 SpriteBatch spriteBatch = this.screenManager.SpriteBatch;
    00381                 scrollingInfoText.Draw(gameTime, spriteBatch);
    00382             }
    00383         }
    00384
    00388         private void UpdateViewMatrix()
    00389         {
    00390             // Camera distance
    00391             double cameraDistance = 30.0f;
    00392             if (this.displaySize <= 1.0f)
    00393             {
    00394                 cameraDistance = cameraDistance + MathHelper.SmoothStep(0.0f, 1.0f, (1.0f - this.displaySize)) * 100.0f * cameraDistance;
    00395             }
    00396             else
    00397             {
    00398                 cameraDistance = cameraDistance - MathHelper.SmoothStep(0.0f, 1.0f, this.displaySize - 1.0f) * cameraDistance;
    00399             }
    00400
    00401             // Right handed system, +ve z goes into screen.
    00402             // This places camera behind screen
    00403             Vector3 cameraPosition = new Vector3(0, 0, (float)cameraDistance);
    00404
    00405             // Copy the camera's reference vector.
    00406             Vector3 cameraLookAtVector = cameraReferenceVector;
    00407
    00408             // Calculate the position the camera is looking at.
    00409             cameraLookAtVector += cameraPosition;
    00410
    00411             // Create a view matrix for the camera
    00412             // The third parameter is a vector which points up
    00413             // - this indicates the direction that "up" is in
    00414             this.viewMatrix = Matrix.CreateLookAt(
    00415                 cameraPosition,
    00416                 cameraLookAtVector,
    00417                 cameraUpVector);
    00418         }
    00419     }
    00420 }