funtts-plus


Namefuntts-plus JSON
Version 0.1.10 PyPI version JSON
download
home_pageNone
Summary统一的文本转语音(TTS)工具库,支持多种开源TTS引擎和字幕格式
upload_time2025-09-19 00:36:12
maintainerNone
docs_urlNone
authorNone
requires_python>=3.8
licenseMIT
keywords tts text-to-speech audio subtitle speech-synthesis
VCS
bugtrack_url
requirements No requirements were recorded.
Travis-CI No Travis.
coveralls test coverage No coveralls.
            # FunTTS - 统一TTS接口库

[![PyPI version](https://badge.fury.io/py/funtts-plus.svg)](https://badge.fury.io/py/funtts-plus)
[![Python](https://img.shields.io/pypi/pyversions/funtts-plus.svg)](https://pypi.org/project/funtts-plus/)
[![License: MIT](https://img.shields.io/badge/License-MIT-yellow.svg)](https://opensource.org/licenses/MIT)

FunTTS是一个现代化的Python文本转语音(TTS)库,提供统一的接口来无缝切换不同的开源TTS引擎。通过简单的配置,你可以在多个TTS引擎之间轻松切换,而无需修改代码。

## ✨ 核心特性

- 🎯 **统一接口**: 所有TTS引擎使用相同的API接口,支持Request/Response模式
- 🔄 **无缝切换**: 通过配置轻松切换不同的TTS引擎
- 🎵 **多引擎支持**: 支持Edge TTS、Azure TTS、eSpeak、pyttsx3等主流引擎
- ⚙️ **灵活配置**: 支持全局配置和引擎特定配置管理
- 📝 **智能字幕**: 支持SRT、VTT、FRT三种字幕格式,自动时间同步
- 🎭 **多角色支持**: 支持多说话者场景,角色信息管理
- 🔧 **工具集成**: 提供音频合并、字幕合并、响应合并等实用工具
- 🌍 **多语言支持**: 支持多种语言和语音,智能语音选择
- 📊 **数据模型**: 完整的数据结构定义,类型安全
- 🚀 **高性能**: 异步处理支持,批量操作优化

## 支持的TTS引擎

| 引擎 | 状态 | 字幕支持 | 描述 | 文档 |
|------|------|----------|------|------|
| Edge TTS | ✅ | ✅ | 微软Edge浏览器的TTS引擎,免费且高质量 | [📖 文档](src/funtts/tts/edge/README.md) |
| Azure TTS | ✅ | ✅ | 微软Azure认知服务TTS,需要API密钥 | [📖 文档](src/funtts/tts/azure/README.md) |
| Coqui TTS | ✅ | ✅ | 功能强大的深度学习TTS工具包,支持多种模型 | [📖 文档](src/funtts/tts/coqui/README.md) |
| Bark TTS | ✅ | ✅ | 支持非语言声音和音乐生成的Transformer TTS | [📖 文档](src/funtts/tts/bark/README.md) |
| Tortoise TTS | ✅ | ✅ | 高质量语音克隆TTS,音质接近真人水平 | [📖 文档](src/funtts/tts/tortoise/README.md) |
| IndexTTS2 | ✅ | ✅ | 工业级可控制TTS,支持情感控制和自然语言指令 | [📖 文档](src/funtts/tts/indextts2/README.md) |
| KittenTTS | ✅ | ✅ | 基于深度学习的高质量TTS引擎,神经网络 | [📖 文档](src/funtts/tts/kitten/README.md) |
| eSpeak | ✅ | ✅ | 开源的多语言语音合成器,轻量级 | [📖 文档](src/funtts/tts/espeak/README.md) |
| pyttsx3 | ✅ | ✅ | 跨平台的Python TTS库,本地离线 | [📖 文档](src/funtts/tts/pyttsx3/README.md) |

> 💡 **提示**: 点击文档链接查看每个引擎的详细配置说明、使用示例和故障排除指南。

## 📦 安装

### 基础安装

```bash
# 基础功能安装
pip install funtts-plus
```

### 按需安装引擎

根据需要安装特定TTS引擎的依赖:

```bash
# Edge TTS (推荐,免费高质量)
pip install funtts-plus[edge]

# Azure TTS (需要API密钥)
pip install funtts-plus[azure]

# Coqui TTS (功能强大的深度学习TTS工具包)
pip install funtts-plus[coqui]

# Bark TTS (支持非语言声音和音乐生成)
pip install funtts-plus[bark]

# Tortoise TTS (高质量语音克隆)
pip install funtts-plus[tortoise]

# IndexTTS2 (工业级TTS,支持情感控制)
pip install funtts-plus[indextts2]

# KittenTTS (深度学习TTS,需要GPU支持)
pip install funtts-plus[kitten]

# pyttsx3 (跨平台本地TTS)
pip install funtts-plus[pyttsx3]

# 完整安装(所有引擎)
pip install funtts-plus[all]
```

### 系统依赖

某些引擎需要额外的系统依赖:

```bash
# eSpeak (需要系统安装)
# Ubuntu/Debian
sudo apt-get install espeak espeak-data

# macOS
brew install espeak

# Windows
# 从 http://espeak.sourceforge.net/download.html 下载安装

# FFmpeg (用于音频处理,可选)
# Ubuntu/Debian
sudo apt-get install ffmpeg

# macOS
brew install ffmpeg

# Windows
# 从 https://ffmpeg.org/download.html 下载安装
```

## 🚀 快速开始

### 基本使用

```python
from funtts import create_tts, TTSRequest

# 使用默认配置创建TTS实例
tts = create_tts()

# 方式1:简单调用(兼容旧版本)
tts.create_tts(
    text="你好,这是一个TTS测试。",
    voice_rate=1.0,
    voice_file="output.wav",
    subtitle_file="output.srt"  # 可选,生成字幕文件
)

# 方式2:使用Request/Response模式(推荐)
request = TTSRequest(
    text="你好,这是FunTTS的新架构演示。",
    voice_name="zh-CN-XiaoxiaoNeural",
    voice_rate=1.2,
    output_file="demo.wav",
    generate_subtitles=True,
    subtitle_format="srt"
)

response = tts.synthesize(request)
if response.success:
    print(f"✅ 生成成功!")
    print(f"音频文件: {response.audio_file}")
    print(f"字幕文件: {response.subtitle_file}")
    print(f"FRT字幕: {response.frt_subtitle_file}")
    print(f"音频时长: {response.duration:.2f}秒")
else:
    print(f"❌ 生成失败: {response.error_message}")
```

### 指定TTS引擎

```python
from funtts import TTSFactory

# 使用Edge TTS
edge_tts = TTSFactory.create_tts(
    engine_name="edge",
    voice_name="zh-CN-XiaoxiaoNeural"
)

# 使用eSpeak
espeak_tts = TTSFactory.create_tts(
    engine_name="espeak", 
    voice_name="zh"
)

# 使用pyttsx3
pyttsx3_tts = TTSFactory.create_tts(
    engine_name="pyttsx3",
    voice_name="0"  # 使用第一个可用语音
)
```

### 配置管理

```python
from funtts import get_config

# 获取全局配置
config = get_config()

# 设置默认引擎
config.set_default_engine("edge")
config.set_default_voice("zh-CN-XiaoxiaoNeural")
config.set_default_rate(1.2)

# 设置引擎特定配置
config.set_engine_config("azure", {
    "subscription_key": "your-api-key",
    "region": "eastus"
})

# 保存配置
config.save_config()
```

### 获取可用语音

```python
from funtts import TTSFactory

# 创建TTS实例
tts = TTSFactory.create_tts("edge", "zh-CN-XiaoxiaoNeural")

# 获取所有可用语音
voices = tts.get_available_voices()

# 获取中文语音
chinese_voices = tts.get_available_voices(language="zh-CN")

# 检查语音是否可用
is_available = tts.is_voice_available("zh-CN-XiaoxiaoNeural")
```

## 高级用法

### 工厂模式

```python
from funtts import TTSFactory, get_available_engines

# 查看所有可用引擎
engines = get_available_engines()
print(f"可用引擎: {engines}")

# 批量创建不同引擎的实例
tts_instances = {}
for engine in engines:
    try:
        tts_instances[engine] = TTSFactory.create_tts(
            engine_name=engine,
            voice_name="default"
        )
    except Exception as e:
        print(f"创建{engine}引擎失败: {e}")
```

### 自定义配置

```python
from funtts import TTSFactory

# 使用自定义配置
custom_config = {
    "volume": 0.8,
    "pitch": 1.1
}

tts = TTSFactory.create_tts(
    engine_name="pyttsx3",
    voice_name="0",
    config=custom_config
)
```

### 批量处理

```python
from funtts import create_tts
import os

# 批量处理文本文件
texts = [
    "第一段文本内容",
    "第二段文本内容", 
    "第三段文本内容"
]

tts = create_tts(engine_name="edge")

for i, text in enumerate(texts):
    audio_file = f"output_{i+1}.wav"
    subtitle_file = f"output_{i+1}.srt"
    
    tts.create_tts(
        text=text,
        voice_rate=1.0,
        voice_file=audio_file,
        subtitle_file=subtitle_file
    )
    
    print(f"生成完成: {audio_file}")
```

## 配置文件

FunTTS使用JSON格式的配置文件,默认位置为 `~/.funtts/config.json`:

```json
{
  "default_engine": "edge",
  "default_voice": "zh-CN-XiaoxiaoNeural",
  "default_rate": 1.0,
  "engines": {
    "edge": {
      "enabled": true,
      "config": {}
    },
    "azure": {
      "enabled": true,
      "config": {
        "subscription_key": "",
        "region": "eastus"
      }
    },
    "espeak": {
      "enabled": true,
      "config": {
        "executable_path": "espeak"
      }
    },
    "pyttsx3": {
      "enabled": true,
      "config": {
        "volume": 1.0
      }
    }
  }
}
```

## 📚 示例代码

项目提供了丰富的示例代码,查看 `examples/` 目录:

- **`basic_usage.py`** - 基本使用示例,展示核心功能
- **`advanced_usage.py`** - 高级功能示例,包括配置管理、引擎对比、自定义引擎
- **`utils_example.py`** - 工具函数示例,音频合并、字幕处理、多角色对话

### 运行示例

```bash
# 基本使用示例
python examples/basic_usage.py

# 高级功能演示
python examples/advanced_usage.py

# 工具函数演示
python examples/utils_example.py
```

## 🏗️ 项目架构

```
funtts/
├── base/           # 基础抽象类
│   └── base.py     # BaseTTS基类
├── models/         # 数据模型
│   ├── audio_segment.py      # 音频片段
│   ├── voice_info.py         # 语音信息
│   ├── subtitle_maker.py     # 字幕制作器
│   └── request_response.py   # 请求响应模型
├── tts/            # TTS引擎实现
│   ├── edge/       # Edge TTS
│   ├── azure/      # Azure TTS
│   ├── espeak/     # eSpeak
│   └── pyttsx3/    # pyttsx3
├── utils/          # 工具函数
│   ├── audio_utils.py        # 音频处理
│   ├── subtitle_utils.py     # 字幕处理
│   └── response_utils.py     # 响应合并
├── config.py       # 配置管理
├── factory.py      # TTS工厂
└── __init__.py     # 主入口
```

## 🔥 高级功能

### 多角色对话生成

```python
from funtts import create_tts, TTSRequest
from funtts.utils import merge_tts_responses_with_speakers

# 创建TTS实例
tts = create_tts("edge")

# 定义对话内容
dialogue = [
    ("小明", "你好,今天天气真不错!", "zh-CN-YunxiNeural"),
    ("小红", "是啊,我们去公园走走吧。", "zh-CN-XiaoxiaoNeural"),
    ("小明", "好主意,我们现在就出发。", "zh-CN-YunxiNeural"),
]

# 生成各角色语音
responses = []
speaker_names = []
for speaker, text, voice in dialogue:
    request = TTSRequest(
        text=text,
        voice_name=voice,
        output_file=f"{speaker}_{len(responses)+1}.wav",
        generate_subtitles=True
    )
    response = tts.synthesize(request)
    if response.success:
        responses.append(response)
        speaker_names.append(speaker)

# 合并成完整对话
merged = merge_tts_responses_with_speakers(
    responses=responses,
    speaker_names=speaker_names,
    output_audio_file="dialogue.wav",
    gap_duration=0.5  # 对话间隔0.5秒
)

if merged.success:
    print(f"🎭 对话生成完成: {merged.audio_file}")
    print(f"📝 字幕文件: {merged.subtitle_file}")
```

### 字幕格式支持

```python
from funtts import create_tts, TTSRequest
from funtts.models import SubtitleMaker

tts = create_tts("edge")

# 生成多种字幕格式
request = TTSRequest(
    text="FunTTS支持多种字幕格式,包括SRT、VTT和FRT格式。",
    voice_name="zh-CN-XiaoxiaoNeural",
    output_file="demo.wav",
    generate_subtitles=True,
    subtitle_format="srt"  # 标准格式
)

response = tts.synthesize(request)
if response.success:
    # 自动生成两种字幕文件
    print(f"📝 SRT字幕: {response.subtitle_file}")
    print(f"🎯 FRT字幕: {response.frt_subtitle_file}")
    
    # 手动保存其他格式
    if response.subtitle_maker:
        # 保存VTT格式
        vtt_file = "demo.sub.vtt"
        response.subtitle_maker.save_to_file(vtt_file, "vtt")
        print(f"🎬 VTT字幕: {vtt_file}")
```

## 📚 引擎文档

每个TTS引擎都有详细的文档说明,包含安装、配置、使用示例和故障排除指南:

### 🎯 Edge TTS
- **文档**: [src/funtts/tts/edge/README.md](src/funtts/tts/edge/README.md)
- **特点**: 免费、高质量、多语言支持
- **适用**: 大多数应用场景,推荐首选

### ☁️ Azure TTS  
- **文档**: [src/funtts/tts/azure/README.md](src/funtts/tts/azure/README.md)
- **特点**: 企业级、SSML支持、高度可定制
- **适用**: 商业应用、需要高级功能的场景

### 🐸 Coqui TTS
- **文档**: [src/funtts/tts/coqui/README.md](src/funtts/tts/coqui/README.md)
- **特点**: 多模型支持、语音克隆、多语言、可训练
- **适用**: 研究开发、自定义模型、多语言应用

### 🌳 Bark TTS
- **文档**: [src/funtts/tts/bark/README.md](src/funtts/tts/bark/README.md)
- **特点**: 非语言声音、音乐生成、特效音效、情感表达
- **适用**: 创意内容、播客制作、游戏音效、娱乐应用

### 🐢 Tortoise TTS
- **文档**: [src/funtts/tts/tortoise/README.md](src/funtts/tts/tortoise/README.md)
- **特点**: 极高音质、语音克隆、接近真人、多种预设
- **适用**: 高质量配音、语音克隆、专业制作

### 🏭 IndexTTS2
- **文档**: [src/funtts/tts/indextts2/README.md](src/funtts/tts/indextts2/README.md)
- **特点**: 工业级、情感控制、自然语言指令、精确时长控制
- **适用**: 专业应用、情感语音、内容创作、AI助手

### 🐱 KittenTTS
- **文档**: [src/funtts/tts/kitten/README.md](src/funtts/tts/kitten/README.md)
- **特点**: 深度学习、高质量、神经网络、多语音风格
- **适用**: 高质量语音需求、AI应用、内容创作

### 🔊 eSpeak TTS
- **文档**: [src/funtts/tts/espeak/README.md](src/funtts/tts/espeak/README.md)
- **特点**: 轻量级、开源、多语言
- **适用**: Linux环境、嵌入式系统、资源受限场景

### 🖥️ Pyttsx3 TTS
- **文档**: [src/funtts/tts/pyttsx3/README.md](src/funtts/tts/pyttsx3/README.md)
- **特点**: 跨平台、本地离线、系统集成
- **适用**: 桌面应用、离线环境、快速原型

> 📋 **开发规范**: 查看 [docs/ENGINE_DEVELOPMENT_GUIDE.md](docs/ENGINE_DEVELOPMENT_GUIDE.md) 了解如何开发新的TTS引擎。

## 🛠️ 开发指南

### 添加新的TTS引擎

1. 继承 `BaseTTS` 基类
2. 实现必要的抽象方法
3. 在工厂类中注册新引擎

```python
from funtts.base import BaseTTS
from funtts import TTSFactory, TTSRequest, TTSResponse
from funtts.models import VoiceInfo
from typing import List

class MyCustomTTS(BaseTTS):
    """自定义TTS引擎示例"""
    
    def synthesize(self, request: TTSRequest) -> TTSResponse:
        """实现语音合成"""
        try:
            # 这里实现你的TTS逻辑
            print(f"CustomTTS: 正在合成 '{request.text[:20]}...'")
            
            # 创建示例音频文件
            with open(request.output_file, 'wb') as f:
                f.write(b'\x00' * 1024)  # 示例数据
            
            return TTSResponse(
                success=True,
                request=request,
                audio_file=request.output_file,
                duration=2.0,
                voice_used="custom_voice",
                engine_info={"engine": "custom", "version": "1.0"}
            )
        except Exception as e:
            return TTSResponse(
                success=False,
                request=request,
                error_message=str(e)
            )
    
    def list_voices(self, language: str = None) -> List[VoiceInfo]:
        """返回可用语音列表"""
        return [
            VoiceInfo(
                name="custom_voice_1",
                display_name="自定义语音1",
                language="zh-CN",
                gender="female",
                engine="custom"
            )
        ]
    
    def is_voice_available(self, voice_name: str) -> bool:
        """检查语音是否可用"""
        return voice_name == "custom_voice_1"

# 注册新引擎
TTSFactory.register_engine("mycustom", MyCustomTTS)

# 使用自定义引擎
custom_tts = TTSFactory.create_tts("mycustom", "custom_voice_1")
```

### 项目构建

```bash
# 克隆项目
git clone https://github.com/farfarfun/funtts.git
cd funtts

# 安装开发依赖
pip install -e .[all]

# 运行测试
python -m pytest tests/

# 代码格式化
black src/
isort src/

# 类型检查
mypy src/
```

## 🤝 贡献指南

我们欢迎各种形式的贡献!

### 如何贡献

1. **Fork** 本仓库
2. **创建** 功能分支 (`git checkout -b feature/AmazingFeature`)
3. **提交** 更改 (`git commit -m 'Add some AmazingFeature'`)
4. **推送** 到分支 (`git push origin feature/AmazingFeature`)
5. **打开** Pull Request

### 贡献类型

- 🐛 **Bug修复**: 修复已知问题
- ✨ **新功能**: 添加新的TTS引擎或功能
- 📚 **文档**: 改进文档和示例
- 🎨 **优化**: 代码重构和性能优化
- 🧪 **测试**: 添加或改进测试用例

### 开发规范

- 遵循PEP 8代码规范
- 添加适当的类型注解
- 编写清晰的文档字符串
- 为新功能添加测试用例
- 更新相关文档

## 📄 许可证

本项目采用 [MIT License](LICENSE) 许可证。

## 🙏 致谢

感谢以下开源项目的支持:

- [edge-tts](https://github.com/rany2/edge-tts) - Microsoft Edge的文本转语音
- [Azure Cognitive Services](https://azure.microsoft.com/services/cognitive-services/) - 微软Azure TTS服务
- [eSpeak](http://espeak.sourceforge.net/) - 开源语音合成器
- [pyttsx3](https://github.com/nateshmbhat/pyttsx3) - Python文本转语音库
- [pydub](https://github.com/jiaaro/pydub) - 音频处理库

## 📞 联系我们

- **GitHub Issues**: [提交问题](https://github.com/farfarfun/funtts/issues)
- **GitHub Discussions**: [参与讨论](https://github.com/farfarfun/funtts/discussions)
- **Email**: farfarfun@qq.com

---

<div align="center">

**如果这个项目对你有帮助,请给我们一个 ⭐ Star!**

Made with ❤️ by [FarFarFun Team](https://github.com/farfarfun)

</div>

            

Raw data

            {
    "_id": null,
    "home_page": null,
    "name": "funtts-plus",
    "maintainer": null,
    "docs_url": null,
    "requires_python": ">=3.8",
    "maintainer_email": "\u725b\u54e5 <niuliangtao@qq.com>, farfarfun <farfarfun@qq.com>",
    "keywords": "tts, text-to-speech, audio, subtitle, speech-synthesis",
    "author": null,
    "author_email": "\u725b\u54e5 <niuliangtao@qq.com>, farfarfun <farfarfun@qq.com>",
    "download_url": null,
    "platform": null,
    "description": "# FunTTS - \u7edf\u4e00TTS\u63a5\u53e3\u5e93\n\n[![PyPI version](https://badge.fury.io/py/funtts-plus.svg)](https://badge.fury.io/py/funtts-plus)\n[![Python](https://img.shields.io/pypi/pyversions/funtts-plus.svg)](https://pypi.org/project/funtts-plus/)\n[![License: MIT](https://img.shields.io/badge/License-MIT-yellow.svg)](https://opensource.org/licenses/MIT)\n\nFunTTS\u662f\u4e00\u4e2a\u73b0\u4ee3\u5316\u7684Python\u6587\u672c\u8f6c\u8bed\u97f3(TTS)\u5e93\uff0c\u63d0\u4f9b\u7edf\u4e00\u7684\u63a5\u53e3\u6765\u65e0\u7f1d\u5207\u6362\u4e0d\u540c\u7684\u5f00\u6e90TTS\u5f15\u64ce\u3002\u901a\u8fc7\u7b80\u5355\u7684\u914d\u7f6e\uff0c\u4f60\u53ef\u4ee5\u5728\u591a\u4e2aTTS\u5f15\u64ce\u4e4b\u95f4\u8f7b\u677e\u5207\u6362\uff0c\u800c\u65e0\u9700\u4fee\u6539\u4ee3\u7801\u3002\n\n## \u2728 \u6838\u5fc3\u7279\u6027\n\n- \ud83c\udfaf **\u7edf\u4e00\u63a5\u53e3**: \u6240\u6709TTS\u5f15\u64ce\u4f7f\u7528\u76f8\u540c\u7684API\u63a5\u53e3\uff0c\u652f\u6301Request/Response\u6a21\u5f0f\n- \ud83d\udd04 **\u65e0\u7f1d\u5207\u6362**: \u901a\u8fc7\u914d\u7f6e\u8f7b\u677e\u5207\u6362\u4e0d\u540c\u7684TTS\u5f15\u64ce\n- \ud83c\udfb5 **\u591a\u5f15\u64ce\u652f\u6301**: \u652f\u6301Edge TTS\u3001Azure TTS\u3001eSpeak\u3001pyttsx3\u7b49\u4e3b\u6d41\u5f15\u64ce\n- \u2699\ufe0f **\u7075\u6d3b\u914d\u7f6e**: \u652f\u6301\u5168\u5c40\u914d\u7f6e\u548c\u5f15\u64ce\u7279\u5b9a\u914d\u7f6e\u7ba1\u7406\n- \ud83d\udcdd **\u667a\u80fd\u5b57\u5e55**: \u652f\u6301SRT\u3001VTT\u3001FRT\u4e09\u79cd\u5b57\u5e55\u683c\u5f0f\uff0c\u81ea\u52a8\u65f6\u95f4\u540c\u6b65\n- \ud83c\udfad **\u591a\u89d2\u8272\u652f\u6301**: \u652f\u6301\u591a\u8bf4\u8bdd\u8005\u573a\u666f\uff0c\u89d2\u8272\u4fe1\u606f\u7ba1\u7406\n- \ud83d\udd27 **\u5de5\u5177\u96c6\u6210**: \u63d0\u4f9b\u97f3\u9891\u5408\u5e76\u3001\u5b57\u5e55\u5408\u5e76\u3001\u54cd\u5e94\u5408\u5e76\u7b49\u5b9e\u7528\u5de5\u5177\n- \ud83c\udf0d **\u591a\u8bed\u8a00\u652f\u6301**: \u652f\u6301\u591a\u79cd\u8bed\u8a00\u548c\u8bed\u97f3\uff0c\u667a\u80fd\u8bed\u97f3\u9009\u62e9\n- \ud83d\udcca **\u6570\u636e\u6a21\u578b**: \u5b8c\u6574\u7684\u6570\u636e\u7ed3\u6784\u5b9a\u4e49\uff0c\u7c7b\u578b\u5b89\u5168\n- \ud83d\ude80 **\u9ad8\u6027\u80fd**: \u5f02\u6b65\u5904\u7406\u652f\u6301\uff0c\u6279\u91cf\u64cd\u4f5c\u4f18\u5316\n\n## \u652f\u6301\u7684TTS\u5f15\u64ce\n\n| \u5f15\u64ce | \u72b6\u6001 | \u5b57\u5e55\u652f\u6301 | \u63cf\u8ff0 | \u6587\u6863 |\n|------|------|----------|------|------|\n| Edge TTS | \u2705 | \u2705 | \u5fae\u8f6fEdge\u6d4f\u89c8\u5668\u7684TTS\u5f15\u64ce\uff0c\u514d\u8d39\u4e14\u9ad8\u8d28\u91cf | [\ud83d\udcd6 \u6587\u6863](src/funtts/tts/edge/README.md) |\n| Azure TTS | \u2705 | \u2705 | \u5fae\u8f6fAzure\u8ba4\u77e5\u670d\u52a1TTS\uff0c\u9700\u8981API\u5bc6\u94a5 | [\ud83d\udcd6 \u6587\u6863](src/funtts/tts/azure/README.md) |\n| Coqui TTS | \u2705 | \u2705 | \u529f\u80fd\u5f3a\u5927\u7684\u6df1\u5ea6\u5b66\u4e60TTS\u5de5\u5177\u5305\uff0c\u652f\u6301\u591a\u79cd\u6a21\u578b | [\ud83d\udcd6 \u6587\u6863](src/funtts/tts/coqui/README.md) |\n| Bark TTS | \u2705 | \u2705 | \u652f\u6301\u975e\u8bed\u8a00\u58f0\u97f3\u548c\u97f3\u4e50\u751f\u6210\u7684Transformer TTS | [\ud83d\udcd6 \u6587\u6863](src/funtts/tts/bark/README.md) |\n| Tortoise TTS | \u2705 | \u2705 | \u9ad8\u8d28\u91cf\u8bed\u97f3\u514b\u9686TTS\uff0c\u97f3\u8d28\u63a5\u8fd1\u771f\u4eba\u6c34\u5e73 | [\ud83d\udcd6 \u6587\u6863](src/funtts/tts/tortoise/README.md) |\n| IndexTTS2 | \u2705 | \u2705 | \u5de5\u4e1a\u7ea7\u53ef\u63a7\u5236TTS\uff0c\u652f\u6301\u60c5\u611f\u63a7\u5236\u548c\u81ea\u7136\u8bed\u8a00\u6307\u4ee4 | [\ud83d\udcd6 \u6587\u6863](src/funtts/tts/indextts2/README.md) |\n| KittenTTS | \u2705 | \u2705 | \u57fa\u4e8e\u6df1\u5ea6\u5b66\u4e60\u7684\u9ad8\u8d28\u91cfTTS\u5f15\u64ce\uff0c\u795e\u7ecf\u7f51\u7edc | [\ud83d\udcd6 \u6587\u6863](src/funtts/tts/kitten/README.md) |\n| eSpeak | \u2705 | \u2705 | \u5f00\u6e90\u7684\u591a\u8bed\u8a00\u8bed\u97f3\u5408\u6210\u5668\uff0c\u8f7b\u91cf\u7ea7 | [\ud83d\udcd6 \u6587\u6863](src/funtts/tts/espeak/README.md) |\n| pyttsx3 | \u2705 | \u2705 | \u8de8\u5e73\u53f0\u7684Python TTS\u5e93\uff0c\u672c\u5730\u79bb\u7ebf | [\ud83d\udcd6 \u6587\u6863](src/funtts/tts/pyttsx3/README.md) |\n\n> \ud83d\udca1 **\u63d0\u793a**: \u70b9\u51fb\u6587\u6863\u94fe\u63a5\u67e5\u770b\u6bcf\u4e2a\u5f15\u64ce\u7684\u8be6\u7ec6\u914d\u7f6e\u8bf4\u660e\u3001\u4f7f\u7528\u793a\u4f8b\u548c\u6545\u969c\u6392\u9664\u6307\u5357\u3002\n\n## \ud83d\udce6 \u5b89\u88c5\n\n### \u57fa\u7840\u5b89\u88c5\n\n```bash\n# \u57fa\u7840\u529f\u80fd\u5b89\u88c5\npip install funtts-plus\n```\n\n### \u6309\u9700\u5b89\u88c5\u5f15\u64ce\n\n\u6839\u636e\u9700\u8981\u5b89\u88c5\u7279\u5b9aTTS\u5f15\u64ce\u7684\u4f9d\u8d56\uff1a\n\n```bash\n# Edge TTS (\u63a8\u8350\uff0c\u514d\u8d39\u9ad8\u8d28\u91cf)\npip install funtts-plus[edge]\n\n# Azure TTS (\u9700\u8981API\u5bc6\u94a5)\npip install funtts-plus[azure]\n\n# Coqui TTS (\u529f\u80fd\u5f3a\u5927\u7684\u6df1\u5ea6\u5b66\u4e60TTS\u5de5\u5177\u5305)\npip install funtts-plus[coqui]\n\n# Bark TTS (\u652f\u6301\u975e\u8bed\u8a00\u58f0\u97f3\u548c\u97f3\u4e50\u751f\u6210)\npip install funtts-plus[bark]\n\n# Tortoise TTS (\u9ad8\u8d28\u91cf\u8bed\u97f3\u514b\u9686)\npip install funtts-plus[tortoise]\n\n# IndexTTS2 (\u5de5\u4e1a\u7ea7TTS\uff0c\u652f\u6301\u60c5\u611f\u63a7\u5236)\npip install funtts-plus[indextts2]\n\n# KittenTTS (\u6df1\u5ea6\u5b66\u4e60TTS\uff0c\u9700\u8981GPU\u652f\u6301)\npip install funtts-plus[kitten]\n\n# pyttsx3 (\u8de8\u5e73\u53f0\u672c\u5730TTS)\npip install funtts-plus[pyttsx3]\n\n# \u5b8c\u6574\u5b89\u88c5\uff08\u6240\u6709\u5f15\u64ce\uff09\npip install funtts-plus[all]\n```\n\n### \u7cfb\u7edf\u4f9d\u8d56\n\n\u67d0\u4e9b\u5f15\u64ce\u9700\u8981\u989d\u5916\u7684\u7cfb\u7edf\u4f9d\u8d56\uff1a\n\n```bash\n# eSpeak (\u9700\u8981\u7cfb\u7edf\u5b89\u88c5)\n# Ubuntu/Debian\nsudo apt-get install espeak espeak-data\n\n# macOS\nbrew install espeak\n\n# Windows\n# \u4ece http://espeak.sourceforge.net/download.html \u4e0b\u8f7d\u5b89\u88c5\n\n# FFmpeg (\u7528\u4e8e\u97f3\u9891\u5904\u7406\uff0c\u53ef\u9009)\n# Ubuntu/Debian\nsudo apt-get install ffmpeg\n\n# macOS\nbrew install ffmpeg\n\n# Windows\n# \u4ece https://ffmpeg.org/download.html \u4e0b\u8f7d\u5b89\u88c5\n```\n\n## \ud83d\ude80 \u5feb\u901f\u5f00\u59cb\n\n### \u57fa\u672c\u4f7f\u7528\n\n```python\nfrom funtts import create_tts, TTSRequest\n\n# \u4f7f\u7528\u9ed8\u8ba4\u914d\u7f6e\u521b\u5efaTTS\u5b9e\u4f8b\ntts = create_tts()\n\n# \u65b9\u5f0f1\uff1a\u7b80\u5355\u8c03\u7528\uff08\u517c\u5bb9\u65e7\u7248\u672c\uff09\ntts.create_tts(\n    text=\"\u4f60\u597d\uff0c\u8fd9\u662f\u4e00\u4e2aTTS\u6d4b\u8bd5\u3002\",\n    voice_rate=1.0,\n    voice_file=\"output.wav\",\n    subtitle_file=\"output.srt\"  # \u53ef\u9009\uff0c\u751f\u6210\u5b57\u5e55\u6587\u4ef6\n)\n\n# \u65b9\u5f0f2\uff1a\u4f7f\u7528Request/Response\u6a21\u5f0f\uff08\u63a8\u8350\uff09\nrequest = TTSRequest(\n    text=\"\u4f60\u597d\uff0c\u8fd9\u662fFunTTS\u7684\u65b0\u67b6\u6784\u6f14\u793a\u3002\",\n    voice_name=\"zh-CN-XiaoxiaoNeural\",\n    voice_rate=1.2,\n    output_file=\"demo.wav\",\n    generate_subtitles=True,\n    subtitle_format=\"srt\"\n)\n\nresponse = tts.synthesize(request)\nif response.success:\n    print(f\"\u2705 \u751f\u6210\u6210\u529f\uff01\")\n    print(f\"\u97f3\u9891\u6587\u4ef6: {response.audio_file}\")\n    print(f\"\u5b57\u5e55\u6587\u4ef6: {response.subtitle_file}\")\n    print(f\"FRT\u5b57\u5e55: {response.frt_subtitle_file}\")\n    print(f\"\u97f3\u9891\u65f6\u957f: {response.duration:.2f}\u79d2\")\nelse:\n    print(f\"\u274c \u751f\u6210\u5931\u8d25: {response.error_message}\")\n```\n\n### \u6307\u5b9aTTS\u5f15\u64ce\n\n```python\nfrom funtts import TTSFactory\n\n# \u4f7f\u7528Edge TTS\nedge_tts = TTSFactory.create_tts(\n    engine_name=\"edge\",\n    voice_name=\"zh-CN-XiaoxiaoNeural\"\n)\n\n# \u4f7f\u7528eSpeak\nespeak_tts = TTSFactory.create_tts(\n    engine_name=\"espeak\", \n    voice_name=\"zh\"\n)\n\n# \u4f7f\u7528pyttsx3\npyttsx3_tts = TTSFactory.create_tts(\n    engine_name=\"pyttsx3\",\n    voice_name=\"0\"  # \u4f7f\u7528\u7b2c\u4e00\u4e2a\u53ef\u7528\u8bed\u97f3\n)\n```\n\n### \u914d\u7f6e\u7ba1\u7406\n\n```python\nfrom funtts import get_config\n\n# \u83b7\u53d6\u5168\u5c40\u914d\u7f6e\nconfig = get_config()\n\n# \u8bbe\u7f6e\u9ed8\u8ba4\u5f15\u64ce\nconfig.set_default_engine(\"edge\")\nconfig.set_default_voice(\"zh-CN-XiaoxiaoNeural\")\nconfig.set_default_rate(1.2)\n\n# \u8bbe\u7f6e\u5f15\u64ce\u7279\u5b9a\u914d\u7f6e\nconfig.set_engine_config(\"azure\", {\n    \"subscription_key\": \"your-api-key\",\n    \"region\": \"eastus\"\n})\n\n# \u4fdd\u5b58\u914d\u7f6e\nconfig.save_config()\n```\n\n### \u83b7\u53d6\u53ef\u7528\u8bed\u97f3\n\n```python\nfrom funtts import TTSFactory\n\n# \u521b\u5efaTTS\u5b9e\u4f8b\ntts = TTSFactory.create_tts(\"edge\", \"zh-CN-XiaoxiaoNeural\")\n\n# \u83b7\u53d6\u6240\u6709\u53ef\u7528\u8bed\u97f3\nvoices = tts.get_available_voices()\n\n# \u83b7\u53d6\u4e2d\u6587\u8bed\u97f3\nchinese_voices = tts.get_available_voices(language=\"zh-CN\")\n\n# \u68c0\u67e5\u8bed\u97f3\u662f\u5426\u53ef\u7528\nis_available = tts.is_voice_available(\"zh-CN-XiaoxiaoNeural\")\n```\n\n## \u9ad8\u7ea7\u7528\u6cd5\n\n### \u5de5\u5382\u6a21\u5f0f\n\n```python\nfrom funtts import TTSFactory, get_available_engines\n\n# \u67e5\u770b\u6240\u6709\u53ef\u7528\u5f15\u64ce\nengines = get_available_engines()\nprint(f\"\u53ef\u7528\u5f15\u64ce: {engines}\")\n\n# \u6279\u91cf\u521b\u5efa\u4e0d\u540c\u5f15\u64ce\u7684\u5b9e\u4f8b\ntts_instances = {}\nfor engine in engines:\n    try:\n        tts_instances[engine] = TTSFactory.create_tts(\n            engine_name=engine,\n            voice_name=\"default\"\n        )\n    except Exception as e:\n        print(f\"\u521b\u5efa{engine}\u5f15\u64ce\u5931\u8d25: {e}\")\n```\n\n### \u81ea\u5b9a\u4e49\u914d\u7f6e\n\n```python\nfrom funtts import TTSFactory\n\n# \u4f7f\u7528\u81ea\u5b9a\u4e49\u914d\u7f6e\ncustom_config = {\n    \"volume\": 0.8,\n    \"pitch\": 1.1\n}\n\ntts = TTSFactory.create_tts(\n    engine_name=\"pyttsx3\",\n    voice_name=\"0\",\n    config=custom_config\n)\n```\n\n### \u6279\u91cf\u5904\u7406\n\n```python\nfrom funtts import create_tts\nimport os\n\n# \u6279\u91cf\u5904\u7406\u6587\u672c\u6587\u4ef6\ntexts = [\n    \"\u7b2c\u4e00\u6bb5\u6587\u672c\u5185\u5bb9\",\n    \"\u7b2c\u4e8c\u6bb5\u6587\u672c\u5185\u5bb9\", \n    \"\u7b2c\u4e09\u6bb5\u6587\u672c\u5185\u5bb9\"\n]\n\ntts = create_tts(engine_name=\"edge\")\n\nfor i, text in enumerate(texts):\n    audio_file = f\"output_{i+1}.wav\"\n    subtitle_file = f\"output_{i+1}.srt\"\n    \n    tts.create_tts(\n        text=text,\n        voice_rate=1.0,\n        voice_file=audio_file,\n        subtitle_file=subtitle_file\n    )\n    \n    print(f\"\u751f\u6210\u5b8c\u6210: {audio_file}\")\n```\n\n## \u914d\u7f6e\u6587\u4ef6\n\nFunTTS\u4f7f\u7528JSON\u683c\u5f0f\u7684\u914d\u7f6e\u6587\u4ef6\uff0c\u9ed8\u8ba4\u4f4d\u7f6e\u4e3a `~/.funtts/config.json`\uff1a\n\n```json\n{\n  \"default_engine\": \"edge\",\n  \"default_voice\": \"zh-CN-XiaoxiaoNeural\",\n  \"default_rate\": 1.0,\n  \"engines\": {\n    \"edge\": {\n      \"enabled\": true,\n      \"config\": {}\n    },\n    \"azure\": {\n      \"enabled\": true,\n      \"config\": {\n        \"subscription_key\": \"\",\n        \"region\": \"eastus\"\n      }\n    },\n    \"espeak\": {\n      \"enabled\": true,\n      \"config\": {\n        \"executable_path\": \"espeak\"\n      }\n    },\n    \"pyttsx3\": {\n      \"enabled\": true,\n      \"config\": {\n        \"volume\": 1.0\n      }\n    }\n  }\n}\n```\n\n## \ud83d\udcda \u793a\u4f8b\u4ee3\u7801\n\n\u9879\u76ee\u63d0\u4f9b\u4e86\u4e30\u5bcc\u7684\u793a\u4f8b\u4ee3\u7801\uff0c\u67e5\u770b `examples/` \u76ee\u5f55\uff1a\n\n- **`basic_usage.py`** - \u57fa\u672c\u4f7f\u7528\u793a\u4f8b\uff0c\u5c55\u793a\u6838\u5fc3\u529f\u80fd\n- **`advanced_usage.py`** - \u9ad8\u7ea7\u529f\u80fd\u793a\u4f8b\uff0c\u5305\u62ec\u914d\u7f6e\u7ba1\u7406\u3001\u5f15\u64ce\u5bf9\u6bd4\u3001\u81ea\u5b9a\u4e49\u5f15\u64ce\n- **`utils_example.py`** - \u5de5\u5177\u51fd\u6570\u793a\u4f8b\uff0c\u97f3\u9891\u5408\u5e76\u3001\u5b57\u5e55\u5904\u7406\u3001\u591a\u89d2\u8272\u5bf9\u8bdd\n\n### \u8fd0\u884c\u793a\u4f8b\n\n```bash\n# \u57fa\u672c\u4f7f\u7528\u793a\u4f8b\npython examples/basic_usage.py\n\n# \u9ad8\u7ea7\u529f\u80fd\u6f14\u793a\npython examples/advanced_usage.py\n\n# \u5de5\u5177\u51fd\u6570\u6f14\u793a\npython examples/utils_example.py\n```\n\n## \ud83c\udfd7\ufe0f \u9879\u76ee\u67b6\u6784\n\n```\nfuntts/\n\u251c\u2500\u2500 base/           # \u57fa\u7840\u62bd\u8c61\u7c7b\n\u2502   \u2514\u2500\u2500 base.py     # BaseTTS\u57fa\u7c7b\n\u251c\u2500\u2500 models/         # \u6570\u636e\u6a21\u578b\n\u2502   \u251c\u2500\u2500 audio_segment.py      # \u97f3\u9891\u7247\u6bb5\n\u2502   \u251c\u2500\u2500 voice_info.py         # \u8bed\u97f3\u4fe1\u606f\n\u2502   \u251c\u2500\u2500 subtitle_maker.py     # \u5b57\u5e55\u5236\u4f5c\u5668\n\u2502   \u2514\u2500\u2500 request_response.py   # \u8bf7\u6c42\u54cd\u5e94\u6a21\u578b\n\u251c\u2500\u2500 tts/            # TTS\u5f15\u64ce\u5b9e\u73b0\n\u2502   \u251c\u2500\u2500 edge/       # Edge TTS\n\u2502   \u251c\u2500\u2500 azure/      # Azure TTS\n\u2502   \u251c\u2500\u2500 espeak/     # eSpeak\n\u2502   \u2514\u2500\u2500 pyttsx3/    # pyttsx3\n\u251c\u2500\u2500 utils/          # \u5de5\u5177\u51fd\u6570\n\u2502   \u251c\u2500\u2500 audio_utils.py        # \u97f3\u9891\u5904\u7406\n\u2502   \u251c\u2500\u2500 subtitle_utils.py     # \u5b57\u5e55\u5904\u7406\n\u2502   \u2514\u2500\u2500 response_utils.py     # \u54cd\u5e94\u5408\u5e76\n\u251c\u2500\u2500 config.py       # \u914d\u7f6e\u7ba1\u7406\n\u251c\u2500\u2500 factory.py      # TTS\u5de5\u5382\n\u2514\u2500\u2500 __init__.py     # \u4e3b\u5165\u53e3\n```\n\n## \ud83d\udd25 \u9ad8\u7ea7\u529f\u80fd\n\n### \u591a\u89d2\u8272\u5bf9\u8bdd\u751f\u6210\n\n```python\nfrom funtts import create_tts, TTSRequest\nfrom funtts.utils import merge_tts_responses_with_speakers\n\n# \u521b\u5efaTTS\u5b9e\u4f8b\ntts = create_tts(\"edge\")\n\n# \u5b9a\u4e49\u5bf9\u8bdd\u5185\u5bb9\ndialogue = [\n    (\"\u5c0f\u660e\", \"\u4f60\u597d\uff0c\u4eca\u5929\u5929\u6c14\u771f\u4e0d\u9519\uff01\", \"zh-CN-YunxiNeural\"),\n    (\"\u5c0f\u7ea2\", \"\u662f\u554a\uff0c\u6211\u4eec\u53bb\u516c\u56ed\u8d70\u8d70\u5427\u3002\", \"zh-CN-XiaoxiaoNeural\"),\n    (\"\u5c0f\u660e\", \"\u597d\u4e3b\u610f\uff0c\u6211\u4eec\u73b0\u5728\u5c31\u51fa\u53d1\u3002\", \"zh-CN-YunxiNeural\"),\n]\n\n# \u751f\u6210\u5404\u89d2\u8272\u8bed\u97f3\nresponses = []\nspeaker_names = []\nfor speaker, text, voice in dialogue:\n    request = TTSRequest(\n        text=text,\n        voice_name=voice,\n        output_file=f\"{speaker}_{len(responses)+1}.wav\",\n        generate_subtitles=True\n    )\n    response = tts.synthesize(request)\n    if response.success:\n        responses.append(response)\n        speaker_names.append(speaker)\n\n# \u5408\u5e76\u6210\u5b8c\u6574\u5bf9\u8bdd\nmerged = merge_tts_responses_with_speakers(\n    responses=responses,\n    speaker_names=speaker_names,\n    output_audio_file=\"dialogue.wav\",\n    gap_duration=0.5  # \u5bf9\u8bdd\u95f4\u96940.5\u79d2\n)\n\nif merged.success:\n    print(f\"\ud83c\udfad \u5bf9\u8bdd\u751f\u6210\u5b8c\u6210: {merged.audio_file}\")\n    print(f\"\ud83d\udcdd \u5b57\u5e55\u6587\u4ef6: {merged.subtitle_file}\")\n```\n\n### \u5b57\u5e55\u683c\u5f0f\u652f\u6301\n\n```python\nfrom funtts import create_tts, TTSRequest\nfrom funtts.models import SubtitleMaker\n\ntts = create_tts(\"edge\")\n\n# \u751f\u6210\u591a\u79cd\u5b57\u5e55\u683c\u5f0f\nrequest = TTSRequest(\n    text=\"FunTTS\u652f\u6301\u591a\u79cd\u5b57\u5e55\u683c\u5f0f\uff0c\u5305\u62ecSRT\u3001VTT\u548cFRT\u683c\u5f0f\u3002\",\n    voice_name=\"zh-CN-XiaoxiaoNeural\",\n    output_file=\"demo.wav\",\n    generate_subtitles=True,\n    subtitle_format=\"srt\"  # \u6807\u51c6\u683c\u5f0f\n)\n\nresponse = tts.synthesize(request)\nif response.success:\n    # \u81ea\u52a8\u751f\u6210\u4e24\u79cd\u5b57\u5e55\u6587\u4ef6\n    print(f\"\ud83d\udcdd SRT\u5b57\u5e55: {response.subtitle_file}\")\n    print(f\"\ud83c\udfaf FRT\u5b57\u5e55: {response.frt_subtitle_file}\")\n    \n    # \u624b\u52a8\u4fdd\u5b58\u5176\u4ed6\u683c\u5f0f\n    if response.subtitle_maker:\n        # \u4fdd\u5b58VTT\u683c\u5f0f\n        vtt_file = \"demo.sub.vtt\"\n        response.subtitle_maker.save_to_file(vtt_file, \"vtt\")\n        print(f\"\ud83c\udfac VTT\u5b57\u5e55: {vtt_file}\")\n```\n\n## \ud83d\udcda \u5f15\u64ce\u6587\u6863\n\n\u6bcf\u4e2aTTS\u5f15\u64ce\u90fd\u6709\u8be6\u7ec6\u7684\u6587\u6863\u8bf4\u660e\uff0c\u5305\u542b\u5b89\u88c5\u3001\u914d\u7f6e\u3001\u4f7f\u7528\u793a\u4f8b\u548c\u6545\u969c\u6392\u9664\u6307\u5357\uff1a\n\n### \ud83c\udfaf Edge TTS\n- **\u6587\u6863**: [src/funtts/tts/edge/README.md](src/funtts/tts/edge/README.md)\n- **\u7279\u70b9**: \u514d\u8d39\u3001\u9ad8\u8d28\u91cf\u3001\u591a\u8bed\u8a00\u652f\u6301\n- **\u9002\u7528**: \u5927\u591a\u6570\u5e94\u7528\u573a\u666f\uff0c\u63a8\u8350\u9996\u9009\n\n### \u2601\ufe0f Azure TTS  \n- **\u6587\u6863**: [src/funtts/tts/azure/README.md](src/funtts/tts/azure/README.md)\n- **\u7279\u70b9**: \u4f01\u4e1a\u7ea7\u3001SSML\u652f\u6301\u3001\u9ad8\u5ea6\u53ef\u5b9a\u5236\n- **\u9002\u7528**: \u5546\u4e1a\u5e94\u7528\u3001\u9700\u8981\u9ad8\u7ea7\u529f\u80fd\u7684\u573a\u666f\n\n### \ud83d\udc38 Coqui TTS\n- **\u6587\u6863**: [src/funtts/tts/coqui/README.md](src/funtts/tts/coqui/README.md)\n- **\u7279\u70b9**: \u591a\u6a21\u578b\u652f\u6301\u3001\u8bed\u97f3\u514b\u9686\u3001\u591a\u8bed\u8a00\u3001\u53ef\u8bad\u7ec3\n- **\u9002\u7528**: \u7814\u7a76\u5f00\u53d1\u3001\u81ea\u5b9a\u4e49\u6a21\u578b\u3001\u591a\u8bed\u8a00\u5e94\u7528\n\n### \ud83c\udf33 Bark TTS\n- **\u6587\u6863**: [src/funtts/tts/bark/README.md](src/funtts/tts/bark/README.md)\n- **\u7279\u70b9**: \u975e\u8bed\u8a00\u58f0\u97f3\u3001\u97f3\u4e50\u751f\u6210\u3001\u7279\u6548\u97f3\u6548\u3001\u60c5\u611f\u8868\u8fbe\n- **\u9002\u7528**: \u521b\u610f\u5185\u5bb9\u3001\u64ad\u5ba2\u5236\u4f5c\u3001\u6e38\u620f\u97f3\u6548\u3001\u5a31\u4e50\u5e94\u7528\n\n### \ud83d\udc22 Tortoise TTS\n- **\u6587\u6863**: [src/funtts/tts/tortoise/README.md](src/funtts/tts/tortoise/README.md)\n- **\u7279\u70b9**: \u6781\u9ad8\u97f3\u8d28\u3001\u8bed\u97f3\u514b\u9686\u3001\u63a5\u8fd1\u771f\u4eba\u3001\u591a\u79cd\u9884\u8bbe\n- **\u9002\u7528**: \u9ad8\u8d28\u91cf\u914d\u97f3\u3001\u8bed\u97f3\u514b\u9686\u3001\u4e13\u4e1a\u5236\u4f5c\n\n### \ud83c\udfed IndexTTS2\n- **\u6587\u6863**: [src/funtts/tts/indextts2/README.md](src/funtts/tts/indextts2/README.md)\n- **\u7279\u70b9**: \u5de5\u4e1a\u7ea7\u3001\u60c5\u611f\u63a7\u5236\u3001\u81ea\u7136\u8bed\u8a00\u6307\u4ee4\u3001\u7cbe\u786e\u65f6\u957f\u63a7\u5236\n- **\u9002\u7528**: \u4e13\u4e1a\u5e94\u7528\u3001\u60c5\u611f\u8bed\u97f3\u3001\u5185\u5bb9\u521b\u4f5c\u3001AI\u52a9\u624b\n\n### \ud83d\udc31 KittenTTS\n- **\u6587\u6863**: [src/funtts/tts/kitten/README.md](src/funtts/tts/kitten/README.md)\n- **\u7279\u70b9**: \u6df1\u5ea6\u5b66\u4e60\u3001\u9ad8\u8d28\u91cf\u3001\u795e\u7ecf\u7f51\u7edc\u3001\u591a\u8bed\u97f3\u98ce\u683c\n- **\u9002\u7528**: \u9ad8\u8d28\u91cf\u8bed\u97f3\u9700\u6c42\u3001AI\u5e94\u7528\u3001\u5185\u5bb9\u521b\u4f5c\n\n### \ud83d\udd0a eSpeak TTS\n- **\u6587\u6863**: [src/funtts/tts/espeak/README.md](src/funtts/tts/espeak/README.md)\n- **\u7279\u70b9**: \u8f7b\u91cf\u7ea7\u3001\u5f00\u6e90\u3001\u591a\u8bed\u8a00\n- **\u9002\u7528**: Linux\u73af\u5883\u3001\u5d4c\u5165\u5f0f\u7cfb\u7edf\u3001\u8d44\u6e90\u53d7\u9650\u573a\u666f\n\n### \ud83d\udda5\ufe0f Pyttsx3 TTS\n- **\u6587\u6863**: [src/funtts/tts/pyttsx3/README.md](src/funtts/tts/pyttsx3/README.md)\n- **\u7279\u70b9**: \u8de8\u5e73\u53f0\u3001\u672c\u5730\u79bb\u7ebf\u3001\u7cfb\u7edf\u96c6\u6210\n- **\u9002\u7528**: \u684c\u9762\u5e94\u7528\u3001\u79bb\u7ebf\u73af\u5883\u3001\u5feb\u901f\u539f\u578b\n\n> \ud83d\udccb **\u5f00\u53d1\u89c4\u8303**: \u67e5\u770b [docs/ENGINE_DEVELOPMENT_GUIDE.md](docs/ENGINE_DEVELOPMENT_GUIDE.md) \u4e86\u89e3\u5982\u4f55\u5f00\u53d1\u65b0\u7684TTS\u5f15\u64ce\u3002\n\n## \ud83d\udee0\ufe0f \u5f00\u53d1\u6307\u5357\n\n### \u6dfb\u52a0\u65b0\u7684TTS\u5f15\u64ce\n\n1. \u7ee7\u627f `BaseTTS` \u57fa\u7c7b\n2. \u5b9e\u73b0\u5fc5\u8981\u7684\u62bd\u8c61\u65b9\u6cd5\n3. \u5728\u5de5\u5382\u7c7b\u4e2d\u6ce8\u518c\u65b0\u5f15\u64ce\n\n```python\nfrom funtts.base import BaseTTS\nfrom funtts import TTSFactory, TTSRequest, TTSResponse\nfrom funtts.models import VoiceInfo\nfrom typing import List\n\nclass MyCustomTTS(BaseTTS):\n    \"\"\"\u81ea\u5b9a\u4e49TTS\u5f15\u64ce\u793a\u4f8b\"\"\"\n    \n    def synthesize(self, request: TTSRequest) -> TTSResponse:\n        \"\"\"\u5b9e\u73b0\u8bed\u97f3\u5408\u6210\"\"\"\n        try:\n            # \u8fd9\u91cc\u5b9e\u73b0\u4f60\u7684TTS\u903b\u8f91\n            print(f\"CustomTTS: \u6b63\u5728\u5408\u6210 '{request.text[:20]}...'\")\n            \n            # \u521b\u5efa\u793a\u4f8b\u97f3\u9891\u6587\u4ef6\n            with open(request.output_file, 'wb') as f:\n                f.write(b'\\x00' * 1024)  # \u793a\u4f8b\u6570\u636e\n            \n            return TTSResponse(\n                success=True,\n                request=request,\n                audio_file=request.output_file,\n                duration=2.0,\n                voice_used=\"custom_voice\",\n                engine_info={\"engine\": \"custom\", \"version\": \"1.0\"}\n            )\n        except Exception as e:\n            return TTSResponse(\n                success=False,\n                request=request,\n                error_message=str(e)\n            )\n    \n    def list_voices(self, language: str = None) -> List[VoiceInfo]:\n        \"\"\"\u8fd4\u56de\u53ef\u7528\u8bed\u97f3\u5217\u8868\"\"\"\n        return [\n            VoiceInfo(\n                name=\"custom_voice_1\",\n                display_name=\"\u81ea\u5b9a\u4e49\u8bed\u97f31\",\n                language=\"zh-CN\",\n                gender=\"female\",\n                engine=\"custom\"\n            )\n        ]\n    \n    def is_voice_available(self, voice_name: str) -> bool:\n        \"\"\"\u68c0\u67e5\u8bed\u97f3\u662f\u5426\u53ef\u7528\"\"\"\n        return voice_name == \"custom_voice_1\"\n\n# \u6ce8\u518c\u65b0\u5f15\u64ce\nTTSFactory.register_engine(\"mycustom\", MyCustomTTS)\n\n# \u4f7f\u7528\u81ea\u5b9a\u4e49\u5f15\u64ce\ncustom_tts = TTSFactory.create_tts(\"mycustom\", \"custom_voice_1\")\n```\n\n### \u9879\u76ee\u6784\u5efa\n\n```bash\n# \u514b\u9686\u9879\u76ee\ngit clone https://github.com/farfarfun/funtts.git\ncd funtts\n\n# \u5b89\u88c5\u5f00\u53d1\u4f9d\u8d56\npip install -e .[all]\n\n# \u8fd0\u884c\u6d4b\u8bd5\npython -m pytest tests/\n\n# \u4ee3\u7801\u683c\u5f0f\u5316\nblack src/\nisort src/\n\n# \u7c7b\u578b\u68c0\u67e5\nmypy src/\n```\n\n## \ud83e\udd1d \u8d21\u732e\u6307\u5357\n\n\u6211\u4eec\u6b22\u8fce\u5404\u79cd\u5f62\u5f0f\u7684\u8d21\u732e\uff01\n\n### \u5982\u4f55\u8d21\u732e\n\n1. **Fork** \u672c\u4ed3\u5e93\n2. **\u521b\u5efa** \u529f\u80fd\u5206\u652f (`git checkout -b feature/AmazingFeature`)\n3. **\u63d0\u4ea4** \u66f4\u6539 (`git commit -m 'Add some AmazingFeature'`)\n4. **\u63a8\u9001** \u5230\u5206\u652f (`git push origin feature/AmazingFeature`)\n5. **\u6253\u5f00** Pull Request\n\n### \u8d21\u732e\u7c7b\u578b\n\n- \ud83d\udc1b **Bug\u4fee\u590d**: \u4fee\u590d\u5df2\u77e5\u95ee\u9898\n- \u2728 **\u65b0\u529f\u80fd**: \u6dfb\u52a0\u65b0\u7684TTS\u5f15\u64ce\u6216\u529f\u80fd\n- \ud83d\udcda **\u6587\u6863**: \u6539\u8fdb\u6587\u6863\u548c\u793a\u4f8b\n- \ud83c\udfa8 **\u4f18\u5316**: \u4ee3\u7801\u91cd\u6784\u548c\u6027\u80fd\u4f18\u5316\n- \ud83e\uddea **\u6d4b\u8bd5**: \u6dfb\u52a0\u6216\u6539\u8fdb\u6d4b\u8bd5\u7528\u4f8b\n\n### \u5f00\u53d1\u89c4\u8303\n\n- \u9075\u5faaPEP 8\u4ee3\u7801\u89c4\u8303\n- \u6dfb\u52a0\u9002\u5f53\u7684\u7c7b\u578b\u6ce8\u89e3\n- \u7f16\u5199\u6e05\u6670\u7684\u6587\u6863\u5b57\u7b26\u4e32\n- \u4e3a\u65b0\u529f\u80fd\u6dfb\u52a0\u6d4b\u8bd5\u7528\u4f8b\n- \u66f4\u65b0\u76f8\u5173\u6587\u6863\n\n## \ud83d\udcc4 \u8bb8\u53ef\u8bc1\n\n\u672c\u9879\u76ee\u91c7\u7528 [MIT License](LICENSE) \u8bb8\u53ef\u8bc1\u3002\n\n## \ud83d\ude4f \u81f4\u8c22\n\n\u611f\u8c22\u4ee5\u4e0b\u5f00\u6e90\u9879\u76ee\u7684\u652f\u6301\uff1a\n\n- [edge-tts](https://github.com/rany2/edge-tts) - Microsoft Edge\u7684\u6587\u672c\u8f6c\u8bed\u97f3\n- [Azure Cognitive Services](https://azure.microsoft.com/services/cognitive-services/) - \u5fae\u8f6fAzure TTS\u670d\u52a1\n- [eSpeak](http://espeak.sourceforge.net/) - \u5f00\u6e90\u8bed\u97f3\u5408\u6210\u5668\n- [pyttsx3](https://github.com/nateshmbhat/pyttsx3) - Python\u6587\u672c\u8f6c\u8bed\u97f3\u5e93\n- [pydub](https://github.com/jiaaro/pydub) - \u97f3\u9891\u5904\u7406\u5e93\n\n## \ud83d\udcde \u8054\u7cfb\u6211\u4eec\n\n- **GitHub Issues**: [\u63d0\u4ea4\u95ee\u9898](https://github.com/farfarfun/funtts/issues)\n- **GitHub Discussions**: [\u53c2\u4e0e\u8ba8\u8bba](https://github.com/farfarfun/funtts/discussions)\n- **Email**: farfarfun@qq.com\n\n---\n\n<div align=\"center\">\n\n**\u5982\u679c\u8fd9\u4e2a\u9879\u76ee\u5bf9\u4f60\u6709\u5e2e\u52a9\uff0c\u8bf7\u7ed9\u6211\u4eec\u4e00\u4e2a \u2b50 Star\uff01**\n\nMade with \u2764\ufe0f by [FarFarFun Team](https://github.com/farfarfun)\n\n</div>\n",
    "bugtrack_url": null,
    "license": "MIT",
    "summary": "\u7edf\u4e00\u7684\u6587\u672c\u8f6c\u8bed\u97f3(TTS)\u5de5\u5177\u5e93\uff0c\u652f\u6301\u591a\u79cd\u5f00\u6e90TTS\u5f15\u64ce\u548c\u5b57\u5e55\u683c\u5f0f",
    "version": "0.1.10",
    "project_urls": {
        "Organization": "https://github.com/farfarfun",
        "Releases": "https://github.com/farfarfun/funtts/releases",
        "Repository": "https://github.com/farfarfun/funtts"
    },
    "split_keywords": [
        "tts",
        " text-to-speech",
        " audio",
        " subtitle",
        " speech-synthesis"
    ],
    "urls": [
        {
            "comment_text": null,
            "digests": {
                "blake2b_256": "e8efcda35be6801b68f90c7196f92c6c2859c1d7ce3b214077c54df64dbc3b9e",
                "md5": "9f97f7ef18fe84e0a54fb9c7f37af58e",
                "sha256": "a58e10a345ad46e6b991efced4f1b178f7a378e0422e3cf2437396891ffb09a6"
            },
            "downloads": -1,
            "filename": "funtts_plus-0.1.10-py3-none-any.whl",
            "has_sig": false,
            "md5_digest": "9f97f7ef18fe84e0a54fb9c7f37af58e",
            "packagetype": "bdist_wheel",
            "python_version": "py3",
            "requires_python": ">=3.8",
            "size": 71368,
            "upload_time": "2025-09-19T00:36:12",
            "upload_time_iso_8601": "2025-09-19T00:36:12.300549Z",
            "url": "https://files.pythonhosted.org/packages/e8/ef/cda35be6801b68f90c7196f92c6c2859c1d7ce3b214077c54df64dbc3b9e/funtts_plus-0.1.10-py3-none-any.whl",
            "yanked": false,
            "yanked_reason": null
        }
    ],
    "upload_time": "2025-09-19 00:36:12",
    "github": true,
    "gitlab": false,
    "bitbucket": false,
    "codeberg": false,
    "github_user": "farfarfun",
    "github_project": "funtts",
    "travis_ci": false,
    "coveralls": false,
    "github_actions": false,
    "lcname": "funtts-plus"
}
        
Elapsed time: 1.14255s