fix:修复页面样式

This commit is contained in:
Daniel
2026-04-14 12:05:56 +08:00
parent 508c28ce31
commit 89b21dd314
36 changed files with 2866 additions and 495 deletions

View File

@@ -1,4 +1,9 @@
FROM nvidia/cuda:12.1.1-runtime-ubuntu22.04 AS builder
ARG NODE_BASE_IMAGE=docker.m.daocloud.io/library/node:20-bookworm-slim
ARG CUDA_BASE_IMAGE=docker.m.daocloud.io/nvidia/cuda:12.1.1-runtime-ubuntu22.04
FROM ${NODE_BASE_IMAGE} AS node20
FROM ${CUDA_BASE_IMAGE} AS builder
ENV DEBIAN_FRONTEND=noninteractive \
PYTHONDONTWRITEBYTECODE=1 \
@@ -11,18 +16,18 @@ ENV DEBIAN_FRONTEND=noninteractive \
WORKDIR /app
# Base deps + Python 3.10 + Node.js 20.x
# Base deps + Python 3.10
RUN sed -i 's|http://archive.ubuntu.com/ubuntu|https://mirrors.tuna.tsinghua.edu.cn/ubuntu|g; s|http://security.ubuntu.com/ubuntu|https://mirrors.tuna.tsinghua.edu.cn/ubuntu|g' /etc/apt/sources.list \
&& apt-get -o Acquire::Retries=5 update \
&& apt-get -o Acquire::Retries=5 install -y --no-install-recommends --fix-missing \
ca-certificates curl gnupg \
python3.10 python3.10-distutils python3-pip \
ffmpeg fonts-dejavu-core \
&& curl -fsSL https://deb.nodesource.com/setup_20.x | bash - \
&& apt-get -o Acquire::Retries=5 install -y --no-install-recommends --fix-missing nodejs \
&& ln -sf /usr/bin/python3.10 /usr/local/bin/python \
&& rm -rf /var/lib/apt/lists/*
COPY --from=node20 /usr/local /usr/local
COPY requirements.txt /app/requirements.txt
RUN python3.10 -m pip install -r /app/requirements.txt
@@ -31,7 +36,7 @@ RUN cd /app/server && npm ci --omit=dev
COPY . /app
FROM nvidia/cuda:12.1.1-runtime-ubuntu22.04 AS runtime
FROM ${CUDA_BASE_IMAGE} AS runtime
ENV DEBIAN_FRONTEND=noninteractive \
PYTHONDONTWRITEBYTECODE=1 \
@@ -50,11 +55,11 @@ RUN sed -i 's|http://archive.ubuntu.com/ubuntu|https://mirrors.tuna.tsinghua.edu
ca-certificates \
python3.10 python3.10-distutils python3-pip \
ffmpeg fonts-dejavu-core \
&& curl -fsSL https://deb.nodesource.com/setup_20.x | bash - \
&& apt-get -o Acquire::Retries=5 install -y --no-install-recommends --fix-missing nodejs \
&& ln -sf /usr/bin/python3.10 /usr/local/bin/python \
&& rm -rf /var/lib/apt/lists/*
COPY --from=node20 /usr/local /usr/local
COPY --from=builder /usr/local/lib/python3.10 /usr/local/lib/python3.10
COPY --from=builder /usr/local/bin /usr/local/bin
COPY --from=builder /app /app

View File

@@ -5,7 +5,7 @@
- Output: a 3-scene narrated video `final_poc.mp4` (mock mode supported)
## Quick start (Docker)
`docker compose up` includes a **ComfyUI** service (default image `jamesbrink/comfyui:latest` from Docker Hub). If you use another registry image, set `COMFYUI_IMAGE` in the environment.
`docker compose up` includes a **ComfyUI** service (default through domestic mirror: `docker.1ms.run/ardenius/comfyui-cpu:latest`). If you use another registry image, set `COMFYUI_IMAGE` in the environment.
Build:
@@ -49,3 +49,4 @@ Open `http://127.0.0.1:3000` and click “运行” to see `main.py --script-onl
- **apt**: TUNA Debian mirrors (baked into `Dockerfile`)
- **pip**: `PIP_INDEX_URL=https://pypi.tuna.tsinghua.edu.cn/simple`
- **npm**: `NPM_CONFIG_REGISTRY=https://registry.npmmirror.com`
- **docker images**: default base images now pull via `docker.m.daocloud.io` mirror

52
clone.html Normal file

File diff suppressed because one or more lines are too long

View File

@@ -10,15 +10,17 @@ services:
- PORT=3000
volumes:
- ./:/app
# Keep dependencies inside container volume to avoid host FS read issues on macOS.
- /app/server/node_modules
ports:
- "3000:3000"
# Default: Docker Hub (anonymous pull). GHCR comfyanonymous image often returns "denied" without login.
# Override: COMFYUI_IMAGE=ghcr.io/... after `docker login ghcr.io`
# Default: use domestic mirror to speed up pulls in CN networks.
# Override with COMFYUI_IMAGE to use another registry/image.
comfyui:
# CPU-friendly default image for non-NVIDIA development machines.
# Override with COMFYUI_IMAGE to switch back to a GPU image.
image: ${COMFYUI_IMAGE:-ardenius/comfyui-cpu:latest}
image: ${COMFYUI_IMAGE:-docker.1ms.run/ardenius/comfyui-cpu:latest}
# Force bind to all interfaces so other containers (and `check_comfy`) can reach it.
# Works with the default ardenius/comfyui-cpu image layout (/ComfyUI-cpu/main.py).
command: ${COMFYUI_COMMAND:-python3 /ComfyUI-cpu/main.py --cpu --cpu-vae --listen 0.0.0.0 --port 8188}

View File

@@ -0,0 +1,61 @@
# AiVideo Studio 重构方案V2
## 目标
- 实现与参考编辑器页面一致的工作台布局:顶部导航、中央预览舞台、底部时间线、右侧参数与日志面板。
- 保留并强化现有能力:自动分镜、单镜头润色、渲染、阶段日志、任务跟踪。
- 将前端代码从“流程散落”改造为“分层架构”,减少重复逻辑与状态不一致风险。
## 新架构
### 1. UI Shell 层
- `TopNav`品牌、快捷操作、Play/Render 入口。
- `ToolBar`上下文状态task/mock与工具位。
- `PreviewStage`:展示当前 Scene 预览或 final video。
- `TimelineStrip`:镜头缩略图时间线与进度条。
- `SceneEditor`:单镜头编辑与润色入口。
### 2. 状态层StudioState
- 统一使用 `useReducer` 管理工作台状态。
- 核心状态:
- `scenes`
- `selectedSceneIndex`
- `stageState`
- `stageLogs`
- `renderProgress`
- `taskId`
- `finalVideoUrl`
- `toast`
- 所有修改均通过 `dispatch(action)` 进入 reducer避免多处 `useState` 导致的竞态和重复。
### 3. API/流处理层StudioAPI
- `startScriptStream()`EventSource 流式接收 Script 阶段事件。
- `postStream()`:统一处理 Refine/Render 的 fetch + SSE 流。
- `consumeFetchSSE()`:抽象 SSE 分块解析,消除重复解析代码。
### 4. 事件编排层
- `onStageEvent(sourceStage, event, data)` 统一路由:
- `task`
- `stage_update`
- `line`
- `error`
- `done`
- `applyStageUpdate()` 负责阶段状态、进度、scene upsert 的单点更新。
## 数据流
1. 用户修改 Prompt / Provider 参数。
2. 自动防抖触发 `startScript()`,进入 Script SSE。
3. `stage_update.scene_json` 持续更新 `scenes`,时间线和右侧编辑器同步刷新。
4. 用户可对当前 Scene 进行编辑与 `refine`
5. 用户触发 `render`,进度与日志实时反馈,完成后挂载 final video URL。
## 兼容性说明
- 继续使用 `babel-standalone@6`,所以 JSX 不使用 `<>...</>`,统一为 `React.Fragment`
- 保持现有后端接口契约不变:
- `GET /api/script`
- `POST /api/refine`
- `POST /api/render`
## 后续建议
- 将当前单文件页面拆分为真正多文件前端工程Vite + React引入 TypeScript 与单元测试。
- 增加 Timeline 的拖拽排序与片段时长编辑。
- 增加右侧“资产库”与“模板库”,进一步贴近参考产品完整体验。

View File

@@ -0,0 +1,19 @@
{
"scenes": [
{
"image_prompt": "写一个温暖的城市夜景故事\n\n\n[Global Constraints]\n- Global Style: 电影感\n请严格遵守上述全局信息并保持三分镜主角一致。城市夜景霓虹灯电影感",
"video_motion": "缓慢推进镜头,轻微摇镜",
"narration": "夜色温柔落在街灯上"
},
{
"image_prompt": "写一个温暖的城市夜景故事\n\n\n[Global Constraints]\n- Global Style: 电影感\n请严格遵守上述全局信息并保持三分镜主角一致。咖啡店窗边暖光细雨",
"video_motion": "侧向平移,人物轻轻抬头",
"narration": "雨声里藏着一段回忆"
},
{
"image_prompt": "写一个温暖的城市夜景故事\n\n\n[Global Constraints]\n- Global Style: 电影感\n请严格遵守上述全局信息并保持三分镜主角一致。桥上远景车流光轨温暖",
"video_motion": "拉远全景,光轨流动",
"narration": "我们在光里学会告别"
}
]
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.1 MiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.1 MiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.1 MiB

View File

@@ -0,0 +1,19 @@
{
"scenes": [
{
"image_prompt": "写一个温暖的城市夜景故事\n\n\n[Global Constraints]\n- Global Style: 电影感\n请严格遵守上述全局信息并保持三分镜主角一致。城市夜景霓虹灯电影感",
"video_motion": "缓慢推进镜头,轻微摇镜",
"narration": "夜色温柔落在街灯上"
},
{
"image_prompt": "写一个温暖的城市夜景故事\n\n\n[Global Constraints]\n- Global Style: 电影感\n请严格遵守上述全局信息并保持三分镜主角一致。咖啡店窗边暖光细雨",
"video_motion": "侧向平移,人物轻轻抬头",
"narration": "雨声里藏着一段回忆"
},
{
"image_prompt": "写一个温暖的城市夜景故事\n\n\n[Global Constraints]\n- Global Style: 电影感\n请严格遵守上述全局信息并保持三分镜主角一致。桥上远景车流光轨温暖",
"video_motion": "拉远全景,光轨流动",
"narration": "我们在光里学会告别"
}
]
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.1 MiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.1 MiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.1 MiB

View File

@@ -0,0 +1,19 @@
{
"scenes": [
{
"image_prompt": "写一个温暖的城市夜景故事\n\n\n[Global Constraints]\n- Global Style: 电影感\n请严格遵守上述全局信息并保持三分镜主角一致。城市夜景霓虹灯电影感",
"video_motion": "缓慢推进镜头,轻微摇镜",
"narration": "夜色温柔落在街灯上"
},
{
"image_prompt": "写一个温暖的城市夜景故事\n\n\n[Global Constraints]\n- Global Style: 电影感\n请严格遵守上述全局信息并保持三分镜主角一致。咖啡店窗边暖光细雨",
"video_motion": "侧向平移,人物轻轻抬头",
"narration": "雨声里藏着一段回忆"
},
{
"image_prompt": "写一个温暖的城市夜景故事\n\n\n[Global Constraints]\n- Global Style: 电影感\n请严格遵守上述全局信息并保持三分镜主角一致。桥上远景车流光轨温暖",
"video_motion": "拉远全景,光轨流动",
"narration": "我们在光里学会告别"
}
]
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.1 MiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.1 MiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.1 MiB

View File

@@ -0,0 +1,19 @@
{
"scenes": [
{
"image_prompt": "写一个温暖的城市夜景故事\n\n\n[Global Constraints]\n- Global Style: 电影感\n请严格遵守上述全局信息并保持三分镜主角一致。城市夜景霓虹灯电影感",
"video_motion": "缓慢推进镜头,轻微摇镜",
"narration": "夜色温柔落在街灯上"
},
{
"image_prompt": "写一个温暖的城市夜景故事\n\n\n[Global Constraints]\n- Global Style: 电影感\n请严格遵守上述全局信息并保持三分镜主角一致。咖啡店窗边暖光细雨",
"video_motion": "侧向平移,人物轻轻抬头",
"narration": "雨声里藏着一段回忆"
},
{
"image_prompt": "写一个温暖的城市夜景故事\n\n\n[Global Constraints]\n- Global Style: 电影感\n请严格遵守上述全局信息并保持三分镜主角一致。桥上远景车流光轨温暖",
"video_motion": "拉远全景,光轨流动",
"narration": "我们在光里学会告别"
}
]
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.1 MiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.1 MiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.1 MiB

View File

@@ -0,0 +1,19 @@
{
"scenes": [
{
"image_prompt": "写一个温暖的城市夜景故事\n\n\n[Global Constraints]\n- Global Style: 电影感\n请严格遵守上述全局信息并保持三分镜主角一致。城市夜景霓虹灯电影感",
"video_motion": "缓慢推进镜头,轻微摇镜",
"narration": "夜色温柔落在街灯上"
},
{
"image_prompt": "写一个温暖的城市夜景故事\n\n\n[Global Constraints]\n- Global Style: 电影感\n请严格遵守上述全局信息并保持三分镜主角一致。咖啡店窗边暖光细雨",
"video_motion": "侧向平移,人物轻轻抬头",
"narration": "雨声里藏着一段回忆"
},
{
"image_prompt": "写一个温暖的城市夜景故事\n\n\n[Global Constraints]\n- Global Style: 电影感\n请严格遵守上述全局信息并保持三分镜主角一致。桥上远景车流光轨温暖",
"video_motion": "拉远全景,光轨流动",
"narration": "我们在光里学会告别"
}
]
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.1 MiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.1 MiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.1 MiB

View File

@@ -0,0 +1,19 @@
{
"scenes": [
{
"image_prompt": "写一个温暖的城市夜景故事\n\n\n[Global Constraints]\n- Global Style: 电影感\n请严格遵守上述全局信息并保持三分镜主角一致。城市夜景霓虹灯电影感",
"video_motion": "缓慢推进镜头,轻微摇镜",
"narration": "夜色温柔落在街灯上"
},
{
"image_prompt": "写一个温暖的城市夜景故事\n\n\n[Global Constraints]\n- Global Style: 电影感\n请严格遵守上述全局信息并保持三分镜主角一致。咖啡店窗边暖光细雨",
"video_motion": "侧向平移,人物轻轻抬头",
"narration": "雨声里藏着一段回忆"
},
{
"image_prompt": "写一个温暖的城市夜景故事\n\n\n[Global Constraints]\n- Global Style: 电影感\n请严格遵守上述全局信息并保持三分镜主角一致。桥上远景车流光轨温暖",
"video_motion": "拉远全景,光轨流动",
"narration": "我们在光里学会告别"
}
]
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.1 MiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.1 MiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.1 MiB

View File

@@ -0,0 +1,19 @@
{
"scenes": [
{
"image_prompt": "写一个温暖的城市夜景故事\n\n\n[Global Constraints]\n- Global Style: 电影感\n请严格遵守上述全局信息并保持三分镜主角一致。城市夜景霓虹灯电影感",
"video_motion": "缓慢推进镜头,轻微摇镜",
"narration": "夜色温柔落在街灯上"
},
{
"image_prompt": "写一个温暖的城市夜景故事\n\n\n[Global Constraints]\n- Global Style: 电影感\n请严格遵守上述全局信息并保持三分镜主角一致。咖啡店窗边暖光细雨",
"video_motion": "侧向平移,人物轻轻抬头",
"narration": "雨声里藏着一段回忆"
},
{
"image_prompt": "写一个温暖的城市夜景故事\n\n\n[Global Constraints]\n- Global Style: 电影感\n请严格遵守上述全局信息并保持三分镜主角一致。桥上远景车流光轨温暖",
"video_motion": "拉远全景,光轨流动",
"narration": "我们在光里学会告别"
}
]
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.1 MiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.1 MiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.1 MiB

373
prompt/v1.md Normal file
View File

@@ -0,0 +1,373 @@
# 3分钟短片分镜脚本5秒/镜头)
## 基础设定
- 总时长180秒
- 分镜数量36个每个5秒
- 叙事风格:军事写实 + 高压营救
- 画幅建议2.39:124fps
- 色调建议:
- 战前与巡航:冷蓝灰
- 被击落与搜捕:黄沙+火光高反差
- 夜间营救:深蓝+红色告警光
## 角色映射(拟人化动物代号)
- 美国:鹰酱
- 伊朗:波猫
- 以色列:乌贼(本片仅作为电台背景提及,不正面出场)
- 中国:熊猫(新闻墙背景信息)
- 俄罗斯:棕熊(新闻墙背景信息)
- 印度:白象(新闻墙背景信息)
- 法国:高卢鸡(新闻墙背景信息)
- 英国:约翰牛(新闻墙背景信息)
## 身份与语言锁定(必须严格保持)
- 人物国籍/身份:
- `Falcon-1``Falcon-2`、Rescue机组、鹰酱指挥链美国人American
- 波猫地面部队、波猫指挥员、波猫电台波斯人Persian / Iranian
- 语种使用:
- 鹰酱侧人物对白与无线电英语English
- 波猫侧人物对白与无线电波斯语Persian / Farsi
- 旁白可保留中文版本用于成片叙事;若做国际版,旁白统一英语。
- 字幕与播报规范:
- 对白保持原语种发声,不要“角色直接说中文”。
- 成片字幕建议双语:中文主字幕 + 英文副字幕;波斯语台词保留音译或意译其一并全片统一。
- 无线电口令优先使用军事短句,避免口语化长句。
## 连续性规则(后续生成必须严格保持)
- 飞行员共2名
- 1号飞行员“Falcon-1”橙色应急信标、右臂擦伤。
- 2号飞行员“Falcon-2”绿色应急信标、左腿轻伤。
- 被击落战机鹰酱双机编队共2架均在山地荒漠区坠毁。
- 营救空中力量:
- 黑鹰直升机2架代号 Rescue-1、Rescue-2
- 加油机1架代号 Shell-6
- 护航战机若干(不固定数量,远景表现)
- 结局战损必须出现:
- 1架运输机被炸毁
- 2架直升机被炸毁对应 Rescue-1 与 Rescue-2
- 主结局必须保留:两名飞行员均被成功救出。
## 人物形象一致性圣经(必须锁定)
- `Falcon-1`(橙标):
- 识别锚点:头盔左侧白色短划痕、右臂外侧止血贴、橙色频闪信标固定在胸挂左下。
- 动作特征:右臂发力受限,举枪与攀爬时明显护臂动作。
- 台词状态:语速偏稳、短句下达信息。
- `Falcon-2`(绿标):
- 识别锚点:头盔后缘绿色反光贴、左腿膝下弹性绷带、绿色频闪信标固定在腰后。
- 动作特征:落地后全程轻度跛行,冲刺时左腿拖步。
- 台词状态:呼吸更急,句尾常有停顿。
- 拟人化呈现边界:
- 仅保留“代号化动物身份”语义,不使用夸张兽化比例。
- 面部与体型遵循真人军事题材比例,装备佩戴方式符合实战逻辑。
- 不出现卡通眼神、夸张毛发、Q版肢体。
- 全员装备佩戴统一:
- 同一角色的头盔编号、护目镜款式、战术背心挂载位置在全片不改变。
- 血迹、划伤、灰尘只增不减,不能在后续镜头“突然变干净”。
## 武器与装备真实性基线(建议锁定)
- 鹰酱舰载打击机:`F/A-18E/F` 双机编队对应镜头02-07
- 营救直升机:`UH-60` 级别中型通用直升机Rescue-1 / Rescue-2侧门机枪位清晰可见。
- 空中加油机:`KC-46/KC-135` 级别Shell-6受油阶段以软管锥套或硬管受油呈现不出现“接驳火花”。
- 运输机:`C-130` 级别战术运输机镜头25、28、29
- 波猫地面防空:
- 中程防空系统(雷达车 + 发射车)负责初次击落。
- 末段近程威胁以重机枪 + 便携防空导弹MANPADS为主。
- 弹药与火力效果写实化:
- 曳光弹比例控制在“数发可见”,避免整条激光束观感。
- 近炸与破片效果优先,减少夸张球形大火团。
- 爆炸后要有二次碎片与烟尘延迟,不要“一炸即净空”。
## 分镜脚本36镜头
### 镜头0100:00-00:05
- 画面:高空俯瞰,波猫领地城市边缘被连续轰炸,冲击波掀起尘墙。
- 机位/运动:无人机式广角,缓慢前推。
- 关键元素:夜色未尽,地表火点连成线,防空探照灯扫空。
- 音效:低沉爆炸滚雷,远处防空警报。
- 台词/旁白:旁白「战争进入第七夜,鹰酱的空袭仍在继续。」
### 镜头0200:05-00:10
- 画面鹰酱航母甲板2架F/A-18E/F挂弹弹射起飞蒸汽与尾焰交叠。
- 机位/运动:低机位仰拍,快速摇镜跟随起飞。
- 关键元素:甲板人员手势指挥、夜航灯闪烁。
- 音效:喷气轰鸣、甲板指令哨音。
- 台词/旁白无线电「Viper编队进入打击航线。」
### 镜头0300:10-00:15
- 画面双机编队穿过云层HUD叠加锁定地面目标。
- 机位/运动:座舱第一视角与外景切换。
- 关键元素:导弹挂架细节、雷达波纹扫描。
- 音效:电子告警“滴滴”,呼吸声。
- 台词/旁白Falcon-1「目标区在前保持队形。」
### 镜头0400:15-00:20
- 画面:波猫山地防空阵地启动,雷达车转入跟踪,导弹发射车舱盖弹开。
- 机位/运动:地面中景,手持震动感。
- 关键元素:士兵奔跑装填,红外追踪镜头特写。
- 音效:机械液压声、点火咆哮。
- 台词/旁白:波猫指挥员「锁定高空双目标,发射!」
### 镜头0500:20-00:25
- 画面:一枚防空导弹破云而出,拖着白色尾迹直扑编队。
- 机位/运动:导弹追踪镜头,高速推进。
- 关键元素:云层被撕开,导弹尾焰占满画面。
- 音效:尖啸上扬,心跳加重。
- 台词/旁白Falcon-2「警报导弹来袭
### 镜头0600:25-00:30
- 画面:第一架战机被命中,机翼断裂起火,飞行员弹射。
- 机位/运动:慢动作+快速拉远。
- 关键元素火球碎片雨、橙色降落伞打开、Falcon-1头盔左侧白色划痕可辨。
- 音效:爆裂巨响后瞬间闷音。
- 台词/旁白Falcon-1「我中弹了弹射
### 镜头0700:30-00:35
- 画面:第二架战机规避失败,在山脊后方爆炸,第二名飞行员跳伞。
- 机位/运动:远景长焦,爆炸后切近景。
- 关键元素绿色信标闪烁黑烟柱升空Falcon-2左腿落地姿态明显受伤。
- 音效:山谷回响爆炸、碎片落地声。
- 台词/旁白Falcon-2「我也跳伞了落点偏东
### 镜头0800:35-00:40
- 画面:两名飞行员分别落入荒漠沟壑,迅速解伞隐蔽。
- 机位/运动:俯拍切地面跟拍。
- 关键元素Falcon-1右臂流血并贴止血贴Falcon-2左腿跛行前进信标颜色不可互换。
- 音效:风沙呼啸,急促喘息。
- 台词/旁白:旁白「两人坠入波猫腹地,距离最近友军超过百公里。」
### 镜头0900:40-00:45
- 画面Falcon-1开启橙色应急信标贴地发报。
- 机位/运动:特写手部操作,微距切换。
- 关键元素终端屏幕坐标跳动Grid K-27。
- 音效:加密电台短促脉冲声。
- 台词/旁白Falcon-1「Mayday坐标K-27等待回收。」
### 镜头1000:45-00:50
- 画面Falcon-2在岩缝内发送绿色信标标记L-31。
- 机位/运动:肩扛镜头,压迫感近景。
- 关键元素:夜视模式闪现,腿部绑带止血。
- 音效:远处履带车轰鸣渐近。
- 台词/旁白Falcon-2「L-31敌巡逻接近快。」
### 镜头1100:50-00:55
- 画面:鹰酱前线基地作战室,大屏锁定两个信标点。
- 机位/运动:环绕镜头扫过指挥台。
- 关键元素:地图上红蓝箭头交错,倒计时启动。
- 音效:键盘急击,警铃短鸣。
- 台词/旁白指挥官「启动CSAR黑鹰立即起飞。」
### 镜头1200:55-01:00
- 画面黑鹰Rescue-1与Rescue-2低空起飞加油机Shell-6升空。
- 机位/运动:侧向跟拍,旋翼掠过镜头。
- 关键元素:机腹绞盘、双侧机枪位、夜航识别灯、机身战术编号清晰。
- 音效:旋翼重拍,地勤呼喊。
- 台词/旁白无线电「Rescue编队离场航线A-9。」
### 镜头1301:00-01:05
- 画面:空中加油,护航机与加油机在云海上方并行。
- 机位/运动:远景稳定镜头后推进到受油管连接点。
- 关键元素:受油管锥套轻微摆动后稳定咬合,无异常火花。
- 音效:稳定低频引擎噪音。
- 台词/旁白Shell-6「油量窗口三分钟动作快。」
### 镜头1401:05-01:10
- 画面:波猫地面部队成网状推进,热成像无人机升空搜捕。
- 机位/运动:高空俯拍+热成像视角切换。
- 关键元素:车灯组成搜索弧线,士兵犬队前导。
- 音效:引擎轰鸣、犬吠、短波口令。
- 台词/旁白波猫电台「封锁K-27到L-31全线搜索。」
### 镜头1501:10-01:15
- 画面Falcon-1躲在废弃输油管下抬头望见搜索无人机掠过。
- 机位/运动:主观视角仰拍,镜头轻颤。
- 关键元素:尘土落在面罩,橙色信标被紧急关闭。
- 音效:无人机电机嗡鸣从近到远。
- 台词/旁白Falcon-1低声「再晚十分钟我就暴露了。」
### 镜头1601:15-01:20
- 画面Falcon-2在峡谷底打出红外闪码远处有敌军灯柱扫来。
- 机位/运动:长焦压缩景深,红外闪码特写。
- 关键元素:膝盖血迹、沙地拖拽痕。
- 音效:高频电报码、远处喊话回声。
- 台词/旁白Falcon-2「我能听见他们快点。」
### 镜头1701:20-01:25
- 画面:黑鹰编队贴地穿越山谷,规避雷达,机枪手戒备。
- 机位/运动:直升机舱门外侧跟拍,快速掠地。
- 关键元素:旋翼扬沙,地形匹配航迹投影。
- 音效:旋翼轰鸣压迫感增强。
- 台词/旁白机组长「保持无线静默距目标12公里。」
### 镜头1801:25-01:30
- 画面:鹰酱空中分队反复盘旋搜寻,终于双点位重合确认。
- 机位/运动:战术地图与夜空外景交叉剪辑。
- 关键元素K-27与L-31连线形成回收走廊。
- 音效系统提示音“Target Confirmed”。
- 台词/旁白:指挥官「位置确认,执行双点同步回收。」
### 镜头1901:30-01:35
- 画面Rescue-1悬停K-27上空绞盘索下降。
- 机位/运动:俯冲到近景,绞盘视角向下看。
- 关键元素地面火光反射在机腹Falcon-1挥荧光棒。
- 音效:钢索摩擦声、机枪上膛声。
- 台词/旁白:救援员「看到你了,接索!」
### 镜头2001:35-01:40
- 画面:波猫地面火力突然开火,曳光弹扫向黑鹰。
- 机位/运动:地面对空仰拍,快速抖动。
- 关键元素重机枪阵地压制、MANPADS射手完成瞄准准备。
- 音效:密集枪声、金属击穿声。
- 台词/旁白:波猫士兵「压住它!别让它降!」
### 镜头2101:40-01:45
- 画面:护航机俯冲压制,投下制导炸弹清除火力点。
- 机位/运动:高速俯冲镜头切地爆炸全景。
- 关键元素:先精确命中火力核心点,再出现破片与次生爆炸扩散。
- 音效:破空尖啸后巨响。
- 台词/旁白:护航飞行员「地面威胁压制中!」
### 镜头2201:45-01:50
- 画面Rescue-2靠近L-31准备接Falcon-2地面车队逼近。
- 机位/运动:机舱内向外拍,远处车灯快速放大。
- 关键元素Falcon-2拖伤腿冲刺绿色信标闪烁。
- 音效:引擎轰鸣、队员喊口令。
- 台词/旁白:救援员「跑!再十米!」
### 镜头2301:50-01:55
- 画面一枚肩射导弹命中Rescue-1尾梁直升机失控。
- 机位/运动:慢动作表现中弹点,然后急速旋转坠落。
- 关键元素:尾桨碎裂,液压失效导致偏航失控,火星与碎片洒落。
- 音效:告警蜂鸣连续拉满。
- 台词/旁白:机组长「我们中弹,迫降失败!」
### 镜头2401:55-02:00
- 画面Rescue-1撞上山坡爆炸火球照亮峡谷。
- 机位/运动:远景定镜,冲击波推沙而来。
- 关键元素:残骸燃烧,弹药殉爆二次闪光。
- 音效:爆炸闷响叠加耳鸣效果。
- 台词/旁白:旁白「第一架黑鹰坠毁,回收窗口骤然收缩。」
### 镜头2502:00-02:05
- 画面:地面快速反应队由运输机空投到临时降落区。
- 机位/运动:机腹舱门外拍,队员索降。
- 关键元素C-130级运输机低空掠过红色舱灯明灭队员按序离机。
- 音效:风噪剧烈,索降扣具碰撞。
- 台词/旁白:指挥官「地面队接管,强行打通撤离点。」
### 镜头2602:05-02:10
- 画面Falcon-1被拉上Rescue-2救援员给右臂注射止痛剂。
- 机位/运动:机舱手持近景,节奏急促。
- 关键元素:橙色信标熄灭,血迹染红手套。
- 音效:呼喊、弹壳落舱声。
- 台词/旁白Falcon-1「还有一个人别丢下他
### 镜头2702:10-02:15
- 画面Falcon-2与地面队汇合巷战式近距离交火爆发。
- 机位/运动:平视跟跑镜头,快速切换掩体点。
- 关键元素废墟掩体崩裂、火花四溅、Falcon-2左腿拖步清晰。
- 音效:突击步枪点射,手雷爆炸。
- 台词/旁白:队长「烟幕弹!掩护伤员后撤!」
### 镜头2802:15-02:20
- 画面:运输机准备二次接应时被便携防空导弹命中右翼油箱。
- 机位/运动:中远景追拍,命中瞬间闪白。
- 关键元素:右侧机翼根部命中起火,燃油泄漏后拖尾燃烧。
- 音效:巨大爆鸣,电流噼啪。
- 台词/旁白:无线电「运输机中弹!重复,中弹!」
### 镜头2902:20-02:25
- 画面:运输机坠地爆炸,火焰蘑菇云升起。
- 机位/运动:超远景静镜,地平线被火光吞没。
- 关键元素:冲击波掀翻附近车辆。
- 音效:低频冲击后环境声短暂真空。
- 台词/旁白:旁白「运输机被摧毁,撤离计划只剩最后通道。」
### 镜头3002:25-02:30
- 画面Rescue-2超低空穿插试图带走Falcon-2与地面队。
- 机位/运动:机头视角穿越电线塔与峡谷拐点。
- 关键元素:曳光弹擦过机身,机体多处中弹,告警面板出现尾传动异常。
- 音效:金属撞击、告警语音不断。
- 台词/旁白:飞行员「坚持住,最后一次进场!」
### 镜头3102:30-02:35
- 画面第二枚导弹命中Rescue-2腹部直升机带火硬着陆后爆炸。
- 机位/运动:侧后方跟拍到撞地翻滚。
- 关键元素:主旋翼断裂飞散,机舱门被炸飞,机体翻滚后二次殉爆。
- 音效:连续爆炸、旋翼断裂尖啸。
- 台词/旁白:旁白「第二架黑鹰也被击毁。」
### 镜头3202:35-02:40
- 画面:幸存救援员与两名飞行员冲入废墟掩体,近距离枪战白热化。
- 机位/运动:手持近景,跟随冲刺与卧倒。
- 关键元素:子弹打碎混凝土,火星与粉尘充满画面。
- 音效:枪声密集、耳麦里杂音尖叫。
- 台词/旁白:队长「全员向北侧缺口突围!」
### 镜头3302:40-02:45
- 画面:护航战机再度空袭,炸开北侧封锁线,制造撤离窗口。
- 机位/运动:空地交叉剪,先空中俯冲再地面仰视。
- 关键元素:封锁阵地连环爆破,烟尘墙形成遮蔽。
- 音效:炸弹连响、无线电倒计时。
- 台词/旁白护航飞行员「北线已开窗口60秒
### 镜头3402:45-02:50
- 画面:备用撤离直升机(无编号)从烟幕中突入,救援员推送两名飞行员登机。
- 机位/运动:地面仰拍到机舱内反打。
- 关键元素Falcon-2被拖上机舱时左腿包扎仍在Falcon-1右臂受限下短点射掩护。
- 音效:旋翼压制一切环境声,喊话靠吼。
- 台词/旁白:救援员「人齐了!起飞!」
### 镜头3502:50-02:55
- 画面:直升机拉升脱离火网,地面仍有零星追击火力。
- 机位/运动:后向追踪镜头,地面火线逐渐变小。
- 关键元素:机舱内两名飞行员并排固定担架,医护紧急处理。
- 音效:呼吸机、心率监测滴答声混合旋翼声。
- 台词/旁白Falcon-2虚弱「我们……还活着吗
### 镜头3602:55-03:00
- 画面:黎明前天际线,撤离机飞向海面方向;地面远处仍燃着三处残骸火点(运输机+两架黑鹰)。
- 机位/运动:超远景缓慢拉远,最后定格。
- 关键元素:火光映出战场轮廓,字幕淡入“救援成功,代价惨重”。
- 音效:音乐转低沉弦乐,枪声远去。
- 台词/旁白:旁白「两名飞行员获救,但这一夜,没人真正获胜。」
## 统一画面生成约束给AI视频模型
- 风格关键词:`cinematic war realism, high detail, volumetric smoke, dramatic lighting, handheld tension, tactical HUD overlay, desert canyon battlefield`
- 画质关键词:`4k, ultra-detailed, film grain, motion blur, depth of field`
- 禁止项:`no cartoon style, no cute style, no exaggerated proportions, no text watermark, no logo`
- 人物一致性:两名飞行员伤情与信标颜色在全片保持一致,不可互换。
- 物件一致性:黑鹰涂装、运输机编号风格、波猫地面车辆迷彩在跨镜头保持一致。
- 时间连续性:夜间到拂晓过渡,光线需逐步变化,不可突变白天。
- 连续伤痕规则:血迹扩散、灰尘堆积、装备磨损按时间递增,不可“重置”。
- 镜头语言约束:爆炸不过曝、枪口焰不过度拉长、烟尘保留体积光层次。
- 语种一致性:鹰酱侧仅英语、波猫侧仅波斯语;不得跨阵营混用口语。
## 音频后期建议
- BGM三段式
- 00:00-01:00低频压迫 + 战争环境声主导
- 01:00-02:30节奏加速、打击乐增强
- 02:30-03:00弦乐收束、留白
- 枪炮声做空间方位:左/右声道随机位变化,增强临场感。
- 关键对白建议保留无线电失真,提升军事纪实感。
- 语言音色区分:英语通话保持北美军用电台质感;波斯语通话保持短波压缩感与环境底噪。
## 声音与特效细节刻画清单(执行版)
- 声音分轨建议至少8轨
- `DX`:角色对白/无线电300Hz以下滚降加入轻微带限失真
- `FX-GUN`:枪声与抛壳(近景强调机械复进声,远景以混响尾音为主)。
- `FX-EXP`:爆炸与破片(分“初爆/碎片/回响”三层,避免单层大轰鸣)。
- `FX-AIR`:固定翼与旋翼(区分掠过、悬停、远离三种多普勒曲线)。
- `FX-FOLEY`:脚步、布料、挂具碰撞、拖拽声。
- `AMB-DAYNIGHT`:风沙/城市远噪/战场底噪,按夜到黎明逐步抬高高频空气感。
- `UI`HUD提示、告警蜂鸣、心率仪。
- `MUS`三段式BGM。
- 关键时间点声音重心:
- `00:20-00:35`击落段导弹尖啸由右后声像切入命中瞬间做0.2-0.4秒闷听觉模拟。
- `01:30-02:00`(首轮回收段):旋翼低频与地面曳光弹破空声交替压制,对白仅保留关键词。
- `02:15-02:35`连环战损段运输机爆炸与Rescue-2坠毁分开设计频段避免低频互相遮蔽。
- `02:45-03:00`(撤离段):枪声快速衰减到远景,心率监测与呼吸机接管听觉焦点。
- 特效VFX颗粒度要求
- 火焰颜色分层:近白芯 + 橙黄主体 + 黑烟边缘,不使用纯色“贴图火”。
- 破片运动遵循抛物线与空气阻力,远小近大,禁止匀速直线飞散。
- 曳光弹亮度受烟尘遮挡衰减,不可全程同亮。
- 夜战镜头保留暗部细节,避免“黑成一片”或“亮如白天”。

View File

@@ -23,6 +23,7 @@ app.use(
},
})
);
app.use("/assets", express.static(path.join(repoRoot, "assets")));
app.use(express.static(path.join(__dirname, "public")));
app.get("/api/health", (_req, res) => {
@@ -475,4 +476,3 @@ const port = Number(process.env.PORT || 3000);
process.exit(1);
}
})();

File diff suppressed because it is too large Load Diff