欢迎来到258分享网,纯净的网络源码分享基地!

258资源分享网

全部作品
全部作品
网站源码
微信源码
素材特效
源码插件
视频教程
建站学院
热门搜索: 织梦  农业种植  农业  安全设置  官方
258资源分享 > 建站学院 > 微信开发 > 小程序canvas开发水果老虎机

推荐下载

HTML5响应式自适应网咯设计

2020-05-12   浏览:736

高端HTML5响应式企业通用网

2020-05-06   浏览:518

html5响应式外贸网站英文版

2020-05-08   浏览:505

HTML5自适应律师工作室类网

2020-04-04   浏览:501

HTML5影视传媒文化公司类网

2020-05-12   浏览:495

小程序canvas开发水果老虎机

发布时间:2021-01-15  

在这个超长假期中,无聊。。。,所以动手做一个早就计划要做的小玩意, 水果老虎机 ,嗯,这是一个小程序而不是小游戏...

小程序canvas开发水果老虎机

使用结构还是canvas?

使用模板结构(view)生成水果盘的好处一是用户可自定义产出 n x n 的定制化老虎机,二是容易通过算法样式生成布局,三是通过 wx.selectQueryAll 的方法能够很方便的抓到定位数据。但,问题是动画性能过于孱弱,如图构建一个 7x7 的水果盘,动画性能估计会惨不忍睹,而且纯粹模板结构无论使用 animation 动画方法还是 css 的keyframe的动画方法得到的动画效果都非常差(测试过的结论),还有是已知的动画方法可控性很差

使用canvas来生成水果盘好处是动画性能很好(canvas2d),但是定制性和扩展性比较差

so综上考虑,使用模板(view)布局,使用canvas来实现动画。既保证了组件的性能,同时定制型,扩展性也很好

准备计时器方法

动画的生成离不开计时器方法,settimeout/setinterval这两兄弟真的不够看啊,问题还多,做过web开发的一定都知道 window.requestAnimationFrame ,这货在小程序的计时器方法中不存在,好在 canvas2d 中可以使用 Canvas.requestAnimationFrame(function callback) 方法来实现

准备运动算法

在水果老虎机中,激活状态会沿着四方的水果盘做非线性运动(easeInOut比较好用),需要基础的运动算法来计算实际的运动距离。在 animation 动画方法中,我们可以使用 ease-in/ease-out 等缓动算法来实现动画效果,但在这里必须要借助 tween.js 中的缓动算法来实现运动效果(因为需要控制运动节点)。

你会不会想到用css的keyframe动画来做这个运动效果,经过我的测试,css的动画和animation的动画会在每一条边上实现一次(ease)缓动运动(很奇怪的效果

使用其中一个,节省代码量

/* * Tween.js * t: current time(当前时间); * b: beginning value(初始值); * c: change in value(变化量); * d: duration(持续时间)。 */ // Quart 四次方的缓动 const easeInOutQuart = function (t, b, c, d) { if ((t /= d / 2) < 1) return c / 2 * t * t * t * t + b; return -c / 2 * ((t -= 2) * t * t * t - 2) + b; } 复制代码

tween算法是以时间为基准(时间比率 = 距离比率)来计算单位时间的实际运动距离

布局

以上面的图为例,我们需要做一个 7 x 7 的水果盘,实际有效的奖品格子数为 7*4-4 共24个有效格子

有效格子算法

js

// 0-6 第一行所有格子全部有效 // 21-27 最后一行所有格子全部有效 // 中间部分 i%7===0 和 i%7 === (7-1) 有效 // 算法源码有点无聊,依据上述思路,即可遍历28个格子并标识奖品格子valide=true // 可以扩展想一想 6x6 5x5,思路是一样的 复制代码

wxml

<view class="fruits-container" > <view class="fruits-table" > <block wx:for="{{ary}}" wx:key="index" > <view wx:if="{{item.valide}}" class="valide">{{item.title}}</view> <view wx:else class="in-valide"></view> </block> </view> <canvas type="2d" .... /> </view> 复制代码 样式

只节选关键样式,目的是让canvas覆盖在水果盘上,长宽一致

.fruits-container { position: relative; width: 400px; height: 400px; ... } .fruits-table { position: absolute; width: 100%; height: 100%; top: 0; left: 0; ... } 复制代码 抓取位置信息

canvas的绘制需要X轴, Y轴的精确信息,可以使用 wx.createSelectorQuery 方式抓取类名为‘valide’的 view (奖品格子)的位置信息

let query = wx.createSelectorQuery().in(this) query.selectAll(`.fruits-table .valide`).boundingClientRect(ret => { .... console.log(ret[0]) // top, left, right, bottom, width, height console.log(ret[1]) // top, left, right, bottom, width, height ... ... console.log(ret[23]) // top, left, right, bottom, width, height }) 复制代码

得到每一个奖品格子的位置信息后,就可以使用canvas的 fillRect 方法来绘制激活状态了。

绘制一个激活状态 let query = wx.createSelectorQuery().in(this) query.selectAll(`.fruits-table .valide`).boundingClientRect(ret => { .... let {top, left, right, bottom, width, height} = ret[0] const canvasQuery = wx.createSelectorQuery() canvasQuery.select('#fruit-canvas') .fields({ node: true, size: true }) .exec((res) => { const canvas = res[0].node const ctx = canvas.getContext('2d') let x = top let y = left let dx = width let dy = height ctx.shadowOffsetX = 2 ctx.shadowOffsetY = -2 ctx.shadowColor = 'red' ctx.shadowBlur = 50 ctx.lineWidth = 5 ctx.strokeStyle = 'red' ctx.clearRect(0, 0, canvas.width, canvas.height) ctx.strokeRect(x, y, dx, dy) }) }) 复制代码 跑起来

本文标签

:备案管家服务帮您把复杂流程变简单,解决您在进行网站备案过程中遇到的效率低下和成功率不高的问题。个人300/2个域名,企业500/5个域名,qq1650004.