Browse Source

Add epic hack so vsync can be toggled in run-time from script. Fixes #14458.
Call needs to be routed via visual server to reach the proper thread.

Juan Linietsky 7 years ago
parent
commit
652c98a7be

+ 10 - 1
core/os/os.cpp

@@ -536,12 +536,21 @@ String OS::get_joy_guid(int p_device) const {
 
 void OS::set_context(int p_context) {
 }
+
+OS::SwitchVSyncCallbackInThread OS::switch_vsync_function = NULL;
+
 void OS::set_use_vsync(bool p_enable) {
+	_use_vsync = p_enable;
+	if (switch_vsync_function) { //if a function was set, use function
+		switch_vsync_function(p_enable);
+	} else { //otherwise just call here
+		_set_use_vsync(p_enable);
+	}
 }
 
 bool OS::is_vsync_enabled() const {
 
-	return true;
+	return _use_vsync;
 }
 
 OS::PowerState OS::get_power_state() {

+ 11 - 2
core/os/os.h

@@ -58,6 +58,7 @@ class OS {
 	int _exit_code;
 	int _orientation;
 	bool _allow_hidpi;
+	bool _use_vsync;
 
 	char *last_error;
 
@@ -435,8 +436,16 @@ public:
 
 	virtual void set_context(int p_context);
 
-	virtual void set_use_vsync(bool p_enable);
-	virtual bool is_vsync_enabled() const;
+	//amazing hack because OpenGL needs this to be set on a separate thread..
+	//also core can't access servers, so a callback must be used
+	typedef void (*SwitchVSyncCallbackInThread)(bool);
+
+	static SwitchVSyncCallbackInThread switch_vsync_function;
+	void set_use_vsync(bool p_enable);
+	bool is_vsync_enabled() const;
+
+	//real, actual overridable function to switch vsync, which needs to be called from graphics thread if needed
+	virtual void _set_use_vsync(bool p_enable) {}
 
 	virtual OS::PowerState get_power_state();
 	virtual int get_power_seconds_left();

+ 2 - 2
platform/osx/os_osx.h

@@ -215,8 +215,8 @@ public:
 
 	virtual bool _check_internal_feature_support(const String &p_feature);
 
-	virtual void set_use_vsync(bool p_enable);
-	virtual bool is_vsync_enabled() const;
+	virtual void _set_use_vsync(bool p_enable);
+	//virtual bool is_vsync_enabled() const;
 
 	void run();
 

+ 3 - 3
platform/osx/os_osx.mm

@@ -2063,14 +2063,14 @@ Error OS_OSX::move_to_trash(const String &p_path) {
 	return OK;
 }
 
-void OS_OSX::set_use_vsync(bool p_enable) {
+void OS_OSX::_set_use_vsync(bool p_enable) {
 	CGLContextObj ctx = CGLGetCurrentContext();
 	if (ctx) {
 		GLint swapInterval = p_enable ? 1 : 0;
 		CGLSetParameter(ctx, kCGLCPSwapInterval, &swapInterval);
 	}
 }
-
+/*
 bool OS_OSX::is_vsync_enabled() const {
 	GLint swapInterval = 0;
 	CGLContextObj ctx = CGLGetCurrentContext();
@@ -2079,7 +2079,7 @@ bool OS_OSX::is_vsync_enabled() const {
 	}
 	return swapInterval ? true : false;
 }
-
+*/
 OS_OSX *OS_OSX::singleton = NULL;
 
 OS_OSX::OS_OSX() {

+ 3 - 3
platform/windows/os_windows.cpp

@@ -2288,19 +2288,19 @@ String OS_Windows::get_joy_guid(int p_device) const {
 	return input->get_joy_guid_remapped(p_device);
 }
 
-void OS_Windows::set_use_vsync(bool p_enable) {
+void OS_Windows::_set_use_vsync(bool p_enable) {
 
 	if (gl_context)
 		gl_context->set_use_vsync(p_enable);
 }
-
+/*
 bool OS_Windows::is_vsync_enabled() const {
 
 	if (gl_context)
 		return gl_context->is_using_vsync();
 
 	return true;
-}
+}*/
 
 OS::PowerState OS_Windows::get_power_state() {
 	return power_manager->get_power_state();

+ 2 - 2
platform/windows/os_windows.h

@@ -275,8 +275,8 @@ public:
 	virtual bool is_joy_known(int p_device);
 	virtual String get_joy_guid(int p_device) const;
 
-	virtual void set_use_vsync(bool p_enable);
-	virtual bool is_vsync_enabled() const;
+	virtual void _set_use_vsync(bool p_enable);
+	//virtual bool is_vsync_enabled() const;
 
 	virtual OS::PowerState get_power_state();
 	virtual int get_power_seconds_left();

+ 3 - 3
platform/x11/os_x11.cpp

@@ -2306,11 +2306,11 @@ String OS_X11::get_joy_guid(int p_device) const {
 	return input->get_joy_guid_remapped(p_device);
 }
 
-void OS_X11::set_use_vsync(bool p_enable) {
+void OS_X11::_set_use_vsync(bool p_enable) {
 	if (context_gl)
 		return context_gl->set_use_vsync(p_enable);
 }
-
+/*
 bool OS_X11::is_vsync_enabled() const {
 
 	if (context_gl)
@@ -2318,7 +2318,7 @@ bool OS_X11::is_vsync_enabled() const {
 
 	return true;
 }
-
+*/
 void OS_X11::set_context(int p_context) {
 
 	XClassHint *classHint = XAllocClassHint();

+ 2 - 2
platform/x11/os_x11.h

@@ -270,8 +270,8 @@ public:
 
 	virtual void set_context(int p_context);
 
-	virtual void set_use_vsync(bool p_enable);
-	virtual bool is_vsync_enabled() const;
+	virtual void _set_use_vsync(bool p_enable);
+	//virtual bool is_vsync_enabled() const;
 
 	virtual OS::PowerState get_power_state();
 	virtual int get_power_seconds_left();

+ 4 - 0
servers/visual/visual_server_raster.cpp

@@ -181,6 +181,10 @@ void VisualServerRaster::set_debug_generate_wireframes(bool p_generate) {
 	VSG::storage->set_debug_generate_wireframes(p_generate);
 }
 
+void VisualServerRaster::call_set_use_vsync(bool p_enable) {
+	OS::get_singleton()->_set_use_vsync(p_enable);
+}
+
 VisualServerRaster::VisualServerRaster() {
 
 	VSG::canvas = memnew(VisualServerCanvas);

+ 2 - 0
servers/visual/visual_server_raster.h

@@ -668,6 +668,8 @@ public:
 	virtual bool has_os_feature(const String &p_feature) const;
 	virtual void set_debug_generate_wireframes(bool p_generate);
 
+	virtual void call_set_use_vsync(bool p_enable);
+
 	VisualServerRaster();
 	~VisualServerRaster();
 

+ 10 - 0
servers/visual/visual_server_wrap_mt.cpp

@@ -158,9 +158,19 @@ void VisualServerWrapMT::finish() {
 	canvas_occluder_polygon_free_cached_ids();
 }
 
+void VisualServerWrapMT::set_use_vsync_callback(bool p_enable) {
+
+	singleton_mt->call_set_use_vsync(p_enable);
+}
+
+VisualServerWrapMT *VisualServerWrapMT::singleton_mt = NULL;
+
 VisualServerWrapMT::VisualServerWrapMT(VisualServer *p_contained, bool p_create_thread) :
 		command_queue(p_create_thread) {
 
+	singleton_mt = this;
+	OS::switch_vsync_function = set_use_vsync_callback; //as this goes to another thread, make sure it goes properly
+
 	visual_server = p_contained;
 	create_thread = p_create_thread;
 	thread = NULL;

+ 6 - 0
servers/visual/visual_server_wrap_mt.h

@@ -64,6 +64,8 @@ class VisualServerWrapMT : public VisualServer {
 
 	//#define DEBUG_SYNC
 
+	static VisualServerWrapMT *singleton_mt;
+
 #ifdef DEBUG_SYNC
 #define SYNC_DEBUG print_line("sync on: " + String(__FUNCTION__));
 #else
@@ -584,6 +586,10 @@ public:
 	virtual bool has_feature(Features p_feature) const { return visual_server->has_feature(p_feature); }
 	virtual bool has_os_feature(const String &p_feature) const { return visual_server->has_os_feature(p_feature); }
 
+	FUNC1(call_set_use_vsync, bool)
+
+	static void set_use_vsync_callback(bool p_enable);
+
 	VisualServerWrapMT(VisualServer *p_contained, bool p_create_thread);
 	~VisualServerWrapMT();
 

+ 1 - 0
servers/visual_server.cpp

@@ -1922,6 +1922,7 @@ VisualServer::VisualServer() {
 
 	//ERR_FAIL_COND(singleton);
 	singleton = this;
+
 	GLOBAL_DEF("rendering/vram_compression/import_s3tc", true);
 	GLOBAL_DEF("rendering/vram_compression/import_etc", false);
 	GLOBAL_DEF("rendering/vram_compression/import_etc2", true);

+ 2 - 0
servers/visual_server.h

@@ -980,6 +980,8 @@ public:
 
 	virtual void set_debug_generate_wireframes(bool p_generate) = 0;
 
+	virtual void call_set_use_vsync(bool p_enable) = 0;
+
 	VisualServer();
 	virtual ~VisualServer();
 };