| import gradio as gr |
| import requests |
| import subprocess |
| import shutil |
| import uuid |
| import json |
| import os |
|
|
| API_BASE = "https://zpdic.ziphil.com/api/v0" |
|
|
| def get_word_json(api_key, dict_id, word_number): |
| try: |
| url = f"{API_BASE}/dictionary/{dict_id}/word/{int(word_number)}" |
| resp = requests.get(url, headers={"X-Api-Key": api_key}) |
| return resp.json() |
| except Exception as e: |
| return {"error": str(e)} |
|
|
| def get_example_json(api_key, dict_id, example_number): |
| try: |
| url = f"{API_BASE}/dictionary/{dict_id}/example/{int(example_number)}" |
| resp = requests.get(url, headers={"X-Api-Key": api_key}) |
| return resp.json() |
| except Exception as e: |
| return {"error": str(e)} |
|
|
| def speak_ipa_to_wav(ipa_text, pitch, speed): |
| if not ipa_text.strip(): |
| return "❌ IPAが入力されていません。", None |
|
|
| out_path = f"/tmp/{uuid.uuid4().hex}.wav" |
|
|
| try: |
| subprocess.run([ |
| "espeak-ng", |
| "-v", "en", |
| "-p", str(pitch), |
| "-s", str(speed), |
| "-w", out_path, |
| f"[[{ipa_text}]]" |
| ], check=True) |
| return f"✅ 発音完了: {ipa_text}", out_path |
| except subprocess.CalledProcessError as e: |
| return f"❌ 発音エラー: {e}", None |
|
|
| with gr.Blocks() as demo: |
| gr.Markdown("## 🎙️ IPA読み上げ + ZpDIC API表示ツール(Docker対応)") |
|
|
| with gr.Row(): |
| api_key = gr.Textbox(label="🔑 APIキー", type="password") |
| dict_id = gr.Textbox(label="📘 辞書ID") |
|
|
| with gr.Tab("📋 単語JSONを表示"): |
| word_num = gr.Number(label="🔢 単語番号", precision=0) |
| fetch_word_btn = gr.Button("📥 単語JSONを取得") |
| word_json = gr.JSON(label="単語データ") |
|
|
| with gr.Tab("📋 例文JSONを表示"): |
| example_num = gr.Number(label="🔢 例文番号", precision=0) |
| fetch_example_btn = gr.Button("📥 例文JSONを取得") |
| example_json = gr.JSON(label="例文データ") |
|
|
| with gr.Tab("🎤 IPA直接読み上げ"): |
| ipa_input = gr.Textbox(label="🎧 IPAを入力 (例: hɛˈloʊ wɜːrld)", lines=2) |
| with gr.Row(): |
| pitch = gr.Slider(0, 99, value=50, label="🎵 ピッチ") |
| speed = gr.Slider(80, 300, value=150, label="🏃 速度") |
| speak_btn = gr.Button("▶ 音声ファイル生成") |
| result = gr.Textbox(label="📣 結果") |
| audio = gr.Audio(label="🔊 音声", type="filepath") |
|
|
| fetch_word_btn.click( |
| get_word_json, |
| inputs=[api_key, dict_id, word_num], |
| outputs=word_json |
| ) |
|
|
| fetch_example_btn.click( |
| get_example_json, |
| inputs=[api_key, dict_id, example_num], |
| outputs=example_json |
| ) |
|
|
| speak_btn.click( |
| speak_ipa_to_wav, |
| inputs=[ipa_input, pitch, speed], |
| outputs=[result, audio] |
| ) |
|
|
| demo.launch() |