akshansh36 commited on
Commit
cfc3b59
1 Parent(s): 3931c03

Update app.py

Browse files
Files changed (1) hide show
  1. app.py +374 -17
app.py CHANGED
@@ -1,27 +1,384 @@
 
1
  import gradio as gr
2
- import numpy as np
 
 
 
3
  import time
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
4
 
5
- def add_to_stream(audio, instream):
6
- time.sleep(1)
7
- if audio is None:
8
- return gr.update(), instream
9
- if instream is None:
10
- ret = audio
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
11
  else:
12
- ret = (audio[0], np.concatenate((instream[1], audio[1])))
13
- return ret, ret
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
14
 
 
 
15
 
16
- with gr.Blocks() as demo:
17
- inp = gr.Audio(sources="microphone")
18
- out = gr.Audio()
19
- stream = gr.State()
20
- clear = gr.Button("Clear")
21
 
22
- inp.stream(add_to_stream, [inp, stream], [out, stream])
23
- clear.click(lambda: [None, None, None], None, [inp, out, stream])
24
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
25
 
26
  if __name__ == "__main__":
27
- demo.launch()
 
 
 
 
 
 
 
 
 
 
 
 
1
+ import os
2
  import gradio as gr
3
+ import spaces
4
+ from infer_rvc_python import BaseLoader
5
+ import random
6
+ import logging
7
  import time
8
+ import soundfile as sf
9
+ from infer_rvc_python.main import download_manager
10
+ import zipfile
11
+ import edge_tts
12
+ import asyncio
13
+ import librosa
14
+ import traceback
15
+ import soundfile as sf
16
+ from pedalboard import Pedalboard, Reverb, Compressor, HighpassFilter
17
+ from pedalboard.io import AudioFile
18
+ from pydub import AudioSegment
19
+ import noisereduce as nr
20
+ import numpy as np
21
+ import urllib.request
22
+ import shutil
23
+ import threading
24
+
25
+ logging.getLogger("infer_rvc_python").setLevel(logging.ERROR)
26
+
27
+ # Ensure the correct path to the models directory
28
+ model_dir = os.path.join(os.path.dirname(__file__), "models")
29
+
30
+ converter = BaseLoader(only_cpu=False, hubert_path=None, rmvpe_path=None)
31
+
32
+ title = "<center><strong><font size='7'>Vodex AI</font></strong></center>"
33
+ theme = "aliabid94/new-theme"
34
+
35
+ def find_files(directory):
36
+ file_paths = []
37
+ for filename in os.listdir(directory):
38
+ if filename.endswith('.pth') or filename.endswith('.zip') or filename.endswith('.index'):
39
+ file_paths.append(os.path.join(directory, filename))
40
+ return file_paths
41
+
42
+ def unzip_in_folder(my_zip, my_dir):
43
+ with zipfile.ZipFile(my_zip) as zip:
44
+ for zip_info in zip.infolist():
45
+ if zip_info.is_dir():
46
+ continue
47
+ zip_info.filename = os.path.basename(zip_info.filename)
48
+ zip.extract(zip_info, my_dir)
49
+
50
+ def find_my_model(a_, b_):
51
+ if a_ is None or a_.endswith(".pth"):
52
+ return a_, b_
53
+
54
+ txt_files = []
55
+ for base_file in [a_, b_]:
56
+ if base_file is not None and base_file.endswith(".txt"):
57
+ txt_files.append(base_file)
58
+
59
+ directory = os.path.dirname(a_)
60
+
61
+ for txt in txt_files:
62
+ with open(txt, 'r') as file:
63
+ first_line = file.readline()
64
+
65
+ download_manager(
66
+ url=first_line.strip(),
67
+ path=directory,
68
+ extension="",
69
+ )
70
+
71
+ for f in find_files(directory):
72
+ if f.endswith(".zip"):
73
+ unzip_in_folder(f, directory)
74
+
75
+ model = None
76
+ index = None
77
+ end_files = find_files(directory)
78
+
79
+ for ff in end_files:
80
+ if ff.endswith(".pth"):
81
+ model = os.path.join(directory, ff)
82
+ gr.Info(f"Model found: {ff}")
83
+ if ff.endswith(".index"):
84
+ index = os.path.join(directory, ff)
85
+ gr.Info(f"Index found: {ff}")
86
+
87
+ if not model:
88
+ gr.Error(f"Model not found in: {end_files}")
89
+
90
+ if not index:
91
+ gr.Warning("Index not found")
92
+
93
+ return model, index
94
+
95
+ def get_file_size(url):
96
+ if "huggingface" not in url:
97
+ raise ValueError("Only downloads from Hugging Face are allowed")
98
+
99
+ try:
100
+ with urllib.request.urlopen(url) as response:
101
+ info = response.info()
102
+ content_length = info.get("Content-Length")
103
+
104
+ file_size = int(content_length)
105
+ if file_size > 500000000:
106
+ raise ValueError("The file is too large. You can only download files up to 500 MB in size.")
107
+
108
+ except Exception as e:
109
+ raise e
110
+
111
+ def clear_files(directory):
112
+ time.sleep(15)
113
+ print(f"Clearing files: {directory}.")
114
+ shutil.rmtree(directory)
115
+
116
+ def get_my_model(url_data):
117
+ if not url_data:
118
+ return None, None
119
+
120
+ if "," in url_data:
121
+ a_, b_ = url_data.split()
122
+ a_, b_ = a_.strip().replace("/blob/", "/resolve/"), b_.strip().replace("/blob/", "/resolve/")
123
+ else:
124
+ a_, b_ = url_data.strip().replace("/blob/", "/resolve/"), None
125
+
126
+ out_dir = "downloads"
127
+ folder_download = str(random.randint(1000, 9999))
128
+ directory = os.path.join(out_dir, folder_download)
129
+ os.makedirs(directory, exist_ok=True)
130
+
131
+ try:
132
+ get_file_size(a_)
133
+ if b_:
134
+ get_file_size(b_)
135
+
136
+ valid_url = [a_] if not b_ else [a_, b_]
137
+ for link in valid_url:
138
+ download_manager(
139
+ url=link,
140
+ path=directory,
141
+ extension="",
142
+ )
143
+
144
+ for f in find_files(directory):
145
+ if f.endswith(".zip"):
146
+ unzip_in_folder(f, directory)
147
+
148
+ model = None
149
+ index = None
150
+ end_files = find_files(directory)
151
+
152
+ for ff in end_files:
153
+ if ff.endswith(".pth"):
154
+ model = ff
155
+ gr.Info(f"Model found: {ff}")
156
+ if ff.endswith(".index"):
157
+ index = ff
158
+ gr.Info(f"Index found: {ff}")
159
+
160
+ if not model:
161
+ raise ValueError(f"Model not found in: {end_files}")
162
+
163
+ if not index:
164
+ gr.Warning("Index not found")
165
+ else:
166
+ index = os.path.abspath(index)
167
+
168
+ return os.path.abspath(model), index
169
+
170
+ except Exception as e:
171
+ raise e
172
+ finally:
173
+ t = threading.Thread(target=clear_files, args=(directory,))
174
+ t.start()
175
+
176
+ def convert_now(audio_files, random_tag, converter):
177
+ return converter(
178
+ audio_files,
179
+ random_tag,
180
+ overwrite=False,
181
+ parallel_workers=8
182
+ )
183
 
184
+ def apply_noisereduce(audio_list):
185
+ print("Applying noise reduction")
186
+
187
+ result = []
188
+ for audio_path in audio_list:
189
+ out_path = f'{os.path.splitext(audio_path)[0]}_noisereduce.wav'
190
+
191
+ try:
192
+ # Load audio file
193
+ audio = AudioSegment.from_file(audio_path)
194
+
195
+ # Convert audio to numpy array
196
+ samples = np.array(audio.get_array_of_samples())
197
+
198
+ reduced_noise = nr.reduce_noise(samples, sr=audio.frame_rate, prop_decrease=0.6)
199
+
200
+
201
+ reduced_audio = AudioSegment(
202
+ reduced_noise.tobytes(),
203
+ frame_rate=audio.frame_rate,
204
+ sample_width=audio.sample_width,
205
+ channels=audio.channels
206
+ )
207
+
208
+
209
+ reduced_audio.export(out_path, format="wav")
210
+ result.append(out_path)
211
+
212
+ except Exception as e:
213
+ traceback.print_exc()
214
+ print(f"Error in noise reduction: {str(e)}")
215
+ result.append(audio_path)
216
+
217
+ return result
218
+
219
+ def run(audio_files, file_m, file_index):
220
+ if not audio_files:
221
+ raise ValueError("Please provide an audio file.")
222
+
223
+ if isinstance(audio_files, str):
224
+ audio_files = [audio_files]
225
+
226
+ try:
227
+ duration_base = librosa.get_duration(filename=audio_files[0])
228
+ print("Duration:", duration_base)
229
+ except Exception as e:
230
+ print(e)
231
+
232
+ file_m = os.path.join(model_dir, file_m)
233
+ file_index = os.path.join(model_dir, file_index) if file_index else None
234
+
235
+ random_tag = "USER_" + str(random.randint(10000000, 99999999))
236
+
237
+ converter.apply_conf(
238
+ tag=random_tag,
239
+ file_model=file_m,
240
+ pitch_algo="rmvpe+",
241
+ pitch_lvl=0,
242
+ file_index=file_index,
243
+ index_influence=0.75,
244
+ respiration_median_filtering=3,
245
+ envelope_ratio=0.25,
246
+ consonant_breath_protection=0.5,
247
+ resample_sr=44100 if audio_files[0].endswith('.mp3') else 0,
248
+ )
249
+ time.sleep(0.1)
250
+
251
+ result = convert_now(audio_files, random_tag, converter)
252
+ result = apply_noisereduce(result)
253
+
254
+ return result, result[0] # Assuming result is a list of file paths
255
+
256
+
257
+ def process_audio(audio_file, uploaded_files, file_m, file_index):
258
+ if audio_file is not None:
259
+ result, _ = run([audio_file], file_m, file_index)
260
+ elif uploaded_files is not None:
261
+ result, _ = run(uploaded_files, file_m, file_index)
262
+
263
+ # Create a mapping from filenames to full paths
264
+ file_mapping = {os.path.basename(path): path for path in result}
265
+ filenames = list(file_mapping.keys())
266
+
267
+ # Return the file_mapping, updated dropdown, initial playback file, and list of all files for download
268
+ return file_mapping, gr.update(choices=filenames, value=filenames[0], visible=True), file_mapping[filenames[0]], result
269
+
270
+ def update_audio_selection(selected_filename, file_mapping):
271
+ if file_mapping is None:
272
+ raise ValueError("File mapping is not available.")
273
+ if selected_filename not in file_mapping:
274
+ raise ValueError(f"Selected filename {selected_filename} not found in file mapping.")
275
+
276
+ # Use the selected filename to find the full path from the mapping
277
+ full_path = file_mapping[selected_filename]
278
+ return gr.update(value=full_path, visible=True)
279
+
280
+
281
+ def switch_input(input_type):
282
+ if input_type == "Record Audio":
283
+ return gr.update(visible=True), gr.update(visible=False)
284
  else:
285
+ return gr.update(visible=False), gr.update(visible=True)
286
+
287
+
288
+ def model_conf():
289
+ model_files = [f for f in os.listdir(model_dir) if f.endswith(".pth")]
290
+ return gr.Dropdown(
291
+ label="Select Model File",
292
+ choices=model_files,
293
+ value=model_files[0] if model_files else None,
294
+ interactive=True,
295
+ )
296
+
297
+ def index_conf():
298
+ index_files = [f for f in os.listdir(model_dir) if f.endswith(".index")]
299
+ return gr.Dropdown(
300
+ label="Select Index File",
301
+ choices=index_files,
302
+ value=index_files[0] if index_files else None,
303
+ interactive=True,
304
+ )
305
+
306
+ def audio_conf():
307
+ return gr.Audio(
308
+ label="Upload or Record Audio",
309
+ sources=["upload", "microphone"], # Allows recording via microphone
310
+ type="filepath",
311
+
312
+ )
313
+
314
+ def button_conf():
315
+ return gr.Button(
316
+ "Inference",
317
+ variant="primary",
318
+ )
319
 
320
+ def output_conf():
321
+ return gr.File(label="Result", file_count="multiple", interactive=False), gr.Audio(label="Play Result",visible=False,show_share_button=False)
322
 
323
+ def get_gui(theme):
324
+ with gr.Blocks(theme=theme, delete_cache=(3200, 3200)) as app:
325
+ gr.Markdown(title)
 
 
326
 
 
 
327
 
328
+ input_type = gr.Radio(["Record Audio", "Upload Files"], label="Select Input Method", value="Record Audio")
329
+
330
+ audio = gr.Audio(label="Record Audio", sources="microphone", type="filepath", visible=True)
331
+ files = gr.File(label="Upload Audio Files", type="filepath", file_count="multiple", visible=False)
332
+
333
+ input_type.change(switch_input, inputs=[input_type], outputs=[audio, files])
334
+
335
+ model = model_conf()
336
+ indx = index_conf()
337
+ button_base = button_conf()
338
+
339
+ dropdown = gr.Dropdown(choices=[], label="Select Processed Audio", visible=False)
340
+ output_audio = gr.Audio(label="Play Selected Audio", visible=False,show_share_button=False)
341
+ output_files = gr.File(label="Download Processed Audio", file_count="multiple", interactive=False)
342
+
343
+ # output_file, output_audio = output_conf()
344
+
345
+ file_mapping_state = gr.State()
346
+
347
+ button_base.click(
348
+ process_audio,
349
+ inputs=[audio, files, model, indx],
350
+ outputs=[file_mapping_state, dropdown, output_audio, output_files], # Store file mapping in state
351
+ )
352
+
353
+ dropdown.change(
354
+ update_audio_selection,
355
+ inputs=[dropdown, file_mapping_state], # Pass the state (file_mapping) and dropdown selection
356
+ outputs=output_audio, # Play the selected audio file using the full path
357
+ )
358
+
359
+ # gr.Examples(
360
+ # examples=[
361
+ # ["./test.ogg", "./model.pth", "./model.index"],
362
+ # ["./example2/test2.ogg", "./example2/model.pth", "./example2/model.index"],
363
+ # ],
364
+ # fn=process_audio,
365
+ # inputs=[audio, files, model, indx],
366
+ # outputs=[output_file, output_audio],
367
+ # cache_examples=False,
368
+ # )
369
+
370
+ return app
371
 
372
  if __name__ == "__main__":
373
+ app = get_gui(theme)
374
+ app.queue(default_concurrency_limit=40)
375
+ app.launch(
376
+ max_threads=40,
377
+ share=False,
378
+ show_error=True,
379
+ quiet=False,
380
+ debug=False,
381
+ allowed_paths=["./downloads/"],
382
+ )
383
+
384
+