|
|
|
import json |
|
|
|
|
|
def create_story_breakdown_prompt(user_idea, genre="sci-fi", mood="suspenseful", num_scenes=3): |
|
return f""" |
|
You are an expert screenwriter and visual storyteller. Based on: "{user_idea}", genre: "{genre}", mood: "{mood}". |
|
Generate a {num_scenes}-scene story breakdown. For each scene: |
|
1. scene_number (int) |
|
2. emotional_beat (str): Short title for the scene's core feeling. |
|
3. setting_description (str): Vivid description (30-50 words). |
|
4. characters_involved (list of str): Names of characters. |
|
5. key_action (str): Main event for video overlay (15-20 words). |
|
6. dialogue_snippet (str): Brief impactful dialogue. |
|
7. visual_style_suggestion (str): Keywords for visual style. |
|
8. camera_angle_suggestion (str): Specific camera shot. |
|
Output ONLY the JSON list of scenes. Example: |
|
{{ "scene_number": 1, "emotional_beat": "Tense Standoff", "setting_description": "Rain-slicked, neon-drenched alleyway...", "characters_involved": ["Detective Kaito", "Informant"], "key_action": "Kaito cautiously approaches a nervous informant.", "dialogue_snippet": "Informant: 'They know...'", "visual_style_suggestion": "Neo-noir, cyberpunk...", "camera_angle_suggestion": "Medium shot..."}} |
|
[{{"scene1_details..."}}, {{"scene2_details..."}}] |
|
""" |
|
|
|
|
|
|
|
def create_image_prompt_from_scene_data(scene_data, character_definitions=None, global_style_reference=""): |
|
emotional_beat_title = scene_data.get('emotional_beat', 'A cinematic scene') |
|
setting_desc = scene_data.get('setting_description', 'A visually interesting setting.') |
|
key_action_desc = scene_data.get('key_action', 'A significant moment unfolds.') |
|
characters_involved_in_scene = scene_data.get('characters_involved', []) |
|
character_prompt_segments = [] |
|
if characters_involved_in_scene: |
|
for char_name_from_scene in characters_involved_in_scene: |
|
char_name_clean = char_name_from_scene.strip(); char_lookup_key = char_name_clean.lower() |
|
if character_definitions and char_lookup_key in character_definitions: |
|
character_prompt_segments.append(f"{char_name_clean} (described as: {character_definitions[char_lookup_key]})") |
|
else: character_prompt_segments.append(char_name_clean) |
|
characters_narrative = "" |
|
if character_prompt_segments: |
|
if len(character_prompt_segments) == 1: characters_narrative = f"The main character is {character_prompt_segments[0]}." |
|
else: characters_narrative = f"The scene features {', '.join(character_prompt_segments[:-1])}, and {character_prompt_segments[-1]}." |
|
narrative_prompt = f"Scene Number: {scene_data.get('scene_number', 'N/A')}. Setting: {setting_desc}. {characters_narrative} Key Action: {key_action_desc}. Emotional Tone: {scene_data.get('emotional_beat', '')}." |
|
style_instructions = f"Visual Style: {scene_data.get('visual_style_suggestion', 'cinematic, photorealistic')}." |
|
if global_style_reference: style_instructions += f" Specific style reference: {global_style_reference}." |
|
camera_instructions = f"Camera Perspective: {scene_data.get('camera_angle_suggestion', 'eye-level medium shot')}." |
|
full_prompt = (f"Generate an ultra-detailed, photorealistic, and highly cinematic digital painting or concept art image. " |
|
f"The image should depict: '{emotional_beat_title}'. Narrative Context: {narrative_prompt} " |
|
f"Artistic & Technical Instructions: {style_instructions} {camera_instructions} " |
|
f"Emphasize: Cinematic composition, dramatic lighting, rich textures, depth of field, strong atmospheric effects. " |
|
f"The image must feel like a high-quality film still. Pay close attention to character details.") |
|
return " ".join(full_prompt.split()) |
|
|
|
|
|
|
|
def create_narration_script_prompt(story_scenes_data, overall_mood, overall_genre): |
|
""" |
|
Generates a prompt for Gemini to write a concise narration script for an animatic, |
|
covering all provided scenes. |
|
""" |
|
scenes_summary = [] |
|
for i, scene in enumerate(story_scenes_data): |
|
scenes_summary.append( |
|
f"Scene {scene.get('scene_number', i+1)} ({scene.get('emotional_beat','')}):\n" |
|
f"- Setting: {scene.get('setting_description','')}\n" |
|
f"- Key Action: {scene.get('key_action','')}\n" |
|
f"- Characters: {', '.join(scene.get('characters_involved',[]))}\n" |
|
f"- Implied Dialogue/Thought: {scene.get('dialogue_snippet','(none)')}" |
|
) |
|
|
|
full_summary_text = "\n\n".join(scenes_summary) |
|
|
|
prompt = f""" |
|
You are a professional scriptwriter for documentary-style voiceovers and cinematic trailers. |
|
Given the following scene summaries for an animatic storyboard: |
|
|
|
--- SCENE SUMMARIES --- |
|
{full_summary_text} |
|
--- END SCENE SUMMARIES --- |
|
|
|
Overall Story Genre: {overall_genre} |
|
Overall Story Mood: {overall_mood} |
|
|
|
Write a concise, engaging, and continuous narration script that flows smoothly across these scenes. |
|
The narration should enhance the visual storytelling, not just describe what's visible. |
|
It should set the tone, build suspense or emotion, and connect the scenes thematically. |
|
The tone of the narration should match the overall mood and genre. |
|
Keep the narration for each scene relatively brief (1-2 short sentences per scene on average). |
|
The total narration should be suitable for a short animatic (e.g., if 3 scenes at 4 seconds each, total ~12 seconds of video, so narration should be ~60-90 words max). |
|
Do not include scene numbers or explicit directives like "(Voiceover)" in the output. Just provide the pure narration text. |
|
Focus on evocative language. |
|
|
|
Example (if scenes were about a space discovery): |
|
"The red dust of Mars whispered secrets of a forgotten age. Deep within the chasm, an impossible structure pulsed with an alien light, beckoning humanity towards a destiny unknown, and perhaps, a truth too vast to comprehend." |
|
|
|
Output ONLY the narration script text. |
|
""" |
|
return " ".join(prompt.split()) |
|
|
|
|
|
|
|
def create_scene_regeneration_prompt(original_scene_data, user_feedback, full_story_context=None): |
|
context_str = f"Original scene (Scene Number {original_scene_data.get('scene_number')}):\n{json.dumps(original_scene_data, indent=2)}\n\n" |
|
if full_story_context: context_str += f"Full story context:\n{json.dumps(full_story_context, indent=2)}\n\n" |
|
return (f"Expert script doctor. Original scene:\n{context_str}User feedback: \"{user_feedback}\"\n" |
|
f"Regenerate ONLY the JSON for this single scene, incorporating feedback. Maintain structure. 'key_action' max 15-20 words.") |
|
|
|
|
|
def create_visual_regeneration_prompt(original_image_prompt_text, user_feedback_on_visuals, scene_data, character_definitions=None, global_style_reference=""): |
|
scene_context_summary = (f"Scene: {scene_data.get('emotional_beat', '')}. Setting: {scene_data.get('setting_description', '')}. " |
|
f"Action: {scene_data.get('key_action', '')}. Characters: {', '.join(scene_data.get('characters_involved',[]))}.") |
|
char_details_str = "Relevant characters: " + (", ".join([f"{name} ({desc})" for name, desc in character_definitions.items() if name.lower() in [cn.lower() for cn in scene_data.get('characters_involved',[])]])) if character_definitions else "None specified." |
|
return (f"AI assistant for refining DALL-E 3 prompts. Original Scene Context: {scene_context_summary} {char_details_str} " |
|
f"Global Style: \"{global_style_reference}\". Original DALL-E 3 prompt was: \"{original_image_prompt_text}\". " |
|
f"User feedback on visual: \"{user_feedback_on_visuals}\". Generate a new, revised DALL-E 3 prompt. " |
|
f"It must be ultra-detailed, photorealistic, cinematic, film/game quality. Translate feedback into concrete visual descriptions. " |
|
f"Respect character descriptions. Output ONLY the new prompt string.") |