kambris commited on
Commit
403f1e2
Β·
verified Β·
1 Parent(s): be33ba4

Update app.py

Browse files
Files changed (1) hide show
  1. app.py +401 -2
app.py CHANGED
@@ -3,6 +3,11 @@ from gtts import gTTS
3
  import tempfile
4
  from deep_translator import GoogleTranslator
5
 
 
 
 
 
 
6
  transliteration_map = {
7
  # Two-character combinations (check first)
8
  'ch': 'Χ—', 'ts': 'Χ¦', 'tz': 'Χ¦', 'sh': 'Χ©', 'kh': 'Χ›',
@@ -25,7 +30,401 @@ def generate_letter_audio(hebrew_letter):
25
  return None
26
 
27
  try:
28
- tts = gTTS(text=hebrew_letter, lang='iw', slow=True)
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
29
  with tempfile.NamedTemporaryFile(delete=False, suffix=".mp3") as tmp_file:
30
  temp_path = tmp_file.name
31
  tts.save(temp_path)
@@ -130,7 +529,7 @@ def hebrew_tts(hebrew_text):
130
  return None
131
 
132
  try:
133
- tts = gTTS(text=hebrew_text, lang='iw', slow=False)
134
  with tempfile.NamedTemporaryFile(delete=False, suffix=".mp3") as tmp_file:
135
  temp_path = tmp_file.name
136
  tts.save(temp_path)
 
3
  import tempfile
4
  from deep_translator import GoogleTranslator
5
 
6
+ transliteration_map = {import gradio as gr
7
+ from gtts import gTTS
8
+ import tempfile
9
+ from deep_translator import GoogleTranslator
10
+
11
  transliteration_map = {
12
  # Two-character combinations (check first)
13
  'ch': 'Χ—', 'ts': 'Χ¦', 'tz': 'Χ¦', 'sh': 'Χ©', 'kh': 'Χ›',
 
30
  return None
31
 
32
  try:
33
+ tts = gTTS(text=hebrew_letter, lang='he', slow=True)
34
+ with tempfile.NamedTemporaryFile(delete=False, suffix=".mp3") as tmp_file:
35
+ temp_path = tmp_file.name
36
+ tts.save(temp_path)
37
+ return temp_path
38
+ except Exception as e:
39
+ print(f"Letter TTS Error: {e}")
40
+ return None
41
+
42
+ def transliterate(text):
43
+ """Convert English text to Hebrew transliteration"""
44
+ if not text:
45
+ return ""
46
+
47
+ text = text.lower()
48
+ result = []
49
+ i = 0
50
+
51
+ while i < len(text):
52
+ # Check for two-letter combinations first
53
+ if i < len(text) - 1:
54
+ two_char = text[i:i+2]
55
+ if two_char in transliteration_map:
56
+ result.append(transliteration_map[two_char])
57
+ i += 2
58
+ continue
59
+
60
+ # Check for single letter
61
+ char = text[i]
62
+ if char in transliteration_map:
63
+ result.append(transliteration_map[char])
64
+ elif char == ' ':
65
+ result.append(' ')
66
+ else:
67
+ result.append(char)
68
+
69
+ i += 1
70
+
71
+ return ''.join(result)
72
+
73
+ def google_translate_hebrew(english_text):
74
+ """Translate English text to Hebrew using Google Translate"""
75
+ if not english_text or not english_text.strip():
76
+ return "No text provided for translation."
77
+
78
+ try:
79
+ translation_text = GoogleTranslator(source='en', target='iw').translate(english_text)
80
+ return translation_text
81
+
82
+ except Exception as e:
83
+ return f"❌ Google Translate error: {str(e)}\n\nPlease check your internet connection and try again."
84
+
85
+ def translate_multiple_words(hebrew_text):
86
+ """Translate multiple Hebrew words - both individually and as a whole phrase"""
87
+ if not hebrew_text or not hebrew_text.strip():
88
+ return "No text provided for translation."
89
+
90
+ try:
91
+ # First translate the whole phrase
92
+ full_translation = GoogleTranslator(source='iw', target='en').translate(hebrew_text)
93
+
94
+ # Then translate individual words if there are multiple words
95
+ words = hebrew_text.strip().split()
96
+
97
+ if len(words) > 1:
98
+ individual_translations = []
99
+ for i, word in enumerate(words[:5], 1): # Limit to first 5 words
100
+ if len(word.strip()) > 1: # Skip single characters
101
+ try:
102
+ word_translation = GoogleTranslator(source='iw', target='en').translate(word)
103
+ individual_translations.append(f"**{i}. {word}** β†’ {word_translation}")
104
+ except:
105
+ individual_translations.append(f"**{i}. {word}** β†’ (translation failed)")
106
+
107
+ if individual_translations:
108
+ result = full_translation + "\n\n" + "─"*50 + "\n\n"
109
+ result += "πŸ“ **Individual Word Translations:**\n\n"
110
+ result += "\n".join(individual_translations)
111
+ return result
112
+
113
+ return full_translation
114
+
115
+ except Exception as e:
116
+ return f"❌ Translation error: {str(e)}"
117
+
118
+ def reverse_translate_english(hebrew_text):
119
+ """Translate Hebrew text to English using Google Translate"""
120
+ if not hebrew_text or not hebrew_text.strip():
121
+ return "No text provided for translation."
122
+
123
+ try:
124
+ # Translate to English
125
+ translation_text = GoogleTranslator(source='iw', target='en').translate(hebrew_text)
126
+
127
+ return translation_text
128
+
129
+ except Exception as e:
130
+ return f"❌ Translation error: {str(e)}"
131
+
132
+ def hebrew_tts(hebrew_text):
133
+ """Generate TTS audio for Hebrew text."""
134
+ if not hebrew_text or not hebrew_text.strip():
135
+ return None
136
+
137
+ try:
138
+ tts = gTTS(text=hebrew_text, lang='he', slow=False)
139
+ with tempfile.NamedTemporaryFile(delete=False, suffix=".mp3") as tmp_file:
140
+ temp_path = tmp_file.name
141
+ tts.save(temp_path)
142
+ return temp_path
143
+ except Exception as e:
144
+ print(f"Hebrew TTS Error: {e}")
145
+ return None
146
+
147
+ def transliterate_and_speak(english_text):
148
+ """Combined function to transliterate and generate audio."""
149
+ hebrew_text = transliterate(english_text)
150
+ hebrew_audio = hebrew_tts(hebrew_text)
151
+ return hebrew_text, hebrew_audio
152
+
153
+ def full_process_with_translation(english_text, mode):
154
+ """Complete processing: translate/transliterate, generate audio, and get word translations"""
155
+ if mode == "Transliteration":
156
+ hebrew_text = transliterate(english_text)
157
+ else:
158
+ hebrew_text = google_translate_hebrew(english_text)
159
+
160
+ hebrew_audio = hebrew_tts(hebrew_text)
161
+ translation_result = translate_multiple_words(hebrew_text)
162
+ return hebrew_text, hebrew_audio, translation_result
163
+
164
+ # Create Gradio interface with custom CSS for copy buttons
165
+ css = """
166
+ .copy-btn {
167
+ font-size: 12px !important;
168
+ padding: 4px 8px !important;
169
+ min-width: 60px !important;
170
+ }
171
+ """
172
+
173
+ with gr.Blocks(title="English to Hebrew Converter", css=css) as demo:
174
+ gr.Markdown("## πŸ“ English-to-Hebrew Converter")
175
+ gr.Markdown("Enter English text to convert to Hebrew script, generate audio, and get translations using Google Translate.")
176
+
177
+ # English to Hebrew Letter Mapping Guide
178
+ with gr.Accordion("πŸ”€ English ↔ Hebrew Letter Mapping Guide", open=False):
179
+ gr.Markdown("""
180
+ ### How English Letters Map to Hebrew
181
+ This shows the transliteration mapping used in **Transliteration** mode:
182
+ """)
183
+
184
+ with gr.Row():
185
+ with gr.Column():
186
+ gr.Markdown("""
187
+ #### Consonants:
188
+ - **a** β†’ א (alef)
189
+ - **b** β†’ Χ‘ (bet)
190
+ - **g** β†’ Χ’ (gimel)
191
+ - **d** β†’ Χ“ (dalet)
192
+ - **h** β†’ Χ” (he)
193
+ - **v, w** β†’ Χ• (vav)
194
+ - **z** β†’ Χ– (zayin)
195
+ - **t** β†’ ט (tet)
196
+ - **y** β†’ Χ™ (yod)
197
+ - **k** β†’ Χ› (kaf)
198
+ - **l** β†’ ל (lamed)
199
+ - **m** β†’ מ (mem)
200
+ """)
201
+
202
+ with gr.Column():
203
+ gr.Markdown("""
204
+ #### More Consonants:
205
+ - **n** β†’ Χ  (nun)
206
+ - **s** β†’ Χ‘ (samekh)
207
+ - **p, f** β†’ Χ€ (pe/fe)
208
+ - **q** β†’ Χ§ (qof)
209
+ - **r** β†’ Χ¨ (resh)
210
+
211
+ #### Special Combinations:
212
+ - **ch** β†’ Χ— (chet)
213
+ - **kh** β†’ Χ› (kaf)
214
+ - **sh** β†’ Χ© (shin)
215
+ - **ts, tz** β†’ Χ¦ (tsadi)
216
+ """)
217
+
218
+ with gr.Column():
219
+ gr.Markdown("""
220
+ #### Vowel Marks:
221
+ - **e** β†’ ΦΆ (segol)
222
+ - **i** β†’ Φ΄ (hiriq)
223
+ - **o** β†’ ΦΉ (holam)
224
+ - **u** β†’ Φ» (kubutz)
225
+
226
+ #### Examples:
227
+ - **shalom** β†’ שאלֹמ
228
+ - **hello** β†’ Χ”ΦΆΧœΧœΦΉ
229
+ - **thanks** β†’ Χ˜Χ”ΧΧ Χ›Χ‘
230
+ """)
231
+
232
+ # Full-width transliteration guide with audio buttons
233
+ with gr.Accordion("πŸ“– Interactive Hebrew Alphabet Guide with Audio", open=False):
234
+ gr.Markdown("### Click the speaker buttons to hear each letter's pronunciation:")
235
+
236
+ # Audio component for letter playback
237
+ letter_audio = gr.Audio(label="Letter Pronunciation", autoplay=True)
238
+
239
+ # Consonants (Row 1)
240
+ gr.Markdown("#### Consonants:")
241
+ with gr.Row():
242
+ gr.Button("πŸ”Š א alef (a)", size="sm").click(fn=generate_letter_audio, inputs=gr.State("א"), outputs=letter_audio)
243
+ gr.Button("πŸ”Š Χ‘ bet (b)", size="sm").click(fn=generate_letter_audio, inputs=gr.State("Χ‘"), outputs=letter_audio)
244
+ gr.Button("πŸ”Š Χ’ gimel (g)", size="sm").click(fn=generate_letter_audio, inputs=gr.State("Χ’"), outputs=letter_audio)
245
+ gr.Button("πŸ”Š Χ“ dalet (d)", size="sm").click(fn=generate_letter_audio, inputs=gr.State("Χ“"), outputs=letter_audio)
246
+ gr.Button("πŸ”Š Χ” he (h)", size="sm").click(fn=generate_letter_audio, inputs=gr.State("Χ”"), outputs=letter_audio)
247
+
248
+ # Consonants (Row 2)
249
+ with gr.Row():
250
+ gr.Button("πŸ”Š Χ• vav (v/w)", size="sm").click(fn=generate_letter_audio, inputs=gr.State("Χ•"), outputs=letter_audio)
251
+ gr.Button("πŸ”Š Χ– zayin (z)", size="sm").click(fn=generate_letter_audio, inputs=gr.State("Χ–"), outputs=letter_audio)
252
+ gr.Button("πŸ”Š Χ— chet (ch)", size="sm").click(fn=generate_letter_audio, inputs=gr.State("Χ—"), outputs=letter_audio)
253
+ gr.Button("πŸ”Š ט tet (t)", size="sm").click(fn=generate_letter_audio, inputs=gr.State("ט"), outputs=letter_audio)
254
+ gr.Button("πŸ”Š Χ™ yod (y)", size="sm").click(fn=generate_letter_audio, inputs=gr.State("Χ™"), outputs=letter_audio)
255
+
256
+ # Consonants (Row 3)
257
+ with gr.Row():
258
+ gr.Button("πŸ”Š Χ› kaf (k/kh)", size="sm").click(fn=generate_letter_audio, inputs=gr.State("Χ›"), outputs=letter_audio)
259
+ gr.Button("πŸ”Š ל lamed (l)", size="sm").click(fn=generate_letter_audio, inputs=gr.State("ל"), outputs=letter_audio)
260
+ gr.Button("πŸ”Š מ mem (m)", size="sm").click(fn=generate_letter_audio, inputs=gr.State("מ"), outputs=letter_audio)
261
+ gr.Button("πŸ”Š Χ  nun (n)", size="sm").click(fn=generate_letter_audio, inputs=gr.State("Χ "), outputs=letter_audio)
262
+ gr.Button("πŸ”Š Χ‘ samekh (s)", size="sm").click(fn=generate_letter_audio, inputs=gr.State("Χ‘"), outputs=letter_audio)
263
+
264
+ # Consonants (Row 4)
265
+ with gr.Row():
266
+ gr.Button("πŸ”Š Χ’ ayin", size="sm").click(fn=generate_letter_audio, inputs=gr.State("Χ’"), outputs=letter_audio)
267
+ gr.Button("πŸ”Š Χ€ pe (p/f)", size="sm").click(fn=generate_letter_audio, inputs=gr.State("Χ€"), outputs=letter_audio)
268
+ gr.Button("πŸ”Š Χ¦ tsadi (ts/tz)", size="sm").click(fn=generate_letter_audio, inputs=gr.State("Χ¦"), outputs=letter_audio)
269
+ gr.Button("πŸ”Š Χ§ qof (q)", size="sm").click(fn=generate_letter_audio, inputs=gr.State("Χ§"), outputs=letter_audio)
270
+ gr.Button("πŸ”Š Χ¨ resh (r)", size="sm").click(fn=generate_letter_audio, inputs=gr.State("Χ¨"), outputs=letter_audio)
271
+
272
+ # Consonants (Row 5)
273
+ with gr.Row():
274
+ gr.Button("πŸ”Š Χ© shin (sh)", size="sm").click(fn=generate_letter_audio, inputs=gr.State("Χ©"), outputs=letter_audio)
275
+ gr.Button("πŸ”Š Χͺ tav (t)", size="sm").click(fn=generate_letter_audio, inputs=gr.State("Χͺ"), outputs=letter_audio)
276
+
277
+ # Mode selection
278
+ mode = gr.Radio(
279
+ choices=["Translation", "Transliteration"],
280
+ value="Transliteration",
281
+ label="Conversion Mode"
282
+ )
283
+
284
+ # Main interface with copy buttons
285
+ with gr.Row():
286
+ with gr.Column():
287
+ with gr.Row():
288
+ english_input = gr.Textbox(
289
+ label="Enter English Text",
290
+ lines=3,
291
+ placeholder="Example: Hello, how are you?",
292
+ scale=5
293
+ )
294
+ copy_english_btn = gr.Button("πŸ“‹ Copy", size="sm", scale=1, elem_classes="copy-btn")
295
+
296
+ with gr.Column():
297
+ with gr.Row():
298
+ hebrew_output = gr.Textbox(
299
+ label="Hebrew Script",
300
+ lines=3,
301
+ rtl=True,
302
+ scale=5
303
+ )
304
+ copy_hebrew_btn = gr.Button("πŸ“‹ Copy", size="sm", scale=1, elem_classes="copy-btn")
305
+
306
+ # Translation output with copy button
307
+ with gr.Row():
308
+ translation_output = gr.Textbox(
309
+ label="Word-by-Word Translation Results",
310
+ lines=3,
311
+ placeholder="Translations will appear here...",
312
+ scale=5
313
+ )
314
+ copy_translation_btn = gr.Button("πŸ“‹ Copy", size="sm", scale=1, elem_classes="copy-btn")
315
+
316
+ # Button controls
317
+ with gr.Row():
318
+ convert_btn = gr.Button("πŸ”„ Convert", variant="primary")
319
+ tts_btn = gr.Button("πŸ”Š Generate Hebrew Sound", variant="secondary")
320
+ translate_btn = gr.Button("🌐 Google Translate", variant="secondary")
321
+
322
+ with gr.Row():
323
+ combined_btn = gr.Button("πŸ”„πŸ”Š Convert & Speak", variant="secondary")
324
+ complete_btn = gr.Button("πŸ”„πŸŒπŸ”Š Complete Process (Audio + Translation)", variant="primary")
325
+
326
+ # Audio output
327
+ with gr.Row():
328
+ hebrew_audio = gr.Audio(label="Hebrew Audio", type="filepath")
329
+
330
+ # Manual translation section
331
+ with gr.Accordion("πŸ” Manual Hebrew to English Translation", open=False):
332
+ with gr.Row():
333
+ with gr.Column():
334
+ with gr.Row():
335
+ manual_hebrew_input = gr.Textbox(
336
+ label="Enter Hebrew text to translate",
337
+ placeholder="Χ”Χ›Χ Χ‘ טקבט Χ‘Χ’Χ‘Χ¨Χ™Χͺ",
338
+ rtl=True,
339
+ lines=3,
340
+ scale=5
341
+ )
342
+ copy_manual_hebrew_btn = gr.Button("πŸ“‹ Copy", size="sm", scale=1, elem_classes="copy-btn")
343
+ manual_translate_btn = gr.Button("🌐 Translate to English", variant="secondary")
344
+
345
+ with gr.Column():
346
+ with gr.Row():
347
+ manual_translation_output = gr.Textbox(
348
+ label="English Translation",
349
+ lines=3,
350
+ scale=5
351
+ )
352
+ copy_manual_translation_btn = gr.Button("πŸ“‹ Copy", size="sm", scale=1, elem_classes="copy-btn")
353
+
354
+ # Event handlers
355
+ def process_convert(text, mode):
356
+ if mode == "Transliteration":
357
+ return transliterate(text)
358
+ else:
359
+ return google_translate_hebrew(text)
360
+
361
+ # Copy button functions
362
+ copy_english_btn.click(fn=lambda x: x, inputs=english_input, outputs=english_input, js="(x) => {navigator.clipboard.writeText(x); return x;}")
363
+ copy_hebrew_btn.click(fn=lambda x: x, inputs=hebrew_output, outputs=hebrew_output, js="(x) => {navigator.clipboard.writeText(x); return x;}")
364
+ copy_translation_btn.click(fn=lambda x: x, inputs=translation_output, outputs=translation_output, js="(x) => {navigator.clipboard.writeText(x); return x;}")
365
+ copy_manual_hebrew_btn.click(fn=lambda x: x, inputs=manual_hebrew_input, outputs=manual_hebrew_input, js="(x) => {navigator.clipboard.writeText(x); return x;}")
366
+ copy_manual_translation_btn.click(fn=lambda x: x, inputs=manual_translation_output, outputs=manual_translation_output, js="(x) => {navigator.clipboard.writeText(x); return x;}")
367
+
368
+ convert_btn.click(
369
+ fn=process_convert,
370
+ inputs=[english_input, mode],
371
+ outputs=hebrew_output
372
+ )
373
+
374
+ tts_btn.click(
375
+ fn=hebrew_tts,
376
+ inputs=hebrew_output,
377
+ outputs=hebrew_audio
378
+ )
379
+
380
+ translate_btn.click(
381
+ fn=translate_multiple_words,
382
+ inputs=hebrew_output,
383
+ outputs=translation_output
384
+ )
385
+
386
+ combined_btn.click(
387
+ fn=lambda text, mode: transliterate_and_speak(text) if mode == "Transliteration" else (google_translate_hebrew(text), hebrew_tts(google_translate_hebrew(text))),
388
+ inputs=[english_input, mode],
389
+ outputs=[hebrew_output, hebrew_audio]
390
+ )
391
+
392
+ complete_btn.click(
393
+ fn=full_process_with_translation,
394
+ inputs=[english_input, mode],
395
+ outputs=[hebrew_output, hebrew_audio, translation_output]
396
+ )
397
+
398
+ manual_translate_btn.click(
399
+ fn=reverse_translate_english,
400
+ inputs=manual_hebrew_input,
401
+ outputs=manual_translation_output
402
+ )
403
+
404
+ if __name__ == "__main__":
405
+ demo.launch()
406
+ # Two-character combinations (check first)
407
+ 'ch': 'Χ—', 'ts': 'Χ¦', 'tz': 'Χ¦', 'sh': 'Χ©', 'kh': 'Χ›',
408
+
409
+ # Single characters
410
+ 'a': 'א', 'b': 'Χ‘', 'g': 'Χ’', 'd': 'Χ“', 'h': 'Χ”', 'v': 'Χ•', 'w': 'Χ•',
411
+ 'z': 'Χ–', 't': 'ט', 'y': 'Χ™', 'k': 'Χ›', 'l': 'ל', 'm': 'מ',
412
+ 'n': 'Χ ', 's': 'Χ‘', 'p': 'Χ€', 'f': 'Χ€', 'q': 'Χ§', 'r': 'Χ¨',
413
+
414
+ # Vowels
415
+ 'e': 'ΦΆ', 'i': 'Φ΄', 'o': 'ΦΉ', 'u': 'Φ»',
416
+
417
+ # Space and punctuation
418
+ ' ': ' ', '.': '.', ',': ',', '?': '?', '!': '!'
419
+ }
420
+
421
+ def generate_letter_audio(hebrew_letter):
422
+ """Generate TTS audio for a single Hebrew letter or character."""
423
+ if not hebrew_letter or not hebrew_letter.strip():
424
+ return None
425
+
426
+ try:
427
+ tts = gTTS(text=hebrew_letter, lang='he', slow=True)
428
  with tempfile.NamedTemporaryFile(delete=False, suffix=".mp3") as tmp_file:
429
  temp_path = tmp_file.name
430
  tts.save(temp_path)
 
529
  return None
530
 
531
  try:
532
+ tts = gTTS(text=hebrew_text, lang='he', slow=False)
533
  with tempfile.NamedTemporaryFile(delete=False, suffix=".mp3") as tmp_file:
534
  temp_path = tmp_file.name
535
  tts.save(temp_path)