H5-canvas-原生-编写俄罗斯转盘抽奖系统

先放上写好之后的样子
在这里插入图片描述
这里面的图片素材是我从别人的网站的拔下来的,如果需要删除的话请联系我哈。
为什么我要写这个呢,因为闲的,然后看见了这个东西,结果下载还要收费,我一想,算了吧,素材扒下来自己写一个。然后就有了后面的代码
这个是文件结构
在这里插入图片描述
下面直接上代码里面有注释
index.html

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>幸运大转盘</title>
    <style>
        * {
            margin: 0;
            padding: 0;
        }

        .allCanvas {
            position: relative;
            width: 500px;
            height: 500px;
            margin: 50px auto;
            background-color: rgba(0, 0, 0, .1);
        }

        #canvasbg {
            position: absolute;
            z-index: 0;
            top: 0;
            left: 0;
        }

        #canvasboxs {
            position: absolute;
            z-index: 1;
            top: 0;
            left: 0;
        }

        #canvasbtn {
            position: absolute;
            z-index: 2;
            top: 180px;
            left: 180px;
            cursor: pointer;
        }
    </style>
</head>
<body>
<div class="allCanvas">
    <canvas id="canvasbg" width="500" height="500"></canvas>
    <canvas id="canvasboxs" width="500" height="500"></canvas>
    <canvas id="canvasbtn" width="140" height="140"></canvas>
</div>
<script src="js/common.js"></script>
<script src="js/main.js"></script>
<script src="js/background.js"></script>
<script src="js/boxs.js"></script>
<script src="js/button.js"></script>
</body>
</html>

js/background.js

//背景渲染函数
function drawbg() {
    ctxbg.clearRect(-WIDTH / 2, -HEIGHT / 2, WIDTH, HEIGHT);
    ctxbg.drawImage(imagebg, (-WIDTH / 2) + (WIDTH * 0.05), (-HEIGHT / 2) + (HEIGHT * 0.05), WIDTH * 0.9, HEIGHT * 0.9);
}

js/boxs.js

function drawboxs() {
    positionlist = [];
    ctxboxs.clearRect(-WIDTH / 2, -HEIGHT / 2, WIDTH, HEIGHT);
    for (let i = 0; i < 8; i++) {
        fill(i);
    }
}

function fill(num) {
    if (num % 2 == 0) {
        ctxboxs.fillStyle = "#F8C950";
        ctxboxs.strokeStyle = "#F8C950";
    } else {
        ctxboxs.fillStyle = "#FBFBE0";
        ctxboxs.strokeStyle = "#FBFBE0";
    }
    ctxboxs.beginPath();
    ctxboxs.moveTo(0, 0);
    ctxboxs.arc(0, 0, 190, num * (Math.PI / 4), (num + 1) * (Math.PI / 4));
    let obj = {
        a: {
            x: (190 * Math.cos((num * (Math.PI / 4)) + deg)),
            y: (190 * Math.sin((num * (Math.PI / 4)) + deg))
        },
        b: {
            x: (190 * Math.cos((num + 1) * (Math.PI / 4) + deg)),
            y: (190 * Math.sin((num + 1) * (Math.PI / 4) + deg))
        }
    };
    positionlist.push({
        x: (obj.a.x + obj.b.x) / 2,
        y: (obj.a.y + obj.b.y) / 2
    });
    ctxboxs.closePath();
    ctxboxs.stroke();
    ctxboxs.fill();
    filltext(num);
}

function filltext(num) {
    ctxboxs.save();
    ctxboxs.rotate(Math.PI / 4 * num);
    ctxboxs.translate(Math.cos(Math.PI / 8) * (Math.cos(Math.PI / 8) * 190), Math.sin(Math.PI / 8) * (Math.cos(Math.PI / 8) * 190));
    ctxboxs.save();
    ctxboxs.rotate(Math.PI / 8 * 5);
    ctxboxs.textAlign = "center";
    ctxboxs.fillStyle = 'black';
    ctxboxs.fillText(boxlist[num], 0, 0);
    ctxboxs.restore();
    ctxboxs.save();
    ctxboxs.translate(Math.cos(Math.PI / 8) * (Math.cos(Math.PI / 8) * 190) - 160, Math.sin(Math.PI / 8) * (Math.cos(Math.PI / 8) * 190) - 95);
    ctxboxs.rotate(Math.PI / 8 * 5);
    ctxboxs.drawImage(boximagelist[num], 0, 0, 60, 60);
    ctxboxs.restore();
    ctxboxs.restore();
}


js/button.js

function drawbtn() {
    ctxbtn.drawImage(imagejt, -imagejt.width * 0.15, -imagejt.height * 0.15, imagejt.width * 0.3, imagejt.height * 0.3);
    ctxbtn.drawImage(imagego, -imagego.width * 0.15, -imagego.height * 0.15, imagego.width * 0.3, imagego.height * 0.3);
}

document.getElementById("canvasbtn").addEventListener("click", function () {
    begin();
});

js/common.js

window.requestAnimFrame = (function () {
    return window.requestAnimationFrame ||
        window.webkitRequestAnimationFrame ||
        window.mozRequestAnimationFrame ||
        window.oRequestAnimationFrame ||
        window.msRequestAnimationFrame ||
        function ( /* function FrameRequestCallback */ callback, /* DOMElement Element */ element) {
            return window.setTimeout(callback, 1000 / 60);
        };
})();

//开始游戏
function begin() {
    if (timer == null) {
        timer = setInterval(() => {
            if (speed < 20 && speedMax === 0) {
                speed += Math.random();
            } else if (speed > 20 && speedMax < 10) {
                speedMax += Math.random();
            } else if (speedMax >= 10 && speed > 1.1) {
                speed -= Math.random();
            } else {
                speed = 0;
                speedMax = 0;
                clearInterval(timer);
                timer = null;
                end();
                setTimeout(function () {
                    speed = 0.1;
                }, 1000);
            }
        }, 100)
    }
}

//结束游戏
function end() {
    space = [];
    for (let i = 0; i < positionlist.length; i++) {
        space.push((Math.pow(positionlist[i]["x"], 2) + Math.pow(positionlist[i]["y"] + 100, 2)))
    }
    alert(`恭喜你获得奖品:${boxlist[space.indexOf(Math.min(...space))]}`)
}

js/main.js

document.body.onload = game;//初始化函数

var WIDTH = 500;//canvas的宽度
var HEIGHT = 500;//canvas的高度

//背景画布
var canvasbg = document.getElementById("canvasbg");//背景画布
var ctxbg = null;//背景画布的画笔
var imagebg = new Image();//背景图片-圆

//奖品画布
var canvasboxs = document.getElementById("canvasboxs");//奖品画布
var ctxboxs = null;//奖品画布的画笔
var boxlist = ["10元现金", "15元加油卡", "20元优惠券", "25元加油卡", "25元现金", "100元优惠券", "谢谢惠顾", "15元加油卡"];//奖品列表
var boximagelist = [new Image(), new Image(), new Image(), new Image(), new Image(), new Image(), new Image(), new Image()];//奖品图片列表
var positionlist = [];//确定位置
var space = [];//距离判断
var deg = 0;//总旋转度数
var speed = 0.1;//旋转速度
var speedMax = 0;//最大旋转速度
var timer = null;//旋转定时器

//按钮画布
var canvasbtn = document.getElementById("canvasbtn");//按钮画布
var ctxbtn = null;//按钮画布的画笔
var imagego = new Image();//GO文字图
var imagejt = new Image();//按钮图


function game() {
    init();
    loop();
}

function init() {
    initbg();
    initboxs();
    initbtn();
}

function loop() {
    requestAnimFrame(loop);
    ctxbg.rotate(0.3 * Math.PI / 180);
    drawbg();
    ctxboxs.rotate(speed * Math.PI / 180);
    deg += speed * Math.PI / 180;
    drawboxs();
}

function initbg() {
    ctxbg = canvasbg.getContext("2d");
    ctxbg.translate(WIDTH / 2, HEIGHT / 2);
    imagebg.src = "./images/bg.png";
}

function initboxs() {
    ctxboxs = canvasboxs.getContext("2d");
    ctxboxs.translate(WIDTH / 2, HEIGHT / 2);
    boximagelist[0].src = "./images/1.png";
    boximagelist[1].src = "./images/2.png";
    boximagelist[2].src = "./images/3.png";
    boximagelist[3].src = "./images/4.png";
    boximagelist[4].src = "./images/5.png";
    boximagelist[5].src = "./images/6.png";
    boximagelist[6].src = "./images/7.png";
    boximagelist[7].src = "./images/8.png";
    // drawboxs();
}

function initbtn() {
    ctxbtn = canvasbtn.getContext("2d");
    imagego.src = "./images/go.png";
    imagejt.src = "./images/jt.png";
    ctxbtn.translate(70, 70);
    imagego.onload=function(){
        imagejt.onload = function () {
            drawbtn();
        }
    };
}

然后呢,图片素材的话,自己去找吧。出来的话还是挺好的。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
1. 首先,需要在HTML中创建一个包含大转盘的容器元素,并在其中添加一个canvas元素。 ```html <div id="lucky-wheel"> <canvas id="wheel-canvas"></canvas> </div> ``` 2. 在CSS中设置容器元素的样式,如宽度、高度、背景颜色等。 ```css #lucky-wheel { width: 500px; height: 500px; background-color: #fff; border-radius: 50%; position: relative; margin: 0 auto; } ``` 3. 在JavaScript编写抽奖逻辑代码。首先需要定义奖品数组,每个奖品包含名称、图片、颜色和概率等信息。 ```javascript const prizes = [ { name: '奖品1', image: 'image1.png', color: '#FFA07A', probability: 0.1 }, { name: '奖品2', image: 'image2.png', color: '#87CEFA', probability: 0.2 }, { name: '奖品3', image: 'image3.png', color: '#FFD700', probability: 0.3 }, { name: '奖品4', image: 'image4.png', color: '#00FA9A', probability: 0.4 } ]; ``` 4. 接着,需要定义转盘的样式和绘制函数。转盘的样式可以使用CSS中的渐变和阴影等效果来实现。 ```javascript const wheelStyle = { lineWidth: 2, strokeStyle: '#000', fillStyle: '#fff', shadowColor: '#666', shadowBlur: 4, gradient: { startColor: '#fff', endColor: '#ccc', startX: 0, startY: 0, endX: 0, endY: wheelRadius } }; function drawWheel() { ctx.save(); ctx.translate(wheelCenterX, wheelCenterY); ctx.rotate((Math.PI / 180) * wheelAngle); ctx.beginPath(); ctx.arc(0, 0, wheelRadius, 0, Math.PI * 2); ctx.lineWidth = wheelStyle.lineWidth; ctx.strokeStyle = wheelStyle.strokeStyle; ctx.fillStyle = wheelStyle.fillStyle; ctx.shadowColor = wheelStyle.shadowColor; ctx.shadowBlur = wheelStyle.shadowBlur; ctx.shadowOffsetX = 0; ctx.shadowOffsetY = 0; ctx.stroke(); ctx.fill(); ctx.restore(); drawWheelText(); } ``` 5. 然后,需要定义每个奖品的位置和角度,以及根据概率计算每个奖品在转盘上的占比。 ```javascript const prizeCount = prizes.length; const prizeAngle = 360 / prizeCount; let prizePositions = []; let prizeProbabilities = []; for (let i = 0; i < prizeCount; i++) { const angle = i * prizeAngle; const position = { x: wheelCenterX + Math.sin(degToRad(angle)) * (wheelRadius - wheelTextMargin), y: wheelCenterY - Math.cos(degToRad(angle)) * (wheelRadius - wheelTextMargin) }; prizePositions.push(position); prizeProbabilities.push(prizes[i].probability); } const totalProbability = prizeProbabilities.reduce((a, b) => a + b, 0); const prizeRatios = prizeProbabilities.map(p => p / totalProbability); ``` 6. 接下来,需要编写抽奖函数。该函数首先根据每个奖品的概率计算出随机的中奖结果,然后根据中奖结果的位置和角度旋转转盘,并触发抽奖结束的回调函数。 ```javascript function startLottery() { const random = Math.random(); let sum = 0; for (let i = 0; i < prizeCount; i++) { sum += prizeRatios[i]; if (random <= sum) { const prizeIndex = i; const prizeAngle = 360 - (prizeIndex * prizeAngle) - (prizeAngle / 2); const targetAngle = prizeAngle + 360 * 5; const animate = () => { if (wheelAngle < targetAngle) { wheelAngle += 5; drawWheel(); requestAnimationFrame(animate); } else { onLotteryEnd(prizes[prizeIndex]); } }; requestAnimationFrame(animate); break; } } } ``` 7. 最后,在初始化函数中调用绘制转盘和绑定抽奖按钮的事件处理函数,即可完成大转盘抽奖的实现。 ```javascript function init() { const canvas = document.getElementById('wheel-canvas'); canvas.width = wheelWidth; canvas.height = wheelHeight; ctx = canvas.getContext('2d'); drawWheel(); const button = document.getElementById('lottery-button'); button.addEventListener('click', startLottery); } ```
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值