d3-drag, 使用鼠标或者触摸输入拖放 SVG,HTML或者画布

分享于 

16分钟阅读

GitHub

  繁體 雙語
Drag and drop SVG, HTML or Canvas using mouse or touch input.
  • 源代码名称:d3-drag
  • 源代码网址:http://www.github.com/d3/d3-drag
  • d3-drag源代码文档
  • d3-drag源代码下载
  • Git URL:
    git://www.github.com/d3/d3-drag.git
    Git Clone代码到本地:
    git clone http://www.github.com/d3/d3-drag
    Subversion代码到本地:
    $ svn co --depth empty http://www.github.com/d3/d3-drag
    Checked out revision 1.
    $ cd repo
    $ svn up trunk
    
    d3-drag

    Drag-and-drop 是一种流行且easy-to-learn的指针手势: 将指针移动到对象,按住并按住它,将对象"拖动"移到新位置,然后释放到"放置"。 drag-and-drop拖动行为为在选择上启用交互提供了一个方便但灵活的抽象。 例如可以使用d3-drag来促进与力定向图的交互,或者模拟碰撞圆:

    Force Dragging IIIForce Dragging II

    你还可以使用d3-drag实现自定义用户界面元素,例如 slider。 但是拖动行为不仅仅是为了周围移动元素;有多种方法可以响应拖动手势。 例如,可以将它用于散列图中的索引元素,或者在画布上绘制线条:

    Line Drawing

    拖动行为可以与其他行为相结合,比如 d3-zoom 用于缩放。

    Drag & Zoom II

    拖动行为对DOM是不可知的,所以你可以将它的与 SVG。HTML甚至画布一起使用 ! 可以使用高级选择技术,如Voronoi叠加或者最近的目标搜索来扩展它:

    Circle Dragging IVCircle Dragging II

    最重要的是,拖动行为自动统一鼠标和触摸输入,并避免浏览器的特性。 当指针事件更广泛可用时,拖动行为也将支持这些事件。

    安装

    如果你使用 NPM,npm install d3-drag。 否则,下载最新版本的。 你也可以直接从 d3js.org 加载,或者作为一个独立库,或者作为D3 4.0的一部分。 支持 AMD,CommonJS和香草环境。 在vanilla中,导出了一个 d3 全局:

    <scriptsrc="https://d3js.org/d3-dispatch.v1.min.js"></script>
    <scriptsrc="https://d3js.org/d3-selection.v1.min.js"></script>
    <scriptsrc="https://d3js.org/d3-drag.v1.min.js"></script>
    <script>var drag =d3.drag();</script>

    在浏览器中尝试 d3-drag。

    API参考

    这里 table 描述拖动行为如何解释本机事件:

    事件侦听元素拖动事件默认值阻止?
    选择开始
    拖动是的
    结尾是的
    窗口-是的
    窗口-是的
    窗口-是的
    touchstart选择开始
    touchmove选择拖动是的
    touchend选择结尾
    touchcancel选择结尾

    所有消费事件的传播都立即停止,立即停止。 如果要防止某些事件引发拖动笔势,请使用 drag drag。





    # d3.drag() <>

    创建新的拖动行为。 返回的行为,即 drag drag,是一个对象和函数,通常通过选择应用到选定元素。调用。

    # drag(selection) <>

    将这里拖动行为应用于指定的 选择。 通常不会直接调用这个函数,而是通过选择调用调用。 例如要实例化拖动行为并将它的应用到选择:

    d3.selectAll(".node").call(d3.drag().on("start", started));

    在内部,拖动行为使用 选择 on在上绑定必要的事件侦听器来进行拖动。 侦听器使用名称 .drag,因此可以随后取消对拖动行为的取消绑定,如下所示:

    selection.on(".drag", null);

    应用拖动行为还将 -webkit-tap-highlight-color 样式设置为透明,禁用iOS上的tap Highlight。 如果你想要不同的点击 Highlight 颜色,请删除或者应用这里样式应用拖动行为后。

    # drag.container( [container] ) <>

    指定容器访问器,将容器访问器设置为指定对象或者函数,并返回拖动行为。 如果未指定容器,则返回当前容器访问器,该访问器默认为:

    functioncontainer() {
     returnthis.parentNode;
    }

    拖放动作的容器决定后续拖动事件的坐标系,影响事件和事件。 容器访问器返回的元素随后传递给 d3.mouse 或者 d3.touch,适当地确定指针的本地坐标。

    默认容器访问器返回原始选择( 请参见 拖动 ) 中接收起始输入事件的元素的父 node。 当拖动SVG或者HTML元素时,这通常是合适的,因为这些元素通常是将 relative 定位到。 但是,对于使用画布拖动图形元素,你可能需要将容器重定义为起始元素本身:

    functioncontainer() {
     returnthis;
    }

    或者,容器可以直接指定为元素,例如 drag.container(canvas)

    # drag.filter( [filter] ) <>

    在指定了过滤器时,将过滤器设置为指定的函数并返回拖动行为。 如果未指定筛选器,则返回当前筛选器,默认为:

    functionfilter() {
     return!d3.event.button;
    }

    如果筛选器返回 falsey,则忽略初始化事件,并且不启动拖动手势。 因这里,筛选器决定忽略哪些输入事件;默认筛选器忽略二次按钮上的,事件。

    # drag.touchable( [touchable] ) <>

    如果指定了触摸屏,则将触摸支持检测器设置为指定函数并返回拖动行为。 如果未指定触摸屏,则返回当前触摸支持检测器,默认为:

    functiontouchable() {
     return"ontouchstart"inthis;
    }

    只有在应用了drag时,如果探测器返回对应元素的truthy,触摸事件监听器才注册。 默认检测器适用于能够触摸输入的大多数浏览器,但不是全部,而是 Chrome 设备 模拟器。

    # drag.subject( [subject] ) <>

    在指定主题时,将主题访问器设置为指定对象或者函数,并返回拖动行为。 如果未指定主题,则返回当前主题访问器,该访问器默认为:

    functionsubject(d) {
     return d ==null? {x:d3.event.x, y:d3.event.y} : d;
    }

    拖动手势的主题表示被拖动的事物。 当接收到一个初始输入事件,如或者touchstart之后,在拖动手势启动之前计算它。 主题随后被公开为事件。在随后的拖动事件中,主题将被。

    default originating originating selection originating originating originating originating originating originating originating originating originating originating default default created created created created。 在SVG中拖动圆元素时,默认的主题是被拖动的圆的数据。 使用画布,默认主题是元素( 无论你在画布上的位置)的画布基准。 这样,自定义主题访问器更合适,例如在给定搜索范围内,将最近的圆圈拾取到鼠标的方法:

    functionsubject() {
     var n =circles.length,
     i,
     dx,
     dy,
     d2,
     s2 = radius * radius,
     circle,
     subject;
     for (i =0; i < n; ++i) {
     circle = circles[i];
     dx =d3.event.x-circle.x;
     dy =d3.event.y-circle.y;
     d2 = dx * dx + dy * dy;
     if (d2 < s2) subject = circle, s2 = d2;
     }
     return subject;
    }

    ( 如有必要,可以使用 quadtree 加速 上面。)

    返回的主体应该是公开 xy 属性的对象,以便在拖动手势期间保留主题和指针的relative 位置。 如果主题为空或者未定义,则不会为此指针启动拖动笔势;但是,其他开始触摸可能会开始拖动手势。 请参见 。拖动

    手势启动后,拖动手势的主题可能无法更改。 使用与 选择相同的上下文和参数调用主题访问器。在上: 当前基准 d 和索引 i,以 this 上下文作为当前DOM元素。 在对主题访问器进行评估期间,d3.event 是一个 beforeStart 拖动事件。 使用事件。sourceEvent访问起始输入事件和事件identifier以访问触摸标识符。 用户定义事件和事件是 relative 到容器,使用 d3.mouse 或者d3.touch 计算。

    # drag.clickDistance( [distance] ) <>

    在指定距离时,设置鼠标在将触发后续单击事件的mousedown和mouseup之间移动的最大距离。 在mousedown和mouseup之间,鼠标在mousedown上的位置大于或者等于距离,click的click事件将被抑制。 如果没有指定距离,则返回当前距离阈值,默认为零。 距离阈值在客户端坐标( 事件事件。clientX事件。clientY ) 中测量。

    # drag.on(typenames, [listener] ) <>

    如果指定了侦听器,则为指定的typenames设置事件侦听器并返回拖动行为。 如果事件侦听器已经注册为同一类型和名称,则在添加新侦听器之前将删除现有侦听器。 如果侦听器为空,则移除指定的typenames的当前事件侦听器,如果有。 如果未指定侦听器,则返回与指定的typenames匹配的第一个当前分配的侦听器( 如果有)。 当指定指定事件时,将使用与 选择相同的上下文和参数来调用每个侦听器在 - 侦听器上: 当前基准 d 和索引 i,以 this 上下文作为当前DOM元素。

    typenames是一个包含一个或者多个typename的字符串,它由空格分隔。 each名称为 ,可以选择 followed ( . ) period period period name,例如 drag.foodrag.bar,名称允许多个侦听器注册为同一类型。 类型必须是下列类型之一:

    • start - 在新指针变为活动的( 在mousedown或者touchstart上) 之后。
    • drag - 活动指针移动( 在mousemove或者touchmove上) 后。
    • end - 在活动指针变为非活动的(。在 mouseup,touchend或者touchcancel上) 之后。

    有关更多信息,请参见 调度。

    在拖动手势的过程中对已经注册的侦听器进行更改。在拖动笔势 ,不会影响当前拖动动作。 相反,你必须使用事件,它还允许你对当前拖动手势中的临时事件侦听器进行 register 操作。 在拖动笔势中,为每个活动指针分配单独的事件。 例如,如果同时拖动多个手指,则每个手指都会发送一个开始事件,即使手指同时触摸。 有关更多信息,请参见拖动事件

    # d3.dragDisable(window) <>

    防止在指定窗口中的本机drag-and-drop和文本选择 。 作为防止mousedown事件( 请参见 #9 ) 默认动作的替代方法,这里方法防止在mousedown之后的不希望的默认操作。 在支持的浏览器中,这意味着捕获dragstart和selectstart事件,阻止关联的默认操作,并立即停止。 在不支持选择事件的浏览器中,用户选择CSS属性在文档元素上设置为无。 这里方法用于在mousedown上调用,然后在mouseup上调用 d3.dragEnable

    # d3.dragEnable(window [, noclick] ) <>

    指定窗口中的本机drag-and-drop和文本选择;撤消 d3.dragDisable的效果。 这里方法打算在mousedown之前调用 mouseup,前面是 d3.dragDisable。 如果 noclick 为 true,这里方法也会暂时取消单击事件。 在零毫秒超时之后,禁止对单击事件进行抑制,这样它只会阻止单击,事件。

    拖动事件

    在调用拖动事件侦听器时, d3.event 被设置为当前拖动事件。 事件对象公开了几个字段:

    • target 关联拖动行为
    • type - string,"拖动"或者"结尾";参见 drag。
    • subject - 拖动主题,由 drag drag。
    • x - subject subject subject subject subject subject -coordinate see see drag drag drag. container。
    • y - new subject subject subject subject -coordinate see drag drag drag drag. container。
    • dx - 自上一次拖动事件以来,x -coordinate的变化。
    • dy - 自上次拖动事件后, y的变化。
    • identifier - 字符串"鼠标",或者数字触摸标识符
    • active - 当前活动的拖动手势的数目( 在开始和结束时,不包括这个)。
    • sourceEvent - 基础输入事件,如mousemove或者 touchmove。

    在concurrent活动gestures中检测第一个启动事件和最后一个结束事件,活动字段是有用的。 当第一个拖动手势开始时为零,当最后一个拖动手势结束时为零。

    事件对象还公开了事件 on on方法。

    # event.on(typenames, [listener] ) <>

    等效,拖动。在上,但仅适用于当前拖动笔势。 在拖动手势开始之前,将生成当前拖动事件侦听器的一个复制。 这里副本绑定到当前拖动笔势,并由事件 modified。 对于只接收当前拖动手势事件的临时侦听器,这非常有用。 例如这里启动事件侦听器将临时拖动和结束事件侦听器注册为闭包:

    functionstarted() {
     var circle =d3.select(this).classed("dragging", true);
     d3.event.on("drag", dragged).on("end", ended);
     functiondragged(d) {
     circle.raise().attr("cx", d.x=d3.event.x).attr("cy", d.y=d3.event.y);
     }
     functionended() {
     circle.classed("dragging", false);
     }
    }

    CAN  SVG  触摸  Canvas  输入  拖动  
    相关文章