283 lines
16 KiB
HTML
283 lines
16 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>图片生成器</title>
|
||
<link rel="stylesheet" href="style.css" />
|
||
</head>
|
||
<body>
|
||
|
||
<div id="app">
|
||
|
||
<!-- Header -->
|
||
<header>
|
||
<div class="logo">
|
||
<svg width="22" height="22" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round">
|
||
<rect x="3" y="3" width="18" height="18" rx="2"/>
|
||
<circle cx="8.5" cy="8.5" r="1.5"/>
|
||
<polyline points="21,15 16,10 5,21"/>
|
||
</svg>
|
||
<span>图片生成器</span>
|
||
</div>
|
||
<div class="header-right">
|
||
<div class="theme-switcher" id="themeSwitcher">
|
||
<button class="theme-btn active" data-theme="dark" title="深邃暗">
|
||
<svg width="14" height="14" viewBox="0 0 24 24" fill="currentColor"><path d="M21 12.79A9 9 0 1 1 11.21 3 7 7 0 0 0 21 12.79z"/></svg>
|
||
</button>
|
||
<button class="theme-btn" data-theme="light" title="纯净白">
|
||
<svg width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2"><circle cx="12" cy="12" r="5"/><line x1="12" y1="1" x2="12" y2="3"/><line x1="12" y1="21" x2="12" y2="23"/><line x1="4.22" y1="4.22" x2="5.64" y2="5.64"/><line x1="18.36" y1="18.36" x2="19.78" y2="19.78"/><line x1="1" y1="12" x2="3" y2="12"/><line x1="21" y1="12" x2="23" y2="12"/><line x1="4.22" y1="19.78" x2="5.64" y2="18.36"/><line x1="18.36" y1="5.64" x2="19.78" y2="4.22"/></svg>
|
||
</button>
|
||
<button class="theme-btn" data-theme="cyber" title="赛博朋克">
|
||
<svg width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2"><polygon points="13,2 3,14 12,14 11,22 21,10 12,10 13,2"/></svg>
|
||
</button>
|
||
<button class="theme-btn" data-theme="morandi" title="莫兰迪">
|
||
<svg width="14" height="14" viewBox="0 0 24 24" fill="currentColor"><circle cx="12" cy="12" r="10"/></svg>
|
||
</button>
|
||
<button class="theme-btn" data-theme="green" title="护眼绿">
|
||
<svg width="14" height="14" viewBox="0 0 24 24" fill="currentColor"><path d="M12 2C6.48 2 2 6.48 2 12s4.48 10 10 10 10-4.48 10-10S17.52 2 12 2zm-2 14.5v-9l6 4.5-6 4.5z"/></svg>
|
||
</button>
|
||
</div>
|
||
<button class="icon-btn" id="openSettings" title="设置">
|
||
<svg width="18" height="18" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round">
|
||
<circle cx="12" cy="12" r="3"/>
|
||
<path d="M19.4 15a1.65 1.65 0 0 0 .33 1.82l.06.06a2 2 0 0 1-2.83 2.83l-.06-.06a1.65 1.65 0 0 0-1.82-.33 1.65 1.65 0 0 0-1 1.51V21a2 2 0 0 1-4 0v-.09A1.65 1.65 0 0 0 9 19.4a1.65 1.65 0 0 0-1.82.33l-.06.06a2 2 0 0 1-2.83-2.83l.06-.06A1.65 1.65 0 0 0 4.68 15a1.65 1.65 0 0 0-1.51-1H3a2 2 0 0 1 0-4h.09A1.65 1.65 0 0 0 4.6 9a1.65 1.65 0 0 0-.33-1.82l-.06-.06a2 2 0 0 1 2.83-2.83l.06.06A1.65 1.65 0 0 0 9 4.68a1.65 1.65 0 0 0 1-1.51V3a2 2 0 0 1 4 0v.09a1.65 1.65 0 0 0 1 1.51 1.65 1.65 0 0 0 1.82-.33l.06-.06a2 2 0 0 1 2.83 2.83l-.06.06A1.65 1.65 0 0 0 19.4 9a1.65 1.65 0 0 0 1.51 1H21a2 2 0 0 1 0 4h-.09a1.65 1.65 0 0 0-1.51 1z"/>
|
||
</svg>
|
||
</button>
|
||
</div>
|
||
</header>
|
||
|
||
<!-- API Key Alert -->
|
||
<div class="alert-banner" id="apiKeyAlert" style="display:none">
|
||
<svg width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2"><circle cx="12" cy="12" r="10"/><line x1="12" y1="8" x2="12" y2="12"/><line x1="12" y1="16" x2="12.01" y2="16"/></svg>
|
||
<span>未配置 API Key,请先在 <button class="link-btn" id="alertSettingsBtn">设置</button> 中填写。</span>
|
||
</div>
|
||
|
||
<main>
|
||
|
||
|
||
|
||
<form id="generateForm">
|
||
|
||
<!-- Quick prompts -->
|
||
<div class="prompt-tags" id="promptTags">
|
||
<span class="tags-label">快捷描述</span>
|
||
<div class="tags-list">
|
||
<!-- 摄影 -->
|
||
<button type="button" class="tag-pill" data-tag="人像摄影,单反背景虚化,专业打光">人像</button>
|
||
<button type="button" class="tag-pill" data-tag="城市夜景,长曝光,车轨,延时摄影">城市夜景</button>
|
||
<button type="button" class="tag-pill" data-tag="自然光,户外拍摄,清新自然">自然光</button>
|
||
<button type="button" class="tag-pill" data-tag="水下摄影,蓝色调,光影折射">水下</button>
|
||
<button type="button" class="tag-pill" data-tag="微距摄影,景深压缩,细节丰富">微距</button>
|
||
<button type="button" class="tag-pill" data-tag="延时摄影,日出日落,流动感">延时</button>
|
||
<!-- 艺术风格 -->
|
||
<button type="button" class="tag-pill" data-tag="动漫风格,插画,精致细节,二次元">动漫</button>
|
||
<button type="button" class="tag-pill" data-tag="油画质感,古典,厚重笔触,暖色调">油画</button>
|
||
<button type="button" class="tag-pill" data-tag="水彩画,清新通透,柔和晕染">水彩</button>
|
||
<button type="button" class="tag-pill" data-tag="中国风,水墨画,留白,意境">水墨</button>
|
||
<button type="button" class="tag-pill" data-tag="浮世绘风格,古典日本,细腻线条">浮世绘</button>
|
||
<button type="button" class="tag-pill" data-tag="像素艺术,复古游戏,8bit风格">像素</button>
|
||
<button type="button" class="tag-pill" data-tag="赛博朋克,霓虹灯,夜晚,雨中城市">赛博朋克</button>
|
||
<button type="button" class="tag-pill" data-tag="蒸汽朋克,机械,复古未来,复古铜色">蒸汽朋克</button>
|
||
<button type="button" class="tag-pill" data-tag="蒸汽波,复古粉蓝,网格,怀旧">蒸汽波</button>
|
||
<button type="button" class="tag-pill" data-tag="极简主义,大面积留白,干净利落">极简</button>
|
||
<button type="button" class="tag-pill" data-tag="孟菲斯风格,彩色几何,活泼有趣">孟菲斯</button>
|
||
<button type="button" class="tag-pill" data-tag="包豪斯,几何构成,撞色,工业感">包豪斯</button>
|
||
<!-- 环境 -->
|
||
<button type="button" class="tag-pill" data-tag="雪景,柔和光线,细腻质感,纯净">雪景</button>
|
||
<button type="button" class="tag-pill" data-tag="日落,金色时刻,暖色调,剪影">日落</button>
|
||
<button type="button" class="tag-pill" data-tag="星空,银河,流星,暗夜">星空</button>
|
||
<button type="button" class="tag-pill" data-tag="森林,薄雾,空气感,阳光穿透">森林</button>
|
||
<button type="button" class="tag-pill" data-tag="海边,浪花,礁石,清凉夏日">海边</button>
|
||
<button type="button" class="tag-pill" data-tag="沙漠,金色沙丘,孤独感,广袤">沙漠</button>
|
||
<button type="button" class="tag-pill" data-tag="高山云海,日出东方,壮丽磅礴">高山云海</button>
|
||
<button type="button" class="tag-pill" data-tag="樱花季,粉白色调,浪漫氛围">樱花</button>
|
||
<button type="button" class="tag-pill" data-tag="下雨天,窗户,雨滴,氛围感">雨天</button>
|
||
<!-- 人物 -->
|
||
<button type="button" class="tag-pill" data-tag="古风汉服,水墨晕染,东方韵味">古风</button>
|
||
<button type="button" class="tag-pill" data-tag="未来科技感服装,机甲,轻未来">未来感</button>
|
||
<button type="button" class="tag-pill" data-tag="可爱 Q 版,大头娃娃,萌系">Q版</button>
|
||
<button type="button" class="tag-pill" data-tag="暗黑风格,哥特,神秘诡异">暗黑</button>
|
||
<button type="button" class="tag-pill" data-tag="治愈系插画,柔和配色,温暖人心">治愈系</button>
|
||
<!-- 光影 -->
|
||
<button type="button" class="tag-pill" data-tag="逆光,光晕,轮廓光,梦幻感">逆光</button>
|
||
<button type="button" class="tag-pill" data-tag="霓虹灯,夜间,光影交织,赛博">霓虹</button>
|
||
<button type="button" class="tag-pill" data-tag="柔光箱,侧光,明暗对比,电影感">柔光</button>
|
||
<button type="button" class="tag-pill" data-tag="丁达尔效应,光束穿透,云雾缭绕">丁达尔</button>
|
||
<!-- 科幻 -->
|
||
<button type="button" class="tag-pill" data-tag="科幻概念设计,太空,细节丰富">科幻</button>
|
||
<button type="button" class="tag-pill" data-tag="外星世界,异域星球,未知探索">外星</button>
|
||
<button type="button" class="tag-pill" data-tag="废土风格,末世,荒凉,锈迹斑斑">废土</button>
|
||
<!-- 美食静物 -->
|
||
<button type="button" class="tag-pill" data-tag="美食摄影,俯拍,精致摆盘,食欲感">美食</button>
|
||
<button type="button" class="tag-pill" data-tag="产品静物,纯白背景,商业摄影">产品静物</button>
|
||
<button type="button" class="tag-pill" data-tag="咖啡厅,暖色调,书本,午后阳光">咖啡厅</button>
|
||
<!-- 建筑 -->
|
||
<button type="button" class="tag-pill" data-tag="建筑摄影,建筑美学,几何线条,对称构图">建筑</button>
|
||
<button type="button" class="tag-pill" data-tag="室内设计,北欧风格,简约明亮">北欧风</button>
|
||
<button type="button" class="tag-pill" data-tag="中式古建筑,雕梁画栋,庄严典雅">中式建筑</button>
|
||
</div>
|
||
</div>
|
||
|
||
<!-- Prompt -->
|
||
<div class="prompt-row">
|
||
<textarea
|
||
id="promptInput"
|
||
placeholder="描述你想要生成的图片..."
|
||
rows="4"
|
||
maxlength="1500"
|
||
autofocus
|
||
></textarea>
|
||
<div class="prompt-footer">
|
||
<span class="char-count" id="charCount">0 / 1500</span>
|
||
</div>
|
||
</div>
|
||
|
||
<!-- Options -->
|
||
<div class="options-grid">
|
||
|
||
<!-- Left column -->
|
||
<div class="options-col">
|
||
|
||
<!-- Aspect ratio -->
|
||
<div class="opt-group">
|
||
<label class="opt-label">比例</label>
|
||
<select id="aspectRatio">
|
||
<option value="1:1">1:1 — 正方形</option>
|
||
<option value="16:9" selected>16:9 — 宽屏</option>
|
||
<option value="4:3">4:3 — 标准</option>
|
||
<option value="3:2">3:2 — 照片</option>
|
||
<option value="2:3">2:3 — 竖图</option>
|
||
<option value="3:4">3:4 — 竖图</option>
|
||
<option value="9:16">9:16 — 竖屏</option>
|
||
<option value="21:9">21:9 — 超宽(仅 image-01)</option>
|
||
</select>
|
||
</div>
|
||
|
||
<!-- Response format -->
|
||
<div class="opt-group">
|
||
<label class="opt-label">输出格式</label>
|
||
<select id="responseFormat">
|
||
<option value="url">URL(24小时有效)</option>
|
||
<option value="base64">Base64(直接保存)</option>
|
||
</select>
|
||
</div>
|
||
|
||
<!-- Count -->
|
||
<div class="opt-group">
|
||
<label class="opt-label">生成数量 <span class="opt-hint">(1-9张)</span></label>
|
||
<div class="stepper">
|
||
<button type="button" class="stepper-btn" id="nMinus">−</button>
|
||
<input type="number" id="nInput" value="1" min="1" max="9" readonly />
|
||
<button type="button" class="stepper-btn" id="nPlus">+</button>
|
||
</div>
|
||
</div>
|
||
|
||
<!-- Seed -->
|
||
<div class="opt-group">
|
||
<label class="opt-label">随机种子 <span class="opt-hint">(留空则随机)</span></label>
|
||
<input type="number" id="seedInput" placeholder="输入整数用于复现" min="0" step="1" />
|
||
</div>
|
||
|
||
</div>
|
||
|
||
<!-- Right column -->
|
||
|
||
<div class="options-col">
|
||
|
||
<!-- image-01: custom dimensions -->
|
||
<div class="opt-group dimension-group" id="dimensionGroup">
|
||
<label class="opt-label">自定义分辨率 <span class="opt-hint">(512-2048,必须是8的倍数)</span></label>
|
||
<div class="dim-row">
|
||
<input type="number" id="widthInput" placeholder="宽度" min="512" max="2048" step="8" />
|
||
<span class="dim-x">×</span>
|
||
<input type="number" id="heightInput" placeholder="高度" min="512" max="2048" step="8" />
|
||
</div>
|
||
<p class="opt-note">同时设置宽高时优先于比例</p>
|
||
</div>
|
||
|
||
|
||
|
||
<!-- Toggles -->
|
||
<div class="toggle-group">
|
||
<label class="toggle-row">
|
||
<input type="checkbox" id="promptOptimizer" />
|
||
<span class="toggle-track"><span class="toggle-thumb"></span></span>
|
||
<span class="toggle-label">自动优化 Prompt</span>
|
||
</label>
|
||
<label class="toggle-row">
|
||
<input type="checkbox" id="watermark" />
|
||
<span class="toggle-track"><span class="toggle-thumb"></span></span>
|
||
<span class="toggle-label">添加 AI 水印</span>
|
||
</label>
|
||
</div>
|
||
|
||
</div>
|
||
</div><!-- /options-grid -->
|
||
|
||
<!-- Generate -->
|
||
<button type="submit" class="generate-btn" id="generateBtn">
|
||
<svg class="btn-icon" width="18" height="18" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round">
|
||
<polygon points="13,2 3,14 12,14 11,22 21,10 12,10 13,2"/>
|
||
</svg>
|
||
<span class="btn-text">生成图片</span>
|
||
<svg class="spinner" width="18" height="18" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2">
|
||
<circle cx="12" cy="12" r="10" stroke-dasharray="60" stroke-dashoffset="20"/>
|
||
</svg>
|
||
</button>
|
||
|
||
</form>
|
||
|
||
<!-- Error -->
|
||
<div class="error-msg" id="errorMsg" style="display:none"></div>
|
||
|
||
<!-- Results -->
|
||
<div id="resultArea" style="display:none">
|
||
<div class="result-meta" id="resultMeta"></div>
|
||
<div class="image-grid" id="imageGrid"></div>
|
||
</div>
|
||
|
||
</main>
|
||
</div>
|
||
|
||
<!-- Settings Modal -->
|
||
<div class="modal-overlay" id="settingsModal">
|
||
<div class="modal">
|
||
<div class="modal-header">
|
||
<h2>设置</h2>
|
||
<button class="icon-btn" id="closeSettings">
|
||
<svg width="18" height="18" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round">
|
||
<line x1="18" y1="6" x2="6" y2="18"/><line x1="6" y1="6" x2="18" y2="18"/>
|
||
</svg>
|
||
</button>
|
||
</div>
|
||
<div class="modal-body">
|
||
<div class="field">
|
||
<label for="apiKeyInput">MiniMax API Key</label>
|
||
<div class="input-row">
|
||
<input type="password" id="apiKeyInput" placeholder="eyJhbGciOiJIUzI1NiIsInR..." />
|
||
<button class="icon-btn" id="toggleKey" type="button" title="显示/隐藏">
|
||
<svg width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round">
|
||
<path d="M1 12s4-8 11-8 11 8 11 8-4 8-11 8-11-8-11-8z"/><circle cx="12" cy="12" r="3"/>
|
||
</svg>
|
||
</button>
|
||
</div>
|
||
<p class="field-hint">请从 <a href="https://platform.minimaxi.com/user-center/payment/token-plan" target="_blank" rel="noopener">platform.minimaxi.com</a> 获取</p>
|
||
</div>
|
||
<div class="field">
|
||
<label for="baseUrlInput">API 地址</label>
|
||
<input type="text" id="baseUrlInput" placeholder="https://api.minimaxi.com" />
|
||
<p class="field-hint">默认使用中国区 API,仅在需要代理时修改。</p>
|
||
</div>
|
||
</div>
|
||
<div class="modal-footer">
|
||
<button class="btn-secondary" id="cancelSettings">取消</button>
|
||
<button class="btn-primary" id="saveSettingsBtn">保存</button>
|
||
</div>
|
||
</div>
|
||
</div>
|
||
|
||
<script src="ui.js" defer></script>
|
||
</body>
|
||
</html>
|