Javascript 如何创建JQuery/svg单击-拖动-选择大纲效果?

Javascript 如何创建JQuery/svg单击-拖动-选择大纲效果?,javascript,jquery,svg,frontend,Javascript,Jquery,Svg,Frontend,我不确定该怎么称呼它,但我正在寻找一种方法,当你点击并拖动一个区域,然后在鼠标上消失(如果它不是原始部分,可以添加)时,通过javascript/svg创建一个虚线轮廓/选择框效果 如果jQuery库存在的话,它会很好。我四处找了找,但还没有找到我要找的东西。 我猜理论是从第一次点击中获得坐标,跟踪鼠标坐标,并相应地调整框 但是不从头开始写就好了。你很幸运我自己做的。我正在使用jQuerySVG插件() paper2是一个div,其中有一个svg元素(因此svg元素和div具有相同的高度/宽度)

我不确定该怎么称呼它,但我正在寻找一种方法,当你点击并拖动一个区域,然后在鼠标上消失(如果它不是原始部分,可以添加)时,通过javascript/svg创建一个虚线轮廓/选择框效果

如果jQuery库存在的话,它会很好。我四处找了找,但还没有找到我要找的东西。
我猜理论是从第一次点击中获得坐标,跟踪鼠标坐标,并相应地调整框


但是不从头开始写就好了。

你很幸运我自己做的。我正在使用jQuerySVG插件()

paper2是一个div,其中有一个svg元素(因此svg元素和div具有相同的高度/宽度)。以下是我创建svg2元素的方式:

var svg2;
var root2;
$(document).ready(function() {
    $("#paper2").svg({
        onLoad: function() {
            svg2= $("#paper2").svg('get');
            svg2.configure({id: 'svg2'});
            var div= $("#paper2");
            root2= svg2.root();
            $("#svg2").attr("viewBox", viewBox[0]+','+viewBox[1]+','+viewBox[2]+','+viewBox[3]);    
        },
        settings: {}
    });
}
如果未在svg元素上使用viewbox,则在计算中不需要:

 * viewBox[2]/parseInt($("#paper2").css("*****"));

viewbox[2]将是viewbox宽度,viewbox[3]将是viewbox高度。

这是我为您制作的演示:)

演示(静态): 演示(动画): 您可以使用CSS来控制字幕的视觉样式。 您可以将一个或两个函数传递给
trackMarquee
方法;这两个函数都将用四个参数调用:选框的x1、y1、x2、y2边界。释放选框时将调用第一个函数。第二个函数(如果存在)将在字幕每次移动时调用(例如,您可以计算该边界框内的项目)

当您开始拖动SVG文档(或您选择跟踪的任何元素)时,它将创建一个
;在拖动过程中,它将调整矩形的大小。使用CSS(如演示中所示)根据需要设置此矩形的样式。我正在用这个属性把边界弄虚作假

对于堆栈溢出的后代,下面是代码(在JSFIDLE关闭的情况下):

(函数createMarquee(全局){
var svgNS=http://www.w3.org/2000/svg',
svg=document.createElements(svgNS,'svg'),
pt=svg.createSVGPoint();
//用法:trackMarquee(mySVG,function(x1,y1,x2,y2){},function(x1,y1,x2,y2){});
//释放选框时将调用第一个函数(如果存在)
//第二个函数(如果存在)将在选框更改时调用
//使用CSS选择器'rect.marquee'选择用于视觉样式的字幕
global.trackMarquee=函数(forElement、onRelease、onDrag){
addEventListener('mousedown',函数(evt){
var point0=getLocalCoordinates fromMouseeEvent(forElement,evt);
var marquee=document.createElements(svgNS,'rect');
setAttribute('class','marquee');
updateMarquee(选框、点0、点0);
附加子元素(选框);
document.documentElement.addEventListener('mousemove',trackMouseMove,false);
document.documentElement.addEventListener('mouseup',stopTrackingMove,false);
函数trackMouseMove(evt){
var point1=getLocalCoordinates fromMouseeEvent(forElement,evt);
updateMarquee(选框,点0,点1);
if(onDrag)调用bbox(onDrag,marquee);
}
函数stopTrackingMove(){
document.documentElement.removeEventListener('mousemove',trackMouseMove,false);
document.documentElement.removeEventListener('mouseup',stopTrackingMove,false);
forElement.removeChild(选框);
if(onRelease)callWithBBox(onRelease,marquee);
}
},假);
};
函数调用WithBBox(func,rect){
var x=rect.getAttribute('x')*1,
y=rect.getAttribute('y')*1,
w=rect.getAttribute('width')*1,
h=rect.getAttribute('height')*1;
func(x,y,x+w,y+h);
}
函数updateMarquee(rect、p0、p1){
var xs=[p0.x,p1.x].sort(sortByNumber),
ys=[p0.y,p1.y]。排序(sortByNumber);
rect.setAttribute('x',xs[0]);
rect.setAttribute('y',ys[0]);
rect.setAttribute('width',xs[1]-xs[0]);
rect.setAttribute('height',ys[1]-ys[0]);
}
函数GetLocalCoordinates fromMouseeEvent(el,evt){
pt.x=evt.clientX;pt.y=evt.clientY;
返回pt.matrixTransform(el.getScreenCTM().inverse());
}
函数sortByNumber(a,b){返回a-b}
})(窗口);

您要查找的术语是“字幕”,或者可能是。您希望在绘制时对其设置动画,还是仅使用虚线边框?需要用点吗?(请注意,Windows 7只是使用了一个半透明的矩形,其拖动选择具有更不透明的笔划。)选择框大小只需在被选择时更改-动画不重要-用户应用程序界面的一部分您可能对我的答案中的
GetLocalCoordinates fromMouseeEvent
函数感兴趣,由于这可以处理viewBox缩放,所以可以将任意嵌套转换为您可能需要鼠标点的任何元素。对于只在根
上跟踪选框的常见情况来说,这不是必需的,但是非常通用,因此可以处理所有情况,可能是在翻译和可缩放的子绘图区域中的选框。你知道Phrogz我正在寻找一个可以做到这一点的函数,我如何在jQuery回调中使用它?在使用jquery时,我尽量避免使用.get()和直接操作DOM元素。该方法需要访问临时的
SVGPoint
;虽然我恰好创建了一个我关闭的,但您也可以这样做:
jQuery.fn.svgCoordsFromEvent=function cursorLoc(evt){var pt=this[0].ownerSVGElement.createSVGPoint();pt.x=evt.clientX;pt.y=evt.clientY;return pt.matrixTransform(this[0].getScreenCTM().inverse())谢谢Phrogz,这真的很有用,甚至在我对整个文档使用CSS转换后它也能工作(这是我遇到的一个问题)。你真的应该和jQuerySVG插件的作者谈谈,让他添加这个小函数
 * viewBox[2]/parseInt($("#paper2").css("*****"));