Spin Wheel App
spinner-arrow

Click On The Spin Button To Start

* { padding: 0; margin: 0; box-sizing: border-box; font-family: "Poppins", sans-serif; } body { height: 100vh; background: linear-gradient(135deg, #c3a3f1, #6414e9); } .wrapper { width: 90%; max-width: 34.37em; max-height: 90vh; background-color: #ffffff; position: absolute; transform: translate(-50%, -50%); top: 50%; left: 50%; padding: 3em; border-radius: 1em; box-shadow: 0 4em 5em rgba(27, 8, 53, 0.2); } .container { position: relative; width: 100%; height: 100%; } #wheel { max-height: inherit; width: inherit; top: 0; padding: 0; } @keyframes rotate { 100% { transform: rotate(360deg); } } #spin-btn { position: absolute; transform: translate(-50%, -50%); top: 50%; left: 50%; height: 26%; width: 26%; border-radius: 50%; cursor: pointer; border: 0; background: radial-gradient(#fdcf3b 50%, #d88a40 85%); color: #c66e16; text-transform: uppercase; font-size: 1.8em; letter-spacing: 0.1em; font-weight: 600; } img { position: absolute; width: 4em; top: 45%; right: -8%; } #final-value { font-size: 1.5em; text-align: center; margin-top: 1.5em; color: #202020; font-weight: 500; } @media screen and (max-width: 768px) { .wrapper { font-size: 12px; } img { right: -5%; } } const wheel = document.getElementById("wheel"); const spinBtn = document.getElementById("spin-btn"); const finalValue = document.getElementById("final-value"); //Object that stores values of minimum and maximum angle for a value const rotationValues = [ { minDegree: 0, maxDegree: 30, value: 2 }, { minDegree: 31, maxDegree: 90, value: 1 }, { minDegree: 91, maxDegree: 150, value: 6 }, { minDegree: 151, maxDegree: 210, value: 5 }, { minDegree: 211, maxDegree: 270, value: 4 }, { minDegree: 271, maxDegree: 330, value: 3 }, { minDegree: 331, maxDegree: 360, value: 2 }, ]; //Size of each piece const data = [16, 16, 16, 16, 16, 16]; //background color for each piece var pieColors = [ "#8b35bc", "#b163da", "#8b35bc", "#b163da", "#8b35bc", "#b163da", ]; //Create chart let myChart = new Chart(wheel, { //Plugin for displaying text on pie chart plugins: [ChartDataLabels], //Chart Type Pie type: "pie", data: { //Labels(values which are to be displayed on chart) labels: [1, 2, 3, 4, 5, 6], //Settings for dataset/pie datasets: [ { backgroundColor: pieColors, data: data, }, ], }, options: { //Responsive chart responsive: true, animation: { duration: 0 }, plugins: { //hide tooltip and legend tooltip: false, legend: { display: false, }, //display labels inside pie chart datalabels: { color: "#ffffff", formatter: (_, context) => context.chart.data.labels[context.dataIndex], font: { size: 24 }, }, }, }, }); //display value based on the randomAngle const valueGenerator = (angleValue) => { for (let i of rotationValues) { //if the angleValue is between min and max then display it if (angleValue >= i.minDegree && angleValue <= i.maxDegree) { finalValue.innerHTML = `

Value: ${i.value}

`; spinBtn.disabled = false; break; } } }; //Spinner count let count = 0; //100 rotations for animation and last rotation for result let resultValue = 101; //Start spinning spinBtn.addEventListener("click", () => { spinBtn.disabled = true; //Empty final value finalValue.innerHTML = `

Good Luck!

`; //Generate random degrees to stop at let randomDegree = Math.floor(Math.random() * (355 - 0 + 1) + 0); //Interval for rotation animation let rotationInterval = window.setInterval(() => { //Set rotation for piechart /* Initially to make the piechart rotate faster we set resultValue to 101 so it rotates 101 degrees at a time and this reduces by 1 with every count. Eventually on last rotation we rotate by 1 degree at a time. */ myChart.options.rotation = myChart.options.rotation + resultValue; //Update chart with new value; myChart.update(); //If rotation>360 reset it back to 0 if (myChart.options.rotation >= 360) { count += 1; resultValue -= 5; myChart.options.rotation = 0; } else if (count > 15 && myChart.options.rotation == randomDegree) { valueGenerator(randomDegree); clearInterval(rotationInterval); count = 0; resultValue = 101; } }, 10); });

No comments:

Post a Comment