diff --git a/js-src/components/overlay-controls.tsx b/js-src/components/overlay-controls.tsx index fc354d7..9110566 100644 --- a/js-src/components/overlay-controls.tsx +++ b/js-src/components/overlay-controls.tsx @@ -8,6 +8,10 @@ export interface OverlayControlsProps { webSocket: WebSocket | null; }; +interface ControlMap { + [id: string]: {key: number, ref: React.RefObject, sym: string, classes: string, transformX?: number, transformY?: number} +}; + export default function OverlayControls({firstMenuElement, setHiddenMenu, webSocket}: OverlayControlsProps) { function showOverlayMenu() { setHiddenMenu(false); @@ -37,7 +41,7 @@ export default function OverlayControls({firstMenuElement, setHiddenMenu, webSoc sendKeyDown(webSocket, false, key); } - const controls: {[id: string]: {key: number, ref: React.RefObject, sym: string, classes: string, transformX?: number, transformY?: number}} = {}; + const controls: ControlMap = {}; controls.a = { ref: React.useRef(null), key: 0, @@ -78,6 +82,37 @@ export default function OverlayControls({firstMenuElement, setHiddenMenu, webSoc transformX: 200, classes: 'control-right control control-pad-button', } + + function determineKey(e: React.TouchEvent, touch: React.Touch): number | null { + const x = touch.pageX; + const y = touch.pageY; + for (const control of Object.keys(controls)) { + const ref = controls[control].ref.current; + if (ref == null) { + console.log('No ref found'); + continue; + } + let top = ref.getBoundingClientRect().top + document.documentElement.scrollTop; + const currentControl = controls[control]; + const transformX = currentControl.transformX; + const transformY = currentControl.transformY; + let offsetLeft = ref.offsetLeft; + const offsetWidth = ref.offsetWidth; + let offsetTop = top; + const offsetHeight = ref.offsetHeight; + if (transformX != null) { + offsetLeft += offsetWidth * (transformX / 100); + } + if (transformY != null) { + offsetTop += offsetHeight * (transformY / 100); + } + console.log(x, y, offsetLeft, offsetTop, offsetWidth, offsetHeight); + if (x >= offsetLeft && x <= offsetLeft + offsetWidth && y >= offsetTop && y <= offsetTop + offsetHeight) { + return controls[control].key; + } + } + return null; + } function touchStartControls(e: React.TouchEvent) { e.preventDefault(); if (webSocket == null) { @@ -86,38 +121,7 @@ export default function OverlayControls({firstMenuElement, setHiddenMenu, webSoc } for (let i = 0; i < e.changedTouches.length; i++) { const touch = e.changedTouches[i]; - const x = touch.pageX; - const y = touch.pageY; - let key: number|null = null; - for (const control of Object.keys(controls)) { - const ref = controls[control].ref.current; - if (ref == null) { - console.log('No ref found'); - continue; - } - let top = ref.getBoundingClientRect().top + document.documentElement.scrollTop; - const currentControl = controls[control]; - const transformX = currentControl.transformX; - const transformY = currentControl.transformY; - let offsetLeft = ref.offsetLeft; - const offsetWidth = ref.offsetWidth; - let offsetTop = top; - const offsetHeight = ref.offsetHeight; - if (transformX != null) { - offsetLeft += offsetWidth * (transformX / 100); - } - if (transformY != null) { - offsetTop += offsetHeight * (transformY / 100); - } - console.log(x, y, offsetLeft, offsetTop, offsetWidth, offsetHeight); - if (x >= offsetLeft && x <= offsetLeft + offsetWidth && y >= offsetTop && y <= offsetTop + offsetHeight) { - key = controls[control].key; - console.log(key); - break; - } - - } - console.log(key); + let key: number|null = determineKey(e, touch); if (key == null) { continue; } @@ -135,44 +139,15 @@ export default function OverlayControls({firstMenuElement, setHiddenMenu, webSoc } for (let i = 0; i < e.changedTouches.length; i++) { const touch = e.changedTouches[i]; - const x = touch.pageX; - const y = touch.pageY; - let key: number|null = null; - for (const control of Object.keys(controls)) { - const ref = controls[control].ref.current; - if (ref == null) { - console.log('No ref found'); - continue; - } - let top = ref.getBoundingClientRect().top + document.documentElement.scrollTop; - const currentControl = controls[control]; - const transformX = currentControl.transformX; - const transformY = currentControl.transformY; - let offsetLeft = ref.offsetLeft; - const offsetWidth = ref.offsetWidth; - let offsetTop = top; - const offsetHeight = ref.offsetHeight; - if (transformX != null) { - offsetLeft += offsetWidth * (transformX / 100); - } - if (transformY != null) { - offsetTop += offsetHeight * (transformY / 100); - } - if (x >= offsetLeft && x <= offsetLeft + offsetWidth && y >= offsetTop && y <= offsetTop + offsetHeight) { - key = controls[control].key; - console.log(key); - break; - } - - } + let key: number|null = determineKey(e, touch); const idx = touch.identifier; + if (key == null) { + continue; + } if (onGoingTouches[idx] != null) { sendKeyDown(webSocket, false, onGoingTouches[idx]); delete onGoingTouches[idx]; } - if (key == null) { - continue; - } onGoingTouches[idx] = key; sendKeyDown(webSocket, true, key); } diff --git a/public/css/styles.css b/public/css/styles.css index 8fa806f..235316f 100644 --- a/public/css/styles.css +++ b/public/css/styles.css @@ -169,3 +169,15 @@ form label, form input { z-index: 4; font-size: 20px; } + +@media (min-aspect-ratio: 176/241) { + .overlay > div.vertical-padding { + height: 0%; + } + .overlay > div.controls { + height: 100%; + } + .full-height { + height: 100vh; + } +} diff --git a/public/js/bundle.js b/public/js/bundle.js index f140f24..4c80f4d 100644 --- a/public/js/bundle.js +++ b/public/js/bundle.js @@ -126,7 +126,7 @@ eval("__webpack_require__.r(__webpack_exports__);\n/* harmony export */ __webpac \************************************************/ /***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => { -eval("__webpack_require__.r(__webpack_exports__);\n/* harmony export */ __webpack_require__.d(__webpack_exports__, {\n/* harmony export */ \"default\": () => (/* binding */ OverlayControls)\n/* harmony export */ });\n/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react */ \"./node_modules/react/index.js\");\n/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_0__);\n/* harmony import */ var _constants__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ../../../constants */ \"./js-src/constants.ts\");\n/* harmony import */ var _packet__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../../../packet */ \"./js-src/packet.ts\");\n\n\n\n;\nfunction OverlayControls({ firstMenuElement, setHiddenMenu, webSocket }) {\n function showOverlayMenu() {\n setHiddenMenu(false);\n setTimeout(() => {\n if (firstMenuElement.current == null) {\n return;\n }\n firstMenuElement.current.focus();\n }, 100);\n }\n const [onGoingTouches, setOnGoingTouches] = react__WEBPACK_IMPORTED_MODULE_0__.useState({});\n function mouseDown(e, key) {\n e.preventDefault();\n if (webSocket == null) {\n console.log('There is not websocket');\n return;\n }\n (0,_packet__WEBPACK_IMPORTED_MODULE_2__.sendKeyDown)(webSocket, true, key);\n }\n function mouseUp(e, key) {\n e.preventDefault();\n if (webSocket == null) {\n console.log('There is not websocket');\n return;\n }\n (0,_packet__WEBPACK_IMPORTED_MODULE_2__.sendKeyDown)(webSocket, false, key);\n }\n const controls = {};\n controls.a = {\n ref: react__WEBPACK_IMPORTED_MODULE_0__.useRef(null),\n key: 0,\n sym: 'A',\n classes: 'control-a control control-button',\n };\n controls.b = {\n ref: react__WEBPACK_IMPORTED_MODULE_0__.useRef(null),\n key: 1,\n sym: 'B',\n transformX: 50,\n classes: 'control-b control control-button',\n };\n controls.up = {\n ref: react__WEBPACK_IMPORTED_MODULE_0__.useRef(null),\n key: 6,\n sym: '^',\n transformX: 100,\n classes: 'control-up control control-pad-button',\n };\n controls.down = {\n ref: react__WEBPACK_IMPORTED_MODULE_0__.useRef(null),\n key: 7,\n sym: 'v',\n transformX: 100,\n classes: 'control-down control control-pad-button',\n };\n controls.left = {\n ref: react__WEBPACK_IMPORTED_MODULE_0__.useRef(null),\n key: 8,\n sym: '<',\n classes: 'control-left control control-pad-button',\n };\n controls.right = {\n ref: react__WEBPACK_IMPORTED_MODULE_0__.useRef(null),\n key: 9,\n sym: '>',\n transformX: 200,\n classes: 'control-right control control-pad-button',\n };\n function touchStartControls(e) {\n e.preventDefault();\n if (webSocket == null) {\n console.log('There is not websocket');\n return;\n }\n for (let i = 0; i < e.changedTouches.length; i++) {\n const touch = e.changedTouches[i];\n const x = touch.pageX;\n const y = touch.pageY;\n let key = null;\n for (const control of Object.keys(controls)) {\n const ref = controls[control].ref.current;\n if (ref == null) {\n console.log('No ref found');\n continue;\n }\n let top = ref.getBoundingClientRect().top + document.documentElement.scrollTop;\n const currentControl = controls[control];\n const transformX = currentControl.transformX;\n const transformY = currentControl.transformY;\n let offsetLeft = ref.offsetLeft;\n const offsetWidth = ref.offsetWidth;\n let offsetTop = top;\n const offsetHeight = ref.offsetHeight;\n if (transformX != null) {\n offsetLeft += offsetWidth * (transformX / 100);\n }\n if (transformY != null) {\n offsetTop += offsetHeight * (transformY / 100);\n }\n console.log(x, y, offsetLeft, offsetTop, offsetWidth, offsetHeight);\n if (x >= offsetLeft && x <= offsetLeft + offsetWidth && y >= offsetTop && y <= offsetTop + offsetHeight) {\n key = controls[control].key;\n console.log(key);\n break;\n }\n }\n console.log(key);\n if (key == null) {\n continue;\n }\n const idx = touch.identifier;\n onGoingTouches[idx] = key;\n (0,_packet__WEBPACK_IMPORTED_MODULE_2__.sendKeyDown)(webSocket, true, key);\n }\n return false;\n }\n function touchMoveControls(e) {\n e.preventDefault();\n if (webSocket == null) {\n console.log('There is not websocket');\n return;\n }\n for (let i = 0; i < e.changedTouches.length; i++) {\n const touch = e.changedTouches[i];\n const x = touch.pageX;\n const y = touch.pageY;\n let key = null;\n for (const control of Object.keys(controls)) {\n const ref = controls[control].ref.current;\n if (ref == null) {\n console.log('No ref found');\n continue;\n }\n let top = ref.getBoundingClientRect().top + document.documentElement.scrollTop;\n const currentControl = controls[control];\n const transformX = currentControl.transformX;\n const transformY = currentControl.transformY;\n let offsetLeft = ref.offsetLeft;\n const offsetWidth = ref.offsetWidth;\n let offsetTop = top;\n const offsetHeight = ref.offsetHeight;\n if (transformX != null) {\n offsetLeft += offsetWidth * (transformX / 100);\n }\n if (transformY != null) {\n offsetTop += offsetHeight * (transformY / 100);\n }\n if (x >= offsetLeft && x <= offsetLeft + offsetWidth && y >= offsetTop && y <= offsetTop + offsetHeight) {\n key = controls[control].key;\n console.log(key);\n break;\n }\n }\n const idx = touch.identifier;\n if (onGoingTouches[idx] != null) {\n (0,_packet__WEBPACK_IMPORTED_MODULE_2__.sendKeyDown)(webSocket, false, onGoingTouches[idx]);\n delete onGoingTouches[idx];\n }\n if (key == null) {\n continue;\n }\n onGoingTouches[idx] = key;\n (0,_packet__WEBPACK_IMPORTED_MODULE_2__.sendKeyDown)(webSocket, true, key);\n }\n return false;\n }\n function touchEndControls(e) {\n e.preventDefault();\n if (webSocket == null) {\n console.log('There is not websocket');\n return;\n }\n for (let i = 0; i < e.changedTouches.length; i++) {\n const touch = e.changedTouches[i];\n const idx = touch.identifier;\n if (onGoingTouches[idx] == null) {\n return;\n }\n (0,_packet__WEBPACK_IMPORTED_MODULE_2__.sendKeyDown)(webSocket, false, onGoingTouches[idx]);\n delete onGoingTouches[idx];\n }\n return false;\n }\n document.onselectstart = () => false;\n return (react__WEBPACK_IMPORTED_MODULE_0__.createElement(\"div\", { className: \"overlay\" },\n react__WEBPACK_IMPORTED_MODULE_0__.createElement(\"div\", { className: \"vertical-padding\" }),\n react__WEBPACK_IMPORTED_MODULE_0__.createElement(\"div\", { className: \"controls\", onTouchStart: touchStartControls, onTouchMove: touchMoveControls, onTouchEnd: touchEndControls },\n react__WEBPACK_IMPORTED_MODULE_0__.createElement(\"a\", { tabIndex: -1, className: \"gear control\", onClick: showOverlayMenu, onTouchStart: showOverlayMenu },\n react__WEBPACK_IMPORTED_MODULE_0__.createElement(\"img\", { src: _constants__WEBPACK_IMPORTED_MODULE_1__.HOME_BUTTON_IMAGE, alt: \"Go to menu. (House icon)\" })),\n Object.keys(controls).map((key) => react__WEBPACK_IMPORTED_MODULE_0__.createElement(\"a\", { tabIndex: -1, className: controls[key].classes, ref: controls[key].ref, key: key, onMouseDown: (e) => mouseDown(e, controls[key].key), onMouseUp: (e) => mouseUp(e, controls[key].key) }, controls[key].sym)))));\n}\n\n\n//# sourceURL=webpack://MSGBA-Web/./js-src/components/overlay-controls.tsx?"); +eval("__webpack_require__.r(__webpack_exports__);\n/* harmony export */ __webpack_require__.d(__webpack_exports__, {\n/* harmony export */ \"default\": () => (/* binding */ OverlayControls)\n/* harmony export */ });\n/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react */ \"./node_modules/react/index.js\");\n/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_0__);\n/* harmony import */ var _constants__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ../../../constants */ \"./js-src/constants.ts\");\n/* harmony import */ var _packet__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../../../packet */ \"./js-src/packet.ts\");\n\n\n\n;\n;\nfunction OverlayControls({ firstMenuElement, setHiddenMenu, webSocket }) {\n function showOverlayMenu() {\n setHiddenMenu(false);\n setTimeout(() => {\n if (firstMenuElement.current == null) {\n return;\n }\n firstMenuElement.current.focus();\n }, 100);\n }\n const [onGoingTouches, setOnGoingTouches] = react__WEBPACK_IMPORTED_MODULE_0__.useState({});\n function mouseDown(e, key) {\n e.preventDefault();\n if (webSocket == null) {\n console.log('There is not websocket');\n return;\n }\n (0,_packet__WEBPACK_IMPORTED_MODULE_2__.sendKeyDown)(webSocket, true, key);\n }\n function mouseUp(e, key) {\n e.preventDefault();\n if (webSocket == null) {\n console.log('There is not websocket');\n return;\n }\n (0,_packet__WEBPACK_IMPORTED_MODULE_2__.sendKeyDown)(webSocket, false, key);\n }\n const controls = {};\n controls.a = {\n ref: react__WEBPACK_IMPORTED_MODULE_0__.useRef(null),\n key: 0,\n sym: 'A',\n classes: 'control-a control control-button',\n };\n controls.b = {\n ref: react__WEBPACK_IMPORTED_MODULE_0__.useRef(null),\n key: 1,\n sym: 'B',\n transformX: 50,\n classes: 'control-b control control-button',\n };\n controls.up = {\n ref: react__WEBPACK_IMPORTED_MODULE_0__.useRef(null),\n key: 6,\n sym: '^',\n transformX: 100,\n classes: 'control-up control control-pad-button',\n };\n controls.down = {\n ref: react__WEBPACK_IMPORTED_MODULE_0__.useRef(null),\n key: 7,\n sym: 'v',\n transformX: 100,\n classes: 'control-down control control-pad-button',\n };\n controls.left = {\n ref: react__WEBPACK_IMPORTED_MODULE_0__.useRef(null),\n key: 8,\n sym: '<',\n classes: 'control-left control control-pad-button',\n };\n controls.right = {\n ref: react__WEBPACK_IMPORTED_MODULE_0__.useRef(null),\n key: 9,\n sym: '>',\n transformX: 200,\n classes: 'control-right control control-pad-button',\n };\n function determineKey(e, touch) {\n const x = touch.pageX;\n const y = touch.pageY;\n for (const control of Object.keys(controls)) {\n const ref = controls[control].ref.current;\n if (ref == null) {\n console.log('No ref found');\n continue;\n }\n let top = ref.getBoundingClientRect().top + document.documentElement.scrollTop;\n const currentControl = controls[control];\n const transformX = currentControl.transformX;\n const transformY = currentControl.transformY;\n let offsetLeft = ref.offsetLeft;\n const offsetWidth = ref.offsetWidth;\n let offsetTop = top;\n const offsetHeight = ref.offsetHeight;\n if (transformX != null) {\n offsetLeft += offsetWidth * (transformX / 100);\n }\n if (transformY != null) {\n offsetTop += offsetHeight * (transformY / 100);\n }\n console.log(x, y, offsetLeft, offsetTop, offsetWidth, offsetHeight);\n if (x >= offsetLeft && x <= offsetLeft + offsetWidth && y >= offsetTop && y <= offsetTop + offsetHeight) {\n return controls[control].key;\n }\n }\n return null;\n }\n function touchStartControls(e) {\n e.preventDefault();\n if (webSocket == null) {\n console.log('There is not websocket');\n return;\n }\n for (let i = 0; i < e.changedTouches.length; i++) {\n const touch = e.changedTouches[i];\n let key = determineKey(e, touch);\n if (key == null) {\n continue;\n }\n const idx = touch.identifier;\n onGoingTouches[idx] = key;\n (0,_packet__WEBPACK_IMPORTED_MODULE_2__.sendKeyDown)(webSocket, true, key);\n }\n return false;\n }\n function touchMoveControls(e) {\n e.preventDefault();\n if (webSocket == null) {\n console.log('There is not websocket');\n return;\n }\n for (let i = 0; i < e.changedTouches.length; i++) {\n const touch = e.changedTouches[i];\n let key = determineKey(e, touch);\n const idx = touch.identifier;\n if (key == null) {\n continue;\n }\n if (onGoingTouches[idx] != null) {\n (0,_packet__WEBPACK_IMPORTED_MODULE_2__.sendKeyDown)(webSocket, false, onGoingTouches[idx]);\n delete onGoingTouches[idx];\n }\n onGoingTouches[idx] = key;\n (0,_packet__WEBPACK_IMPORTED_MODULE_2__.sendKeyDown)(webSocket, true, key);\n }\n return false;\n }\n function touchEndControls(e) {\n e.preventDefault();\n if (webSocket == null) {\n console.log('There is not websocket');\n return;\n }\n for (let i = 0; i < e.changedTouches.length; i++) {\n const touch = e.changedTouches[i];\n const idx = touch.identifier;\n if (onGoingTouches[idx] == null) {\n return;\n }\n (0,_packet__WEBPACK_IMPORTED_MODULE_2__.sendKeyDown)(webSocket, false, onGoingTouches[idx]);\n delete onGoingTouches[idx];\n }\n return false;\n }\n document.onselectstart = () => false;\n return (react__WEBPACK_IMPORTED_MODULE_0__.createElement(\"div\", { className: \"overlay\" },\n react__WEBPACK_IMPORTED_MODULE_0__.createElement(\"div\", { className: \"vertical-padding\" }),\n react__WEBPACK_IMPORTED_MODULE_0__.createElement(\"div\", { className: \"controls\", onTouchStart: touchStartControls, onTouchMove: touchMoveControls, onTouchEnd: touchEndControls },\n react__WEBPACK_IMPORTED_MODULE_0__.createElement(\"a\", { tabIndex: -1, className: \"gear control\", onClick: showOverlayMenu, onTouchStart: showOverlayMenu },\n react__WEBPACK_IMPORTED_MODULE_0__.createElement(\"img\", { src: _constants__WEBPACK_IMPORTED_MODULE_1__.HOME_BUTTON_IMAGE, alt: \"Go to menu. (House icon)\" })),\n Object.keys(controls).map((key) => react__WEBPACK_IMPORTED_MODULE_0__.createElement(\"a\", { tabIndex: -1, className: controls[key].classes, ref: controls[key].ref, key: key, onMouseDown: (e) => mouseDown(e, controls[key].key), onMouseUp: (e) => mouseUp(e, controls[key].key) }, controls[key].sym)))));\n}\n\n\n//# sourceURL=webpack://MSGBA-Web/./js-src/components/overlay-controls.tsx?"); /***/ }),