Offex commited on
Commit
5169bfd
·
verified ·
1 Parent(s): ef89a6f

Update index.html

Browse files
Files changed (1) hide show
  1. index.html +97 -19
index.html CHANGED
@@ -8,19 +8,24 @@
8
  body { font-family: Arial, sans-serif; max-width: 600px; margin: 40px auto; padding: 20px; background-color: #f4f4f9; }
9
  .container { background: white; padding: 20px; border-radius: 10px; box-shadow: 0 4px 8px rgba(0,0,0,0.1); }
10
  h2 { text-align: center; color: #333; }
11
- label { font-weight: bold; display: block; margin-top: 10px; }
12
  input, textarea, select { width: 100%; padding: 10px; margin-top: 5px; border: 1px solid #ccc; border-radius: 5px; box-sizing: border-box; }
13
- button { width: 100%; background-color: #28a745; color: white; padding: 12px; border: none; border-radius: 5px; margin-top: 15px; cursor: pointer; font-size: 16px; font-weight: bold; transition: 0.3s; }
14
- button:disabled { background-color: #6c757d; cursor: not-allowed; }
15
- button:hover:not(:disabled) { background-color: #218838; }
 
 
 
 
16
 
17
  #audioContainer { margin-top: 20px; text-align: center; display: none; padding: 15px; background: #e9ecef; border-radius: 8px; }
18
 
19
- /* Status Box Styling */
20
  .status-box { text-align: center; margin-top: 15px; padding: 10px; border-radius: 5px; font-weight: bold; display: none; transition: 0.3s; }
21
  .status-loading { background-color: #fff3cd; color: #856404; display: block; }
22
  .status-success { background-color: #d4edda; color: #155724; display: block; }
23
  .status-error { background-color: #f8d7da; color: #721c24; display: block; }
 
 
24
  </style>
25
  </head>
26
  <body>
@@ -30,9 +35,18 @@
30
 
31
  <label for="apiKey">ElevenLabs API Key:</label>
32
  <input type="password" id="apiKey" placeholder="Apni API key yahan daalein..." required>
 
33
 
34
- <label for="voiceId">Voice ID:</label>
35
- <input type="text" id="voiceId" value="EXAVITQu4vr4xnSDxMaL" placeholder="Voice ID (e.g., Bella)">
 
 
 
 
 
 
 
 
36
 
37
  <label for="modelSelect">Select Model:</label>
38
  <select id="modelSelect">
@@ -44,7 +58,7 @@
44
  <label for="text">Text to Speech:</label>
45
  <textarea id="text" rows="5" placeholder="Jo bulwana hai yahan type karein..." required></textarea>
46
 
47
- <button onclick="generateAudio()" id="generateBtn">Generate Audio</button>
48
 
49
  <div id="statusBox" class="status-box"></div>
50
 
@@ -56,27 +70,93 @@
56
  </div>
57
 
58
  <script>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
59
  async function generateAudio() {
60
  const apiKey = document.getElementById('apiKey').value.trim();
61
- const voiceId = document.getElementById('voiceId').value.trim();
62
  const modelId = document.getElementById('modelSelect').value;
63
  const text = document.getElementById('text').value.trim();
 
64
 
65
- const statusBox = document.getElementById('statusBox');
 
 
 
 
66
  const audioContainer = document.getElementById('audioContainer');
67
  const audioPlayer = document.getElementById('audioPlayer');
68
  const downloadLink = document.getElementById('downloadLink');
69
  const generateBtn = document.getElementById('generateBtn');
70
 
71
- // Validation
72
  if (!apiKey || !text || !voiceId) {
73
- showStatus('Bhai, pehle API Key, Voice ID aur Text dalo!', 'error');
74
  return;
75
  }
76
 
77
- // Reset UI for new request
78
  audioContainer.style.display = "none";
79
- showStatus('Audio generate ho raha hai, thoda wait karo... ⏳', 'loading');
80
  generateBtn.disabled = true;
81
  generateBtn.innerText = "Processing...";
82
 
@@ -100,18 +180,17 @@
100
 
101
  if (!response.ok) {
102
  const errData = await response.json();
103
- throw new Error(errData.detail.message || "API request fail ho gayi!");
104
  }
105
 
106
  const blob = await response.blob();
107
  const audioUrl = URL.createObjectURL(blob);
108
 
109
- // Set audio URL to player and download link
110
  audioPlayer.src = audioUrl;
111
  downloadLink.href = audioUrl;
112
  audioContainer.style.display = "block";
113
 
114
- showStatus('Audio Ready! Ab play karo ya download karo 🎉', 'success');
115
 
116
  } catch (error) {
117
  showStatus('Error: ' + error.message, 'error');
@@ -121,11 +200,10 @@
121
  }
122
  }
123
 
124
- // Status dikhane ka function
125
  function showStatus(message, type) {
126
  const statusBox = document.getElementById('statusBox');
127
  statusBox.innerText = message;
128
- statusBox.className = 'status-box'; // Purani classes hatane ke liye
129
 
130
  if(type === 'loading') statusBox.classList.add('status-loading');
131
  if(type === 'success') statusBox.classList.add('status-success');
 
8
  body { font-family: Arial, sans-serif; max-width: 600px; margin: 40px auto; padding: 20px; background-color: #f4f4f9; }
9
  .container { background: white; padding: 20px; border-radius: 10px; box-shadow: 0 4px 8px rgba(0,0,0,0.1); }
10
  h2 { text-align: center; color: #333; }
11
+ label { font-weight: bold; display: block; margin-top: 15px; }
12
  input, textarea, select { width: 100%; padding: 10px; margin-top: 5px; border: 1px solid #ccc; border-radius: 5px; box-sizing: border-box; }
13
+
14
+ .btn { width: 100%; color: white; padding: 12px; border: none; border-radius: 5px; margin-top: 15px; cursor: pointer; font-size: 16px; font-weight: bold; transition: 0.3s; }
15
+ .btn-blue { background-color: #007bff; }
16
+ .btn-blue:hover { background-color: #0056b3; }
17
+ .btn-green { background-color: #28a745; }
18
+ .btn-green:hover:not(:disabled) { background-color: #218838; }
19
+ .btn:disabled { background-color: #6c757d; cursor: not-allowed; }
20
 
21
  #audioContainer { margin-top: 20px; text-align: center; display: none; padding: 15px; background: #e9ecef; border-radius: 8px; }
22
 
 
23
  .status-box { text-align: center; margin-top: 15px; padding: 10px; border-radius: 5px; font-weight: bold; display: none; transition: 0.3s; }
24
  .status-loading { background-color: #fff3cd; color: #856404; display: block; }
25
  .status-success { background-color: #d4edda; color: #155724; display: block; }
26
  .status-error { background-color: #f8d7da; color: #721c24; display: block; }
27
+
28
+ #customVoiceDiv { display: none; margin-top: 10px; padding: 10px; background: #fff8e1; border-left: 4px solid #ffc107; border-radius: 4px; }
29
  </style>
30
  </head>
31
  <body>
 
35
 
36
  <label for="apiKey">ElevenLabs API Key:</label>
37
  <input type="password" id="apiKey" placeholder="Apni API key yahan daalein..." required>
38
+ <button class="btn btn-blue" onclick="connectAPI()" id="connectBtn">Connect API & Load Voices</button>
39
 
40
+ <label for="voiceDropdown">Select Voice:</label>
41
+ <select id="voiceDropdown" onchange="toggleCustomVoice()">
42
+ <option value="">-- Pehle API Connect Karein --</option>
43
+ <option value="custom">✏️ Enter Custom Voice ID</option>
44
+ </select>
45
+
46
+ <div id="customVoiceDiv">
47
+ <label for="customVoiceId">Custom Voice ID:</label>
48
+ <input type="text" id="customVoiceId" placeholder="Voice ID paste karein (e.g., EXAVITQu4vr4xnSDxMaL)">
49
+ </div>
50
 
51
  <label for="modelSelect">Select Model:</label>
52
  <select id="modelSelect">
 
58
  <label for="text">Text to Speech:</label>
59
  <textarea id="text" rows="5" placeholder="Jo bulwana hai yahan type karein..." required></textarea>
60
 
61
+ <button class="btn btn-green" onclick="generateAudio()" id="generateBtn">Generate Audio</button>
62
 
63
  <div id="statusBox" class="status-box"></div>
64
 
 
70
  </div>
71
 
72
  <script>
73
+ // API Connect karke Voices load karna
74
+ async function connectAPI() {
75
+ const apiKey = document.getElementById('apiKey').value.trim();
76
+ const connectBtn = document.getElementById('connectBtn');
77
+ const voiceDropdown = document.getElementById('voiceDropdown');
78
+
79
+ if (!apiKey) {
80
+ showStatus('कृपया पहले API Key डालें!', 'error');
81
+ return;
82
+ }
83
+
84
+ showStatus('Voices लोड हो रही हैं... ⏳', 'loading');
85
+ connectBtn.disabled = true;
86
+
87
+ try {
88
+ const response = await fetch('https://api.elevenlabs.io/v1/voices', {
89
+ method: 'GET',
90
+ headers: { 'xi-api-key': apiKey }
91
+ });
92
+
93
+ if (!response.ok) {
94
+ throw new Error("API Key गलत है या नेटवर्क समस्या है!");
95
+ }
96
+
97
+ const data = await response.json();
98
+
99
+ // Dropdown clear karke naye options daalna
100
+ voiceDropdown.innerHTML = '<option value="custom">✏️ Enter Custom Voice ID</option>';
101
+
102
+ data.voices.forEach(voice => {
103
+ const option = document.createElement('option');
104
+ option.value = voice.voice_id;
105
+ option.textContent = voice.name;
106
+ voiceDropdown.appendChild(option);
107
+ });
108
+
109
+ // Default pehli voice select karna agar available ho
110
+ if (data.voices.length > 0) {
111
+ voiceDropdown.value = data.voices[0].voice_id;
112
+ }
113
+
114
+ toggleCustomVoice(); // Custom box ko hide karne ke liye
115
+ showStatus('API Connected! ' + data.voices.length + ' Voices लोड हो गईं ✅', 'success');
116
+
117
+ } catch (error) {
118
+ showStatus('Error: ' + error.message, 'error');
119
+ } finally {
120
+ connectBtn.disabled = false;
121
+ }
122
+ }
123
+
124
+ // Custom Voice ID box ko dikhana ya chhupana
125
+ function toggleCustomVoice() {
126
+ const dropdown = document.getElementById('voiceDropdown');
127
+ const customDiv = document.getElementById('customVoiceDiv');
128
+
129
+ if (dropdown.value === 'custom') {
130
+ customDiv.style.display = 'block';
131
+ } else {
132
+ customDiv.style.display = 'none';
133
+ }
134
+ }
135
+
136
+ // Audio Generate karna
137
  async function generateAudio() {
138
  const apiKey = document.getElementById('apiKey').value.trim();
 
139
  const modelId = document.getElementById('modelSelect').value;
140
  const text = document.getElementById('text').value.trim();
141
+ const dropdown = document.getElementById('voiceDropdown');
142
 
143
+ let voiceId = dropdown.value;
144
+ if (voiceId === 'custom') {
145
+ voiceId = document.getElementById('customVoiceId').value.trim();
146
+ }
147
+
148
  const audioContainer = document.getElementById('audioContainer');
149
  const audioPlayer = document.getElementById('audioPlayer');
150
  const downloadLink = document.getElementById('downloadLink');
151
  const generateBtn = document.getElementById('generateBtn');
152
 
 
153
  if (!apiKey || !text || !voiceId) {
154
+ showStatus('कृपया API Key, Voice ID और Text भरें!', 'error');
155
  return;
156
  }
157
 
 
158
  audioContainer.style.display = "none";
159
+ showStatus('Audio जनरेट हो रहा है, कृपया प्रतीक्षा करें... ⏳', 'loading');
160
  generateBtn.disabled = true;
161
  generateBtn.innerText = "Processing...";
162
 
 
180
 
181
  if (!response.ok) {
182
  const errData = await response.json();
183
+ throw new Error(errData.detail.message || "API request फेल हो गई!");
184
  }
185
 
186
  const blob = await response.blob();
187
  const audioUrl = URL.createObjectURL(blob);
188
 
 
189
  audioPlayer.src = audioUrl;
190
  downloadLink.href = audioUrl;
191
  audioContainer.style.display = "block";
192
 
193
+ showStatus('Audio तैयार है! 🎉', 'success');
194
 
195
  } catch (error) {
196
  showStatus('Error: ' + error.message, 'error');
 
200
  }
201
  }
202
 
 
203
  function showStatus(message, type) {
204
  const statusBox = document.getElementById('statusBox');
205
  statusBox.innerText = message;
206
+ statusBox.className = 'status-box';
207
 
208
  if(type === 'loading') statusBox.classList.add('status-loading');
209
  if(type === 'success') statusBox.classList.add('status-success');