用前端html如何实现2024烟花效果
用HTML、CSS和JavaScript编写的网页,主要用于展示“2024新年快乐!”的文字形式烟花效果。下面是对代码主要部分的分析:
HTML结构
- 包含三个
<canvas>
元素,用于绘制动画。 - 引入百度统计的脚本。
CSS样式
- 设置
body
的背景为黑色,并使得canvas
元素绝对定位,覆盖整个页面。
JavaScript 功能
-
百度统计脚本:页面开始时引入了百度统计的脚本,用于网页访问数据分析。
-
获取URL参数:
GetRequest
函数用于解析URL中的查询字符串参数。 -
烟花碎片(Shard)类:
- 每个
Shard
代表烟花爆炸后的一个碎片。 - 包含碎片的位置、颜色、大小、速度等属性。
draw
方法用于在canvas上绘制碎片。update
方法用于更新碎片的位置和状态。
- 每个
-
火箭(Rocket)类:
- 表示发射的烟花火箭。
- 包含火箭的位置、速度、颜色等属性。
draw
方法用于在canvas上绘制火箭。update
方法用于更新火箭的位置。explode
方法用于模拟火箭爆炸,生成多个Shard
实例。
-
初始化和动画循环:
- 获取所有canvas元素和对应的2D渲染上下文。
- 根据屏幕大小调整字体大小,以适应屏幕宽度,并在一个
canvas
上绘制“2024新年快乐!”文字。 - 通过读取绘制的文字的像素数据,确定烟花爆炸的目标位置。
- 使用
requestAnimationFrame
创建动画循环,不断更新和绘制火箭和碎片,模拟烟花效果。
-
辅助函数:
lerp
(线性插值函数):用于平滑地在两个值之间插值,常用于动画效果中。
-
执行流程:
-
页面加载完成后,动画循环开始运行。
-
每隔一定帧数,生成一个新的
Rocket
实例,模拟火箭发射。 -
当火箭达到一定高度后,调用
explode
方法,生成多个Shard
实例,模拟烟花爆炸。 -
碎片根据预设的目标位置移动,最终形成“2024新年快乐!”的文字形状。
<!DOCTYPE html> <html lang="en"> <script>var _hmt = _hmt || [];(function () {var hm = document.createElement("script");hm.src = "https://hm.baidu.com/hm.js?c923daf3182a4b0ce01878475080aadc";var s = document.getElementsByTagName("script")[0];s.parentNode.insertBefore(hm, s);})(); </script><head><meta charset="UTF-8"><title>2024,新年快乐!</title> </head> <style>body {margin: 0;overflow: hidden;background: black;}canvas {position: absolute;} </style><body><canvas></canvas><canvas></canvas><canvas></canvas><script>function GetRequest() {var url = decodeURI(location.search); //获取url中"?"符后的字串var theRequest = new Object();if (url.indexOf("?") != -1) {var str = url.substr(1);strs = str.split("&");for (var i = 0; i < strs.length; i++) {theRequest[strs[i].split("=")[0]] = unescape(strs[i].split("=")[1]);}}return theRequest;}class Shard {constructor(x, y, hue) {this.x = x;this.y = y;this.hue = hue;this.lightness = 50;this.size = 15 + Math.random() * 10;const angle = Math.random() * 2 * Math.PI;const blastSpeed = 1 + Math.random() * 6;this.xSpeed = Math.cos(angle) * blastSpeed;this.ySpeed = Math.sin(angle) * blastSpeed;this.target = getTarget();this.ttl = 100;this.timer = 0;}draw() {ctx2.fillStyle = `hsl(${this.hue}, 100%, ${this.lightness}%)`;ctx2.beginPath();ctx2.arc(this.x, this.y, this.size, 0, 2 * Math.PI);ctx2.closePath();ctx2.fill();}update() {if (this.target) {const dx = this.target.x - this.x;const dy = this.target.y - this.y;const dist = Math.sqrt(dx * dx + dy * dy);const a = Math.atan2(dy, dx);const tx = Math.cos(a) * 5;const ty = Math.sin(a) * 5;this.size = lerp(this.size, 1.5, 0.05);if (dist < 5) {this.lightness = lerp(this.lightness, 100, 0.01);this.xSpeed = this.ySpeed = 0;this.x = lerp(this.x, this.target.x + fidelity / 2, 0.05);this.y = lerp(this.y, this.target.y + fidelity / 2, 0.05);this.timer += 1;} elseif (dist < 10) {this.lightness = lerp(this.lightness, 100, 0.01);this.xSpeed = lerp(this.xSpeed, tx, 0.1);this.ySpeed = lerp(this.ySpeed, ty, 0.1);this.timer += 1;} else {this.xSpeed = lerp(this.xSpeed, tx, 0.02);this.ySpeed = lerp(this.ySpeed, ty, 0.02);}} else {this.ySpeed += 0.05;//this.xSpeed = lerp(this.xSpeed, 0, 0.1);this.size = lerp(this.size, 1, 0.05);if (this.y > c2.height) {shards.forEach((shard, idx) => {if (shard === this) {shards.splice(idx, 1);}});}}this.x = this.x + this.xSpeed;this.y = this.y + this.ySpeed;}}class Rocket {constructor() {const quarterW = c2.width / 4;this.x = quarterW + Math.random() * (c2.width - quarterW);this.y = c2.height - 15;this.angle = Math.random() * Math.PI / 4 - Math.PI / 6;this.blastSpeed = 6 + Math.random() * 7;this.shardCount = 15 + Math.floor(Math.random() * 15);this.xSpeed = Math.sin(this.angle) * this.blastSpeed;this.ySpeed = -Math.cos(this.angle) * this.blastSpeed;this.hue = Math.floor(Math.random() * 360);this.trail = [];}draw() {ctx2.save();ctx2.translate(this.x, this.y);ctx2.rotate(Math.atan2(this.ySpeed, this.xSpeed) + Math.PI / 2);ctx2.fillStyle = `hsl(${this.hue}, 100%, 50%)`;ctx2.fillRect(0, 0, 5, 15);ctx2.restore();}update() {this.x = this.x + this.xSpeed;this.y = this.y + this.ySpeed;this.ySpeed += 0.1;}explode() {for (let i = 0; i < 70; i++) {shards.push(new Shard(this.x, this.y, this.hue));}}}console.log(GetRequest('val').val)// INITIALIZATIONconst [c1, c2, c3] = document.querySelectorAll('canvas');const [ctx1, ctx2, ctx3] = [c1, c2, c3].map(c => c.getContext('2d'));let fontSize = 200;const rockets = [];const shards = [];const targets = [];const fidelity = 3;let counter = 0;c2.width = c3.width = window.innerWidth;c2.height = c3.height = window.innerHeight;ctx1.fillStyle = '#000';const text = '2024新年快乐!'let textWidth = 99999999;while (textWidth > window.innerWidth) {ctx1.font = `900 ${fontSize--}px Arial`;textWidth = ctx1.measureText(text).width;}c1.width = textWidth;c1.height = fontSize * 1.5;ctx1.font = `900 ${fontSize}px Arial`;ctx1.fillText(text, 0, fontSize);const imgData = ctx1.getImageData(0, 0, c1.width, c1.height);for (let i = 0, max = imgData.data.length; i < max; i += 4) {const alpha = imgData.data[i + 3];const x = Math.floor(i / 4) % imgData.width;const y = Math.floor(i / 4 / imgData.width);if (alpha && x % fidelity === 0 && y % fidelity === 0) {targets.push({ x, y });}}ctx3.fillStyle = '#FFF';ctx3.shadowColor = '#FFF';ctx3.shadowBlur = 25;// ANIMATION LOOP(function loop() {ctx2.fillStyle = "rgba(0, 0, 0, .1)";ctx2.fillRect(0, 0, c2.width, c2.height);//ctx2.clearRect(0, 0, c2.width, c2.height);counter += 1;if (counter % 15 === 0) {rockets.push(new Rocket());}rockets.forEach((r, i) => {r.draw();r.update();if (r.ySpeed > 0) {r.explode();rockets.splice(i, 1);}});shards.forEach((s, i) => {s.draw();s.update();if (s.timer >= s.ttl || s.lightness >= 99) {ctx3.fillRect(s.target.x, s.target.y, fidelity + 1, fidelity + 1);shards.splice(i, 1);}});requestAnimationFrame(loop);})();// HELPER FUNCTIONSconst lerp = (a, b, t) => Math.abs(b - a) > 0.1 ? a + t * (b - a) : b;function getTarget() {if (targets.length > 0) {const idx = Math.floor(Math.random() * targets.length);let { x, y } = targets[idx];targets.splice(idx, 1);x += c2.width / 2 - textWidth / 2;y += c2.height / 2 - fontSize / 2;return { x, y };}}</script></body></html>
步骤 1: 页面结构和引入脚本
-
HTML定义了三个
canvas
元素用于绘制烟花动画。 -
引入百度统计脚本,用于收集页面访问数据。
-
步骤 2: 样式设置
-
页面背景设置为黑色,
canvas
元素被设置为绝对定位,覆盖整个屏幕。 -
步骤 3: JavaScript 功能实现
3.1 获取URL参数
-
GetRequest
函数解析当前URL的查询字符串,将参数保存在一个对象中返回。 -
3.2 定义烟花碎片(Shard)类
-
每个
Shard
实例代表烟花爆炸后的一个碎片。 -
包含位置、颜色、大小、速度等属性。
-
draw
方法用于绘制碎片。 -
update
方法用于更新碎片的状态和位置,包括模拟重力影响和向目标位置移动。 -
3.3 定义火箭(Rocket)类
-
每个
Rocket
实例代表一个发射的烟花火箭。 -
包含位置、速度、颜色等属性。
-
draw
方法用于绘制火箭。 -
update
方法用于更新火箭的位置,模拟火箭上升。 -
3.4 初始化和动画循环
-
初始化:根据屏幕大小调整字体大小,确保“2024新年快乐!”文字适应屏幕宽度,并在
canvas
上绘制该文字。通过读取文字像素数据来确定烟花爆炸的目标位置。 -
动画循环:使用
requestAnimationFrame
循环不断更新和绘制火箭和碎片,以及检测碎片是否达到目标位置或生命周期结束。 -
3.5 辅助函数
-
lerp
函数:用于在两个数值之间进行线性插值,帮助平滑动画效果。 -
步骤 4: 执行动画
-
初始化画布:调整画布大小以适应窗口,绘制“2024新年快乐!”文字,并基于此文字的像素数据确定烟花目标位置。
-
启动动画循环:
- 每隔一定时间间隔,创建一个新的
Rocket
实例,模拟火箭发射。 - 更新每个火箭的位置,当火箭达到一定高度时触发爆炸,生成多个
Shard
实例。 - 更新每个
Shard
的位置,使其朝目标位置移动。 - 当
Shard
到达目标位置或生命周期结束时,从数组中移除。
- 每隔一定时间间隔,创建一个新的
-
渲染烟花效果:通过不断更新
canvas
上的火箭和碎片位置,以及绘制这些元素,形成动态的烟花效果。碎片最终会根据预设的目标位置排列,形成“2024新年快乐!”的文字形状。 -
通过这些步骤,代码实现了一个视觉吸引的新年烟花祝福动画,既展示了编程技巧,也增添了节日气氛。
-
explode
方法在火箭达到顶点时被调用,生成多个Shard
实例。
-
相关文章:

用前端html如何实现2024烟花效果
用HTML、CSS和JavaScript编写的网页,主要用于展示“2024新年快乐!”的文字形式烟花效果。下面是对代码主要部分的分析: HTML结构 包含三个<canvas>元素,用于绘制动画。引入百度统计的脚本。 CSS样式 设置body的背景为黑…...

Redis应用-在用户数据里的应用
1.社区电商的业务闭环 接下来介绍的社区电商是以Redis作为主体技术、以MySQL和RocketMQ作为辅助技术实现的。 (1)社区电商运作模式 社区电商的关键点在于社区,而电商则是辅助性质(次要地位,流量变现)。社区可以分成很多种社区,比如美食社区、美妆社区、影评社区、妈妈社区…...

C++ 中面向对象编程如实现数据隐藏
在C中,面向对象编程(OOP)通过封装(Encapsulation)来实现数据隐藏。封装是OOP的一个核心概念,它允许将对象的属性和行为(即数据和方法)组合在一起,并对外隐藏对象的内部实…...

JavaEE 【知识改变命运】04 多线程(3)
文章目录 多线程带来的风险-线程安全线程不安全的举例分析产出线程安全的原因:1.线程是抢占式的2. 多线程修改同一个变量(程序的要求)3. 原子性4. 内存可见性5. 指令重排序 总结线程安全问题产生的原因解决线程安全问题1. synchronized关键字…...

gz中生成模型
生成模型 通过服务调用生成 还记得parameter_bridge 吗? 我们在生成桥接的时候调用了这个cpp文件。 一个 parameter_bridge 实例用于消息传递(传感器数据)。之前的例子 另一个 parameter_bridge 实例用于服务桥接(动态生成模型…...

前端(Axios和Promis)
Promise 语法 <script>// 创建promise对象// 此函数需要再传入两个参数,都是函数类型let pnew Promise((resolve,reject)>{if(3>2){resolve({name:"李思蕾",age:23,地址:"河南省"});}else{reject("error");}});console.log(p);p.th…...

AI Agent:重塑业务流程自动化的未来力量(2/30)
《AI Agent:重塑业务流程自动化的未来力量》 摘要:整体思路是先介绍 AI Agent 的基本情况,再深入阐述其实现业务流程自动化的方法和在不同领域的应用,接着分析其价值和面临的挑战,最后得出结论,为读者全面…...

前端页面导出word
html-docx-js bug: vite使用html-docx.js会报错,点击下载上方文件替换即可 正文 npm install html-docx-js -S npm install file-saver -S<template><div id"managerReport">word内容......</div> </template><script>&l…...

【考前预习】1.计算机网络概述
往期推荐 子网掩码、网络地址、广播地址、子网划分及计算-CSDN博客 一文搞懂大数据流式计算引擎Flink【万字详解,史上最全】-CSDN博客 浅学React和JSX-CSDN博客 浅谈云原生--微服务、CICD、Serverless、服务网格_云原生 serverless-CSDN博客 浅谈维度建模、数据分析…...

ubuntu20.04复现 Leg-KILO
这里写目录标题 opencv版本问题下载3.2.0源代码进入解压后的目录创建构建目录运行 CMake 配置 配置时指定一个独立的安装目录,例如 /opt/opencv-3.2:出错: 使用多线程编译错误1: stdlib.h: 没有那个文件或目录错误2:er…...

Ensembl数据库下载参考基因组(常见模式植物)bioinfomatics 工具37
拟南芥参考基因组_拟南芥数据库-CSDN博客 1 Ensembl数据库网址 http://plants.ensembl.org/index.html #官网 如拟南芥等 那么问题来了,基因组fa文件和gff文件在哪里? 2 参考案例 拟南芥基因组fa在这里 注释gff文件在这里...

简单介绍web开发和HTML CSS_web网站开发流程
一、Web 开发:探索互联网世界的基石 1.1 什么是 Web 开发 Web 开发,简单来说,就是构建能够通过浏览器访问的网站的过程。Web 代表着全球广域网,也就是我们熟知的万维网(www),它连接着世界各地的…...

Docker 中使用 PHP 通过 Canal 同步 Mysql 数据到 ElasticSearch
一、Mysql 的安装和配置 1.使用 docker 安装 mysql,并且映射端口和 root 账号的密码 # 获取镜像 docker pull mysql:8.0.40-debian# 查看镜像是否下载成功 docker images# 运行msyql镜像 docker run -d -p 3388:3306 --name super-mysql -e MYSQL_ROOT_PASSWORD12…...

数据结构之五:排序
void*类型的实现:排序(void*类型)-CSDN博客 一、插入排序 1、直接插入排序 思想:把待排序的数据逐个插入到一个已经排好序的有序序列中,直到所有的记录插入完为止,得到一个新的有序序列 。 单趟&#x…...

科研绘图系列:R语言绘制热图和散点图以及箱线图(pheatmap, scatterplot boxplot)
禁止商业或二改转载,仅供自学使用,侵权必究,如需截取部分内容请后台联系作者! 文章目录 介绍加载R包数据下载图1图2图3系统信息参考介绍 R语言绘制热图和散点图以及箱线图(pheatmap, scatterplot & boxplot) 加载R包 library(magrittr) library(dplyr) library(ve…...

基于 webRTC Vue 的局域网 文件传输工具
文件传输工具,匿名加密,只需访问网页,即可连接到其他设备,基于 webRTC 和 Vue.js coturn TURN 服务器 docker pull coturn/coturn docker run -d --networkhost \-v $(pwd)/my.conf:/etc/coturn/turnserver.conf \coturn/coturn…...

LeetCode 718. 最长重复子数组 java题解
https://leetcode.cn/problems/maximum-length-of-repeated-subarray/description/ 动态规划 class Solution {public int findLength(int[] nums1, int[] nums2) {int len1nums1.length,len2nums2.length;int[][] dpnew int[len11][len21];dp[0][0]0;//没有意义,…...

算法知识-15-深搜
一、概念 深度优先搜索(Deep First Search, DFS)是一种用于遍历或搜索树或图的算法。这种策略沿着树的深度遍历树的节点,尽可能深地搜索树的分支。 二、关键步骤 选择起点:根据题目要求,选择一个或多个节点作为搜索…...

区块链dapp 开发详解(VUE3.0)
1、安装metamask 插件。 2、使用封装的工具包: wagmi . 3、 wagmi 操作手册地址:connect | Wagmi 4、注意事项: 因为最初是react 版本,所以在VUE版的官方文档有很多地方在 import 用的是 wagmi,需要改为 wagmi/vue 。 连接成功后打印的内容如下&…...

Plugin [id: ‘flutter‘] was not found in any of the following sources解决方法
文章目录 错误描述解决方法修正方案:继续使用 apply from修正后的 build.gradle说明警告的处理进一步验证 错误描述 Plugin [id: ‘flutter’] was not found in any of the following sources: Gradle Core Plugins (not a core plugin, please see https://docs…...

专升本-高数 1
第 0 章,基础知识 一,重要公式 1、完全平方 (ab)a2abb (a-b)a-2abb 2、平方差公式 (a-b)(ab)a-b 3、立方差公式 a-b(a-b)(aabb) 4、 立方和公式 ab(ab)(a-abb) 二,基本初等函数 1,幂函数 一元二…...

【考前预习】3.计算机网络—数据链路层
往期推荐 【考前预习】2.计算机网络—物理层-CSDN博客 【考前预习】1.计算机网络概述-CSDN博客 浅谈云原生--微服务、CICD、Serverless、服务网格_云原生cicd-CSDN博客 子网掩码、网络地址、广播地址、子网划分及计算_子网广播地址-CSDN博客 浅学React和JSX-CSDN博客 目录 1.数…...

DockeUI 弱口令登录漏洞+未授权信息泄露
0x01 产品描述: DockerUI是一款开源的、强大的、轻量级的Docker管理工具。DockerUI覆盖了 docker cli 命令行 95% 以上的命令功能,通过可视化的界面,即使是不熟悉docker命令的用户也可以非常方便的进行Docker和Docker Swarm集群进行管理和维护。0x02 漏洞描述: DockerUI中存…...

【电子元器件】电感基础知识
本文章是笔者整理的备忘笔记。希望在帮助自己温习避免遗忘的同时,也能帮助其他需要参考的朋友。如有谬误,欢迎大家进行指正。 一、 电感的基本工作原理 1. 电感的基本工作原理如下: (1) 当线圈中有电流通过时&#…...

【SSH+X11】VsCode使用Remote-SSH在远程服务器的docker中打开Rviz
🚀今天来分享一下通过VsCode的Remote-SSH插件在远程服务器的docker中打开Rviz进行可视化的方法。 具体流程如下图所示,在操作开始前,请先重启设备,排除之前运行配置的影响: ⭐️ 我这里是使用主机连接服务器ÿ…...

Vue Web开发(五)
1. axios axios官方文档 异步库axios和mockjs模拟后端数据,axios是一个基于promise的HTTP库,使用npm i axios。在main.js中引入,需要绑定在Vue的prototype属性上,并重命名。 (1)main.js文件引用 imp…...

HarmonyOS:使用Grid构建网格
一、概述 网格布局是由“行”和“列”分割的单元格所组成,通过指定“项目”所在的单元格做出各种各样的布局。网格布局具有较强的页面均分能力,子组件占比控制能力,是一种重要自适应布局,其使用场景有九宫格图片展示、日历、计算器…...

开源Java快速自测工具,可以调用系统内任意一个方法
java快速测试框架,可以调到系统内任意一个方法,告别写单测和controller的困扰。 开源地址:https://gitee.com/missyouch/Easy-JTest 我们在开发时很多时候想要测试下自己的代码,特别是service层或者是更底层的代码,就…...

力扣刷题TOP101: 29.BM36 判断是不是平衡二叉树
目录: 目的 思路 复杂度 记忆秘诀 python代码 目的: 输入一棵节点数为 n 二叉树,判断该二叉树是否是平衡二叉树。 思路 什么是平衡二叉树(AVL 树)? 每个节点的左子树和右子树的高度差不能超过 1。确保…...

【在Linux世界中追寻伟大的One Piece】自旋锁
目录 1 -> 概述 2 -> 原理 3 -> 优缺点及使用场景 3.1 -> 优点 3.2 -> 缺点 3.3 -> 使用场景 4 -> 纯软件自旋锁类似的原理实现 4.1 -> 结论 5 -> 样例代码 1 -> 概述 自旋锁是一种多线程同步机制,用于保护共享资源避免受并…...