graphics frame rate fixed
This commit is contained in:
parent
e41714c2bb
commit
29280949a8
7 changed files with 203 additions and 121 deletions
|
|
@ -1,129 +1,27 @@
|
||||||
|
|
||||||
#include "Window.hpp"
|
#include "GraphicApplication.hpp"
|
||||||
#include "Graphics.hpp"
|
|
||||||
|
|
||||||
#include "Timing.hpp"
|
|
||||||
|
|
||||||
#include "imgui.h"
|
#include "imgui.h"
|
||||||
|
|
||||||
using namespace tp;
|
using namespace tp;
|
||||||
|
|
||||||
class Application {
|
class ExampleApplication : public Application {
|
||||||
public:
|
public:
|
||||||
Application() :
|
ExampleApplication() = default;
|
||||||
mApplicaitonModule("Application", nullptr, nullptr, mModuleDeps) {
|
|
||||||
mInitialized = mApplicaitonModule.initialize();
|
|
||||||
if (!mInitialized) return;
|
|
||||||
|
|
||||||
mWindow = Window::createWindow();
|
void processFrame(EventHandler* eventHandler) override {
|
||||||
|
// example
|
||||||
mDrawTimer.setDuration(1000.f / mDrawPerSecond);
|
|
||||||
mProcTimer.setDuration(1000.f / mProcPerSecond);
|
|
||||||
mPerSecondTimer.setDuration(1000.f);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void run() {
|
virtual void drawFrame(Canvas* canvas) override {
|
||||||
Graphics graphics(mWindow);
|
ImGui::Text("Frames processed per second: %f", this->mFramesProcessedPerSecond);
|
||||||
auto eventHandler = new EventHandler();
|
ImGui::Text("Frames drawn per second: %f", this->mFramesDrawnPerSecond);
|
||||||
|
|
||||||
mWindow->setEventHandler(eventHandler);
|
|
||||||
|
|
||||||
mDrawTimer.reset();
|
|
||||||
mProcTimer.reset();
|
|
||||||
mPerSecondTimer.reset();
|
|
||||||
|
|
||||||
bool redrawNeeded = false;
|
|
||||||
|
|
||||||
while (!mWindow->shouldClose()) {
|
|
||||||
if (mProcTimer.isTimeout()) {
|
|
||||||
|
|
||||||
mWindow->processEvents();
|
|
||||||
|
|
||||||
while (eventHandler->isEvents()) {
|
|
||||||
eventHandler->processEvent();
|
|
||||||
processFrame(eventHandler);
|
|
||||||
|
|
||||||
redrawNeeded = true;
|
|
||||||
mFramesProcessed++;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// graphics.procBegin();
|
virtual ~ExampleApplication() = default;
|
||||||
// graphics.procEnd();
|
|
||||||
redrawNeeded = true;
|
|
||||||
mFramesProcessed++;
|
|
||||||
|
|
||||||
mProcTimer.wait();
|
|
||||||
mProcTimer.reset();
|
|
||||||
}
|
|
||||||
|
|
||||||
if (mDrawTimer.isTimeout()) {
|
|
||||||
mDrawTimer.reset();
|
|
||||||
|
|
||||||
if (redrawNeeded) {
|
|
||||||
graphics.drawBegin();
|
|
||||||
|
|
||||||
drawFrame(graphics.getCanvas());
|
|
||||||
|
|
||||||
graphics.drawEnd();
|
|
||||||
|
|
||||||
mWindow->draw();
|
|
||||||
|
|
||||||
redrawNeeded = false;
|
|
||||||
mFramesDrawn++;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (mPerSecondTimer.isTimeout()) {
|
|
||||||
mPerSecondTimer.reset();
|
|
||||||
|
|
||||||
mFramesProcessedPerSecond = mFramesProcessed;
|
|
||||||
mFramesDrawnPerSecond = mFramesDrawn;
|
|
||||||
|
|
||||||
mFramesDrawn = 0;
|
|
||||||
mFramesProcessed = 0;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
delete eventHandler;
|
|
||||||
}
|
|
||||||
|
|
||||||
virtual void processFrame(EventHandler* eventHandler) {
|
|
||||||
}
|
|
||||||
|
|
||||||
virtual void drawFrame(Canvas* canvas) {
|
|
||||||
ImGui::Text("Frames processed per second: %f", mFramesProcessedPerSecond);
|
|
||||||
ImGui::Text("Frames drawn per second: %f", mFramesDrawnPerSecond);
|
|
||||||
}
|
|
||||||
|
|
||||||
~Application() {
|
|
||||||
if (!mInitialized) return;
|
|
||||||
Window::destroyWindow(mWindow);
|
|
||||||
mApplicaitonModule.deinitialize();
|
|
||||||
}
|
|
||||||
|
|
||||||
private:
|
|
||||||
ModuleManifest* mModuleDeps[2] = { &gModuleGraphics, nullptr };
|
|
||||||
ModuleManifest mApplicaitonModule;
|
|
||||||
|
|
||||||
Window* mWindow = nullptr;
|
|
||||||
|
|
||||||
bool mInitialized = false;
|
|
||||||
|
|
||||||
ualni mDrawPerSecond = 60;
|
|
||||||
ualni mProcPerSecond = 1000;
|
|
||||||
|
|
||||||
Timer mDrawTimer;
|
|
||||||
Timer mProcTimer;
|
|
||||||
Timer mPerSecondTimer;
|
|
||||||
|
|
||||||
halnf mFramesProcessedPerSecond = 0;
|
|
||||||
halnf mFramesDrawnPerSecond = 0;
|
|
||||||
|
|
||||||
halnf mFramesProcessed = 0;
|
|
||||||
halnf mFramesDrawn = 0;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
int main() {
|
int main() {
|
||||||
Application app;
|
ExampleApplication app;
|
||||||
app.run();
|
app.run();
|
||||||
}
|
}
|
||||||
|
|
|
||||||
89
Graphics/private/GraphicApplication.cpp
Normal file
89
Graphics/private/GraphicApplication.cpp
Normal file
|
|
@ -0,0 +1,89 @@
|
||||||
|
|
||||||
|
#include "GraphicApplication.hpp"
|
||||||
|
|
||||||
|
using namespace tp;
|
||||||
|
|
||||||
|
Application::Application() :
|
||||||
|
mApplicationModule("Application", nullptr, nullptr, mModuleDeps) {
|
||||||
|
mInitialized = mApplicationModule.initialize();
|
||||||
|
if (!mInitialized) return;
|
||||||
|
|
||||||
|
mWindow = Window::createWindow();
|
||||||
|
|
||||||
|
mDrawTimer.setDuration(1000.f / mDrawPerSecond);
|
||||||
|
mProcTimer.setDuration(1000.f / mProcPerSecond);
|
||||||
|
mPerSecondTimer.setDuration(1000.f);
|
||||||
|
}
|
||||||
|
|
||||||
|
void Application::run() {
|
||||||
|
Graphics graphics(mWindow);
|
||||||
|
auto eventHandler = new EventHandler();
|
||||||
|
|
||||||
|
mWindow->setEventHandler(eventHandler);
|
||||||
|
|
||||||
|
mDrawTimer.reset();
|
||||||
|
mProcTimer.reset();
|
||||||
|
mPerSecondTimer.reset();
|
||||||
|
|
||||||
|
bool redrawNeeded = false;
|
||||||
|
|
||||||
|
while (!mWindow->shouldClose()) {
|
||||||
|
if (mProcTimer.isTimeout()) {
|
||||||
|
|
||||||
|
mWindow->processEvents();
|
||||||
|
|
||||||
|
while (eventHandler->isEvents()) {
|
||||||
|
eventHandler->processEvent();
|
||||||
|
processFrame(eventHandler);
|
||||||
|
|
||||||
|
redrawNeeded = true;
|
||||||
|
mFramesProcessed++;
|
||||||
|
}
|
||||||
|
|
||||||
|
mProcTimer.wait();
|
||||||
|
mProcTimer.reset();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (mDrawTimer.isTimeout()) {
|
||||||
|
mDrawTimer.reset();
|
||||||
|
|
||||||
|
if (redrawNeeded) {
|
||||||
|
graphics.drawBegin();
|
||||||
|
|
||||||
|
drawFrame(graphics.getCanvas());
|
||||||
|
|
||||||
|
graphics.drawEnd();
|
||||||
|
|
||||||
|
mWindow->draw();
|
||||||
|
|
||||||
|
redrawNeeded = false;
|
||||||
|
mFramesDrawn++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (mPerSecondTimer.isTimeout()) {
|
||||||
|
mPerSecondTimer.reset();
|
||||||
|
|
||||||
|
mFramesProcessedPerSecond = mFramesProcessed;
|
||||||
|
mFramesDrawnPerSecond = mFramesDrawn;
|
||||||
|
|
||||||
|
mFramesDrawn = 0;
|
||||||
|
mFramesProcessed = 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
delete eventHandler;
|
||||||
|
}
|
||||||
|
|
||||||
|
void Application::processFrame(EventHandler* eventHandler) {}
|
||||||
|
|
||||||
|
void Application::drawFrame(Canvas* canvas) {
|
||||||
|
// ImGui::Text("Frames processed per second: %f", mFramesProcessedPerSecond);
|
||||||
|
// ImGui::Text("Frames drawn per second: %f", mFramesDrawnPerSecond);
|
||||||
|
}
|
||||||
|
|
||||||
|
Application::~Application() {
|
||||||
|
if (!mInitialized) return;
|
||||||
|
Window::destroyWindow(mWindow);
|
||||||
|
mApplicationModule.deinitialize();
|
||||||
|
}
|
||||||
|
|
@ -3,6 +3,8 @@
|
||||||
#include "WindowContext.hpp"
|
#include "WindowContext.hpp"
|
||||||
#include "Allocators.hpp"
|
#include "Allocators.hpp"
|
||||||
|
|
||||||
|
#include "Rect.hpp"
|
||||||
|
|
||||||
#include <GL/glew.h>
|
#include <GL/glew.h>
|
||||||
|
|
||||||
#ifdef ENV_OS_WINDOWS
|
#ifdef ENV_OS_WINDOWS
|
||||||
|
|
@ -92,11 +94,8 @@ void Window::destroyWindow(Window* window) {
|
||||||
bool Window::shouldClose() const { return glfwWindowShouldClose(mContext->window); }
|
bool Window::shouldClose() const { return glfwWindowShouldClose(mContext->window); }
|
||||||
|
|
||||||
void Window::processEvents() {
|
void Window::processEvents() {
|
||||||
glfwPollEvents();
|
glfwWaitEvents();
|
||||||
|
checkAxisUpdates();
|
||||||
int w, h;
|
|
||||||
glfwGetWindowSize(mContext->window, &w, &h);
|
|
||||||
mSize = { (halnf) w, (halnf) h };
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void Window::draw() {
|
void Window::draw() {
|
||||||
|
|
@ -111,6 +110,35 @@ void Window::setEventHandler(EventHandler* eventHandler) { mEventHandler = event
|
||||||
EventHandler* Window::getEventHandler() { return mEventHandler; }
|
EventHandler* Window::getEventHandler() { return mEventHandler; }
|
||||||
|
|
||||||
|
|
||||||
|
void Window::checkAxisUpdates() {
|
||||||
|
if (!mEventHandler) return;
|
||||||
|
|
||||||
|
int w, h;
|
||||||
|
glfwGetWindowSize(mContext->window, &w, &h);
|
||||||
|
|
||||||
|
if (mSize != Vec2F((halnf) w, (halnf) h)) {
|
||||||
|
mSize = { (halnf) w, (halnf) h };
|
||||||
|
mEventHandler->postEvent(InputID::WINDOW_RESIZE, {});
|
||||||
|
}
|
||||||
|
|
||||||
|
double x, y;
|
||||||
|
glfwGetCursorPos(mContext->window, &x, &y);
|
||||||
|
|
||||||
|
int posX, posY;
|
||||||
|
glfwGetWindowPos(mContext->window, &posX, &posY);
|
||||||
|
|
||||||
|
if (mPointerPos != Vec2F{ (halnf) x, (halnf) y }) {
|
||||||
|
mPointerPos = { (halnf) x, (halnf) y };
|
||||||
|
|
||||||
|
auto pos = Vec2F{ (halnf) posX, (halnf) posY };
|
||||||
|
RectF windowRec = { { 0, 0 }, mSize };
|
||||||
|
|
||||||
|
if (windowRec.isInside(mPointerPos)) {
|
||||||
|
mEventHandler->postEvent(InputID::MOUSE1, { {}, {}, mPointerPos });
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
static void keyCallback(GLFWwindow* window, int key, int scancode, int action, int mods) {
|
static void keyCallback(GLFWwindow* window, int key, int scancode, int action, int mods) {
|
||||||
|
|
||||||
auto* self = static_cast<Window*>(glfwGetWindowUserPointer(window));
|
auto* self = static_cast<Window*>(glfwGetWindowUserPointer(window));
|
||||||
|
|
@ -119,6 +147,8 @@ static void keyCallback(GLFWwindow* window, int key, int scancode, int action, i
|
||||||
EventHandler* eventHandler = self->getEventHandler();
|
EventHandler* eventHandler = self->getEventHandler();
|
||||||
if (!eventHandler) return;
|
if (!eventHandler) return;
|
||||||
|
|
||||||
|
self->checkAxisUpdates();
|
||||||
|
|
||||||
// post key event
|
// post key event
|
||||||
/*
|
/*
|
||||||
if (action == GLFW_PRESS) {
|
if (action == GLFW_PRESS) {
|
||||||
|
|
@ -137,6 +167,8 @@ static void mouseButtonCallback(GLFWwindow* window, int button, int action, int
|
||||||
EventHandler* eventHandler = self->getEventHandler();
|
EventHandler* eventHandler = self->getEventHandler();
|
||||||
if (!eventHandler) return;
|
if (!eventHandler) return;
|
||||||
|
|
||||||
|
self->checkAxisUpdates();
|
||||||
|
|
||||||
// post mouse button event
|
// post mouse button event
|
||||||
// inputManager->mouseButtonStates[button] = action;
|
// inputManager->mouseButtonStates[button] = action;
|
||||||
// inputManager->isEvent = true;
|
// inputManager->isEvent = true;
|
||||||
|
|
|
||||||
|
|
@ -60,11 +60,27 @@ namespace tp {
|
||||||
~EventHandler();
|
~EventHandler();
|
||||||
|
|
||||||
public: // Event Poster Interface
|
public: // Event Poster Interface
|
||||||
void postEvent(InputID inputID, InputEvent inputEvent); // Record event
|
|
||||||
|
// Record event
|
||||||
|
void postEvent(InputID inputID, InputEvent inputEvent) {
|
||||||
|
mMutex.lock();
|
||||||
|
mEventQueue.pushBack({ inputID, inputEvent });
|
||||||
|
mMutex.unlock();
|
||||||
|
}
|
||||||
|
|
||||||
public: // User interface
|
public: // User interface
|
||||||
bool isEvents() { return false; }
|
bool isEvents() {
|
||||||
void processEvent() {}
|
mMutex.lock();
|
||||||
|
auto res = mEventQueue.length();
|
||||||
|
mMutex.unlock();
|
||||||
|
return res;
|
||||||
|
}
|
||||||
|
|
||||||
|
void processEvent() {
|
||||||
|
mMutex.lock();
|
||||||
|
mEventQueue.popFront();
|
||||||
|
mMutex.unlock();
|
||||||
|
}
|
||||||
|
|
||||||
const Vec2F& getPointer() const;
|
const Vec2F& getPointer() const;
|
||||||
|
|
||||||
|
|
@ -78,7 +94,7 @@ namespace tp {
|
||||||
std::mutex mMutex = {};
|
std::mutex mMutex = {};
|
||||||
|
|
||||||
// Store thread protected queue of posted events
|
// Store thread protected queue of posted events
|
||||||
List<InputEvent> mEventQueue;
|
List<std::pair<InputID, InputEvent>> mEventQueue;
|
||||||
|
|
||||||
// input states
|
// input states
|
||||||
Vec2F mPointer;
|
Vec2F mPointer;
|
||||||
|
|
|
||||||
41
Graphics/public/GraphicApplication.hpp
Normal file
41
Graphics/public/GraphicApplication.hpp
Normal file
|
|
@ -0,0 +1,41 @@
|
||||||
|
|
||||||
|
#pragma once
|
||||||
|
|
||||||
|
#include "Window.hpp"
|
||||||
|
#include "Graphics.hpp"
|
||||||
|
#include "Timing.hpp"
|
||||||
|
|
||||||
|
namespace tp {
|
||||||
|
class Application {
|
||||||
|
public:
|
||||||
|
Application();
|
||||||
|
|
||||||
|
void run();
|
||||||
|
|
||||||
|
virtual void processFrame(EventHandler* eventHandler);
|
||||||
|
virtual void drawFrame(Canvas* canvas);
|
||||||
|
|
||||||
|
virtual ~Application();
|
||||||
|
|
||||||
|
protected:
|
||||||
|
ModuleManifest* mModuleDeps[2] = { &gModuleGraphics, nullptr };
|
||||||
|
ModuleManifest mApplicationModule;
|
||||||
|
|
||||||
|
Window* mWindow = nullptr;
|
||||||
|
|
||||||
|
bool mInitialized = false;
|
||||||
|
|
||||||
|
ualni mDrawPerSecond = 60;
|
||||||
|
ualni mProcPerSecond = 160;
|
||||||
|
|
||||||
|
Timer mDrawTimer;
|
||||||
|
Timer mProcTimer;
|
||||||
|
Timer mPerSecondTimer;
|
||||||
|
|
||||||
|
halnf mFramesProcessedPerSecond = 0;
|
||||||
|
halnf mFramesDrawnPerSecond = 0;
|
||||||
|
|
||||||
|
halnf mFramesProcessed = 0;
|
||||||
|
halnf mFramesDrawn = 0;
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
@ -146,5 +146,7 @@ namespace tp {
|
||||||
MOUSE_DOWN = 507,
|
MOUSE_DOWN = 507,
|
||||||
|
|
||||||
LAST_KEY_CODE = 508,
|
LAST_KEY_CODE = 508,
|
||||||
|
|
||||||
|
WINDOW_RESIZE = 1000,
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
@ -29,8 +29,12 @@ namespace tp {
|
||||||
[[nodiscard]] bool shouldClose() const;
|
[[nodiscard]] bool shouldClose() const;
|
||||||
[[nodiscard]] const Vec2F& getSize() const;
|
[[nodiscard]] const Vec2F& getSize() const;
|
||||||
|
|
||||||
|
void checkAxisUpdates();
|
||||||
|
|
||||||
private:
|
private:
|
||||||
Vec2F mSize;
|
Vec2F mSize;
|
||||||
|
Vec2F mPointerPos;
|
||||||
|
|
||||||
Context* mContext;
|
Context* mContext;
|
||||||
EventHandler* mEventHandler = nullptr;
|
EventHandler* mEventHandler = nullptr;
|
||||||
};
|
};
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue