diff --git a/diagnostic/index.html b/diagnostic/index.html
index 6155652..ff38df4 100644
--- a/diagnostic/index.html
+++ b/diagnostic/index.html
@@ -1252,30 +1252,49 @@
sendToRVS_raw({ type: 'xtts_list_voices', payload: {}, timestamp: Date.now() });
}
+ function arrayBufferToBase64(buffer) {
+ const bytes = new Uint8Array(buffer);
+ let binary = '';
+ for (let i = 0; i < bytes.length; i += 8192) {
+ binary += String.fromCharCode.apply(null, bytes.subarray(i, i + 8192));
+ }
+ return btoa(binary);
+ }
+
async function uploadVoiceSamples() {
const name = document.getElementById('xtts-clone-name').value.trim();
const files = document.getElementById('xtts-clone-files').files;
if (!name) { alert('Bitte einen Namen eingeben'); return; }
if (!files || files.length === 0) { alert('Bitte Audio-Dateien auswaehlen'); return; }
+ if (files.length > 10) { alert('Maximal 10 Dateien'); return; }
- document.getElementById('xtts-clone-status').textContent = `Lade ${files.length} Datei(en) hoch...`;
+ const status = document.getElementById('xtts-clone-status');
+ status.textContent = `Lade ${files.length} Datei(en)...`;
+ status.style.color = '#FFD60A';
- const samples = [];
- for (const file of files) {
- const buffer = await file.arrayBuffer();
- const base64 = btoa(String.fromCharCode(...new Uint8Array(buffer)));
- samples.push({ base64, name: file.name, size: file.size });
+ try {
+ const samples = [];
+ for (let i = 0; i < files.length; i++) {
+ status.textContent = `Lese Datei ${i + 1}/${files.length}: ${files[i].name}...`;
+ const buffer = await files[i].arrayBuffer();
+ const base64 = arrayBufferToBase64(buffer);
+ samples.push({ base64, name: files[i].name, size: files[i].size });
+ }
+
+ const totalSize = samples.reduce((s, f) => s + f.size, 0);
+ status.textContent = `Sende ${samples.length} Sample(s) (${(totalSize / 1024).toFixed(0)}KB)...`;
+
+ sendToRVS_raw({
+ type: 'voice_upload',
+ payload: { name, samples },
+ timestamp: Date.now(),
+ });
+
+ status.textContent = `Gesendet — warte auf Bestaetigung vom XTTS-Server...`;
+ } catch (err) {
+ status.textContent = `Fehler: ${err.message}`;
+ status.style.color = '#FF3B30';
}
-
- const totalSize = samples.reduce((s, f) => s + f.size, 0);
- document.getElementById('xtts-clone-status').textContent =
- `Sende ${samples.length} Sample(s) (${(totalSize / 1024).toFixed(0)}KB) an XTTS-Server...`;
-
- sendToRVS_raw({
- type: 'voice_upload',
- payload: { name, samples },
- timestamp: Date.now(),
- });
}
// ── Abbrechen ──────────────────────────────