refactored event handling; added _dirty flag to only update when dirty

This commit is contained in:
Bob Polis 2020-11-13 16:54:49 +01:00
parent 6202c7dba7
commit 32ac8b4e0f
2 changed files with 38 additions and 16 deletions

View File

@ -53,18 +53,12 @@ bool Window::handle_global_event(const SDL_Event& event) {
} }
} }
switch (event.window.event) { switch (event.window.event) {
case SDL_WINDOWEVENT_CLOSE: { case SDL_WINDOWEVENT_CLOSE:
// remove window from window list quit = close(event);
SDL_Window* w {SDL_GetWindowFromID(event.window.windowID)}; break;
auto it = std::remove_if(_windows.begin(), _windows.end(), [w](Window& win) { case SDL_WINDOWEVENT_EXPOSED:
return win.window() == w; quit = expose(event);
});
_windows.erase(it, _windows.end());
if (_windows.size() == 0) {
quit = true;
}
break; break;
}
default: default:
break; break;
} }
@ -81,6 +75,24 @@ void Window::add_global_event_handler(WindowEventHandler handler, SDL_WindowEven
} }
} }
bool Window::expose(const SDL_Event& event) {
Window* w {from_sdl(event.window.windowID)};
if (w) w->dirty(true);
return false;
}
bool Window::close(const SDL_Event& event) {
// remove window from window list
SDL_Window* w {SDL_GetWindowFromID(event.window.windowID)};
auto it = std::remove_if(_windows.begin(), _windows.end(), [w](Window& win) {
return win.window() == w;
});
_windows.erase(it, _windows.end());
// quit if it was the last window
return _windows.size() == 0;
}
Window::Window(const std::string& title) : _title {title} { Window::Window(const std::string& title) : _title {title} {
SDL_Window* win = SDL_CreateWindow(title.c_str(), SDL_Window* win = SDL_CreateWindow(title.c_str(),
SDL_WINDOWPOS_CENTERED, SDL_WINDOWPOS_CENTERED, SDL_WINDOWPOS_CENTERED, SDL_WINDOWPOS_CENTERED,
@ -94,11 +106,14 @@ void Window::set_size(int w, int h) {
SDL_SetWindowSize(_w.get(), w, h); SDL_SetWindowSize(_w.get(), w, h);
} }
void Window::update() const { void Window::update() {
if (_dirty) {
_dirty = false;
SDL_RenderClear(_r.get()); SDL_RenderClear(_r.get());
SDL_RenderCopy(_r.get(), _t.get(), nullptr, nullptr); SDL_RenderCopy(_r.get(), _t.get(), nullptr, nullptr);
SDL_RenderPresent(_r.get()); SDL_RenderPresent(_r.get());
} }
}
void Window::show_image(const Image& image) { void Window::show_image(const Image& image) {
// create texture from surface // create texture from surface

View File

@ -43,18 +43,25 @@ namespace sc {
int width() const; int width() const;
int height() const; int height() const;
void update() const; void update();
void show_image(const Image& image); void show_image(const Image& image);
void dirty(bool flag) { _dirty = flag; }
bool dirty() const { return _dirty; }
private: private:
static std::vector<Window> _windows; static std::vector<Window> _windows;
static std::map<SDL_WindowEventID, std::vector<WindowEventHandler>> _global_event_handlers; static std::map<SDL_WindowEventID, std::vector<WindowEventHandler>> _global_event_handlers;
bool _dirty {true};
std::string _title; std::string _title;
std::unique_ptr<SDL_Window, void(*)(SDL_Window*)> _w {nullptr, SDL_DestroyWindow}; std::unique_ptr<SDL_Window, void(*)(SDL_Window*)> _w {nullptr, SDL_DestroyWindow};
std::unique_ptr<SDL_Renderer, void(*)(SDL_Renderer*)> _r {nullptr, SDL_DestroyRenderer}; std::unique_ptr<SDL_Renderer, void(*)(SDL_Renderer*)> _r {nullptr, SDL_DestroyRenderer};
std::unique_ptr<SDL_Texture, void(*)(SDL_Texture*)> _t {nullptr, SDL_DestroyTexture}; std::unique_ptr<SDL_Texture, void(*)(SDL_Texture*)> _t {nullptr, SDL_DestroyTexture};
std::map<SDL_WindowEventID, std::vector<WindowEventHandler>> _event_handlers; std::map<SDL_WindowEventID, std::vector<WindowEventHandler>> _event_handlers;
static bool close(const SDL_Event& event);
static bool expose(const SDL_Event& event);
}; };
} }
} }