首页 > 作文

详解Canvas 实现炫丽的粒子运动效果(粒子生成文字)

更新时间:2023-04-03 08:18:34 阅读: 评论:0

没有最好,只有更好,如题所示,这篇文章只要是分享一个用 canvas 来实现的粒子运动效果。感觉有点标题党了,但换个角度,三八节最想说的话勉勉强强算是炫丽吧,虽然色彩上与炫丽无关,但运动效果上还是算得上有点点炫的。不管怎么样,我们还是开始这个所谓的炫丽效果吧!

直接上代码 ,不懂可以看代码注释。估计就会看明白大概的思路了。

html 代码

<!doctype html><html lang="en"><head><meta chart="utf-8"><title>canvas 实现炫丽的粒子运动效果-云库前端</title><style>* {    margin: 0;    padding: 0;}html,body {    width: 100%;    height: 100%;}canvas {    display: block;    background: #000;}body::-webkit-scrollbar{    display: none;}.operator-box{    position: fixed;    top: 0;    left: 50%;    border: 1px solid #fff;    background: rgba(255,255,255,0.5);    padding: 20px 10px;    -webkit-transform: translatex(-50%);    transform: translatex(-50%);}.back-type,.back-animate{    margin-right: 20px;}.flex-box{    display: flex;    justify-content: center;    align国企好还是央企好-items: center;}#input-text{    line-height: 35px;    width: 260px;    height: 35px;    background: rgba(0, 0, 0,0.7);    color: #fff;    font-size: 16px;    border: none;    outline: none;    text-indent: 12px;    box-shadow: int 0 0 12px 1px rgba(0,0,0,0.7);}#input-text::placeholder{    color: #ccc;    line-height: 55px;    height: 55px;}lect{    -webkit-appearance: none;    -moz-appearance: none;    appearance: none;    border: none;    padding: 0px 20px 0px 6px;    height: 35px;    color: #fff;    text-align: left;    background: rgba(0, 0, 0,0.7) url(data:image/png;ba64,ivborw0kggoaaaansuheugaaaauaaaaicayaaaax8tu7aaaaouleq…r4gpgweimaioybcs4c8zdairbq4gignkztqefmi6auqhesapmexiemiwfpaaaaaelftksuqmcc) no-repeat 190px 12px;    background-size: 5px 8px;    box-shadow: int 0 0 12px 1px rgba(0,0,0,0.7);}</style></head&更迭gt;<body><div class="operator-box"><div class="flex-box">    <div class="back-type">散开类型:        <lect name="" id="lecttype">            <option value="back">归位</option>            <option value="auto">随机</option>        </lect>    </div>    <div class="back-animate">散开效果(对归位有效):       <lect class="back-dynamics" id="lectdynamics">           <option value="spring">dynamics.spring</option>           <option value="bounce">dynamics.bounce</option>           <option value="forcewithgravity">dynamics.forcewithgravity</option>           <option value="gravity">dynamics.gravity</option>           <option value="eainout">dynamics.eainout</option>           <option value="eain">dynamics.eain</option>           <option value="eaout">dynamics.eaout</option>           <option value="linear">dynamics.linear</option>       </lect>    </div>    <div class="input-box"><input type="text" placeholder="输入汉字后回车" id="input-text"></div></div></div><script src="dynamics.min.js"></script><script src="index.js"></script><script>var icircle = new circle();</script></body></html>

html 代码不多,只要是几个操作元素。这里一看就明白。不费过多口舌。我们来看看本文的主角 javascript 代码,不过,在看代码前,我们不妨先听听实现这个效果的思路:

首先,我们得先生成一堆群众演员(粒子);把每个粒子的相关参数挂到自身的一些属性上,因为第个粒子都会有自己的运动轨迹;接着得让它们各自运动起来。运动有两种(自由运动和生成文字的运动);

javascript 代码中使用了三个 canvas 画布,this.icanvas(主场)、this.icanvascalculate(用来计算文字宽度)、this.icanvaspixel(用于画出文字,并从中得到文字对应的像素点的位置坐标)。

this.icanvascalculate 和 this.icanvaspixel 这两个无需在页面中显示出来,只是辅助作用。

下面就献上棒棒的 js 实现代码

function circle() {var this = this;this.init();this.generalrandomparam();this.drawcircles();this.ballanimate();this.geturtext();// 窗口改变大小后,生计算并获取画面window.onresize = function(){this.statew = document.body.offtwidth;this.stateh = document.body.offtheight;this.icanvasw = this.icanvas.width = this.statew;this.icanvash = this.icanvas.height = this.stateh;this.ctx = this.icanvas.getcontext("2d");}}// 初始化circle.prototype.init = function(){//父元素宽高this.statew = document.body.offtwidth;this.stateh = document.body.offtheight;this.icanvas = document.createelement("canvas");// 设置canvas 与父元素同宽高this.icanvasw = this.icanvas.width = this.statew;this.icanvash = this.icanvas.height = this.stateh;// 获取 2d 绘画环境this.ctx = this.icanvas.getcontext("2d");// 插入到 body 元素中document.body.appendchild(this.icanvas);this.icanvascalculate = document.createelement("canvas");// 用于保存计算文字宽度的画布this.mctx =  this.icanvascalculate.getcontext("2d");this.mctx.font = "128px 微软雅黑";this.icanvaspixel = document.createelement("canvas");this.icanvaspixel.tattribute("style","position:absolute;top:0;left:0;");this.pctx = null; // 用于绘画文字的画布// 随机生成圆的数量this.ballnumber = ramdomnumber(1000, 2000);// 保存所有小球的数组this.balls = [];// 保存动画中最后一个停止运动的小球this.animte = null;this.imagedata = null;this.textwidth = 0; // 保存生成文字的宽度this.textheight = 150; // 保存生成文字的高度this.inputtext = ""; // 保存用户输入的内容this.actioncount = 0;this.ballactor = []; // 保存生成文字的粒子this.actornumber = 0; // 保存生成文字的粒子数量this.backtype = "back"; // 归位this.backdynamics = ""; // 动画效果this.isplay = fal; // 标识(在生成文字过程中,不能再生成)}// 渲染出所有圆circle.prototype.drawcircles = function () {for(var i=0;i<this.ballnumber;i++){this.renderball(this.balls[0]);}}// 获取用户输入文字circle.prototype.geturtext = function(){this = this; // 保存 this 指向ipu = document.getelementbyid("input-text");ipu.addeventlistener("keydown",function(event){if(event.which === 13){ // 如果是回车键ipu.value = ipu.value.trim(); // 去头尾空格var pat = /[\u4e00-\u9fa5]/; // 中文判断var ischine = pat.test(ipu.value);if(ipu.value.length !=0 && ischine){this.inputtext = ipu.value;}el{alert("请输入汉字");return;}if(this.isplay){return}this.getanimatetype();this.gettextpixel();this.isplay = true;}});}// 计算文字的宽circle.prototype.calculatetextwidth = function () {this.textwidth = this.mctx.measuretext(this.inputtext).width;}// 获取文字像素点circle.prototype.gettextpixel = function () {if(this.pctx){this.pctx.clearrect(0,0,this.textwidth,this.textheight);}this.calculatetextwidth(this.inputtext);this.icanvaspixel.width = this.textwidth;this.icanvaspixel.height = this.textheight;this.pctx =  this.icanvaspixel.getcontext("2d");this.pctx.font = "128px 微软雅黑";this.pctx.fillstyle = "#ff0000";this.pctx.textbaline = "botom";this.pctx.filltext(this.inputtext,0,110);this.imagedata = this.pctx.getimagedata(0,0,this.textwidth,this.textheight).data;this.gettextpixelposition(this.textwidth,this.textheight);}// 获取文字粒子像素点位置circle.prototype.gettextpixelposition = function (width,height) {var left = (this.icanvasw - width)/2;var top = (this.icanvash - height)/2;var space = 4;this.actioncount = 0;for(var i=0;i<this.textheight;i+=space){for(var j=0;j<this.textwidth;j+=space){var index = j*space+i*this.textwidth*4;if(this.imagedata[index] == 255){if(this.actioncount<this.ballnumber){this.balls[this.actioncount].status = 1;this.balls[this.actioncount].targetx = left+j;this.balls[this.actioncount].targety = top+i;this.balls[this.actioncount].backx = this.balls[this.actioncount].x;this.balls[this.actioncount].backy = this.balls[this.actioncount].y;this.ballactor.push(this.balls[this.actioncount]);this.actioncount++;}}}this.actornumber = this.ballactor.length;}this.animatetotext();}// 粒子运动到指定位置circle.prototype.animatetotext = function(){for(var i=0;i<this.actornumber;i++){dynamics.animate(this.ballactor[i], {x: this.ballactor[i].targetx,y: this.ballactor[i].targety},{type: dynamics.eain,duration: 1024,});}ttimeout(function(){this.ballbacktype();},3000);}// 粒子原路返回circle.prototype.ballbackposition = function(){for(var i=0;i<this.actornumber;i++){var ball = this.ballactor[i];dynamics.animate(ball, {x: ball.backx,y: ball.backy},{type: dynamics[this.backdynamics],duration: 991,complete:this.changestatus(ball)});}}// 获取类型|动画效果circle.prototype.getanimatetype = function() {var lecttype = document.getelementbyid("lecttype");var lectdynamics = document.getelementbyid("lectdynamics");this.backtype = lecttype.options[lecttype.options.lectedindex].value;this.backdynamics = lectdynamics.options[lectdynamics.options.lectedindex].value;}// 复位散开circle.prototype.ballbacktype = function(){if(this.backtype == "back"){this.ballbackposition();}el{this.ballautoposition();}this.ballactor = [];}// 随机散开circle.prototype.ballautoposition = function(ball){for(var i=0;i<this.actornumber;i++){this.changestatus(this.ballactor[i])}}// 更改小球状态circle.prototype.changestatus = function(ball){ball.status = 0;if(this.isplay == true){this.isplay = fal;}}// 随机生成每个圆的相关参数circle.prototype.generalrandomparam = function(){for(var i=0;i<this.ballnumber;i++){var ball = {};ball.size = 1; // 随机生成圆半径// 随机生成圆心 x 坐标ball.x = ramdomnumber(0+ball.size, this.icanvasw-ball.size);ball.y = ramdomnumber(0+ball.size, this.icanvash-ball.size);ball.speedx = ramdomnumber(-1, 1);ball.speedy = ramdomnumber(-1, 1);this.balls.push(ball);ball.status = 0;ball.targetx = 0;ball.targety = 0;ball.backx = 0;ball.backy = 0;}}// 改变圆的位置circle.prototype.changeposition = function(){for(var i=0;i<this.ballnumber;i++){if( this.balls[i].status == 0){this.balls[i].x += this.balls[i].speedx;this.balls[i].y += this.balls[i].speedy;}}}// 画圆circle.prototype.renderball = function(ball){this.ctx.fillstyle = "#fff";this.ctx.beginpath(); // 这个一定要加this.ctx.arc(ball.x, ball.y, ball.size, 0, 2 * math.pi);this.ctx.clopath(); // 这个一定要加this.ctx.fill();}// 小球碰撞判断circle.prototype.collision = function(ball){for(var i=0;i<this.ballnumber;i++){if(ball.x>this.icanvasw-ball.size || ball.x<ball.size){if(ball.x>this.icanvasw-石油是混合物吗ball.size){ball.x = this.icanvasw-ball.size;}el{ball.x = ball.size;}ball.speedx = - ball.speedx;}if(ball.y>this.icanvash-ball.size || ball.y<ball.size){if(ball.y>this.icanvash-ball.size){ball.y = this.icanvash-ball.size;}el{ball.y = ball.size;}ball.speedy = - ball.speedy;}}}// 开始动画circle.prototype.ballanimate = function(){var this = this;var animateframe = window.requestanimationframe || window.mozrequestanimationframe || window.webkitrequestanimationframe || window.msrequestanimationframe;(function move(){animte = animateframe(move);this.ctx.clearrect(0, 0, this.icanvasw, this.icanvash);this.changeposition();for(var i=0;i<this.ballnumber;i++){this.collision(this.balls[i]);this.renderball(this.balls[i]);}})();}// 生成一个随机数function ramdomnumber(min, max) {return math.r全国高速公路免费到什么时候结束andom() * (max - min) + min;}

看了代码估计也只是心里炫了一下,也没有让你想把这个东西做出来的欲望,为此我知道必需得让你眼睛心服口服才行。在线 demo: 。

人无完人,代码也一样。看起来运行顺畅的代码也或多或少有一些瑕疵,日前这个效果还只支持中文。英文的话,我得再努力一把,不管怎么样,英文后面肯定是会加入来的,只是时间问题了。还有代码中用于标记是否可再次执行生成文字的 属性:this.isplay ,还是一点瑕疵,this.isplay 的状态更改没有准确的在粒子归位的那一瞬间更改,而是提前更改了状态。但这个状态不会影响本例子效果的完整实现。

这个例子中用到了 dynamics.js 库,主要是用到它里面的一些运动函数,让粒子动起来更感人一些,仅此而已。

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持www.887551.com。

本文发布于:2023-04-03 08:18:33,感谢您对本站的认可!

本文链接:https://www.wtabcd.cn/fanwen/zuowen/e284360b750beeb6b24f3c14b5f0c820.html

版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系,我们将在24小时内删除。

本文word下载地址:详解Canvas 实现炫丽的粒子运动效果(粒子生成文字).doc

本文 PDF 下载地址:详解Canvas 实现炫丽的粒子运动效果(粒子生成文字).pdf

标签:粒子   文字   代码   效果
相关文章
留言与评论(共有 0 条评论)
   
验证码:
Copyright ©2019-2022 Comsenz Inc.Powered by © 专利检索| 网站地图