I'm writing a small Game-Engine (which is used as a library) while re-reading myself into c++. I've coded in Java for several years, but it seems like c++ handles polymorphism a little bit different and I am encountering the following problem:
I have a class GameObject, which represents the basic functionalities of any type of object within the game. So this basically is used as an abstract class. I have several Objects, which override GameObject including a class Map. These objects are finally used within the game.
All this is compiled into a library and used by the game.
Here is the basic code I use: gameobject.h:
class GameObject {
public:
void loadFromJson(nlohmann::json& json);
void load();
// [...] not relevant
}
gameobject.cpp:
void GameObject::loadFromJson(nlohmann::json& json) {
// [...] not relevant
std::cout << "base-class function" << std::endl;
}
void GameObject::load() {
// [...] not relevant
this->loadFromJson(json);
}
map.h:
class Map : public GameObject {
public:
void loadFromJson(nlohmann::json& json);
// [...] not relevant
}
map.cpp:
void Map::loadFromJson(nlohmann::json& json) {
// [...] not relevant
GameObject::loadFromJson(json);
std::cout << "derived class function" << std::endl;
}
main within game:
int main() {
Map* map = new Map(...);
map->load();
}
I'm not sure which arguments within the makefile are relevant or not, therefore I simply paste all I use, including libraries, which should be irrelevant: makefile, gameengine (called gct):
COMPARGS=-Wall -I$(INCLUDEPATH) -I$(LIBPATH) -I$(LIBPATHGLADINCLUDE) -std=c++17 -fsanitize=address -fPIC $(SDL_FLAGS) $(PKG_FLAGS) -lplibfnt -lSOIL -lstdc++fs -g
$(OUTPUTPATH)libgct.so: [...] gameobject [...] map
$(CC) -shared [...] gameobject [...] map -o $(OUTPUTPATH)libgct.so
gameobject: $(SRCPATH)gameobject.cpp $(INCLUDEPATHGCT)gameobject.h
$(CC) $(SRCPATH)gameobject.cpp -c -o gameobject $(COMPARGS)
map: $(SRCPATHMAP)map.cpp $(INCLUDEPATHGCTMAP)map.h
$(CC) $(SRCPATHMAP)map.cpp -c -o map $(COMPARGS)
makefile, game:
COMPARGS=-Wall -std=c++17 -fsanitize=address -I$(LIBINCLUDE) -lgct -lplibfnt -lplibul $(SDL_FLAGS) $(PKG_FLAGS) -lSOIL -lstdc++fs -g
testgame: $(SRCPATH)main.cpp [...]
$(CC) $(SRCPATH)main.cpp [...] $(COMPARGS) -o testgame
Now my expected behavior would be the output: "base-class function" "derived class function"
But what I get is: "base-class function"
I already had problems with using polymorphism within the library in the way, that loadFromJson() was virtual in base class. And using it with an array of GameObjects (at that time it was with other classes and other methods, but the priciple behind it should become clear). This caused strange errors, which google explained with that such polymorphism is slow, and not supposed to be used within libraries. I know, there shouldn't be much of a difference with this way of polymorphism, but I don't get any errors. Just not the expected behavior and I have the feeling this should work.
However that was a different problem with other classes and other methods which I was able to workaround. But this would be quite anoying, if I wasn't able to use it, since I would have to rewrite load() within the derived classes over and over again. I found other posts with a (relativly) similar Problem regarding polymorphism, but there the answers always represented my expected behavior. So my question is: What are the possibilities why this is not working as I want to, or more precise: could this be a result of using the code as a shared library? Maybe there is a error within the code I can't find...I hope and think, that the code I gave you should be enough. I doupt, that it's anything else. If, however, the problem must be somewhere else, I would be glad about some potential mistakes, that could cause this.