diff --git a/examples/main.cpp b/examples/main.cpp index 691c9e1..ea39c5c 100644 --- a/examples/main.cpp +++ b/examples/main.cpp @@ -1,4 +1,4 @@ -#include "../src/store.hpp" +#include "../src/adapters/adapter.hpp" #include "../src/scene.hpp" #include "../src/camera.hpp" #include "../src/lights/sun.hpp" @@ -15,6 +15,7 @@ #include static Store store; +static const Adapter adapter(store); static void iterate(); @@ -78,12 +79,12 @@ int main() camera.projection = glm::perspective(45.0f, (float)640 / (float)480, 0.1f, 100.0f); - protagonist = store.load("protagonist.obj"); - car = store.load("car.obj"); - suzanne = store.load("suzanne.obj"); - teapot = store.load("teapot.obj"); - bunny = store.load("bunny.obj"); - untitled = store.load("untitled.raw"); + protagonist = adapter.load("protagonist.obj"); + car = adapter.load("car.obj"); + suzanne = adapter.load("suzanne.obj"); + teapot = adapter.load("teapot.obj"); + bunny = adapter.load("bunny.obj"); + untitled = adapter.load("untitled.raw"); protagonist1 = new Objects::WithModel(*protagonist); protagonist1->position.z = 4; diff --git a/src/adapters/adapter.hpp b/src/adapters/adapter.hpp new file mode 100644 index 0000000..a4d4638 --- /dev/null +++ b/src/adapters/adapter.hpp @@ -0,0 +1,36 @@ +#ifndef _ADAPTER_HPP_ +#define _ADAPTER_HPP_ + +#include "../store.hpp" + +struct Adapter +{ + Adapter(Store &store): _store(store) {}; + + template + const T *load(const std::string &name) const; + + template + const std::string filename(const std::string &name) const; + +private: + Store &_store; +}; + +template +const T *Adapter::load(const std::string &name) const +{ + static_assert(std::is_convertible::value + && !std::is_same::value, + "Adapter can deal with only Resource's children"); + + return _store.load(*this, name); +} + +template +const std::string Adapter::filename(const std::string &name) const +{ + return "/data" + T::filename(name); +} + +#endif // _ADAPTER_HPP_ diff --git a/src/models/raw.cpp b/src/models/raw.cpp index 0083af1..072a26c 100644 --- a/src/models/raw.cpp +++ b/src/models/raw.cpp @@ -21,17 +21,17 @@ const GLchar *const Raw::uniforms[] = { const std::string Raw::filename(const std::string &name) { - return "/data/models/" + name; + return "/models/" + name; } -Raw::Raw(__attribute__((unused)) Store &store, const std::string &name) +Raw::Raw(const Adapter &adapter, const std::string &name) { - exe = store.load("normal")->build( + exe = adapter.load("normal")->build( __attrib_count, attribs, __uniform_count, uniforms ); - FILE *file = fopen(filename(name).c_str(), "r"); + FILE *file = fopen(adapter.filename(name).c_str(), "r"); while (!feof(file)) { diff --git a/src/models/static.cpp b/src/models/static.cpp index ab088e7..e7da6ba 100644 --- a/src/models/static.cpp +++ b/src/models/static.cpp @@ -27,17 +27,17 @@ const GLchar *const Static::uniforms[] = { const std::string Static::filename(const std::string &name) { - return "/data/models/" + name; + return "/models/" + name; } -Static::Static(Store &store, const std::string &name) +Static::Static(const Adapter &adapter, const std::string &name) { - exe = store.load("textured")->build( + exe = adapter.load("textured")->build( __attrib_count, attribs, __uniform_count, uniforms ); - std::ifstream file(filename(name), std::ios::in); + std::ifstream file(adapter.filename(name), std::ios::in); const Mtllib *mtllib = nullptr; @@ -104,7 +104,7 @@ Static::Static(Store &store, const std::string &name) else if (line.substr(0, 7) == "mtllib ") { - mtllib = (Mtllib*)store.load(line.substr(7)); + mtllib = adapter.load(line.substr(7)); } else if (line.substr(0, 7) == "usemtl ") diff --git a/src/mtllib.cpp b/src/mtllib.cpp index 65a487f..f6cab5e 100644 --- a/src/mtllib.cpp +++ b/src/mtllib.cpp @@ -5,12 +5,12 @@ const std::string Mtllib::filename(const std::string &name) { - return "/data/materials/" + name; + return "/materials/" + name; } -Mtllib::Mtllib(Store &store, const std::string &name) +Mtllib::Mtllib(const Adapter &adapter, const std::string &name) { - std::ifstream file(filename(name), std::ios::in); + std::ifstream file(adapter.filename(name), std::ios::in); Material *material = nullptr; @@ -28,7 +28,7 @@ Mtllib::Mtllib(Store &store, const std::string &name) else if (line.substr(0, 7) == "map_Kd ") { - material->texture = store.load(line.substr(7)); + material->texture = adapter.load(line.substr(7)); } } } diff --git a/src/program.cpp b/src/program.cpp index 9e5fae7..02d1ef0 100644 --- a/src/program.cpp +++ b/src/program.cpp @@ -6,12 +6,12 @@ const std::string Program::filename(const std::string &name) { - return "/data/programs/" + name; + return "/programs/" + name; } -Program::Program(Store &store, const std::string &name): - vertex_shader(store.load(name + ".vert")), - fragment_shader(store.load(name + ".frag")) +Program::Program(const Adapter &adapter, const std::string &name): + vertex_shader(adapter.load(name + ".vert")), + fragment_shader(adapter.load(name + ".frag")) {} const Executable *Program::build( diff --git a/src/resource.hpp b/src/resource.hpp index c1e1e9a..c24ab5c 100644 --- a/src/resource.hpp +++ b/src/resource.hpp @@ -1,7 +1,7 @@ #ifndef _RESOURCE_HPP_ #define _RESOURCE_HPP_ -#include "store.hpp" +#include "adapters/adapter.hpp" struct Resource { @@ -14,7 +14,7 @@ private: #define RESOURCE(T) \ friend struct ::Store; \ - T(Store &store, const std::string &name); \ + T(const Adapter &adapter, const std::string &name); \ static const std::string filename(const std::string &name); #endif // _RESOURCE_HPP_ diff --git a/src/shader.cpp b/src/shader.cpp index a46da58..cea2baf 100644 --- a/src/shader.cpp +++ b/src/shader.cpp @@ -5,14 +5,14 @@ const std::string Shader::filename(const std::string &name) { - return "/data/shaders/" + name; + return "/shaders/" + name; } -Shader::Shader(__attribute__((unused)) Store &store, const std::string &name) +Shader::Shader(const Adapter &adapter, const std::string &name) { const GLuint type = name.substr(name.size() - 5) == ".vert" ? GL_VERTEX_SHADER : GL_FRAGMENT_SHADER; - FILE *file = fopen(filename(name).c_str(), "r"); + FILE *file = fopen(adapter.filename(name).c_str(), "r"); fseek(file, 0, SEEK_END); const long size = ftell(file); diff --git a/src/store.hpp b/src/store.hpp index ff60c2b..4882433 100644 --- a/src/store.hpp +++ b/src/store.hpp @@ -5,26 +5,27 @@ #include #include +struct Adapter; struct Resource; struct Store { template - const T *load(const std::string &name); + const T *load(const Adapter &adapter, const std::string &name); private: std::map _resources; }; template -const T *Store::load(const std::string &name) +const T *Store::load(const Adapter &adapter, const std::string &name) { static_assert(std::is_convertible::value && !std::is_same::value, "Store can load only Resource's children"); if (_resources.find(T::filename(name)) == _resources.end()) - _resources[T::filename(name)] = new T(*this, name); + _resources[T::filename(name)] = new T(adapter, name); _resources[T::filename(name)]->_ref_count++; return (T*)_resources[T::filename(name)]; diff --git a/src/texture.cpp b/src/texture.cpp index 4469647..98f9944 100644 --- a/src/texture.cpp +++ b/src/texture.cpp @@ -6,12 +6,12 @@ const std::string Texture::filename(const std::string &name) { - return "/data/textures/" + name; + return "/textures/" + name; } -Texture::Texture(__attribute__((unused)) Store &store, const std::string &name) +Texture::Texture(const Adapter &adapter, const std::string &name) { - SDL_Surface *surface = IMG_Load(filename(name).c_str()); + SDL_Surface *surface = IMG_Load(adapter.filename(name).c_str()); glGenTextures(1, &_id); glBindTexture(GL_TEXTURE_2D, _id);