zoukankan      html  css  js  c++  java
  • 使用vue+vis.js实现关系图的任意拖拽,编辑等功能

    步骤

    1. 根据官网,进行安装(旧版)
    2. npm install vis(旧版)
    3. npm install vis-network(新版)
    4. 装好之后,在main.js(获取其他名称,入口的js文件即可引入vis的css)

        import 'iview/dist/styles/iview.css'

    1. 在关系图的页面引入vis

      

            import Vis from 'vis'
    1. html中定义容器

    <div id="network_id" class="network" style="height:800px"></div>

    在script中,定义所需变量,这里需要注意的是,network不可以在data中进行定义,否则会出现拖拽节点的时候,其他节点不跟随变换位置的bug

      export default {

           name: 'home',

          data () {

                 return {

                     nodes:[],

                     edges:[],

                    // network:null,

                     container:null,

                     nodesArray:[

                         {id: 0, label: "0", group: 0},

                         {id: 1, label: "1", group: 0},

                         {id: 2, label: "2", group: 0},

                         {id: 3, label: "3", group: 1},

                         {id: 4, label: "4", group: 1},

                         {id: 5, label: "5", group: 1},

                         {id: 6, label: "6", group: 2},

                         {id: 7, label: "7", group: 2},

                         {id: 8, label: "8", group: 2},

                         {id: 9, label: "9", group: 3},

                         {id: 10, label: "10", group: 3},

                         {id: 11, label: "11", group: 3},

                         {id: 12, label: "12", group: 4},

                         {id: 13, label: "13", group: 4},

                         {id: 14, label: "14", group: 4},

                         {id: 15, label: "15", group: 5},

                         {id: 16, label: "16", group: 5},

                         {id: 17, label: "17", group: 5},

                         {id: 18, label: "18", group: 6},

                         {id: 19, label: "19", group: 6},

                         {id: 20, label: "20", group: 6},

                         {id: 21, label: "21", group: 7},

                         {id: 22, label: "22", group: 7},

                         {id: 23, label: "23", group: 7},

                         {id: 24, label: "24", group: 8},

                         {id: 25, label: "25", group: 8},

                         {id: 26, label: "26", group: 8},

                         {id: 27, label: "27", group: 9},

                         {id: 28, label: "28", group: 9},

                         {id: 29, label: "29", group: 9}

                     ],

                     edgesArray:[

                         {from: 1, to: 0,label:"hahah"},

                         {from: 2, to: 0},

                         {from: 4, to: 3},

                         {from: 5, to: 4},

                         {from: 4, to: 0},

                         {from: 7, to: 6},

                         {from: 8, to: 7},

                         {from: 7, to: 0},

                         {from: 10, to: 9},

                         {from: 11, to: 10},

                         {from: 10, to: 4},

                         {from: 13, to: 12},

                         {from: 14, to: 13},

                         {from: 13, to: 0},

                         {from: 16, to: 15},

                         {from: 17, to: 15},

                         {from: 15, to: 10},

                         {from: 19, to: 18},

                         {from: 20, to: 19},

                         {from: 19, to: 4},

                         {from: 22, to: 21},

                         {from: 23, to: 22},

                         {from: 22, to: 13},

                         {from: 25, to: 24},

                         {from: 26, to: 25},

                         {from: 25, to: 7},

                         {from: 28, to: 27},

                         {from: 29, to: 28},

                         {from: 28, to: 0}

                     ],

                     options:{},

                     data:{}

                 }

             },

             methods:{

               init(){

                   let this_ = this;

                   this_.nodes = new Vis.DataSet(this_.nodesArray);

                   this_.edges = new Vis.DataSet(this_.edgesArray);

                   this_.container = document.getElementById('network_id');

                   this_.data = {

                     nodes: this_.nodes,

                     edges: this_.edges

                   };

                   this_.options = {

                     autoResize: true,

                     groups:{

                         useDefaultGroups: true,

                         myGroupId:{

                         /*node options*/

                         }

                     },

                    nodes: {

                        shape: 'dot',

                        size: 30,

                        font: {

                            size: 32,

                        },

                        borderWidth: 2

                    },

                    edges: {

                         2,

                               smooth:{  //设置两个节点之前的连线的状态

                                   enabled: false  //默认是true,设置为false之后,两个节点之前的连线始终为直线,不会出现贝塞尔曲线

                               }

                  },

                    physics: { //计算节点之前斥力,进行自动排列的属性

                        enabled: true, //默认是true,设置为false后,节点将不会自动改变,拖动谁谁动。不影响其他的节点

                        barnesHut: {

                            gravitationalConstant: -4000,

                            centralGravity: 0.3,

                            springLength: 120,

                            springConstant: 0.04,

                            damping: 0.09,

                            avoidOverlap: 0

                        }

                    },

                    interaction:{

                        hover:true,

                        dragNodes: true, //是否能拖动节点

                        dragView: true, //是否能拖动画布

                        hover: true, //鼠标移过后加粗该节点和连接线

                        multiselect: true, //按 ctrl 多选

                        selectable: true, //是否可以点击选择

                        selectConnectedEdges: true, //选择节点后是否显示连接线

                        hoverConnectedEdges: true, //鼠标滑动节点后是否显示连接线

                        zoomView: true //是否能缩放画布

                    },

                    manipulation: {  //该属性表示可以编辑,出现编辑操作按钮

                        enabled: true

                    }

                };

                this_.network = new Vis.Network(this_.container, this_.data, this_.options);

              },

              resetAllNodes() {

                let this_ = this;

                this_.nodes.clear();

                this_.edges.clear();

                this_.nodes.add(this_.nodesArray);

                this_.edges.add(this_.edgesArray);

                this_.data = {

                    nodes: this_.nodes,

                    edges: this_.edges

                };

                this_.network = new Vis.Network(this_.container, this_.data, this_.options);

              },

              resetAllNodesStabilize() {

                let this_ = this;

                this_.resetAllNodes();

                this_.network.stabilize();

              }

            },

            mounted(){

                this.init();

                this.network.on("click", function (params) {

                    params.event = "[original event]";

                    document.getElementById('eventSpan').innerHTML = '<h2>Click event:</h2>' + JSON.stringify(params, null, 4);

                    console.log('click event, getNodeAt returns: ' + this.getNodeAt(params.pointer.DOM));

                });

            }

        }

    7.需求:出现选框,获取选框中的选中的节点,如右图;

    已获取到选框的位置

     ,节点的位置是随机生成的,如何获取?

     解答:

    function returnPos(params){

        var nodePosCanvas = [],selectNodes=[],nodePosDom=[];

    // 通过network.getPositions(节点id),来获取到随机生成的节点的canvas的坐标

        $.each(nodes._data,function(index,item){

            var obj=network.getPositions(item.id)[item.id];

            obj.id=item.id;

            nodePosCanvas.push(obj)

        });

     // 通过network.canvasToDOM({x:x,y:y}),将获取到的canvas坐标转化为DOM坐标

        $.each(nodePosCanvas,function(indexpos,itempos){

            var obj=network.canvasToDOM({x:itempos.x,y:itempos.y}); 

            obj.id=itempos.id;

            nodePosDom.push(obj)

        });

        // 通过对上下左右的限制,获取到选中的节点

        $.each(nodePosDom,function(indexposDom,itemposDom){

            if((itemposDom.x>params.left||itemposDom.x == params.left) && (itemposDom.x<params.right||itemposDom.x == params.right)){

                if((itemposDom.y>params.top||itemposDom.y == params.top) && (itemposDom.y<params.bottom||itemposDom.y == params.bottom)){

                    selectNodes.push(itemposDom)   

                }

            }

        });

      }

    实现vis.js中的编辑节点,增加节点,删除节点,增加边缘的操作

    Vis的option中直接有属性就可以进行这些操作

    manipulation: {  //该属性表示可以编辑,出现编辑操作按钮

            enabled: false,

            initiallyActive:true,

            addNode:function(nodeData,callback){  对增加节点的操作,一般使用默认的话就不需要写这个函数

                    nodesArrayCopy.forEach(item=>{

                        if(item.status){

                            delete item.status;

                        }

                    });

                nodesArrayCopy.push({id:nodesArray.length, label:"I'm new!",group:0,status:"lastest"})

                nodes.add({id:nodesArray.length, label:"I'm new!",x:nodeData.x,y:nodeData.y});

            }

        },

    那如果不想使用默认的增加节点功能呢,需要使用什么方法进行增加

    var nodes = new vis.DataSet(nodesArray);

    nodes.add({id: 1001, x: x, y:y, label: name, group:group, value: value,  physics:false});

    使用nodes.add()方法进行添加

    想要增加边缘edge

    var edges = new vis.DataSet(edgesArray);

    edges.add({

                    id: edge.id,

                    arrows:'to',

                    from: edge.fromNodeId,

                    to: edge.toNodeId,

                    label:edge.label,

                    font:{align:"middle"},

                    length:150

                });

    想要对已有的节点进行更新

    nodes.update([{id:id, group:group}]);

     

    对文档做了一点翻译,有需求的可以查看

    具体参考 https://yajunfan.github.io/vis/#/

     

     

    过network.canvasToDOM({x:x,y:y}),将获取到的canvas坐标转化为DOM坐标
    [Guò network.CanvasToDOM({x:X,y:Y}), jiāng huòqǔ dào de canvas zuòbiāo zhuǎnhuà wéi DOM zuòbiāo]
    Through network.canvasToDOM ({x: x, y: y}), the acquired coordinates into the canvas coordinate DOM
  • 相关阅读:
    html基础之html标签
    unittest框架(二)单元测试及测试报告
    unittest框架(一)用例管理
    python实现http接口自动化测试(完善版)
    python学习笔记(二十九)为什么python的多线程不能利用多核CPU
    深入理解JVM(三)——配置参数
    深入理解JVM(二)——内存模型、可见性、指令重排序
    深入理解JVM(一)——基本原理
    做了两款数据库监控工具,打算在近期开源
    电商系统中的商品模型的分析与设计—续
  • 原文地址:https://www.cnblogs.com/fyjz/p/11598720.html
Copyright © 2011-2022 走看看