Empresas
Empleos
  • Sobre nosotros
  • Soluciones
    • Publicación de vacantes
      Publica tu vacante y recibe candidatos calificados en 48h.
    • Evaluación de candidatos
      500+ pruebas técnicas y psicológicas, más anti-fraude.
    • Headhunting
      Búsqueda ejecutiva a la medida de principio a fin.
    • Nómina + EOR
      Dispersión de nómina y EOR en más de 15 países de LATAM.
  • Precios
  • Empleos

0

244
Vistas
Javascript Canvas Relative Mouse Coordinates on Rotated Rectangle?

I am trying to treat a rectangle in canvas as a piece of paper, and get the same relative coordinates returned when I hover over the same point regardless of scale, rotation, or translation of the page.

Currently I get accurate results when in portrait or inverted portrait rotations and regardless of scale/translation. However, when I switch to landscape or inverted landscape my results are off.

I've attempted to switch to rotating mouse coordinates with some trigonometric functions I found, but math is not my strong suit and it didn't work.

If someone could point me in the right direction, I would be grateful. I suspect I need to swap axis or height/width when rotating landscape but that hasn't been fruitful either.

R key rotates the "page" through 4, 90 degree changes. Coordinates of your mouse relative to the page, clamped to the page's width/height are displayed in console.

https://jsfiddle.net/2hg6u3wd/2/ (Note, JSFiddle offsets coordinates slightly for an unknown reason)

const orientation = Object.freeze({
  portrait: 0,
  landscape: -90,
  invertedPortrait: 180,
  invertedLandscape: 90
});

function CameraRotate(rotation) {
  // Rotates using the center of target as origin. 
  ctx.translate(target.width / 2, target.height / 2);
  ctx.rotate(-(currentRot * Math.PI / 180)); // Negate currentRot because ctx.rotate() is additive.
  ctx.rotate(rotation * Math.PI / 180);
  ctx.translate(-(target.width / 2), -(target.height / 2));
  currentRot = rotation;
}

function CameraCalcRelTargetCoords(viewX, viewY) {
  return {
    x: clamp((viewX - ctx.getTransform().e) / ctx.getTransform().a, 0, page.width),
    y: clamp((viewY - ctx.getTransform().f) / ctx.getTransform().d, 0, page.height)
  };
}

function clamp(number, min, max) {
  return Math.max(min, Math.min(number, max));
}

canvas.addEventListener(`mousemove`, function(e) {
    console.log(CameraCalcRelTargetCoords(e.x, e.y));
});
about 4 years ago · Juan Pablo Isaza
1 Respuestas
Responde la pregunta

0

When rotating (-)180 degrees, the scale is stored as skew since the axis are flipped. Thus you must divide by m12 and m21. This flipping also means x and y mouse coordinates need to be swapped as well.

Here is my solution:

function CameraCalcRelTargetCoords(viewX, viewY) {
    // Mouse coordinates are translated to a position within the target's rectangle.
    let relX, relY

    if (currentRot == orientation.landscape || currentRot == orientation.invertedLandscape) {
        // Landscape rotation uses skewing for scale as X/Y axis are flipped.
        relX = clamp((viewY - ctx.getTransform().f) / ctx.getTransform().b, 0, target.width);
        relY = clamp((viewX - ctx.getTransform().e) / ctx.getTransform().c, 0, target.height);
    } else {
        relX = clamp((viewX - ctx.getTransform().e) / ctx.getTransform().a, 0, target.width),
        relY = clamp((viewY - ctx.getTransform().f) / ctx.getTransform().d, 0, target.height)
    }

    return {x: relX, y: relY};
}
about 4 years ago · Juan Pablo Isaza Denunciar
Responde la pregunta
Encuentra empleos remotos

¡Descubre la nueva forma de encontrar empleo!

Top de empleos
Top categorías de empleo
Empresas
Publicar vacante Precios Comercial
Legal
Términos y condiciones Política de privacidad
© 2026 PeakU Inc. All Rights Reserved.
Andres GPT
Recomiéndame algunas ofertas
Necesito ayuda