test_ui / frontend /index.html
britto224's picture
Upload 9 files
4c371dd verified
<!doctype html>
<html lang="vi">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>Yue AI - Discord Connection</title>
<script src="https://cdn.socket.io/4.7.2/socket.io.min.js"></script>
<script>
window.GLOBAL_CONF = {
base: "https://nopeprime-open-llm.hf.space",
ws: "wss://nopeprime-open-llm.hf.space/client-ws",
model: "https://nopeprime-open-llm.hf.space/live2d-models/Kamiyahakuk_pro/runtime/Kamiyahakuk_pro.model3.json"
};
const OriginalWS = window.WebSocket;
window.WebSocket = class extends OriginalWS {
constructor(url, p) {
let u = url || window.GLOBAL_CONF.ws;
if (u.includes('undefined')) u = window.GLOBAL_CONF.ws;
super(u, p);
}
};
</script>
<script type="module" crossorigin src="./assets/main-nu7uwxNJ.js?v=2026"></script>
<link rel="stylesheet" crossorigin href="./assets/main-QEkl09-0.css">
<style>
body { margin: 0; background: #1a1a1a; overflow: hidden; height: 100vh; font-family: sans-serif; }
#root { position: absolute; width: 100%; height: 100%; z-index: 1; }
.discord-btn {
position: fixed; top: 15px; right: 15px; z-index: 9999;
padding: 12px 24px; background: #5865F2; color: white;
border-radius: 8px; cursor: pointer; border: none; font-weight: bold;
box-shadow: 0 4px 15px rgba(0,0,0,0.5);
}
</style>
</head>
<body>
<div id="root"></div>
<button class="discord-btn" onclick="window.connectDiscord()">🎙️ Kết nối Discord</button>
<script>
const dsSocket = io('https://nopeprime-discord-bot.hf.space', { transports: ['websocket'] });
let sharedAudioCtx = null;
let mainDest = null;
async function initAudio() {
if (!sharedAudioCtx) {
sharedAudioCtx = new (window.AudioContext || window.webkitAudioContext)();
mainDest = sharedAudioCtx.createMediaStreamDestination();
// Recorder tối ưu cho Discord
const recorder = new MediaRecorder(mainDest.stream, {
mimeType: 'audio/webm;codecs=opus',
audioBitsPerSecond: 128000
});
recorder.ondataavailable = async (e) => {
if (e.data.size > 0 && dsSocket.connected) {
const buffer = await e.data.arrayBuffer();
dsSocket.emit('ai_audio_stream', buffer);
}
};
recorder.start(100);
console.log("🎙️ Hệ thống Stream đã sẵn sàng!");
}
if (sharedAudioCtx.state === 'suspended') await sharedAudioCtx.resume();
}
// Hook tất cả AudioContext phát sinh từ Live2D hoặc Audio tag
const originalCreateElementSource = AudioContext.prototype.createMediaElementSource;
AudioContext.prototype.createMediaElementSource = function(element) {
const source = originalCreateElementSource.call(this, element);
if (mainDest) {
source.connect(mainDest);
console.log("🔗 Đã kết nối nguồn âm thanh mới vào luồng Discord");
}
return source;
};
// Tìm và gắn thẻ audio (nhạc, voice)
setInterval(() => {
document.querySelectorAll('audio').forEach(a => {
if (!a.dataset.hooked) {
a.dataset.hooked = "true";
a.crossOrigin = "anonymous";
if (sharedAudioCtx && mainDest) {
try {
const s = sharedAudioCtx.createMediaElementSource(a);
s.connect(mainDest);
s.connect(sharedAudioCtx.destination);
} catch(e) {}
}
}
});
}, 1000);
window.connectDiscord = async () => {
await initAudio();
fetch('https://nopeprime-discord-bot.hf.space/join')
.then(() => console.log("✅ Đã gọi Bot vào phòng voice"));
};
// Ghi đè log để bắt lệnh hát
const oldLog = console.log;
console.log = function(...args) {
oldLog.apply(console, args);
if (typeof args[0] === 'string' && args[0].includes('[[SING_COMMAND]]')) {
let song = args[0].split('[[SING_COMMAND]]')[1].trim().split(' ')[0].replace('.mp3','') + '.mp3';
let p = document.getElementById('m-player') || document.createElement('audio');
p.id = 'm-player'; p.src = `./music/${song}`;
if(!p.parentElement) document.body.appendChild(p);
p.play();
}
};
document.addEventListener('mousedown', initAudio, { once: true });
</script>
</body>
</html>