0

I'm trying to make a website of mine responsive. It uses JavaScript to let you select parts of an image on PC but it doesn't work on mobile. That's because of the events used - mouseup, mousedown, mousemove. How can I refactor my code so that it works on mobile? All I need to know is the coordinates of the selection.

Current code:

editCanvas.addEventListener("mousedown", (event) => {
    painting = true;
    canvasPosition = editCanvas.getBoundingClientRect();

    startCoords = {
        x: event.clientX - canvasPosition.left,
        y: event.clientY - canvasPosition.top,
    };
});

editCanvas.addEventListener("mousemove", (event) => {
    if (painting) {
        canvasPosition = editCanvas.getBoundingClientRect();
        let endCoords = {
            x: event.clientX - canvasPosition.left,
            y: event.clientY - canvasPosition.top,
        };

        renderSelections();

        dimensions = {
            x: startCoords.x,
            y: startCoords.y,
            width: endCoords.x - startCoords.x,
            height: endCoords.y - startCoords.y,
        };

        drawSelectionRect("#", dimensions, strokeStyle, "#BBBB");
    }
});

editCanvas.addEventListener("mouseup", () => (painting = false));

function drawSelectionRect(
    text,
    { x, y, width, height },
    { strokeWidth, lineDash, strokeColor },
    fillColor
) {
    ctx.lineWidth = strokeWidth;
    ctx.setLineDash(lineDash);
    ctx.strokeStyle = strokeColor;

    ctx.strokeRect(x, y, width, height);

    ctx.fillStyle = fillColor;

    ctx.fillRect(x, y, width, height);

    ctx.fillStyle = "#000";
    ctx.font = "16px sans-serif";
    ctx.textBaseline = "middle";
    ctx.textAlign = "center";

    ctx.fillText(text, x + width / 2, y + height / 2, width);
}

Update:

editCanvas.addEventListener("mousedown", (event) => {
    painting = true;
    canvasPosition = editCanvas.getBoundingClientRect();

    startCoords = {
        x: event.clientX - canvasPosition.left,
        y: event.clientY - canvasPosition.top,
    };
});

editCanvas.addEventListener("mousemove", (event) => {
    if (painting) {
        canvasPosition = editCanvas.getBoundingClientRect();
        let endCoords = {
            x: event.clientX - canvasPosition.left,
            y: event.clientY - canvasPosition.top,
        };

        renderSelections();

        dimensions = {
            x: startCoords.x,
            y: startCoords.y,
            width: endCoords.x - startCoords.x,
            height: endCoords.y - startCoords.y,
        };

        dimensions = correctDimensions(dimensions);

        drawSelectionRect("#", dimensions, strokeStyle, "#BBBB");
    }
});

editCanvas.addEventListener("mouseup", () => (painting = false));

editCanvas.addEventListener("touchstart", (event) => {
    event.preventDefault();

    painting = true;
    canvasPosition = editCanvas.getBoundingClientRect();

    startCoords = {
        x: event.touches[0].clientX - canvasPosition.left,
        y: event.touches[0].clientY - canvasPosition.top,
    };
});

editCanvas.addEventListener("touchmove", (event) => {
    event.preventDefault();

    if (painting) {
        canvasPosition = editCanvas.getBoundingClientRect();
        let endCoords = {
            x: event.touches[0].clientX - canvasPosition.left,
            y: event.touches[0].clientY - canvasPosition.top,
        };

        renderSelections();

        dimensions = {
            x: startCoords.x,
            y: startCoords.y,
            width: endCoords.x - startCoords.x,
            height: endCoords.y - startCoords.y,
        };

        dimensions = correctDimensions(dimensions);

        drawSelectionRect("#", dimensions, strokeStyle, "#BBBB");
    }
});

editCanvas.addEventListener("touchend", () => (painting = false));

function drawSelectionRect(
    text,
    { x, y, width, height },
    { strokeWidth, lineDash, strokeColor },
    fillColor
) {
    ctx.lineWidth = strokeWidth;
    ctx.setLineDash(lineDash);
    ctx.strokeStyle = strokeColor;

    ctx.strokeRect(x, y, width, height);

    ctx.fillStyle = fillColor;

    ctx.fillRect(x, y, width, height);

    ctx.fillStyle = "#000";
    ctx.font = "16px sans-serif";
    ctx.textBaseline = "middle";
    ctx.textAlign = "center";

    ctx.fillText(text, x + width / 2, y + height / 2, width);
}
ProGamer2711
  • 451
  • 1
  • 5
  • 18
  • Could you please provide some code of what you have already achieved? – Palladium02 Feb 03 '22 at 14:53
  • 1
    You might want to look into the touchstart, touchmove and touchend event. – Palladium02 Feb 03 '22 at 14:59
  • @Palladium02 I added the code and also tried the touch thingie but couldn't figure it out. When is the touch event triggered? – ProGamer2711 Feb 04 '22 at 06:29
  • https://developer.mozilla.org/en-US/docs/Web/API/Touch_events/Using_Touch_Events Take a look at this – consolenine Feb 04 '22 at 06:57
  • @consolenine I found a problem. When someone tries to do the selecting part from Safari, it doesn't want to zoom out the image. How can I fix that? – ProGamer2711 Feb 04 '22 at 08:29
  • @Palladium02 I found a problem. When someone tries to do the selecting part from Safari, it doesn't want to zoom out the image. How can I fix that? – ProGamer2711 Feb 04 '22 at 08:29
  • @AlexanderShestakov What do you exactly mean by "does not want to zoom out the image"? – Palladium02 Feb 04 '22 at 08:40
  • @Palladium02 Well the user picks an image on which they make the selections. As you know mobile screens can only be so big. So the image needs to be zoomed out in the browser and then the selections - made. On `Android` it lets me zoom in and out but when I try on `iOS` it doesn't. – ProGamer2711 Feb 04 '22 at 09:43
  • 1
    @AlexanderShestakov The question is still a bit unclear. I suggest creating a new question thread and share some images as well. – consolenine Feb 04 '22 at 10:06
  • @consolenine Sadly I'm unable to share images. My sister tested it on iPhone and there's no way she's letting me take pictures. I just think that when I do the touch event, because the canvas is so big and the screen so small it starts selecting instead of zooming out. I'm asking how I can stop that. – ProGamer2711 Feb 04 '22 at 15:41
  • @AlexanderShestakov In that case, you can add a pinch gesture event as well and make it so that the select function does not fire whilst the pinch event is active. I think the following guide will be useful in learning how to do the gesture. https://developer.mozilla.org/en-US/docs/Web/API/Pointer_events/Pinch_zoom_gestures Also take a look at this. https://stackoverflow.com/questions/11183174/simplest-way-to-detect-a-pinch – consolenine Feb 04 '22 at 16:20
  • @consolenine When I tried this the selection stopped working. Could you please show me how it would work? I'm adding the current code for when it was working to the original question. – ProGamer2711 Feb 04 '22 at 17:44
  • @consolenine I think it's not specifically on `iOS`. It's just zomming in/out in the canvas. So how do I detect it exactly and stop the selection and zoom? – ProGamer2711 Feb 05 '22 at 06:43

0 Answers0