Hamed744 commited on
Commit
fe7c760
·
verified ·
1 Parent(s): ad54948

Update app.py

Browse files
Files changed (1) hide show
  1. app.py +20 -10
app.py CHANGED
@@ -26,6 +26,7 @@ else:
26
  logging.warning("هشدار: کلید API گوگل (GOOGLE_API_KEY) تنظیم نشده است. قابلیت ترجمه غیرفعال خواهد بود.")
27
 
28
  # --- دیکشنری کامل‌تر صداهای انگلیسی ---
 
29
  language_dict_persian_keys = {
30
  'انگلیسی (آمریکا) - جنی (زن)': 'en-US-JennyNeural', 'انگلیسی (آمریکا) - گای (مرد)': 'en-US-GuyNeural',
31
  'انگلیسی (آمریکا) - آنا (زن، صدای کودک)': 'en-US-AnaNeural', 'انگلیسی (آمریکا) - آریا (زن)': 'en-US-AriaNeural',
@@ -46,10 +47,10 @@ language_dict_persian_keys = {
46
  'انگلیسی (استرالیا) - کن (مرد، جدید)': 'en-AU-KenNeural', 'انگلیسی (استرالیا) - کیمبرلی (زن، جدید)': 'en-AU-KimNeural',
47
  'انگلیسی (استرالیا) - تینا (زن، جدید)': 'en-AU-TinaNeural',
48
  'انگلیسی (کانادا) - کلارا (زن)': 'en-CA-ClaraNeural', 'انگلیسی (کانادا) - لیام (مرد)': 'en-CA-LiamNeural',
49
- 'انگلیسی (کانادا) - کوبی (مرد، جدید)': 'en-CA-CobiNeural', 'انگلیسی (کانادا) - ژان (مرد، جدید)': 'en-CA-JeanNeural',
50
  'انگلیسی (ایرلند) - امیلی (زن)': 'en-IE-EmilyNeural', 'انگلیسی (ایرلند) - کانر (مرد)': 'en-IE-ConnorNeural',
51
  'انگلیسی (هند) - نیرجا (زن)': 'en-IN-NeerjaNeural', 'انگلیسی (هند) - پرابهات (مرد)': 'en-IN-PrabhatNeural',
52
- 'انگلیسی (هند) - میتالی (زن، جدید)': 'en-IN-MithaliNeural',
53
  'انگلیسی (آفریقای جنوبی) - لیا (زن)': 'en-ZA-LeahNeural', 'انگلیسی (آفریقای جنوبی) - لوک (مرد)': 'en-ZA-LukeNeural',
54
  'انگلیسی (هنگ کنگ) - یان (زن)': 'en-HK-YanNeural', 'انگلیسی (هنگ کنگ) - سم (مرد)': 'en-HK-SamNeural',
55
  'انگلیسی (نیوزیلند) - هیزل (زن)': 'en-NZ-HazelNeural', 'انگلیسی (نیوزیلند) - میچل (مرد)': 'en-NZ-MitchellNeural',
@@ -75,19 +76,28 @@ async def translate_text_gemini(text, target_language="English"):
75
  return f"خطای ترجمه: {type(e).__name__}", None
76
 
77
  async def text_to_speech_edge_async(text_to_speak, tts_voice_key, rate, volume, pitch):
 
 
 
 
 
 
 
78
  try:
79
  if not text_to_speak or not text_to_speak.strip(): return "خطای TTS: متن ترجمه شده برای خواندن خالی است.", None
80
- voice_id = language_dict_persian_keys.get(tts_voice_key)
81
- if voice_id is None: return f"خطای TTS: صدای '{tts_voice_key}' یافت نشد.", None
82
  rate_str, volume_str, pitch_str = f"{int(rate):+g}%", f"{int(volume):+g}%", f"{int(pitch):+g}Hz"
83
  communicate = edge_tts.Communicate(text_to_speak, voice_id, rate=rate_str, volume=volume_str, pitch=pitch_str)
84
  with tempfile.NamedTemporaryFile(delete=False, suffix=".mp3") as tmp_file: tmp_path = tmp_file.name
85
  await communicate.save(tmp_path)
 
86
  return "TTS موفق", tmp_path
87
- except edge_tts.exceptions.NoAudioReceived: return f"خطای TTS: صدایی برای '{tts_voice_key}' دریافت نشد. (NoAudioReceived)", None
 
 
88
  except Exception as e:
89
- logging.error(f"خطای Edge-TTS: {e}\n{traceback.format_exc()}")
90
- return f"خطای TTS: {type(e).__name__}", None
91
 
92
  _event_loops_by_thread = {}
93
  def _get_or_create_event_loop():
@@ -379,7 +389,6 @@ with gr.Blocks(theme=app_theme_outer, css=custom_css, title="آموزش زبان
379
  lines=4,
380
  label="📝 متن فارسی برای ترجمه",
381
  placeholder="مثال: سلام، فردا هوا چطور است؟"
382
- # value="سلام، امروز می‌خواهیم در مورد رنگ‌ها صحبت کنیم." # <--- متن پیشفرض حذف شد
383
  )
384
 
385
  dropdown_label = "🗣️ انتخاب گوینده و لهجه انگلیسی"
@@ -410,7 +419,8 @@ with gr.Blocks(theme=app_theme_outer, css=custom_css, title="آموزش زبان
410
  type="filepath",
411
  label="🎧 فایل صوتی",
412
  format="mp3",
413
- interactive=False
 
414
  )
415
 
416
  if language_dict_persian_keys and default_english_tts_voice and default_english_tts_voice != "لیست صداها خالی است":
@@ -435,7 +445,7 @@ with gr.Blocks(theme=app_theme_outer, css=custom_css, title="آموزش زبان
435
  else:
436
  gr.Markdown("<p style='text-align:center; color:var(--fly-text-secondary); margin-top:1rem;'>نمونه‌ای برای نمایش موجود نیست (لیست صداها خالی است یا صدای پیش‌فرض معتبر نیست).</p>")
437
 
438
- gr.Markdown("<p class='app-footer-fly'>Fly Language Learning © 2025</p>") # <--- سال به ۲۰۲۵ تغییر کرد
439
 
440
  if 'submit_button' in locals() and submit_button is not None:
441
  submit_button.click(
 
26
  logging.warning("هشدار: کلید API گوگل (GOOGLE_API_KEY) تنظیم نشده است. قابلیت ترجمه غیرفعال خواهد بود.")
27
 
28
  # --- دیکشنری کامل‌تر صداهای انگلیسی ---
29
+ # !!! توجه: این لیست باید با خروجی `edge-tts --list-voices` در محیط اجرایی شما بررسی و به‌روز شود.
30
  language_dict_persian_keys = {
31
  'انگلیسی (آمریکا) - جنی (زن)': 'en-US-JennyNeural', 'انگلیسی (آمریکا) - گای (مرد)': 'en-US-GuyNeural',
32
  'انگلیسی (آمریکا) - آنا (زن، صدای کودک)': 'en-US-AnaNeural', 'انگلیسی (آمریکا) - آریا (زن)': 'en-US-AriaNeural',
 
47
  'انگلیسی (استرالیا) - کن (مرد، جدید)': 'en-AU-KenNeural', 'انگلیسی (استرالیا) - کیمبرلی (زن، جدید)': 'en-AU-KimNeural',
48
  'انگلیسی (استرالیا) - تینا (زن، جدید)': 'en-AU-TinaNeural',
49
  'انگلیسی (کانادا) - کلارا (زن)': 'en-CA-ClaraNeural', 'انگلیسی (کانادا) - لیام (مرد)': 'en-CA-LiamNeural',
50
+ 'انگلیسی (کانادا) - کوبی (مرد، جدید)': 'en-CA-CobiNeural', 'انگلیسی (کانادا) - ژان (مرد، جدید)': 'en-CA-JeanNeural', # یکی از موارد مشکل‌دار
51
  'انگلیسی (ایرلند) - امیلی (زن)': 'en-IE-EmilyNeural', 'انگلیسی (ایرلند) - کانر (مرد)': 'en-IE-ConnorNeural',
52
  'انگلیسی (هند) - نیرجا (زن)': 'en-IN-NeerjaNeural', 'انگلیسی (هند) - پرابهات (مرد)': 'en-IN-PrabhatNeural',
53
+ 'انگلیسی (هند) - میتالی (زن، جدید)': 'en-IN-MithaliNeural', # یکی از موارد مشکل‌دار
54
  'انگلیسی (آفریقای جنوبی) - لیا (زن)': 'en-ZA-LeahNeural', 'انگلیسی (آفریقای جنوبی) - لوک (مرد)': 'en-ZA-LukeNeural',
55
  'انگلیسی (هنگ کنگ) - یان (زن)': 'en-HK-YanNeural', 'انگلیسی (هنگ کنگ) - سم (مرد)': 'en-HK-SamNeural',
56
  'انگلیسی (نیوزیلند) - هیزل (زن)': 'en-NZ-HazelNeural', 'انگلیسی (نیوزیلند) - میچل (مرد)': 'en-NZ-MitchellNeural',
 
76
  return f"خطای ترجمه: {type(e).__name__}", None
77
 
78
  async def text_to_speech_edge_async(text_to_speak, tts_voice_key, rate, volume, pitch):
79
+ voice_id = language_dict_persian_keys.get(tts_voice_key)
80
+ if voice_id is None:
81
+ logging.error(f"کلید صدای '{tts_voice_key}' در دیکشنری یافت نشد.")
82
+ return f"خطای TTS: صدای '{tts_voice_key}' یافت نشد (پیکربندی داخلی).", None
83
+
84
+ logging.info(f"تلاش برای تولید صدا با: VoiceKey='{tts_voice_key}', VoiceID='{voice_id}', Text='{text_to_speak[:30]}...'")
85
+
86
  try:
87
  if not text_to_speak or not text_to_speak.strip(): return "خطای TTS: متن ترجمه شده برای خواندن خالی است.", None
88
+
 
89
  rate_str, volume_str, pitch_str = f"{int(rate):+g}%", f"{int(volume):+g}%", f"{int(pitch):+g}Hz"
90
  communicate = edge_tts.Communicate(text_to_speak, voice_id, rate=rate_str, volume=volume_str, pitch=pitch_str)
91
  with tempfile.NamedTemporaryFile(delete=False, suffix=".mp3") as tmp_file: tmp_path = tmp_file.name
92
  await communicate.save(tmp_path)
93
+ logging.info(f"صدای '{voice_id}' با موفقیت در '{tmp_path}' ذخیره شد.")
94
  return "TTS موفق", tmp_path
95
+ except edge_tts.exceptions.NoAudioReceived:
96
+ logging.error(f"خطای NoAudioReceived برای VoiceID='{voice_id}', VoiceKey='{tts_voice_key}'. متن: '{text_to_speak[:50]}...'")
97
+ return f"خطای TTS: صدایی برای '{tts_voice_key}' دریافت نشد (NoAudioReceived). ممکن است این صدا موقتا در دسترس نباشد.", None
98
  except Exception as e:
99
+ logging.error(f"خطای Edge-TTS برای VoiceID='{voice_id}', VoiceKey='{tts_voice_key}': {e}\n{traceback.format_exc()}")
100
+ return f"خطای TTS ({type(e).__name__}): مشکلی در تولید صدا برای '{tts_voice_key}' پیش آمد.", None
101
 
102
  _event_loops_by_thread = {}
103
  def _get_or_create_event_loop():
 
389
  lines=4,
390
  label="📝 متن فارسی برای ترجمه",
391
  placeholder="مثال: سلام، فردا هوا چطور است؟"
 
392
  )
393
 
394
  dropdown_label = "🗣️ انتخاب گوینده و لهجه انگلیسی"
 
419
  type="filepath",
420
  label="🎧 فایل صوتی",
421
  format="mp3",
422
+ interactive=False,
423
+ autoplay=True # <--- پخش خودکار فعال شد
424
  )
425
 
426
  if language_dict_persian_keys and default_english_tts_voice and default_english_tts_voice != "لیست صداها خالی است":
 
445
  else:
446
  gr.Markdown("<p style='text-align:center; color:var(--fly-text-secondary); margin-top:1rem;'>نمونه‌ای برای نمایش موجود نیست (لیست صداها خالی است یا صدای پیش‌فرض معتبر نیست).</p>")
447
 
448
+ gr.Markdown("<p class='app-footer-fly'>Fly Language Learning © 2025</p>")
449
 
450
  if 'submit_button' in locals() and submit_button is not None:
451
  submit_button.click(