Browse Source

Added a click count argument to love.mousepressed/released. Tracks double/triple/etc. clicks.

--HG--
branch : minor
Alex Szpakowski 9 years ago
parent
commit
b38e567e74
4 changed files with 91 additions and 39 deletions
  1. 67 28
      src/modules/event/sdl/Event.cpp
  2. 14 3
      src/modules/event/sdl/Event.h
  3. 4 4
      src/scripts/boot.lua
  4. 6 4
      src/scripts/boot.lua.h

+ 67 - 28
src/modules/event/sdl/Event.cpp

@@ -31,6 +31,7 @@
 #include "common/Exception.h"
 #include "common/Exception.h"
 #include "audio/Audio.h"
 #include "audio/Audio.h"
 #include "common/config.h"
 #include "common/config.h"
+#include "timer/Timer.h"
 
 
 #include <cmath>
 #include <cmath>
 
 
@@ -146,7 +147,7 @@ void Event::clear()
 	love::event::Event::clear();
 	love::event::Event::clear();
 }
 }
 
 
-Message *Event::convert(const SDL_Event &e) const
+Message *Event::convert(const SDL_Event &e)
 {
 {
 	Message *msg = nullptr;
 	Message *msg = nullptr;
 
 
@@ -243,31 +244,7 @@ Message *Event::convert(const SDL_Event &e) const
 		break;
 		break;
 	case SDL_MOUSEBUTTONDOWN:
 	case SDL_MOUSEBUTTONDOWN:
 	case SDL_MOUSEBUTTONUP:
 	case SDL_MOUSEBUTTONUP:
-		{
-			// SDL uses button index 3 for the right mouse button, but we use
-			// index 2.
-			int button = e.button.button;
-			switch (button)
-			{
-			case SDL_BUTTON_RIGHT:
-				button = 2;
-				break;
-			case SDL_BUTTON_MIDDLE:
-				button = 3;
-				break;
-			}
-
-			double x = (double) e.button.x;
-			double y = (double) e.button.y;
-			windowToPixelCoords(&x, &y);
-			vargs.emplace_back(x);
-			vargs.emplace_back(y);
-			vargs.emplace_back((double) button);
-			vargs.emplace_back(e.button.which == SDL_TOUCH_MOUSEID);
-			msg = new Message((e.type == SDL_MOUSEBUTTONDOWN) ?
-							  "mousepressed" : "mousereleased",
-							  vargs);
-		}
+		msg = convertMouseButtonEvent(e);
 		break;
 		break;
 	case SDL_MOUSEWHEEL:
 	case SDL_MOUSEWHEEL:
 		vargs.emplace_back((double) e.wheel.x);
 		vargs.emplace_back((double) e.wheel.x);
@@ -385,7 +362,69 @@ Message *Event::convert(const SDL_Event &e) const
 	return msg;
 	return msg;
 }
 }
 
 
-Message *Event::convertJoystickEvent(const SDL_Event &e) const
+Message *Event::convertMouseButtonEvent(const SDL_Event &e)
+{
+	bool down = e.type == SDL_MOUSEBUTTONDOWN;
+
+	std::vector<Variant> vargs;
+	vargs.reserve(5);
+
+	// SDL uses button index 3 for the right mouse button, but we use index 2.
+	int button = e.button.button;
+	switch (button)
+	{
+	case SDL_BUTTON_RIGHT:
+		button = 2;
+		break;
+	case SDL_BUTTON_MIDDLE:
+		button = 3;
+		break;
+	}
+
+	double px = (double) e.button.x;
+	double py = (double) e.button.y;
+	windowToPixelCoords(&px, &py);
+	vargs.emplace_back(px);
+	vargs.emplace_back(py);
+	vargs.emplace_back((double) button);
+	vargs.emplace_back(e.button.which == SDL_TOUCH_MOUSEID);
+
+#if SDL_VERSION_ATLEAST(2,0,4)
+	SDL_version version;
+	SDL_GetVersion(&version);
+	if (version.major >= 2 && (version.minor > 0 || version.patch >= 4))
+		vargs.emplace_back((double) e.button.clicks);
+	else
+#endif
+	{
+		ClickState state = clickCounts[e.button.which];
+
+		// Matches the behaviour of SDL 2.0.4's click count tracking code when
+		// it doesn't know any OS-specific information.
+		if (down)
+		{
+			double now = timer::Timer::getTime();
+			int diffX = abs(e.button.x - state.lastX);
+			int diffY = abs(e.button.y - state.lastY);
+
+			if ((now - state.time) >= 0.5 || diffX > 1 || diffY > 1)
+				state.count = 0;
+
+			state.count++;
+			state.lastX = e.button.x;
+			state.lastY = e.button.y;
+			state.time = now;
+
+			clickCounts[e.button.which] = state;
+		}
+
+		vargs.emplace_back((double) state.count);
+	}
+
+	return new Message(down ? "mousepressed" : "mousereleased", vargs);
+}
+
+Message *Event::convertJoystickEvent(const SDL_Event &e)
 {
 {
 	auto joymodule = Module::getInstance<joystick::JoystickModule>(Module::M_JOYSTICK);
 	auto joymodule = Module::getInstance<joystick::JoystickModule>(Module::M_JOYSTICK);
 	if (!joymodule)
 	if (!joymodule)
@@ -510,7 +549,7 @@ Message *Event::convertJoystickEvent(const SDL_Event &e) const
 	return msg;
 	return msg;
 }
 }
 
 
-Message *Event::convertWindowEvent(const SDL_Event &e) const
+Message *Event::convertWindowEvent(const SDL_Event &e)
 {
 {
 	Message *msg = nullptr;
 	Message *msg = nullptr;
 
 

+ 14 - 3
src/modules/event/sdl/Event.h

@@ -68,9 +68,20 @@ public:
 
 
 private:
 private:
 
 
-	Message *convert(const SDL_Event &e) const;
-	Message *convertJoystickEvent(const SDL_Event &e) const;
-	Message *convertWindowEvent(const SDL_Event &e) const;
+	struct ClickState
+	{
+		int count;
+		int lastX;
+		int lastY;
+		double time;
+	};
+
+	Message *convert(const SDL_Event &e);
+	Message *convertMouseButtonEvent(const SDL_Event &e);
+	Message *convertJoystickEvent(const SDL_Event &e);
+	Message *convertWindowEvent(const SDL_Event &e);
+
+	std::map<int, ClickState> clickCounts;
 
 
 	static std::map<SDL_Keycode, love::keyboard::Keyboard::Key> createKeyMap();
 	static std::map<SDL_Keycode, love::keyboard::Keyboard::Key> createKeyMap();
 	static std::map<SDL_Keycode, love::keyboard::Keyboard::Key> keys;
 	static std::map<SDL_Keycode, love::keyboard::Keyboard::Key> keys;

+ 4 - 4
src/scripts/boot.lua

@@ -169,11 +169,11 @@ function love.createhandlers()
 		mousemoved = function (x,y,dx,dy,t)
 		mousemoved = function (x,y,dx,dy,t)
 			if love.mousemoved then return love.mousemoved(x,y,dx,dy,t) end
 			if love.mousemoved then return love.mousemoved(x,y,dx,dy,t) end
 		end,
 		end,
-		mousepressed = function (x,y,b,t)
-			if love.mousepressed then return love.mousepressed(x,y,b,t) end
+		mousepressed = function (x,y,b,t,c)
+			if love.mousepressed then return love.mousepressed(x,y,b,t,c) end
 		end,
 		end,
-		mousereleased = function (x,y,b,t)
-			if love.mousereleased then return love.mousereleased(x,y,b,t) end
+		mousereleased = function (x,y,b,t,c)
+			if love.mousereleased then return love.mousereleased(x,y,b,t,c) end
 		end,
 		end,
 		wheelmoved = function (x,y)
 		wheelmoved = function (x,y)
 			if love.wheelmoved then return love.wheelmoved(x,y) end
 			if love.wheelmoved then return love.wheelmoved(x,y) end

+ 6 - 4
src/scripts/boot.lua.h

@@ -294,18 +294,20 @@ const unsigned char boot_lua[] =
 	0x64, 0x78, 0x2c, 0x64, 0x79, 0x2c, 0x74, 0x29, 0x20, 0x65, 0x6e, 0x64, 0x0a,
 	0x64, 0x78, 0x2c, 0x64, 0x79, 0x2c, 0x74, 0x29, 0x20, 0x65, 0x6e, 0x64, 0x0a,
 	0x09, 0x09, 0x65, 0x6e, 0x64, 0x2c, 0x0a,
 	0x09, 0x09, 0x65, 0x6e, 0x64, 0x2c, 0x0a,
 	0x09, 0x09, 0x6d, 0x6f, 0x75, 0x73, 0x65, 0x70, 0x72, 0x65, 0x73, 0x73, 0x65, 0x64, 0x20, 0x3d, 0x20, 0x66, 
 	0x09, 0x09, 0x6d, 0x6f, 0x75, 0x73, 0x65, 0x70, 0x72, 0x65, 0x73, 0x73, 0x65, 0x64, 0x20, 0x3d, 0x20, 0x66, 
-	0x75, 0x6e, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x20, 0x28, 0x78, 0x2c, 0x79, 0x2c, 0x62, 0x2c, 0x74, 0x29, 0x0a,
+	0x75, 0x6e, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x20, 0x28, 0x78, 0x2c, 0x79, 0x2c, 0x62, 0x2c, 0x74, 0x2c, 0x63, 
+	0x29, 0x0a,
 	0x09, 0x09, 0x09, 0x69, 0x66, 0x20, 0x6c, 0x6f, 0x76, 0x65, 0x2e, 0x6d, 0x6f, 0x75, 0x73, 0x65, 0x70, 0x72, 
 	0x09, 0x09, 0x09, 0x69, 0x66, 0x20, 0x6c, 0x6f, 0x76, 0x65, 0x2e, 0x6d, 0x6f, 0x75, 0x73, 0x65, 0x70, 0x72, 
 	0x65, 0x73, 0x73, 0x65, 0x64, 0x20, 0x74, 0x68, 0x65, 0x6e, 0x20, 0x72, 0x65, 0x74, 0x75, 0x72, 0x6e, 0x20, 
 	0x65, 0x73, 0x73, 0x65, 0x64, 0x20, 0x74, 0x68, 0x65, 0x6e, 0x20, 0x72, 0x65, 0x74, 0x75, 0x72, 0x6e, 0x20, 
 	0x6c, 0x6f, 0x76, 0x65, 0x2e, 0x6d, 0x6f, 0x75, 0x73, 0x65, 0x70, 0x72, 0x65, 0x73, 0x73, 0x65, 0x64, 0x28, 
 	0x6c, 0x6f, 0x76, 0x65, 0x2e, 0x6d, 0x6f, 0x75, 0x73, 0x65, 0x70, 0x72, 0x65, 0x73, 0x73, 0x65, 0x64, 0x28, 
-	0x78, 0x2c, 0x79, 0x2c, 0x62, 0x2c, 0x74, 0x29, 0x20, 0x65, 0x6e, 0x64, 0x0a,
+	0x78, 0x2c, 0x79, 0x2c, 0x62, 0x2c, 0x74, 0x2c, 0x63, 0x29, 0x20, 0x65, 0x6e, 0x64, 0x0a,
 	0x09, 0x09, 0x65, 0x6e, 0x64, 0x2c, 0x0a,
 	0x09, 0x09, 0x65, 0x6e, 0x64, 0x2c, 0x0a,
 	0x09, 0x09, 0x6d, 0x6f, 0x75, 0x73, 0x65, 0x72, 0x65, 0x6c, 0x65, 0x61, 0x73, 0x65, 0x64, 0x20, 0x3d, 0x20, 
 	0x09, 0x09, 0x6d, 0x6f, 0x75, 0x73, 0x65, 0x72, 0x65, 0x6c, 0x65, 0x61, 0x73, 0x65, 0x64, 0x20, 0x3d, 0x20, 
-	0x66, 0x75, 0x6e, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x20, 0x28, 0x78, 0x2c, 0x79, 0x2c, 0x62, 0x2c, 0x74, 0x29, 0x0a,
+	0x66, 0x75, 0x6e, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x20, 0x28, 0x78, 0x2c, 0x79, 0x2c, 0x62, 0x2c, 0x74, 0x2c, 
+	0x63, 0x29, 0x0a,
 	0x09, 0x09, 0x09, 0x69, 0x66, 0x20, 0x6c, 0x6f, 0x76, 0x65, 0x2e, 0x6d, 0x6f, 0x75, 0x73, 0x65, 0x72, 0x65, 
 	0x09, 0x09, 0x09, 0x69, 0x66, 0x20, 0x6c, 0x6f, 0x76, 0x65, 0x2e, 0x6d, 0x6f, 0x75, 0x73, 0x65, 0x72, 0x65, 
 	0x6c, 0x65, 0x61, 0x73, 0x65, 0x64, 0x20, 0x74, 0x68, 0x65, 0x6e, 0x20, 0x72, 0x65, 0x74, 0x75, 0x72, 0x6e, 
 	0x6c, 0x65, 0x61, 0x73, 0x65, 0x64, 0x20, 0x74, 0x68, 0x65, 0x6e, 0x20, 0x72, 0x65, 0x74, 0x75, 0x72, 0x6e, 
 	0x20, 0x6c, 0x6f, 0x76, 0x65, 0x2e, 0x6d, 0x6f, 0x75, 0x73, 0x65, 0x72, 0x65, 0x6c, 0x65, 0x61, 0x73, 0x65, 
 	0x20, 0x6c, 0x6f, 0x76, 0x65, 0x2e, 0x6d, 0x6f, 0x75, 0x73, 0x65, 0x72, 0x65, 0x6c, 0x65, 0x61, 0x73, 0x65, 
-	0x64, 0x28, 0x78, 0x2c, 0x79, 0x2c, 0x62, 0x2c, 0x74, 0x29, 0x20, 0x65, 0x6e, 0x64, 0x0a,
+	0x64, 0x28, 0x78, 0x2c, 0x79, 0x2c, 0x62, 0x2c, 0x74, 0x2c, 0x63, 0x29, 0x20, 0x65, 0x6e, 0x64, 0x0a,
 	0x09, 0x09, 0x65, 0x6e, 0x64, 0x2c, 0x0a,
 	0x09, 0x09, 0x65, 0x6e, 0x64, 0x2c, 0x0a,
 	0x09, 0x09, 0x77, 0x68, 0x65, 0x65, 0x6c, 0x6d, 0x6f, 0x76, 0x65, 0x64, 0x20, 0x3d, 0x20, 0x66, 0x75, 0x6e, 
 	0x09, 0x09, 0x77, 0x68, 0x65, 0x65, 0x6c, 0x6d, 0x6f, 0x76, 0x65, 0x64, 0x20, 0x3d, 0x20, 0x66, 0x75, 0x6e, 
 	0x63, 0x74, 0x69, 0x6f, 0x6e, 0x20, 0x28, 0x78, 0x2c, 0x79, 0x29, 0x0a,
 	0x63, 0x74, 0x69, 0x6f, 0x6e, 0x20, 0x28, 0x78, 0x2c, 0x79, 0x29, 0x0a,