From b0c00624dabc8d39179236887cdb80db1a1ef598 Mon Sep 17 00:00:00 2001 From: Airnan Date: Sun, 14 Apr 2024 16:27:26 +0800 Subject: [PATCH] =?UTF-8?q?=E6=96=B0=E5=A2=9E=EF=BC=9A=E7=BB=98=E7=94=BB?= =?UTF-8?q?=E5=8A=9F=E8=83=BD=EF=BC=8C=E5=B7=B2=E5=A4=84=E7=90=86PC?= =?UTF-8?q?=E7=AB=AF=E5=92=8C=E7=A7=BB=E5=8A=A8=E7=AB=AF=E5=85=BC=E5=AE=B9?= =?UTF-8?q?=E6=80=A7=E9=97=AE=E9=A2=98?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/resources/static/css/game.css | 1 + src/main/resources/static/index.html | 60 ++++++++++-- src/main/resources/static/js/draw.js | 127 +++++++++++++++++++++++++ 3 files changed, 178 insertions(+), 10 deletions(-) create mode 100644 src/main/resources/static/js/draw.js diff --git a/src/main/resources/static/css/game.css b/src/main/resources/static/css/game.css index 279bfb0..624f871 100644 --- a/src/main/resources/static/css/game.css +++ b/src/main/resources/static/css/game.css @@ -33,6 +33,7 @@ background-color: #ffffff; box-shadow: #000000 0 0 1px; border-radius: 10px; + touch-action: none; } .color-btn { diff --git a/src/main/resources/static/index.html b/src/main/resources/static/index.html index 37712fe..b63517d 100644 --- a/src/main/resources/static/index.html +++ b/src/main/resources/static/index.html @@ -47,17 +47,31 @@
题目:坐井观天
提示:成语,四个字
- +
- - - - - + + + + +
-
- +
+ + + + +
张
@@ -88,8 +102,10 @@ let playerId = ""; // 当前房间id let roomId = ""; - let backendAddr = "192.168.31.222:8080" + const backendAddr = "192.168.31.222:8080" const api = "http://" + backendAddr + "/api" + + init(); function init() { @@ -312,6 +328,28 @@ if (result.type === "room-chat") { $("#chat-box").append("

" + result.data + "

") } + if (result.type === "room-draw") { + let brush = JSON.parse(result.data); + console.log("收到坐标: ", brush.x, brush.y); + if (brush.isPoint) { + brushPoint = {x: brush.x, y: brush.y} + drawPoint(brush.x, brush.y, brush.width, brush.color); + } else { + // 移动端若按下事件坐标为空,则在划线事件中处理,将新的坐标作为点补充画点事件 + if (brushPoint.x == null || brushPoint.y == null) { + drawPoint(brush.x, brush.y, brush.width, brush.color); + brushPoint = {x: brush.x, y: brush.y}; + return; + } + drawLine(brushPoint, { + x: brush.x, + y: brush.y + }, brush.width, brush.color); + brushPoint = {x: brush.x, y: brush.y}; + } + + } + }; ws.onclose = function () { // 关闭 websocket @@ -412,4 +450,6 @@ } - \ No newline at end of file + + + \ No newline at end of file diff --git a/src/main/resources/static/js/draw.js b/src/main/resources/static/js/draw.js new file mode 100644 index 0000000..5fedca8 --- /dev/null +++ b/src/main/resources/static/js/draw.js @@ -0,0 +1,127 @@ +// canvas画板 +let canvas = document.getElementById("board"); +let context = canvas.getContext("2d"); +context.imageSmoothingEnabled = true; +let brushColor = "#000000"; +let brushWidth = 2; +let brushPoint = {x: 0, y: 0}; +let isDrawing = false; +// PC端 ******************************* +// 鼠标按下事件处理程序 +canvas.addEventListener("mousedown", function (event) { + isDrawing = true; + brushPoint = getBrushPoint(event); + // 广播绘画数据 + sendDrawData(brushPoint.x, brushPoint.y, true); + drawPoint(brushPoint.x, brushPoint.y, brushWidth, brushColor); +}); + +// 鼠标移动事件处理程序 +canvas.addEventListener("mousemove", function (event) { + if (isDrawing) { + let newPoint = getBrushPoint(event); + // 广播绘画数据 + sendDrawData(newPoint.x, newPoint.y, false); + drawLine(brushPoint, newPoint, brushWidth, brushColor); + brushPoint = newPoint; + } +}); + +// 鼠标释放事件处理程序 +canvas.addEventListener("mouseup", function () { + isDrawing = false; +}); + +// 移动端 ******************************* +// 触摸开始事件处理程序 +canvas.addEventListener("touchstart", function (event) { + isDrawing = true; + brushPoint = getTouchPoint(event); + // 广播绘画数据 + sendDrawData(brushPoint.x, brushPoint.y, true); + drawPoint(brushPoint.x, brushPoint.y, brushWidth, brushColor); +}); + +// 触摸移动事件处理程序 +canvas.addEventListener("touchmove", function (event) { + event.preventDefault(); // 防止滚动页面 + if (isDrawing) { + let newPoint = getTouchPoint(event.touches[0]); // 使用第一个触摸点 + // 广播绘画数据 + sendDrawData(newPoint.x, newPoint.y, false); + drawLine(brushPoint, newPoint, brushWidth, brushColor); + brushPoint = newPoint; + } +}); + +// 触摸结束事件处理程序 +canvas.addEventListener("touchend", function () { + isDrawing = false; +}); + +// 计算画笔在画布上的坐标 +function getBrushPoint(event) { + let rect = canvas.getBoundingClientRect(); + return { + x: (event.clientX - rect.left) * 2, + y: (event.clientY - rect.top) * 2 + }; +} +// 计算画笔在画布上的触摸坐标 +function getTouchPoint(touch) { + let rect = canvas.getBoundingClientRect(); + return { + x: (touch.clientX - rect.left) * (canvas.width / rect.width), + y: (touch.clientY - rect.top) * (canvas.height / rect.height) + }; +} +// 绘制单个点 +function drawPoint(x, y, width, color) { + context.beginPath(); + context.fillStyle = color; + context.arc(x, y, width / 2, 0, Math.PI * 2); + context.fill(); + context.closePath(); +} + +// 绘制线段 +function drawLine(startPoint, endPoint, whidth, color) { + context.beginPath(); + context.strokeStyle = color; + context.lineWidth = whidth; + context.lineCap = "round"; + context.moveTo(startPoint.x, startPoint.y); + context.lineTo(endPoint.x, endPoint.y); + context.stroke(); + context.closePath(); +} + +// 发送绘图信息的函数 +function sendDrawData(x, y, isPoint) { + // 构造绘图信息对象 + const drawData = { + x, + y, + color: brushColor, + width: brushWidth, + isPoint + }; + + sendMessage("room-draw", JSON.stringify(drawData)); +} + +/** + * 切换画笔颜色 + * @param color + */ +function changeBrushColor(color) { + brushColor = color; +} + +/** + * 切换画笔宽度 + * @param width 整数 + */ +function changeBrushWidth(width) { + brushWidth = width; +} \ No newline at end of file