美文网首页
4.7 自定义节点-html

4.7 自定义节点-html

作者: skoll | 来源:发表于2021-12-24 11:14 被阅读0次

    简介

    1 .可以插入节点后,我们几乎就可以做任意的样式定制了,还有一些逻辑相关比如点击收起这种,我们只要把相关的数据传递给html节点,然后让他来渲染就可以了,包括删除节点那些操作.打开了新世界
    2 .原理:SVG中的一个特殊元素foreignObject元素,在这个元素中可以内嵌任何XHTML元素,所以我们可以借助这个元素来渲染HTML元素和React组件来渲染想要的操作到位置
    3 .将节点的shape属性指定为HTML,就可以通过html属性来指定需要渲染的html元素或一个返回HTML元素的方法
    4 .关键:当HTML属性为HTML元素或函数时,将不能通过graph.toJSON方法导出画布
    5 .https://codesandbox.io/s/icno7?file=/src/app.tsx

    框架

    1 .单个节点特别复杂,有需要交互的操作的时候最需要
    2 .比如点击收起,手风琴.框架以及html最关键的是这里吧
    3 .

    渲染React节点

    1 .@antv/x6-react-shape 包
    2 .通过 component 属性来指定渲染节点的 React 组件
    3 .优化渲染之后在考虑把,有专门的hook,可以走useMemo那一套

    挂载React节点,方便导出数据显示

    1 .注册React节点到Graph里面
    // 注册 React 组件
    Graph.registerReactComponent('my-component1', <MyComponent text="Hello" />)
    
    // 注册返回 React 组件的函数
    Graph.registerReactComponent('my-component2', (node) => {
      const data = node.getData()
      return (<div>{data.text}</div>)
    })
    
    2 .添加的节点里面也要通知
    graph.addNode({
      x: 40,
      y: 40,
      width: 100,
      height: 40,
      shape: 'react-shape',
      component: 'my-component1',
    })
    

    自定义开关节点

    1 .电路联通的开关,组合单个SVG节点,构成组合图案


    image.png

    2 .其实就是三根线,中间那个根线角度发生变化

    <!DOCTYPE html>
    <html lang="en">
    <head>
        <meta charset="UTF-8">
        <meta http-equiv="X-UA-Compatible" content="IE=edge">
        <meta name="viewport" content="width=device-width, initial-scale=1.0">
        <title>Document</title>
        <script src="https://unpkg.com/@antv/x6/dist/x6.js"></script>
        <style>
            .my-btn{
                position: relative;
                display: inline-block;
                padding: 10px 20px;
                color: #03e9f4;
                font-size: 16px;
                text-decoration: none;
                text-transform: uppercase;
                overflow: hidden;
                transition: .3s;
                margin-top: 40px;
                letter-spacing: 3px
              }
            
              .my-btn:hover {
                background: #03e9f4;
                color: #fff;
                border-radius: 5px;
                box-shadow: 0 0 5px #03e9f4,
                            0 0 25px #03e9f4,
                            0 0 50px #03e9f4,
                            0 0 100px #03e9f4;
              }
        </style>
    </head>
    <body>
        <h3>多边形</h3>
        <div id="container">
    
        </div>
        <script>
            const graph=new X6.Graph({
                container:document.getElementById('container'),
                width:800,
                height:600,
                grid:true,
            })
            const switchCenter={
                x:35,
                y:-2
            }
    
            const switchOpen=`rotate(-30 ${switchCenter.x} ${switchCenter.y})`
            const switchClose=`rotate(-12 ${switchCenter.x} ${switchCenter.y})`
    
            graph.addNode({
                x:200,
                y:200,
                markup:[
                  {
                    tagName:'g',
                    //这里还是一种集合,里面包含两个独立的元素
                    selector:'left-group',
                    children:[
                        {
                            tagName:'rect',
                            selector:"left",
                            //下面以及后面的操作也是看这里的样式
                            groupSelector:'line',
                            attrs:{
                                x:0,
                                y:0,
                            }
                        },{
                            tagName:'circle',
                            selector:'lco',
                            groupSelector:'co',
                            attrs:{
                                cx:30
                            }
                        },
                        //大圆,黑色
                        {
                            tagName:'circle',
                            selector:'lci',
                            groupSelector:'ci',
                            attrs:{
                                cx:30
                            }
                        }
                        //小圆,白色
                    ]
                  },
                  //第一条线,其实也算是不在同一个联通关系的,可以拆分的操作
                  {
                      tagName:"rect",
                      selector:'switch',
                      groupSelector:'line'
                  },
                  //右边的横线
                  {
                    tagName:'g',
                    selector:"right-group",
                    children:[
                        {
                            tagName:'rect',
                            selector:'right',
                            groupSelector:'line',
                            attrs:{
                                x:70,
                                y:0,
                            }
                        },{
                            tagName:"circle",
                            selector:'rco',
                            groupSelector:'co',
                            attrs:{
                                cx:70
                            }
                        },{
                            tagName:'circle',
                            selector:'rci',
                            //操作的时候选择器是这个
                            groupSelector:'ci',
                            //用来让下边的attrs选到这个
                            attrs:{
                                cx:70
                            }
                        }
                    ]
                  }
                ],  
                //大量绘制SVG的操作全都是用这种方法
                attrs:{
                    line:{
                        width:20,
                        height:2,
                        fill:"#000",
                        stroke:'#000'
                    },
                    co:{
                        r:8,
                        fill:"#000"
                    },
                    //大圆,黑色
                    ci:{
                        r:4,
                        fill:'#fff'
                    },
                    //小圆,白色.合起来就是一个黑色的环
                    switch:{
                        x:35,
                        y:-2,
                        width:35,
                        transform:switchOpen,
                    }
                    //连接线的样式.transform有点类似css样式
                }
            })
    
            graph.on('node:click',({node})=>{
                const attrPath='attrs/switch/transform'
                const current=node.prop(attrPath)
                //获取这个节点的属性: 获取指定路径的属性值
    
                //console.log(node.prop())
                //不传参数是获取全部属性
                
                //动画变化版本
                //const target=current===switchOpen?switchClose:switchOpen
                //node.transition(attrPath, target, {
                //    interp: (a, b) => {
                //      const reg = /-?\d+/g
                //      const start = parseInt(a.match(reg)[0], 10)
                //      const end = parseInt(b.match(reg)[0], 10)
                //      const d = end - start
                //      return (t) => {
                //        return `rotate(${start + d * t} ${switchCenter.x} ${switchCenter.y})`
                //      }
                //    },
                //})
    
                //非动画版本
                if(current===switchOpen){
                    node.prop(attrPath,switchClose)
                }else{
                    node.prop(attrPath,switchOpen)
                }
            })
        </script>
    </body>
    </html>
    

    相关文章

      网友评论

          本文标题:4.7 自定义节点-html

          本文链接:https://www.haomeiwen.com/subject/vlrlqrtx.html