如何在不使用Group的情况下将多个形状移动到一起

时间:2013-04-20 20:03:12

标签: kineticjs

我是KineticJS的新手并且有一个非常基本的问题。

我正在尝试使用KineticJS创建图形(父子层次结构)。所以在任何节点我都会有3件事:

1)一个圆圈作为节点本身

2)附在圆圈上的“+”符号的小图像。单击此“+”将允许创建 子节点。

3)将此节点与子节点连接的一条线。

我尝试将它们中的所有3个捆绑在一个'组'中但问题是当我拖动组时它们中的所有3个一起移动 - 这显然是预期的 - 但是当我拖动子节点它“分离”时它是一个问题连接到父节点的行。

基本上只有连接到子节点的线路的一端应该移动,并且连接到父节点的端部应该是固定的。

我如何实现这一目标?一个快速的代码片段将帮助我处理这个问题,我试图在过去2天内徒劳无功。

非常感谢!

-S

1 个答案:

答案 0 :(得分:2)

您可以通过使用自定义drawFunc创建一行来保持父节点和子节点的连接。

该行的自定义drawFunc只获取父&孩子的位置,并在他们之间吸引。

drawFunc: function(canvas){
    var ctx=canvas.getContext();
    var x1=parentNode.getPosition().x;
    var y1=parentNode.getPosition().y;
    var x2=childNode.getPosition().x;
    var y2=childNode.getPosition().y;
    ctx.save();
    ctx.strokeStyle="red";
    ctx.lineWidth=3;
    ctx.beginPath();
    ctx.moveTo(x1,y1);
    ctx.lineTo(x2,y2);
    ctx.stroke();
    ctx.restore();
},

您可能还希望将线条保留在节点后面而不是顶部。

您可以通过设置stage.getDragLayer.afterDraw函数将连接线移动到z-index的底部来实现此目的

stage.getDragLayer().afterDraw(function() {
    connector.moveToBottom();
    layer.draw();
});

这是代码和小提琴:http://jsfiddle.net/m1erickson/tt2KG/

<!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://www.html5canvastutorials.com/libraries/kinetic-v4.3.3-beta.js"></script>

<style>
#container{
  border:solid 1px #ccc;
  margin-top: 10px;
}
</style>        
<script>
$(function(){


    function init(){

        var stage = new Kinetic.Stage({
            container: 'container',
            width: 400,
            height: 400
        });
        var layer = new Kinetic.Layer();
        stage.add(layer);

        var parentNode = new Kinetic.Circle({
          x: 50,
          y: 80,
          radius: 40,
          fill: "blue",
          stroke: "red",
          strokeWidth: 3,
          draggable: true
        });    

        var childNode = new Kinetic.Circle({
          x: 150,
          y: 80,
          radius:25,
          fill: "green",
          stroke: "red",
          strokeWidth: 3,
          draggable: true
        });    

        var connector = new Kinetic.Line({
            drawFunc: function(canvas){
                var ctx=canvas.getContext();
                var x1=parentNode.getPosition().x;
                var y1=parentNode.getPosition().y;
                var x2=childNode.getPosition().x;
                var y2=childNode.getPosition().y;
                ctx.save();
                ctx.strokeStyle="red";
                ctx.lineWidth=3;
                ctx.beginPath();
                ctx.moveTo(x1,y1);
                ctx.lineTo(x2,y2);
                ctx.stroke();
                ctx.restore();
            },
            points: [1,1,1,3],
            stroke: "red",
            strokeWidth: 2,
            lineCap: 'round',
            lineJoin: 'round',
            opacity: 1,
            draggable:false
        });
        layer.add(connector);
        layer.add(parentNode);
        layer.add(childNode);

        // keep connector on rect1+rect2
        stage.getDragLayer().afterDraw(function() {
            connector.moveToBottom();
            layer.draw();
        });

        layer.draw();
    }

init();

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

</script>       
</head>

<body>
    <div id="container"></div>
</body>
</html>