Prechádzať zdrojové kódy

Add display_modes() and set_display_mode(). Windows implementation missing.

Daniele Bartolini 11 rokov pred
rodič
commit
19550c2bae

+ 88 - 66
engine/Device.h

@@ -53,150 +53,172 @@ class World;
 class WorldManager;
 class WorldManager;
 struct Camera;
 struct Camera;
 
 
+/// @defgroup Device Device.
+
+/// Holds data for a display mode.
+///
+/// @ingroup Device
+struct DisplayMode
+{
+	uint32_t id;
+	uint16_t width;
+	uint16_t height;
+};
+
 /// This is the place where to look for accessing all of
 /// This is the place where to look for accessing all of
 /// the engine subsystems and related stuff.
 /// the engine subsystems and related stuff.
+///
+/// @ingroup Device
 class CE_EXPORT Device
 class CE_EXPORT Device
 {
 {
 public:
 public:
 
 
-							Device();
-							~Device();
+	Device();
+	~Device();
 
 
-	void					init();
+	void init();
 
 
 	/// Shutdowns the engine freeing all the allocated resources
 	/// Shutdowns the engine freeing all the allocated resources
-	void					shutdown();
+	void shutdown();
 
 
 	/// Returns the number of command line arguments passed to
 	/// Returns the number of command line arguments passed to
 	/// the engine executable.
 	/// the engine executable.
-	int32_t					argc() const { return m_argc; }
+	int32_t argc() const { return m_argc; }
 
 
 	/// Returns the string value of the command line arguments passed
 	/// Returns the string value of the command line arguments passed
 	/// to the engine executable.
 	/// to the engine executable.
 	/// The size of the returned array is given by Device::argc().
 	/// The size of the returned array is given by Device::argc().
-	const char**			argv() const { return (const char**) m_argv; }
+	const char** argv() const { return (const char**) m_argv; }
 
 
 	/// Returns wheter the engine is running (i.e. it is actually
 	/// Returns wheter the engine is running (i.e. it is actually
 	/// doing work).
 	/// doing work).
-	bool					is_running() const;
+	bool is_running() const;
 
 
 	/// Returns whether the engine is correctly initialized
 	/// Returns whether the engine is correctly initialized
-	bool					is_init() const;
+	bool is_init() const;
 
 
 	/// Returns wheter the engine is paused
 	/// Returns wheter the engine is paused
-	bool 					is_paused() const;
+	bool is_paused() const;
 
 
 	/// Return the number of frames rendered from the first
 	/// Return the number of frames rendered from the first
 	/// call to Device::start()
 	/// call to Device::start()
-	uint64_t				frame_count() const;
+	uint64_t frame_count() const;
 
 
 	/// Returns the time in seconds needed to render the last frame
 	/// Returns the time in seconds needed to render the last frame
-	float					last_delta_time() const;
+	float last_delta_time() const;
 
 
 	/// Returns the time in seconds since the first call to start().
 	/// Returns the time in seconds since the first call to start().
-	double					time_since_start() const;
+	double time_since_start() const;
 
 
 	/// Forces the engine to actually start doing work.
 	/// Forces the engine to actually start doing work.
-	void					start();
+	void start();
 
 
 	/// Forces the engine to stop all the work it is doing
 	/// Forces the engine to stop all the work it is doing
 	/// and normally terminates the program.
 	/// and normally terminates the program.
-	void					stop();
+	void stop();
 
 
 	/// Pauses the engine
 	/// Pauses the engine
-	void					pause();
+	void pause();
 
 
 	/// Unpauses the engine
 	/// Unpauses the engine
-	void					unpause();
+	void unpause();
+
+	virtual int32_t run(int argc, char** argv) = 0;
+
+	/// Returns an array of video @a modes.
+	/// Each DisplayMode has an id that can be passed to set_video_mode().
+	virtual void display_modes(Array<DisplayMode>& modes) = 0;
 
 
-	virtual int32_t			run(int argc, char** argv) = 0;
+	/// Sets the video mode @a id.
+	/// @note See video_modes().
+	virtual void set_display_mode(uint32_t id) = 0;
 
 
 	/// Updates all the subsystems
 	/// Updates all the subsystems
-	void					frame();
+	void frame();
 
 
 	/// Updates the given @a world and renders it from the given @a camera.
 	/// Updates the given @a world and renders it from the given @a camera.
-	void					update_world(World* world, float dt);
+	void update_world(World* world, float dt);
 
 
 	/// Renders the given @a world from the point of view of the given @æ camera.
 	/// Renders the given @a world from the point of view of the given @æ camera.
-	void					render_world(World* world, Camera* camera);
+	void render_world(World* world, Camera* camera);
 
 
-	WorldId					create_world();
-	void					destroy_world(WorldId world);
+	WorldId create_world();
+	void destroy_world(WorldId world);
 
 
 	/// Returns the resource package with the given @a package_name name.
 	/// Returns the resource package with the given @a package_name name.
-	ResourcePackage*		create_resource_package(const char* name);
+	ResourcePackage* create_resource_package(const char* name);
 
 
 	/// Destroy a previously created resource @a package.
 	/// Destroy a previously created resource @a package.
 	/// @note
 	/// @note
 	/// To unload the resources loaded by the package, you have to call
 	/// To unload the resources loaded by the package, you have to call
 	/// ResourcePackage::unload() first.
 	/// ResourcePackage::unload() first.
-	void					destroy_resource_package(ResourcePackage* package);
+	void destroy_resource_package(ResourcePackage* package);
 
 
-	void					compile(const char* bundle_dir, const char* source_dir, const char* resource);
+	void compile(const char* bundle_dir, const char* source_dir, const char* resource);
 
 
-	void					reload(const char* type, const char* name);
+	void reload(const char* type, const char* name);
 
 
-	Filesystem*				filesystem();
-	ResourceManager*		resource_manager();
-	LuaEnvironment*			lua_environment();
+	Filesystem* filesystem();
+	ResourceManager* resource_manager();
+	LuaEnvironment* lua_environment();
 
 
-	OsWindow*				window();
-	Renderer*				renderer();
+	OsWindow* window();
+	Renderer* renderer();
 
 
-	Keyboard*				keyboard();
-	Mouse*					mouse();
-	Touch*					touch();
-	Accelerometer*			accelerometer();
-	ConsoleServer*			console() { return m_console; }
-	WorldManager*			world_manager() { return m_world_manager; }
+	Keyboard* keyboard();
+	Mouse* mouse();
+	Touch* touch();
+	Accelerometer* accelerometer();
+	ConsoleServer* console() { return m_console; }
+	WorldManager* world_manager() { return m_world_manager; }
 
 
 protected:
 protected:
 
 
 	// Used to allocate all subsystems
 	// Used to allocate all subsystems
-	LinearAllocator			m_allocator;
+	LinearAllocator m_allocator;
 
 
-	int32_t					m_argc;
-	char**					m_argv;
+	int32_t m_argc;
+	char** m_argv;
 
 
 	// Preferred settings
 	// Preferred settings
-	char					m_source_dir[MAX_PATH_LENGTH];
-	char 					m_bundle_dir[MAX_PATH_LENGTH];
-	char 					m_boot_file[MAX_PATH_LENGTH];
-	int32_t					m_fileserver;
-	uint16_t				m_console_port;
+	char m_source_dir[MAX_PATH_LENGTH];
+	char m_bundle_dir[MAX_PATH_LENGTH];
+	char m_boot_file[MAX_PATH_LENGTH];
+	int32_t m_fileserver;
+	uint16_t m_console_port;
 
 
-	bool					m_is_init		: 1;
-	bool					m_is_running	: 1;
-	bool					m_is_paused		: 1;
+	bool m_is_init		: 1;
+	bool m_is_running	: 1;
+	bool m_is_paused	: 1;
 
 
-	uint64_t				m_frame_count;
+	uint64_t m_frame_count;
 
 
-	uint64_t				m_last_time;
-	uint64_t				m_current_time;
-	float					m_last_delta_time;
-	double					m_time_since_start;
+	uint64_t m_last_time;
+	uint64_t m_current_time;
+	float m_last_delta_time;
+	double m_time_since_start;
 
 
 	// Public subsystems
 	// Public subsystems
-	Filesystem*				m_filesystem;
+	Filesystem* m_filesystem;
 
 
-	OsWindow*				m_window;
+	OsWindow* m_window;
 
 
-	Keyboard*				m_keyboard;
-	Mouse*					m_mouse;
-	Touch*					m_touch;
+	Keyboard* m_keyboard;
+	Mouse* m_mouse;
+	Touch* m_touch;
 
 
-	LuaEnvironment*			m_lua_environment;
-	Renderer*				m_renderer;
+	LuaEnvironment* m_lua_environment;
+	Renderer* m_renderer;
 
 
 	// Private subsystems
 	// Private subsystems
-	BundleCompiler*			m_bundle_compiler;
-	ConsoleServer*			m_console;
-	ResourceManager*		m_resource_manager;
-	Bundle*					m_resource_bundle;
-	WorldManager*			m_world_manager;
+	BundleCompiler* m_bundle_compiler;
+	ConsoleServer* m_console;
+	ResourceManager* m_resource_manager;
+	Bundle* m_resource_bundle;
+	WorldManager* m_world_manager;
 
 
 	// Configuration resources
 	// Configuration resources
-	ResourceId				m_physics_config;
+	ResourceId m_physics_config;
 
 
 private:
 private:
 
 

+ 37 - 0
engine/lua/LuaDevice.cpp

@@ -30,6 +30,8 @@ OTHER DEALINGS IN THE SOFTWARE.
 #include "WorldManager.h"
 #include "WorldManager.h"
 #include "LuaEnvironment.h"
 #include "LuaEnvironment.h"
 #include "LuaStack.h"
 #include "LuaStack.h"
+#include "TempAllocator.h"
+#include "Array.h"
 
 
 namespace crown
 namespace crown
 {
 {
@@ -157,6 +159,39 @@ static int device_destroy_resource_package(lua_State* L)
 	return 0;
 	return 0;
 }
 }
 
 
+//-----------------------------------------------------------------------------
+static int device_display_modes(lua_State* L)
+{
+	LuaStack stack(L);
+
+	TempAllocator512 alloc;
+	Array<DisplayMode> modes(alloc);
+
+	device()->display_modes(modes);
+
+	stack.push_table();
+	for (uint32_t i = 0; i < array::size(modes); i++)
+	{
+		stack.push_key_begin((int32_t) i + 1);
+		stack.push_table();
+		stack.push_key_begin("id"); stack.push_uint32(modes[i].id); stack.push_key_end();
+		stack.push_key_begin("width"); stack.push_uint32(modes[i].width); stack.push_key_end();
+		stack.push_key_begin("height"); stack.push_uint32(modes[i].height); stack.push_key_end();
+		stack.push_key_end();
+	}
+
+	return 1;
+}
+
+//-----------------------------------------------------------------------------
+static int device_set_display_mode(lua_State* L)
+{
+	LuaStack stack(L);
+	device()->set_display_mode(stack.get_int(1));
+	return 0;
+}
+
+
 //-----------------------------------------------------------------------------
 //-----------------------------------------------------------------------------
 void load_device(LuaEnvironment& env)
 void load_device(LuaEnvironment& env)
 {
 {
@@ -171,6 +206,8 @@ void load_device(LuaEnvironment& env)
 	env.load_module_function("Device", "render_world",             device_render_world);
 	env.load_module_function("Device", "render_world",             device_render_world);
 	env.load_module_function("Device", "create_resource_package",  device_create_resource_package);
 	env.load_module_function("Device", "create_resource_package",  device_create_resource_package);
 	env.load_module_function("Device", "destroy_resource_package", device_destroy_resource_package);
 	env.load_module_function("Device", "destroy_resource_package", device_destroy_resource_package);
+	env.load_module_function("Device", "display_modes",            device_display_modes);
+	env.load_module_function("Device", "set_display_mode",         device_set_display_mode);
 }
 }
 
 
 } // namespace crown
 } // namespace crown

+ 12 - 0
engine/os/android/AndroidDevice.cpp

@@ -49,6 +49,18 @@ public:
 		#endif
 		#endif
 	}
 	}
 
 
+	//-----------------------------------------------------------------------------
+	void display_modes(Array<DisplayMode>& /*modes*/)
+	{
+		// Do nothing
+	}
+
+	//-----------------------------------------------------------------------------
+	void set_display_mode(uint32_t /*id*/)
+	{
+		// Do nothing
+	}
+
 	//-----------------------------------------------------------------------------
 	//-----------------------------------------------------------------------------
 	int32_t run(int, char**)
 	int32_t run(int, char**)
 	{
 	{

+ 60 - 0
engine/os/linux/main.cpp

@@ -28,6 +28,7 @@ OTHER DEALINGS IN THE SOFTWARE.
 #include <X11/Xatom.h>
 #include <X11/Xatom.h>
 #include <X11/Xlib.h>
 #include <X11/Xlib.h>
 #include <X11/XKBlib.h>
 #include <X11/XKBlib.h>
+#include <X11/extensions/Xrandr.h>
 #include "Config.h"
 #include "Config.h"
 #include "Crown.h"
 #include "Crown.h"
 #include "Device.h"
 #include "Device.h"
@@ -128,6 +129,7 @@ public:
 		, m_x11_window(None)
 		, m_x11_window(None)
 		, m_x11_parent_window(None)
 		, m_x11_parent_window(None)
 		, m_x11_hidden_cursor(None)
 		, m_x11_hidden_cursor(None)
+		, m_screen_config(NULL)
 		, m_exit(false)
 		, m_exit(false)
 		, m_x(0)
 		, m_x(0)
 		, m_y(0)
 		, m_y(0)
@@ -186,6 +188,41 @@ public:
 		#endif
 		#endif
 	}
 	}
 
 
+	//-----------------------------------------------------------------------------
+	void display_modes(Array<DisplayMode>& modes)
+	{
+		int num_rrsizes = 0;
+		XRRScreenSize* rrsizes = XRRConfigSizes(m_screen_config, &num_rrsizes);
+
+		for (int i = 0; i < num_rrsizes; i++)
+		{
+			DisplayMode dm;
+			dm.id = (uint32_t) i;
+			dm.width = rrsizes[i].width;
+			dm.height = rrsizes[i].height;
+			array::push_back(modes, dm);
+		}
+	}
+
+	//-----------------------------------------------------------------------------
+	void set_display_mode(uint32_t id)
+	{
+		// Check if id is valid
+		int num_rrsizes = 0;
+		XRRScreenSize* rrsizes = XRRConfigSizes(m_screen_config, &num_rrsizes);
+		(void) rrsizes;
+
+		if ((int) id >= num_rrsizes)
+			return;
+
+		XRRSetScreenConfig(m_x11_display,
+							m_screen_config,
+							RootWindow(m_x11_display, DefaultScreen(m_x11_display)),
+							(int) id,
+							RR_Rotate_0,
+							CurrentTime);
+	}
+
 	//-----------------------------------------------------------------------------
 	//-----------------------------------------------------------------------------
 	int32_t run(int argc, char** argv)
 	int32_t run(int argc, char** argv)
 	{
 	{
@@ -256,6 +293,12 @@ public:
 		oswindow_set_window(m_x11_display, m_x11_window);
 		oswindow_set_window(m_x11_display, m_x11_window);
 		set_x11_display_and_window(m_x11_display, m_x11_window);
 		set_x11_display_and_window(m_x11_display, m_x11_window);
 
 
+		// Get screen configuration
+		m_screen_config = XRRGetScreenInfo(m_x11_display, RootWindow(m_x11_display, screen));
+
+		Rotation rr_old_rot;
+		const SizeID rr_old_sizeid = XRRConfigCurrentConfiguration(m_screen_config, &rr_old_rot);
+
 		OsThread game_thread("game-thread");
 		OsThread game_thread("game-thread");
 		game_thread.start(main_loop, (void*)this);
 		game_thread.start(main_loop, (void*)this);
 
 
@@ -266,6 +309,21 @@ public:
 
 
 		game_thread.stop();
 		game_thread.stop();
 
 
+		// Restore previous screen configuration if changed
+		Rotation rr_cur_rot;
+		const SizeID rr_cur_sizeid = XRRConfigCurrentConfiguration(m_screen_config, &rr_cur_rot);
+
+		if (rr_cur_rot != rr_old_rot || rr_cur_sizeid != rr_old_sizeid)
+		{
+			XRRSetScreenConfig(m_x11_display,
+								m_screen_config,
+								RootWindow(m_x11_display, screen),
+								rr_old_sizeid,
+								rr_old_rot,
+								CurrentTime);
+		}
+		XRRFreeScreenConfigInfo(m_screen_config);
+
 		LinuxDevice::shutdown();
 		LinuxDevice::shutdown();
 		XDestroyWindow(m_x11_display, m_x11_window);
 		XDestroyWindow(m_x11_display, m_x11_window);
 		XCloseDisplay(m_x11_display);
 		XCloseDisplay(m_x11_display);
@@ -652,6 +710,8 @@ private:
 	Cursor m_x11_hidden_cursor;
 	Cursor m_x11_hidden_cursor;
 	Atom m_wm_delete_message;
 	Atom m_wm_delete_message;
 
 
+	XRRScreenConfiguration* m_screen_config;
+
 	bool m_exit;
 	bool m_exit;
 	uint32_t m_x;
 	uint32_t m_x;
 	uint32_t m_y;
 	uint32_t m_y;

+ 12 - 0
engine/os/win/main.cpp

@@ -185,6 +185,18 @@ public:
 		#endif
 		#endif
 	}
 	}
 
 
+	//-----------------------------------------------------------------------------
+	void display_modes(Array<DisplayMode>& /*modes*/)
+	{
+		#error "Implement me"
+	}
+
+	//-----------------------------------------------------------------------------
+	void set_display_mode(uint32_t /*id*/)
+	{
+		#error "Implement me"
+	}
+
 	//-----------------------------------------------------------------------------
 	//-----------------------------------------------------------------------------
 	int32_t	run(int argc, char** argv)
 	int32_t	run(int argc, char** argv)
 	{
 	{