mosi77/5
0
1import os
2import subprocess
3import sys
4import shutil
5import gradio as gr
6from assets.i18n.i18n import I18nAuto
7from core import (
8 run_preprocess_script,
9 run_extract_script,
10 run_train_script,
11 run_index_script,
12 run_prerequisites_script,
13)
14from rvc.configs.config import max_vram_gpu, get_gpu_info
15from rvc.lib.utils import format_title
16from tabs.settings.restart import restart_applio
17
18i18n = I18nAuto()
19now_dir = os.getcwd()
20sys.path.append(now_dir)
21
22pretraineds_v1 = [
23 (
24 "pretrained_v1/",
25 [
26 "D32k.pth",
27 "D40k.pth",
28 "D48k.pth",
29 "G32k.pth",
30 "G40k.pth",
31 "G48k.pth",
32 "f0D32k.pth",
33 "f0D40k.pth",
34 "f0D48k.pth",
35 "f0G32k.pth",
36 "f0G40k.pth",
37 "f0G48k.pth",
38 ],
39 ),
40]
41
42folder_mapping = {
43 "pretrained_v1/": "rvc/pretraineds/pretrained_v1/",
44}
45
46sup_audioext = {
47 "wav",
48 "mp3",
49 "flac",
50 "ogg",
51 "opus",
52 "m4a",
53 "mp4",
54 "aac",
55 "alac",
56 "wma",
57 "aiff",
58 "webm",
59 "ac3",
60}
61
62# Custom Pretraineds
63pretraineds_custom_path = os.path.join(
64 now_dir, "rvc", "pretraineds", "pretraineds_custom"
65)
66
67pretraineds_custom_path_relative = os.path.relpath(pretraineds_custom_path, now_dir)
68
69custom_embedder_root = os.path.join(now_dir, "rvc", "embedders", "embedders_custom")
70custom_embedder_root_relative = os.path.relpath(custom_embedder_root, now_dir)
71
72os.makedirs(custom_embedder_root, exist_ok=True)
73os.makedirs(pretraineds_custom_path_relative, exist_ok=True)
74
75
76def get_pretrained_list(suffix):
77 return [
78 os.path.join(dirpath, filename)
79 for dirpath, _, filenames in os.walk(pretraineds_custom_path_relative)
80 for filename in filenames
81 if filename.endswith(".pth") and suffix in filename
82 ]
83
84
85pretraineds_list_d = get_pretrained_list("D")
86pretraineds_list_g = get_pretrained_list("G")
87
88
89def refresh_custom_pretraineds():
90 return (
91 {"choices": sorted(get_pretrained_list("G")), "__type__": "update"},
92 {"choices": sorted(get_pretrained_list("D")), "__type__": "update"},
93 )
94
95
96# Dataset Creator
97datasets_path = os.path.join(now_dir, "assets", "datasets")
98
99if not os.path.exists(datasets_path):
100 os.makedirs(datasets_path)
101
102datasets_path_relative = os.path.relpath(datasets_path, now_dir)
103
104
105def get_datasets_list():
106 return [
107 dirpath
108 for dirpath, _, filenames in os.walk(datasets_path_relative)
109 if any(filename.endswith(tuple(sup_audioext)) for filename in filenames)
110 ]
111
112
113def refresh_datasets():
114 return {"choices": sorted(get_datasets_list()), "__type__": "update"}
115
116
117# Model Names
118models_path = os.path.join(now_dir, "logs")
119
120
121def get_models_list():
122 return [
123 os.path.basename(dirpath)
124 for dirpath in os.listdir(models_path)
125 if os.path.isdir(os.path.join(models_path, dirpath))
126 and all(excluded not in dirpath for excluded in ["zips", "mute"])
127 ]
128
129
130def refresh_models():
131 return {"choices": sorted(get_models_list()), "__type__": "update"}
132
133
134# Refresh Models and Datasets
135def refresh_models_and_datasets():
136 return (
137 {"choices": sorted(get_models_list()), "__type__": "update"},
138 {"choices": sorted(get_datasets_list()), "__type__": "update"},
139 )
140
141
142# Refresh Custom Pretraineds
143def get_embedder_custom_list():
144 return [
145 os.path.join(dirpath, filename)
146 for dirpath, _, filenames in os.walk(custom_embedder_root_relative)
147 for filename in filenames
148 if filename.endswith(".pt")
149 ]
150
151
152def refresh_custom_embedder_list():
153 return {"choices": sorted(get_embedder_custom_list()), "__type__": "update"}
154
155
156# Drop Model
157def save_drop_model(dropbox):
158 if ".pth" not in dropbox:
159 gr.Info(
160 i18n(
161 "The file you dropped is not a valid pretrained file. Please try again."
162 )
163 )
164 else:
165 file_name = os.path.basename(dropbox)
166 pretrained_path = os.path.join(pretraineds_custom_path_relative, file_name)
167 if os.path.exists(pretrained_path):
168 os.remove(pretrained_path)
169 os.rename(dropbox, pretrained_path)
170 gr.Info(
171 i18n(
172 "Click the refresh button to see the pretrained file in the dropdown menu."
173 )
174 )
175 return None
176
177
178# Drop Dataset
179def save_drop_dataset_audio(dropbox, dataset_name):
180 if not dataset_name:
181 gr.Info("Please enter a valid dataset name. Please try again.")
182 return None, None
183 else:
184 file_extension = os.path.splitext(dropbox)[1][1:].lower()
185 if file_extension not in sup_audioext:
186 gr.Info("The file you dropped is not a valid audio file. Please try again.")
187 else:
188 dataset_name = format_title(dataset_name)
189 audio_file = format_title(os.path.basename(dropbox))
190 dataset_path = os.path.join(now_dir, "assets", "datasets", dataset_name)
191 if not os.path.exists(dataset_path):
192 os.makedirs(dataset_path)
193 destination_path = os.path.join(dataset_path, audio_file)
194 if os.path.exists(destination_path):
195 os.remove(destination_path)
196 os.rename(dropbox, destination_path)
197 gr.Info(
198 i18n(
199 "The audio file has been successfully added to the dataset. Please click the preprocess button."
200 )
201 )
202 dataset_path = os.path.dirname(destination_path)
203 relative_dataset_path = os.path.relpath(dataset_path, now_dir)
204
205 return None, relative_dataset_path
206
207
208# Drop Custom Embedder
209def save_drop_custom_embedder(dropbox):
210 if ".pt" not in dropbox:
211 gr.Info(
212 i18n("The file you dropped is not a valid embedder file. Please try again.")
213 )
214 else:
215 file_name = os.path.basename(dropbox)
216 custom_embedder_path = os.path.join(custom_embedder_root, file_name)
217 if os.path.exists(custom_embedder_path):
218 os.remove(custom_embedder_path)
219 os.rename(dropbox, custom_embedder_path)
220 gr.Info(
221 i18n(
222 "Click the refresh button to see the embedder file in the dropdown menu."
223 )
224 )
225 return None
226
227
228# Export
229## Get Pth and Index Files
230def get_pth_list():
231 return [
232 os.path.relpath(os.path.join(dirpath, filename), now_dir)
233 for dirpath, _, filenames in os.walk(models_path)
234 for filename in filenames
235 if filename.endswith(".pth")
236 ]
237
238
239def get_index_list():
240 return [
241 os.path.relpath(os.path.join(dirpath, filename), now_dir)
242 for dirpath, _, filenames in os.walk(models_path)
243 for filename in filenames
244 if filename.endswith(".index") and "trained" not in filename
245 ]
246
247
248def refresh_pth_and_index_list():
249 return (
250 {"choices": sorted(get_pth_list()), "__type__": "update"},
251 {"choices": sorted(get_index_list()), "__type__": "update"},
252 )
253
254
255## Export Pth and Index Files
256def export_pth(pth_path):
257 if pth_path and os.path.exists(pth_path):
258 return pth_path
259 return None
260
261
262def export_index(index_path):
263 if index_path and os.path.exists(index_path):
264 return index_path
265 return None
266
267
268## Upload to Google Drive
269def upload_to_google_drive(pth_path, index_path):
270 def upload_file(file_path):
271 if file_path:
272 try:
273 gr.Info(f"Uploading {pth_path} to Google Drive...")
274 google_drive_folder = "/content/drive/MyDrive/ApplioExported"
275 if not os.path.exists(google_drive_folder):
276 os.makedirs(google_drive_folder)
277 google_drive_file_path = os.path.join(
278 google_drive_folder, os.path.basename(file_path)
279 )
280 if os.path.exists(google_drive_file_path):
281 os.remove(google_drive_file_path)
282 shutil.copy2(file_path, google_drive_file_path)
283 gr.Info("File uploaded successfully.")
284 except Exception as error:
285 print(error)
286 gr.Info("Error uploading to Google Drive")
287
288 upload_file(pth_path)
289 upload_file(index_path)
290
291
292# Train Tab
293def train_tab():
294 with gr.Accordion(i18n("Preprocess")):
295 with gr.Row():
296 with gr.Column():
297 model_name = gr.Dropdown(
298 label=i18n("Model Name"),
299 info=i18n("Name of the new model."),
300 choices=get_models_list(),
301 value="my-project",
302 interactive=True,
303 allow_custom_value=True,
304 )
305 dataset_path = gr.Dropdown(
306 label=i18n("Dataset Path"),
307 info=i18n("Path to the dataset folder."),
308 # placeholder=i18n("Enter dataset path"),
309 choices=get_datasets_list(),
310 allow_custom_value=True,
311 interactive=True,
312 )
313 refresh = gr.Button(i18n("Refresh"))
314 dataset_creator = gr.Checkbox(
315 label=i18n("Dataset Creator"),
316 value=False,
317 interactive=True,
318 visible=True,
319 )
320
321 with gr.Column(visible=False) as dataset_creator_settings:
322 with gr.Accordion(i18n("Dataset Creator")):
323 dataset_name = gr.Textbox(
324 label=i18n("Dataset Name"),
325 info=i18n("Name of the new dataset."),
326 placeholder=i18n("Enter dataset name"),
327 interactive=True,
328 )
329 upload_audio_dataset = gr.File(
330 label=i18n("Upload Audio Dataset"),
331 type="filepath",
332 interactive=True,
333 )
334
335 with gr.Column():
336 sampling_rate = gr.Radio(
337 label=i18n("Sampling Rate"),
338 info=i18n("The sampling rate of the audio files."),
339 choices=["32000", "40000", "48000"],
340 value="40000",
341 interactive=True,
342 )
343
344 rvc_version = gr.Radio(
345 label=i18n("RVC Version"),
346 info=i18n("The RVC version of the model."),
347 choices=["v1", "v2"],
348 value="v2",
349 interactive=True,
350 )
351
352 preprocess_output_info = gr.Textbox(
353 label=i18n("Output Information"),
354 info=i18n("The output information will be displayed here."),
355 value="",
356 max_lines=8,
357 interactive=False,
358 )
359
360 with gr.Row():
361 preprocess_button = gr.Button(i18n("Preprocess Dataset"))
362 preprocess_button.click(
363 fn=run_preprocess_script,
364 inputs=[model_name, dataset_path, sampling_rate],
365 outputs=[preprocess_output_info],
366 api_name="preprocess_dataset",
367 )
368
369 with gr.Accordion(i18n("Extract")):
370 with gr.Row():
371 hop_length = gr.Slider(
372 1,
373 512,
374 128,
375 step=1,
376 label=i18n("Hop Length"),
377 info=i18n(
378 "Denotes the duration it takes for the system to transition to a significant pitch change. Smaller hop lengths require more time for inference but tend to yield higher pitch accuracy."
379 ),
380 visible=False,
381 interactive=True,
382 )
383 with gr.Row():
384 with gr.Column():
385 f0method = gr.Radio(
386 label=i18n("Pitch extraction algorithm"),
387 info=i18n(
388 "Pitch extraction algorithm to use for the audio conversion. The default algorithm is rmvpe, which is recommended for most cases."
389 ),
390 choices=["pm", "dio", "crepe", "crepe-tiny", "harvest", "rmvpe"],
391 value="rmvpe",
392 interactive=True,
393 )
394 embedder_model = gr.Radio(
395 label=i18n("Embedder Model"),
396 info=i18n("Model used for learning speaker embedding."),
397 choices=["hubert", "contentvec", "custom"],
398 value="hubert",
399 interactive=True,
400 )
401 with gr.Column(visible=False) as embedder_custom:
402 with gr.Accordion(i18n("Custom Embedder"), open=True):
403 embedder_upload_custom = gr.File(
404 label=i18n("Upload Custom Embedder"),
405 type="filepath",
406 interactive=True,
407 )
408 embedder_custom_refresh = gr.Button(i18n("Refresh"))
409 embedder_model_custom = gr.Dropdown(
410 label=i18n("Custom Embedder"),
411 info=i18n(
412 "Select the custom embedder to use for the conversion."
413 ),
414 choices=sorted(get_embedder_custom_list()),
415 interactive=True,
416 allow_custom_value=True,
417 )
418
419 extract_output_info = gr.Textbox(
420 label=i18n("Output Information"),
421 info=i18n("The output information will be displayed here."),
422 value="",
423 max_lines=8,
424 interactive=False,
425 )
426 extract_button = gr.Button(i18n("Extract Features"))
427 extract_button.click(
428 fn=run_extract_script,
429 inputs=[
430 model_name,
431 rvc_version,
432 f0method,
433 hop_length,
434 sampling_rate,
435 embedder_model,
436 embedder_model_custom,
437 ],
438 outputs=[extract_output_info],
439 api_name="extract_features",
440 )
441
442 with gr.Accordion(i18n("Train")):
443 with gr.Row():
444 batch_size = gr.Slider(
445 1,
446 50,
447 max_vram_gpu(0),
448 step=1,
449 label=i18n("Batch Size"),
450 info=i18n(
451 "It's advisable to align it with the available VRAM of your GPU. A setting of 4 offers improved accuracy but slower processing, while 8 provides faster and standard results."
452 ),
453 interactive=True,
454 )
455 save_every_epoch = gr.Slider(
456 1,
457 100,
458 10,
459 step=1,
460 label=i18n("Save Every Epoch"),
461 info=i18n("Determine at how many epochs the model will saved at."),
462 interactive=True,
463 )
464 total_epoch = gr.Slider(
465 1,
466 10000,
467 500,
468 step=1,
469 label=i18n("Total Epoch"),
470 info=i18n(
471 "Specifies the overall quantity of epochs for the model training process."
472 ),
473 interactive=True,
474 )
475 with gr.Row():
476 pitch_guidance = gr.Checkbox(
477 label=i18n("Pitch Guidance"),
478 info=i18n(
479 "By employing pitch guidance, it becomes feasible to mirror the intonation of the original voice, including its pitch. This feature is particularly valuable for singing and other scenarios where preserving the original melody or pitch pattern is essential."
480 ),
481 value=True,
482 interactive=True,
483 )
484 pretrained = gr.Checkbox(
485 label=i18n("Pretrained"),
486 info=i18n(
487 "Utilize pretrained models when training your own. This approach reduces training duration and enhances overall quality."
488 ),
489 value=True,
490 interactive=True,
491 )
492 save_only_latest = gr.Checkbox(
493 label=i18n("Save Only Latest"),
494 info=i18n(
495 "Enabling this setting will result in the G and D files saving only their most recent versions, effectively conserving storage space."
496 ),
497 value=False,
498 interactive=True,
499 )
500 save_every_weights = gr.Checkbox(
501 label=i18n("Save Every Weights"),
502 info=i18n(
503 "This setting enables you to save the weights of the model at the conclusion of each epoch."
504 ),
505 value=True,
506 interactive=True,
507 )
508 custom_pretrained = gr.Checkbox(
509 label=i18n("Custom Pretrained"),
510 info=i18n(
511 "Utilizing custom pretrained models can lead to superior results, as selecting the most suitable pretrained models tailored to the specific use case can significantly enhance performance."
512 ),
513 value=False,
514 interactive=True,
515 )
516 multiple_gpu = gr.Checkbox(
517 label=i18n("GPU Settings"),
518 info=(
519 i18n(
520 "Sets advanced GPU settings, recommended for users with better GPU architecture."
521 )
522 ),
523 value=False,
524 interactive=True,
525 )
526 overtraining_detector = gr.Checkbox(
527 label=i18n("Overtraining Detector"),
528 info=i18n(
529 "Detect overtraining to prevent the model from learning the training data too well and losing the ability to generalize to new data."
530 ),
531 value=False,
532 interactive=True,
533 )
534 sync_graph = gr.Checkbox(
535 label=i18n("Sync Graph"),
536 info=i18n(
537 "Synchronize the graph of the tensorbaord. Only enable this setting if you are training a new model."
538 ),
539 value=False,
540 interactive=True,
541 )
542
543 with gr.Row():
544 with gr.Column(visible=False) as pretrained_custom_settings:
545 with gr.Accordion(i18n("Pretrained Custom Settings")):
546 upload_pretrained = gr.File(
547 label=i18n("Upload Pretrained Model"),
548 type="filepath",
549 interactive=True,
550 )
551 refresh_custom_pretaineds_button = gr.Button(
552 i18n("Refresh Custom Pretraineds")
553 )
554 g_pretrained_path = gr.Dropdown(
555 label=i18n("Custom Pretrained G"),
556 info=i18n(
557 "Select the custom pretrained model for the generator."
558 ),
559 choices=sorted(pretraineds_list_g),
560 interactive=True,
561 allow_custom_value=True,
562 )
563 d_pretrained_path = gr.Dropdown(
564 label=i18n("Custom Pretrained D"),
565 info=i18n(
566 "Select the custom pretrained model for the discriminator."
567 ),
568 choices=sorted(pretraineds_list_d),
569 interactive=True,
570 allow_custom_value=True,
571 )
572 with gr.Column(visible=False) as gpu_custom_settings:
573 with gr.Accordion(i18n("GPU Settings")):
574 gpu = gr.Textbox(
575 label=i18n("GPU Number"),
576 info=i18n(
577 "Specify the number of GPUs you wish to utilize for training by entering them separated by hyphens (-)."
578 ),
579 placeholder=i18n("0 to ∞ separated by -"),
580 value="0",
581 interactive=True,
582 )
583 gr.Textbox(
584 label=i18n("GPU Information"),
585 info=i18n("The GPU information will be displayed here."),
586 value=get_gpu_info(),
587 interactive=False,
588 )
589 with gr.Column(visible=False) as overtraining_settings:
590 with gr.Accordion(i18n("Overtraining Detector Settings")):
591 overtraining_threshold = gr.Slider(
592 1,
593 100,
594 50,
595 step=1,
596 label=i18n("Overtraining Threshold"),
597 info=i18n(
598 "Set the maximum number of epochs you want your model to stop training if no improvement is detected."
599 ),
600 interactive=True,
601 )
602
603 with gr.Row():
604 train_output_info = gr.Textbox(
605 label=i18n("Output Information"),
606 info=i18n("The output information will be displayed here."),
607 value="",
608 max_lines=8,
609 interactive=False,
610 )
611
612 with gr.Row():
613 train_button = gr.Button(i18n("Start Training"))
614 train_button.click(
615 fn=run_train_script,
616 inputs=[
617 model_name,
618 rvc_version,
619 save_every_epoch,
620 save_only_latest,
621 save_every_weights,
622 total_epoch,
623 sampling_rate,
624 batch_size,
625 gpu,
626 pitch_guidance,
627 overtraining_detector,
628 overtraining_threshold,
629 pretrained,
630 custom_pretrained,
631 sync_graph,
632 g_pretrained_path,
633 d_pretrained_path,
634 ],
635 outputs=[train_output_info],
636 api_name="start_training",
637 )
638
639 stop_train_button = gr.Button(
640 i18n("Stop Training & Restart Applio"), visible=False
641 )
642 stop_train_button.click(
643 fn=restart_applio,
644 inputs=[],
645 outputs=[],
646 )
647
648 index_button = gr.Button(i18n("Generate Index"))
649 index_button.click(
650 fn=run_index_script,
651 inputs=[model_name, rvc_version],
652 outputs=[train_output_info],
653 api_name="generate_index",
654 )
655
656 with gr.Accordion(i18n("Export Model"), open=False):
657 if not os.name == "nt":
658 gr.Markdown(
659 i18n(
660 "The button 'Upload' is only for google colab: Uploads the exported files to the ApplioExported folder in your Google Drive."
661 )
662 )
663 with gr.Row():
664 with gr.Column():
665 pth_file_export = gr.File(
666 label=i18n("Exported Pth file"),
667 type="filepath",
668 value=None,
669 interactive=False,
670 )
671 pth_dropdown_export = gr.Dropdown(
672 label=i18n("Pth file"),
673 info=i18n("Select the pth file to be exported"),
674 choices=get_pth_list(),
675 value=None,
676 interactive=True,
677 allow_custom_value=True,
678 )
679 with gr.Column():
680 index_file_export = gr.File(
681 label=i18n("Exported Index File"),
682 type="filepath",
683 value=None,
684 interactive=False,
685 )
686 index_dropdown_export = gr.Dropdown(
687 label=i18n("Index File"),
688 info=i18n("Select the index file to be exported"),
689 choices=get_index_list(),
690 value=None,
691 interactive=True,
692 allow_custom_value=True,
693 )
694 with gr.Row():
695 with gr.Column():
696 refresh_export = gr.Button(i18n("Refresh"))
697 if not os.name == "nt":
698 upload_exported = gr.Button(i18n("Upload"), variant="primary")
699 upload_exported.click(
700 fn=upload_to_google_drive,
701 inputs=[pth_dropdown_export, index_dropdown_export],
702 outputs=[],
703 )
704
705 def toggle_visible(checkbox):
706 return {"visible": checkbox, "__type__": "update"}
707
708 def toggle_visible_hop_length(f0method):
709 if f0method == "crepe" or f0method == "crepe-tiny":
710 return {"visible": True, "__type__": "update"}
711 return {"visible": False, "__type__": "update"}
712
713 def toggle_pretrained(pretrained, custom_pretrained):
714 if custom_pretrained == False:
715 return {"visible": pretrained, "__type__": "update"}, {
716 "visible": False,
717 "__type__": "update",
718 }
719 else:
720 return {"visible": pretrained, "__type__": "update"}, {
721 "visible": pretrained,
722 "__type__": "update",
723 }
724
725 def enable_stop_train_button():
726 return {"visible": False, "__type__": "update"}, {
727 "visible": True,
728 "__type__": "update",
729 }
730
731 def disable_stop_train_button():
732 return {"visible": True, "__type__": "update"}, {
733 "visible": False,
734 "__type__": "update",
735 }
736
737 def download_prerequisites(version):
738 for remote_folder, file_list in pretraineds_v1:
739 local_folder = folder_mapping.get(remote_folder, "")
740 missing = False
741 for file in file_list:
742 destination_path = os.path.join(local_folder, file)
743 if not os.path.exists(destination_path):
744 missing = True
745 if version == "v1" and missing == True:
746 gr.Info(
747 "Downloading prerequisites... Please wait till it finishes to start preprocessing."
748 )
749 run_prerequisites_script("True", "False", "True", "True")
750 gr.Info(
751 "Prerequisites downloaded successfully, you may now start preprocessing."
752 )
753
754 def toggle_visible_embedder_custom(embedder_model):
755 if embedder_model == "custom":
756 return {"visible": True, "__type__": "update"}
757 return {"visible": False, "__type__": "update"}
758
759 rvc_version.change(
760 fn=download_prerequisites,
761 inputs=[rvc_version],
762 outputs=[],
763 )
764
765 refresh.click(
766 fn=refresh_models_and_datasets,
767 inputs=[],
768 outputs=[model_name, dataset_path],
769 )
770
771 dataset_creator.change(
772 fn=toggle_visible,
773 inputs=[dataset_creator],
774 outputs=[dataset_creator_settings],
775 )
776
777 upload_audio_dataset.upload(
778 fn=save_drop_dataset_audio,
779 inputs=[upload_audio_dataset, dataset_name],
780 outputs=[upload_audio_dataset, dataset_path],
781 )
782
783 f0method.change(
784 fn=toggle_visible_hop_length,
785 inputs=[f0method],
786 outputs=[hop_length],
787 )
788
789 embedder_model.change(
790 fn=toggle_visible_embedder_custom,
791 inputs=[embedder_model],
792 outputs=[embedder_custom],
793 )
794 embedder_upload_custom.upload(
795 fn=save_drop_custom_embedder,
796 inputs=[embedder_upload_custom],
797 outputs=[embedder_upload_custom],
798 )
799 embedder_custom_refresh.click(
800 fn=refresh_custom_embedder_list,
801 inputs=[],
802 outputs=[embedder_model_custom],
803 )
804
805 pretrained.change(
806 fn=toggle_pretrained,
807 inputs=[pretrained, custom_pretrained],
808 outputs=[custom_pretrained, pretrained_custom_settings],
809 )
810
811 custom_pretrained.change(
812 fn=toggle_visible,
813 inputs=[custom_pretrained],
814 outputs=[pretrained_custom_settings],
815 )
816
817 refresh_custom_pretaineds_button.click(
818 fn=refresh_custom_pretraineds,
819 inputs=[],
820 outputs=[g_pretrained_path, d_pretrained_path],
821 )
822
823 upload_pretrained.upload(
824 fn=save_drop_model,
825 inputs=[upload_pretrained],
826 outputs=[upload_pretrained],
827 )
828
829 overtraining_detector.change(
830 fn=toggle_visible,
831 inputs=[overtraining_detector],
832 outputs=[overtraining_settings],
833 )
834
835 multiple_gpu.change(
836 fn=toggle_visible,
837 inputs=[multiple_gpu],
838 outputs=[gpu_custom_settings],
839 )
840
841 train_button.click(
842 fn=enable_stop_train_button,
843 inputs=[],
844 outputs=[train_button, stop_train_button],
845 )
846
847 train_output_info.change(
848 fn=disable_stop_train_button,
849 inputs=[],
850 outputs=[train_button, stop_train_button],
851 )
852
853 pth_dropdown_export.change(
854 fn=export_pth,
855 inputs=[pth_dropdown_export],
856 outputs=[pth_file_export],
857 )
858
859 index_dropdown_export.change(
860 fn=export_index,
861 inputs=[index_dropdown_export],
862 outputs=[index_file_export],
863 )
864
865 refresh_export.click(
866 fn=refresh_pth_and_index_list,
867 inputs=[],
868 outputs=[pth_dropdown_export, index_dropdown_export],
869 )
870 