为了实现元素的添加,删除,拖拽,左键点击,右键单击,悬浮等功能,使用了d3 + svg 的技术来实现界面。

最开始是采用canvas,但是由于功能原因放弃了该技术,可以看下 canvas简介

另附:canvas和svg区别

首先,下载d3.min.js和snap.svg-min.js

如果使用的是bower,

安装d3,bower --allow-root install -S d3

安装svg,bower --allow-root install -S snap.svg

然后页面再引入。

新建画布主要有两种方式,

(1)html页面中

<svg id="svg_order" xmlns="http://www.w3.org/2000/svg" version="1.1" width="622px" height="417px">
</svg>

js中

var svg = Snap("#svg_order");
var rect = svg.paper.rect(hengwidth*widthOffest,shuwidth*heightOffest,imageWidth,imageHeight,imageRadius);
var text = svg.paper.text((hengwidth*widthOffest)+imageWidth/2-5, (shuwidth*heightOffest)+imageHeight/2, i+1);
var group = svg.paper.g(rect, text).attr({id:"groupId"+i,class:"groupClass"});

(2)html页面中

<div id="main_client_order">
</div>

js中

var svg = null;

        /*构建基础画布*/
function drawPanel(screenWidth, screenHeight) {
svg = d3.select('#main_client_order')
.append('svg:svg')
.attr('width', screenWidth+100)
.attr('height', screenHeight+100)
.style("margin-left", "20px")
.style("margin-top", "20px")
.attr("id", "orderId");
}
var addRect = svg.append("g");
addRect.append("rect");
addRect.append("text");

在画布上面开始画图

var addRect = svg.append("g");
addRect.append("rect");
addRect.append("text");
addRect.append("rect").style('visibility', 'hidden');(标记1)
addRect = addRect.call(drag);//给元素添加拖拽事件,拖拽事件需要定义在此代码之前。

给元素添加事件

悬浮事件和右键事件

addRect.on("contextmenu", function (data, index) {
//右键事件
d3.event.preventDefault();
}).on("mouseover", function (data, index) {
//悬浮事件 over
}).on('mouseleave', function () {
//悬浮事件 leave
});

拖拽事件(此方法要放在元素添加拖拽事件之前)

var drag = d3.behavior.drag()
.on('dragstart', function (d) {
//拖拽开始事件,需要通过标志位区分点击按下时和拖拽开始。
}).on('drag', function (d) {
//拖拽中事件,此时可以限制拖拽的边缘范围。
}).on('dragend', function (d) {
//拖拽结束事件,需要通过标志位区分点击松起时和拖拽结束。
});

事件实现概述

在界面中画图时,需要边画边在页面存入数据,我存入的数据是一个二维数组,a[i][j] i表示的是行 j表示的是列

var rect = "{id:'inner_" + id + "',x:" + startX + ",y:" + startY + ",type:" + colortype + ",highlight:"+highlighttype+"}";
var jsonRect = eval('(' + rect + ')');
var a1 = startX / widthOffset;
var a2 = startY / heightOffset;
if (gData[a2] == null) {
gData[a2] = new Array();
}
//存储元素的id,x,y
gData[a2][a1] = jsonRect;
//存储id备份值 只存储id (标记2)
var rect_id_bak = "{id:'inner_" + id + "'}";
var jsonRect_id_bak = eval('(' + rect_id_bak + ')');
if (gDataId_bak[a2] == null) {
gDataId_bak[a2] = new Array();
}
gDataId_bak[a2][a1] = jsonRect_id_bak;

只所以存储一个备份id,是为了保存行列元素与id值的对应。也就是第几行第几列的元素的id值。

针对以上的两次标记,解释如下:

  1.g元素是空元素,无法捕捉悬浮,点击,拖拽等事件。需要在等位置填充一个元素。目前是采用相同位置,相同长宽的方块来填充该位置。(对应标记1)

The g element is just an empty container which cannot capture click events,then appending an invisible rectangle to it as a place to hover over 来源:d3-js-mouseover-event-not-working-properly-on-svg-group

  2.g元素没有x,y值,移动g元素只能用transform(x,y)的方式。(对应标记2)

The <g>-element doesn't have x and y attributes. To move the contents of a <g>-element you can only do so using the transform attribute, using the "translate" function, like this: transform="translate(x,y)".来源:SVG g element

鼠标点击的mouse()方法只能获取在画布中的位置,根据该位置的行列,x除以长得到i,y除以宽得到j,然后再从备份数据gDataId_bak中,找到对应的id,然后再根据id在html中获取该元素的偏移量,也就是transform(x,y)中的x,y,相加之后得到实际位置的x,y,x除以长得到i,y除以宽得到j,然后再从gData中获取真正的元素。

需要注意几点:

  1.拖拽中,d3.event.x  d3.event.y可以获取真实位置信息。

  2.d3.event.sourceEvent.button 可以区分左右键点击事件,0 是左键 2是右键

  3.另附d3文档

svg + d3的更多相关文章

  1. D3+svg 案例

    <!doctype html><html lang="en"><head> <meta charset="UTF-8" ...

  2. [D3] 2. Basics of SVG

    1. svg should use 'fill' prop instead 'background-color'2. svg width & height no need 'px'3. att ...

  3. 【D3.V3.js系列教程】--(十五)SVG基本图形绘制

    [D3.V3.js系列教程]--(十五)SVG基本图形绘制 1.path <!DOCTYPE html> <html> <head> <meta charse ...

  4. D3中的each() 以及svg defs元素 clipPath的使用

    each() 方法允许我们定制对选择集中DOM元素的处理行为: selection . each ( func ) 参数 func 是调用者定义的函数,在d3中被称为 访问器/accessor . d ...

  5. D3.js & Data Visualization & SVG

    D3.js & Data Visualization & SVG https://davidwalsh.name/learning-d3 // import {scaleLinear} ...

  6. angular7 + d3 显示svg

    汇总一些之前没有注意到的问题 总体思路: app只是显示svg为主,接收后端推送的数据改变,显示变化后的svg. 因此,只用d3的数据绑定更新组件里<svg></svg>节点. ...

  7. 使用d3.v3插件绘制出svg图

    众所周知,这个插件使用的svg技术,而IE8(包括IE8)之前的浏览器是不支持svg的 接下来看代码吧 从后台获取到带id和父id的目录数据[json格式] var module = requestU ...

  8. SVG基础图形和D3.js

    使用D3.js画一个SVG 的 圆 circle 可以使用如下代码创建: <svg width="50" height="50"> <circ ...

  9. D3——绘制SVG图形-直方图

    1.创建SVG元素 var svg = d3.select("body").append("svg"); 2.为SVG元素设置属性 svg.attr() .at ...

随机推荐

  1. [LeetCode] First Unique Character in a String 字符串第一个不同字符

    Given a string, find the first non-repeating character in it and return it's index. If it doesn't ex ...

  2. [LeetCode] Sum of Two Integers 两数之和

    Calculate the sum of two integers a and b, but you are not allowed to use the operator + and -. Exam ...

  3. [翻译] Android是怎样绘制视图的

    原文:How Android Draws Views 当一个Activity获取到焦点的时候,它的布局就开始被绘制. 绘制的过程由Android framework处理.但布局层级的根节点必须由Act ...

  4. 如何做好PMO,PMO分哪些方面?

    谢邀! 理论的东西,中国PMO大会的帐号说的很全面了. 我分享一些个人感受.失败经验: 我曾帮助中国区COO创立过PMO并且运营两年,COO离职后终止. 成功案例: 我曾看过总部老大们设立Busine ...

  5. NSRunLoop

    1.什么是RunLoop 运行循环 一个线程对应一个RunLoop,主线程的RunLoop默认已经启动,子线程的RunLoop得手动启动(调用run方法) RunLoop只能选择一个Mode启动,如果 ...

  6. Tomcat内存溢出的三种情况及解决办法分析

    Tomcat内存溢出的原因 在生产环境中tomcat内存设置不好很容易出现内存溢出.造成内存溢出是不一样的,当然处理方式也不一样. 这里根据平时遇到的情况和相关资料进行一个总结.常见的一般会有下面三种 ...

  7. CSS实例练习

    蓝色导航为图片,用background-image实现. 排版用到ul,li标签,下划线运用border-bottom中的dashed,右边文字用到CSS浮动float. 实例: 代码: <!D ...

  8. MathType6.9按章节插入编号

    先插入Chapter,然后修改break主要是该起始编号. 这样话会用一行红色红代码,选中,邮件字体,然后在格式里选择隐藏就好了,这个不能删除.

  9. [半转]1px边框 移动端

    半转的意思是借鉴参考,搬砖,加了一些自己的想法. 在移动端里,因为存在2倍像素的问题,所以很多时候,移动端上的1px边框并不是意义上的.从下图红色框看到dpr:2.0 ,表示1px等于2倍的物理像素. ...

  10. C#知识点记录

    用于记录C#知识要点. 参考:CLR via C#.C#并发编程.MSDN.百度 记录方式:读每本书,先看一遍,然后第二遍的时候,写笔记. CLR:公共语言运行时(Common Language Ru ...