Bootstrap

使用 canvas 和面向对象思想绘制流星动画

本人也是前端小白,正在努力学习的路上奔跑~最近看到一位博主大大的绘制星空博文,加上最近对面向对象编程思想的理解,也照葫芦画瓢复现了一个demo,顺便熟悉一下canvas的一些API。

源代码

<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="UTF-8" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <title>StarSky</title>
  </head>
  <body></body>
  <style>
    * {
      margin: 0;
      padding: 0;
      width: 100vw;
      height: 100vh;
      overflow: hidden;
    }
  </style>
  <script>
    /**
     *  © WindyZ write in 2020
     *  进度表
     *  1125 完成初始化方法以及相关参数
     *       完成绘制背景,以及窗口大小改变的监听
     *  1126 完成月亮绘制,修复窗口大小监听无效的问题
     *  1127 完成星星绘制,未解决月亮周围减少星星问题
     *  1201 完成流星绘制,抽象出 Star 和 Commet 类
     *  1211 完成山体绘制,完成大体的动画
     */

    // 星星类
    class Star {
      x = 0; // x 坐标
      y = 0; // y 坐标
      opacity = 0; // 星星透明度
      radius = 0; // 星星半径
      is_weak = true; // 星星闪烁的时候,透明度是否先减小到0,再增加到1

      constructor(width, height, moon_radius) {
        this.init(width, height, moon_radius);
      }

      init(w, h, m_r) {
        this.x = Math.random() * w;
        this.y = Math.random() * h * 0.8;

        this.x >= w / 9 - m_r && this.x <= w / 9 + m_r * 3
          ? (this.x = this.x + (Math.random() >= 0.5 ? -m_r * 2 : m_r * 2))
          : "";

        this.y >= h / 9 - m_r && this.y <= h / 9 + m_r * 3
          ? (this.y = this.y + (Math.random() >= 0.5 ? -m_r * 2 : m_r * 2))
          : "";

        this.opacity = Math.random() * 1.1;
        this.radius = Math.random() * 0.8 + 0.5;
      }

      // 获得参数
      get getStarVal() {
        return {
          x: this.x,
          y: this.y,
          opacity: this.opacity,
          radius: this.radius,
          is_weak: this.is_weak,
        };
      }

      // 更改参数
      setStarVal(val) {
        if (!!val) {
          for (let key in val) {
            if (key == "x") {
              this.x = val[key];
            }
            if (key == "y") {
              this.y = val[key];
            }
            if (key == "opacity") {
              this.opacity = val[key];
            }
            if (key == "radius") {
              this.radius = val[key];
            }
            if (key == "is_weak") {
              this.is_weak = val[key];
            }
          }
        }
      }
    }

    // 流星类
    class Commet {
      x = 0; // 流星 x 坐标
      y = 0; // 流星 y 坐标
      radius = 0; // 流星半径
      opacity = 0; // 流星透明度
      tail_length = 0; // 流星尾巴长度
      tail_direct = 0; // 流星的方向,暂时未做开发
      ori_speed = 0; // 流星的初始速度
      velocity = 0; // 流星的加速度,一般来说是个负数,使速度递减

      constructor(width, height) {
        this.init(width, height);
      }

      // 初始化流星参数
      init(w, h) {
        this.x = Math.random() * w;
        this.y = Math.random() * h * 0.8;
        this.radius = Math.random() * 0.5 + 0.5;
        this.opacity = Math.random() * 0.7 + 0.4;
        this.tail_length = Math.random() * 15 + 25;
        this.ori_speed = Math.random() * 0.5 + 2;
        this.velocity = -(Math.random() * 0.005 + 0.005);
      }

      // 更改参数
      setCommetVal(val) {
        if (!!val) {
          for 
;