vue中实现大转盘抽奖灯光闪烁

编程入门 行业动态 更新时间:2024-10-23 11:27:04

vue中实现大<a href=https://www.elefans.com/category/jswz/34/1740101.html style=转盘抽奖灯光闪烁"/>

vue中实现大转盘抽奖灯光闪烁

官方文档入口

一. 在 Vue 中使用

  1. 安装插件
npm install vue-luck-draw
  1. 找到 main.js 全局引入插件并 use,或者在组件中按需引入插件。
// 按需引入
import { LuckyWheel } from 'vue-luck-draw'
Vueponents('LuckyWheel', LuckyWheel)
  1. 最后在页面内使用 <LuckyWheel />大转盘组件,根据官方文档想要的配置参数

二. 转盘抽奖正常流程

1. 当你点击抽奖按钮时触发strat回调函数,接下来你可以调用play()方法先让大转盘转起来,然后紧接着去请求接口拿数据,或是你自己随机一个index
2. 当接口拿到index中奖索引之后,你就可以调用stop(index)方法了,此时大转盘会缓慢停止,当完全停止之后就会触发end回调函数(当接口返回的速度很快的时候,会跳过匀速阶段,此时可手动加一个定时器延缓调用的时机)
3. 最后在end回调函数里面,得到中奖奖品的全部信息,你就可以在这里执行逻辑告诉用户他中奖了

三. 转盘灯光闪烁

根据判断条件替换背景图,需要注意的是需要提前加载出背景图,不然会闪烁一下

背景图闪烁的原因:

(1)博主是通过class三元表达式,来引入不同的class,引入不同的背景图片实现灯光闪烁的。
:class="[imgIndex == 1 ? 'changeImg_one' : 'changeImg_two']"
.changeImg_one {background: url("../../assets/image/luckly/xx.png") no-repeat;}
(2)这种通过class加载的方式,默认是使用changeImg_one这个class,所以changeImg_one对应的图片是
正常加载的,而changeImg_two这个class是通过点击方法来切换的。所以就导致changeImg_two的背景图
没加载出来,点击需要重新去加载图片,然后替换,出现闪烁。
(3)预防方案使用图片预加载,就是在实际点击抽奖之前,就把两张灯光的图片都加载到浏览器缓存。可以使用 new Image()对象,或者一进入页面就加载的方式。
(4)博主这里是直接通过img标签引入背景图,然后定位。这样vue就会自动加载img图片,然后我们通过v-show来控制即可

代码如下:

<template><div class="wrap"><div class="lucky_wheel"><imgclass="lucky_title"src="../../assets/image/luckly/written words.png"/><div class="wheel_main"><LuckyWheelclass="role"ref="LuckyWheel"width="6.48rem"height="6.48rem":prizes="prizes":buttons="buttons":default-style="defaultStyle"@start="startCallBack"@end="endCallBack"/><div class="count_info">还可抽奖<span class="count">{{ count }}次</span></div><imgclass="lotteryBorder"v-show="imgIndex === 1"src="../../assets/image/luckly/turntable.png"/><imgclass="lotteryBorder"v-show="imgIndex === 2"src="../../assets/image/luckly/turntable_lights.png"/></div></div><div class="tip_con"><imgclass="tip_btn"src="../../assets/image/luckly/activity details.png"/><div class="tip_content"><div class="tip_item"><div class="img_num"><span class="number">1</span></div><p>活动细则活动细则活动细则活动细则活动细则活动细则活动细则活动细则</p></div><div class="tip_item"><div class="img_num"><span class="number">2</span></div><p>活动细则活动细则活动细则活动细则活动细则活动细则活动细则活动细则</p></div></div><img class="logo" src="../../assets/image/luckly/luckly-logo.png" /><van-overlay :show="verifyDialogShow"><div class="overlayMain"><div class="overlay_title">中奖信息</div><div class="info">{{ overlayInfo }}</div><div class="confirm" @click="confirm">确认</div></div></van-overlay></div></div>
</template><script>
import { LuckyWheel } from "vue-luck-draw";
import { Overlay } from "vant";
export default {data() {return {prizes: [],buttons: [{radius: "30%",imgs: [{src: require("../../assets/image/luckly/luckly_btn.png"),width: "200%",top: "-185%"}]}],defaultStyle: {fontSize: "10px",fontColor: "#EC652D"},verifyDialogShow: false,count: 0, // 剩余抽奖次数winId: "", //获取奖品的idwinName: "", //中奖奖品名字mid: 999,currentIndex: 0 //抽中数组中第几个奖品};},computed: {overlayInfo() {return this.winId > 0 ? `恭喜你获得${this.winName}` : "谢谢参与";}},created() {this.getPrizesList();},// mounted() { //让灯光闪烁的另一种办法,用的时候去掉html里的两个img标签就好//   var temp_timer = setInterval(this.changeImg, 100);//   setTimeout(() => {//     clearInterval(temp_timer);//   }, 300);// },methods: {getPrizesList() {let data = [{id: "12",name: "奖品1",image: require("../../assets/image/luckly/doubledouzi.png")},{id: "24",name: "奖品2",image: require("../../assets/image/luckly/douzi.png")},{id: "3",name: "奖品3",image: require("../../assets/image/luckly/pinggai.png")},{id: "14",name: "奖品4",image: require("../../assets/image/luckly/double_pinggai.png")},{id: "5",name: "奖品5",image: require("../../assets/image/luckly/qiandai.png")},{id: "6",name: "奖品6",image: require("../../assets/image/luckly/qiandai.png")}];this.dataList = data;this.count = 2;var thanks_obj = {id: "0",name: "谢谢参与",image: require("../../assets/image/luckly/thank.png")};if (this.dataList.length % 2 == 1) {//如果数组是奇数的话,直接在数组最前面添加谢谢参与,为了转盘背景颜色是间隔的this.dataList.unshift(thanks_obj);} else {//如果数组是偶数的话,在数组最前面和数组中间添加谢谢参与this.mid = this.dataList.length / 2;this.dataList.splice(this.mid, 0, thanks_obj);this.dataList.unshift(thanks_obj);}console.log(this.dataList);this.dataList.forEach((item, index) => {this.prizes.push({name: item.name,background: index % 2 ? "#FFD787" : "#fff",fonts: [{text: item.name,top: "10px"}],imgs: [{src: item.image,width: "35px",// top: "30px",// width: "25%",top: "30%"}]});});},startCallBack() {//没有抽奖次数return出去if (this.count == 0) {this.$toast("没有抽奖次数了");return;}this.count--;this.$refs.LuckyWheel.play();this.winId = parseInt("5"); //模拟接口,这里转换为number类型//留出匀速的时间setTimeout(() => {if (this.winId == 0) {this.$refs.LuckyWheel.stop(0); //如果winId=0,直接取数组里的第一个} else {this.dataList.forEach((item, index) => {//否则循环数组,拿中奖奖品id去数组里item.id比对,如果两个id值相等的话,就取数组当前的索引,赋值给 this.currentIndexif (item.id == this.winId) {this.currentIndex = index;console.log(index);}});this.$refs.LuckyWheel.stop(this.currentIndex);//一开始用的下面这种取索引方法,发现不行,因为当时想象的是id从1开始,依次排列。但是在真正项目中,id会打乱//如果是数组长度是奇数的话走if,偶数的话多加了两个谢谢参与,中间谢谢参与之前的索引走if;之后的索引取值走else// if (this.winId <= this.mid) {  //   this.$refs.LuckyWheel.stop(this.winId);// } else {//   this.$refs.LuckyWheel.stop(this.winId + 1);// }}}, 3000);},endCallBack(prize) {this.winName = prize.name;this.verifyDialogShow = true;},confirm() {this.verifyDialogShow = false;}},components: {VanOverlay: Overlay,LuckyWheel: LuckyWheel}
};
</script><style lang="scss" scoped>
.lucky_wheel {height: 572px;background: url("../../assets/image/luckly/background_2.png") no-repeat;background-size: cover;.lucky_title {width: 312px;margin: 0 auto;padding-top: 13px;}.wheel_main {position: relative;background: url("../../assets/image/luckly/turntable.png") no-repeat;background-size: cover;width: 345px;height: 399px;margin: -8px auto;.role {// width: 243px;// height: 243px;// border-radius: 500px;position: absolute;top: 50px;left: 51px;// overflow: hidden;}.count_info {position: absolute;bottom: 14px;left: 50%;transform: translateX(-50%);color: #fff;text-align: center;margin-top: -30px;letter-spacing: 3px;font-size: 12px;.count {color: #ffc47c;font-weight: bold;}.lotteryBorder {position: absolute;width: 345px;height: 399px;top: 0;left: 0;right: 0;bottom: 0;}}}
}
.tip_con {height: auto;background: url("../../assets/image/luckly/background_3.png") no-repeat;background-size: 100% 100%;display: flex;justify-content: center;flex-wrap: wrap;position: relative;.tip_btn {position: absolute;top: -26px;width: 292px;height: 59px;}.tip_content {background: url("../../assets/image/luckly/rule_bg.png") no-repeat;background-size: 100% 100%;width: 344px;height: auto;padding: 50px 14px 30px 14px;box-sizing: border-box;border-radius: 5px;.tip_item {display: flex;margin-bottom: 8px;.img_num {background: url("../../assets/image/luckly/digital.png") no-repeat;background-size: cover;width: 20px;height: 20px;display: flex;justify-content: center;align-items: center;margin-right: 5px;}.number {font-size: 13px;color: #de192e;}p {flex: 1;color: #fcf6ef;letter-spacing: 1px;line-height: 16px;font-size: 12px;}}}.logo {margin: 25px auto 44px;width: 90px;height: 21px;}.overlayMain {width: 90%;height: auto;border-radius: 12px;background: #fff;position: absolute;top: 200px;left: 50%;transform: translateX(-50%);display: flex;align-items: center;flex-direction: column;.overlay_title {padding-top: 26px;font-size: 16px;font-weight: bold;}.info {font-size: 14px;padding: 8px 24px 26px;text-align: center;}.confirm {width: 100%;height: 48px;line-height: 48px;border-top: 1px solid #ebedf0;color: #ee0a24;font-size: 16px;text-align: center;}}
}
</style>

三. 遇到的bug

1)转盘抽奖这里遇到一个bug,点击指针让转盘转的时候,ios上需要点击两下,安卓上是正常的
排查问题发现是用的vant dialog弹窗组件的问题,更换成Overlay 遮罩层组件问题就解决了

2)灯光闪烁这里是通过判断条件来替换转盘背景图,但是每次在页面刚进来时候点击转盘按钮让转盘转起来,背景图就会闪烁一下,解决方法就是先让需要切换的这张背景图提前加载出来
目前我用了两种方法都实现了:
方法一:
.html里新增两个img标签,给它定好位置和原来转盘背景图吻合;再条件判断下,当imgIndex === 1时,展示第一张;imgIndex === 2时,展示第二张;相当于提前用img标签加载出来了
方法二:
vue的mounted生命周期函数里,setInterval定时器提前开启背景图

更多推荐

vue中实现大转盘抽奖灯光闪烁

本文发布于:2024-02-12 19:52:20,感谢您对本站的认可!
本文链接:https://www.elefans.com/category/jswz/34/1689191.html
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系,我们将在24小时内删除。
本文标签:转盘   灯光   vue

发布评论

评论列表 (有 0 条评论)
草根站长

>www.elefans.com

编程频道|电子爱好者 - 技术资讯及电子产品介绍!