From 8a2cd14092da1e9bd56c70cf488d3ac74bc72f46 Mon Sep 17 00:00:00 2001
From: Kalina <kalinabc@gmx.net>
Date: Tue, 19 Dec 2023 13:56:20 +0100
Subject: [PATCH 1/2] Added mouseup, mousedown, mousemove and mousewheel event
 handling to screens

---
 BondageClub/Scripts/ColorPicker.js |  4 +-
 BondageClub/Scripts/Common.js      | 32 ++++++++++
 BondageClub/Scripts/Game.js        | 98 +++++++++++++++++++++---------
 BondageClub/Scripts/Typedef.d.ts   | 20 ++++++
 4 files changed, 123 insertions(+), 31 deletions(-)

diff --git a/BondageClub/Scripts/ColorPicker.js b/BondageClub/Scripts/ColorPicker.js
index 5a5fa905fa..d34a5c10c7 100644
--- a/BondageClub/Scripts/ColorPicker.js
+++ b/BondageClub/Scripts/ColorPicker.js
@@ -146,11 +146,11 @@ function ColorPickerGetCoordinates(Event) {
 	if (isTouchEvent(Event)) {
 		if (Event.changedTouches) {
 			// Mobile
-			TouchMove(Event);
+			GameTouchMove(Event, false);
 		}
 	} else {
 		// PC
-		MouseMove(Event);
+		GameMouseMove(Event, false);
 	}
 
 	return { X: MouseX, Y: MouseY };
diff --git a/BondageClub/Scripts/Common.js b/BondageClub/Scripts/Common.js
index 71c1972c6a..f9fad68eda 100644
--- a/BondageClub/Scripts/Common.js
+++ b/BondageClub/Scripts/Common.js
@@ -250,6 +250,34 @@ function CommonGetRetry(Path, Callback, RetriesLeft) {
 	}
 }
 
+function CommonMouseDown(event) {
+	if (CurrentScreenFunctions.MouseDown)
+	{
+		CurrentScreenFunctions.MouseDown(event);
+	}
+}
+
+function CommonMouseUp(event) {
+	if (CurrentScreenFunctions.MouseUp)
+	{
+		CurrentScreenFunctions.MouseUp(event);
+	}
+}
+
+function CommonMouseMove(event) {
+	if (CurrentScreenFunctions.MouseMove)
+	{
+		CurrentScreenFunctions.MouseMove(event);
+	}
+}
+
+function CommonMouseWheel(event) {
+	if (CurrentScreenFunctions.MouseWheel)
+	{
+		CurrentScreenFunctions.MouseWheel(event);
+	}
+}
+
 /**
  * Catches the clicks on the main screen and forwards it to the current screen click function if it exists, otherwise it sends it to the dialog click function
  * @param {MouseEvent | TouchEvent} event - The event that triggered this
@@ -430,6 +458,10 @@ function CommonSetScreen(NewModule, NewScreen) {
 	CurrentScreenFunctions = {
 		Run: window[`${NewScreen}Run`],
 		Click: window[`${NewScreen}Click`],
+		MouseDown: typeof window[`${NewScreen}MouseDown`] === "function" ? window[`${NewScreen}MouseDown`] : undefined,
+		MouseUp: typeof window[`${NewScreen}MouseUp`] === "function" ? window[`${NewScreen}MouseUp`] : undefined,
+		MouseMove: typeof window[`${NewScreen}MouseMove`] === "function" ? window[`${NewScreen}MouseMove`] : undefined,
+		MouseWheel: typeof window[`${NewScreen}MouseWheel`] === "function" ? window[`${NewScreen}MouseWheel`] : undefined,
 		Load: typeof window[`${NewScreen}Load`] === "function" ? window[`${NewScreen}Load`] : undefined,
 		Unload: typeof window[`${NewScreen}Unload`] === "function" ? window[`${NewScreen}Unload`] : undefined,
 		Resize: typeof window[`${NewScreen}Resize`] === "function" ? window[`${NewScreen}Resize`] : undefined,
diff --git a/BondageClub/Scripts/Game.js b/BondageClub/Scripts/Game.js
index a32843c02a..d12107e24b 100644
--- a/BondageClub/Scripts/Game.js
+++ b/BondageClub/Scripts/Game.js
@@ -33,14 +33,16 @@ function GameStart() {
 	canvas.tabIndex = 1000;
 
 	canvas.addEventListener("keypress", GameKeyDown);
+	
+	canvas.addEventListener("mousedown", GameMouseDown);
+	canvas.addEventListener("mouseup", GameMouseUp);
+	canvas.addEventListener("mousemove", GameMouseMove);
+	canvas.addEventListener("wheel", GameMouseWheel);
+	canvas.addEventListener("mouseleave", GameMouseLeave);
 
-	canvas.addEventListener("click", MouseClick);
-	canvas.addEventListener("mousemove", MouseMove);
-	canvas.addEventListener("mouseleave", MouseLeave);
-
-	canvas.addEventListener("touchstart", TouchStart);
-	canvas.addEventListener("touchmove", TouchMove);
-	canvas.addEventListener("touchend", TouchEnd);
+	canvas.addEventListener("touchstart", GameTouchStart);
+	canvas.addEventListener("touchmove", GameTouchMove);
+	canvas.addEventListener("touchend", GameTouchEnd);
 
 	requestAnimationFrame(GameRun);
 }
@@ -96,55 +98,93 @@ function DocumentKeyDown(event) {
 	}
 }
 
+var GameMouseIsDown = false
 /**
- * When mouse move, we keep the mouse position for other scripts
+ * If the user presses the mouse button, we fire the mousedown event for other screens
  * @param {MouseEvent} event
  */
-function MouseMove(event) {
-	MouseX = Math.round(event.offsetX * 2000 / MainCanvas.canvas.clientWidth);
-	MouseY = Math.round(event.offsetY * 1000 / MainCanvas.canvas.clientHeight);
+function GameMouseDown(event) {
+	if (CommonIsMobile) { return }
+	if (GameMouseIsDown) { return }
+	CommonMouseDown(event);
+	GameMouseIsDown = true
+}
+
+/**
+ * If the user releases the mouse button, we fire the mouseup and click events for other screens
+ * @param {MouseEvent} event
+ */
+function GameMouseUp(event) {
+	if (CommonIsMobile) { return }
+	if (!GameMouseIsDown) { return }
+	GameMouseMove(event, false);
+	CommonMouseUp(event);
+	CommonClick(event);
+	GameMouseIsDown = false
 }
 
 /**
- * When the user clicks, we fire the click event for other screens
+ * If the user rolls the mouse wheel, we fire the mousewheel event for other screens
  * @param {MouseEvent} event
  */
-function MouseClick(event) {
-	if (!CommonIsMobile) {
-		MouseMove(event);
-		CommonClick(event);
+function GameMouseWheel(event) {
+	if (CommonIsMobile) { return }
+	CommonMouseWheel(event);
+	CommonClick(event);
+}
+
+/**
+ * If the user moves the mouse mouse, we keep the mouse position for other scripts and fire the mousemove event for other screens
+ * @param {MouseEvent} event
+ */
+function GameMouseMove(event, forwardToScreens = true) {
+	MouseX = Math.round(event.offsetX * 2000 / MainCanvas.canvas.clientWidth);
+	MouseY = Math.round(event.offsetY * 1000 / MainCanvas.canvas.clientHeight);
+	if(forwardToScreens)
+	{
+		CommonMouseMove(event);
 	}
 }
 
 /**
- * When the user touches the screen (mobile only), we fire the click event for other screens
+ * If the user starts touching the screen (mobile only), we fire the mousedown and click events for other screens
  * @param {TouchEvent} event
  */
-function TouchStart(event) {
-	if (!CommonIsMobile) return;
-	TouchMove(event);
+function GameTouchStart(event) {
+	if (!CommonIsMobile) { return; }
+	if (GameMouseIsDown) { return }
+	GameTouchMove(event, false);
+	CommonMouseDown(event);
 	CommonClick(event);
+	GameMouseIsDown = true
 	CommonTouchList = event.touches;
 }
 
 /**
- * When the user touches the screen (mobile only), we fire the click event for other screens
+ * If the user stops touching the screen (mobile only), we fire the mouseup event for other screens
  * @param {TouchEvent} event
  */
-function TouchEnd(event) {
-	if (!CommonIsMobile) return;
+function GameTouchEnd(event) {
+	if (!CommonIsMobile) { return; }
+	if (!GameMouseIsDown) { return }
+	CommonMouseUp(event);
+	GameMouseIsDown = false
 	CommonTouchList = event.touches;
 }
 
 /**
- * When touch moves, we keep it's position for other scripts
+ * if the user moves the touch, we keep the mouse position for other scripts and fire the mousemove event for other screens
  * @param {TouchEvent} event
  */
-function TouchMove(event) {
-	if (!CommonIsMobile) return;
+function GameTouchMove(event, forwardToScreens = true) {
+	if (!CommonIsMobile) { return; }
 	const touch = event.changedTouches[0];
 	MouseX = Math.round((touch.clientX - MainCanvas.canvas.offsetLeft) * 2000 / MainCanvas.canvas.clientWidth);
 	MouseY = Math.round((touch.clientY - MainCanvas.canvas.offsetTop) * 1000 / MainCanvas.canvas.clientHeight);
+	if(forwardToScreens)
+	{
+		CommonMouseMove(event);
+	}
 }
 
 /**
@@ -152,7 +192,7 @@ function TouchMove(event) {
  * we also check for false positives with "relatedTarget"
  * @param {MouseEvent} event
  */
-function MouseLeave(event) {
+function GameMouseLeave(event) {
 	if (event.relatedTarget) {
 		MouseX = -1;
 		MouseY = -1;
@@ -164,6 +204,6 @@ function KeyDown(event) { GameKeyDown(event); }
 /** @deprecated */
 function MainRun(Timestamp) { GameRun(Timestamp); }
 /** @deprecated */
-function Click(event) { MouseClick(event); }
+function Click(event) { if (!CommonIsMobile) { CommonClick(event); } }
 /** @deprecated */
-function LoseFocus(event) { MouseLeave(event); }
+function LoseFocus(event) { GameMouseLeave(event); }
diff --git a/BondageClub/Scripts/Typedef.d.ts b/BondageClub/Scripts/Typedef.d.ts
index 6ad3f3207a..baddd00202 100644
--- a/BondageClub/Scripts/Typedef.d.ts
+++ b/BondageClub/Scripts/Typedef.d.ts
@@ -1006,6 +1006,26 @@ interface ScreenFunctions {
 	 * @param {number} time - The current time for frame
 	 */
 	Run(time: number): void;
+	/**
+	 * Called if the user presses the mouse button or touches the touchscreen on the canvas
+	 * @param {MouseEvent | TouchEvent} event - The event that triggered this
+	 */
+	MouseDown(event: MouseEvent | TouchEvent): void;
+		/**
+	 * Called if the user releases the mouse button or the touchscreen on the canvas
+	 * @param {MouseEvent | TouchEvent} event - The event that triggered this
+	 */
+	MouseUp(event: MouseEvent | TouchEvent): void;
+	/**
+	 * Called if the user moves the mouse cursor or the touch on the touchscreen over the canvas
+	 * @param {MouseEvent | TouchEvent} event - The event that triggered this
+	 */
+	MouseMove(event: MouseEvent | TouchEvent): void;
+	/**
+	 * Called if user moves the mouse wheel on the canvas
+	 * @param {MouseEvent | TouchEvent} event - The event that triggered this
+	 */
+	MouseWheel(event: MouseEvent | TouchEvent): void;
 	/**
 	 * Called when user clicks on the canvas
 	 * @param {MouseEvent | TouchEvent} event - The event that triggered this
-- 
GitLab


From 21d1b0b8e67d24cedd07ea50074744140d2ed5a4 Mon Sep 17 00:00:00 2001
From: Kalina <kalinabc@gmx.net>
Date: Tue, 19 Dec 2023 14:08:36 +0100
Subject: [PATCH 2/2] Add KeyUp Event and change KeyDown logic to always send
 keys to the current screen as long as they are not needed anywhere else

---
 BondageClub/Scripts/Common.js    | 26 ++++++++++++++++++--------
 BondageClub/Scripts/Game.js      |  7 ++++++-
 BondageClub/Scripts/Typedef.d.ts | 19 ++++++++++++-------
 3 files changed, 36 insertions(+), 16 deletions(-)

diff --git a/BondageClub/Scripts/Common.js b/BondageClub/Scripts/Common.js
index f9fad68eda..ceea8ec06a 100644
--- a/BondageClub/Scripts/Common.js
+++ b/BondageClub/Scripts/Common.js
@@ -319,18 +319,27 @@ function CommonTouchActive(X, Y, W, H, TL) {
  * @returns {void} - Nothing
  */
 function CommonKeyDown(event) {
-	if (CurrentCharacter == null) {
-		if (CurrentScreenFunctions.KeyDown)
-			CurrentScreenFunctions.KeyDown(event);
-		if (ControllerIsActive()) {
-			ControllerSupportKeyDown();
-		}
-	}
-	else {
+	if(StruggleMinigameIsRunning()) {
 		StruggleKeyDown();
 		if (ControllerIsActive()) {
 			ControllerSupportKeyDown();
 		}
+		return;
+	}
+	if (CurrentScreenFunctions.KeyDown)
+	{
+		CurrentScreenFunctions.KeyDown(event);
+	}
+	if (ControllerIsActive()) {
+		ControllerSupportKeyDown();
+	}
+}
+
+function CommonKeyUp(event) {
+	if(StruggleMinigameIsRunning()) { return; }
+	if (CurrentScreenFunctions.KeyUp)
+	{
+		CurrentScreenFunctions.KeyUp(event);
 	}
 }
 
@@ -466,6 +475,7 @@ function CommonSetScreen(NewModule, NewScreen) {
 		Unload: typeof window[`${NewScreen}Unload`] === "function" ? window[`${NewScreen}Unload`] : undefined,
 		Resize: typeof window[`${NewScreen}Resize`] === "function" ? window[`${NewScreen}Resize`] : undefined,
 		KeyDown: typeof window[`${NewScreen}KeyDown`] === "function" ? window[`${NewScreen}KeyDown`] : undefined,
+		KeyUp: typeof window[`${NewScreen}KeyUp`] === "function" ? window[`${NewScreen}KeyUp`] : undefined,
 		Exit: typeof window[`${NewScreen}Exit`] === "function" ? window[`${NewScreen}Exit`] : undefined
 	};
 
diff --git a/BondageClub/Scripts/Game.js b/BondageClub/Scripts/Game.js
index d12107e24b..2670ce6200 100644
--- a/BondageClub/Scripts/Game.js
+++ b/BondageClub/Scripts/Game.js
@@ -32,7 +32,8 @@ function GameStart() {
 	const canvas = document.getElementById("MainCanvas");
 	canvas.tabIndex = 1000;
 
-	canvas.addEventListener("keypress", GameKeyDown);
+	canvas.addEventListener("keydown", GameKeyDown);
+	canvas.addEventListener("keyup", GameKeyUp);
 	
 	canvas.addEventListener("mousedown", GameMouseDown);
 	canvas.addEventListener("mouseup", GameMouseUp);
@@ -79,6 +80,10 @@ function GameKeyDown(event) {
 	CommonKeyDown(event);
 }
 
+function GameKeyUp(event) {
+	CommonKeyUp(event);
+}
+
 /**
  * Handler for document-wide keydown event
  * @param {KeyboardEvent} event
diff --git a/BondageClub/Scripts/Typedef.d.ts b/BondageClub/Scripts/Typedef.d.ts
index baddd00202..2fbb6f1651 100644
--- a/BondageClub/Scripts/Typedef.d.ts
+++ b/BondageClub/Scripts/Typedef.d.ts
@@ -1010,24 +1010,24 @@ interface ScreenFunctions {
 	 * Called if the user presses the mouse button or touches the touchscreen on the canvas
 	 * @param {MouseEvent | TouchEvent} event - The event that triggered this
 	 */
-	MouseDown(event: MouseEvent | TouchEvent): void;
+	MouseDown?(event: MouseEvent | TouchEvent): void;
 		/**
 	 * Called if the user releases the mouse button or the touchscreen on the canvas
 	 * @param {MouseEvent | TouchEvent} event - The event that triggered this
 	 */
-	MouseUp(event: MouseEvent | TouchEvent): void;
+	MouseUp?(event: MouseEvent | TouchEvent): void;
 	/**
 	 * Called if the user moves the mouse cursor or the touch on the touchscreen over the canvas
 	 * @param {MouseEvent | TouchEvent} event - The event that triggered this
 	 */
-	MouseMove(event: MouseEvent | TouchEvent): void;
+	MouseMove?(event: MouseEvent | TouchEvent): void;
 	/**
-	 * Called if user moves the mouse wheel on the canvas
+	 * Called if the user moves the mouse wheel on the canvas
 	 * @param {MouseEvent | TouchEvent} event - The event that triggered this
 	 */
-	MouseWheel(event: MouseEvent | TouchEvent): void;
+	MouseWheel?(event: MouseEvent | TouchEvent): void;
 	/**
-	 * Called when user clicks on the canvas
+	 * Called if the user clicks on the canvas
 	 * @param {MouseEvent | TouchEvent} event - The event that triggered this
 	 */
 	Click(event: MouseEvent | TouchEvent): void;
@@ -1043,10 +1043,15 @@ interface ScreenFunctions {
 	 */
 	Resize?(load: boolean): void;
 	/**
-	 * Called when user presses any key
+	 * Called if the the user presses any key
 	 * @param {KeyboardEvent} event - The event that triggered this
 	 */
 	KeyDown?(event: KeyboardEvent): void;
+	/**
+	 * Called if the user releases a pressed key
+	 * @param {KeyboardEvent} event - The event that triggered this
+	 */
+	KeyUp?(event: KeyboardEvent): void;
 	/** Called when user presses Esc */
 	Exit?(): void;
 }
-- 
GitLab