Began working on a graphical playground for testing.
Improved SDL exception class. Engine code changes. General progress.
This commit is contained in:
parent
0f0395fd63
commit
a013c476e7
@ -14,18 +14,21 @@ namespace SlatedGameToolkit.Framework.Exceptions
|
||||
/// Creates an SDL exception.
|
||||
/// </summary>
|
||||
/// <param name="Fetch">Whether or not to fetch the last error message that occurred in SDL.</param>
|
||||
public SDLException(bool autoFlush = true) : base() {
|
||||
public SDLException(bool autoFlush = true) : base(autoFlush ? SDL.SDL_GetError() : "SDL error has occurred.") {
|
||||
if (autoFlush) {
|
||||
SDLMessage = SDL.SDL_GetError();
|
||||
SDL.SDL_ClearError();
|
||||
}
|
||||
}
|
||||
|
||||
public SDLException(string message, Exception inner) : base(message, inner) {
|
||||
|
||||
public SDLException(string message, bool autoFlush = true) : base(message + " (" + (autoFlush ? SDL.SDL_GetError() : "SDL error has occurred.") + ")") {
|
||||
if (autoFlush) {
|
||||
SDLMessage = SDL.SDL_GetError();
|
||||
SDL.SDL_ClearError();
|
||||
}
|
||||
}
|
||||
|
||||
public SDLException(string message, bool autoFlush = true) : base(message) {
|
||||
public SDLException(string message, Exception inner, bool autoFlush = true) : base(message + " (" + (autoFlush ? SDL.SDL_GetError() : "SDL error has occurred.") + ")", inner) {
|
||||
if (autoFlush) {
|
||||
SDLMessage = SDL.SDL_GetError();
|
||||
SDL.SDL_ClearError();
|
||||
|
@ -17,47 +17,69 @@ namespace SlatedGameToolkit.Framework {
|
||||
CreateLogger();
|
||||
private static readonly object ignitionLock = new object();
|
||||
private static Thread thread;
|
||||
private static volatile bool exit = false, loopCompleted = true;
|
||||
private static long updateDeltaTime = 50, frameDeltaTime = 0;
|
||||
private static volatile bool exit = false, stopped = true;
|
||||
private static volatile bool deltaChanged = true;
|
||||
private static long updateDeltaTime = 25, frameDeltaTime = 16;
|
||||
|
||||
/// <summary>
|
||||
/// The amount of updates per second.
|
||||
/// Is floored to milleseconds.
|
||||
/// Maximum updates per second is 200.
|
||||
/// </summary>
|
||||
/// <value>The updates per second.</value>
|
||||
public static double UpdatesPerSecond {
|
||||
get {
|
||||
return TimeSpan.FromMilliseconds(1 / updateDeltaTime).TotalSeconds;
|
||||
return 1 / TimeSpan.FromMilliseconds(updateDeltaTime).TotalSeconds;
|
||||
}
|
||||
set {
|
||||
Interlocked.Exchange(ref updateDeltaTime, (long) TimeSpan.FromSeconds(1 / value).TotalMilliseconds);
|
||||
Interlocked.Exchange(ref updateDeltaTime, Math.Min(5, (long) TimeSpan.FromSeconds(1 / value).TotalMilliseconds));
|
||||
deltaChanged = true;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// The target frames per second. Will not go above this number, but may dip below this number.
|
||||
/// This value is floored to millesconds.
|
||||
/// This value is floored to millesconds units.
|
||||
/// Setting this to 0 renders as many frames as the system can handle.
|
||||
/// Default is 60.
|
||||
/// </summary>
|
||||
/// <value>The target frames per second.</value>
|
||||
public static double targetFPS {
|
||||
get {
|
||||
return TimeSpan.FromMilliseconds(1 / frameDeltaTime).TotalSeconds;
|
||||
if (frameDeltaTime == 0) return 0;
|
||||
return 1 / TimeSpan.FromMilliseconds(frameDeltaTime).TotalSeconds;
|
||||
}
|
||||
set {
|
||||
if (value == 0) Interlocked.Exchange(ref frameDeltaTime, 0);
|
||||
Interlocked.Exchange(ref frameDeltaTime, (long) TimeSpan.FromSeconds(1 / value).TotalMilliseconds);
|
||||
deltaChanged = true;
|
||||
}
|
||||
}
|
||||
|
||||
public static bool Running {
|
||||
get {
|
||||
return !stopped;
|
||||
}
|
||||
}
|
||||
|
||||
private static void Loop(Object o) {
|
||||
if (!(o is Manager)) throw new InternalFrameworkException(String.Format("Expected manager object for asynchronous loop. Got {0}", o));
|
||||
Manager manager = (Manager) o;
|
||||
manager.initialize();
|
||||
long currentTime = DateTimeOffset.Now.ToUnixTimeMilliseconds();
|
||||
long timePassedFromLastUpdate = 0;
|
||||
long timePassedFromLastRender = 0;
|
||||
loopCompleted = false;
|
||||
long updateDeltaTime = 0;
|
||||
long frameDeltaTime = 0;
|
||||
stopped = false;
|
||||
logger.Information("Game engine initiated.");
|
||||
while (!exit) {
|
||||
long updateDeltaTime = Interlocked.Read(ref GameEngine.updateDeltaTime);
|
||||
long frameDeltaTime = Interlocked.Read(ref GameEngine.frameDeltaTime);
|
||||
if (deltaChanged) {
|
||||
updateDeltaTime = Interlocked.Read(ref GameEngine.updateDeltaTime);
|
||||
frameDeltaTime = Interlocked.Read(ref GameEngine.frameDeltaTime);
|
||||
deltaChanged = false;
|
||||
}
|
||||
|
||||
long frameStart = DateTimeOffset.Now.ToUnixTimeMilliseconds();
|
||||
long difference = frameStart - currentTime;
|
||||
currentTime = frameStart;
|
||||
@ -74,8 +96,10 @@ namespace SlatedGameToolkit.Framework {
|
||||
timePassedFromLastRender = 0;
|
||||
}
|
||||
}
|
||||
loopCompleted = true;
|
||||
manager.Dispose();
|
||||
stopped = true;
|
||||
SDL.SDL_Quit();
|
||||
logger.Information("Game engine has stopped.");
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@ -96,28 +120,25 @@ namespace SlatedGameToolkit.Framework {
|
||||
/// Requests to start the game engine.
|
||||
/// </summary>
|
||||
/// <returns>True iff the engine is not already running.</returns>
|
||||
private static bool Ignite(Manager manager) {
|
||||
public static bool Ignite(Manager manager) {
|
||||
if (manager == null) throw new ArgumentNullException("manager");
|
||||
SDL.SDL_version SDLVersion;
|
||||
SDL.SDL_version SDLBuiltVersion;
|
||||
SDL.SDL_GetVersion(out SDLVersion);
|
||||
SDL.SDL_VERSION(out SDLBuiltVersion);
|
||||
logger.Information(String.Format("Attempting to initiate game engine with SDL version: {0}", SDLVersion.ToString()));
|
||||
if (SDL.SDL_VERSION_ATLEAST(SDLBuiltVersion.major, SDLBuiltVersion.minor, SDLBuiltVersion.patch)) {
|
||||
logger.Warning(String.Format("Engine was designed with SDL version {0}, currently running on {1}", SDLVersion.ToString(), SDLBuiltVersion.ToString()));
|
||||
logger.Information(String.Format("Attempting to initiate game engine with SDL version: {0}.{1}.{2}", SDLVersion.major, SDLVersion.minor, SDLVersion.patch));
|
||||
if (!SDL.SDL_VERSION_ATLEAST(SDLBuiltVersion.major, SDLBuiltVersion.minor, SDLBuiltVersion.patch)) {
|
||||
logger.Warning(String.Format("Engine was designed with SDL version {0}.{1}.{2}, currently running on {3}.{4}.{5}", SDLBuiltVersion.major, SDLBuiltVersion.minor, SDLBuiltVersion.patch, SDLVersion.major, SDLVersion.minor, SDLVersion.patch));
|
||||
if (SDLVersion.major < 2) {
|
||||
logger.Error("This engine was designed to work with SDL2. The version you're currently running is severely outdated.");
|
||||
throw new FrameworkUsageException("Outdated SDL binaries.");
|
||||
}
|
||||
}
|
||||
lock (ignitionLock) {
|
||||
if (!loopCompleted) return false;
|
||||
loopCompleted = false;
|
||||
|
||||
if (SDL.SDL_GL_SetAttribute(SDL.SDL_GLattr.SDL_GL_CONTEXT_MAJOR_VERSION, 3) < 0) throw new FrameworkSDLException();
|
||||
if (SDL.SDL_GL_SetAttribute(SDL.SDL_GLattr.SDL_GL_CONTEXT_MINOR_VERSION, 1) < 0) throw new FrameworkSDLException();
|
||||
if (SDL.SDL_GL_SetAttribute(SDL.SDL_GLattr.SDL_GL_CONTEXT_PROFILE_MASK, SDL.SDL_GLprofile.SDL_GL_CONTEXT_PROFILE_CORE) < 0) throw new FrameworkSDLException();
|
||||
|
||||
if (!stopped) {
|
||||
logger.Warning("Engine is already running.");
|
||||
return false;
|
||||
}
|
||||
exit = false;
|
||||
if (SDL.SDL_Init(SDL.SDL_INIT_VIDEO) != 0) {
|
||||
throw new FrameworkSDLException();
|
||||
@ -125,6 +146,11 @@ namespace SlatedGameToolkit.Framework {
|
||||
if (SDL.SDL_Init(SDL.SDL_INIT_AUDIO) != 0) {
|
||||
throw new FrameworkSDLException();
|
||||
}
|
||||
|
||||
if (SDL.SDL_GL_SetAttribute(SDL.SDL_GLattr.SDL_GL_CONTEXT_MAJOR_VERSION, 3) < 0) throw new FrameworkSDLException();
|
||||
if (SDL.SDL_GL_SetAttribute(SDL.SDL_GLattr.SDL_GL_CONTEXT_MINOR_VERSION, 1) < 0) throw new FrameworkSDLException();
|
||||
if (SDL.SDL_GL_SetAttribute(SDL.SDL_GLattr.SDL_GL_CONTEXT_PROFILE_MASK, SDL.SDL_GLprofile.SDL_GL_CONTEXT_PROFILE_CORE) < 0) throw new FrameworkSDLException();
|
||||
|
||||
thread = new Thread(Loop);
|
||||
thread.Start(manager);
|
||||
return true;
|
||||
|
@ -207,9 +207,13 @@ namespace SlatedGameToolkit.Framework.Graphics.Window
|
||||
/// Makes this window the window that is currently being drawn to.
|
||||
/// More specifically, it sets the OpenGL Context associated with this window to be the one
|
||||
/// that is actively receiving all OpenGL calls.
|
||||
///
|
||||
/// If the current context is already of this window, nothing happens.
|
||||
/// </summary>
|
||||
public void DrawToWindow() {
|
||||
SDL.SDL_GL_MakeCurrent(window, glContext);
|
||||
if (SDL.SDL_GL_GetCurrentContext() != glContext) {
|
||||
SDL.SDL_GL_MakeCurrent(window, glContext);
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
|
@ -1,13 +0,0 @@
|
||||
using SDL2;
|
||||
|
||||
namespace SlatedGameToolkit.Framework.Input
|
||||
{
|
||||
internal class InputMatrix {
|
||||
public void update() {
|
||||
SDL.SDL_Event inputEvent;
|
||||
while (SDL.SDL_PollEvent(out inputEvent) != 0) {
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
@ -26,6 +26,10 @@ namespace SlatedGameToolkit.Framework.StateSystem
|
||||
if (!this.states.TryGetValue(initialState, out currentState)) throw new ArgumentException("The requested initial state name does not exist in the provided list of states.");
|
||||
}
|
||||
|
||||
internal void initialize() {
|
||||
thread = Thread.CurrentThread;
|
||||
}
|
||||
|
||||
internal void update(double delta) {
|
||||
if (nextState != null) {
|
||||
if (currentState.Deactivate() & nextState.Activate()) {
|
||||
|
@ -0,0 +1,60 @@
|
||||
using SlatedGameToolkit.Framework;
|
||||
using SlatedGameToolkit.Framework.StateSystem;
|
||||
using SlatedGameToolkit.Tools.System;
|
||||
using SlatedGameToolkit.Tools.System.Interaction;
|
||||
using SlatedGameToolkit.Tools.Utilities.GraphicalPlayground;
|
||||
|
||||
namespace SlatedGameToolkit.Tools.Commands
|
||||
{
|
||||
public class GraphicalPlaygroundCommand : IInvocable
|
||||
{
|
||||
private readonly string[] invokers = new string[] {"playground"};
|
||||
|
||||
public bool Execute(IInteractable interactable, string[] args)
|
||||
{
|
||||
if (args.Length != 1) return false;
|
||||
if (args[0].Equals("start")) {
|
||||
if (GameEngine.Running) {
|
||||
interactable.Tell("Engine is already running!");
|
||||
return true;
|
||||
}
|
||||
Manager manager = new Manager("main state", new MainState());
|
||||
GameEngine.Ignite(manager);
|
||||
return true;
|
||||
} else if (args[0].Equals("stop")) {
|
||||
if (!GameEngine.Running) {
|
||||
interactable.Tell("Engine was never running!");
|
||||
return true;
|
||||
}
|
||||
GameEngine.Stop();
|
||||
return true;
|
||||
} else if (args[0].Equals("status")) {
|
||||
interactable.Tell("Running: " + GameEngine.Running);
|
||||
interactable.Tell("Target FPS: " + GameEngine.targetFPS);
|
||||
interactable.Tell("Target Update Rate: " + GameEngine.UpdatesPerSecond);
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
public string getDescription()
|
||||
{
|
||||
return "Starts and stops the graphical playground.";
|
||||
}
|
||||
|
||||
public string[] GetInvokers()
|
||||
{
|
||||
return invokers;
|
||||
}
|
||||
|
||||
public string getUsage(string arg)
|
||||
{
|
||||
return "Usage: \"playground [start | stop | status]\" the required argument being whether to start, stop or get the current status of the game engine.";
|
||||
}
|
||||
|
||||
public void Dispose()
|
||||
{
|
||||
GameEngine.Stop();
|
||||
}
|
||||
}
|
||||
}
|
@ -52,5 +52,10 @@ namespace SlatedGameToolkit.Tools.Commands
|
||||
{
|
||||
return invokers;
|
||||
}
|
||||
|
||||
public void Dispose()
|
||||
{
|
||||
|
||||
}
|
||||
}
|
||||
}
|
@ -27,5 +27,9 @@ namespace SlatedGameToolkit.Tools.Commands
|
||||
{
|
||||
return invokers;
|
||||
}
|
||||
|
||||
public void Dispose()
|
||||
{
|
||||
}
|
||||
}
|
||||
}
|
@ -11,8 +11,10 @@ namespace SlatedGameToolkit.Tools
|
||||
static private bool running;
|
||||
static void Main(string[] args)
|
||||
{
|
||||
CommandMap commands = new CommandMap(new StopCommand());
|
||||
CommandMap commands = new CommandMap();
|
||||
commands.Add(new StopCommand());
|
||||
commands.Add(new HelpCommand(commands));
|
||||
commands.Add(new GraphicalPlaygroundCommand());
|
||||
CommandProcessor processor = new CommandProcessor("The command \"{input}\" was not understood. Please type \"help\" for more information.", commands);
|
||||
AssemblyName name = Assembly.GetExecutingAssembly().GetName();
|
||||
ConsoleInteraction consoleInteracter = new ConsoleInteraction("Tools");
|
||||
@ -24,6 +26,7 @@ namespace SlatedGameToolkit.Tools
|
||||
processor.Process(consoleInteracter);
|
||||
}
|
||||
consoleInteracter.Tell("Exiting tool.");
|
||||
commands.Dispose();
|
||||
}
|
||||
|
||||
public static void Stop() {
|
||||
|
@ -5,7 +5,7 @@ using SlatedGameToolkit.Tools.System.Interaction;
|
||||
|
||||
namespace SlatedGameToolkit.Tools.System
|
||||
{
|
||||
public class CommandMap : ICollection<IInvocable> {
|
||||
public class CommandMap : ICollection<IInvocable>, IDisposable {
|
||||
Dictionary<string, IInvocable> invocations;
|
||||
HashSet<IInvocable> values;
|
||||
|
||||
@ -79,5 +79,17 @@ namespace SlatedGameToolkit.Tools.System
|
||||
values.Remove(item);
|
||||
return true;
|
||||
}
|
||||
|
||||
public void Dispose()
|
||||
{
|
||||
foreach (IInvocable invocable in this)
|
||||
{
|
||||
invocable.Dispose();
|
||||
}
|
||||
}
|
||||
|
||||
~CommandMap() {
|
||||
Dispose();
|
||||
}
|
||||
}
|
||||
}
|
@ -1,8 +1,9 @@
|
||||
using System;
|
||||
using SlatedGameToolkit.Tools.System.Interaction;
|
||||
|
||||
namespace SlatedGameToolkit.Tools.System
|
||||
{
|
||||
public interface IInvocable
|
||||
public interface IInvocable : IDisposable
|
||||
{
|
||||
/// <summary>
|
||||
/// Invokers are the strings that should invoke this command.
|
||||
|
@ -4,7 +4,6 @@ namespace SlatedGameToolkit.Tools.System.Interaction
|
||||
{
|
||||
void Tell(string message);
|
||||
void Separate();
|
||||
|
||||
string Listen();
|
||||
}
|
||||
}
|
@ -0,0 +1,40 @@
|
||||
using SlatedGameToolkit.Framework.StateSystem;
|
||||
using SlatedGameToolkit.Framework.StateSystem.States;
|
||||
|
||||
namespace SlatedGameToolkit.Tools.Utilities.GraphicalPlayground
|
||||
{
|
||||
public class MainState : IState
|
||||
{
|
||||
public bool Activate()
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
||||
public bool Deactivate()
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
||||
public void Dispose()
|
||||
{
|
||||
}
|
||||
|
||||
public string getName()
|
||||
{
|
||||
return "main state";
|
||||
}
|
||||
|
||||
public void Initialize(Manager manager)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
public void Render(double delta)
|
||||
{
|
||||
}
|
||||
|
||||
public void Update(double delta)
|
||||
{
|
||||
}
|
||||
}
|
||||
}
|
Loading…
Reference in New Issue
Block a user