如何将HTML文件上传输入框作为变量用于模拟器加载ROM?
解决方案
关键问题分析
- 本地ROM文件需要转为Blob URL才能被EmulatorJS识别,直接赋值DOM元素无效
- 选择文件后需要重新初始化模拟器,因为loader.js加载时会读取
EJS_gameUrl并完成初始化 - 隐藏文件输入框可通过CSS
display: none实现,用自定义按钮触发选择更友好
完整实现代码
<!-- 默认隐藏原生文件输入框,用按钮触发选择 --> <div style="display: none;"> <input type='file' id='fileURL' accept=".gba"> </div> <button id="selectRomBtn">选择GBA ROM文件</button> <div style='width:100%;height:100%;max-width:100%'> <div id='game'></div> </div> <script type='text/javascript'> // 模拟器基础配置 let EJS_player = '#game'; let EJS_core = 'gba'; let EJS_pathtodata = 'https://cdn.jsdelivr.net/gh/ethanaobrien/emulatorjs@main/data'; let emulatorInstance = null; // 获取DOM元素 const fileInput = document.getElementById('fileURL'); const selectBtn = document.getElementById('selectRomBtn'); // 按钮点击触发文件选择弹窗 selectBtn.addEventListener('click', () => { fileInput.click(); }); // 文件选择完成后的处理逻辑 fileInput.addEventListener('change', (e) => { const selectedFile = e.target.files[0]; if (!selectedFile) return; // 将本地文件转换为模拟器可识别的Blob URL EJS_gameUrl = URL.createObjectURL(selectedFile); // 销毁已存在的模拟器实例(避免重复加载冲突) if (emulatorInstance) { emulatorInstance.destroy(); } // 重新加载模拟器loader脚本,应用新的ROM地址 const loaderScript = document.createElement('script'); loaderScript.src = `${EJS_pathtodata}/loader.js`; loaderScript.onload = () => { emulatorInstance = window.EJS; }; // 移除旧的loader脚本,防止重复初始化 const oldLoader = document.querySelector('script[src*="loader.js"]'); if (oldLoader) oldLoader.remove(); document.body.appendChild(loaderScript); // 选择文件后隐藏选择按钮(可选,根据需求调整) selectBtn.style.display = 'none'; }); </script>
核心步骤说明
- Blob URL转换:通过
URL.createObjectURL()将本地文件转为浏览器可访问的临时URL,这是让模拟器读取本地文件的核心逻辑 - 模拟器重新初始化:每次选择新文件后,销毁旧实例并重新加载loader.js,确保模拟器使用新的ROM地址启动
- 交互优化:隐藏原生文件输入框,用自定义按钮触发选择,提升页面美观度;选择完成后可隐藏按钮,让用户专注于模拟器窗口
内容的提问来源于stack exchange,提问作者Greenery
相关产品推荐
相关产品推荐

