using System; using System.Linq; using Chernobyl.Collections.Generic.Event; using Chernobyl.Config; using Chernobyl.Dependency; using Chernobyl.Graphics; using Chernobyl.Plugin; using Chernobyl.StateMachine; using Chernobyl.Update; using Microsoft.Xna.Framework; using Microsoft.Xna.Framework.Content; using Microsoft.Xna.Framework.Graphics; using Microsoft.Xna.Framework.Input; namespace Chernobyl.Xna { /// /// The plug-in that allows XNA to be used within Chernobyl. /// public class XnaPlugin : Game, IPlugin { /// /// Initializes a new instance of the class. /// /// The instance that gives out services for use /// by this type and takes services from this type for use by other systems. public XnaPlugin(IEventCollection services) { Graphics = new GraphicsDeviceManager(this); Content.RootDirectory = "../../Content"; Services = services; Core core = Services.OfType().First(); if (core == null) throw new Exception("Failed to create the Chernobyl XNA plug-in. " + "The Chernobyl core must be created before this plug-in can be created."); core.Runner = Run; // Note: IEventCollection.Inject(this) is invoked in XnaPlugin.Initialize(). } /// /// The services provided by this plug-in or null if no services are /// provided. /// public new IEventCollection Services { get; set; } /// /// The device that is used to create and manager graphics level services /// such as rendering and creating graphics objects like shaders. /// [Provide] public new GraphicsDevice GraphicsDevice { get { return base.GraphicsDevice; } } /// /// The instance used by XNA to manage /// content produced by the content pipeline. /// [Provide] public new ContentManager Content { get { return base.Content; } set { base.Content = value; } } /// /// A instance which can be used to draw a /// group of XNA sprites with the same settings. /// [Provide] public SpriteBatch SpriteBatch { get; private set; } /// /// Gets the underlying operating system window for XNA. /// [Provide] public new GameWindow Window { get { return base.Window; } } /// /// The that manages the state of the entire /// application. /// [Inject] public IState ApplicationState { get; set; } /// /// An used as the default value for /// the . /// [Inject] public ILoadingState LoadingState { get; set; } /// /// The that represents the started running state /// after the configuration state (). /// [Inject] public IRunningState RunningState { get; set; } /// /// The that is responible /// for updating Chernobyl. /// [Inject(Type = typeof(IRootUpdateable))] public Update.IUpdateable RootUpdateable { get; set; } /// /// The primary that needs to be drawn. /// [Inject] public Scene MainScene { get; set; } /// /// The that manages the configuration /// and management of the graphics device for XNA. /// GraphicsDeviceManager Graphics { get; set; } /// /// Allows the game to perform any initialization it needs to before starting to run. /// This is where it can query for any required services and load any non-graphic /// related content. Calling base.Initialize will enumerate through any components /// and initialize them as well. /// protected override void Initialize() { SpriteBatch = new SpriteBatch(GraphicsDevice); Services.Inject(this); base.Initialize(); } /// /// LoadContent will be called once per game and is the place to load /// all of your content. /// protected override void LoadContent() { ApplicationState.ChildState = LoadingState; ApplicationState.ChildState = RunningState; } /// /// UnloadContent will be called once per game and is the place to unload /// all content. /// protected override void UnloadContent() { } /// /// Allows the game to run logic such as updating the world, /// checking for collisions, gathering input, and playing audio. /// /// Provides a snapshot of timing values. protected override void Update(GameTime gameTime) { // Allows the game to exit if (GamePad.GetState(PlayerIndex.One).Buttons.Back == ButtonState.Pressed || Keyboard.GetState().IsKeyDown(Keys.Escape)) this.Exit(); RootUpdateable.Update(gameTime.ElapsedGameTime); base.Update(gameTime); } /// /// This is called when the game should draw itself. /// /// Provides a snapshot of timing values. protected override void Draw(GameTime gameTime) { GraphicsDevice.Clear(ClearOptions.Target | ClearOptions.DepthBuffer, Microsoft.Xna.Framework.Graphics.Color.CornflowerBlue, 1, 0); // This code ensures alpha blending works properly. // TODO: remove this code and place it in an IDrawable that can be // used where necessary. GraphicsDevice.RenderState.AlphaBlendEnable = true; GraphicsDevice.RenderState.SourceBlend = Blend.SourceAlpha; GraphicsDevice.RenderState.DestinationBlend = Blend.InverseSourceAlpha; MainScene.Draw(); base.Draw(gameTime); } } }