Daniele Bartolini 12 lat temu
rodzic
commit
5f3614ffcd

+ 3 - 1
engine/CMakeLists.txt

@@ -282,6 +282,7 @@ set (RENDERERS_SRC
 	renderers/Mesh.cpp
 	renderers/Sprite.cpp
 	renderers/Material.cpp
+	renderers/DebugLine.cpp
 )
 
 set (RENDERERS_HEADERS
@@ -290,9 +291,9 @@ set (RENDERERS_HEADERS
 	renderers/Mesh.h
 	renderers/Sprite.h
 	renderers/Material.h
+	renderers/DebugLine.h
 )
 
-
 set (RESOURCE_SRC
 	resource/ResourceLoader.cpp
 	resource/ResourceManager.cpp
@@ -355,6 +356,7 @@ set (LUA_SRC
 	lua/LuaActor.cpp
 	lua/LuaCamera.cpp
 	lua/LuaController.cpp
+	lua/LuaDebugLine.cpp
 	lua/LuaDevice.cpp
 	lua/LuaEnvironment.cpp
 	lua/LuaFloatSetting.cpp

+ 2 - 0
engine/Config.h.in

@@ -62,3 +62,5 @@ OTHER DEALINGS IN THE SOFTWARE.
 #define CE_MAX_GUI_TRIANGLES 				64					// Per Gui
 #define CE_MAX_GUI_IMAGES 					64					// Per Gui
 #define CE_MAX_GUI_TEXTS 					64					// Per Gui
+
+#define CE_MAX_DEBUG_LINES					2 * 1024			// Per DebugLine

+ 91 - 0
engine/lua/LuaDebugLine.cpp

@@ -0,0 +1,91 @@
+/*
+Copyright (c) 2013 Daniele Bartolini, Michele Rossi
+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.
+*/
+
+#include "LuaStack.h"
+#include "LuaEnvironment.h"
+#include "DebugLine.h"
+#include "Vector3.h"
+#include "Color4.h"
+
+namespace crown
+{
+
+//-----------------------------------------------------------------------------
+CE_EXPORT int debug_line_add_line(lua_State* L)
+{
+	LuaStack stack(L);
+
+	DebugLine* line = stack.get_debug_line(1);
+	const Vector3& start = stack.get_vector3(2);
+	const Vector3& end = stack.get_vector3(3);
+
+	line->add_line(Color4::RED, start, end);
+	return 0;
+}
+
+//-----------------------------------------------------------------------------
+CE_EXPORT int debug_line_add_sphere(lua_State* L)
+{
+	LuaStack stack(L);
+
+	DebugLine* line = stack.get_debug_line(1);
+	const Vector3& center = stack.get_vector3(2);
+	const float radius = stack.get_float(3);
+
+	line->add_sphere(Color4::RED, center, radius);
+	return 0;
+}
+
+//-----------------------------------------------------------------------------
+CE_EXPORT int debug_line_clear(lua_State* L)
+{
+	LuaStack stack(L);
+
+	DebugLine* line = stack.get_debug_line(1);
+	line->clear();
+	return 0;
+}
+
+//-----------------------------------------------------------------------------
+CE_EXPORT int debug_line_commit(lua_State* L)
+{
+	LuaStack stack(L);
+
+	DebugLine* line = stack.get_debug_line(1);
+	line->commit();
+	return 0;
+}
+
+//-----------------------------------------------------------------------------
+void load_debug_line(LuaEnvironment& env)
+{
+	env.load_module_function("DebugLine", "add_line",    debug_line_add_line);
+	env.load_module_function("DebugLine", "add_sphere",  debug_line_add_sphere);
+	env.load_module_function("DebugLine", "clear",       debug_line_clear);
+	env.load_module_function("DebugLine", "commit",      debug_line_commit);
+}
+
+} // namespace crown

+ 2 - 0
engine/lua/LuaEnvironment.cpp

@@ -86,6 +86,8 @@ CE_EXPORT int luaopen_libcrown(lua_State* /*L*/)
 
 	load_gui(*env);
 
+	load_debug_line(*env);
+
 	return 1;
 }
 

+ 15 - 15
engine/lua/LuaEnvironment.h

@@ -46,51 +46,50 @@ class LuaEnvironment
 {
 
 public:
-	/// Constructor
-							LuaEnvironment();
+
+	LuaEnvironment();
+	
 	/// Init Lua state and open libraries. Must be called first
-	void					init();
+	void init();
 	/// Close Lua state and shutdown LuaEnvironment
-	void					shutdown();
+	void shutdown();
 
 	/// Loads and execute the given @a res_name Lua resource, returns
 	/// true if success, false otherwise.
-	bool					load_and_execute(const char* res_name);
+	bool load_and_execute(const char* res_name);
 
-	bool					execute_string(const char* s);
+	bool execute_string(const char* s);
 
 	/// Load a function which will be used in Lua. @a module is the name of table contenitor,
 	/// @a name is the name of function in module and @func is the pointer to the function.
 	/// _func_ must be a C/lua function (__int32_t function_name(lua_State* L)__)
-	void					load_module_function(const char* module, const char* name, const lua_CFunction func);
+	void load_module_function(const char* module, const char* name, const lua_CFunction func);
 
 	/// Load a enum's value which will be used in Lua. 
 	/// @a module is the name of table contenitor, generally take  enum's name
 	/// @a name is module's name that refears _value_ and @value is an unsigned integer
-	void					load_module_enum(const char* module, const char* name, uint32_t value);
+	void load_module_enum(const char* module, const char* name, uint32_t value);
 
 	/// Calls the global function @a func with @a argc argument number.
 	/// Each argument is a pair (type, value).
 	/// Example call:
 	/// call_global("myfunc", 1, ARGUMENT_FLOAT, 3.14f)
 	/// Returns true if success, false otherwise
-	bool					call_global(const char* func, uint8_t argc, ...);
+	bool call_global(const char* func, uint8_t argc, ...);
 
-	void					error();
+	void error();
 
 private:
 
 	// Disable copying
-							LuaEnvironment(const LuaEnvironment&);
-	LuaEnvironment& 		operator=(const LuaEnvironment&);
+	LuaEnvironment(const LuaEnvironment&);
+	LuaEnvironment& operator=(const LuaEnvironment&);
 
 private:
 
-	lua_State*				m_state;
-
+	lua_State* m_state;
 };
 
-
 void load_accelerometer(LuaEnvironment& env);
 void load_actor(LuaEnvironment& env);
 void load_camera(LuaEnvironment& env);
@@ -116,6 +115,7 @@ void load_vector2(LuaEnvironment& env);
 void load_vector3(LuaEnvironment& env);
 void load_window(LuaEnvironment& env);
 void load_world(LuaEnvironment& env);
+void load_debug_line(LuaEnvironment& env);
 
 CE_EXPORT int32_t luaopen_libcrown(lua_State* L);
 

+ 12 - 0
engine/lua/LuaStack.h

@@ -48,6 +48,7 @@ struct Sprite;
 struct Unit;
 struct Vector2;
 struct Vector3;
+struct DebugLine;
 
 typedef Id SoundInstanceId;
 typedef Id GuiId;
@@ -369,6 +370,17 @@ public:
 		return id;	
 	}
 
+	//-----------------------------------------------------------------------------
+	void push_debug_line(DebugLine* line)
+	{
+		lua_pushlightuserdata(m_state, line);
+	}
+
+	//-----------------------------------------------------------------------------
+	DebugLine* get_debug_line(int32_t index)
+	{
+		return (DebugLine*) lua_touserdata(m_state, index);
+	}
 
 	bool is_vector2(int32_t index);
 	bool is_vector3(int32_t index);

+ 27 - 0
engine/lua/LuaWorld.cpp

@@ -228,6 +228,30 @@ CE_EXPORT int world_sound_world(lua_State* L)
 	return 1;
 }
 
+//-----------------------------------------------------------------------------
+CE_EXPORT int world_create_debug_line(lua_State* L)
+{
+	LuaStack stack(L);
+
+	World* world = stack.get_world(1);
+	const bool depth_test = stack.get_bool(2);
+
+	stack.push_debug_line(world->create_debug_line(depth_test));
+	return 1;
+}
+
+//-----------------------------------------------------------------------------
+CE_EXPORT int world_destroy_debug_line(lua_State* L)
+{
+	LuaStack stack(L);
+
+	World* world = stack.get_world(1);
+	DebugLine* line = stack.get_debug_line(2);
+
+	world->destroy_debug_line(line);
+	return 0;
+}
+
 //-----------------------------------------------------------------------------
 void load_world(LuaEnvironment& env)
 {
@@ -249,6 +273,9 @@ void load_world(LuaEnvironment& env)
 
 	env.load_module_function("World", "physics_world",		world_physics_world);
 	env.load_module_function("World", "sound_world",        world_sound_world);
+
+	env.load_module_function("World", "create_debug_line",  world_create_debug_line);
+	env.load_module_function("World", "destroy_debug_line", world_destroy_debug_line);
 }
 
 } // namespace crown

+ 132 - 0
engine/renderers/DebugLine.cpp

@@ -0,0 +1,132 @@
+/*
+Copyright (c) 2013 Daniele Bartolini, Michele Rossi
+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.
+*/
+
+#include "DebugLine.h"
+#include "MathUtils.h"
+#include "Color4.h"
+#include "Vector3.h"
+#include "Device.h"
+#include "Renderer.h"
+
+namespace crown
+{
+
+typedef Id GPUProgramId;
+extern GPUProgramId default_program;
+
+//-----------------------------------------------------------------------------
+DebugLine::DebugLine(bool depth_test)
+	: m_depth_test(depth_test)
+	, m_num_lines(0)
+{
+}
+
+//-----------------------------------------------------------------------------
+void DebugLine::add_line(const Color4& color, const Vector3& start, const Vector3& end)
+{
+	if (m_num_lines >= CE_MAX_DEBUG_LINES)
+	{
+		 return;
+	}
+
+	m_lines[m_num_lines].position_0[0] = start.x;
+	m_lines[m_num_lines].position_0[1] = start.y;
+	m_lines[m_num_lines].position_0[2] = start.z;
+	m_lines[m_num_lines].color_0[0] = color.r;
+	m_lines[m_num_lines].color_0[1] = color.g;
+	m_lines[m_num_lines].color_0[2] = color.b;
+	m_lines[m_num_lines].color_0[3] = color.a;
+	m_lines[m_num_lines].position_1[0] = end.x;
+	m_lines[m_num_lines].position_1[1] = end.y;
+	m_lines[m_num_lines].position_1[2] = end.z;
+	m_lines[m_num_lines].color_1[0] = color.r;
+	m_lines[m_num_lines].color_1[1] = color.g;
+	m_lines[m_num_lines].color_1[2] = color.b;
+	m_lines[m_num_lines].color_1[3] = color.a;
+
+	m_num_lines++;
+}
+
+//-----------------------------------------------------------------------------
+void DebugLine::add_sphere(const Color4& color, const Vector3& center, const float radius)
+{
+	const uint32_t deg_step = 15;
+
+	for (uint32_t deg = 0; deg < 360; deg += deg_step)
+	{
+		const float rad0 = math::deg_to_rad(deg);
+		const float rad1 = math::deg_to_rad(deg + deg_step);
+
+		// XZ plane
+		const Vector3 start0(math::cos(rad0) * radius, 0, -math::sin(rad0) * radius);
+		const Vector3 end0  (math::cos(rad1) * radius, 0, -math::sin(rad1) * radius);
+		add_line(color, center + start0, center + end0);
+
+		// XY plane
+		const Vector3 start1(math::cos(rad0) * radius, math::sin(rad0) * radius, 0);
+		const Vector3 end1  (math::cos(rad1) * radius, math::sin(rad1) * radius, 0);
+		add_line(color, center + start1, center + end1);
+
+		// YZ plane
+		const Vector3 start2(0, math::sin(rad0) * radius, -math::cos(rad0) * radius);
+		const Vector3 end2  (0, math::sin(rad1) * radius, -math::cos(rad1) * radius);
+		add_line(color, center + start2, center + end2);
+	}
+}
+
+//-----------------------------------------------------------------------------
+void DebugLine::clear()
+{
+	m_num_lines = 0;
+}
+
+//-----------------------------------------------------------------------------
+void DebugLine::commit()
+{
+	Renderer* r = device()->renderer();
+
+	TransientVertexBuffer tvb;
+	TransientIndexBuffer tib;
+	r->reserve_transient_vertex_buffer(&tvb, m_num_lines * 2, VertexFormat::P3_C4);
+	r->reserve_transient_index_buffer(&tib, m_num_lines * 2);
+
+	memcpy(tvb.data, m_lines, sizeof(Line) * m_num_lines);
+
+	uint16_t* indices = (uint16_t*) tib.data;
+	for (uint32_t i = 0; i < m_num_lines * 2; i++)
+	{
+		indices[i] = i;
+	}
+
+	r->set_state((m_depth_test ? 0 : STATE_DEPTH_TEST_ALWAYS) | STATE_COLOR_WRITE | STATE_CULL_CW | STATE_PRIMITIVE_LINES);
+	r->set_vertex_buffer(tvb);
+	r->set_index_buffer(tib);
+	r->set_program(default_program);
+	r->set_pose(Matrix4x4::IDENTITY);
+	r->commit(0);
+}
+
+} // namespace crown

+ 74 - 0
engine/renderers/DebugLine.h

@@ -0,0 +1,74 @@
+/*
+Copyright (c) 2013 Daniele Bartolini, Michele Rossi
+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
+
+#include "Types.h"
+#include "Config.h"
+
+namespace crown
+{
+
+struct Color4;
+struct Matrix4x4;
+struct Vector3;
+
+struct DebugLine
+{
+	/// Whether to enable @a depth_test
+	DebugLine(bool depth_test);
+
+	/// Adds a line from @start to @end with the given @a color.
+	void add_line(const Color4& color, const Vector3& start, const Vector3& end);
+
+	/// Adds a sphere at @a center with the given @a radius and @a color.
+	void add_sphere(const Color4& color, const Vector3& center, const float radius);
+
+	/// Adds a @a pose with the given @a color
+	//void add_pose(const Color4& color, const Matrix4x4& pose);
+
+	/// Clears all the lines.
+	void clear();
+
+	/// Sends the lines to renderer for drawing.
+	void commit();
+
+private:
+
+	struct Line
+	{
+		float position_0[3];
+		float color_0[4];
+		float position_1[3];
+		float color_1[4];
+	};
+
+	bool m_depth_test;
+	uint32_t m_num_lines;
+	Line m_lines[CE_MAX_DEBUG_LINES];
+};
+
+} // namespace crown

+ 13 - 0
engine/world/World.cpp

@@ -29,6 +29,7 @@ OTHER DEALINGS IN THE SOFTWARE.
 #include "Allocator.h"
 #include "Device.h"
 #include "ResourceManager.h"
+#include "DebugLine.h"
 
 namespace crown
 {
@@ -258,6 +259,18 @@ Gui* World::lookup_gui(GuiId id)
 	return m_render_world.lookup_gui(id);
 }
 
+//-----------------------------------------------------------------------------
+DebugLine* World::create_debug_line(bool depth_test)
+{
+	return CE_NEW(default_allocator(), DebugLine)(depth_test);
+}
+
+//-----------------------------------------------------------------------------
+void World::destroy_debug_line(DebugLine* line)
+{
+	CE_DELETE(default_allocator(), line);
+}
+
 //-----------------------------------------------------------------------------
 SceneGraphManager* World::scene_graph_manager()
 {

+ 6 - 2
engine/world/World.h

@@ -51,6 +51,7 @@ struct Actor;
 struct Vector3;
 struct Quaternion;
 struct PhysicsResource;
+struct DebugLine;
 
 class World
 {
@@ -93,6 +94,9 @@ public:
 	void								destroy_gui(GuiId id);
 	Gui*								lookup_gui(GuiId id);
 
+	DebugLine*							create_debug_line(bool depth_test);
+	void								destroy_debug_line(DebugLine* line);
+
 	SceneGraphManager*					scene_graph_manager();
 	RenderWorld*						render_world();
 	PhysicsWorld*						physics_world();
@@ -103,8 +107,8 @@ private:
 	PoolAllocator						m_unit_pool;
 	PoolAllocator						m_camera_pool;
 
-	IdArray<CE_MAX_UNITS, Unit*>			m_units;
-	IdArray<CE_MAX_CAMERAS, Camera*>		m_cameras;
+	IdArray<CE_MAX_UNITS, Unit*>		m_units;
+	IdArray<CE_MAX_CAMERAS, Camera*>	m_cameras;
 
 	SceneGraphManager					m_scenegraph_manager;
 	RenderWorld							m_render_world;