轉盤效果使用原生js 和css3動畫實現
中獎概率由后端控制,后端返回中獎金額和中獎名稱,前端處理指針顯示的地方
本demo 實現的是 轉盤轉動指針不動的效果
本組件可直接復制代碼至自己的項目,加上圖片即可運行,圖片已在備注中標出
lucky.vue
<template><div class="container"><div class="lucky-wheel"><div class="lucky-title"><!--轉盤標題圖片定位在轉盤上邊--><img src="../../assets/img/pc/jctitle_03.png" alt=""></div><div class="wheel-main"><div class="wheel-pointer-box"><div class="wheel-pointer wheelBefor" @click="tcFun()" :style="{transform:rotate_angle_pointer,transition:rotate_transition_pointer}"><!-- 指針程呼吸狀態,兩張指針進行透明度切換,使用css3改變透明度當條件成立時--><img src="../../assets/img/pc/strat_befor.png" alt=""></div></div><div class="wheel-bg" :style="{transform:rotate_angle,transition:rotate_transition}"><div class="prize-list"><div class="prize-item" v-for="(item,index) in prize_list" :key="item.id"><div class="prize-type">{{item.name}}</div><div class="prize-count" v-if="item.count">{{item.count}}元</div><div class="prize-pic"><img :src="item.icon"></div></div><div class="zplightBox"><!-- 透明彩燈,使用css3改變透明度使其閃動 --><img src="../../assets/img/pc/zplight.png" alt=""></div></div></div></div></div><!-- 中獎彈窗 --><div class="toast" v-show="toast_control"><div class="toastTop"><img src="../../assets/img/pc/tctop.png" alt=""></div><div class="toast-container"><div class="containerBox"><div class="toast-title"><p>恭喜獲得 <span>{{prize_list[this.index].name}} 獎池</span></p><p><strong>現金{{number}}元</strong></p></div><div class="toast-btn"><div class="toast-cancel" @click="close_toast">確定</div></div></div></div></div><div class="toast-mask" v-show="toast_control"></div><!--提示--><el-dialogtitle="提示":visible.sync="promptDialogVisible"class="promptBox"center><p>將消耗5個字符開啟獎池</p><span slot="footer" class="dialog-footer"><el-button class="cancelBtn" @click="promptDialogVisible = false">取 消</el-button><el-button class="submitBtn" @click="rotate_handle()">確 定</el-button></span></el-dialog></div>
</template>
<script>
export default {props:[‘wheelStartBol'],// 從父組建傳 狀態過來data() {return {easejoy_bean: 0, //金豆lottery_ticket: 0, //抽獎次數prize_list: [//獎品列表{icon: require("../../assets/img/pc/jcico_10.png"), // 獎品圖片count: 500, // 獎品數量name: "青銅", // 獎品名稱isPrize: 1 ,// 該獎項是否為獎品id:201901},{icon: require("../../assets/img/pc/jcico_03.png"),count: 10000,name: "鉑金",isPrize: 1,id:201902},{icon: require("../../assets/img/pc/jcico_06.png"),count: 5000,name: "黃金",isPrize: 1,id:201903},{icon: require("../../assets/img/pc/jcico_10.png"), // 獎品圖片count: 500, // 獎品數量name: "青銅", // 獎品名稱isPrize: 1, // 該獎項是否為獎品id:201904},{icon: require("../../assets/img/pc/jcico_18.png"),count: 50000,name: "鉆石",isPrize: 1,id:201905},{icon: require("../../assets/img/pc/jcico_15.png"),count: 1000,name: "白銀",isPrize: 1,id:201906},{icon: require("../../assets/img/pc/jcico_03.png"),count: 10000,name: "鉑金",isPrize: 1,id:201907},{icon: require("../../assets/img/pc/jcico_10.png"), // 獎品圖片count: 500, // 獎品數量name: "青銅", // 獎品名稱isPrize: 1, // 該獎項是否為獎品id:201908},{icon: require("../../assets/img/pc/jcico_06.png"),count: 5000,name: "黃金",isPrize: 1,id:201909},{icon: require("../../assets/img/pc/jcico_15.png"),count: 1000,name: "白銀",isPrize: 1,id:201910},],toast_control: false, //抽獎結果彈出框控制器hasPrize: false, //是否中獎start_rotating_degree: 0, //初始旋轉角度rotate_angle: 0, //將要旋轉的角度start_rotating_degree_pointer: 0, //指針初始旋轉角度rotate_angle_pointer: 0, //指針將要旋轉的度數rotate_transition: "transform 6s ease-in-out", //初始化選中的過度屬性控制rotate_transition_pointer: "transform 12s ease-in-out", //初始化指針過度屬性控制click_flag: true, //是否可以旋轉抽獎index: 0 ,//中獎keynumber:null,//中獎金額promptDialogVisible:false,statusLists:{guaStatus:0,kaStatus:0,fenStatus:0,jiangStatus:0},kaLists :{BEgua:0,BEka:0,BEfen:0,BEjiang:0,BEchi:0}};},methods: {tcFun(){// 條件成立,才可以啟動轉盤// 獲取后端接口,拿到當前擁有的卡片,這里只做示范//if (this.statusLists.guaStatus == 2 || this.statusLists.kaStatus == 2 || this.statusLists.fenStatus == 2 || this.statusLists.jiangStatus == 2){// this.$message({// message: '每天只可以兌換1次,請明天再試',// type: 'warning',customClass:'messageBox'// });// return// }// if(this.kaLists.BEgua <= 0 || this.kaLists.BEka <= 0 || this.kaLists.BEfen <= 0 || this.kaLists.BEjiang <= 0 || this.kaLists.BEchi <= 0 ){// this.$message({// message: '獲得5張卡才可以開獎',// type: 'warning',// customClass:'messageBox'// });//}else {// this.promptDialogVisible = true;//}//條件成立,彈出確認彈框this.promptDialogVisible = true;},//獲取中獎數據rotate_handle() {this.promptDialogVisible = false;// this.$Api.redeemTaskWordPrize().then(resp => {//模擬后臺返回數據let resp = { prizeLevel:1,bonus :1000,txt:鉑金};if (resp){// 如果此獎項在轉盤中有兩項以上,隨機轉動到其中一項if (resp.prizeLevel == 1){//青銅let arr =[0,3,7];let i = Math.floor(Math.random() * arr.length + 1)-1;this.index = arr[i] ;//指定每次旋轉到的獎品下標}else if(resp.prizeLevel == 2){//白銀let arr =[5,9];let i = Math.floor(Math.random() * arr.length + 1)-1;//隨機數this.index = arr[i] ;//指定每次旋轉到的獎品下標}else if(resp.prizeLevel == 3){//黃金let arr =[2,8];let i = Math.floor(Math.random() * arr.length + 1)-1;this.index = arr[i] ;//指定每次旋轉到的獎品下標}else if(resp.prizeLevel == 4){//鉑金let arr =[1,6];let i = Math.floor(Math.random() * arr.length + 1)-1;this.index = arr[i] ;//指定每次旋轉到的獎品下標}else if(resp.prizeLevel == 5){//鉆石this.index = 4}this.rotating();this.number = resp.bonus;this.$emit('bonus',this.number);this.$parent.$parent.$parent.myTaskWordDataFun();this.$parent.$parent.$parent.jcFun();}else {this.$message({message: '網絡異常,請稍后重試',type: 'error',customClass:'messageBox'});}// });},rotating() {if (!this.click_flag) return;var type = 0; // 默認為 0 轉盤轉動 1 箭頭和轉盤都轉動(暫且遺留)var during_time = 5; // 默認為1svar random = Math.floor(Math.random() * 7);var result_index = this.index ; // 最終要旋轉到哪一塊,對應prize_list的下標// var result_angle = [337.5, 292.5, 247.5, 202.5, 157.5, 112.5, 67.5, 22.5]; //最終會旋轉到下標的位置所需要的度數var result_angle = [360,324, 288, 252, 216, 180, 144, 108,72,36]; //最終會旋轉到下標的位置所需要的度數var rand_circle = 6; // 附加多轉幾圈,2-3this.click_flag = false; // 旋轉結束前,不允許再次觸發if (type == 0) {// 轉動盤子var rotate_angle =this.start_rotating_degree +rand_circle * 360 +result_angle[result_index] -this.start_rotating_degree % 360;this.start_rotating_degree = rotate_angle;this.rotate_angle = "rotate(" + rotate_angle + "deg)";// // //轉動指針// this.rotate_angle_pointer = "rotate("+this.start_rotating_degree_pointer + 360*rand_circle+"deg)";// this.start_rotating_degree_pointer =360*rand_circle;var that = this;// 旋轉結束后,允許再次觸發setTimeout(function() {that.click_flag = true;that.game_over();}, during_time * 1000 + 1500); // 延時,保證轉盤轉完} else {//}},game_over() {this.toast_control = true;this.hasPrize = this.prize_list[this.index].isPrize// this.hasPrize = this.index},//關閉彈窗close_toast() {this.toast_control = false;// this.$parent.$parent.$parent.myTaskWordDataFun();}}
};
</script>
<style scoped lang="less">
.container {width: 652px;padding-top: 58px;background: url("../../assets/img/pc/jcboxbg_03.png") no-repeat top center; /*轉盤背景,不包含轉盤 *//padding-bottom: 30px;margin: 0px auto;
}
.lucky-wheel {width: 625px;height: 625px;padding-top: 25px;position: relative;
}
.lucky-title{position: absolute;top:0px;left: 36px;z-index: 999;
}
.wheel-main {display: flex;align-items: center;justify-content: center;position: relative;
}
.wheel-bg {width: 625px;height: 625px;background: url("../../assets/img/pc/zpbg_03.png") no-repeat center top; /**轉盤 *//background-size: 100%;color: #fff;font-weight: 500;display: flex;flex-direction: column;justify-content: center;align-content: center;transition: transform 3s ease;
}.zplightBox{width: 659px;height: 657px;position: absolute;top: -15px;left: -16px;img{width: 100%;height: 100%;/*-webkit-animation-timing-function: ease-in-out !important;*//*-webkit-animation-name: twinkling !important;*//*-webkit-animation-duration: 300ms !important;*//*-webkit-animation-iteration-count: infinite !important;*//*-webkit-animation-direction: alternate !important;*/-webkit-animation: twinkling 400ms infinite ease-in-out;}
}.wheel-pointer-box {position: absolute;top: 50%;left: 50%;z-index: 100;transform: translate(-50%, -60%);/*width: 625px;*//*height: 625px;*/
}
.wheel-pointer {width: 238px;height: 263px;transform-origin: center 60%;img{width: 100%;/*-webkit-animation: twinkling 1s infinite ease-in-out;*/-webkit-animation-timing-function: ease-in-out;-webkit-animation-name: twinkling;-webkit-animation-duration: 800ms;-webkit-animation-iteration-count: infinite;-webkit-animation-direction: alternate;}}.wheelBefor{background: url("../../assets/img/pc/strat_btn.png") no-repeat center top; /**指針 *//background-size: 100%;}
.wheel-bg div {text-align: center;
}
.prize-list {width: 100%;height: 100%;position: relative;
}
.prize-list .prize-item {position: absolute;top: 0;left: 0;z-index: 2;
}.prize-item {width: 137px;height: 197px;
}.prize-pic img {width:69px;
}
.prize-count {font-size: 26px;font-weight: bold;color: #ea3697;
}
.prize-type {font-size: 24px;font-weight: bold;
}.prize-list .lightBox{width: 57px;height: 58px;position: absolute;}// 轉盤內容傾斜度
.prize-list .prize-item:first-child {top: 44px;left: 245px;transform: rotate(0deg);.prize-type{color: #c23800;text-shadow:-1px 0 #fff,0 1px #fff,2px 0 #fff,0 -1px #fff;}}
.prize-list .prize-item:nth-child(2) {top: 74px;left: 345px;transform: rotate(37deg);.prize-type{color: #00a004;}
}
.prize-list .prize-item:nth-child(3) {top: 162px;left: 409px;transform: rotate(70deg);.prize-type{color: #d99900;}
}
.prize-list .prize-item:nth-child(4) {top: 264px;left: 411px;transform: rotate(111deg);.prize-type{color: #c22e00;text-shadow:-1px 0 #fff,0 1px #fff,2px 0 #fff,0 -1px #fff;}
}
.prize-list .prize-item:nth-child(5) {top: 354px;left: 343px;transform: rotate(-220deg);.prize-type{color: #f83bff;}
}
.prize-list .prize-item:nth-child(6) {top: 386px;left: 247px;transform: rotate(-181deg);.prize-type{color: #fff;}
}
.prize-list .prize-item:nth-child(7) {top: 353px;left: 147px;transform: rotate(-146deg);.prize-type{color: #00a004;}
}
.prize-list .prize-item:nth-child(8) {top: 268px;left: 82px;transform: rotate(-108deg);.prize-type{color: #c22e00;text-shadow:-1px 0 #fff,0 1px #fff,2px 0 #fff,0 -1px #fff;}
}
.prize-list .prize-item:nth-child(9) {top: 158px;left: 82px;transform: rotate(-75deg);.prize-type{color: #d99900;}
}
.prize-list .prize-item:nth-child(10) {top: 75px;left: 145px;transform: rotate(-39deg);.prize-type{color: #fff;}
}
.tip {position: relative;margin: 2.5rem auto 0;width: 300px;border: 1px solid #fbc27f;
}
.tip-title {position: absolute;top: -1rem;left: 50%;transform: translate(-50%, 0);font-size: 1rem;color: #fccc6e;background: rgb(243, 109, 86);padding: 0.3125rem 0.625rem;
}
.tip-content {padding: 1.5625rem 0.625rem;font-size: 0.875rem;color: #fff8c5;line-height: 1.5;
}
.toast-mask {position: fixed;top: 0;left: 0;background: rgba(0, 0, 0, 0.75);z-index: 10000;width: 100%;height: 100%;
}
.toast {position: fixed;top: 57%;left: 50%;z-index: 20000;transform: translate(-50%, -50%);width: 552px;height: 490px;.toastTop{position: absolute;top:-122px;left: 86px;/*-webkit-animation: twinkling 1s infinite ease-in-out;*/-webkit-transform: rotate(360deg);animation: rotation 4s linear infinite;-moz-animation: rotation 4s linear infinite;-webkit-animation: rotation 4s linear infinite;-o-animation: rotation 4s linear infinite;width: 386px;img{width: 100%;}}}.toast-container {background: url("../../assets/img/pc/tc_win.png") no-repeat top center; /**中獎彈窗背景 *//background-size: 100% 100%;width: 552px;height: 430px;position: absolute;top: 0px;left: 0px;margin: 0px auto;.containerBox{width: 194px;position: absolute;bottom: 106px;left: 191px;}
}
.toast-picture {position: absolute;top: 0px;left: 0px;width: 600px;}
.toast-pictrue-change {position: absolute;top: -1.5rem;left: -1.375rem;width: 17.5rem;height: 3.125rem;
}
.toast-title {padding: 60px 0;padding-bottom: 30px;font-size: 18px;color: #fc7939;text-align: center;margin-top: 130px;p{color: #fff;line-height: 45px;span{color: #fcff21;}strong{font-size: 30px;color: #fcff21;font-weight: normal;}}
}
.toast-btn {display: flex;align-items: center;justify-content: center;/*margin-bottom: 0.9375rem;*/
}
.toast-btn div {width: 154px;height: 60px;text-align: center;line-height: 60px;font-size: 26px;font-weight: bold;color:#fff;text-shadow:-1px 0 #ab7d1c,0 1px #ab7d1c,2px 0 #ab7d1c,0 -1px #ab7d1c;cursor: pointer;background: url("../../assets/img/pc/tcbtn.png") no-repeat center;//**彈窗確定按鈕背景 */background-size: 100% 100%;
}</style>
<style lang="less">.container{.promptBox{.el-dialog{width: 415px !important;// 錯誤提示背景,不滿足抽獎條件時background: url("../../assets/img/pc/rulebg.png") no-repeat center !important;background-size: 100% 100% !important;box-shadow:none;.el-dialog__headerbtn{display: none;}.el-dialog__header{padding: 12px 20px 10px;}.el-dialog__title{font-size: 22px;color: #2d78c4;font-weight: bold;display: inline-block;padding-top: 3px;}.el-button{width: 123px;height: 46px;line-height: 46px;text-align:center;font-size: 22px;font-weight: bold;color:#fff;padding: 0px;border: 0;}.cancelBtn{background: url("../../assets/img/pc/tcbtn.png") no-repeat center;/**彈窗確定按鈕背景 *//text-shadow:-1px 0 #ab7d1c,0 1px #ab7d1c,1px 0 #ab7d1c,0 -1px #ab7d1c;}.submitBtn{background: url("../../assets/img/pc/submitbtn.png") no-repeat center;/**確定 *//text-shadow:-1px 0 #2073bb,0 1px #2073bb,1px 0 #2073bb,0 -1px #2073bb;}.el-dialog__body{p{width: 100%;height: 130px;line-height: 130px;text-align: center;font-size: 20px;color: #fff;background: url("../../assets/img/pc/tsbg.png") no-repeat center;background-size: 100% 100%;}}}}}.messageBox.el-message{min-width: 400px !important;}// 彈窗呼吸效果@-webkit-keyframes twinkling{0%{opacity:0.5}100%{opacity:1}}@keyframes twinkling{0%{opacity:0.5}100%{opacity:1}}</style>
項目保密機制,就不放效果圖了 有疑問可以私信我
總結
以上是生活随笔為你收集整理的vue 实现抽奖转盘的全部內容,希望文章能夠幫你解決所遇到的問題。
如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。