Text-to-Speech
VoxCPM
Laz
Turkish
tts
speech-synthesis
audio
laz
lazca
lazuri
lora
low-resource
endangered-languages
turkey
mozilla-common-voice
Instructions to use Anadilorg/MozilLaz with libraries, inference providers, notebooks, and local apps. Follow these links to get started.
- Libraries
- VoxCPM
How to use Anadilorg/MozilLaz with VoxCPM:
import soundfile as sf from voxcpm import VoxCPM model = VoxCPM.from_pretrained("Anadilorg/MozilLaz") wav = model.generate( text="VoxCPM is an innovative end-to-end TTS model from ModelBest, designed to generate highly expressive speech.", prompt_wav_path=None, # optional: path to a prompt speech for voice cloning prompt_text=None, # optional: reference text cfg_value=2.0, # LM guidance on LocDiT, higher for better adherence to the prompt, but maybe worse inference_timesteps=10, # LocDiT inference timesteps, higher for better result, lower for fast speed normalize=True, # enable external TN tool denoise=True, # enable external Denoise tool retry_badcase=True, # enable retrying mode for some bad cases (unstoppable) retry_badcase_max_times=3, # maximum retrying times retry_badcase_ratio_threshold=6.0, # maximum length restriction for bad case detection (simple but effective), it could be adjusted for slow pace speech ) sf.write("output.wav", wav, 16000) print("saved: output.wav") - Notebooks
- Google Colab
- Kaggle
| #!/usr/bin/env python3 | |
| """ | |
| MozilLaz — Lazca Text-to-Speech | |
| Standalone inference script. | |
| Kullanım: | |
| python inference.py | |
| python inference.py --text "[speaker:spk_tmp_001 language:lzz] Ngolaşa uluri?" | |
| python inference.py --text "..." --output ses.wav --device cuda | |
| Model yükleme: | |
| 1. openbmb/VoxCPM2 base modeli HuggingFace'den otomatik indirilir (~4.6 GB) | |
| 2. Bu dizindeki lora_config.json okunarak LoRA katmanları kurulur | |
| 3. lora_weights.safetensors adapter ağırlıkları yüklenir | |
| 4. 48 kHz Lazca ses üretilir | |
| Not: LoRA yüklemesi voxcpm paketinin kendi (native) LoRA desteğiyle yapılır; | |
| peft gerekmez. Doğru giriş noktası `voxcpm.VoxCPM` sınıfıdır. | |
| """ | |
| import argparse | |
| import json | |
| import sys | |
| import warnings | |
| from pathlib import Path | |
| import numpy as np | |
| import soundfile as sf | |
| import torch | |
| warnings.filterwarnings("ignore", category=UserWarning) | |
| warnings.filterwarnings("ignore", category=FutureWarning) | |
| DEFAULT_BASE_MODEL = "openbmb/VoxCPM2" | |
| DEFAULT_TEXT = "[speaker:spk_tmp_001 language:lzz] Ngolaşa uluri?" | |
| def load_json(path: Path) -> dict: | |
| with open(path, encoding="utf-8") as f: | |
| return json.load(f) | |
| def resolve_device(requested: str) -> str: | |
| """auto → cuda > mps > cpu""" | |
| if requested != "auto": | |
| return requested | |
| if torch.cuda.is_available(): | |
| return "cuda" | |
| if torch.backends.mps.is_available(): | |
| return "mps" | |
| return "cpu" | |
| def load_model(base_model_name: str, lora_config_path: Path, lora_weights_path: Path, device: str): | |
| """ | |
| VoxCPM2 base model + MozilLaz LoRA adapter yükle. | |
| voxcpm >= 2.0 API'si: LoRA config ve ağırlık yolu doğrudan | |
| `VoxCPM.from_pretrained`e verilir; model kurulurken LoRA katmanları | |
| eklenir ve safetensors ağırlıkları yüklenir. | |
| """ | |
| try: | |
| from voxcpm import VoxCPM | |
| from voxcpm.model.voxcpm import LoRAConfig | |
| except ImportError: | |
| print("❌ voxcpm paketi bulunamadı!") | |
| print(" pip install voxcpm komutuyla yükleyin (>= 2.0).") | |
| sys.exit(1) | |
| lc = load_json(lora_config_path).get("lora_config", {}) | |
| lora_cfg = LoRAConfig(**{k: v for k, v in lc.items() if k in LoRAConfig.model_fields}) | |
| print(f"📦 Base model yükleniyor: {base_model_name}") | |
| print(" (İlk seferde HuggingFace'den ~4.6 GB indirilir)") | |
| model = VoxCPM.from_pretrained( | |
| base_model_name, | |
| load_denoiser=False, | |
| lora_config=lora_cfg, | |
| lora_weights_path=str(lora_weights_path), | |
| device=device, | |
| ) | |
| # Ağırlıkların gerçekten eşleştiğini doğrula | |
| loaded, skipped = model.load_lora(str(lora_weights_path)) | |
| print(f"🔧 LoRA adapter: {len(loaded)} anahtar yüklendi, {len(skipped)} atlandı") | |
| if skipped: | |
| print(f"⚠️ Atlanan anahtarlar (ilk 5): {skipped[:5]}") | |
| return model | |
| def generate_speech(model, text: str, output_path: str, | |
| inference_timesteps: int = 10, cfg_value: float = 2.0): | |
| """Metinden ses üret ve dosyaya kaydet.""" | |
| print(f"\n🎙️ Metin: {text}") | |
| print(" Ses üretiliyor...") | |
| audio = model.generate( | |
| text=text, | |
| inference_timesteps=inference_timesteps, | |
| cfg_value=cfg_value, | |
| ) | |
| audio = np.asarray(audio).squeeze() | |
| sample_rate = getattr(getattr(model, "tts_model", None), "sample_rate", 48000) | |
| sf.write(output_path, audio, sample_rate) | |
| print(f"\n✅ Ses üretildi! → {output_path}") | |
| print(f" Uzunluk: {len(audio) / sample_rate:.2f} saniye") | |
| print(f" Sample rate: {sample_rate} Hz") | |
| def main(): | |
| parser = argparse.ArgumentParser( | |
| description="MozilLaz — Lazca Text-to-Speech", | |
| formatter_class=argparse.RawDescriptionHelpFormatter, | |
| epilog=f""" | |
| Örnekler: | |
| # Varsayılan Lazca metin ile: | |
| python inference.py | |
| # Özel metin: | |
| python inference.py --text "[speaker:spk_tmp_001 language:lzz] Xelaǩaoba, manebrape!" | |
| # Cihaz seçimi (varsayılan auto: cuda > mps > cpu): | |
| python inference.py --device cuda | |
| # Farklı adımlarla (daha kaliteli ama yavaş): | |
| python inference.py --timesteps 20 | |
| Lazca metin formatı: | |
| [speaker:spk_tmp_001 language:lzz] <metin burada> | |
| Speaker: spk_tmp_001 (Mozilla Lazca veri setinden) | |
| Donanım notu: | |
| float32 inference ~9 GB bellek ister. CUDA GPU'da bfloat16 ile daha az. | |
| 16 GB birleşik bellekli Apple Silicon'da çalışır ama swap nedeniyle | |
| ÇOK yavaştır; pratik kullanım için CUDA GPU veya >=24 GB önerilir. | |
| """ | |
| ) | |
| parser.add_argument("--text", type=str, default=DEFAULT_TEXT, | |
| help="Söylemesini istediğiniz Lazca metin") | |
| parser.add_argument("--output", "-o", type=str, default="mozilaz_output.wav", | |
| help="Çıktı WAV dosya yolu (varsayılan: mozilaz_output.wav)") | |
| parser.add_argument("--device", type=str, default="auto", | |
| choices=["auto", "cuda", "mps", "cpu"], | |
| help="Hesaplama cihazı (varsayılan: auto)") | |
| parser.add_argument("--timesteps", type=int, default=10, | |
| help="Inference adım sayısı (10=normal, 20=kaliteli, 5=hızlı)") | |
| parser.add_argument("--cfg-value", type=float, default=2.0, | |
| help="Classifier-free guidance değeri (varsayılan: 2.0)") | |
| parser.add_argument("--base-model", type=str, default=DEFAULT_BASE_MODEL, | |
| help=f"Base VoxCPM2 model adı (varsayılan: {DEFAULT_BASE_MODEL})") | |
| parser.add_argument("--lora-path", type=str, default=None, | |
| help="LoRA weights yolu (varsayılan: bu dizindeki lora_weights.safetensors)") | |
| args = parser.parse_args() | |
| script_dir = Path(__file__).parent | |
| lora_weights = Path(args.lora_path) if args.lora_path else script_dir / "lora_weights.safetensors" | |
| lora_config = script_dir / "lora_config.json" | |
| for p, ad in [(lora_weights, "LoRA weights"), (lora_config, "lora_config.json")]: | |
| if not p.exists(): | |
| print(f"❌ {ad} dosyası bulunamadı: {p}") | |
| sys.exit(1) | |
| config_path = script_dir / "config.json" | |
| if config_path.exists(): | |
| config = load_json(config_path) | |
| print("=" * 60) | |
| print(" MozilLaz — Lazca Text-to-Speech Modeli") | |
| print(" " + "=" * 43) | |
| print(f" Dil: {config.get('language_name', 'Lazuri (Lazca)')}") | |
| print(f" Base model: {config.get('base_model', args.base_model)}") | |
| print(f" Konuşucu: {', '.join(config.get('speakers', ['spk_tmp_001']))}") | |
| print(f" LoRA: r={config.get('lora_config', {}).get('r', 32)}, " | |
| f"α={config.get('lora_config', {}).get('alpha', 32)}") | |
| print(f" Training steps: {config.get('training', {}).get('steps', 2000)}") | |
| print("=" * 60) | |
| device = resolve_device(args.device) | |
| print(f"\n🚀 {device.upper()} üzerinde çalışıyor...") | |
| model = load_model(args.base_model, lora_config, lora_weights, device) | |
| generate_speech( | |
| model, | |
| text=args.text, | |
| output_path=args.output, | |
| inference_timesteps=args.timesteps, | |
| cfg_value=args.cfg_value, | |
| ) | |
| if __name__ == "__main__": | |
| main() | |