html5利用canvas绘画二级树形结构图的示例


Posted in HTML / CSS onSeptember 27, 2017

上周需要做一个把页面左侧列表内容拖拽到右侧区域,并且绘制成关系树的功能。

看了设计图,第一反应是用canvas绘制关系线。

吭哧吭哧搞定这个功能后,发现用canvas绘图,有一个很严重的缺陷。那就是如果左侧关系特别多,需要绘制成百上千条时,而canvas画布的宽高在写dom的时候就已声明。关系很多的情况下,无法使用canvas。

不过还是记录一下研究成果。

下面是设计图:

html5利用canvas绘画二级树形结构图的示例

做出效果如下:

html5利用canvas绘画二级树形结构图的示例

html、css代码就不贴了。 js主要用到了拖拽、canvas绘制。

function startDrag(ev) {
    ev.dataTransfer.setData("Text",ev.target.innerText);
}

function allowDrop(ev) {
    ev.preventDefault();
}

function decideDrop(ev) {
    ev.preventDefault();
    var length = $('.main-target').length;
    if(length == 0){
        dropToMain(ev);
    }else {
        dropToRelate(ev);
    }
}

function dropToMain(ev) {
    var data=ev.dataTransfer.getData("Text");
    var _html = '<div class="main-target">' + data + '</div>';
    $('.main-target-wrap').width('auto').append(_html);
}

function dropToRelate(ev) {
    //画关系线
    drawLineOne(document.getElementById('canvasOne'), 'begin');
    drawLineOne(document.getElementById('canvasTwo'), 'end');

    //插入图片 以及图片初始化点击事件
    var _img = $('<img src="inner.png">');
    $('.imgBox').append(_img);
    _img.click(showRelationBox);
    //写入数据
    var data = ev.dataTransfer.getData('Text');
    var _html = '<div class="item-text">' + data + '</div>';
    $('.relation-text-box').append(_html);
}

以上是拖拽的方法,我也是一边看菜鸟教程,一边写出的拖拽方法。

function drawLineOne(canvas, flag) {
    var context = canvas.getContext('2d');
    var position = {};
    if(flag == "begin"){
        position = getCanvasOnePosition();
    }else {
        position = getCanvasTwoPosition();
    }
    context.beginPath();
    context.moveTo(position.beginX, position.beginY);
    context.lineTo(position.endX, position.endY);
    if(position.endX2 && position.endY2){
        context.lineTo(position.endX2, position.endY2);
    }
    context.strokeStyle = "#333";
    context.stroke();
}

/**
 * 左侧关系线
 * @returns {{beginX: *, beginY: *, endX: *, endY: *}}
 */
function getCanvasOnePosition() {
    var imgLength = $('.imgBox img').length;
    var beginX = (imgLength == 0) ? 0 : 77,
        beginY = (imgLength == 0) ? 15 : (15 + 60 * (imgLength-1)),
        endX = (imgLength == 0) ? 155 : 77,
        endY = 60*imgLength + 15;
    var position = {beginX: beginX, beginY: beginY, endX: endX, endY: endY};
    if(imgLength > 0){
        position.endX2 = 155;
        position.endY2 = endY;
    }
    return position;
}

function getCanvasTwoPosition() {
    var imgLength = $('.imgBox img').length;
    var endY = 15 + 60*imgLength
    return {beginX: 0, beginY: endY, endX: 155, endY: endY}
}

以上是canvas画线的方法,代码没什么难点,主要就是分析线的起始坐标麻烦一些。希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

HTML / CSS 相关文章推荐
纯CSS3发光分享按钮的实现教程
Sep 06 HTML / CSS
纯CSS3实现自定义Tooltip边框涂鸦风格的教程
Nov 05 HTML / CSS
CSS3实现文本垂直排列的方法
Jul 10 HTML / CSS
解决img标签上下出现间隙的方法
Dec 14 HTML / CSS
localStorage 设置过期时间的方法实现
Dec 21 HTML / CSS
HTML5几个设计和修改的页面范例分享
Sep 29 HTML / CSS
Html5在手机端调用相机的方法实现
May 13 HTML / CSS
amazeui页面分析之登录页面的示例代码
Aug 25 HTML / CSS
css position fixed 左右双定位的实现代码
Apr 29 HTML / CSS
Html5获取用户当前位置的几种方式
Jan 18 HTML / CSS
table不让td文字溢出操作方法
Dec 24 HTML / CSS
使用CSS实现按钮边缘跑马灯动画
May 07 HTML / CSS
html5新增的定时器requestAnimationFrame实现进度条功能
Dec 13 #HTML / CSS
详解使用HTML5的classList属性操作CSS类
Oct 13 #HTML / CSS
HTML5网页音乐播放器的示例代码
Nov 09 #HTML / CSS
js实现移动端H5页面手指滑动刻度尺功能
Nov 16 #HTML / CSS
HTML5实现视频直播功能思路详解
Nov 16 #HTML / CSS
基于HTML5 Canvas 实现商场监控实例详解
Nov 20 #HTML / CSS
微信浏览器左上角返回按钮拦截功能
Nov 21 #HTML / CSS
You might like
php获取url参数方法总结
2014/11/13 PHP
JS 学习笔记 防止发生命名冲突
2009/07/30 Javascript
深入理解JavaScript系列(9) 根本没有“JSON对象”这回事!
2012/01/15 Javascript
JavaScript之Getters和Setters 平台支持等详细介绍
2012/12/07 Javascript
document.documentElement的一些使用技巧
2013/04/18 Javascript
JS解析XML文件和XML字符串详解
2015/04/17 Javascript
js实现简单的联动菜单效果
2015/08/19 Javascript
jQuery实现网页顶部固定导航效果代码
2015/12/24 Javascript
Reactjs实现通用分页组件的实例代码
2017/01/19 Javascript
node.js支持多用户web终端实现及安全方案
2017/11/29 Javascript
webstorm中配置nodejs环境及npm的实例
2018/05/15 NodeJs
Javascript中弹窗confirm与prompt的区别
2018/10/26 Javascript
JS字典Dictionary类定义与用法示例
2019/02/01 Javascript
vue计算属性computed的使用方法示例
2019/03/13 Javascript
vue实现axios图片上传功能
2019/08/20 Javascript
uniapp微信小程序实现一个页面多个倒计时
2020/11/01 Javascript
vue组件中节流函数的失效的原因和解决方法
2020/12/02 Vue.js
在python的WEB框架Flask中使用多个配置文件的解决方法
2014/04/18 Python
使用tensorflow实现线性svm
2018/09/07 Python
浅谈python str.format与制表符\t关于中文对齐的细节问题
2019/01/14 Python
Python3实现统计单词表中每个字母出现频率的方法示例
2019/01/28 Python
对Python 多线程统计所有csv文件的行数方法详解
2019/02/12 Python
Python selenium文件上传下载功能代码实例
2020/04/13 Python
html5使用Drag事件编辑器拖拽上传图片的示例代码
2017/08/22 HTML / CSS
Belvilla德国:在线预订度假屋
2018/04/10 全球购物
美国高档帽子网上商店:Hats.com
2018/08/09 全球购物
会计主管岗位职责范文
2013/11/08 职场文书
计算机网络及管理学专业求职信
2014/06/05 职场文书
护士找工作求职信
2014/07/02 职场文书
普通党员对照检查材料
2014/08/28 职场文书
群众路线剖析材料
2014/09/30 职场文书
办理收楼委托书范本
2014/10/09 职场文书
酒店收银员岗位职责
2015/04/07 职场文书
公司欠款证明
2015/06/24 职场文书
简历自我评价:教师师德表现自我评价
2019/04/24 职场文书
详解Python中下划线的5种含义
2021/07/15 Python