2014-03-13 77 views
4
$(function() { 
var canvas = document.getElementById("canvas"); 
var ctx = canvas.getContext("2d"); 

// get the offset position of the container 
var $canvas = $("#canvas"); 
var Offset = $canvas.offset(); 
var offsetX = Offset.left; 
var offsetY = Offset.top; 

// select all .tool's 
var $tools = $(".tool"); 

// make all .tool's draggable 
$tools.draggable({ 
helper: 'clone', 
revert: 'invalid' 
}); 


    // assign each .tool its index in $tools 
$tools.each(function (index, element) { 
$(this).data("toolsIndex", index); 
}); 

// make the canvas a dropzone 
$canvas.droppable({ 
drop: dragDrop, 
}); 

// handle a drop into the canvas 
function dragDrop(e, ui) { 

// get the drop point (be sure to adjust for border) 
var x = parseInt(ui.offset.left - offsetX); 
var y = parseInt(ui.offset.top - offsetY); 

// get the drop payload (here the payload is the $tools index) 
var theIndex = ui.draggable.data("toolsIndex"); 

// drawImage at the drop point using the dropped image 
ctx.drawImage($tools[theIndex], x, y, 32, 32); 

} 
}); 

我尝试了很多东西,但是失败了。该代码允许我将多个图像拖放到画布元素上。我需要做的是增加拖放图像后再次拖放的可能性。我知道画布必须每次重绘,但我不知道如何。在将图像放到画布上后允许拖动

任何人都可以解决这个问题吗?

+0

是什么意思哟* '再次拖动图像' *?你的意思是在画布上开始拖动一次? –

+0

我拖动的图像不在画布元素中。我从画布外面(实际上是手风琴)拖放到画布元素上。所以,一旦他们进入画布,我不能再移动它们,我需要它们可以拖动,改变它们的位置(为了应用程序的灵活性)。 –

+0

你的意思是说,一旦你放弃它们,它们将从手风琴中移除,但是你希望它们仍然存在,所以你可以再次拖动它们? –

回答

5

既然你评论说,你打开帆布库,这里是让你一个例子:

  • 拖累使用jQueryUI的工具栏-DIV img元素。
  • 将img放在画布上并创建一个可以在画布上拖动的KineticJS.Image对象。

甲演示:http://jsfiddle.net/m1erickson/gkefk/

结果:一个IMG拖动3X从蓝色工具栏,滴在灰色帆布,然后拖在画布上。

enter image description here

这里有一个注释代码示例:

<!DOCTYPE html> 
<html> 
    <head> 
    <meta charset="utf-8"> 
    <title>Prototype</title> 
    <script type="text/javascript" src="http://code.jquery.com/jquery.min.js"></script> 
    <script src="http://d3lp1msu2r81bx.cloudfront.net/kjs/js/lib/kinetic-v4.7.2.min.js"></script> 
    <script src="http://code.jquery.com/ui/1.9.2/jquery-ui.min.js"></script> 
<style> 
    body{padding:20px;} 
    #container{ 
     border:solid 1px #ccc; 
     margin-top: 10px; 
     width:350px; 
     height:350px; 
    } 
    #toolbar{ 
     width:350px; 
     height:35px; 
     border:solid 1px blue; 
    } 
</style>   
<script> 
$(function(){ 

    // get a reference to the house icon in the toolbar 
    // hide the icon until its image has loaded 
    var $house=$("#house"); 
    $house.hide(); 

    // get the offset position of the kinetic container 
    var $stageContainer=$("#container"); 
    var stageOffset=$stageContainer.offset(); 
    var offsetX=stageOffset.left; 
    var offsetY=stageOffset.top; 

    // create the Kinetic.Stage and layer 
    var stage = new Kinetic.Stage({ 
     container: 'container', 
     width: 350, 
     height: 350 
    }); 
    var layer = new Kinetic.Layer(); 
    stage.add(layer); 

    // start loading the image used in the draggable toolbar element 
    // this image will be used in a new Kinetic.Image 
    var image1=new Image(); 
    image1.onload=function(){ 
     $house.show(); 
    } 
    image1.src="https://dl.dropboxusercontent.com/u/139992952/stackoverflow/house32x32transparent.png"; 

    // make the toolbar image draggable 
    $house.draggable({ 
     helper:'clone', 
    }); 

    // set the data payload 
    $house.data("url","house.png"); // key-value pair 
    $house.data("width","32"); // key-value pair 
    $house.data("height","33"); // key-value pair 
    $house.data("image",image1); // key-value pair 

    // make the Kinetic Container a dropzone 
    $stageContainer.droppable({ 
     drop:dragDrop, 
    }); 

    // handle a drop into the Kinetic container 
    function dragDrop(e,ui){ 

     // get the drop point 
     var x=parseInt(ui.offset.left-offsetX); 
     var y=parseInt(ui.offset.top-offsetY); 

     // get the drop payload (here the payload is the image) 
     var element=ui.draggable; 
     var data=element.data("url"); 
     var theImage=element.data("image"); 

     // create a new Kinetic.Image at the drop point 
     // be sure to adjust for any border width (here border==1) 
     var image = new Kinetic.Image({ 
      name:data, 
      x:x, 
      y:y, 
      image:theImage, 
      draggable: true 
     }); 
     layer.add(image); 
     layer.draw(); 
    } 

}); // end $(function(){}); 

</script>  
</head> 
<body> 
    <div id="toolbar"> 
     <img id="house" width=32 height=32 src="https://dl.dropboxusercontent.com/u/139992952/stackoverflow/house32x32transparent.png"><br> 
    </div> 
    <div id="container"></div> 
</body> 
</html> 
+0

你的代码不工作.Drop操作不执行。 – Developer

+1

@Singh,我刚刚运行我的示例代码和演示上面&他们似乎运行良好... – markE

+0

@markE我可以删除它在某些情况下丢弃图像? –

1

你想要的东西当然不容易。现在,您只需放下图像并将其绘制在鼠标位置。做你想做的事,你需要:

  1. 跟踪添加的图像,他们的位置,他们的大小,和他们的Z指数。最好的方法是使用堆栈结构,具有以下属性的对象数组:urlxywidth,height。 z-index可以是数组的索引。
  2. 在画布上开始拖动操作后,需要获取要拖动的点,然后找到包含该点的z-index最高的图像(基本上是实现点击测试)。
  3. 要移动它,则必须将其从画布中移除,这意味着使用除拖动的图像之外的所有图像重绘整个画布。为此,您可以使用先前定义的堆栈,并按顺序绘制图像。
  4. 最后,您需要在放下图像后再次绘制图像,从数组中的位置开始并在末尾附加它。

这不是一件容易的事。我建议你为它使用一些库。我不能推荐你,因为我对画布几乎没有任何经验。

+0

起初我决定使用EaselJS库,最后我用纯JS和jQuery来做。我没有在这个库上找到好的文档,它总是很简单的演示,而且当你看到我正在处理的应用程序需要的不仅仅是这些演示。谢谢你:-) –

+0

我希望我可以帮助你更多的代码,但我不能承诺,因为这需要一些时间,我不知道我是否有时间。 –