【HTML】制作一个简单的线性动画

这篇具有很好参考价值的文章主要介绍了【HTML】制作一个简单的线性动画。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

 目录

前言

HTML部分

CSS部分

JS部分

效果图

总结


前言

        无需多言,本文将详细介绍一段HTML代码,具体内容如下:

【HTML】制作一个简单的线性动画,经验分享类,# 前端 后端,html,前端

开始

        首先新建文件夹,创建一个文本文档,两个文件夹,其中HTML的文件名改为[index.html];CSS的文件名改为[css],里面新建一个文本文档重命名为[normalize.min.css];JS的文件名改为[js],里面新建两个文本文档,分别重命名为 [script.js] [simplex-noise.min.js],创建好后右键用文本文档打开,再把下面相对应代码填入后保存即可。

【HTML】制作一个简单的线性动画,经验分享类,# 前端 后端,html,前端

HTML部分

        这段HTML代码定义了一个基本的网页结构,包括了必要的文档类型声明、网页头部(head)和主体(body)部分。具体来说:

  1. <!DOCTYPE html>: 这是HTML5文档的声明,用于告诉浏览器这是一个HTML5文档。

  2. <html lang="en">: 根元素,定义了整个HTML文档,并设置页面的语言为英语。

  3. <head>: 包含了文档的元数据,不影响页面的可见内容,但对搜索引擎优化(SEO)和页面表现很重要。

    • <meta charset="UTF-8">: 设置字符编码为UTF-8,这是一种广泛使用的国际字符编码,可以显示几乎所有语言的字符。
    • <title>雷神Leo</title>: 设置了浏览器标签页上显示的标题,这里是“雷神Leo”。
    • <link rel="stylesheet" href="css/normalize.min.css">: 引入了一个外部CSS文件,用于样式重置和标准化不同浏览器间的默认样式差异,以确保网页的一致性。
  4. <body>: 包含了网页的所有可见内容。

    • <script src='js/simplex-noise.min.js'></script>: 引入了一个JavaScript库,用于生成简单的噪声效果,常用于创建视觉效果。
    • <script src="js/script.js"></script>: 引入了网页的主要JavaScript文件,负责处理网页的行为和交互逻辑。

        这个网页模板是一个起点,开发者可以在此基础上添加更多的HTML元素、CSS样式和JavaScript代码,以创建具有丰富功能和吸引人设计的网页。需要注意的是,实际使用时,需要确保外部文件路径正确,并编写相应的CSS和JavaScript代码来实现所需的功能。

<!DOCTYPE html> <!-- 声明文档类型为HTML5 -->
<html lang="en" ><!-- 根元素,设置语言为英语 -->
<head>
    <meta charset="UTF-8"> <!-- 设置字符编码为UTF-8,确保网页正确显示多语言字符 -->
    <title>雷神Leo</title> <!-- 网页标题,将显示在浏览器标签页上 -->
    <!-- 引入外部CSS样式表,用于网页的样式布局 -->
    <link rel="stylesheet" href="css/normalize.min.css">
</head>
<body>
    <!-- 页面的主体内容将会放在这里 -->
    <!-- 引入外部JavaScript文件,用于网页的行为和动态效果 -->
    <script src='js/simplex-noise.min.js'></script>
    <script src="js/script.js"></script>
</body>
</html>

CSS部分

        这段代码是一个CSS样式表的一部分,主要使用了Normalize.css,它是一个用于网页的CSS库,旨在创建一个更平滑的用户体验,同时保持不同浏览器和设备之间的一致性。以下是对这段代码的总结和注释:

  1. button,hr,input{overflow:visible}: 设置按钮、水平规则线(hr)和输入框的溢出内容为可见,以确保这些元素的溢出内容不会影响布局。

  2. audio,canvas,progress,video{display:inline-block}: 将音频、画布、进度条和视频等元素设置为内联块状元素,使它们既能像内联元素一样参与文本流,又能设置宽高。

  3. progress,sub,sup{vertical-align:baseline}: 设置进度条、下标和上标元素的垂直对齐方式为基线对齐,以确保它们与文本的基线对齐。

  4. html{font-family:sans-serif;line-height:1.15;...}: 设置默认的字体系列为无衬线字体,并设置行高为1.15倍,同时禁用了一些浏览器的默认文本大小调整功能。

  5. body{margin:0}: 设置页面主体的默认外边距为0,以避免浏览器的默认边距影响布局。

  6. menu,article,aside,...{display:block}: 将一些HTML5新增的语义化元素设置为块状元素,确保它们占据一整行。

  7. h1{font-size:2em;margin:.67em 0}: 设置一级标题的字体大小为2em,并设置上下外边距。

  8. figcaption,figure,main{display:block}: 设置图题、图形和主要内容区域为块状元素。

  9. hr{box-sizing:content-box;height:0}: 设置水平规则线的盒模型为内容盒模型,并将其高度设置为0。

  10. code,kbd,pre,samp{font-family:monospace,monospace;font-size:1em}: 设置代码、键盘输入、预格式化文本和样本文本的字体为等宽字体,并设置字体大小为1em。

  11. a{background-color:transparent;...}: 设置超链接的背景颜色为透明,并禁用了一些浏览器的默认文本装饰。

  12. abbr[title]{...}: 设置有标题属性的缩写词的文本装饰为下划线点状,以提供解释性的文本。

  13. b,strong{font-weight:bolder}: 设置加粗文本的字体权重更强。

  14. small{font-size:80%}: 设置小号文字的字体大小为80%。

  15. sub,sup{...}: 设置下标和上标的字体大小为75%,并设置行高为0,以及它们的相对位置。

  16. audio:not([controls]){...}: 隐藏没有控件的音频元素。

  17. img{border-style:none}: 设置图片的边框样式为无。

  18. button,input,...{...}: 设置一系列表单元素的字体系列、大小、外边距等。

  19. fieldset{border:1px solid silver...}: 设置字段集的边框样式、间距和填充。

  20. legend{...}: 设置图例的盒模型、颜色、显示方式和白空间。

  21. progress{}textarea{overflow:auto}: 为进度条和文本区域设置样式。

  22. [type=checkbox],...{...}: 设置复选框、单选按钮等表单元素的盒模型和样式。

  23. summary{display:list-item}: 设置摘要元素的显示方式为列表项。

  24. [hidden],template{display:none}: 隐藏隐藏元素和模板元素。

        最后,/*# sourceMappingURL=normalize.min.css.map */ 是一个注释,用于指示这个CSS文件的源映射文件的位置,便于开发者调试。

        这段代码的目的是为网页提供一个统一的样式基础,减少浏览器之间的默认样式差异,使得开发者可以更轻松地创建一致且易于维护的网页。

button,hr,input{overflow:visible}audio,canvas,progress,video{display:inline-block}progress,sub,sup{vertical-align:baseline}html{font-family:sans-serif;line-height:1.15;-ms-text-size-adjust:100%;-webkit-text-size-adjust:100%}body{margin:0} menu,article,aside,details,footer,header,nav,section{display:block}h1{font-size:2em;margin:.67em 0}figcaption,figure,main{display:block}figure{margin:1em 40px}hr{box-sizing:content-box;height:0}code,kbd,pre,samp{font-family:monospace,monospace;font-size:1em}a{background-color:transparent;-webkit-text-decoration-skip:objects}a:active,a:hover{outline-width:0}abbr[title]{border-bottom:none;text-decoration:underline;text-decoration:underline dotted}b,strong{font-weight:bolder}dfn{font-style:italic}mark{background-color:#ff0;color:#000}small{font-size:80%}sub,sup{font-size:75%;line-height:0;position:relative}sub{bottom:-.25em}sup{top:-.5em}audio:not([controls]){display:none;height:0}img{border-style:none}svg:not(:root){overflow:hidden}button,input,optgroup,select,textarea{font-family:sans-serif;font-size:100%;line-height:1.15;margin:0}button,input{}button,select{text-transform:none}[type=submit], [type=reset],button,html [type=button]{-webkit-appearance:button}[type=button]::-moz-focus-inner,[type=reset]::-moz-focus-inner,[type=submit]::-moz-focus-inner,button::-moz-focus-inner{border-style:none;padding:0}[type=button]:-moz-focusring,[type=reset]:-moz-focusring,[type=submit]:-moz-focusring,button:-moz-focusring{outline:ButtonText dotted 1px}fieldset{border:1px solid silver;margin:0 2px;padding:.35em .625em .75em}legend{box-sizing:border-box;color:inherit;display:table;max-width:100%;padding:0;white-space:normal}progress{}textarea{overflow:auto}[type=checkbox],[type=radio]{box-sizing:border-box;padding:0}[type=number]::-webkit-inner-spin-button,[type=number]::-webkit-outer-spin-button{height:auto}[type=search]{-webkit-appearance:textfield;outline-offset:-2px}[type=search]::-webkit-search-cancel-button,[type=search]::-webkit-search-decoration{-webkit-appearance:none}::-webkit-file-upload-button{-webkit-appearance:button;font:inherit}summary{display:list-item}[hidden],template{display:none}/*# sourceMappingURL=normalize.min.css.map */

JS部分

[script.js]

        这段代码定义了几个类,用于生成随机数、颜色、处理向量运算、碰撞检测、计时、动画定时以及绘制分形图形。

  1. Utils 类提供了一些静态方法,用于生成随机数、随机颜色值和渐变颜色。还包括一个计算当前帧率(FPS)的方法。

  2. Vector2d 类表示二维向量,提供了一系列方法来执行向量运算,如缩放、加法、减法、取反、归一化、旋转和转换为字符串表示。

  3. Collision 类用于处理对象之间的碰撞检测和碰撞反弹。它提供了一个 collideAll 方法来检查所有对象对之间的碰撞,并调用 bounce 方法来处理碰撞反弹。

  4. Stopwatch 类用于计时,提供了开始、停止、获取经过时间、检查是否正在运行和重置计时器的方法。

  5. AnimationTimer 类用于动画定时,它可以创建一个基于时间的动画效果,支持不同的缓动函数,如Ease-In、Ease-Out、Ease-In-Out、Elastic和Bounce。还包括一个线性缓动函数和一个方法来检查动画是否完成。

  6. Angle 类用于表示角度,可以增加或减少角度值,并将角度值转换为弧度。

  7. Canvas 类用于创建和管理分形图形的绘制。它提供了初始化、渲染、绘制帧率和响应窗口大小变化的方法。

  8. PointObj 类表示一个二维点,包含 x 和 y 坐标。

  9. FractalRoot 类用于生成分形的根节点,它初始化分形的结构并绘制形状。

  10. Branch 类表示分形中的一个分支,它负责计算分支的中间点、结构点,并绘制分支。

        最后,代码中的自执行函数用于初始化 Canvas 类,并设置窗口大小变化的事件监听器,以确保画布随着浏览器窗口的变化而调整大小。整个代码展示了一个分形动画的生成和渲染过程,包括碰撞检测和帧率显示。

class Utils {

  static randomNumber(min, max) {
    return Math.floor(Math.random() * (max - min + 1) + min);
  }

  static randomColorRGB() {
    return (
      "rgb(" +
      this.randomNumber(0, 255) +
      ", " +
      this.randomNumber(0, 255) +
      ", " +
      this.randomNumber(0, 255) +
      ")"
    );
  }

  static randomColorHSL(hue, saturation, lightness) {
    return (
      "hsl(" +
      hue +
      ", " +
      saturation +
      "%, " +
      lightness +
      "%)"
    );
  }

  static gradientColor(ctx, cr, cg, cb, ca, x, y, r) {
    const col = cr + "," + cg + "," + cb;
    const g = ctx.createRadialGradient(x, y, 0, x, y, r);
    g.addColorStop(0, "rgba(" + col + ", " + (ca * 1) + ")");
    g.addColorStop(0.5, "rgba(" + col + ", " + (ca * 0.5) + ")");
    g.addColorStop(1, "rgba(" + col + ", " + (ca * 0) + ")");
    return g;
  }

  static calcFPS() {
    const now = (+new Date());
    const fps = 1000 / (now - lastTime);
    lastTime = now;
    return fps.toFixed();
  }
}

class Vector2d {
  constructor(x, y) {
    this.vx = x;
    this.vy = y;
  }

  scale(scale) {
    this.vx *= scale;
    this.vy *= scale;
  }

  add(vec2) {
    this.vx += vec2.vx;
    this.vy += vec2.vy
  }

  sub(vec2) {
    this.vx -= vec2.vx;
    this.vy -= vec2.vy;
  }

  negate() {
    this.vx = -this.vx;
    this.vy = -this.vy;
  }

  length() {
    return Math.sqrt(this.vx * this.vx + this.vy * this.vy);
  }

  lengthSquared() {
    return this.vx * this.vx + this.vy * this.vy;
  }

  normalize() {
    let len = Math.sqrt(this.vx * this.vx + this.vy * this.vy);
    if (len) {
      this.vx /= len;
      this.vy /= len;
    }
    return len;
  }

  rotate(angle) {
    let vx = this.vx;
    let vy = this.vy;
    let cosVal = Math.cos(angle);
    let sinVal = Math.sin(angle);
    this.vx = vx * cosVal - vy * sinVal;
    this.vy = vx * sinVal + vy * cosVal;
  }

  toString() {
    return '(' + this.vx.toFixed(3) + ',' + this.vy.toFixed(3) + ')';
  }
}

class Collision {
  constructor(targetArr) {
    this.arr = targetArr;
  }

  collideAll() {
    let vec = new Vector2d(0, 0);
    let dist;
    let obj1;
    let obj2;
    let c;
    let i;
    for (c = 0; c < this.arr.length; c++) {
      obj1 = this.arr[c];
      for (i = c + 1; i < this.arr.length; i++) {
        obj2 = this.arr[i];
        vec.vx = obj2.x - obj1.x;
        vec.vy = obj2.y - obj1.y;
        dist = vec.length();
        if (dist < obj1.r + obj2.r) {
          vec.normalize();
          vec.scale(obj1.r + obj2.r - dist);
          vec.negate();
          obj1.x += vec.vx;
          obj1.y += vec.vy;
          this.bounce(obj1, obj2);
        }
      }
    }
  }

  bounce(obj1, obj2) {
    let colnAngle = Math.atan2(obj1.y - obj2.y, obj1.x - obj2.x);
    let length1 = obj1.v.length();
    let length2 = obj2.v.length();
    let dirAngle1 = Math.atan2(obj1.v.vy, obj1.v.vx);
    let dirAngle2 = Math.atan2(obj2.v.vy, obj2.v.vx);
    let newVX1 = length1 * Math.cos(dirAngle1 - colnAngle);
    let newVX2 = length2 * Math.cos(dirAngle2 - colnAngle);
    obj1.v.vy = length1 * Math.sin(dirAngle1 - colnAngle);
    obj2.v.vy = length2 * Math.sin(dirAngle2 - colnAngle);
    obj1.v.vx = ((obj1.r - obj2.r) * newVX1 + (2 * obj2.r) * newVX2) / (obj1.r + obj2.r);
    obj2.v.vx = ((obj2.r - obj1.r) * newVX2 + (2 * obj1.r) * newVX1) / (obj1.r + obj2.r);
    obj1.v.rotate(colnAngle);
    obj2.v.rotate(colnAngle);
  }
}

class Stopwatch {
  constructor(time) {
    this.startTime = 0;
    this.running = false;
    this.elapsed = undefined;
  }

  start() {
    this.startTime = +new Date();
    this.elapsedTime = null;
    this.running = true;
  }

  stop() {
    this.elapsed = (+new Date()) - this.startTime;
    this.running = false;
  }

  getElapsedTime() {
    if (this.running) {
      return (+new Date()) - this.startTime;
    } else {
      return this.elapsed;
    }
  }

  isRunning() {
    return this.running;
  }

  reset() {
    this.elapsed = 0;
  }
}

class AnimationTimer {
  constructor(duration, timeWarp) {
    if (duration !== undefined) this.duration = duration;
    if (timeWarp !== undefined) this.timeWarp = timeWarp;
    this.stopwatch = new Stopwatch();
  }

  start() {
    this.stopwatch.start();
  }

  stop() {
    this.stopwatch.stop();
  }

  getElapsedTime() {
    const elapsedTime = this.stopwatch.getElapsedTime();
    const percentComplete = elapsedTime / this.duration;
    if (!this.stopwatch.running) return undefined;
    if (this.timeWarp === undefined) return elapsedTime;
    return elapsedTime * (this.timeWarp(percentComplete) / percentComplete);
  }

  isRunning() {
    return this.stopwatch.running;
  }

  isOver() {
    return this.stopwatch.getElapsedTime() > this.duration;
  }

  makeEaseIn(strength) {
    return function(percentComplete) {
      return Math.pow(percentComplete, strength * 2);
    }
  }

  makeEaseOut(strength) {
    return function(percentComplete) {
      return 1 - Math.pow(1 - percentComplete, strength * 2);
    }
  }

  makeEaseInOut() {
    return function(percentComplete) {
      return percentComplete - Math.sin(percentComplete * 2 * Math.PI) / (2 * Math.PI);
    }
  }

  makeElastic(passes) {
    passes = passes || default_elastic_passes;
    return function(percentComplete) {
      return ((1 - Math.cos(percentComplete * Math.PI * passes)) * (1 - percentComplete)) + percentComplete;
    }
  }

  makeBounce(bounces) {
    const fn = this.makeElastic(bounces);
    return function(percentComplete) {
      percentComplete = fn(percentComplete);
      return percentComplete <= 1 ? percentComplete : 2 - percentComplete;
    }
  }

  makeLinear() {
    return function(percentComplete) {
      return percentComplete;
    }
  }
}

class Angle {
  constructor(angle) {
    this.a = angle;
    this.rad = this.a * Math.PI / 180;
  }

  incDec(num) {
    this.a += num;
    this.rad = this.a * Math.PI / 180;
    return this.rad;
  }
}

let canvas;

let lastTime = 0;

const simplex = new SimplexNoise();

class Canvas {
  constructor(bool) {

    this.canvas = document.createElement("canvas");

    if (bool === true) {
      this.canvas.style.position = 'relative';
      this.canvas.style.display = 'block';
      this.canvas.style.backgroundColor = 'black';
      this.canvas.style.top = '0';
      this.canvas.style.left = '0';
      document.getElementsByTagName("body")[0].appendChild(this.canvas);
    }
    this.ctx = this.canvas.getContext("2d");
    this.width = this.canvas.width = window.innerWidth;
    this.height = this.canvas.height = window.innerHeight;

    this.mouseX = null;
    this.mouseY = null;
    this.mouseZ = null;

    this.number_of_shapes = 5;
    this.shapes_array = [];
  }
  

  init() {
    for (let i = 0; i < this.number_of_shapes; i++) {
      const f = new FractalRoot(this.ctx, this.width / 2, this.height / 2, i);
      this.shapes_array.push(f);
    }
  }

  render() {
    if (Math.random() < 0.001) this.ctx.clearRect(0, 0, this.width, this.height);
    for (let i = 0; i < this.shapes_array.length; i++) {
      this.shapes_array[i].drawShape();
    }

    window.requestAnimationFrame(() => {
      this.render();
    });
  }

  drawFPS() {
    const ctx = this.ctx;
    ctx.save();
    ctx.fillStyle = 'white';
    ctx.font = '16px sans-serif';
    ctx.textAlign = 'right';
    ctx.textBaseline = 'bottom';
    ctx.fillText(Utils.calcFPS() + ' FPS', this.width, this.height);
    ctx.restore();
  }
  
  resize() {
    this.shapes_array = [];
    this.width = this.canvas.width = window.innerWidth;
    this.height = this.canvas.height = window.innerHeight;
    this.init();
  }
}

class PointObj {
  constructor(ex, ey) {
    this.x = ex;
    this.y = ey;
  }
}

class FractalRoot {
  constructor(ctx, x, y, i) {
    this.random = Math.random();
    this.ctx = ctx;
    this.x = x;
    this.y = y;
    this.i = i;
    this.a = 0;
    this.r = 100;
    this.ri = this.r;
    this.maxLevels = 4;
    this.structFactor = null;
    this.rootBranch = null;
    this.numSlides = 5;
    this.pointArr = new Array(this.numSlides);
    this.angleStep = 360 / this.numSlides;
    this.init();
  }
  
  init(time, noise) {
    let count = 0;
    for (let i = 0; i < 360; i += this.angleStep) {
      let x = this.x + (this.r * Math.cos((this.a + i) * Math.PI / 180));
      let y = this.y + (this.r * Math.sin((this.a + i) * Math.PI / 180));
      this.pointArr[count] = new PointObj(x, y);
      count++;
    }
    this.rootBranch = new Branch(
      this.ctx,
      0,
      0,
      this.pointArr,
      this.structFactor,
      this.maxLevels,
      time,
      noise
    );
  }
  
  drawShape() {
    const time = Date.now() / 5000 * this.random;
    const noise = simplex.noise3D(this.x, this.y, time);
    this.structFactor = Math.sin(time) * noise * 3;
    this.r = Math.sin(time) * noise * this.ri + 100;
    this.init(time, noise);
    this.rootBranch.drawMe();
    this.a += noise;
  }
}

class Branch {
  constructor(ctx, lev, n, points, factor, max, time, noise) {
    this.ctx = ctx;
    this.level = lev;
    this.num = n;
    this.outerPoints = points;
    this.structFactor = factor;
    this.maxLevels = max;
    this.time = time;
    this.noise = noise;
    this.myBranches = [];
    this.midPoints = this.calcMidPoints();
    this.projPoints = this.calcStructPoints();
    if (this.level + 1 < this.maxLevels) {
      let childBranch = new Branch(
        this.ctx,
        this.level + 1,
        0,
        this.projPoints,
        this.structFactor,
        this.maxLevels,
        this.time,
        this.noise
      );
      this.myBranches.push(childBranch);
      for (let i = 0; i < this.outerPoints.length; i++) {
        let n = i - 1;
        if (n < 0) {
          n += this.outerPoints.length;
        }
        let newPoints = [
          this.projPoints[i],
          this.midPoints[i],
          this.outerPoints[i],
          this.midPoints[n],
          this.projPoints[n]
        ];
        let childBranch = new Branch(
          this.ctx,
          this.level + 1,
          i + 1,
          newPoints,
          this.structFactor,
          this.maxLevels,
          this.time,
          this.noise
        );
        this.myBranches.push(childBranch);
      }
    }
  }
  
  drawMe() {
    const ctx = this.ctx;
    ctx.save();
    ctx.lineWidth = 0.1;

    ctx.strokeStyle = 'hsl(' + 360 * (this.noise * 2) + ', 80% ,60%)';

    ctx.beginPath();
    ctx.moveTo(this.outerPoints[0].x,this.outerPoints[0].y);
    for (let i = 1; i < this.outerPoints.length; i++) {
      ctx.lineTo(this.outerPoints[i].x, this.outerPoints[i].y);
    }
    ctx.closePath();
    ctx.stroke();
    ctx.restore();
    for (let i = 0; i < this.myBranches.length; i++) {
      this.myBranches[i].drawMe();
    }
  }
  
  calcMidPoints() {
    let mpArray = [];
    for (let i = 0; i < this.outerPoints.length; i++) {
      let n = i + 1;
      if (n === this.outerPoints.length) {
        n = 0;
      }
      let thisMp = this.calcMidPoint(this.outerPoints[i], this.outerPoints[n]);
      mpArray[i] = thisMp;
    }
    return mpArray;
  }
  
  calcMidPoint(end1, end2) {
    let mx, my;
    if (end1.x > end2.x) {
      mx = end2.x + ((end1.x - end2.x) / 2);
    } else {
      mx = end1.x + ((end2.x - end1.x) / 2);
    }
    if (end1.y > end2.y) {
      my = end2.y + ((end1.y - end2.y) / 2);
    } else {
      my = end1.y + ((end2.y - end1.y) / 2);
    }
    return new PointObj(mx, my);
  }
  
  calcStructPoints() {
    let structArray = new Array(this.midPoints.length);
    for (let i = 0; i < this.midPoints.length; i++) {
      let n = i + 3;
      if (n >= this.midPoints.length) {
        n -= this.midPoints.length;
      }
      let thisSP = this.calcProjPoint(this.midPoints[i], this.outerPoints[n]);
      structArray[i] = thisSP;
    }
    return structArray;
  }
  
  calcProjPoint(mp, op) {
    let px, py, adj, opp;
    if (op.x > mp.x) {
      opp = op.x - mp.x;
    } else {
      opp = mp.x - op.x;
    }
    if (op.y > mp.y) {
      adj = op.y - mp.y;
    } else {
      adj = mp.y - op.y;
    }
    if (op.x > mp.x) {
      px = mp.x + (opp * this.structFactor);
    } else {
      px = mp.x - (opp * this.structFactor);
    }
    if (op.y > mp.y) {
      py = mp.y + (adj * this.structFactor);
    } else {
      py = mp.y - (adj * this.structFactor);
    }
    return new PointObj(px, py);
  }
}

(() => {
  'use strict';
  window.addEventListener('load', () => {
    canvas = new Canvas(true);
    canvas.init();
    canvas.render();

    window.addEventListener("resize", () => {
      canvas.resize();
    }, false);
  }, false);
})();

[simplex-noise.min.js]

        这段代码定义了一个名为 SimplexNoise 的 JavaScript 类,用于生成多维的简单噪声(Simplex Noise)。简单噪声是一种用于生成自然外观的纹理或形状的数学函数,常用于计算机图形学、游戏开发和数据可视化等领域。

        以下是对代码中各个部分的总结:

  1. 初始化和配置

    • 定义了一系列的常量(如 retao),这些常量用于后续的噪声计算。
    • i 函数是一个工厂方法,用于创建 SimplexNoise 实例。它接受一个参数,该参数可以是一个函数或者一个数字。如果参数是一个函数,它会调用该函数来生成随机数;如果参数是数字,它会使用这个数字来初始化噪声生成器的随机数种子。
  2. Permutation Table(置换表)

    • n 函数用于生成置换表,这是一个包含随机排列的字节数组。置换表用于在噪声计算中引入随机性。
    • i.prototype 对象包含了噪声生成的核心方法和数据,如 grad3 和 grad4 梯度数组,以及 noise2Dnoise3D 和 noise4D 方法,用于计算二维、三维和四维的简单噪声。
  3. 噪声计算方法

    • noise2D 方法接受两个参数 t 和 a,分别代表二维空间中的 x 和 y 坐标,返回一个介于 -1 和 1 之间的噪声值。
    • noise3D 方法接受三个参数 re 和 a,分别代表三维空间中的 xy 和 z 坐标,同样返回一个介于 -1 和 1 之间的噪声值。
    • noise4D 方法接受四个参数 ret 和 i,分别代表四维空间中的四个坐标轴,返回一个噪声值。
  4. 兼容性和模块导出

    • 代码的最后部分检查了 defineexports 和 window 对象是否存在,以确定如何导出 SimplexNoise 类。如果使用 AMD(异步模块定义)规范,则通过 define 函数导出;如果使用 CommonJS 规范(如 Node.js 环境),则通过 module.exports 导出;如果运行在浏览器环境中,则将 SimplexNoise 添加到 window 对象上。

        总的来说,这段代码提供了一个完整的简单噪声生成器实现,可以用于各种需要自然随机性的场景。通过提供不同维度的噪声计算方法,它为开发者提供了灵活性,可以根据具体需求选择合适的噪声维度。

!function(){"use strict";var r=.5*(Math.sqrt(3)-1),e=(3-Math.sqrt(3))/6,t=1/6,a=(Math.sqrt(5)-1)/4,o=(5-Math.sqrt(5))/20;function i(r){var e;e="function"==typeof r?r:r?function(){var r=0,e=0,t=0,a=1,o=(i=4022871197,function(r){r=r.toString();for(var e=0;e<r.length;e++){var t=.02519603282416938*(i+=r.charCodeAt(e));t-=i=t>>>0,i=(t*=i)>>>0,i+=4294967296*(t-=i)}return 2.3283064365386963e-10*(i>>>0)});var i;r=o(" "),e=o(" "),t=o(" ");for(var n=0;n<arguments.length;n++)(r-=o(arguments[n]))<0&&(r+=1),(e-=o(arguments[n]))<0&&(e+=1),(t-=o(arguments[n]))<0&&(t+=1);return o=null,function(){var o=2091639*r+2.3283064365386963e-10*a;return r=e,e=t,t=o-(a=0|o)}}(r):Math.random,this.p=n(e),this.perm=new Uint8Array(512),this.permMod12=new Uint8Array(512);for(var t=0;t<512;t++)this.perm[t]=this.p[255&t],this.permMod12[t]=this.perm[t]%12}function n(r){var e,t=new Uint8Array(256);for(e=0;e<256;e++)t[e]=e;for(e=0;e<255;e++){var a=e+~~(r()*(256-e)),o=t[e];t[e]=t[a],t[a]=o}return t}i.prototype={grad3:new Float32Array([1,1,0,-1,1,0,1,-1,0,-1,-1,0,1,0,1,-1,0,1,1,0,-1,-1,0,-1,0,1,1,0,-1,1,0,1,-1,0,-1,-1]),grad4:new Float32Array([0,1,1,1,0,1,1,-1,0,1,-1,1,0,1,-1,-1,0,-1,1,1,0,-1,1,-1,0,-1,-1,1,0,-1,-1,-1,1,0,1,1,1,0,1,-1,1,0,-1,1,1,0,-1,-1,-1,0,1,1,-1,0,1,-1,-1,0,-1,1,-1,0,-1,-1,1,1,0,1,1,1,0,-1,1,-1,0,1,1,-1,0,-1,-1,1,0,1,-1,1,0,-1,-1,-1,0,1,-1,-1,0,-1,1,1,1,0,1,1,-1,0,1,-1,1,0,1,-1,-1,0,-1,1,1,0,-1,1,-1,0,-1,-1,1,0,-1,-1,-1,0]),noise2D:function(t,a){var o,i,n=this.permMod12,f=this.perm,s=this.grad3,v=0,h=0,l=0,u=(t+a)*r,d=Math.floor(t+u),p=Math.floor(a+u),M=(d+p)*e,m=t-(d-M),c=a-(p-M);m>c?(o=1,i=0):(o=0,i=1);var y=m-o+e,w=c-i+e,g=m-1+2*e,A=c-1+2*e,x=255&d,q=255&p,D=.5-m*m-c*c;if(D>=0){var S=3*n[x+f[q]];v=(D*=D)*D*(s[S]*m+s[S+1]*c)}var U=.5-y*y-w*w;if(U>=0){var b=3*n[x+o+f[q+i]];h=(U*=U)*U*(s[b]*y+s[b+1]*w)}var F=.5-g*g-A*A;if(F>=0){var N=3*n[x+1+f[q+1]];l=(F*=F)*F*(s[N]*g+s[N+1]*A)}return 70*(v+h+l)},noise3D:function(r,e,a){var o,i,n,f,s,v,h,l,u,d,p=this.permMod12,M=this.perm,m=this.grad3,c=(r+e+a)*(1/3),y=Math.floor(r+c),w=Math.floor(e+c),g=Math.floor(a+c),A=(y+w+g)*t,x=r-(y-A),q=e-(w-A),D=a-(g-A);x>=q?q>=D?(s=1,v=0,h=0,l=1,u=1,d=0):x>=D?(s=1,v=0,h=0,l=1,u=0,d=1):(s=0,v=0,h=1,l=1,u=0,d=1):q<D?(s=0,v=0,h=1,l=0,u=1,d=1):x<D?(s=0,v=1,h=0,l=0,u=1,d=1):(s=0,v=1,h=0,l=1,u=1,d=0);var S=x-s+t,U=q-v+t,b=D-h+t,F=x-l+2*t,N=q-u+2*t,C=D-d+2*t,P=x-1+.5,T=q-1+.5,_=D-1+.5,j=255&y,k=255&w,z=255&g,B=.6-x*x-q*q-D*D;if(B<0)o=0;else{var E=3*p[j+M[k+M[z]]];o=(B*=B)*B*(m[E]*x+m[E+1]*q+m[E+2]*D)}var G=.6-S*S-U*U-b*b;if(G<0)i=0;else{var H=3*p[j+s+M[k+v+M[z+h]]];i=(G*=G)*G*(m[H]*S+m[H+1]*U+m[H+2]*b)}var I=.6-F*F-N*N-C*C;if(I<0)n=0;else{var J=3*p[j+l+M[k+u+M[z+d]]];n=(I*=I)*I*(m[J]*F+m[J+1]*N+m[J+2]*C)}var K=.6-P*P-T*T-_*_;if(K<0)f=0;else{var L=3*p[j+1+M[k+1+M[z+1]]];f=(K*=K)*K*(m[L]*P+m[L+1]*T+m[L+2]*_)}return 32*(o+i+n+f)},noise4D:function(r,e,t,i){var n,f,s,v,h,l,u,d,p,M,m,c,y,w,g,A,x,q=this.perm,D=this.grad4,S=(r+e+t+i)*a,U=Math.floor(r+S),b=Math.floor(e+S),F=Math.floor(t+S),N=Math.floor(i+S),C=(U+b+F+N)*o,P=r-(U-C),T=e-(b-C),_=t-(F-C),j=i-(N-C),k=0,z=0,B=0,E=0;P>T?k++:z++,P>_?k++:B++,P>j?k++:E++,T>_?z++:B++,T>j?z++:E++,_>j?B++:E++;var G=P-(l=k>=3?1:0)+o,H=T-(u=z>=3?1:0)+o,I=_-(d=B>=3?1:0)+o,J=j-(p=E>=3?1:0)+o,K=P-(M=k>=2?1:0)+2*o,L=T-(m=z>=2?1:0)+2*o,O=_-(c=B>=2?1:0)+2*o,Q=j-(y=E>=2?1:0)+2*o,R=P-(w=k>=1?1:0)+3*o,V=T-(g=z>=1?1:0)+3*o,W=_-(A=B>=1?1:0)+3*o,X=j-(x=E>=1?1:0)+3*o,Y=P-1+4*o,Z=T-1+4*o,$=_-1+4*o,rr=j-1+4*o,er=255&U,tr=255&b,ar=255&F,or=255&N,ir=.6-P*P-T*T-_*_-j*j;if(ir<0)n=0;else{var nr=q[er+q[tr+q[ar+q[or]]]]%32*4;n=(ir*=ir)*ir*(D[nr]*P+D[nr+1]*T+D[nr+2]*_+D[nr+3]*j)}var fr=.6-G*G-H*H-I*I-J*J;if(fr<0)f=0;else{var sr=q[er+l+q[tr+u+q[ar+d+q[or+p]]]]%32*4;f=(fr*=fr)*fr*(D[sr]*G+D[sr+1]*H+D[sr+2]*I+D[sr+3]*J)}var vr=.6-K*K-L*L-O*O-Q*Q;if(vr<0)s=0;else{var hr=q[er+M+q[tr+m+q[ar+c+q[or+y]]]]%32*4;s=(vr*=vr)*vr*(D[hr]*K+D[hr+1]*L+D[hr+2]*O+D[hr+3]*Q)}var lr=.6-R*R-V*V-W*W-X*X;if(lr<0)v=0;else{var ur=q[er+w+q[tr+g+q[ar+A+q[or+x]]]]%32*4;v=(lr*=lr)*lr*(D[ur]*R+D[ur+1]*V+D[ur+2]*W+D[ur+3]*X)}var dr=.6-Y*Y-Z*Z-$*$-rr*rr;if(dr<0)h=0;else{var pr=q[er+1+q[tr+1+q[ar+1+q[or+1]]]]%32*4;h=(dr*=dr)*dr*(D[pr]*Y+D[pr+1]*Z+D[pr+2]*$+D[pr+3]*rr)}return 27*(n+f+s+v+h)}},i._buildPermutationTable=n,"undefined"!=typeof define&&define.amd&&define(function(){return i}),"undefined"!=typeof exports?exports.SimplexNoise=i:"undefined"!=typeof window&&(window.SimplexNoise=i),"undefined"!=typeof module&&(module.exports=i)}();

效果图

【HTML】制作一个简单的线性动画,经验分享类,# 前端 后端,html,前端【HTML】制作一个简单的线性动画,经验分享类,# 前端 后端,html,前端【HTML】制作一个简单的线性动画,经验分享类,# 前端 后端,html,前端【HTML】制作一个简单的线性动画,经验分享类,# 前端 后端,html,前端【HTML】制作一个简单的线性动画,经验分享类,# 前端 后端,html,前端【HTML】制作一个简单的线性动画,经验分享类,# 前端 后端,html,前端

总结

  1. HTML

    • 定义了一个网页的基本结构,包括DOCTYPE声明、html、head和body标签。
    • 在head部分,设置了页面字符集为UTF-8,并定义了网页标题。
    • 引入了一个外部CSS文件normalize.min.css用于样式重置,以及两个JavaScript文件simplex-noise.min.jsscript.js,这些文件将用于网页的样式和行为。
  2. CSS

    • 包含了一系列的CSS规则,用于重置和标准化HTML元素的默认样式,以确保在不同浏览器中具有一致的表现。
    • 涉及的样式包括按钮、表单元素、媒体元素等的显示方式、字体、外边距、内边距和边框样式。
    • 还包括了一些针对HTML5新语义元素的样式设置,如articleasidefooter等。
  3. JavaScript文章来源地址https://www.toymoban.com/news/detail-848901.html

    • 定义了一系列的类和方法,用于生成随机数、颜色、渐变色、计算帧率(FPS)、处理向量运算、碰撞检测、计时和动画定时。
    • Utils类提供了生成随机数和颜色的方法,以及创建渐变色和计算FPS的功能。
    • Vector2d类表示二维向量,提供了一系列向量运算的方法,如缩放、加法、减法、取反、归一化和旋转。
    • Collision类处理对象之间的碰撞检测和碰撞反弹。
    • Stopwatch类用于计时,提供了开始、停止、获取经过时间、检查是否正在运行和重置计时器的方法。
    • AnimationTimer类用于动画定时,支持不同的缓动函数,如Ease-In、Ease-Out、Ease-In-Out、Elastic和Bounce。
    • Angle类用于表示角度,可以增加或减少角度值,并将其转换为弧度。
    • Canvas类用于创建和管理分形图形的绘制,提供了初始化、渲染、绘制帧率和响应窗口大小变化的方法。
    • PointObjFractalRoot类用于生成分形图形的结构和绘制。
    • Branch类表示分形中的一个分支,负责计算分支的中间点、结构点,并绘制分支。
    • 最后,自执行函数用于初始化Canvas类,并设置窗口大小变化的事件监听器。
    • 另外,还有一个SimplexNoise类,用于生成多维的简单噪声,这在计算机图形学中非常有用,可以用于创建自然纹理或形状。

到了这里,关于【HTML】制作一个简单的线性动画的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • 使用HTML+CSS制作一个简单的网页

    简单学习了一下HTML和CSS,制作了下面这个网页(第一次做还在学习中),里面包含一些基础的布局包括 导航条、分页栏、悬浮列表 等内容。 网页预览 (网页中的图片与图标均来自阿里巴巴矢量图标库) CSS代码 里面包含悬浮、画面自适应等效果

    2024年02月11日
    浏览(75)
  • 【HTML】简单制作一个动态3D正方体

     目录 前言 开始 HTML部分 JS部分 CSS部分 效果图 总结           无需多言,本文将详细介绍一段代码,具体内容如下:           首先新建文件夹,创建两个文本文档,其中HTML的文件名改为[index.html],JS的文件名改为[script.js],CSS的文件名改为[style.css],创建好后右键用文本

    2024年04月11日
    浏览(39)
  • 制作一个简单HTML中华传统文化网页(HTML+CSS)

    🎉精彩专栏推荐 💭文末获取联系 ✍️ 作者简介: 一个热爱把逻辑思维转变为代码的技术博主 💂 作者主页: 【主页——🚀获取更多优质源码】 🎓 web前端期末大作业: 【📚毕设项目精品实战案例 (1000套) 】 🧡 程序员有趣的告白方式:【💌HTML七夕情人节表白网页制作 (

    2024年02月08日
    浏览(65)
  • 制作一个简单HTML校园网页(HTML+CSS)学校网站制作 校园网站设计与实现

    🎉精彩专栏推荐👇🏻👇🏻👇🏻 ✍️ 作者简介: 一个热爱把逻辑思维转变为代码的技术博主 💂 作者主页: 【主页——🚀获取更多优质源码】 🎓 web前端期末大作业: 【📚毕设项目精品实战案例 (1000套) 】 🧡 程序员有趣的告白方式:【💌HTML七夕情人节表白网页制作

    2024年01月16日
    浏览(53)
  • HTML和CSS配合制作一个简单的登录界面

    这是一个CSS样式表,用于为网页中的HTML元素设置样式。接下来我会逐句解释每个选择器和样式的作用。 *{ box-sizing: border-box; } :这行代码将所有HTML元素的盒模型设置为 border-box ,使元素的宽高包括内容、内边距和边框,而不仅仅是内容。 body{ font-family: Arial, Helvetica, sans-ser

    2024年02月12日
    浏览(44)
  • 制作一个简单HTML传统端午节日网页(HTML+CSS)7页 带报告

    ⛵ 源码获取 文末联系 ✈ Web前端开发技术 描述 网页设计题材,DIV+CSS 布局制作,HTML+CSS网页设计期末课程大作业 | 传统春节网页设计 | 圣诞节节日发展 | 中秋 | 端午传统节日习俗庆祝 | 地区特色 | 网站模板 | 等网站的设计与制 | HTML期末大学生网页设计作业 HTML:结构 CSS:样式

    2024年02月09日
    浏览(54)
  • 制作一个简单HTML个人网页网页(HTML+CSS)大话西游之大圣娶亲电影网页设计

    HTML实例网页代码, 本实例适合于初学HTML的同学。该实例里面有设置了css的样式设置,有div的样式格局,这个实例比较全面,有助于同学的学习,本文将介绍如何通过从头开始设计个人网站并将其转换为代码的过程来实践设计。 ❤ 【作者主页——🔥获取更多优质源码】 ❤ 【学

    2024年02月04日
    浏览(53)
  • 一个简单的HTML网页(千与千寻电影) 大二学生网页设计与制作 电影主题网页制作

    HTML实例网页代码, 本实例适合于初学HTML的同学。该实例里面有设置了css的样式设置,有div的样式格局,这个实例比较全面,有助于同学的学习,本文将介绍如何通过从头开始设计个人网站并将其转换为代码的过程来实践设计。 1 网页简介 :此作品为学生个人主页网页设计题材

    2024年02月06日
    浏览(54)
  • HTML5 Canvas API制作一个简单的猜字单机游戏

    这篇文章主要介绍了借助HTML5 Canvas API制作一个简单的猜字单机游戏的实例分享,游戏中每局会自动生成一个字母,玩家按键盘来猜测该字母是哪一个,需要的朋友可以参考下 HTML代码 !doctype html   html lang=\\\"en\\\"       head           meta charset=\\\"utf-8\\\" /           script 

    2024年02月16日
    浏览(47)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包