记一次做九宫格抽奖转动音效嘟嘟嘟

记一次做九宫格抽奖转动音效嘟嘟嘟

采用的文章的地址:https://blog.csdn.net/qq_39759115/article/details/78604912

当我知道要做一个九宫格抽奖的时候,心里很崩溃,正值毕业季,毕设都忙不过来,于是我翻了很多抽奖的博客,最终找到了这一篇,现在我完成了,可是我不知道我当时是翻的哪位小姐姐小哥哥的博客了,就没有引用链接。
这是界面,概率什么的都加上去了,准备交差,结果要做一个嘟嘟嘟的音效,就像lh机抽奖的音效,每转一个格子就响一声音效。然后我找到了这段代码,代码如下
在这里插入图片描述

<div id="div_play1" style='display: none'></div>
<div id="div_play2" style='display: none'></div>

<script type="text/javascript">
function play()
{
	var url = "Msg.mp3";
	var div = document.getElementById('div_play1');
	div.innerHTML = '<embed src="'+url+'" loop="1" autostart="true" hidden="true"></embed>';
	var emb = document.getElementsByTagName('EMBED')[0];
	if (emb) {
		div = document.getElementById('div_play2');
		div.innerHTML = 'loading: '+emb.src;
		setTimeout(function(){div.innerHTML='';},1000);
	}
}
</script>

把play()方法到 点击事件里面,结果只实现了,点击抽奖响起一段音效,不能让音效跟随格子的转动而嘟嘟嘟的响。而且就算可以伴随格子的转动响,全程都是一种声音太单调了,于是我大脑搜索关键字,继续寻找方法。
找到一篇博客,关于OscillatorNode的,调用系统里面的音效创建一个周期性波形震荡,加进去后就实现了转动一个格子,响一声,而且还会每个音调都不一样,音调上坡,然后音调下坡。

window.AudioContext = window.AudioContext || window.webkitAudioContext;
var audioCtx = new AudioContext();//实例化AudioContext对象
// 发出的声音频率数据,表现为音调的高低
var arrFrequency = [196.00, 220.00, 246.94, 261.63, 293.66, 329.63, 349.23, 392.00, 440.00, 493.88, 523.25, 587.33, 659.25, 698.46, 783.99, 880.00, 987.77, 1046.50];
 // 音调依次递增或者递减处理需要的参数
var start = 0, direction = 1;
function test() {
	//当前频率
    var frequency = arrFrequency[start];
	//如果到头,改变音调的变化规则
    if (!frequency) {
        direction = -1 * direction;
        start = start + 2 * direction;
        frequency = arrFrequency[start];
    }
	//改变索引
    start = start + direction;
	//创建一个oscillator,它表示一个周期性波形震荡,基本上来说创造了一个音调
    var oscillator = audioCtx.createOscillator();
	//创建一个gainNode,控制音频的总音量
    var gainNode = audioCtx.createGain();
	//把音量,音调和终结点进行关联
    oscillator.connect(gainNode);
	//audioCtx.destination返回audioDestinationNode对象,表示当前audio context中所有节点的最终节点,表示音频渲染设备
    gainNode.connect(audioCtx.destination);
	//指定音调的类型
    oscillator.type = 'sine';
	//设置当前播放声音的频率,也就是最终播放声音的调调
    oscillator.frequency.value = frequency;
	//当前时间音量设置为0
    gainNode.gain.setValueAtTime(0, audioCtx.currentTime);
	//0.01秒后音量为1
    gainNode.gain.linearRampToValueAtTime(1, audioCtx.currentTime + 0.01);
	//音调从当前时间开始播放
    oscillator.start(audioCtx.currentTime);
	//一秒内声音慢慢降低
    gainNode.gain.exponentialRampToValueAtTime(0.001, audioCtx.currentTime + 1);
	//1秒后声音完全停止
    oscillator.stop(audioCtx.currentTime + 1);
};
<think>好的,我现在要帮用户解决如何开发一个带有流星动画和星空背景的HTML5随机点名网页的问题。用户提到的功能需求挺多的,我需要逐一分析每个功能如何实现,并确保它们能够协同工作。 首先,用户需要导入TXT或Excel名单。这部分我需要考虑前端如何读取文件。对于TXT文件,可以用FileReader来读取文本内容。而Excel文件可能需要使用第三方库,比如xlsx.js,这样可以在浏览器中解析Excel文件。接下来需要处理上传的文件,将名单存储到数组中,方便后续随机抽取。 然后是流星动画效果。用户提到单根快速移动流星,这可能需要用CSS动画或Canvas来实现。考虑到性能,使用CSS动画可能更简单。流星可以用一个div元素,通过关键帧动画从右上角移动到左下角,同时旋转角度,使其看起来像流星划过。可能需要调整动画的速度和出现频率,比如使用JavaScript定时器随机生成流星的位置和时间间隔。 两种点名模式,默认和自定义。默认模式可能是一次抽取一个人,而自定义模式可能允许用户设置抽取人数或其他条件。这部分需要在前端设计相应的UI控件,比如下拉菜单或输入框,根据用户的选择调整抽取逻辑。 隐藏的内定规则,比如姓名后缀-1/-2控制优先级但不显示。这需要在处理名单时,解析每个名字的后缀,将带有-1的名字优先级调高,可能在抽取时增加它们的权重。但用户看不到这个规则,所以在显示时需要去掉后缀。可以用JavaScript的字符串处理函数,比如split('-')来分离名字和后缀,并在抽取算法中考虑权重。 指定抽取人数需要一个输入框,让用户输入需要抽取的人数,然后从处理后的名单中随机选取相应数量的人。要注意去重,避免重复抽取,可能需要维护一个已选名单的数组。 声音特效部分,用户可能需要点击按钮时播放音效,比如开始和结束时的声音。这可以通过HTML5的Audio元素来实现,在特定事件触发时播放音频文件。需要确保音频文件预先加载,避免延迟。 接下来是整合所有功能到HTML结构中。页面结构大致分为背景、流星动画、控制面板和显示区域。控制面板包括文件上传、模式选择、人数输入、开始按钮等。显示区域展示被抽中的名字,可能用动态创建的DOM元素来显示。 测试时需要注意不同浏览器的兼容性,特别是文件读取和音频播放部分。另外,流星动画的性能可能会影响页面流畅度,需要优化CSS属性,使用硬件加速,比如transform属性。 最后,确保代码结构清晰,各部分功能模块化,方便后续维护和扩展。比如将文件处理、动画控制、抽取逻辑等分开写成函数,提高可读性。</think>以下是如何使用HTML5实现带流星动画的随机点名网页的详细解决方案: 一、基础结构搭建 ```html <!DOCTYPE html> <html> <head> <style> body { background: #000; overflow: hidden; margin: 0; font-family: Arial; } #container { position: relative; height: 100vh; } .meteor { position: absolute; width: 60px; height: 2px; background: linear-gradient(90deg, rgba(255,255,255,0), #fff); transform-origin: 100% 50%; animation: meteor 1s linear; } @keyframes meteor { 0% { transform: translate(100vw, -50vh) rotate(-45deg); } 100% { transform: translate(-100vw, 50vh) rotate(-45deg); } } </style> </head> <body> <input type="file" id="fileInput"> <select id="modeSelect"> <option value="default">默认模式</option> <option value="custom">自定义模式</option> </select> <input type="number" id="countInput" value="1" min="1"> <button onclick="startLottery()">开始</button> <div id="result"></div> <script> let names = []; // 初始化Web Audio API const audioContext = new (window.AudioContext || window.webkitAudioContext)(); </script> </body> </html> ``` 二、核心功能实现 1. 文件导入模块(支持TXT/Excel) ```javascript document.getElementById('fileInput').addEventListener('change', function(e) { const file = e.target.files[0]; const reader = new FileReader(); reader.onload = function(e) { if (file.name.endsWith('.xlsx')) { // 使用xlsx.js解析Excel const workbook = XLSX.read(e.target.result, {type: 'array'}); names = XLSX.utils.sheet_to_json(workbook.Sheets[workbook.SheetNames[0]]) .map(row => Object.values(row)[0]); } else { names = e.target.result.split('\n') .map(name => name.trim()) .filter(name => name); } processHiddenRules(); // 处理隐藏规则 }; if (file.name.endsWith('.xlsx')) { reader.readAsArrayBuffer(file); } else { reader.readAsText(file); } }); function processHiddenRules() { names = names.map(name => { const [realName, priority] = name.split(/-([12])$/); return { display: realName, weight: priority ? (priority === '1' ? 3 : 2) : 1 }; }); } ``` 2. 流星动画控制 ```javascript function createMeteor() { const meteor = document.createElement('div'); meteor.className = 'meteor'; meteor.style.top = `${Math.random() * 100}%`; meteor.style.left = `${Math.random() * 100}%`; document.getElementById('container').appendChild(meteor); setTimeout(() => meteor.remove(), 1000); } // 定时生成流星(每秒1-3个) setInterval(() => { const count = Math.floor(Math.random() * 3) + 1; for(let i=0; i<count; i++) { setTimeout(createMeteor, Math.random() * 300); } }, 1000); ``` 3. 随机抽取算法(含隐藏规则) ```javascript function weightedRandom(names, count) { const totalWeight = names.reduce((sum, item) => sum + item.weight, 0); const results = []; while(results.length < count) { let random = Math.random() * totalWeight; for(const item of names) { random -= item.weight; if(random < 0 && !results.includes(item)) { results.push(item); break; } } } return results.map(item => item.display); } ``` 4. 声音特效模块 ```javascript function playSound(frequency = 440, duration = 0.5) { const oscillator = audioContext.createOscillator(); const gainNode = audioContext.createGain(); oscillator.connect(gainNode); gainNode.connect(audioContext.destination); oscillator.frequency.setValueAtTime(frequency, audioContext.currentTime); gainNode.gain.setValueAtTime(0.5, audioContext.currentTime); gainNode.gain.exponentialRampToValueAtTime(0.01, audioContext.currentTime + duration); oscillator.start(); oscillator.stop(audioContext.currentTime + duration); } ``` 三、功能整合 ```javascript function startLottery() { const mode = document.getElementById('modeSelect').value; const count = parseInt(document.getElementById('countInput').value); // 播放开始音效 playSound(523.25, 0.3); // C5音 // 实现不同模式逻辑 const result = mode === 'default' ? [names[Math.floor(Math.random() * names.length)].display] : weightedRandom(names, count); // 显示结果动画 animateResult(result); // 播放结束音效 setTimeout(() => playSound(784, 0.5), 1000); // G5音 } ``` 四、性能优化建议 1. 使用`requestAnimationFrame`优化动画性能 2. 对频繁操作的DOM元素使用CSS `will-change`属性 3. 使用Web Worker处理大数据量的名单解析 4. 流星动画采用Canvas渲染替代DOM元素(性能提升50%+
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值