let Scene decide when to draw itself & when to play music

GitOrigin-RevId: 0eac6682b0bbe4d436707c44d9685c1e518b8295
This commit is contained in:
Colin McMillen 2020-03-02 16:46:13 -05:00
parent 29cf5eb0c9
commit 65fe870a9a
2 changed files with 23 additions and 24 deletions

View File

@ -1,4 +1,5 @@
using Microsoft.Xna.Framework; using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework.Audio;
using Microsoft.Xna.Framework.Graphics; using Microsoft.Xna.Framework.Graphics;
using System; using System;
@ -6,8 +7,6 @@ namespace SemiColinGames {
class Scene : IDisposable { class Scene : IDisposable {
const float DESIRED_ASPECT_RATIO = 1920.0f / 1080.0f; const float DESIRED_ASPECT_RATIO = 1920.0f / 1080.0f;
public bool Enabled = false;
Color backgroundColor = Color.CornflowerBlue; Color backgroundColor = Color.CornflowerBlue;
readonly GraphicsDevice graphics; readonly GraphicsDevice graphics;
@ -16,6 +15,12 @@ namespace SemiColinGames {
readonly RenderTarget2D sceneTarget; readonly RenderTarget2D sceneTarget;
readonly BasicEffect basicEffect; readonly BasicEffect basicEffect;
readonly SpriteBatch spriteBatch; readonly SpriteBatch spriteBatch;
readonly SoundEffectInstance music;
// Draw() needs to be called without IsRunningSlowly this many times before we actually
// attempt to draw the scene. This is a workaround for the fact that otherwise the first few
// frames can be really slow to draw.
int framesToSuppress = 2;
public Scene(GraphicsDevice graphics, Camera camera) { public Scene(GraphicsDevice graphics, Camera camera) {
this.graphics = graphics; this.graphics = graphics;
@ -32,6 +37,10 @@ namespace SemiColinGames {
}; };
spriteBatch = new SpriteBatch(graphics); spriteBatch = new SpriteBatch(graphics);
music = SoundEffects.IntroMusic.CreateInstance();
music.IsLooped = true;
music.Volume = 0.1f;
} }
~Scene() { ~Scene() {
@ -39,16 +48,22 @@ namespace SemiColinGames {
} }
public void Dispose() { public void Dispose() {
music.Stop();
music.Dispose();
sceneTarget.Dispose(); sceneTarget.Dispose();
basicEffect.Dispose(); basicEffect.Dispose();
spriteBatch.Dispose(); spriteBatch.Dispose();
GC.SuppressFinalize(this); GC.SuppressFinalize(this);
} }
public void Draw(World world, Player player, LinesOfSight linesOfSight, bool paused) { public void Draw(
bool isRunningSlowly, World world, Player player, LinesOfSight linesOfSight, bool paused) {
graphics.SetRenderTarget(null); graphics.SetRenderTarget(null);
graphics.Clear(backgroundColor); graphics.Clear(backgroundColor);
if (!Enabled) {
// Enable the scene after we've gotten enough non-slow frames.
if (framesToSuppress > 0 && !isRunningSlowly) {
framesToSuppress--;
return; return;
} }
@ -110,6 +125,9 @@ namespace SemiColinGames {
string text = "Paused"; string text = "Paused";
Vector2 position = Textures.BannerFont.CenteredOn(text, camera.HalfSize); Vector2 position = Textures.BannerFont.CenteredOn(text, camera.HalfSize);
Text.DrawOutlined(spriteBatch, Textures.BannerFont, text, position, Color.White); Text.DrawOutlined(spriteBatch, Textures.BannerFont, text, position, Color.White);
music.Pause();
} else {
music.Play();
} }
spriteBatch.End(); spriteBatch.End();

View File

@ -1,5 +1,4 @@
using Microsoft.Xna.Framework; using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework.Audio;
using Microsoft.Xna.Framework.Graphics; using Microsoft.Xna.Framework.Graphics;
using Microsoft.Xna.Framework.Input; using Microsoft.Xna.Framework.Input;
using MonoGame.Framework.Utilities; using MonoGame.Framework.Utilities;
@ -21,10 +20,6 @@ namespace SemiColinGames {
readonly FpsCounter fpsCounter = new FpsCounter(); readonly FpsCounter fpsCounter = new FpsCounter();
readonly Timer updateTimer = new Timer(TARGET_FRAME_TIME / 2.0, "UpdateTimer"); readonly Timer updateTimer = new Timer(TARGET_FRAME_TIME / 2.0, "UpdateTimer");
readonly Timer drawTimer = new Timer(TARGET_FRAME_TIME / 2.0, "DrawTimer"); readonly Timer drawTimer = new Timer(TARGET_FRAME_TIME / 2.0, "DrawTimer");
// Draw() needs to be called without IsRunningSlowly this many times before we actually
// attempt to draw the scene. This is a workaround for the fact that otherwise the first few
// frames can be really slow to draw.
int framesToSuppress;
int levelIdx = -1; int levelIdx = -1;
Scene scene; Scene scene;
@ -68,15 +63,10 @@ namespace SemiColinGames {
SoundEffects.Load(Content); SoundEffects.Load(Content);
Textures.Load(Content); Textures.Load(Content);
linesOfSight = new LinesOfSight(GraphicsDevice); linesOfSight = new LinesOfSight(GraphicsDevice);
SoundEffectInstance music = SoundEffects.IntroMusic.CreateInstance();
music.IsLooped = true;
music.Volume = 0.1f;
music.Play();
LoadLevel(); LoadLevel();
} }
private void LoadLevel() { private void LoadLevel() {
framesToSuppress = 2;
camera = new Camera(); camera = new Camera();
player = new Player(); player = new Player();
levelIdx++; levelIdx++;
@ -143,15 +133,6 @@ namespace SemiColinGames {
protected override void Draw(GameTime gameTime) { protected override void Draw(GameTime gameTime) {
drawTimer.Start(); drawTimer.Start();
// Enable the scene after we've gotten enough non-slow frames.
// TODO: the Scene should handle this, really.
if (framesToSuppress > 0 && !gameTime.IsRunningSlowly) {
framesToSuppress--;
if (framesToSuppress == 0) {
scene.Enabled = true;
}
}
// We need to update the FPS counter in Draw() since Update() might get called more // We need to update the FPS counter in Draw() since Update() might get called more
// frequently, especially when gameTime.IsRunningSlowly. // frequently, especially when gameTime.IsRunningSlowly.
fpsCounter.Update(); fpsCounter.Update();
@ -163,7 +144,7 @@ namespace SemiColinGames {
Debug.SetFpsText(fpsText); Debug.SetFpsText(fpsText);
scene.Draw(world, player, linesOfSight, paused); scene.Draw(gameTime.IsRunningSlowly, world, player, linesOfSight, paused);
base.Draw(gameTime); base.Draw(gameTime);
drawTimer.Stop(); drawTimer.Stop();