|
|
@@ -4420,7 +4420,7 @@ Q版卡通风格,头大身小,造型圆润可爱,线条简单,色彩明
|
|
|
3.以上两条要求对修改主体角色或场景不生效,允许用户调整主体角色说明和场景描述等
|
|
|
4.用户如果要求你帮忙写一个故事或者剧本,此类要求不属于与剧本无关,请帮助用户完成请求
|
|
|
5.强制按照示例格式返回内容,不要更改格式或随意增加符号
|
|
|
- 6.如果给出的本集剧情内容是剧本格式,则不要改动剧本内容,严格按照剧本的旁白和台词进行分镜的策划\n
|
|
|
+ 6.如果给出的本集剧情内容是剧本格式,则不要改动剧本内容,严格按照剧本的旁白和台词进行分镜的策划,不要跳过任何剧情\n
|
|
|
普通要求:
|
|
|
1.剧集标题必须与文档内容高度相关,剧集序号是{$episode_number}。
|
|
|
{$role_demo}
|
|
|
@@ -4626,7 +4626,7 @@ Q版卡通风格,头大身小,造型圆润可爱,线条简单,色彩明
|
|
|
'model' => $model,
|
|
|
'messages' => $messages,
|
|
|
// 'max_tokens' => 8192,
|
|
|
- 'temperature' => 0.7,
|
|
|
+ 'temperature' => 0.2,
|
|
|
'frequency_penalty' => 0,
|
|
|
'presence_penalty' => 0,
|
|
|
'response_format' => ['type' => 'text'],
|
|
|
@@ -5462,7 +5462,7 @@ Q版卡通风格,头大身小,造型圆润可爱,线条简单,色彩明
|
|
|
$episode['episode_id'] = $episode_id;
|
|
|
$episode['roles'] = $merged_roles;
|
|
|
$episode['scenes'] = $merged_scenes;
|
|
|
- $episode['acts'] = isset($episode_arr['acts']) && is_array($episode_arr['acts']) ? $episode_arr['acts'] : [];
|
|
|
+ // $episode['acts'] = isset($episode_arr['acts']) && is_array($episode_arr['acts']) ? $episode_arr['acts'] : [];
|
|
|
yield [
|
|
|
'type' => 'done',
|
|
|
'episode' => $episode,
|
|
|
@@ -5532,6 +5532,8 @@ Q版卡通风格,头大身小,造型圆润可爱,线条简单,色彩明
|
|
|
|
|
|
// 获取 mp_animes 表中的全局 roles 和 scenes 用于对比
|
|
|
$anime = DB::table('mp_animes')->where('id', $anime_id)->first();
|
|
|
+ $ace_mode = getProp($anime, 'ace_mode');
|
|
|
+ dLog('deepseek')->info('ace_mode', ['ace_mode' => $ace_mode]);
|
|
|
$global_roles = json_decode(getProp($anime, 'roles'), true);
|
|
|
$global_scenes = json_decode(getProp($anime, 'scenes'), true);
|
|
|
$global_roles = is_array($global_roles) ? $global_roles : [];
|
|
|
@@ -5663,6 +5665,10 @@ Q版卡通风格,头大身小,造型圆润可爱,线条简单,色彩明
|
|
|
'voice_type' => getProp($prev_role, 'voice_type'),
|
|
|
'voice_audio_url' => getProp($prev_role, 'voice_audio_url'),
|
|
|
];
|
|
|
+ $voice_prompt = getProp($prev_role, 'voice_prompt');
|
|
|
+ if ($voice_prompt) {
|
|
|
+ $previous_roles_voice[$role_name]['voice_prompt'] = $voice_prompt;
|
|
|
+ }
|
|
|
}
|
|
|
}
|
|
|
}
|
|
|
@@ -5678,10 +5684,13 @@ Q版卡通风格,头大身小,造型圆润可爱,线条简单,色彩明
|
|
|
$role['voice_name'] = $previous_roles_voice[$role_name]['voice_name'];
|
|
|
$role['voice_type'] = $previous_roles_voice[$role_name]['voice_type'];
|
|
|
$role['voice_audio_url'] = $previous_roles_voice[$role_name]['voice_audio_url'];
|
|
|
+ // 如果上一集有 voice_prompt 则继承,否则跳过
|
|
|
+ if (!empty($previous_roles_voice[$role_name]['voice_prompt'])) {
|
|
|
+ $role['voice_prompt'] = $previous_roles_voice[$role_name]['voice_prompt'];
|
|
|
+ }
|
|
|
}
|
|
|
}
|
|
|
unset($role); // 解除引用
|
|
|
-
|
|
|
// 更新 role_arr 以便后续使用
|
|
|
$role_arr = [];
|
|
|
foreach ($merged_roles as $item) {
|
|
|
@@ -5697,33 +5706,14 @@ Q版卡通风格,头大身小,造型圆润可爱,线条简单,色彩明
|
|
|
continue;
|
|
|
}
|
|
|
|
|
|
- foreach ($act_segments as $segment) {
|
|
|
- $voice_actor = getProp($segment, 'voice_actor');
|
|
|
-
|
|
|
- // 优先从上一集继承音色数据
|
|
|
- $timbre_info = [];
|
|
|
- if (isset($previous_roles_voice[$voice_actor])) {
|
|
|
- // 从上一集继承音色数据
|
|
|
- $timbre_info = $previous_roles_voice[$voice_actor];
|
|
|
- } elseif (isset($role_arr[$voice_actor])) {
|
|
|
- // 使用当前集的主体音色数据
|
|
|
- $timbre_info = $role_arr[$voice_actor];
|
|
|
- }
|
|
|
-
|
|
|
- $voice_type = getProp($timbre_info, 'voice_type');
|
|
|
- $timbre_emotion = DB::table('mp_timbres')->where('timbre_type', $voice_type)->value('emotion');
|
|
|
- if ($timbre_emotion) {
|
|
|
- $timbre_emotion = explode(',', $timbre_emotion);
|
|
|
- } else {
|
|
|
- $timbre_emotion = [];
|
|
|
- }
|
|
|
-
|
|
|
- $emotion = getProp($segment, 'emotion', '中性');
|
|
|
- if (!in_array($emotion, $timbre_emotion)) {
|
|
|
- $emotion = '中性';
|
|
|
+ if ((int)$ace_mode === 1) {
|
|
|
+ // ace_mode=1: 按幕合并 segment_content,每幕只存一条记录
|
|
|
+ $merged_parts = [];
|
|
|
+ foreach ($act_segments as $seg) {
|
|
|
+ $seg_num = getProp($seg, 'segment_number');
|
|
|
+ $seg_content = getProp($seg, 'segment_content');
|
|
|
+ $merged_parts[] = "【镜头{$seg_num}】{$seg_content}\n";
|
|
|
}
|
|
|
- $emotion_type = isset($emotion_list[$emotion]) ? $emotion_list[$emotion] : 'neutral';
|
|
|
-
|
|
|
$segments[] = [
|
|
|
'anime_id' => $anime_id,
|
|
|
'episode_id' => $episode_id,
|
|
|
@@ -5731,31 +5721,71 @@ Q版卡通风格,头大身小,造型圆润可爱,线条简单,色彩明
|
|
|
'act_number' => getProp($act, 'act_number'),
|
|
|
'act_title' => getProp($act, 'act_title'),
|
|
|
'act_duration' => getProp($act, 'act_duration'),
|
|
|
- 'segment_id' => getProp($segment, 'segment_id'),
|
|
|
- 'segment_number' => getProp($segment, 'segment_number'),
|
|
|
- 'segment_content' => getProp($segment, 'segment_content'),
|
|
|
- 'description' => getProp($segment, 'description'),
|
|
|
- 'composition' => getProp($segment, 'composition'),
|
|
|
- 'camera_movement' => getProp($segment, 'camera_movement'),
|
|
|
- 'voice_actor' => $voice_actor,
|
|
|
- 'dialogue' => getProp($segment, 'dialogue'),
|
|
|
- 'frame_type' => getProp($segment, 'frame_type'),
|
|
|
- 'scene' => getProp($segment, 'scene'),
|
|
|
- 'characters' => getProp($segment, 'characters'),
|
|
|
- 'tail_frame' => getProp($segment, 'tail_frame'),
|
|
|
- 'voice_name' => getProp($timbre_info, 'voice_name'),
|
|
|
- 'voice_type' => $voice_type,
|
|
|
- 'voice_audio_url' => getProp($timbre_info, 'voice_audio_url'),
|
|
|
- 'emotion' => $emotion,
|
|
|
- 'emotion_type' => $emotion_type,
|
|
|
- 'gender' => getProp($segment, 'gender', '0'),
|
|
|
- 'speed_ratio' => getProp($segment, 'speed_ratio', 0),
|
|
|
- 'loudness_ratio' => getProp($segment, 'loudness_ratio', 0),
|
|
|
- 'emotion_scale' => getProp($segment, 'emotion_scale', 4),
|
|
|
- 'pitch' => getProp($segment, 'pitch', 0),
|
|
|
+ 'act_content' => implode("\n", $merged_parts),
|
|
|
'created_at' => $now,
|
|
|
'updated_at' => $now
|
|
|
];
|
|
|
+ } else {
|
|
|
+ foreach ($act_segments as $segment) {
|
|
|
+ $voice_actor = getProp($segment, 'voice_actor');
|
|
|
+
|
|
|
+ // 优先从上一集继承音色数据
|
|
|
+ $timbre_info = [];
|
|
|
+ if (isset($previous_roles_voice[$voice_actor])) {
|
|
|
+ // 从上一集继承音色数据
|
|
|
+ $timbre_info = $previous_roles_voice[$voice_actor];
|
|
|
+ } elseif (isset($role_arr[$voice_actor])) {
|
|
|
+ // 使用当前集的主体音色数据
|
|
|
+ $timbre_info = $role_arr[$voice_actor];
|
|
|
+ }
|
|
|
+
|
|
|
+ $voice_type = getProp($timbre_info, 'voice_type');
|
|
|
+ $timbre_emotion = DB::table('mp_timbres')->where('timbre_type', $voice_type)->value('emotion');
|
|
|
+ if ($timbre_emotion) {
|
|
|
+ $timbre_emotion = explode(',', $timbre_emotion);
|
|
|
+ } else {
|
|
|
+ $timbre_emotion = [];
|
|
|
+ }
|
|
|
+
|
|
|
+ $emotion = getProp($segment, 'emotion', '中性');
|
|
|
+ if (!in_array($emotion, $timbre_emotion)) {
|
|
|
+ $emotion = '中性';
|
|
|
+ }
|
|
|
+ $emotion_type = isset($emotion_list[$emotion]) ? $emotion_list[$emotion] : 'neutral';
|
|
|
+
|
|
|
+ $segments[] = [
|
|
|
+ 'anime_id' => $anime_id,
|
|
|
+ 'episode_id' => $episode_id,
|
|
|
+ 'episode_number' => $episode_number,
|
|
|
+ 'act_number' => getProp($act, 'act_number'),
|
|
|
+ 'act_title' => getProp($act, 'act_title'),
|
|
|
+ 'act_duration' => getProp($act, 'act_duration'),
|
|
|
+ 'segment_id' => getProp($segment, 'segment_id'),
|
|
|
+ 'segment_number' => getProp($segment, 'segment_number'),
|
|
|
+ 'segment_content' => getProp($segment, 'segment_content'),
|
|
|
+ 'description' => getProp($segment, 'description'),
|
|
|
+ 'composition' => getProp($segment, 'composition'),
|
|
|
+ 'camera_movement' => getProp($segment, 'camera_movement'),
|
|
|
+ 'voice_actor' => $voice_actor,
|
|
|
+ 'dialogue' => getProp($segment, 'dialogue'),
|
|
|
+ 'frame_type' => getProp($segment, 'frame_type'),
|
|
|
+ 'scene' => getProp($segment, 'scene'),
|
|
|
+ 'characters' => getProp($segment, 'characters'),
|
|
|
+ 'tail_frame' => getProp($segment, 'tail_frame'),
|
|
|
+ 'voice_name' => getProp($timbre_info, 'voice_name'),
|
|
|
+ 'voice_type' => $voice_type,
|
|
|
+ 'voice_audio_url' => getProp($timbre_info, 'voice_audio_url'),
|
|
|
+ 'emotion' => $emotion,
|
|
|
+ 'emotion_type' => $emotion_type,
|
|
|
+ 'gender' => getProp($segment, 'gender', '0'),
|
|
|
+ 'speed_ratio' => getProp($segment, 'speed_ratio', 0),
|
|
|
+ 'loudness_ratio' => getProp($segment, 'loudness_ratio', 0),
|
|
|
+ 'emotion_scale' => getProp($segment, 'emotion_scale', 4),
|
|
|
+ 'pitch' => getProp($segment, 'pitch', 0),
|
|
|
+ 'created_at' => $now,
|
|
|
+ 'updated_at' => $now
|
|
|
+ ];
|
|
|
+ }
|
|
|
}
|
|
|
}
|
|
|
|
|
|
@@ -5773,7 +5803,37 @@ Q版卡通风格,头大身小,造型圆润可爱,线条简单,色彩明
|
|
|
Utils::throwError('20003:分镜内容保存失败');
|
|
|
}
|
|
|
}
|
|
|
+ dLog('deepseek')->info('segments', $segments);
|
|
|
|
|
|
+ // ace_mode=1: acts 返回值按合并格式调整
|
|
|
+ if ((int)$ace_mode === 1) {
|
|
|
+ $restructured_acts = [];
|
|
|
+ foreach ($acts as $act) {
|
|
|
+ $act_segments = getProp($act, 'segments', []);
|
|
|
+ if (!is_array($act_segments)) {
|
|
|
+ continue;
|
|
|
+ }
|
|
|
+ $merged_parts = [];
|
|
|
+ foreach ($act_segments as $seg) {
|
|
|
+ $seg_num = getProp($seg, 'segment_number');
|
|
|
+ $seg_content = getProp($seg, 'segment_content');
|
|
|
+ $merged_parts[] = "【镜头{$seg_num}】{$seg_content}\n";
|
|
|
+ }
|
|
|
+ $restructured_acts[] = [
|
|
|
+ 'anime_id' => $anime_id,
|
|
|
+ 'episode_id' => $episode_id,
|
|
|
+ 'episode_number' => $episode_number,
|
|
|
+ 'act_number' => getProp($act, 'act_number'),
|
|
|
+ 'act_title' => getProp($act, 'act_title'),
|
|
|
+ 'act_duration' => getProp($act, 'act_duration'),
|
|
|
+ 'act_content' => implode("\n", $merged_parts),
|
|
|
+ 'created_at' => $now,
|
|
|
+ 'updated_at' => $now,
|
|
|
+ ];
|
|
|
+ }
|
|
|
+ $acts = $restructured_acts;
|
|
|
+ }
|
|
|
+ dLog('deepseek')->info('$acts', $acts);
|
|
|
$episode['episode_id'] = $episode_id;
|
|
|
$episode['roles'] = $merged_roles;
|
|
|
$episode['scenes'] = $merged_scenes;
|