在特定边界内拖动旋转的元素

时间:2013-06-03 15:27:15

标签: javascript raphael

在下面的小提琴中,您可以单击并拖动图像,它将无法退出蓝色边框。通过单击红色和绿色矩形,您可以旋转图像。但是,单击并拖动旋转的对象时​​,图像不会跟随鼠标。即使旋转,我也希望图像跟随鼠标。

http://jsfiddle.net/n3Sn5/

我认为问题发生在我的移动功能

move = function (dx, dy)
{
  nowX = Math.min(boundary.attr("x")+boundary.attr("width")-this.attr("width"), this.ox + dx);
  nowY = Math.min(boundary.attr("y")+boundary.attr("height")-this.attr("height"), this.oy + dy);
  nowX = Math.max(boundary.attr("x"), nowX);
  nowY = Math.max(boundary.attr("y"), nowY);

  this.attr({x: nowX, y: nowY });
}

有一点需要注意的是,当您单击并拖动旋转的对象时​​,在释放鼠标单击后,如果旋转图像,它会在您释放鼠标单击时捕捉到鼠标所在的位置,甚至服从边界。

我之前可以用鼠标拖动旋转的图像,但是通过添加边界矩形,我不得不使用更复杂的方法。

如果有人知道我需要改变什么,我将非常感激! 谢谢!

2 个答案:

答案 0 :(得分:1)

可以通过稍微不同的方式实现所需的输出。请在http://jsfiddle.net/6BbRL/查看小提琴。我已修剪代码以保留演示的基本部分。

var paper = Raphael(0, 0, 475, 475),
    boxX = 100,
    boxY = 100,
    boxWidth = 300,
    boxHeight = 200,
    // EDITED
    imgWidth = 50,
    imgHeight = 50,

    box = paper.rect(boxX, boxY, boxWidth, boxHeight).attr({fill:"#ffffff"}),
    // EDITED
    html5 = paper.image("http://www.w3.org/html/logo/downloads/HTML5_Badge_512.png",boxX+boxWidth-imgWidth,boxY+boxHeight-imgHeight,imgWidth,imgHeight)
        .attr({cursor: "move"}),

    elementCounterClockwise = paper.rect(180, 0, 50, 50).attr({fill:"#ff5555", cursor:"pointer"}),
    elementClockwise = paper.rect(250, 0, 50, 50).attr({ fill: "#55ff55", cursor: "pointer" }),

    boundary = paper.rect(50,50,400,300).attr({stroke: '#3333FF'}),

    transform,
    // EDITED
    xBound = {min: 50 + imgWidth/2, max: 450 - imgWidth/2},
    yBound = {min: 50 + imgHeight/2, max: 350 - imgHeight/2};

start = function (x, y) {
    // Find min and max values of dx and dy for "html5" element and store them for validating dx and dy in move()
    // This is required to impose a rectagular bound on drag movement of "html5" element.
    transform = html5.transform();
}

move = function (dx, dy, x, y) {
    // To restrict movement of the dragged element, Validate dx and dy before applying below.
    // Here, dx and dy are shifts along x and y axes, with respect to drag start position.
    // EDITED 
    var deltaX = x > xBound.max && xBound.max - x || x < xBound.min && xBound.min - x || 0;
        deltaY = y > yBound.max && yBound.max - y || y < yBound.min && yBound.min - y || 0;
    this.attr({transform: transform + 'T'+ [dx + deltaX, dy + deltaY]});     
}

up = function () {
};

html5.drag(move, start, up);

elementClockwise.click(function() {
  html5.animate({transform: '...r90'}, 100);
})

elementCounterClockwise.click(function() {
  html5.animate({transform: '...r-90'}, 100);
})

使用'...'将转换附加到预先存在的转换状态(Raphael API)对于旋转问题非常重要。而对于在拖动时平移元素需要绝对平移,这会在翻译元素时忽略元素的旋转状态。

//编辑注释

拖动边界已处理并更新。但是,结合鼠标位置和图像中心之间的差异仍存在问题。

答案 1 :(得分:0)

我可以帮助您解决旋转和拖动问题,您需要存储旋转并在移动对象后应用它。

elementClockwise.node.onclick = function()
{
    html5.animate({'transform': html5.transform() +'r90'}, 100, onAnimComplete);
}

elementCounterClockwise.node.onclick = function()
{
    html5.animate({'transform': html5.transform() +'r-90'}, 100, onAnimComplete);

}

function onAnimComplete(){
    default_transform = html5.transform();
}

目前我无法使边界工作,但稍后会尝试。

http://jsfiddle.net/n3Sn5/2/