I'm using Kineticjs for a rotating pie-chart widget. When I try to draw on a rotated canvas element (the parent node is rotated 60deg using CSS3), the events don't seem to be working properly. For example, the hover event on a 15 deg clockwise rotated canvas is 15 deg off. Any Ideas?
The answer to your question is not trivial---here's why:
Your DOM container is in transformed space.
Your Kinetic objects react as if they are in non-transformed space.
Your kinetic objects are mis-responding because the browser is feeding them transformed mouse positions.
The simple fix: Leave the DOM container untransformed and do all rotations inside KineticJS
The difficult fix: convert rotated DOM mousepoints into unrotated points for Kinetic to use.
Here's the difficult fix:
The default rotation-point of CSS transforms is 50%,50% (the middle of the element) so find the center of the Kinetic stage
var cx=stage.getWidth()/2;
var cy=stage.getHeight()/2;
Given a mouseX/mouseY in transformed space (DOM space), you need to find the untransformed point (KineticJS space)
var unrotatedPoint = unrotatedXY(cx,cy, mouseX,mouseY, cssDegreeRotation);
Here's the function that does that calculation:
function unrotatedXY(cx,cy, mouseX,mouseY, cssDegreeRotation) {
var dx=mouseX-cx;
var dy=mouseY-cy;
var r=Math.sqrt(dx*dx+dy*dy);
var cssRadianAngle = cssDegreeRotation * Math.PI/180;
// calc the angle of the mouse position
var rotatedAngle = Math.atan2(dy,dx);
// unrotate the mouse position by the css rotation
var unrotatedAngle = rotatedAngle -= cssRadianAngle;
// normalize the angle
if(unrotatedAngle<0){ unrotatedAngle+=Math.PI*2; }
// calc the unrotated XY
unrotatedX = cx+ r * Math.cos(unrotatedAngle);
unrotatedY = cy+ r * Math.sin(unrotatedAngle);
return({x:unrotatedX,y:unrotatedY});
}
The mouseX/mouseY above are coming from the document, not KineticJS.
This means you must listen for mouse events on the document (or your container element), not in KineticJS itself.
$(document).mousemove(function(e){handleMouseMove(e);});
function handleMouseMove(e){
mouseX=parseInt(e.clientX-offsetX);
mouseY=parseInt(e.clientY-offsetY);
// convert the DOM mousepoint to a Kinetic mousepoint
var unrotatedPoint = unrotatedXY(cx,cy, mouseX,mouseY, cssDegreeRotation);
// Now you can check for hovers, etc against your Kinetic nodes …
}
To tie back into KineticJS, you might use node.fire to trigger events using custom event objects containing your converted mouse coordinates.
Update:
As markE suggested, there was no easy fix. The issue can be seen here . It was closed recently.
The original error was apparently caused by jquery's event handling code. It works properly as of the latest version.
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.