zoukankan      html  css  js  c++  java
  • 网站动态背景线条跟随鼠标移动,吸附鼠标效果

    网站动态背景线条跟随鼠标移动,吸附鼠标效果

    动态背景线条,鼠标移动可以吸附,可以添加配置,代码如下:

    <!DOCTYPE html>
    <html lang="en">
    
    <head>
        <meta charset="UTF-8">
        <title>粒子线条canvas效果</title>
        <style>
            #J_dotLine {
                display: block;
                margin: 0 auto;
            }
        </style>
    </head>
    
    <body>
        <canvas id="J_dotLine"></canvas>
        <script>
            ; (function (window) {
                function Dotline(option) {
                    this.opt = this.extend({
                        dom: 'J_dotLine',//画布id
                        cw: 1000,//画布宽
                        ch: 500,//画布高
                        ds: 100,//点的个数
                        r: 0.5,//圆点半径
                        cl: '#000',//颜色
                        dis: 100//触发连线的距离
                    }, option);
                    this.c = document.getElementById(this.opt.dom);//canvas元素id
                    this.ctx = this.c.getContext('2d');
                    this.c.width = this.opt.cw;//canvas宽
                    this.c.height = this.opt.ch;//canvas高
                    this.dotSum = this.opt.ds;//点的数量
                    this.radius = this.opt.r;//圆点的半径
                    this.disMax = this.opt.dis * this.opt.dis;//点与点触发连线的间距
                    this.color = this.color2rgb(this.opt.cl);//设置粒子线颜色
                    this.dots = [];
                    //requestAnimationFrame控制canvas动画
                    var RAF = window.requestAnimationFrame || window.webkitRequestAnimationFrame || window.mozRequestAnimationFrame || window.oRequestAnimationFrame || window.msRequestAnimationFrame || function (callback) {
                        window.setTimeout(callback, 1000 / 60);
                    };
                    var _self = this;
                    //增加鼠标效果
                    var mousedot = { x: null, y: null, label: 'mouse' };
                    this.c.onmousemove = function (e) {
                        var e = e || window.event;
                        mousedot.x = e.clientX - _self.c.offsetLeft;
                        mousedot.y = e.clientY - _self.c.offsetTop;
                    };
                    this.c.onmouseout = function (e) {
                        mousedot.x = null;
                        mousedot.y = null;
                    }
                    //控制动画
                    this.animate = function () {
                        _self.ctx.clearRect(0, 0, _self.c.width, _self.c.height);
                        _self.drawLine([mousedot].concat(_self.dots));
                        RAF(_self.animate);
                    };
                }
                //合并配置项,es6直接使用obj.assign();
                Dotline.prototype.extend = function (o, e) {
                    for (var key in e) {
                        if (e[key]) {
                            o[key] = e[key]
                        }
                    }
                    return o;
                };
                Dotline.prototype.color2rgb = function (colorStr) {
                    var red = null,
                        green = null,
                        blue = null;
                    var cstr = colorStr.toLowerCase();//变小写
                    var cReg = /^#[0-9a-fA-F]{3,6}$/;//确定是16进制颜色码
                    if (cstr && cReg.test(cstr)) {
                        if (cstr.length == 4) {
                            var cstrnew = '#';
                            for (var i = 1; i < 4; i++) {
                                cstrnew += cstr.slice(i, i + 1).concat(cstr.slice(i, i + 1));
                            }
                            cstr = cstrnew;
                        }
                        red = parseInt('0x' + cstr.slice(1, 3));
                        green = parseInt('0x' + cstr.slice(3, 5));
                        blue = parseInt('0x' + cstr.slice(5, 7));
                    }
                    return red + ',' + green + ',' + blue;
                }
                //画点
                Dotline.prototype.addDots = function () {
                    var dot;
                    for (var i = 0; i < this.dotSum; i++) {//参数
                        dot = {
                            x: Math.floor(Math.random() * this.c.width) - this.radius,
                            y: Math.floor(Math.random() * this.c.height) - this.radius,
                            ax: (Math.random() * 2 - 1) / 1.5,
                            ay: (Math.random() * 2 - 1) / 1.5
                        }
                        this.dots.push(dot);
                    }
                };
                //点运动
                Dotline.prototype.move = function (dot) {
                    dot.x += dot.ax;
                    dot.y += dot.ay;
                    //点碰到边缘返回
                    dot.ax *= (dot.x > (this.c.width - this.radius) || dot.x < this.radius) ? -1 : 1;
                    dot.ay *= (dot.y > (this.c.height - this.radius) || dot.y < this.radius) ? -1 : 1;
                    //绘制点
                    this.ctx.beginPath();
                    this.ctx.arc(dot.x, dot.y, this.radius, 0, Math.PI * 2, true);
                    this.ctx.stroke();
                };
                //点之间画线
                Dotline.prototype.drawLine = function (dots) {
                    var nowDot;
                    var _that = this;
                    //自己的思路:遍历两次所有的点,比较点之间的距离,函数的触发放在animate里
                    this.dots.forEach(function (dot) {
    
                        _that.move(dot);
                        for (var j = 0; j < dots.length; j++) {
                            nowDot = dots[j];
                            if (nowDot === dot || nowDot.x === null || nowDot.y === null) continue;//continue跳出当前循环开始新的循环
                            var dx = dot.x - nowDot.x,//别的点坐标减当前点坐标
                                dy = dot.y - nowDot.y;
                            var dc = dx * dx + dy * dy;
                            if (Math.sqrt(dc) > Math.sqrt(_that.disMax)) continue;
                            // 如果是鼠标,则让粒子向鼠标的位置移动
                            if (nowDot.label && Math.sqrt(dc) > Math.sqrt(_that.disMax) / 2) {
                                dot.x -= dx * 0.02;
                                dot.y -= dy * 0.02;
                            }
                            var ratio;
                            ratio = (_that.disMax - dc) / _that.disMax;
                            _that.ctx.beginPath();
                            _that.ctx.lineWidth = ratio / 2;
                            _that.ctx.strokeStyle = 'rgba(' + _that.color + ',' + parseFloat(ratio + 0.2).toFixed(1) + ')';
                            _that.ctx.moveTo(dot.x, dot.y);
                            _that.ctx.lineTo(nowDot.x, nowDot.y);
                            _that.ctx.stroke();//不描边看不出效果
    
                            //dots.splice(dots.indexOf(dot), 1);
                        }
                    });
                };
                //开始动画
                Dotline.prototype.start = function () {
                    var _that = this;
                    this.addDots();
                    setTimeout(function () {
                        _that.animate();
                    }, 100);
                }
                window.Dotline = Dotline;
            }(window));
            //调用
            window.onload = function () {
                var dotline = new Dotline({
                    dom: 'J_dotLine',//画布id
                    cw: 1000,//画布宽
                    ch: 500,//画布高
                    ds: 100,//点的个数
                    r: 0.5,//圆点半径
                    cl: '#fff',//粒子线颜色
                    dis: 100//触发连线的距离
                }).start();
            }
        </script>
    </body>
    
    </html>

    vue,react写法,类分装:
    创建一个dotline.js

    class Dotline {
      constructor(option) {
        this.opt = this.extend({
          dom: 'J_dotLine',//画布id
          cw: 1000,//画布宽
          ch: 500,//画布高
          ds: 100,//点的个数
          r: 0.5,//圆点半径
          cl: '#000',//颜色
          dis: 100//触发连线的距离
        }, option);
        this.c = document.getElementById(this.opt.dom);//canvas元素id
        this.ctx = this.c.getContext('2d');
        this.c.width = this.opt.cw;//canvas宽
        this.c.height = this.opt.ch;//canvas高
        this.dotSum = this.opt.ds;//点的数量
        this.radius = this.opt.r;//圆点的半径
        this.disMax = this.opt.dis * this.opt.dis;//点与点触发连线的间距
        this.color = this.color2rgb(this.opt.cl);//设置粒子线颜色
        this.dots = [];
        //requestAnimationFrame控制canvas动画
        var RAF = window.requestAnimationFrame || window.webkitRequestAnimationFrame || window.mozRequestAnimationFrame || window.oRequestAnimationFrame || window.msRequestAnimationFrame || function (callback) {
          window.setTimeout(callback, 1000 / 60);
        };
        var _self = this;
        //增加鼠标效果
        var mousedot = { x: null, y: null, label: 'mouse' };
        this.c.onmousemove = function (e) {
          var e = e || window.event;
          mousedot.x = e.clientX - _self.c.offsetLeft;
          mousedot.y = e.clientY - _self.c.offsetTop;
        };
        this.c.onmouseout = function (e) {
          mousedot.x = null;
          mousedot.y = null;
        }
        //控制动画
        this.animate = function () {
          _self.ctx.clearRect(0, 0, _self.c.width, _self.c.height);
          _self.drawLine([mousedot].concat(_self.dots));
          RAF(_self.animate);
        };
      }
    
      //合并配置项,es6直接使用obj.assign();
      extend(o, e) {
        for (var key in e) {
          if (e[key]) {
            o[key] = e[key]
          }
        }
        return o;
      }
    
      //设置线条颜色
      color2rgb(colorStr) {
        var red = null,
          green = null,
          blue = null;
        var cstr = colorStr.toLowerCase();//变小写
        var cReg = /^#[0-9a-fA-F]{3,6}$/;//确定是16进制颜色码
        if (cstr && cReg.test(cstr)) {
          if (cstr.length == 4) {
            var cstrnew = '#';
            for (var i = 1; i < 4; i++) {
              cstrnew += cstr.slice(i, i + 1).concat(cstr.slice(i, i + 1));
            }
            cstr = cstrnew;
          }
          red = parseInt('0x' + cstr.slice(1, 3));
          green = parseInt('0x' + cstr.slice(3, 5));
          blue = parseInt('0x' + cstr.slice(5, 7));
        }
        return red + ',' + green + ',' + blue;
      }
    
      //画点
      addDots() {
        var dot;
        for (var i = 0; i < this.dotSum; i++) {//参数
          dot = {
            x: Math.floor(Math.random() * this.c.width) - this.radius,
            y: Math.floor(Math.random() * this.c.height) - this.radius,
            ax: (Math.random() * 2 - 1) / 1.5,
            ay: (Math.random() * 2 - 1) / 1.5
          }
          this.dots.push(dot);
        }
      }
    
      //点运动
      move(dot) {
        dot.x += dot.ax;
        dot.y += dot.ay;
        //点碰到边缘返回
        dot.ax *= (dot.x > (this.c.width - this.radius) || dot.x < this.radius) ? -1 : 1;
        dot.ay *= (dot.y > (this.c.height - this.radius) || dot.y < this.radius) ? -1 : 1;
        //绘制点
        this.ctx.beginPath();
        this.ctx.arc(dot.x, dot.y, this.radius, 0, Math.PI * 2, true);
        this.ctx.stroke();
      }
    
      //点之间画线
      drawLine(dots) {
        var nowDot;
        var _that = this;
        //自己的思路:遍历两次所有的点,比较点之间的距离,函数的触发放在animate里
        this.dots.forEach(function (dot) {
    
          _that.move(dot);
          for (var j = 0; j < dots.length; j++) {
            nowDot = dots[j];
            if (nowDot === dot || nowDot.x === null || nowDot.y === null) continue;//continue跳出当前循环开始新的循环
            var dx = dot.x - nowDot.x,//别的点坐标减当前点坐标
              dy = dot.y - nowDot.y;
            var dc = dx * dx + dy * dy;
            if (Math.sqrt(dc) > Math.sqrt(_that.disMax)) continue;
            // 如果是鼠标,则让粒子向鼠标的位置移动
            if (nowDot.label && Math.sqrt(dc) > Math.sqrt(_that.disMax) / 2) {
              dot.x -= dx * 0.02;
              dot.y -= dy * 0.02;
            }
            var ratio;
            ratio = (_that.disMax - dc) / _that.disMax;
            _that.ctx.beginPath();
            _that.ctx.lineWidth = ratio / 2;
            _that.ctx.strokeStyle = 'rgba(' + _that.color + ',' + parseFloat(ratio + 0.2).toFixed(1) + ')';
            _that.ctx.moveTo(dot.x, dot.y);
            _that.ctx.lineTo(nowDot.x, nowDot.y);
            _that.ctx.stroke();//不描边看不出效果
    
            //dots.splice(dots.indexOf(dot), 1);
          }
        });
      }
    
      //开始动画
      start() {
        var _that = this;
        this.addDots();
        setTimeout(function () {
          _that.animate();
        }, 100);
      }
    }
    
    export default Dotline;

    调用方法:
    html:

    <canvas id="J_dotLine"></canvas>

    js:

    import Dotline from "./dotline.js";
    
    const option = {
       dom: 'J_dotLine',//画布id
       cw: 1000,//画布宽
       ch: 500,//画布高
       ds: 250,//点的个数
       r: 3,//圆点半径
       cl: '#061eb3',//粒子线颜色
       dis: 120//触发连线的距离
     }
    const dotline = new Dotline(option).start();

    转载:https://blog.csdn.net/weixin_44149978/article/details/98076605

    -------------------------------------------------------------------------------------------------

    <template>
      <div>
        <canvas id="J_dotLine"></canvas>
      </div>
    </template>
    
    <script>
    import Dotline from "../../assets/js/dotline.js";
    export default {
      mounted: function () {
        this.swippertab();
      },
      methods: {
        swippertab() {
          const option = {
            dom: "J_dotLine", //画布id
            cw: 1000, //画布宽
            ch: 500, //画布高
            ds: 250, //点的个数
            r: 3, //圆点半径
            cl: "#8FDAF8", //粒子线颜色
            dis: 120, //触发连线的距离
          };
          new Dotline(option).start();
        },
      },
    };
    </script>
    
    <style>
    </style>

  • 相关阅读:
    Django入门
    初识json
    回来了
    python学习
    JavaScript 中获取元素样式
    浏览器检测与特征检测
    DOM 节点的类型及判定
    浏览器的控制台工具
    .htaccess 配置文件的使用
    workLog:07001:补充0829 前
  • 原文地址:https://www.cnblogs.com/yehuisir/p/14824773.html
Copyright © 2011-2022 走看看