0

参考https://jqueryui.com/draggable/我能够在父元素(例如 div)中实现拖放功能。但是我需要让这个可拖动的功能在多边形元素(如 SVG 多边形)中工作。我一直在网上搜索,但是有一些示例说明如何使 svg 多边形可拖动,但不是“如何在多边形父级 (div) 中包含拖放功能。

任何想法/指针都会有所帮助。

谢谢。

4

1 回答 1

0

简短的故事是您需要一个函数来检查一个点是否在多边形内,然后检查可拖动对象的四个角是否在该形状内。

这是一个粗略的例子,使用来自 jQuery 的可拖动样本,以及来自 this answer 的多边形函数中的一个点。这个例子远非完美,但我希望它能为您指明正确的方向。

// These are the points from the polygon
var polyPoints = [
  [200, 27],
  [364, 146],
  [301, 339],
  [98, 339],
  [35, 146]
];

$("#draggable").draggable({
  drag: function(e, ui) {
    var element = $("#draggable")[0];
    var rect = element.getBoundingClientRect();
    var rectPoints = rect2points(rect);
    
    let inside = true;
    rectPoints.forEach(p => {
      if(!pointInside(p, polyPoints)){
        inside = false;
      }
    });
    $("#draggable")[inside ? 'addClass' : 'removeClass']('inside').text(inside ? 'Yay!' : 'Boo!');
  }
});

function rect2points(rect) {
  return ([
    [rect.left, rect.top],
    [rect.right, rect.top],
    [rect.right, rect.bottom],
    [rect.left, rect.bottom]
  ]);
};

function pointInside(point, vs) {
  var x = point[0],
    y = point[1];

  var inside = false;
  for (var i = 0, j = vs.length - 1; i < vs.length; j = i++) {
    var xi = vs[i][0],
      yi = vs[i][1];
    var xj = vs[j][0],
      yj = vs[j][1];

    var intersect = ((yi > y) != (yj > y)) &&
      (x < (xj - xi) * (y - yi) / (yj - yi) + xi);
    if (intersect) inside = !inside;
  }

  return inside;
};
#draggable {
  width: 100px;
  height: 80px;
  background: red;
  position: absolute;
  text-align: center;
  padding-top: 20px;
  color:#fff;
}
#draggable.inside{
  background: green;
}
html, body{
  margin: 0;
}
<script src="//code.jquery.com/jquery-1.12.4.js"></script>
<script src="//code.jquery.com/ui/1.12.1/jquery-ui.js"></script>


<div id="draggable">Drag me</div>
<svg width="400px" height="400px" viewBox="0 0 400 400">
  <rect width="600" height="600" fill="#efefef"></rect>
  <polygon points="200,27 364,146 301,339 98,339 35,146" fill="rgba(255,200,0, 1)" stroke="rgba(255,0,0,0.2" stroke-width="2"></polygon>
</svg>

于 2019-03-08T18:30:10.853 回答