Skip to content

Commit

Permalink
Increased window handler type safety
Browse files Browse the repository at this point in the history
 * The sender is passed as `Window*` instead of `void*`
 * Downcasting is done using runtime safe `dynamic_cast` instead of regular cast
  • Loading branch information
ooxi committed Jan 7, 2016
1 parent fee2d46 commit 86a4edd
Show file tree
Hide file tree
Showing 7 changed files with 63 additions and 42 deletions.
38 changes: 19 additions & 19 deletions src/program.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -169,7 +169,7 @@ void spawnEnemy(float x, float y, float r, int baseLvl, int lvl) {
}

// Start the game in selected mode
void startGame(void* sender, std::string elementName) {
void startGame(Window* sender, std::string elementName) {
cam->setW(1600);

hud->reset();
Expand Down Expand Up @@ -457,7 +457,7 @@ void shutdownSystem() {
delete splash;
}

void backFromOptionsAndSave(void* sender, std::string elementName);
void backFromOptionsAndSave(Window* sender, std::string elementName);

void refreshOptionsWindow() {
const int l = videoManager->getVideoMode().Width * 0.1f;
Expand Down Expand Up @@ -506,7 +506,7 @@ void refreshOptionsWindow() {
13 * h, TextManager::LEFT, TextManager::MIDDLE);
}

void switchGameOption(void* sender, std::string elementName) {
void switchGameOption(Window* sender, std::string elementName) {
map<string, bool*> m;
m["autoreload"] = &config->AutoReload;
m["autopickup"] = &config->AutoWeaponPickup;
Expand All @@ -520,7 +520,7 @@ void switchGameOption(void* sender, std::string elementName) {
}
}

void switchVolumeDown(void* sender, std::string elementName) {
void switchVolumeDown(Window* sender, std::string elementName) {
if (elementName == "musicvolume") {
if (config->MusicVolume > 0) {
config->MusicVolume--;
Expand All @@ -547,7 +547,7 @@ void switchVolumeDown(void* sender, std::string elementName) {
refreshOptionsWindow();
}

void switchVolumeUp(void* sender, std::string elementName) {
void switchVolumeUp(Window* sender, std::string elementName) {
if (elementName == "musicvolume") {
if (config->MusicVolume <= 9) {
config->MusicVolume++;
Expand All @@ -574,7 +574,7 @@ void switchVolumeUp(void* sender, std::string elementName) {
refreshOptionsWindow();
}

void switchResolutionDown(void* sender, std::string elementName) {
void switchResolutionDown(Window* sender, std::string elementName) {
vector<SDL_Rect> modes = videoManager->GetAvailableModes();

bool set = false;
Expand All @@ -595,7 +595,7 @@ void switchResolutionDown(void* sender, std::string elementName) {
refreshOptionsWindow();
}

void switchResolutionUp(void* sender, std::string elementName) {
void switchResolutionUp(Window* sender, std::string elementName) {
vector<SDL_Rect> modes = videoManager->GetAvailableModes();

bool set = false;
Expand All @@ -618,7 +618,7 @@ void switchResolutionUp(void* sender, std::string elementName) {

void refreshControlsMenuWindow();

void changeControlStyle(void* sender, std::string elementName) {
void changeControlStyle(Window* sender, std::string elementName) {
enum ControlStyle style = GetNextControlStyle(config->Control);
config->Control = style;

Expand All @@ -628,7 +628,7 @@ void changeControlStyle(void* sender, std::string elementName) {
refreshControlsMenuWindow();
}

void controlsMenuWindowController(void* sender, std::string elementName);
void controlsMenuWindowController(Window* sender, std::string elementName);

inline void addControlElement(Window* w, unsigned i, unsigned strN,
unsigned lx, unsigned rx) {
Expand Down Expand Up @@ -704,7 +704,7 @@ void drawWindows() {
}
}

void controlsMenuWindowController(void* sender, std::string elementName) {
void controlsMenuWindowController(Window* sender, std::string elementName) {
Window *w = new Window(0.0f, 0.0f, config->Screen.Width,
config->Screen.Height, 0.0f, 0.0f, 0.0f, 0.5f);

Expand Down Expand Up @@ -757,9 +757,9 @@ void controlsMenuWindowController(void* sender, std::string elementName) {
}

void drawWindows();
void showHighScores(void* sender, std::string);
void showHighScores(Window* sender, std::string);

void createControlsMenuWindow(void* sender, std::string elementName) {
void createControlsMenuWindow(Window* sender, std::string elementName) {
Window *w = new Window(0.0f, 0.0f, config->Screen.Width,
config->Screen.Height, 0.0f, 0.0f, 0.0f, 0.5f);

Expand All @@ -770,7 +770,7 @@ void createControlsMenuWindow(void* sender, std::string elementName) {
windows["options"]->CloseFlag = true;
}

void resetControls(void* sender, std::string elementName) {
void resetControls(Window* sender, std::string elementName) {
Configuration* config_default = new Configuration(fileUtility);
for (int i = 0; i < InputHandler::GameInputEventsCount; i++)
config->PlayerInputBinding[i] = config_default->PlayerInputBinding[i];
Expand Down Expand Up @@ -849,12 +849,12 @@ void createOptionsWindow() {
refreshOptionsWindow();
}

void showOptions(void* sender, std::string elementName) {
void showOptions(Window* sender, std::string elementName) {
windows["mainmenu"]->CloseFlag = true;
createOptionsWindow();
}

void resumeGame(void* sender, std::string elementName) {
void resumeGame(Window* sender, std::string elementName) {
Window* w = windows.find("mainmenu")->second;
w->CloseFlag = true;
switchGamePause();
Expand All @@ -880,7 +880,7 @@ void refreshMainMenuWindow() {
TextManager::MIDDLE);
}

void switchGameMode(void* sender, std::string elementName) {
void switchGameMode(Window* sender, std::string elementName) {
switch (gameMode) {
case GAMEMODE_SURVIVAL:
gameMode = GAMEMODE_WAVES;
Expand Down Expand Up @@ -913,7 +913,7 @@ void createMainMenuWindow() {
refreshMainMenuWindow();
}

void highScoresWindowController(void* sender, std::string elementName) {
void highScoresWindowController(Window* sender, std::string elementName) {
if (elementName == "back") {
windows["highscores"]->CloseFlag = true;
createMainMenuWindow();
Expand Down Expand Up @@ -995,7 +995,7 @@ void createHighscoresWindow() {
windows["highscores"] = w;
}

void showHighScores(void* sender, std::string elementName) {
void showHighScores(Window* sender, std::string elementName) {
windows["mainmenu"]->CloseFlag = true;
createHighscoresWindow();
}
Expand All @@ -1012,7 +1012,7 @@ void unloadResources() {
delete config;
}

void backFromOptionsAndSave(void* sender, std::string elementName) {
void backFromOptionsAndSave(Window* sender, std::string elementName) {
bool changeVideoMode = config->Screen.Width != tempConfig->Screen.Width
|| config->Screen.Height != tempConfig->Screen.Height;

Expand Down
30 changes: 24 additions & 6 deletions src/windows/CharStatsWindow.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -28,21 +28,39 @@ const char* CharStatsWindow::paramIds[] = {

const unsigned CharStatsWindow::paramIdsNumber = sizeof(CharStatsWindow::paramIds) / sizeof(char*);

void CharStatsWindow::onPlayerParamClickEvent(void* sender, string paramName)
void CharStatsWindow::onPlayerParamClickEvent(Window* sender, string paramName)
{
CharStatsWindow* window = (CharStatsWindow*)sender;
CharStatsWindow* window = dynamic_cast<CharStatsWindow*>(sender);

if (NULL == window) {
std::cerr << "onPlayerParamClickEvent was called with unexpected sender" << std::endl;
return;
}

window->increasePlayerParam(paramName);
}

void CharStatsWindow::onPerkHoverEvent(void* sender, string perkName)
void CharStatsWindow::onPerkHoverEvent(Window* sender, string perkName)
{
CharStatsWindow* window = (CharStatsWindow*)sender;
CharStatsWindow* window = dynamic_cast<CharStatsWindow*>(sender);

if (NULL == window) {
std::cerr << "onPerkHoverEvent was called with unexpected sender" << std::endl;
return;
}

window->showPerkDetails(perkName);
}

void CharStatsWindow::onPerkClickEvent(void* sender, string perkName)
void CharStatsWindow::onPerkClickEvent(Window* sender, string perkName)
{
CharStatsWindow* window = (CharStatsWindow*)sender;
CharStatsWindow* window = dynamic_cast<CharStatsWindow*>(sender);

if (NULL == window) {
std::cerr << "onPerkClickEvent was called with unexpected sender" << std::endl;
return;
}

window->givePerkToPlayer(perkName);
}

Expand Down
6 changes: 3 additions & 3 deletions src/windows/CharStatsWindow.h
Original file line number Diff line number Diff line change
Expand Up @@ -20,9 +20,9 @@ class CharStatsWindow: public Window {
static const char* paramIds[];
static const unsigned paramIdsNumber;

static void onPlayerParamClickEvent(void* sender, std::string paramName);
static void onPerkHoverEvent(void* sender, std::string perkName);
static void onPerkClickEvent(void* sender, std::string perkName);
static void onPlayerParamClickEvent(Window* sender, std::string paramName);
static void onPerkHoverEvent(Window* sender, std::string perkName);
static void onPerkClickEvent(Window* sender, std::string perkName);

CharStatsWindow(Configuration* config, VideoManager* videoManager,
Player* player);
Expand Down
9 changes: 7 additions & 2 deletions src/windows/MainMenuWindow.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -35,9 +35,14 @@ void MainMenuWindow::exitGame()
m_gameState->end();
}

void MainMenuWindow::onMenuItemClick(void* sender, string menuItem)
void MainMenuWindow::onMenuItemClick(Window* sender, string menuItem)
{
MainMenuWindow* window = (MainMenuWindow*)sender;
MainMenuWindow* window = dynamic_cast<MainMenuWindow*>(sender);

if (NULL == window) {
std::cerr << "onMenuItemClick was called with unexpected sender" << std::endl;
return;
}

if (menuItem == "exit")
window->exitGame();
Expand Down
2 changes: 1 addition & 1 deletion src/windows/MainMenuWindow.h
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@ class MainMenuWindow: public Window {
void exitGame();

public:
static void onMenuItemClick(void* sender, std::string menuItem);
static void onMenuItemClick(Window* sender, std::string menuItem);

MainMenuWindow(Configuration* config, GameState* gameState,
TextManager* text);
Expand Down
11 changes: 5 additions & 6 deletions src/windows/Window.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -53,8 +53,7 @@ void Window::removeElement(std::string name, bool remainHandler) {
removeHandler(hdl_click, name);
}

void Window::addHandler(HandlerType hdl, std::string elementName, void(*func)(void* sender,
std::string elementName)) {
void Window::addHandler(HandlerType hdl, std::string elementName, void(*func)(Window* sender, std::string elementName)) {
removeHandler(hdl, elementName);
if (hdl == hdl_click || hdl == hdl_lclick)
m_lcHandlers[elementName] = func;
Expand All @@ -66,17 +65,17 @@ void Window::addHandler(HandlerType hdl, std::string elementName, void(*func)(vo

void Window::removeHandler(HandlerType hdl, std::string elementName) {
if (hdl == hdl_all || hdl == hdl_click || hdl == hdl_lclick) {
std::map<std::string, void(*)(void* sender, std::string elementName)>::iterator it = m_lcHandlers.find(elementName);
std::map<std::string, void(*)(Window* sender, std::string elementName)>::iterator it = m_lcHandlers.find(elementName);
if (it != m_lcHandlers.end())
m_lcHandlers.erase(elementName);
}
if (hdl == hdl_all || hdl == hdl_click || hdl == hdl_rclick) {
std::map<std::string, void(*)(void* sender, std::string elementName)>::iterator it = m_rcHandlers.find(elementName);
std::map<std::string, void(*)(Window* sender, std::string elementName)>::iterator it = m_rcHandlers.find(elementName);
if (it != m_rcHandlers.end())
m_rcHandlers.erase(elementName);
}
if (hdl == hdl_all || hdl == hdl_move) {
std::map<std::string, void(*)(void* sender, std::string elementName)>::iterator it = m_mvHandlers.find(elementName);
std::map<std::string, void(*)(Window* sender, std::string elementName)>::iterator it = m_mvHandlers.find(elementName);
if (it != m_mvHandlers.end())
m_mvHandlers.erase(elementName);
}
Expand Down Expand Up @@ -118,7 +117,7 @@ void Window::process(InputHandler* input) {
int gmy = input->mouseY;

// Mouse hover handlers
std::map<std::string, void(*)(void* sender, std::string)>::const_iterator iter;
std::map<std::string, void(*)(Window* sender, std::string)>::const_iterator iter;
for (iter = m_mvHandlers.begin(); iter != m_mvHandlers.end(); ++iter) {
std::map<std::string, TextObject*>::iterator it = m_elements.find(iter->first);
if (it != m_elements.end()) {
Expand Down
9 changes: 4 additions & 5 deletions src/windows/Window.h
Original file line number Diff line number Diff line change
Expand Up @@ -11,9 +11,9 @@ class Window {
protected:
float m_left, m_top, m_right, m_bottom, m_r, m_g, m_b, m_a;
std::map<std::string, TextObject*> m_elements;
std::map<std::string, void(*)(void* sender, std::string elementName)> m_lcHandlers;
std::map<std::string, void(*)(void* sender, std::string elementName)> m_rcHandlers;
std::map<std::string, void(*)(void* sender, std::string elementName)> m_mvHandlers;
std::map<std::string, void(*)(Window* sender, std::string elementName)> m_lcHandlers;
std::map<std::string, void(*)(Window* sender, std::string elementName)> m_rcHandlers;
std::map<std::string, void(*)(Window* sender, std::string elementName)> m_mvHandlers;
public:
enum HandlerType {
hdl_all = 0, hdl_click, hdl_lclick, hdl_rclick, hdl_move
Expand All @@ -31,8 +31,7 @@ class Window {
TextManager::TextHAlignFlag halign, TextManager::TextVAlignFlag valign);
void removeElement(std::string name, bool remainHandler);
// void addHandler(HandlerType hdl, std::string elementName, void(*func)());
void addHandler(HandlerType hdl, std::string elementName, void(*func)(void* sender,
std::string elementName));
void addHandler(HandlerType hdl, std::string elementName, void(*func)(Window* sender, std::string elementName));
void removeHandler(HandlerType hdl, std::string elementName);
void process(InputHandler* input);
void draw();
Expand Down

0 comments on commit 86a4edd

Please sign in to comment.