454 lines
		
	
	
		
			23 KiB
		
	
	
	
		
			HTML
		
	
	
	
	
	
			
		
		
	
	
			454 lines
		
	
	
		
			23 KiB
		
	
	
	
		
			HTML
		
	
	
	
	
	
{% extends "base.html" %}
 | 
						||
 | 
						||
{% block title %}语音克隆测试 - 儿童语言学习系统{% endblock %}
 | 
						||
 | 
						||
{% block content %}
 | 
						||
<div class="container py-4">
 | 
						||
    <!-- 页面标题 -->
 | 
						||
    <div class="row mb-4">
 | 
						||
        <div class="col-12">
 | 
						||
            <div class="d-flex align-items-center">
 | 
						||
                <a href="{{ url_for('main.dashboard') }}" class="btn btn-outline-secondary me-3">
 | 
						||
                    <i class="fas fa-arrow-left me-2"></i>返回主页
 | 
						||
                </a>
 | 
						||
                <div>
 | 
						||
                    <h2 class="fw-bold mb-1">
 | 
						||
                        <i class="fas fa-magic text-primary me-2"></i>
 | 
						||
                        语音克隆技术测试
 | 
						||
                    </h2>
 | 
						||
                    <p class="text-muted mb-0">体验"听自己说"的神奇技术 - 让AI学会你的声音</p>
 | 
						||
                </div>
 | 
						||
            </div>
 | 
						||
        </div>
 | 
						||
    </div>
 | 
						||
 | 
						||
    <!-- 连接状态检测 -->
 | 
						||
    <div class="row mb-4">
 | 
						||
        <div class="col-12">
 | 
						||
            <div class="card border-0 shadow-sm">
 | 
						||
                <div class="card-body">
 | 
						||
                    <h5 class="card-title">
 | 
						||
                        <i class="fas fa-plug me-2"></i>服务连接状态
 | 
						||
                    </h5>
 | 
						||
                    <div class="d-flex align-items-center">
 | 
						||
                        <button id="test-connection-btn" class="btn btn-primary me-3">
 | 
						||
                            <i class="fas fa-wifi me-2"></i>测试连接
 | 
						||
                        </button>
 | 
						||
                        <div id="connection-status" class="flex-grow-1">
 | 
						||
                            <span class="text-muted">点击测试连接按钮检查服务状态</span>
 | 
						||
                        </div>
 | 
						||
                    </div>
 | 
						||
                </div>
 | 
						||
            </div>
 | 
						||
        </div>
 | 
						||
    </div>
 | 
						||
 | 
						||
    <!-- 核心功能:语音克隆工作流程 -->
 | 
						||
    <div class="row mb-4">
 | 
						||
        <div class="col-12">
 | 
						||
            <div class="card border-0 shadow-sm border-primary" style="border-width: 2px !important;">
 | 
						||
                <div class="card-body">
 | 
						||
                    <h4 class="card-title text-primary">
 | 
						||
                        <i class="fas fa-clone me-2"></i>语音克隆工作流程
 | 
						||
                        <span class="badge bg-primary ms-2">核心功能</span>
 | 
						||
                    </h4>
 | 
						||
                    <p class="text-muted mb-4">按照步骤操作,体验完整的语音克隆过程</p>
 | 
						||
 | 
						||
                    <!-- 步骤指示器 -->
 | 
						||
                    <div class="row mb-4">
 | 
						||
                        <div class="col-12">
 | 
						||
                            <div class="d-flex justify-content-between position-relative">
 | 
						||
                                <div class="step-indicator active" id="step-1-indicator">
 | 
						||
                                    <div class="step-circle">1</div>
 | 
						||
                                    <div class="step-label">录制声音</div>
 | 
						||
                                </div>
 | 
						||
                                <div class="step-line"></div>
 | 
						||
                                <div class="step-indicator" id="step-2-indicator">
 | 
						||
                                    <div class="step-circle">2</div>
 | 
						||
                                    <div class="step-label">识别文字</div>
 | 
						||
                                </div>
 | 
						||
                                <div class="step-line"></div>
 | 
						||
                                <div class="step-indicator" id="step-3-indicator">
 | 
						||
                                    <div class="step-circle">3</div>
 | 
						||
                                    <div class="step-label">克隆生成</div>
 | 
						||
                                </div>
 | 
						||
                                <div class="step-line"></div>
 | 
						||
                                <div class="step-indicator" id="step-4-indicator">
 | 
						||
                                    <div class="step-circle">4</div>
 | 
						||
                                    <div class="step-label">效果对比</div>
 | 
						||
                                </div>
 | 
						||
                            </div>
 | 
						||
                        </div>
 | 
						||
                    </div>
 | 
						||
 | 
						||
                    <div class="row">
 | 
						||
                        <!-- 步骤1:语音样本采集 -->
 | 
						||
                        <div class="col-lg-6 mb-4">
 | 
						||
                            <div class="step-content" id="step-1-content">
 | 
						||
                                <h5 class="text-success">
 | 
						||
                                    <i class="fas fa-microphone me-2"></i>步骤1:录制你的声音样本
 | 
						||
                                </h5>
 | 
						||
                                <p class="text-muted">录制一段3-10秒的清晰语音,作为语音克隆的模板</p>
 | 
						||
                                
 | 
						||
                                <form id="voice-sample-form" enctype="multipart/form-data">
 | 
						||
                                    <div class="mb-3">
 | 
						||
                                        <label class="form-label">方式一:上传音频文件</label>
 | 
						||
                                        <input type="file" class="form-control" id="voice-sample-upload" 
 | 
						||
                                               accept=".wav,.mp3,.m4a,.flac">
 | 
						||
                                        <div class="form-text">建议:WAV格式,16kHz采样率,3-10秒时长</div>
 | 
						||
                                    </div>
 | 
						||
                                    
 | 
						||
                                    <div class="mb-3 text-center">
 | 
						||
                                        <span class="text-muted">或</span>
 | 
						||
                                    </div>
 | 
						||
                                    
 | 
						||
                                    <div class="mb-3">
 | 
						||
                                        <label class="form-label">方式二:在线录音</label>
 | 
						||
                                        <div class="text-center">
 | 
						||
                                            <button type="button" id="start-recording" class="btn btn-danger me-2">
 | 
						||
                                                <i class="fas fa-record-vinyl me-2"></i>开始录音
 | 
						||
                                            </button>
 | 
						||
                                            <button type="button" id="stop-recording" class="btn btn-secondary" disabled>
 | 
						||
                                                <i class="fas fa-stop me-2"></i>停止录音
 | 
						||
                                            </button>
 | 
						||
                                            <div class="mt-2">
 | 
						||
                                                <small id="recording-status" class="text-muted">点击开始录音</small>
 | 
						||
                                            </div>
 | 
						||
                                        </div>
 | 
						||
                                    </div>
 | 
						||
                                    
 | 
						||
                                    <button type="submit" class="btn btn-success w-100" disabled id="upload-sample-btn">
 | 
						||
                                        <i class="fas fa-upload me-2"></i>上传语音样本
 | 
						||
                                    </button>
 | 
						||
                                </form>
 | 
						||
 | 
						||
                                <!-- 样本播放区域 -->
 | 
						||
                                <div id="sample-player" class="mt-3" style="display: none;">
 | 
						||
                                    <div class="alert alert-info">
 | 
						||
                                        <h6><i class="fas fa-headphones me-2"></i>你的语音样本:</h6>
 | 
						||
                                        <audio controls class="w-100 mt-2" id="sample-audio">
 | 
						||
                                            <source id="sample-audio-source" type="audio/wav">
 | 
						||
                                        </audio>
 | 
						||
                                    </div>
 | 
						||
                                </div>
 | 
						||
                            </div>
 | 
						||
                        </div>
 | 
						||
 | 
						||
                        <!-- 步骤2:语音识别 -->
 | 
						||
                        <div class="col-lg-6 mb-4">
 | 
						||
                            <div class="step-content" id="step-2-content">
 | 
						||
                                <h5 class="text-info">
 | 
						||
                                    <i class="fas fa-text-width me-2"></i>步骤2:语音识别结果
 | 
						||
                                </h5>
 | 
						||
                                <p class="text-muted">AI识别出你说的内容,这将用于语音克隆训练</p>
 | 
						||
                                
 | 
						||
                                <div id="recognition-result" style="display: none;">
 | 
						||
                                    <div class="mb-3">
 | 
						||
                                        <label class="form-label">识别的文本内容:</label>
 | 
						||
                                        <textarea class="form-control" id="recognized-text" rows="3" 
 | 
						||
                                                  placeholder="语音识别结果将显示在这里..."></textarea>
 | 
						||
                                        <div class="form-text">你可以手动修正识别错误的文字</div>
 | 
						||
                                    </div>
 | 
						||
                                    
 | 
						||
                                    <div class="d-flex justify-content-between">
 | 
						||
                                        <small class="text-success">
 | 
						||
                                            <i class="fas fa-check-circle me-1"></i>识别完成
 | 
						||
                                        </small>
 | 
						||
                                        <button class="btn btn-outline-primary btn-sm" onclick="goToStep(3)">
 | 
						||
                                            下一步:克隆生成 <i class="fas fa-arrow-right ms-1"></i>
 | 
						||
                                        </button>
 | 
						||
                                    </div>
 | 
						||
                                </div>
 | 
						||
                                
 | 
						||
                                <div id="recognition-waiting" class="text-center text-muted">
 | 
						||
                                    <i class="fas fa-clock fa-2x mb-2"></i>
 | 
						||
                                    <p>等待上传语音样本...</p>
 | 
						||
                                </div>
 | 
						||
                            </div>
 | 
						||
                        </div>
 | 
						||
 | 
						||
                        <!-- 步骤3:语音克隆生成 -->
 | 
						||
                        <div class="col-lg-6 mb-4">
 | 
						||
                            <div class="step-content" id="step-3-content">
 | 
						||
                                <h5 class="text-warning">
 | 
						||
                                    <i class="fas fa-magic me-2"></i>步骤3:克隆你的声音
 | 
						||
                                </h5>
 | 
						||
                                <p class="text-muted">让AI用你的声音说新的话</p>
 | 
						||
                                
 | 
						||
                                <form id="clone-generation-form">
 | 
						||
                                    <div class="mb-3">
 | 
						||
                                        <label class="form-label">想让AI用你的声音说什么?</label>
 | 
						||
                                        <textarea class="form-control" id="clone-text" rows="3" 
 | 
						||
                                                  placeholder="例如:你好,我是AI克隆的声音,听起来像真的一样!">你好,我是AI克隆的声音,听起来像真的一样!</textarea>
 | 
						||
                                    </div>
 | 
						||
                                    
 | 
						||
                                    <div class="row mb-3">
 | 
						||
                                        <div class="col-6">
 | 
						||
                                            <label class="form-label">随机种子</label>
 | 
						||
                                            <div class="input-group">
 | 
						||
                                                <input type="number" class="form-control" id="clone-seed" value="42">
 | 
						||
                                                <button type="button" class="btn btn-outline-secondary" id="clone-random-seed">
 | 
						||
                                                    <i class="fas fa-dice"></i>
 | 
						||
                                                </button>
 | 
						||
                                            </div>
 | 
						||
                                        </div>
 | 
						||
                                        <div class="col-6">
 | 
						||
                                            <label class="form-label">克隆质量</label>
 | 
						||
                                            <select class="form-select">
 | 
						||
                                                <option>高质量(推荐)</option>
 | 
						||
                                            </select>
 | 
						||
                                        </div>
 | 
						||
                                    </div>
 | 
						||
                                    
 | 
						||
                                    <button type="submit" class="btn btn-warning w-100" disabled id="generate-clone-btn">
 | 
						||
                                        <i class="fas fa-magic me-2"></i>生成克隆语音
 | 
						||
                                    </button>
 | 
						||
                                </form>
 | 
						||
                            </div>
 | 
						||
                        </div>
 | 
						||
 | 
						||
                        <!-- 步骤4:效果对比 -->
 | 
						||
                        <div class="col-lg-6 mb-4">
 | 
						||
                            <div class="step-content" id="step-4-content">
 | 
						||
                                <h5 class="text-success">
 | 
						||
                                    <i class="fas fa-balance-scale me-2"></i>步骤4:效果对比
 | 
						||
                                </h5>
 | 
						||
                                <p class="text-muted">对比原声和克隆声音的效果</p>
 | 
						||
                                
 | 
						||
                                <div id="comparison-result" style="display: none;">
 | 
						||
                                    <div class="row">
 | 
						||
                                        <div class="col-6">
 | 
						||
                                            <h6><i class="fas fa-user me-2"></i>原声样本</h6>
 | 
						||
                                            <audio controls class="w-100" id="original-audio">
 | 
						||
                                                <source id="original-audio-source" type="audio/wav">
 | 
						||
                                            </audio>
 | 
						||
                                            <small class="text-muted">你录制的原始声音</small>
 | 
						||
                                        </div>
 | 
						||
                                        <div class="col-6">
 | 
						||
                                            <h6><i class="fas fa-robot me-2"></i>克隆声音</h6>
 | 
						||
                                            <audio controls class="w-100" id="cloned-audio">
 | 
						||
                                                <source id="cloned-audio-source" type="audio/wav">
 | 
						||
                                            </audio>
 | 
						||
                                            <small class="text-muted">AI克隆的声音</small>
 | 
						||
                                        </div>
 | 
						||
                                    </div>
 | 
						||
                                    
 | 
						||
                                    <div class="mt-3 p-3 bg-light rounded">
 | 
						||
                                        <h6><i class="fas fa-star me-2"></i>给克隆效果打分:</h6>
 | 
						||
                                        <div class="btn-group" role="group">
 | 
						||
                                            <input type="radio" class="btn-check" name="rating" id="rating1">
 | 
						||
                                            <label class="btn btn-outline-warning" for="rating1">1★</label>
 | 
						||
                                            <input type="radio" class="btn-check" name="rating" id="rating2">
 | 
						||
                                            <label class="btn btn-outline-warning" for="rating2">2★</label>
 | 
						||
                                            <input type="radio" class="btn-check" name="rating" id="rating3">
 | 
						||
                                            <label class="btn btn-outline-warning" for="rating3">3★</label>
 | 
						||
                                            <input type="radio" class="btn-check" name="rating" id="rating4">
 | 
						||
                                            <label class="btn btn-outline-warning" for="rating4">4★</label>
 | 
						||
                                            <input type="radio" class="btn-check" name="rating" id="rating5">
 | 
						||
                                            <label class="btn btn-outline-warning" for="rating5">5★</label>
 | 
						||
                                        </div>
 | 
						||
                                    </div>
 | 
						||
                                </div>
 | 
						||
                                
 | 
						||
                                <div id="comparison-waiting" class="text-center text-muted">
 | 
						||
                                    <i class="fas fa-hourglass-half fa-2x mb-2"></i>
 | 
						||
                                    <p>等待生成克隆语音...</p>
 | 
						||
                                </div>
 | 
						||
                            </div>
 | 
						||
                        </div>
 | 
						||
                    </div>
 | 
						||
 | 
						||
                    <!-- 重新开始按钮 -->
 | 
						||
                    <div class="text-center mt-4">
 | 
						||
                        <button class="btn btn-outline-primary" onclick="resetWorkflow()">
 | 
						||
                            <i class="fas fa-redo me-2"></i>重新开始克隆流程
 | 
						||
                        </button>
 | 
						||
                    </div>
 | 
						||
                </div>
 | 
						||
            </div>
 | 
						||
        </div>
 | 
						||
    </div>
 | 
						||
 | 
						||
    <!-- 高级功能区域 -->
 | 
						||
    <div class="row mb-4">
 | 
						||
        <div class="col-12">
 | 
						||
            <div class="card border-0 shadow-sm">
 | 
						||
                <div class="card-body">
 | 
						||
                    <h5 class="card-title">
 | 
						||
                        <i class="fas fa-cogs me-2"></i>高级功能
 | 
						||
                        <button class="btn btn-outline-secondary btn-sm float-end" type="button" data-bs-toggle="collapse" data-bs-target="#advanced-features">
 | 
						||
                            <i class="fas fa-chevron-down"></i>
 | 
						||
                        </button>
 | 
						||
                    </h5>
 | 
						||
                    
 | 
						||
                    <div class="collapse" id="advanced-features">
 | 
						||
                        <div class="row">
 | 
						||
                            <!-- 预训练音色测试 -->
 | 
						||
                            <div class="col-lg-6 mb-4">
 | 
						||
                                <h6 class="text-secondary">预训练音色测试</h6>
 | 
						||
                                <form id="preset-voice-form">
 | 
						||
                                    <div class="mb-3">
 | 
						||
                                        <textarea class="form-control" id="preset-text" rows="2" 
 | 
						||
                                            placeholder="输入要转换成语音的文字...">今天天气真不错,适合出门散步。</textarea>
 | 
						||
                                    </div>
 | 
						||
                                    <div class="mb-3">
 | 
						||
                                        <select class="form-select" id="preset-voice">
 | 
						||
                                            <option value="中文女">中文女</option>
 | 
						||
                                        </select>
 | 
						||
                                    </div>
 | 
						||
                                    <button type="submit" class="btn btn-secondary btn-sm">
 | 
						||
                                        <i class="fas fa-play me-2"></i>生成语音
 | 
						||
                                    </button>
 | 
						||
                                </form>
 | 
						||
                                <div id="preset-result" class="mt-2" style="display: none;">
 | 
						||
                                    <audio controls class="w-100">
 | 
						||
                                        <source id="preset-audio-source" type="audio/wav">
 | 
						||
                                    </audio>
 | 
						||
                                </div>
 | 
						||
                            </div>
 | 
						||
 | 
						||
                            <!-- 自然语言控制测试 -->
 | 
						||
                            <div class="col-lg-6 mb-4">
 | 
						||
                                <h6 class="text-secondary">自然语言控制</h6>
 | 
						||
                                <form id="natural-control-form">
 | 
						||
                                    <div class="mb-3">
 | 
						||
                                        <textarea class="form-control" id="natural-text" rows="2" 
 | 
						||
                                            placeholder="输入要合成的文字...">这是自然语言控制测试。</textarea>
 | 
						||
                                    </div>
 | 
						||
                                    <div class="mb-3">
 | 
						||
                                        <input class="form-control" id="natural-instruction" 
 | 
						||
                                               placeholder="语音指令,如:请用温柔甜美的女声朗读" 
 | 
						||
                                               value="请用温柔甜美的女声朗读">
 | 
						||
                                    </div>
 | 
						||
                                    <button type="submit" class="btn btn-secondary btn-sm">
 | 
						||
                                        <i class="fas fa-magic me-2"></i>生成语音
 | 
						||
                                    </button>
 | 
						||
                                </form>
 | 
						||
                                <div id="natural-result" class="mt-2" style="display: none;">
 | 
						||
                                    <audio controls class="w-100">
 | 
						||
                                        <source id="natural-audio-source" type="audio/wav">
 | 
						||
                                    </audio>
 | 
						||
                                </div>
 | 
						||
                            </div>
 | 
						||
                        </div>
 | 
						||
                    </div>
 | 
						||
                </div>
 | 
						||
            </div>
 | 
						||
        </div>
 | 
						||
    </div>
 | 
						||
 | 
						||
    <!-- 操作日志 -->
 | 
						||
    <div class="row">
 | 
						||
        <div class="col-12">
 | 
						||
            <div class="card border-0 shadow-sm">
 | 
						||
                <div class="card-body">
 | 
						||
                    <h5 class="card-title">
 | 
						||
                        <i class="fas fa-history me-2"></i>操作日志
 | 
						||
                        <button class="btn btn-outline-secondary btn-sm float-end" id="clear-log">
 | 
						||
                            <i class="fas fa-trash me-1"></i>清空
 | 
						||
                        </button>
 | 
						||
                    </h5>
 | 
						||
                    <div id="test-log" class="border rounded p-3" style="height: 300px; overflow-y: auto; background-color: #f8f9fa;">
 | 
						||
                        <p class="text-muted">操作记录将显示在这里...</p>
 | 
						||
                    </div>
 | 
						||
                </div>
 | 
						||
            </div>
 | 
						||
        </div>
 | 
						||
    </div>
 | 
						||
</div>
 | 
						||
 | 
						||
<!-- Loading Modal -->
 | 
						||
<div class="modal fade" id="loadingModal" data-bs-backdrop="static" data-bs-keyboard="false" tabindex="-1">
 | 
						||
    <div class="modal-dialog modal-dialog-centered">
 | 
						||
        <div class="modal-content">
 | 
						||
            <div class="modal-body text-center py-4">
 | 
						||
                <div class="spinner-border text-primary mb-3" role="status"></div>
 | 
						||
                <h5 id="loading-message">正在处理中...</h5>
 | 
						||
                <p id="loading-detail" class="text-muted">请稍候...</p>
 | 
						||
            </div>
 | 
						||
        </div>
 | 
						||
    </div>
 | 
						||
</div>
 | 
						||
 | 
						||
<!-- 添加步骤指示器样式 -->
 | 
						||
<style>
 | 
						||
.step-indicator {
 | 
						||
    display: flex;
 | 
						||
    flex-direction: column;
 | 
						||
    align-items: center;
 | 
						||
    position: relative;
 | 
						||
    z-index: 2;
 | 
						||
}
 | 
						||
 | 
						||
.step-circle {
 | 
						||
    width: 40px;
 | 
						||
    height: 40px;
 | 
						||
    border-radius: 50%;
 | 
						||
    background-color: #e9ecef;
 | 
						||
    color: #6c757d;
 | 
						||
    display: flex;
 | 
						||
    align-items: center;
 | 
						||
    justify-content: center;
 | 
						||
    font-weight: bold;
 | 
						||
    margin-bottom: 8px;
 | 
						||
    transition: all 0.3s ease;
 | 
						||
}
 | 
						||
 | 
						||
.step-indicator.active .step-circle {
 | 
						||
    background-color: #0d6efd;
 | 
						||
    color: white;
 | 
						||
}
 | 
						||
 | 
						||
.step-indicator.completed .step-circle {
 | 
						||
    background-color: #198754;
 | 
						||
    color: white;
 | 
						||
}
 | 
						||
 | 
						||
.step-label {
 | 
						||
    font-size: 0.9rem;
 | 
						||
    text-align: center;
 | 
						||
    color: #6c757d;
 | 
						||
}
 | 
						||
 | 
						||
.step-indicator.active .step-label {
 | 
						||
    color: #0d6efd;
 | 
						||
    font-weight: 600;
 | 
						||
}
 | 
						||
 | 
						||
.step-indicator.completed .step-label {
 | 
						||
    color: #198754;
 | 
						||
    font-weight: 600;
 | 
						||
}
 | 
						||
 | 
						||
.step-line {
 | 
						||
    flex: 1;
 | 
						||
    height: 2px;
 | 
						||
    background-color: #e9ecef;
 | 
						||
    margin: 20px 0;
 | 
						||
    position: relative;
 | 
						||
    z-index: 1;
 | 
						||
}
 | 
						||
 | 
						||
.step-line.completed {
 | 
						||
    background-color: #198754;
 | 
						||
}
 | 
						||
 | 
						||
@media (max-width: 768px) {
 | 
						||
    .step-indicator {
 | 
						||
        flex-direction: row;
 | 
						||
        align-items: center;
 | 
						||
        margin-bottom: 10px;
 | 
						||
    }
 | 
						||
    
 | 
						||
    .step-circle {
 | 
						||
        margin-bottom: 0;
 | 
						||
        margin-right: 10px;
 | 
						||
    }
 | 
						||
}
 | 
						||
</style>
 | 
						||
{% endblock %}
 | 
						||
 | 
						||
{% block scripts %}
 | 
						||
<script src="{{ url_for('static', filename='js/voice_test.js') }}"></script>
 | 
						||
{% endblock %}
 |