mikymod před 12 roky
rodič
revize
f2f829342f

+ 1 - 1
CMakeLists.txt

@@ -11,7 +11,7 @@ option (CROWN_BUILD_OPENGL "Whether to build the OpenGL renderer or not." ON)
 option (CROWN_BUILD_OPENGLES "Whether to build the OpenGL|ES 1.0 renderer or not." OFF)
 option (CROWN_BUILD_SAMPLES "Whether to build the samples" ON)
 option (CROWN_BUILD_TOOLS "Whether to build the tools" ON)
-option (CROWN_BUILD_TESTS "Whether to build unit tests" ON)
+option (CROWN_BUILD_TESTS "Whether to build unit tests" OFF)
 
 set (INCLUDES
 	${CMAKE_SOURCE_DIR}/src

+ 17 - 13
game/Game.h

@@ -28,20 +28,24 @@ OTHER DEALINGS IN THE SOFTWARE.
 namespace crown
 {
 
-class Game
+extern "C"
 {
-public:
-
-					Game() {}
-	virtual			~Game() {}
-
-	virtual void	init() = 0;
-	virtual void	shutdown() = 0;
-	virtual void	update(float dt) = 0;
-};
-
-typedef Game* create_game_t();
-typedef void destroy_game_t(Game* game);
+	/// Called exactly once after the engine is fully initialized
+	/// and ready to use. This function is the right place to allocate
+	/// and initialize all the main components of the game.
+	void init();
+
+	/// Called just before the engine starts to deallocate resources and
+	/// subsystems leading to terminating the execution.
+	/// Here you can safely perform all the necessary deallocation/destruction
+	/// of the previously allocated game resources and/or systems. 
+	void shutdown();
+
+	/// Called once per frame, here is the place you tipically perform input checking,
+	/// updates, drawing and so on. The @dt parameter contains the last frame delta time
+	/// in seconds. 
+	void frame(float dt);
+}
 
 } // namespace crown
 

+ 2 - 3
samples/lua/lua.cpp

@@ -29,11 +29,10 @@ int main(int argc, char** argv)
 
   ResourceId script = res_manager.load("lua/hello.lua");
 
+  res_manager.flush();
+
   while (1)
   {
-    res_manager.flush_load_queue();
-    res_manager.bring_loaded_online();
-
     if (res_manager.is_loaded(script))
     {
 

+ 57 - 56
samples/terrain/terrain.cpp

@@ -31,7 +31,8 @@ public:
 	MainScene() :
 		optShowSkybox(true),
 		optShowCrate(true),
-		optShowTerrain(true)
+		optShowTerrain(true),
+		camera_active(true)
 	{
 		device()->input_manager()->register_keyboard_listener(this);
 		device()->input_manager()->register_mouse_listener(this);
@@ -59,6 +60,16 @@ public:
 		{		
 			terrain.PlotCircle(8, 8, 8, 2);
 		}
+
+		if (event.key == KC_F5)
+		{
+			device()->reload(grass);
+		}
+
+		if (event.key == KC_SPACE)
+		{
+			camera_active = !camera_active;
+		}
 	}
 
 	void button_pressed(const MouseEvent& event)
@@ -115,51 +126,54 @@ public:
 	void on_load()
 	{
 		crown::Renderer* renderer = crown::device()->renderer();
-
-		renderer->set_clear_color(Color4::LIGHTBLUE);
 		
 		Vec3 start = Vec3(0.0f, 10.0f, 0.0f);
 
 		// Add a movable camera
 		cam = new Camera(start, 90.0f, 1.6f);
-
 		system = new FPSSystem(cam, 10.0f, 2.5f);
-
 		// Add a skybox
 		skybox = new Skybox(Vec3::ZERO, true);
 
-		//if (skybox)
-		//{
-		//	skybox->SetFace(SF_NORTH,	GetTextureManager()->Load("res/red_north.tga"));
-		//	skybox->SetFace(SF_SOUTH,	GetTextureManager()->Load("res/red_south.tga"));
-		//	skybox->SetFace(SF_EAST,	GetTextureManager()->Load("res/red_east.tga"));
-		//	skybox->SetFace(SF_WEST,	GetTextureManager()->Load("res/red_west.tga"));
-		//	skybox->SetFace(SF_UP,		GetTextureManager()->Load("res/red_up.tga"));
-		//	skybox->SetFace(SF_DOWN,	GetTextureManager()->Load("res/red_down.tga"));
-		//}
-
 		terrain.CreateTerrain(64, 64, 1, 0.0f);
+		terrain.PlotCircle(4, 4, 4, 2);
+		terrain.UpdateVertexBuffer(true);
 
-		device()->resource_manager()->load("textures/red_north.tga");
-		device()->resource_manager()->load("textures/red_south.tga");
-		device()->resource_manager()->load("textures/red_east.tga");
-		device()->resource_manager()->load("textures/red_west.tga");
-		device()->resource_manager()->load("textures/red_up.tga");
-		device()->resource_manager()->load("textures/red_down.tga");
+		red_north = device()->load("textures/red_north.tga");
+		red_south = device()->load("textures/red_south.tga");
+		red_east  = device()->load("textures/red_east.tga");
+		red_west  = device()->load("textures/red_west.tga");
+		red_up    = device()->load("textures/red_up.tga");
+		red_down  = device()->load("textures/red_down.tga");
+		grass     = device()->load("textures/grass.tga");
 
-		grass = device()->resource_manager()->load("textures/grass.tga");
+		device()->resource_manager()->flush();
 
-		terrain.PlotCircle(4, 4, 4, 2);
+		TextureResource* grass_texture = (TextureResource*)device()->data(grass);
+		grass_id = device()->renderer()->load_texture(grass_texture);
+	}
 
-		//terrain.ApplyBrush(32, 32, 1.25f);
-		terrain.UpdateVertexBuffer(true);
+	void on_unload()
+	{
+		device()->unload(grass);
+		device()->unload(red_north);
+		device()->unload(red_south);
+		device()->unload(red_east);
+		device()->unload(red_west);
+		device()->unload(red_up);
+		device()->unload(red_down);
 	}
 
 	void render(float dt)
 	{
 		Renderer* renderer = device()->renderer();
+
+		renderer->set_clear_color(Color4::LIGHTBLUE);
 		
-		system->set_view_by_cursor();
+		if (camera_active)
+		{
+			system->set_view_by_cursor();
+		}
 		system->update(dt);
 
 		renderer->set_lighting(false);
@@ -186,18 +200,11 @@ public:
 
 		renderer->set_matrix(MT_MODEL, Mat4::IDENTITY);
 
-		if (device()->resource_manager()->is_loaded(grass))
+		if (device()->is_loaded(grass))
 		{
-			TextureResource* grass_tex = (TextureResource*)device()->resource_manager()->data(grass);
-			if (grass_tex)
-			{
-				TextureId grass_id = grass_tex->m_render_texture;
-				renderer->set_texturing(0, true);
-				renderer->set_texture(0, grass_id);
-				renderer->set_lighting(true);
-			}
+			renderer->set_texturing(0, true);
+			renderer->set_texture(0, grass_id);
 		}
-
 		
 		//glColor3f(1, 1, 1);
 
@@ -234,6 +241,13 @@ private:
 
 	// Resources
 	ResourceId grass;
+	ResourceId red_north;
+	ResourceId red_south;
+	ResourceId red_east;
+	ResourceId red_west;
+	ResourceId red_up;
+	ResourceId red_down;
+	TextureId grass_id;
 
 	bool optShowSkybox;
 	bool optShowCrate;
@@ -241,13 +255,15 @@ private:
 	bool mouseLeftPressed;
 	bool mouseRightPressed;
 	float wheel;
+	bool camera_active;
 	Ray ray;
 };
 
-class TerrainGame : public Game
-{
-public:
+MainScene m_scene;
+WndCtrl m_ctrl;
 
+extern "C"
+{
 	void init()
 	{
 		m_scene.on_load();
@@ -255,26 +271,11 @@ public:
 
 	void shutdown()
 	{
+		m_scene.on_unload();
 	}
 
-	void update(float dt)
+	void frame(float dt)
 	{
 		m_scene.render(dt);
 	}
-
-private:
-
-	MainScene m_scene;
-	WndCtrl m_ctrl;
-};
-
-extern "C" Game* create_game()
-{
-	return new TerrainGame;
 }
-
-extern "C" void destroy_game(Game* game)
-{
-	delete game;
-}
-

+ 2 - 4
src/CMakeLists.txt

@@ -3,17 +3,16 @@ set (SRC
 	Device.cpp
 	EventBuffer.cpp
 	Filesystem.cpp
-	Font.cpp
 	Image.cpp
 	MaterialResource.cpp
 	ResourceManager.cpp
 	Skybox.cpp
 	Terrain.cpp
-	World.cpp
 
 	TextureResource.cpp
 	TextResource.cpp
 	ScriptResource.cpp
+	FontResource.cpp
 	ArchiveResourceArchive.cpp
 	FileResourceArchive.cpp
 
@@ -28,7 +27,6 @@ set (HEADERS
 	Device.h
 	EventBuffer.h
 	Filesystem.h
-	Font.h
 	Glyph.h
 	Image.h
 	MaterialResource.h
@@ -37,11 +35,11 @@ set (HEADERS
 	ResourceArchive.h
 	Skybox.h
 	Terrain.h
-	World.h
 
 	TextureResource.h
 	TextResource.h
 	ScriptResource.h
+	FontResource.h
 	ArchiveResourceArchive.h
 	FileResourceArchive.h
 

+ 7 - 0
src/Config.h.in

@@ -33,3 +33,10 @@ OTHER DEALINGS IN THE SOFTWARE.
 #cmakedefine CROWN_BUILD_OPENGL
 #cmakedefine CROWN_BUILD_OPENGLES
 #cmakedefine CROWN_USE_FLOAT
+
+// OS peculiarities
+#if defined(LINUX) || defined(ANDROID)
+	#define GAME_LIBRARY_NAME "libgame.so"
+#elif defined(WINDOWS)
+	#define GAME_LIBRARY_NAME "game.dll"
+#endif

+ 1 - 1
src/Crown.h

@@ -96,7 +96,6 @@ OTHER DEALINGS IN THE SOFTWARE.
 // Engine
 #include "Camera.h"
 #include "Device.h"
-#include "Font.h"
 #include "Glyph.h"
 #include "Image.h"
 #include "ResourceArchive.h"
@@ -109,6 +108,7 @@ OTHER DEALINGS IN THE SOFTWARE.
 #include "TextureResource.h"
 #include "ScriptResource.h"
 #include "MaterialResource.h"
+#include "FontResource.h"
 
 // Engine/Filesystem
 #include "Filesystem.h"

+ 71 - 23
src/Device.cpp

@@ -39,6 +39,7 @@ OTHER DEALINGS IN THE SOFTWARE.
 #include "ArchiveResourceArchive.h"
 #include "FileResourceArchive.h"
 #include "ResourceManager.h"
+#include "TextureResource.h"
 
 #ifdef CROWN_BUILD_OPENGL
 	#include "renderers/gl/GLRenderer.h"
@@ -51,7 +52,9 @@ OTHER DEALINGS IN THE SOFTWARE.
 namespace crown
 {
 
-static const char* GAME_LIBRARY_NAME = "libgame.so";
+static void (*game_init)(void) = NULL;
+static void (*game_shutdown)(void) = NULL;
+static void (*game_frame)(float) = NULL;
 
 //-----------------------------------------------------------------------------
 Device::Device() :
@@ -71,14 +74,13 @@ Device::Device() :
 	m_last_delta_time(0.0f),
 
 	m_filesystem(NULL),
-	m_resource_manager(NULL),
 	m_input_manager(NULL),
 	m_renderer(NULL),
 	m_debug_renderer(NULL),
 
+	m_resource_manager(NULL),
 	m_resource_archive(NULL),
 
-	m_game(NULL),
 	m_game_library(NULL)
 {
 	string::strcpy(m_preferred_root_path, string::EMPTY);
@@ -121,7 +123,16 @@ bool Device::init(int argc, char** argv)
 
 	Log::i("Initializing Game...");
 
-	const char* game_library_path = m_filesystem->build_os_path(m_filesystem->root_path(), GAME_LIBRARY_NAME);
+	// Try to locate the game library
+	if (!m_filesystem->exists(GAME_LIBRARY_NAME))
+	{
+		Log::e("Unable to find the game library in the root path.", GAME_LIBRARY_NAME);
+		return false;
+	}
+
+	// Try to load the game library and bind functions
+	const char* game_library_path = m_filesystem->os_path(GAME_LIBRARY_NAME);
+
 	m_game_library = os::open_library(game_library_path);
 
 	if (m_game_library == NULL)
@@ -130,11 +141,12 @@ bool Device::init(int argc, char** argv)
 		return false;
 	}
 
-	create_game_t* create_game = (create_game_t*)os::lookup_symbol(m_game_library, "create_game");
-
-	m_game = create_game();
+	*(void**)(&game_init) = os::lookup_symbol(m_game_library, "init");
+	*(void**)(&game_shutdown) = os::lookup_symbol(m_game_library, "shutdown");
+	*(void**)(&game_frame) = os::lookup_symbol(m_game_library, "frame");
 
-	m_game->init();
+	// Initialize the game
+	game_init();
 
 	m_is_init = true;
 
@@ -152,14 +164,14 @@ void Device::shutdown()
 		return;
 	}
 
-	m_game->shutdown();
-
-	destroy_game_t* destroy_game = (destroy_game_t*)os::lookup_symbol(m_game_library, "destroy_game");
-
-	destroy_game(m_game);
-	m_game = NULL;
+	// Shutdowns the game
+	game_shutdown();
 
-	os::close_library(m_game_library);
+	// Unload the game library
+	if (m_game_library)
+	{
+		os::close_library(m_game_library);
+	}
 
 	if (m_input_manager)
 	{
@@ -283,21 +295,18 @@ float Device::last_delta_time() const
 //-----------------------------------------------------------------------------
 void Device::frame()
 {
-	m_current_time = os::milliseconds();
-	m_last_delta_time = (m_current_time - m_last_time) / 1000.0f;
+	m_current_time = os::microseconds();
+	m_last_delta_time = (m_current_time - m_last_time) / 1000000.0f;
 	m_last_time = m_current_time;
 
-	if (frame_count() % 5 == 0)
-	{
-		m_resource_manager->flush_load_queue();
-		m_resource_manager->bring_loaded_online();
-	}
+	m_resource_manager->check_load_queue();
+	m_resource_manager->bring_loaded_online();
 
 	m_input_manager->event_loop();
 
 	m_renderer->begin_frame();
 
-	m_game->update(last_delta_time());
+	game_frame(last_delta_time());
 
 	m_debug_renderer->draw_all();
 
@@ -306,6 +315,45 @@ void Device::frame()
 	m_frame_count++;
 }
 
+//-----------------------------------------------------------------------------
+ResourceId Device::load(const char* name)
+{
+	return m_resource_manager->load(name);
+}
+
+//-----------------------------------------------------------------------------
+void Device::unload(ResourceId name)
+{
+	m_resource_manager->unload(name);
+}
+
+//-----------------------------------------------------------------------------
+void Device::reload(ResourceId name)
+{
+	const void* old_resource = m_resource_manager->data(name);
+
+	m_resource_manager->reload(name);
+
+	const void* new_resource = m_resource_manager->data(name);
+
+	if (name.type == TEXTURE_TYPE)
+	{
+		m_renderer->reload_texture((TextureResource*)old_resource, (TextureResource*)new_resource);
+	}
+}
+
+//-----------------------------------------------------------------------------
+bool Device::is_loaded(ResourceId name)
+{
+	return m_resource_manager->is_loaded(name);
+}
+
+//-----------------------------------------------------------------------------
+const void* Device::data(ResourceId name)
+{
+	return m_resource_manager->data(name);
+}
+
 //-----------------------------------------------------------------------------
 void Device::create_filesystem()
 {

+ 9 - 2
src/Device.h

@@ -29,6 +29,7 @@ OTHER DEALINGS IN THE SOFTWARE.
 #include "Config.h"
 #include "OS.h"
 #include "MallocAllocator.h"
+#include "Resource.h"
 
 namespace crown
 {
@@ -83,6 +84,13 @@ public:
 	/// Updates all the subsystems
 	void					frame();
 
+	/// Loads a resource and returns its unique identifier.
+	ResourceId				load(const char* name);
+	void					unload(ResourceId name);
+	void					reload(ResourceId name);
+	bool					is_loaded(ResourceId name);
+	const void*				data(ResourceId name);
+
 	Filesystem*				filesystem();
 	ResourceManager*		resource_manager();
 	InputManager*			input_manager();
@@ -123,17 +131,16 @@ private:
 
 	// Public subsystems
 	Filesystem*				m_filesystem;
-	ResourceManager*		m_resource_manager;
 	InputManager*			m_input_manager;
 	Renderer*				m_renderer;
 	DebugRenderer*			m_debug_renderer;
 
 	// Private subsystems
+	ResourceManager*		m_resource_manager;
 	ResourceArchive*		m_resource_archive;
 	MallocAllocator			m_resource_allocator;
 
 	// The game currently running
-	Game*					m_game;
 	void*					m_game_library;
 
 private:

+ 5 - 9
src/FileResourceArchive.cpp

@@ -49,22 +49,18 @@ FileResourceArchive::~FileResourceArchive()
 FileStream* FileResourceArchive::find(ResourceId name)
 {
 	// Convert name/type into strings
-	char name_string[512];
-	char type_string[512];
+	char resource_name[512];
 
-	// FIXME
-	snprintf(name_string, 512, "%X", name.name);
-	snprintf(type_string, 512, "%X", name.type);
-
-	string::strncat(name_string, type_string, 512);
+	// Fixme
+	snprintf(resource_name, 512, "%.8X%.8X", name.name, name.type);
 
 	// Search the resource in the filesystem
-	if (m_filesystem.exists(name_string) == false)
+	if (m_filesystem.exists(resource_name) == false)
 	{
 		return NULL;
 	}
 
-	FileStream* file = (FileStream*)m_filesystem.open(name_string, SOM_READ);
+	FileStream* file = (FileStream*)m_filesystem.open(resource_name, SOM_READ);
 
 	/// FIXME harcoded!!!
 	file->skip(sizeof(uint32_t) * 3);

+ 10 - 2
src/Filesystem.cpp

@@ -38,8 +38,6 @@ Filesystem::Filesystem(const char* root_path)
 	assert(os::is_absolute_path(root_path));
 
 	string::strncpy(m_root_path, root_path, os::MAX_PATH_LENGTH);
-
-	Log::i("Root path : %s", m_root_path);
 }
 
 //-----------------------------------------------------------------------------
@@ -171,6 +169,16 @@ bool Filesystem::delete_dir(const char* relative_path)
 	return os::rmdir(os_path);
 }
 
+//-----------------------------------------------------------------------------
+const char* Filesystem::os_path(const char* relative_path)
+{
+	FilesystemEntry entry;
+
+	get_info(relative_path, entry);
+
+	return entry.os_path;
+}
+
 //-----------------------------------------------------------------------------
 FileStream* Filesystem::open(const char* relative_path, StreamOpenMode mode)
 {

+ 6 - 0
src/Filesystem.h

@@ -132,6 +132,12 @@ public:
 	/// Deletes the directory @relative_path
 	bool				delete_dir(const char* relative_path);
 
+	/// Returns the os-specific path which @relative_path refers to.
+	/// @note
+	/// In general, you typically do not want to use it for normal
+	/// file interactions. Prefer using the other methods whenever possible.
+	const char*			os_path(const char* relative_path);
+
 	/// Opens the file @relative_path with the specified access @mode
 	FileStream*			open(const char* relative_path, StreamOpenMode mode);
 

+ 27 - 6
src/Font.cpp → src/FontResource.cpp

@@ -23,27 +23,36 @@ FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
 OTHER DEALINGS IN THE SOFTWARE.
 */
 
-#include "Font.h"
-#include "MathUtils.h"
 #include "Types.h"
-#include "Image.h"
-#include "Log.h"
-#include "Filesystem.h"
+#include "FontResource.h"
 
 namespace crown
 {
 
+<<<<<<< HEAD:src/Font.cpp
 FontResource::FontResource() :
 	m_max_text_height(0),
 	m_max_character_height(0),
 	m_max_character_width(0)
+=======
+//-----------------------------------------------------------------------------
+void* FontResource::load(Allocator& allocator, ResourceArchive& archive, ResourceId id)
+>>>>>>> ba0fda4e8fc32e2c778ec5c565355d5b6fafe5c0:src/FontResource.cpp
 {
+	(void)allocator;
+	(void)archive;
+	(void)id;
+
+	return NULL;
 }
 
-FontResource::~FontResource()
+//-----------------------------------------------------------------------------
+void FontResource::online(void* resource)
 {
+	(void)resource;
 }
 
+<<<<<<< HEAD:src/Font.cpp
 Glyph& FontResource::glyph(uint32_t code)
 {
 	if (m_code_glyph_dict.contains(code))
@@ -65,6 +74,18 @@ void FontResource::set_code_glyph_metrics(uint32_t code, float left, float right
 	{
 		m_code_glyph_dict[code] = Glyph(code, left, right, bottom, top, width, height, advance, baseline);
 	}
+=======
+//-----------------------------------------------------------------------------
+void FontResource::unload(Allocator& allocator, void* resource)
+{
+	(void)allocator;
+	(void)resource;
+}
+
+//-----------------------------------------------------------------------------
+void FontResource::offline()
+{
+>>>>>>> ba0fda4e8fc32e2c778ec5c565355d5b6fafe5c0:src/FontResource.cpp
 }
 
 } // namespace crown

+ 10 - 21
src/Font.h → src/FontResource.h

@@ -26,49 +26,38 @@ OTHER DEALINGS IN THE SOFTWARE.
 #pragma once
 
 #include "Types.h"
-#include "List.h"
-#include "Dictionary.h"
 #include "Glyph.h"
 #include "Resource.h"
-#include "Image.h"
 
 namespace crown
 {
 
-class Image;
-class Texture;
+class Allocator;
+class ResourceArchive;
 
-/**
-	Font resource for using in text rendering.
-*/
 class FontResource
 {
+public:
 
-	typedef Dictionary<uint32_t, Glyph> CodeGlyphDict;
+	static void*		load(Allocator& allocator, ResourceArchive& archive, ResourceId id);
+	static void			online(void* resource);
+	static void			unload(Allocator& allocator, void* resource);
+	static void			offline();
 
 public:
 
-							FontResource();
-							~FontResource();
-
-	Glyph&					glyph(uint32_t code);	//! Returns the glyph for the desired point code
-	void					set_code_glyph_metrics(uint32_t code, float left, float right, float bottom, float top, float width, float height, float advance, float baseline);
+	/// Returns the glyph for the desired point32_t code
+	Glyph&					glyph(uint32_t code);
 
-	inline uint32_t			max_text_height() { return m_max_text_height; }
+	inline uint32_t			mat_text_heigth() { return m_max_text_height; }
 	inline uint32_t			max_character_height() { return m_max_character_height; }
 	inline uint32_t			max_character_width() { return m_max_character_width; }
 
-	ResourceId				texture() { return m_texture; }
-
 private:
 
-	CodeGlyphDict			m_code_glyph_dict;
-
 	uint32_t				m_max_text_height;
 	uint32_t				m_max_character_height;
 	uint32_t				m_max_character_width;
-
-	ResourceId				m_texture;
 };
 
 } // namespace crown

+ 31 - 3
src/Glyph.h

@@ -32,10 +32,9 @@ namespace crown
 
 class Glyph
 {
-
 public:
 
-	//! Constructor
+	/// Constructor
 	Glyph() :
 		m_code_point(0),
 		m_left(0),
@@ -49,8 +48,13 @@ public:
 	{
 	}
 
+<<<<<<< HEAD
 	//! Constructor
 	Glyph(uint32_t code, float left, float right, float bottom, float top, float width, float height, float advance, float baseline) :
+=======
+	/// Constructor
+	Glyph(uint32_t code, float left, float right, float bottom, float top, float width, float height, float advance, float m_baseline) :
+>>>>>>> ba0fda4e8fc32e2c778ec5c565355d5b6fafe5c0
 		m_code_point(code),
 		m_left(left),
 		m_right(right),
@@ -59,17 +63,26 @@ public:
 		m_width(width),
 		m_height(height),
 		m_advance(advance),
+<<<<<<< HEAD
 		m_baseline(baseline)
+=======
+		m_baseline(m_baseline)
+>>>>>>> ba0fda4e8fc32e2c778ec5c565355d5b6fafe5c0
 	{
 	}
 
-	//! Destructor
+	/// Destructor
 	~Glyph()
 	{
 	}
 
+<<<<<<< HEAD
 	//! Returns the glyph's metrics
 	void metrics(float& left, float& right, float& bottom, float& top, float& width, float& height, float& advance, float& baseline) const
+=======
+	/// Returns the glyph's metrics
+	void metrics(float& left, float& right, float& bottom, float& top, float& width, float& height, float& advance, float& m_baseline) const
+>>>>>>> ba0fda4e8fc32e2c778ec5c565355d5b6fafe5c0
 	{
 		left = m_left;
 		right = m_right;
@@ -78,11 +91,19 @@ public:
 		width = m_width;
 		height = m_height;
 		advance = m_advance;
+<<<<<<< HEAD
 		baseline = m_baseline;
 	}
 
 	//! Sets the glyph's metrics
 	void set_metrics(float left, float right, float bottom, float top, float width, float height, float advance, float baseline)
+=======
+		m_baseline = m_baseline;
+	}
+
+	/// Sets the glyph's metrics
+	void set_metrics(float left, float right, float bottom, float top, float width, float height, float advance, float m_baseline)
+>>>>>>> ba0fda4e8fc32e2c778ec5c565355d5b6fafe5c0
 	{
 		m_left = left;
 		m_right = right;
@@ -91,10 +112,17 @@ public:
 		m_width = width;
 		m_height = height;
 		m_advance = advance;
+<<<<<<< HEAD
 		m_baseline = baseline;
 	}
 
 	//! Returns the glyph's code point
+=======
+		m_baseline = m_baseline;
+	}
+
+	/// Returns the glyph's code point32_t
+>>>>>>> ba0fda4e8fc32e2c778ec5c565355d5b6fafe5c0
 	uint32_t code_point() const
 	{
 		return m_code_point;

+ 20 - 0
src/Resource.h

@@ -26,10 +26,25 @@ OTHER DEALINGS IN THE SOFTWARE.
 #pragma once
 
 #include "Types.h"
+#include "Hash.h"
+#include "String.h"
 
 namespace crown
 {
 
+/// Hashed values for supported resource types
+const char* const TEXTURE_EXTENSION		= "tga";
+const char* const MESH_EXTENSION		= "dae";
+const char* const SCRIPT_EXTENSION		= "lua";
+const char* const TEXT_EXTENSION		= "txt";
+const char* const MATERIAL_EXTENSION	= "material";
+
+const uint32_t TEXTURE_TYPE		= hash::murmur2_32(TEXTURE_EXTENSION,  string::strlen(TEXTURE_EXTENSION),  0);
+const uint32_t MESH_TYPE		= hash::murmur2_32(MESH_EXTENSION,     string::strlen(MESH_EXTENSION),     0);
+const uint32_t SCRIPT_TYPE		= hash::murmur2_32(SCRIPT_EXTENSION,   string::strlen(SCRIPT_EXTENSION),   0);
+const uint32_t TEXT_TYPE		= hash::murmur2_32(TEXT_EXTENSION,     string::strlen(TEXT_EXTENSION),     0);
+const uint32_t MATERIAL_TYPE	= hash::murmur2_32(MATERIAL_EXTENSION, string::strlen(MATERIAL_EXTENSION), 0);
+
 /// Enumerates the loading states of a resource
 enum ResourceState
 {
@@ -46,6 +61,11 @@ struct ResourceId
 	uint32_t		name;		// Hashed resource name
 	uint32_t		type;		// Hashed resource type
 	uint32_t		index;		// Index into the ResourceManager internal list
+
+	bool			operator==(const ResourceId& b)
+	{
+		return name == b.name && type == b.type && index == b.index;
+	}
 };
 
 } // namespace crown

+ 80 - 31
src/ResourceManager.cpp

@@ -47,12 +47,6 @@ ResourceManager::ResourceManager(ResourceArchive& archive, Allocator& allocator)
 	m_loaded_queue(m_allocator),
 	m_thread(ResourceManager::background_thread, (void*)this, "resource-loader-thread")
 {
-	// FIXME hardcoded seed
-	m_config_hash = hash::murmur2_32("config", 6, 0);
-	m_texture_hash = hash::murmur2_32("tga", 3, 0);
-	m_mesh_hash = hash::murmur2_32("mesh", 4, 0);
-	m_txt_hash = hash::murmur2_32("txt", 3, 0);
-	m_script_hash = hash::murmur2_32("lua", 3, 0);
 }
 
 //-----------------------------------------------------------------------------
@@ -81,17 +75,23 @@ void ResourceManager::unload(ResourceId name)
 {
 	assert(has(name));
 	
+	m_resources_mutex.lock();
+
 	ResourceEntry& entry = m_resources[name.index];
 	
 	entry.references--;
 	
 	if (entry.references == 0 && entry.state == RS_LOADED)
 	{
-		//m_resource_loader.unload(name, entry.resource);
+		unload_by_type(name, entry.resource);
 
 		entry.state = RS_UNLOADED;
 		entry.resource = NULL;
+
+
 	}
+
+	m_resources_mutex.unlock();
 }
 
 //-----------------------------------------------------------------------------
@@ -99,12 +99,22 @@ void ResourceManager::reload(ResourceId name)
 {
 	assert(has(name));
 	
+	m_resources_mutex.lock();
+
 	ResourceEntry& entry = m_resources[name.index];
 	
 	if (entry.state == RS_LOADED)
 	{
-		// FIXME
+		unload_by_type(name, entry.resource);
+
+		entry.state = RS_UNLOADED;
+		entry.resource = NULL;
+
+		entry.resource = load_by_type(name);
+		entry.state = RS_LOADED;
 	}
+
+	m_resources_mutex.unlock();
 }
 
 //-----------------------------------------------------------------------------
@@ -167,7 +177,44 @@ uint32_t ResourceManager::references(ResourceId name) const
 }
 
 //-----------------------------------------------------------------------------
-void ResourceManager::flush_load_queue()
+uint32_t ResourceManager::remaining() const
+{
+	uint32_t count = 0;
+
+	m_loading_mutex.lock();
+
+	count = m_loading_queue.size();
+
+	m_loading_mutex.unlock();
+
+	return count;
+}
+
+//-----------------------------------------------------------------------------
+void ResourceManager::flush()
+{
+	check_load_queue();
+
+	while (true)
+	{
+		// Wait for all the resources to be loaded
+		// by the background thread
+		m_loading_mutex.lock();
+		while (m_loading_queue.size() > 0)
+		{
+			m_all_loaded.wait(m_loading_mutex);
+		}
+		m_loading_mutex.unlock();
+
+		// When all loaded, bring them online
+		bring_loaded_online();
+
+		return;
+	}
+}
+
+//-----------------------------------------------------------------------------
+void ResourceManager::check_load_queue()
 {
 	m_loading_mutex.lock();
 
@@ -175,7 +222,7 @@ void ResourceManager::flush_load_queue()
 	{
 		m_loading_requests.signal();
 	}
-	
+
 	m_loading_mutex.unlock();
 }
 
@@ -184,7 +231,6 @@ void ResourceManager::bring_loaded_online()
 {
 	m_loaded_mutex.lock();
 
-	// Update master table and bring online
 	while (m_loaded_queue.size() > 0)
 	{
 		LoadedResource lr = m_loaded_queue.front();
@@ -236,11 +282,13 @@ ResourceId ResourceManager::load(uint32_t name, uint32_t type)
 //-----------------------------------------------------------------------------
 void ResourceManager::background_load()
 {
-	// FIXME: Maybe epic crash because of concurrent access to the same allocator?
 	while (true)
 	{
 		m_loading_mutex.lock();
-		m_loading_requests.wait(m_loading_mutex);
+		while (m_loading_queue.size() == 0)
+		{
+			m_loading_requests.wait(m_loading_mutex);
+		}
 
 		ResourceId resource = m_loading_queue.front();
 		m_loading_queue.pop_front();
@@ -254,29 +302,30 @@ void ResourceManager::background_load()
 		lr.data = data;
 
 		m_loaded_mutex.lock();
-
 		m_loaded_queue.push_back(lr);
-
 		m_loaded_mutex.unlock();
+
+		m_loading_mutex.lock();
+		if (m_loading_queue.size() == 0)
+		{
+			m_all_loaded.signal();
+		}
+		m_loading_mutex.unlock();
 	}
 }
 
 //-----------------------------------------------------------------------------
 void* ResourceManager::load_by_type(ResourceId name) const
 {
-	if (name.type == m_config_hash)
-	{
-		return NULL;
-	}
-	else if (name.type == m_texture_hash)
+	if (name.type == TEXTURE_TYPE)
 	{
 		return TextureResource::load(m_resource_allocator, m_resource_archive, name);
 	}
-	else if (name.type == m_txt_hash)
+	else if (name.type == TEXT_TYPE)
 	{
 		return TextResource::load(m_resource_allocator, m_resource_archive, name);
 	}
-	else if (name.type == m_script_hash)
+	else if (name.type == SCRIPT_TYPE)
 	{
 		return ScriptResource::load(m_resource_allocator, m_resource_archive, name);
 	}
@@ -287,19 +336,15 @@ void* ResourceManager::load_by_type(ResourceId name) const
 //-----------------------------------------------------------------------------
 void ResourceManager::unload_by_type(ResourceId name, void* resource) const
 {
-	if (name.type == m_config_hash)
-	{
-		return;
-	}
-	else if (name.type == m_texture_hash)
+	if (name.type == TEXTURE_TYPE)
 	{
 		TextureResource::unload(m_resource_allocator, (TextureResource*)resource);
 	}
-	else if (name.type == m_txt_hash)
+	else if (name.type == TEXT_TYPE)
 	{
 		TextResource::unload(m_resource_allocator, (TextResource*)resource);
 	}
-	else if (name.type == m_script_hash)
+	else if (name.type == SCRIPT_TYPE)
 	{
 		ScriptResource::unload(m_resource_allocator, (ScriptResource*)resource);
 	}
@@ -310,11 +355,15 @@ void ResourceManager::unload_by_type(ResourceId name, void* resource) const
 //-----------------------------------------------------------------------------
 void ResourceManager::online(ResourceId name, void* resource)
 {
-	if (name.type == m_texture_hash)
+	if (name.type == TEXTURE_TYPE)
 	{
 		TextureResource::online((TextureResource*)resource);
 	}
-	else if (name.type == m_script_hash)
+	else if (name.type == TEXT_TYPE)
+	{
+		TextResource::unload(m_resource_allocator, (TextResource*)resource);
+	}
+	else if (name.type == SCRIPT_TYPE)
 	{
 		ScriptResource::online((ScriptResource*)resource);
 	}

+ 18 - 12
src/ResourceManager.h

@@ -110,14 +110,24 @@ public:
 	/// you can use the data associated with it).
 	bool					is_loaded(ResourceId name) const;
 
-	// Returns the number of references to the @resource
+	/// Returns the number of references to the @resource
 	uint32_t				references(ResourceId name) const;
 
-	void					flush_load_queue();
-	void					bring_loaded_online();
+	/// Returns the number of resources still waiting to load.
+	uint32_t				remaining() const;
+
+	/// Forces all the loading requests to complete before preceeding.
+	void					flush();
 
 private:
 
+	// Checks the load queue and signal the backgroud about pending
+	// requests. It is normally called only by the Device.
+	void					check_load_queue();
+	// Calls online() on loaded resources. Must be called only
+	// in the main thread and generally only by Device.
+	void					bring_loaded_online();
+
 	// Loads the resource by name and type and returns its ResourceId.
 	ResourceId				load(uint32_t name, uint32_t type);
 
@@ -149,19 +159,15 @@ private:
 
 	// Background loading thread
 	Thread					m_thread;
-	Mutex					m_loading_mutex;
+
+	mutable Mutex			m_loading_mutex;
 	Cond 					m_loading_requests;
+	Cond 					m_all_loaded;
+
 	Mutex					m_loaded_mutex;
 	mutable Mutex			m_resources_mutex;
 
-private:
-
-	// Hashes of resource types (FIXME)
-	uint32_t			m_config_hash;
-	uint32_t			m_texture_hash;
-	uint32_t			m_mesh_hash;
-	uint32_t			m_txt_hash;
-	uint32_t			m_script_hash;
+	friend class			Device;
 };
 
 } // namespace crown

+ 0 - 2
src/TextureResource.cpp

@@ -39,8 +39,6 @@ void* TextureResource::load(Allocator& allocator, ResourceArchive& archive, Reso
 void TextureResource::online(void* resource)
 {
 	assert(resource != NULL);
-
-	((TextureResource*)resource)->m_render_texture = device()->renderer()->load_texture((TextureResource*)resource);
 }
 
 //-----------------------------------------------------------------------------

+ 0 - 4
src/TextureResource.h

@@ -58,10 +58,6 @@ private:
 	uint16_t			m_width;
 	uint16_t			m_height;
 	uint8_t*			m_data;
-
-public:
-
-	TextureId			m_render_texture;
 };
 
 } // namespace crown

+ 0 - 25
src/World.cpp

@@ -1,25 +0,0 @@
-/*
-Copyright (c) 2012 Daniele Bartolini, Simone Boscaratto
-
-Permission is hereby granted, free of charge, to any person
-obtaining a copy of this software and associated documentation
-files (the "Software"), to deal in the Software without
-restriction, including without limitation the rights to use,
-copy, modify, merge, publish, distribute, sublicense, and/or sell
-copies of the Software, and to permit persons to whom the
-Software is furnished to do so, subject to the following
-conditions:
-
-The above copyright notice and this permission notice shall be
-included in all copies or substantial portions of the Software.
-
-THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
-EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
-OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
-NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
-HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
-WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
-FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
-OTHER DEALINGS IN THE SOFTWARE.
-*/
-

+ 0 - 62
src/World.h

@@ -1,62 +0,0 @@
-/*
-Copyright (c) 2012 Daniele Bartolini, Simone Boscaratto
-
-Permission is hereby granted, free of charge, to any person
-obtaining a copy of this software and associated documentation
-files (the "Software"), to deal in the Software without
-restriction, including without limitation the rights to use,
-copy, modify, merge, publish, distribute, sublicense, and/or sell
-copies of the Software, and to permit persons to whom the
-Software is furnished to do so, subject to the following
-conditions:
-
-The above copyright notice and this permission notice shall be
-included in all copies or substantial portions of the Software.
-
-THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
-EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
-OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
-NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
-HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
-WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
-FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
-OTHER DEALINGS IN THE SOFTWARE.
-*/
-
-#pragma once
-
-namespace crown
-{
-
-/**
-	The game world.
-
-	World represents the place where int32_teractions between all the
-	game entities occur. It holds the systems which 
-*/
-class World
-{
-
-public:
-
-				World();
-				~World();
-
-	void		SetTimeOfDay(uint16_t seconds);		//!< Sets the time of day in seconds
-	uint16_t		GetTimeOfDay() const;				//!< Returns the time of day in seconds
-
-	void		Update(uint32_t dt);
-
-private:
-
-	uint16_t		mTimeOfDay;			// Time of day in seconds. (60 * 60 * 24 secs)
-	uint16_t		mTimeOfDaySpeed;	// Speed of seconds in 1/100 of seconds. (100 = 1 game second equals 1 real second)
-
-	float		mGravity;			// Gravity of the world in meters/seconds
-
-	Camera		mCamera;			// Camera (i.e. the point32_t of view)
-	Skybox		mSkybox;			// The skybox
-};
-
-} // namespace crown
-

+ 6 - 6
src/core/bv/Box.h

@@ -63,22 +63,22 @@ public:
 	/// Adds @count @boxes expanding if necessay.
 	void			add_boxes(const Box* boxes, uint32_t count);
 
-	/// Returns whether point32_t "p" is contained.
+	/// Returns whether point @p is contained in the box.
 	bool			contains_point(const Vec3& p) const;
 
-	/// Returns a box's vertex.
+	/// Returns the @index -th vertex of the box.
 	Vec3			vertex(uint32_t index) const;		
 
-	/// Returns the box trasformed according to "mat" matrix.
+	/// Returns the box trasformed according to @mat matrix into @result.
 	void			transformed(const Mat4& mat, Box& result) const;	
 
-	/// Returns the eight box's vertices
+	/// Returns the eight vertices of the box.
 	void			to_vertices(Vec3 v[8]) const;	
 
-	/// Returns as a sphere						
+	/// Returns as a sphere.						
 	Sphere			to_sphere() const;										
 
-	/// Sets min and max to zero
+	/// Sets min and max to zero.
 	void			zero();													
 
 private:

+ 4 - 5
src/core/bv/Circle.h

@@ -41,22 +41,21 @@ class Circle
 {
 public:
 
-	/// Does nothing for efficiency
+	/// Does nothing for efficiency.
 					Circle();
 					
-	/// Constructs from @center and @radius
+	/// Constructs from @center and @radius.
 					Circle(const Vec2& center, real radius);	
 					Circle(const Circle& circle);				
 
 	const Vec2&		center() const;							
-	real			radius() const;				
-
+	real			radius() const;	
 	void			set_center(const Vec2& center);			
 	void			set_radius(real radius);				
 
 	real			area() const;						
 
-	/// Returns a Rect containing the circle
+	/// Returns a Rect containing the circle.
 	Rect			to_rect() const;
 
 private:

+ 0 - 6
src/core/bv/Frustum.cpp

@@ -34,12 +34,6 @@ namespace crown
 //-----------------------------------------------------------------------------
 Frustum::Frustum()
 {
-	m_planes[FP_LEFT]		= Plane::ZERO;
-	m_planes[FP_RIGHT]		= Plane::ZERO;
-	m_planes[FP_BOTTOM]		= Plane::ZERO;
-	m_planes[FP_TOP]		= Plane::ZERO;
-	m_planes[FP_NEAR]		= Plane::ZERO;
-	m_planes[FP_FAR]		= Plane::ZERO;
 }
 
 //-----------------------------------------------------------------------------

+ 5 - 4
src/core/bv/Frustum.h

@@ -49,19 +49,20 @@ class Frustum
 {
 public:
 
+	/// Does nothing for efficiency.
 				Frustum();				
 				Frustum(const Frustum& frustum);
 
-	/// Returns whether @point is contained into the frustum
+	/// Returns whether @point is contained into the frustum.
 	bool		contains_point(const Vec3& point) const;	
 
-	/// Returns one of the eight frustum's corners
+	/// Returns one of the eight frustum's corners.
 	Vec3		vertex(uint32_t index) const;			
 
-	/// Builds the view frustum according to the matrix @m
+	/// Builds the view frustum according to the matrix @m.
 	void		from_matrix(const Mat4& m);				
 
-	/// Returns a Box containing the frustum volume
+	/// Returns a Box containing the frustum volume.
 	Box			to_box() const;							
 
 private:

+ 8 - 8
src/core/bv/Rect.h

@@ -58,28 +58,28 @@ public:
 	real			radius() const;					
 	real			area() const;		
 
-	/// Returns the diagonal
+	/// Returns the diagonal of the rect.
 	Vec2			size() const;						
 
-	/// Returns whether @point is contained
+	/// Returns whether @point point is contained into the rect.
 	bool			contains_point(const Vec2& point) const;
 
-	/// Returns whether intersects @r
+	/// Returns whether the rect intersects @r.
 	bool			intersects_rect(const Rect& rect) const;	
 
-	/// Sets the Rect from a center and a width - height
+	/// Sets the Rect from a @center and a @width - @height
 	void			set_from_center_and_dimensions(Vec2 center, real width, real height);	
 
-	/// Returns the four rect's vertices
+	/// Returns the four vertices of the rect.
 	void			vertices(Vec2 v[4]) const;
 
-	/// Returns a rect's vertex
+	/// Returns the @index -th vetex of the rect.
 	Vec2			vertex(uint32_t index) const;			
 
-	/// Returns the equivalent circle
+	/// Returns the equivalent circle.
 	Circle			to_circle() const;
 
-	/// Ensures that min and max aren't swapped
+	/// Ensures that min and max aren't swapped.
 	void			fix();									
 
 private:

+ 4 - 4
src/core/bv/Sphere.h

@@ -43,7 +43,7 @@ public:
 	/// Does nothing for efficiency.
 					Sphere();
 
-	/// Constructs from center and radius.
+	/// Constructs from @center and @radius.
 					Sphere(const Vec3& center, real radius);
 					Sphere(const Sphere& a);
 
@@ -54,13 +54,13 @@ public:
 	void			set_center(const Vec3& center);
 	void			set_radius(real radius);
 
-	/// Adds a point expanding if necessary.
+	/// Adds @count @points to the sphere expanding if necessary.
 	void			add_points(const Vec3* points, uint32_t count);	
 
-	/// Adds a sphere expanding if necessary.
+	/// Adds @count @spheres expanding if necessary.
 	void			add_spheres(const Sphere* spheres, uint32_t count);	
 
-	/// Returns whether point @p is contained.
+	/// Returns whether point @p is contained into the sphere.
 	bool			contains_point(const Vec3& p) const;		
 
 private:

+ 3 - 0
src/core/strings/Hash.h

@@ -25,6 +25,9 @@ OTHER DEALINGS IN THE SOFTWARE.
 
 #pragma once
 
+#include <cassert>
+#include "Types.h"
+
 namespace crown
 {
 

+ 3 - 7
src/renderers/Renderer.h

@@ -94,6 +94,9 @@ public:
 	/// Set whether the given texture @unit is enabled.
 	virtual void set_texturing(uint32_t unit, bool texturing) = 0;
 
+	//! Sets the texture to use in the specified layer
+	virtual void set_texture(uint32_t layer, TextureId texture) = 0;
+
 	/// Sets the texture @mode for the given texture @unit.
 	virtual void set_texture_mode(uint32_t unit, TextureMode mode, const Color4& blendColor) = 0;
 
@@ -169,13 +172,7 @@ public:
 	virtual void set_point_size(float size) = 0;
 	virtual void set_point_params(float min, float max) = 0;
 
-	//! Sets the texture to use in the specified layer
-	virtual void set_texture(uint32_t layer, TextureId texture) = 0;
-
-	//! Returns the current matrix
 	virtual Mat4 get_matrix(MatrixType type) const = 0;
-
-	//! Loads the current matrix
 	virtual void set_matrix(MatrixType type, const Mat4& matrix) = 0;
 
 	virtual void draw_vertex_index_buffer(const VertexBuffer* vertices, const IndexBuffer* indices) = 0;
@@ -184,7 +181,6 @@ public:
 	virtual void draw_lines(const float* vertices, const float* colors, uint32_t count) = 0;
 	virtual void draw_triangles(const float* vertices, const float* normals, const float* uvs, const uint16_t* indices, uint32_t count) = 0;
 
-	// FIXME
 	virtual TextureId	load_texture(TextureResource* texture) = 0;
 	virtual void		unload_texture(TextureResource* texture) = 0;
 	virtual TextureId	reload_texture(TextureResource* old_texture, TextureResource* new_texture) = 0;

+ 24 - 30
src/renderers/gl/GLRenderer.cpp

@@ -37,7 +37,6 @@ OTHER DEALINGS IN THE SOFTWARE.
 #include "Log.h"
 #include "Material.h"
 #include "Allocator.h"
-
 #include "TextureResource.h"
 
 #if defined(WINDOWS)
@@ -259,7 +258,7 @@ void GLRenderer::set_texture_mode(uint32_t unit, TextureMode mode, const Color4&
 	if (!activate_texture_unit(unit))
 		return;
 
-	GLint envMode = GL::GetTextureMode(mode);
+	GLint envMode = GL::texture_mode(mode);
 
 	if (envMode == GL_BLEND)
 	{
@@ -272,7 +271,7 @@ void GLRenderer::set_texture_mode(uint32_t unit, TextureMode mode, const Color4&
 //-----------------------------------------------------------------------------
 void GLRenderer::set_texture_wrap(uint32_t unit, TextureWrap wrap)
 {
-	GLenum glWrap = GL::GetTextureWrap(wrap);
+	GLenum glWrap = GL::texture_wrap(wrap);
 
 	glTexParameteri(m_texture_unit_target[unit], GL_TEXTURE_WRAP_S, glWrap);
 	glTexParameteri(m_texture_unit_target[unit], GL_TEXTURE_WRAP_T, glWrap);
@@ -288,7 +287,7 @@ void GLRenderer::set_texture_filter(uint32_t unit, TextureFilter filter)
 	GLint minFilter;
 	GLint magFilter;
 
-	GL::GetTextureFilter(filter, minFilter, magFilter);
+	GL::texture_filter(filter, minFilter, magFilter);
 
 	glTexParameteri(m_texture_unit_target[unit], GL_TEXTURE_MIN_FILTER, minFilter);
 	glTexParameteri(m_texture_unit_target[unit], GL_TEXTURE_MAG_FILTER, magFilter);
@@ -342,7 +341,7 @@ void GLRenderer::set_depth_write(bool write)
 //-----------------------------------------------------------------------------
 void GLRenderer::set_depth_func(CompareFunction func)
 {
-	GLenum glFunc = GL::GetCompareFunction(func);
+	GLenum glFunc = GL::compare_function(func);
 
 	glDepthFunc(glFunc);
 }
@@ -376,12 +375,12 @@ void GLRenderer::set_blending(bool blending)
 //-----------------------------------------------------------------------------
 void GLRenderer::set_blending_params(BlendEquation equation, BlendFunction src, BlendFunction dst, const Color4& color)
 {
-	GLenum glEquation = GL::GetBlendEquation(equation);
+	GLenum glEquation = GL::blend_equation(equation);
 
 	glBlendEquation(glEquation);
 
-	GLenum glSrcFactor = GL::GetBlendFunction(src);
-	GLenum glDstFactor = GL::GetBlendFunction(dst);
+	GLenum glSrcFactor = GL::blend_function(src);
+	GLenum glDstFactor = GL::blend_function(dst);
 
 	glBlendFunc(glSrcFactor, glDstFactor);
 
@@ -417,7 +416,7 @@ void GLRenderer::set_fog(bool fog)
 //-----------------------------------------------------------------------------
 void GLRenderer::set_fog_params(FogMode mode, float density, float start, float end, const Color4& color)
 {
-	GLenum glMode = GL::GetFogMode(mode);
+	GLenum glMode = GL::fog_mode(mode);
 
 	glFogi(GL_FOG_MODE, glMode);
 	glFogf(GL_FOG_DENSITY, density);
@@ -442,7 +441,7 @@ void GLRenderer::set_alpha_test(bool test)
 //-----------------------------------------------------------------------------
 void GLRenderer::set_alpha_params(CompareFunction func, float ref)
 {
-	GLenum glFunc = GL::GetCompareFunction(func);
+	GLenum glFunc = GL::compare_function(func);
 
 	glAlphaFunc(glFunc, ref);
 }
@@ -463,7 +462,7 @@ void GLRenderer::set_shading_type(ShadingType type)
 //-----------------------------------------------------------------------------
 void GLRenderer::set_polygon_mode(PolygonMode mode)
 {
-	GLenum glMode = GL::GetPolygonMode(mode);
+	GLenum glMode = GL::polygon_mode(mode);
 
 	glPolygonMode(GL_FRONT_AND_BACK, glMode);
 }
@@ -762,29 +761,15 @@ void GLRenderer::draw_triangles(const float* vertices, const float* normals, con
 //-----------------------------------------------------------------------------
 TextureId GLRenderer::load_texture(TextureResource* texture)
 {
-	// Search for an already existent texture
-	for (uint32_t i = 0; i < MAX_TEXTURES; i++)
-	{
-		if (m_textures[i].texture_resource == texture)
-		{
-			return m_textures[i].id;
-		}
-	}
-
 	// If texture not found, create a new one
 	GLuint gl_texture_object;
 
 	glGenTextures(1, &gl_texture_object);
-
 	glBindTexture(GL_TEXTURE_2D, gl_texture_object);
-
-	GLint gl_texture_format = GL::GetPixelFormat(texture->format());
-
-	//FIXME FIXME FIXME
 	glTexParameteri(GL_TEXTURE_2D, GL_GENERATE_MIPMAP, GL_TRUE);
 
 	glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, texture->width(), texture->height(), 0,
-				 gl_texture_format, GL_UNSIGNED_BYTE, texture->data());
+				 GL::pixel_format(texture->format()), GL_UNSIGNED_BYTE, texture->data());
 
 	TextureId id;
 	id.index = m_texture_count;
@@ -809,10 +794,19 @@ void GLRenderer::unload_texture(TextureResource* texture)
 //-----------------------------------------------------------------------------
 TextureId GLRenderer::reload_texture(TextureResource* old_texture, TextureResource* new_texture)
 {
-	// FIXME
-	(void)old_texture;
-	(void)new_texture;
-	return TextureId();
+	for (uint32_t i = 0; i < m_texture_count; i++)
+	{
+		if (m_textures[i].texture_resource == old_texture)
+		{
+			// Reload texture
+			glBindTexture(GL_TEXTURE_2D, m_textures[i].texture_object);
+
+			glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, new_texture->width(), new_texture->height(),
+				GL::pixel_format(new_texture->format()), GL_UNSIGNED_BYTE, new_texture->data());
+
+			m_textures[i].texture_resource = new_texture;
+		}
+	}
 }
 
 //-----------------------------------------------------------------------------

+ 5 - 2
src/renderers/gl/GLRenderer.h

@@ -27,6 +27,7 @@ OTHER DEALINGS IN THE SOFTWARE.
 
 #include <GL/glew.h>
 #include "Renderer.h"
+#include "Resource.h"
 
 #define MAX_TEXTURES 1024
 #define MAX_TEXTURE_UNITS 8
@@ -41,8 +42,9 @@ class TextureResource;
 struct GLTexture
 {
 	TextureId			id;
-	GLuint				texture_object;
 	TextureResource*	texture_resource;
+
+	GLuint				texture_object;
 };
 
 /// OpenGL renderer
@@ -123,7 +125,8 @@ public:
 
 private:
 
-	bool				activate_texture_unit(uint32_t unit);		//!< Activates a texture unit and returns true if succes
+	/// Activates a texture unit and returns true if succes
+	bool				activate_texture_unit(uint32_t unit);
 	bool				activate_light(uint32_t light);
 
 	void				check_gl_errors();

+ 21 - 25
src/renderers/gl/GLUtils.h

@@ -41,26 +41,22 @@ OTHER DEALINGS IN THE SOFTWARE.
 namespace crown
 {
 
-/**
-	OpenGL utilities.
-
-	Utilities for converting from wrapped names to GL names and vice-versa.
-*/
+/// OpenGL Utilities for converting from wrapped names to GL names and vice-versa.
 class GL
 {
 
 public:
 
-	static GLenum			GetCompareFunction(CompareFunction function);
-	static GLenum			GetBlendFunction(BlendFunction function);
-	static GLenum			GetBlendEquation(BlendEquation equation);
-	static GLenum			GetTextureMode(TextureMode mode);
-	static GLenum			GetTextureWrap(TextureWrap wrap);
-	static void				GetTextureFilter(TextureFilter filter, GLint& minFilter, GLint& magFilter);
-	static GLenum			GetFogMode(FogMode mode);
-	static GLenum			GetPolygonMode(PolygonMode mode);
-	static GLenum			GetPixelFormat(PixelFormat format);
-	static PixelFormat		GetPixelFormatFromGLFormat(GLenum format);
+	static GLenum			compare_function(CompareFunction function);
+	static GLenum			blend_function(BlendFunction function);
+	static GLenum			blend_equation(BlendEquation equation);
+	static GLenum			texture_mode(TextureMode mode);
+	static GLenum			texture_wrap(TextureWrap wrap);
+	static void				texture_filter(TextureFilter filter, GLint& minFilter, GLint& magFilter);
+	static GLenum			fog_mode(FogMode mode);
+	static GLenum			polygon_mode(PolygonMode mode);
+	static GLenum			pixel_format(PixelFormat format);
+	static PixelFormat		pixel_format_from_gl_format(GLenum format);
 
 private:
 
@@ -79,7 +75,7 @@ private:
 };
 
 //-----------------------------------------------------------------------------
-inline GLenum GL::GetCompareFunction(CompareFunction function)
+inline GLenum GL::compare_function(CompareFunction function)
 {
 	assert(function < CF_COUNT);
 
@@ -87,7 +83,7 @@ inline GLenum GL::GetCompareFunction(CompareFunction function)
 }
 
 //-----------------------------------------------------------------------------
-inline GLenum GL::GetBlendFunction(BlendFunction function)
+inline GLenum GL::blend_function(BlendFunction function)
 {
 	assert(function < BF_COUNT);
 
@@ -95,7 +91,7 @@ inline GLenum GL::GetBlendFunction(BlendFunction function)
 }
 
 //-----------------------------------------------------------------------------
-inline GLenum GL::GetBlendEquation(BlendEquation equation)
+inline GLenum GL::blend_equation(BlendEquation equation)
 {
 	assert(equation < BE_COUNT);
 
@@ -103,7 +99,7 @@ inline GLenum GL::GetBlendEquation(BlendEquation equation)
 }
 
 //-----------------------------------------------------------------------------
-inline GLenum GL::GetTextureMode(TextureMode mode)
+inline GLenum GL::texture_mode(TextureMode mode)
 {
 	assert(mode < TM_COUNT);
 
@@ -111,7 +107,7 @@ inline GLenum GL::GetTextureMode(TextureMode mode)
 }
 
 //-----------------------------------------------------------------------------
-inline GLenum GL::GetTextureWrap(TextureWrap wrap)
+inline GLenum GL::texture_wrap(TextureWrap wrap)
 {
 	assert(wrap < TW_COUNT);
 
@@ -119,7 +115,7 @@ inline GLenum GL::GetTextureWrap(TextureWrap wrap)
 }
 
 //-----------------------------------------------------------------------------
-inline void GL::GetTextureFilter(TextureFilter filter, GLint& minFilter, GLint& magFilter)
+inline void GL::texture_filter(TextureFilter filter, GLint& minFilter, GLint& magFilter)
 {
 	assert(filter < TF_COUNT);
 
@@ -128,7 +124,7 @@ inline void GL::GetTextureFilter(TextureFilter filter, GLint& minFilter, GLint&
 }
 
 //-----------------------------------------------------------------------------
-inline GLenum GL::GetFogMode(FogMode mode)
+inline GLenum GL::fog_mode(FogMode mode)
 {
 	assert(mode < FM_COUNT);
 
@@ -136,7 +132,7 @@ inline GLenum GL::GetFogMode(FogMode mode)
 }
 
 //-----------------------------------------------------------------------------
-inline GLenum GL::GetPolygonMode(PolygonMode mode)
+inline GLenum GL::polygon_mode(PolygonMode mode)
 {
 	assert(mode < PM_COUNT);
 
@@ -144,7 +140,7 @@ inline GLenum GL::GetPolygonMode(PolygonMode mode)
 }
 
 //-----------------------------------------------------------------------------
-inline GLenum GL::GetPixelFormat(PixelFormat format)
+inline GLenum GL::pixel_format(PixelFormat format)
 {
 	switch (format)
 	{
@@ -162,7 +158,7 @@ inline GLenum GL::GetPixelFormat(PixelFormat format)
 }
 
 //-----------------------------------------------------------------------------
-inline PixelFormat GL::GetPixelFormatFromGLFormat(GLenum format)
+inline PixelFormat GL::pixel_format_from_gl_format(GLenum format)
 {
 	switch (format)
 	{

+ 1 - 1
tools/CMakeLists.txt

@@ -10,7 +10,7 @@ link_directories(${CROWN_BINARY_DIR} ${GTKMM_LIBRARY_DIRS})
 include_directories(${INCLUDES} ${GTKMM_INCLUDE_DIRS})
 
 add_subdirectory(compilers)
-add_subdirectory(editors/world-editor)
+#add_subdirectory(editors/world-editor)
 add_subdirectory(editors/resource-browser)
 add_subdirectory(pycrown)
 

+ 21 - 5
tools/compilers/Compiler.cpp

@@ -23,17 +23,19 @@ FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
 OTHER DEALINGS IN THE SOFTWARE.
 */
 
+#include <cstring>
+#include <cstdlib>
 #include "Compiler.h"
 #include "Hash.h"
 #include "Path.h"
 #include "FileStream.h"
-#include <cstring>
+#include "Log.h"
 
 namespace crown
 {
 
 //-----------------------------------------------------------------------------
-Compiler::Compiler(const char* root_path, const char* dest_path, const char* resource, uint32_t seed) :
+Compiler::Compiler(const char* root_path, const char* dest_path, const char* resource, uint32_t type_expected, uint32_t seed) :
 	m_name_hash(0),
 	m_type_hash(0),
 	m_seed(seed),
@@ -64,17 +66,31 @@ Compiler::Compiler(const char* root_path, const char* dest_path, const char* res
 	path::filename_without_extension(m_resource, m_name, MAX_RESOURCE_NAME_LENGTH);
 	path::extension(m_resource, m_type, MAX_RESOURCE_TYPE_LENGTH);
 
-	// Compute hashes
+	// Compute the resource hashes
 	m_name_hash = hash::murmur2_32(m_name, string::strlen(m_name), m_seed);
-	m_type_hash = hash::murmur2_32(m_type, string::strlen(m_type), m_seed);
+
+	// NOTE: The type hash _MUST_ be generated with seed = 0
+	m_type_hash = hash::murmur2_32(m_type, string::strlen(m_type), 0);
+
+	if (m_type_hash != type_expected)
+	{
+		Log::e("Compiler: Trying to compile '%s' with the wrong compiler. Aborting.", resource_path());
+		exit(-1);
+	}
 
 	char dest_name[17];
 	memset(dest_name, 0, 17);
 
-	snprintf(dest_name, 17, "%X%X", m_name_hash, m_type_hash);
+	snprintf(dest_name, 17, "%.8X%.8X", m_name_hash, m_type_hash);
 
 	// Open streams
 	m_src_file = (FileStream*)m_root_fs.open(m_resource, SOM_READ);
+
+	if (!m_dest_fs.exists(dest_name))
+	{
+		m_dest_fs.create_file(dest_name);
+	}
+
 	m_dest_file = (FileStream*)m_dest_fs.open(dest_name, SOM_WRITE);
 }
 

+ 7 - 4
tools/compilers/Compiler.h

@@ -54,12 +54,15 @@ class Compiler
 {
 public:
 
-						/// Looks for the @resource int the @root_path and prepares it to
-						/// compilation using @seed to generate string hashes.
-						Compiler(const char* root_path, const char* dest_path, const char* resource, uint32_t seed);
+	/// Looks for the @resource int the @root_path and prepares it to
+	/// compilation using @seed to generate hashes for the resource name.
+	/// Implementation must declare the type of resource they are expecting
+	/// to work on by setting @type_expected appropriately.
+						Compiler(const char* root_path, const char* dest_path, const char* resource,
+								 uint32_t type_expected, uint32_t seed);
 	virtual				~Compiler();
 
-						/// Actually compiles the resource.
+	/// Actually compiles the resource.
 	virtual bool		compile() = 0;
 
 	virtual void		write() = 0;

+ 2 - 1
tools/compilers/lua/LuaCompiler.cpp

@@ -1,12 +1,13 @@
 #include "LuaCompiler.h"
 #include "FileStream.h"
+#include "Resource.h"
 
 namespace crown
 {
 
 //-----------------------------------------------------------------------------
 LuaCompiler::LuaCompiler(const char* root_path, const char* dest_path, const char* resource, uint32_t seed) :
-	Compiler(root_path, dest_path, resource, seed),
+	Compiler(root_path, dest_path, resource, SCRIPT_TYPE, seed),
 	m_file_size(0),
 	m_file_data(NULL)
 {

+ 1 - 1
tools/compilers/mat/MATCompiler.cpp

@@ -31,7 +31,7 @@ namespace crown
 
 //-----------------------------------------------------------------------------
 MATCompiler::MATCompiler(const char* root_path, const char* dest_path, const char* resource, uint32_t seed) :
-	Compiler(root_path, dest_path, resource, seed)
+	Compiler(root_path, dest_path, resource, MATERIAL_TYPE, seed)
 {
 }
 

+ 1 - 0
tools/compilers/mat/MATCompiler.h

@@ -27,6 +27,7 @@ OTHER DEALINGS IN THE SOFTWARE.
 
 #include "Compiler.h"
 #include "FileStream.h"
+#include "Resource.h"
 
 namespace crown
 {

+ 12 - 6
tools/compilers/resource-hash.cpp

@@ -29,17 +29,23 @@ int main(int argc, char** argv)
 	path::extension(resource_in, resource_extension, 256);
 	
 	uint32_t resource_basename_hash = hash::murmur2_32(resource_basename, string::strlen(resource_basename), hash_seed);
-	uint32_t resource_extension_hash = hash::murmur2_32(resource_extension, string::strlen(resource_extension), hash_seed);
+	uint32_t resource_extension_hash = hash::murmur2_32(resource_extension, string::strlen(resource_extension), 0);
+
+	if (resource_extension_hash != TEXTURE_TYPE &&
+		resource_extension_hash != MESH_TYPE &&
+		resource_extension_hash != SCRIPT_TYPE &&
+		resource_extension_hash != TEXT_TYPE &&
+		resource_extension_hash != MATERIAL_TYPE)
+	{
+		printf("%s: ERROR: cannot generate hash for resource '%s': Unknown type.\n", argv[0], resource_in);
+		exit(-1);
+	}
 
 	char out_filename[512];
 	out_filename[0] = '\0';
 
-	snprintf(resource_basename, 256, "%X", resource_basename_hash);
-	snprintf(resource_extension, 256, "%X", resource_extension_hash);
+	snprintf(out_filename, 256, "%.8X%.8X", resource_basename_hash, resource_extension_hash);
 	
-	string::strncat(out_filename, resource_basename, 512);
-	string::strncat(out_filename, resource_extension, 512);
-
 	printf("%s\n", out_filename);
 
 	return 0;

+ 2 - 1
tools/compilers/tga/TGACompiler.cpp

@@ -26,13 +26,14 @@ OTHER DEALINGS IN THE SOFTWARE.
 #include "TGACompiler.h"
 #include "FileStream.h"
 #include "Pixel.h"
+#include "Resource.h"
 
 namespace crown
 {
 
 //-----------------------------------------------------------------------------
 TGACompiler::TGACompiler(const char* root_path, const char* dest_path, const char* resource, uint32_t seed) :
-	Compiler(root_path, dest_path, resource, seed),
+	Compiler(root_path, dest_path, resource, TEXTURE_TYPE, seed),
 	m_image_format(PF_UNKNOWN),
 	m_image_channels(0),
 	m_image_size(0),

+ 2 - 1
tools/compilers/txt/TXTCompiler.cpp

@@ -25,13 +25,14 @@ OTHER DEALINGS IN THE SOFTWARE.
 
 #include "TXTCompiler.h"
 #include "FileStream.h"
+#include "Resource.h"
 
 namespace crown
 {
 
 //-----------------------------------------------------------------------------
 TXTCompiler::TXTCompiler(const char* root_path, const char* dest_path, const char* resource, uint32_t seed) :
-	Compiler(root_path, dest_path, resource, seed),
+	Compiler(root_path, dest_path, resource, TEXT_TYPE, seed),
 	m_file_size(0),
 	m_file_data(NULL)
 {

+ 40 - 4
tools/pycrown/Compiler.py

@@ -79,13 +79,47 @@ class Compiler:
 			resource_hashes.clear()
 			seed = seed + 1;
 
+	# Compiles all the texture resources in the repository
+	def compile_textures(self):
+		textures = self.m_repository.texture_resources();
+
+		for res in textures:
+			self.compile(res)
+
+	# Compiles all the mesh resources in the repository
+	def compile_meshes(self):
+		meshes = self.m_repository.mesh_resources();
+
+		for res in meshes:
+			self.compile(res)
+
+	# Compiles all the text resources in the repository
+	def compile_texts(self):
+		texts = self.m_repository.text_resources();
+
+		for res in texts:
+			self.compile(res)
+
+	# Compiles all the script resources in the repository
+	def compile_scripts(self):
+		scripts = self.m_repository.script_resources();
+
+		for res in scripts:
+			self.compile(res)
+
 	# Compiles all the resources in the repository
 	def compile_all(self):
-		# Obtain resources from repository
-		resources = self.m_repository.all_resources()
+		print("Compiling textures...")
+		self.compile_textures()
 
-		for res in resources:
-			self.compile(res)
+		print("Compiling meshes...")
+		self.compile_meshes()
+
+		print("Compiling texts...")
+		self.compile_texts()
+
+		print("Compiling scripts...")
+		self.compile_scripts()
 
 	# Compile a single resource from the repository
 	def compile(self, resource):
@@ -95,6 +129,8 @@ class Compiler:
 
 		root_path = self.m_repository.root_path()
 
+		print(resource + " => ???")
+
 		# Call appropriate compiler based on resource extension
 		if resource.endswith('.txt'):
 			p = subprocess.call([TXT_C, ROOT_P, root_path, DEST_P, self.m_dest_path, RES_IN, resource, SEED, str(self.m_perfect_seed)]);

+ 8 - 8
tools/pycrown/Repository.py

@@ -50,7 +50,7 @@ class Repository:
 	def texture_resources(self):
 		textures = []
 
-		for res in resources:
+		for res in self.m_resources:
 			if (res.endswith(TEXTURE_EXTENSION)):
 				textures.append(res)
 
@@ -60,7 +60,7 @@ class Repository:
 	def text_resources(self):
 		texts = []
 
-		for res in resources:
+		for res in self.m_resources:
 			if (res.endswith(TEXT_EXTENSION)):
 				texts.append(res)
 
@@ -70,21 +70,21 @@ class Repository:
 	def mesh_resources(self):
 		meshes = []
 
-		for res in resources:
+		for res in self.m_resources:
 			if (res.endswith(MESH_EXTENSION)):
 				meshes.append(res)
 
 		return meshes
 
 	# Returns a list of all the lua resources found
-	def lua_resources(self):
-		luas = []
+	def script_resources(self):
+		scripts = []
 
-		for res in resources:
+		for res in self.m_resources:
 			if (res.endswith(LUA_EXTENSION)):
-				luas.append(res)
+				scripts.append(res)
 
-		return luas
+		return scripts
 
 	# Scans the root path to find resources
 	def scan(self):