开发者

How do I link and drag 2 Circle shapes in Raphael JS?

开发者 https://www.devze.com 2023-02-20 14:03 出处:网络
For some reason i can get this working with rectangle variables but not with circles. At the moment, this code allows both circles to be dragged independently but not together

For some reason i can get this working with rectangle variables but not with circles. At the moment, this code allows both circles to be dragged independently but not together

Anybody know how to fix this or an alterna开发者_Go百科tive method?

addIntermediateSymbol = function()
{
    var Intermediate = raphaelReference.set();
    Intermediate.push(
        raphaelReference.circle(74, 79, 20).attr({fill: "#ff7f00",stroke: "#000000",'stroke-width': 3}),
        raphaelReference.circle(74, 79, 10).attr({fill: "#ff7f00",stroke: "#000000",'stroke-width': 4})
        );

var start = function () {
    // storing original coordinates
    this.ox = this.attr("cx");
    this.oy = this.attr("cy");
},
move = function (dx, dy) {
    // move will be called with dx and dy
    this.attr({cx: this.ox + dx, cy: this.oy + dy});
},
up = function () {
    ;
};
Intermediate.drag(move, start, up);
}


You have to use Intermediate again in the drag functions (start, move, up), but with translate function (which make everybody in the set move in the same way):

var start = function () {
    Intermediate.oBB = Intermediate.getBBox();
},
move = function (dx, dy) {
    var bb = Intermediate.getBBox();
    Intermediate.translate(Intermediate.oBB.x - bb.x + dx, Intermediate.oBB.y - bb.y + dy);
},

See http://irunmywebsite.com/raphael/additionalhelp.php?v=1&q=anglebannersoncurves#PAGETOP (click on "Draggable Set" down of the right hand side list of examples)

It seems Intermediate.func() is just mapping the property func() to the elements inside of the set (applies to drag() and translate()), like:

for (var shape in Intermediate) {shape.func();}

About monkee answer:

  • As monkee points it out, in the dragging methods this references the clicked SVG object
  • Raphael sets don't have "cx" as such, so Intermediate.attr({cx:this.ox ... is working only if all the elements of the set are circles and have the same geometrical center ...


In the move function, "this" references to the clicked Raphäel object.

Instead of:

move = function (dx, dy) {
    this.attr({cx: this.ox + dx, cy: this.oy + dy});
}

Do this:

move = function (dx, dy) {
    Intermediate.attr({cx: this.ox + dx, cy: this.oy + dy});    
}

Bad formatted working example here: http://jsbin.com/uxege4/7/edit


Here is a helpful js Fiddle solution that does exactly what you want, adapted from http://www.irunmywebsite.com/raphael/additionalhelp.php?v=2#pagetop

http://jsfiddle.net/q4vUx/102/

var paper = Raphael('stage', 300, 300);
var r = paper.rect(50,100,30,50).attr({fill:"#FFF"}),
c = paper.circle(90,150,10).attr({fill:"#FFF"}),
t = paper.text(50, 140, "Hello");


var rr = paper.rect(200,100,30,50).attr({fill:"#FFF"}),
cc = paper.circle(240,150,10).attr({fill:"#FFF"}),
tt = paper.text(200, 140, "Hello");

var pp = paper.set(rr, cc, tt);
var p = paper.set(r, c, t);

r.set = p, c.set = p, t.set = p;
rr.set = pp, cc.set = pp, tt.set = pp;

p.newTX=0,p.newTY=0,p.fDx=0,p.fDy=0,p.tAddX,p.tAddY,p.reInitialize=false,
pp.newTX=0,pp.newTY=0,pp.fDx=0,pp.fDy=0,pp.tAddX,pp.tAddY,pp.reInitialize=false,
start = function () {

},
move = function (dx, dy) {
    var a = this.set;
    a.tAddX=dx-a.fDx,a.tAddY=dy-a.fDy,a.fDx=dx,a.fDy=dy;
    if(a.reInitialize)
    {
        a.tAddX=0,a.fDx=0,a.tAddY=0;a.fDy=0,a.reInitialize=false;
    }
    else
    {
        a.newTX+=a.tAddX,a.newTY+=a.tAddY;
        a.attr({transform: "t"+a.newTX+","+a.newTY});
    }

},
up = function () {
    this.set.reInitialize=true;
};
p.drag(move, start, up);
pp.drag(move, start, up);


I was running into all sort of problems too regards dragging sets around.

It does: - extends Raphael to make dragging sets possible - creates new sets with a mouse click - keeps the dragged set within the canvas boundaries.

The code in short:

CANVAS_WIDTH = 250;
CANVAS_HEIGHT = 250;
var newSet = document.getElementById("newSet");
paper = Raphael('canvas', CANVAS_WIDTH, CANVAS_HEIGHT);
var backGround = paper.rect(0,0,CANVAS_HEIGHT, CANVAS_WIDTH);
backGround.attr({fill: "lightgrey", "fill-opacity": 0.5, "stroke-width": 0});

newSet.onclick = function() {
    createNewSet();
}

createNewSet = function() {
  var mySet = paper.set();
  var rect = paper.rect(0, 0, 50, 50);
    rect.attr({fill: "red", "fill-opacity": 0.5, "stroke-width": 0});
  var bBox = rect.getBBox();  
  var text = paper.text(10, 10, "Hello");
    text.attr({fill: 'black', 'text-anchor': 'start'});

    mySet.push(rect, text);

    mySet.draggable();
    //mySet = reposText(mySet);
    mySet.max_x = CANVAS_WIDTH - bBox.width;
    mySet.min_x = 0;
    mySet.max_y = CANVAS_HEIGHT - bBox.height;
    mySet.min_y = 0;   
};

Raphael.st.draggable = function() {
  var me = this,
      lx = 0,
      ly = 0,
      ox = 0,
      oy = 0,
      moveFnc = function(dx, dy) {
        lx = dx + ox;
        ly = dy + oy;

        if (lx < me.min_x ) {
          lx = me.min_x;
        } 
        else if ( lx > me.max_x) {
          lx = me.max_x;
        }

        if ( ly < me.min_y ) {
          ly = me.min_y;
        } 
        else if ( ly > me.max_y) {
          ly = me.max_y;
        }

          me.transform('t' + lx + ',' + ly);
      },
      startFnc = function() {},
      endFnc = function() {
          ox = lx;
          oy = ly;
      };

  this.drag(moveFnc, startFnc, endFnc);
};

See this code in action here: http://jsfiddle.net/Alexis2000/mG2EL/ Good Luck!

0

精彩评论

暂无评论...
验证码 换一张
取 消