142 lines
5.9 KiB
HTML
142 lines
5.9 KiB
HTML
|
|
<!DOCTYPE html>
|
|||
|
|
<html lang="zh-CN">
|
|||
|
|
<head>
|
|||
|
|
<meta charset="UTF-8">
|
|||
|
|
<meta name="viewport" content="width=device-width,initial-scale=1.0">
|
|||
|
|
<title>之秋 · AI 真人短剧工坊</title>
|
|||
|
|
<style>
|
|||
|
|
*{margin:0;padding:0;box-sizing:border-box}
|
|||
|
|
body{font-family:-apple-system,'PingFang SC','Microsoft YaHei',sans-serif;background:#f5f0eb;color:#2c2c2c;min-height:100vh}
|
|||
|
|
.container{max-width:900px;margin:0 auto;padding:20px}
|
|||
|
|
.header{text-align:center;padding:40px 0 20px}
|
|||
|
|
.header h1{font-size:28px;font-weight:600;letter-spacing:2px}
|
|||
|
|
.header p{color:#888;margin-top:6px;font-size:14px}
|
|||
|
|
.modes{display:flex;gap:10px;margin:20px 0}
|
|||
|
|
.mode-btn{flex:1;padding:14px;border:2px solid #ddd;border-radius:12px;background:#fff;cursor:pointer;text-align:center;transition:all .2s;font-size:14px}
|
|||
|
|
.mode-btn:hover{border-color:#c8a882}
|
|||
|
|
.mode-btn.active{border-color:#b8916e;background:#faf5ef;font-weight:600}
|
|||
|
|
.mode-btn .icon{font-size:22px;display:block;margin-bottom:4px}
|
|||
|
|
.mode-btn .desc{font-size:12px;color:#999;margin-top:4px}
|
|||
|
|
.input-area{background:#fff;border-radius:12px;padding:20px;box-shadow:0 2px 8px rgba(0,0,0,.06)}
|
|||
|
|
.input-area textarea{width:100%;min-height:120px;border:1px solid #e0ddd8;border-radius:8px;padding:12px;font-size:14px;line-height:1.6;resize:vertical;font-family:inherit}
|
|||
|
|
.input-area textarea:focus{outline:none;border-color:#b8916e}
|
|||
|
|
.btn-row{display:flex;gap:10px;margin-top:12px}
|
|||
|
|
.btn-gen{flex:1;padding:12px;background:#b8916e;color:#fff;border:none;border-radius:8px;font-size:15px;cursor:pointer;transition:background .2s}
|
|||
|
|
.btn-gen:hover{background:#a07d5c}
|
|||
|
|
.btn-gen:disabled{background:#ccc;cursor:not-allowed}
|
|||
|
|
.btn-clear{padding:12px 20px;background:#f0ece6;border:1px solid #ddd;border-radius:8px;cursor:pointer;color:#666}
|
|||
|
|
.loading{display:none;text-align:center;padding:30px 0;color:#b8916e}
|
|||
|
|
.loading.show{display:block}
|
|||
|
|
.loading .spinner{display:inline-block;width:20px;height:20px;border:2px solid #e0ddd8;border-top-color:#b8916e;border-radius:50%;animation:spin .8s linear infinite;margin-right:8px;vertical-align:middle}
|
|||
|
|
@keyframes spin{to{transform:rotate(360deg)}}
|
|||
|
|
.result{display:none;background:#fff;border-radius:12px;padding:24px;margin-top:16px;box-shadow:0 2px 8px rgba(0,0,0,.06);white-space:pre-wrap;line-height:1.8;font-size:14px}
|
|||
|
|
.result.show{display:block}
|
|||
|
|
.result .meta{color:#999;font-size:12px;margin-bottom:10px;padding-bottom:10px;border-bottom:1px solid #f0ece6}
|
|||
|
|
.hint{text-align:center;color:#bbb;font-size:13px;margin-top:40px;padding-bottom:20px}
|
|||
|
|
</style>
|
|||
|
|
</head>
|
|||
|
|
<body>
|
|||
|
|
|
|||
|
|
<div class="container">
|
|||
|
|
<div class="header">
|
|||
|
|
<h1>🎬 之秋 · 真人短剧工坊</h1>
|
|||
|
|
<p>AI 帮你写剧本 · 三种创作模式</p>
|
|||
|
|
</div>
|
|||
|
|
|
|||
|
|
<div class="modes" id="modeSelector">
|
|||
|
|
<div class="mode-btn active" data-mode="auto">
|
|||
|
|
<span class="icon">🤖</span>
|
|||
|
|
AI 全自动
|
|||
|
|
<div class="desc">给主题,出完整剧本</div>
|
|||
|
|
</div>
|
|||
|
|
<div class="mode-btn" data-mode="assist">
|
|||
|
|
<span class="icon">💡</span>
|
|||
|
|
想法辅助
|
|||
|
|
<div class="desc">你提想法,AI 展开</div>
|
|||
|
|
</div>
|
|||
|
|
<div class="mode-btn" data-mode="polish">
|
|||
|
|
<span class="icon">✨</span>
|
|||
|
|
AI 润色
|
|||
|
|
<div class="desc">已有草稿,优化提升</div>
|
|||
|
|
</div>
|
|||
|
|
</div>
|
|||
|
|
|
|||
|
|
<div class="input-area">
|
|||
|
|
<textarea id="inputText" placeholder="请输入…… 例如:都市爱情,追妻火葬场,女主是咖啡店主理人" rows="5"></textarea>
|
|||
|
|
<div class="btn-row">
|
|||
|
|
<button class="btn-gen" id="btnGen">🎬 生成剧本</button>
|
|||
|
|
<button class="btn-clear" id="btnClear">清空</button>
|
|||
|
|
</div>
|
|||
|
|
</div>
|
|||
|
|
|
|||
|
|
<div class="loading" id="loading">
|
|||
|
|
<span class="spinner"></span>AI 正在创作中,请稍候…
|
|||
|
|
</div>
|
|||
|
|
|
|||
|
|
<div class="result" id="result">
|
|||
|
|
<div class="meta">✍️ 生成完毕</div>
|
|||
|
|
<div id="resultContent"></div>
|
|||
|
|
</div>
|
|||
|
|
|
|||
|
|
<div class="hint">生成内容由 AI 创作 · 仅供参考</div>
|
|||
|
|
</div>
|
|||
|
|
|
|||
|
|
<script>
|
|||
|
|
const modeBtns = document.querySelectorAll('.mode-btn');
|
|||
|
|
let currentMode = 'auto';
|
|||
|
|
|
|||
|
|
modeBtns.forEach(btn => {
|
|||
|
|
btn.addEventListener('click', () => {
|
|||
|
|
modeBtns.forEach(b => b.classList.remove('active'));
|
|||
|
|
btn.classList.add('active');
|
|||
|
|
currentMode = btn.dataset.mode;
|
|||
|
|
// 根据模式调整 placeholder
|
|||
|
|
const ta = document.getElementById('inputText');
|
|||
|
|
if (currentMode === 'auto') ta.placeholder = '请输入主题……\n\n例如:都市爱情,追妻火葬场,女主是咖啡店主理人';
|
|||
|
|
else if (currentMode === 'assist') ta.placeholder = '请输入你的想法……\n\n例如:女主是咖啡店主理人,偶遇前男友,两人在店里有一场对话';
|
|||
|
|
else ta.placeholder = '粘贴你的剧本草稿……\n\nAI 会润色优化,不改核心情节';
|
|||
|
|
});
|
|||
|
|
});
|
|||
|
|
|
|||
|
|
document.getElementById('btnClear').addEventListener('click', () => {
|
|||
|
|
document.getElementById('inputText').value = '';
|
|||
|
|
document.getElementById('result').classList.remove('show');
|
|||
|
|
});
|
|||
|
|
|
|||
|
|
document.getElementById('btnGen').addEventListener('click', async () => {
|
|||
|
|
const input = document.getElementById('inputText').value.trim();
|
|||
|
|
if (!input) { alert('请先输入内容'); return; }
|
|||
|
|
|
|||
|
|
const btn = document.getElementById('btnGen');
|
|||
|
|
const loading = document.getElementById('loading');
|
|||
|
|
const result = document.getElementById('result');
|
|||
|
|
const content = document.getElementById('resultContent');
|
|||
|
|
|
|||
|
|
btn.disabled = true;
|
|||
|
|
loading.classList.add('show');
|
|||
|
|
result.classList.remove('show');
|
|||
|
|
|
|||
|
|
try {
|
|||
|
|
const res = await fetch('api/generate', {
|
|||
|
|
method: 'POST',
|
|||
|
|
headers: { 'Content-Type': 'application/json' },
|
|||
|
|
body: JSON.stringify({ mode: currentMode, input })
|
|||
|
|
});
|
|||
|
|
const data = await res.json();
|
|||
|
|
if (data.success) {
|
|||
|
|
content.textContent = data.content;
|
|||
|
|
result.classList.add('show');
|
|||
|
|
} else {
|
|||
|
|
alert('生成失败:' + (data.error || '未知错误'));
|
|||
|
|
}
|
|||
|
|
} catch (e) {
|
|||
|
|
alert('网络错误:' + e.message);
|
|||
|
|
} finally {
|
|||
|
|
btn.disabled = false;
|
|||
|
|
loading.classList.remove('show');
|
|||
|
|
}
|
|||
|
|
});
|
|||
|
|
</script>
|
|||
|
|
</body>
|
|||
|
|
</html>
|