Spaces:
Running
Running
| JEWELLERY_ANALYSIS_PROMPT = """ | |
| Analyze this jewellery product image. | |
| Return: | |
| 1. jewellery type | |
| 2. silhouette and structure | |
| 3. likely metal finish | |
| 4. gemstones or stone style | |
| 5. setting style | |
| 6. motifs and ornamentation | |
| 7. colors | |
| 8. design style | |
| 9. target audience and occasion | |
| 10. what must remain recognizable | |
| Focus only on visible factual product details. | |
| Do not suggest redesign ideas. | |
| """.strip() | |
| def build_design_directions_prompt(analysis: str) -> str: | |
| return f""" | |
| You are a luxury jewellery product design director. | |
| PRODUCT ANALYSIS: | |
| {analysis} | |
| TASK: | |
| Generate exactly 6 new jewellery design concepts inspired by the reference product. | |
| SIMILARITY TARGET: | |
| - Each new design should remain about 60-65% similar to the reference product | |
| - The product category must remain the same | |
| - The core design language should remain recognizable | |
| - The overall luxury style should remain related to the reference | |
| ALLOWED CHANGES: | |
| - Change metal finish | |
| - Change gemstone color | |
| - Change accent stones | |
| - Change ornamentation | |
| - Change surface texture | |
| - Change engraving style | |
| - Change motif details | |
| - Change decorative borders | |
| - Change pavé density | |
| - Change luxury styling | |
| - Slightly change proportions | |
| - Slightly change silhouette | |
| - Add or remove small decorative elements | |
| NOT ALLOWED: | |
| - Do not change product category | |
| - Do not create a completely unrelated design | |
| - Do not make it look like a different jewellery type | |
| - Do not ignore the reference product | |
| - Do not create a generic jewellery item | |
| COLLECTION RULE: | |
| Each design must feel like a new SKU in the same collection. | |
| OUTPUT: | |
| Return JSON only. | |
| """.strip() | |
| def build_design_preview_prompt(direction: dict, analysis: str) -> str: | |
| return f""" | |
| Use the uploaded jewellery image as a design inspiration reference, not an exact product lock. | |
| PRODUCT ANALYSIS: | |
| {analysis} | |
| NEW DESIGN DIRECTION: | |
| {direction.get("name", "")} | |
| DESIGN PHILOSOPHY: | |
| {direction.get("design_philosophy", "")} | |
| WHAT TO KEEP FROM REFERENCE: | |
| {direction.get("what_to_keep", "")} | |
| WHAT TO CHANGE: | |
| {direction.get("what_to_change", "")} | |
| MATERIAL CHANGES: | |
| {direction.get("material_changes", "")} | |
| GEMSTONE CHANGES: | |
| {direction.get("gemstone_changes", "")} | |
| IMAGE GENERATION INSTRUCTIONS: | |
| {direction.get("image_generation_prompt", "")} | |
| SIMILARITY TARGET: | |
| - Generate a new jewellery product design that is 60-65% similar to the reference image | |
| - Keep the same jewellery category | |
| - Keep the same general design family | |
| - Keep the same core luxury style | |
| - Keep enough visual DNA so it feels related to the reference | |
| - It should look like a new SKU from the same collection | |
| ALLOWED DESIGN CHANGES: | |
| - Change decorative details | |
| - Change gemstone color or accent stones | |
| - Change metal finish | |
| - Change surface texture | |
| - Change engraving style | |
| - Change motif details | |
| - Change pavé density | |
| - Slightly adjust proportions | |
| - Slightly adjust silhouette | |
| - Add or remove small decorative elements | |
| NOT ALLOWED: | |
| - Do not create an unrelated jewellery product | |
| - Do not change jewellery category | |
| - Do not make it look like a completely different product type | |
| - Do not create a generic design | |
| - Do not include model, hand, face, ear, or human body parts | |
| OUTPUT REQUIREMENTS: | |
| - Product-only jewellery image | |
| - No model | |
| - No hand | |
| - No human | |
| - Clean luxury catalogue background | |
| - Photorealistic product photography | |
| - Real metal reflections | |
| - Real gemstone reflections | |
| - Sharp jewellery details | |
| """.strip() | |
| def build_product_description_prompt(direction: dict, analysis: str) -> str: | |
| return f""" | |
| You are a luxury jewellery copywriter. | |
| PRODUCT ANALYSIS: | |
| {analysis} | |
| DESIGN NAME: | |
| {direction.get("name", "")} | |
| DESIGN DETAILS: | |
| - Design philosophy: {direction.get("design_philosophy", "")} | |
| - What to keep: {direction.get("what_to_keep", "")} | |
| - What to change: {direction.get("what_to_change", "")} | |
| - Material changes: {direction.get("material_changes", "")} | |
| - Gemstone changes: {direction.get("gemstone_changes", "")} | |
| TASK: | |
| Write an ecommerce product description for this jewellery design using exactly | |
| this structure: | |
| 1. First paragraph: introduce the product using its exact design name, and | |
| describe its style and standout features in an elegant, evocative tone. | |
| 2. Blank line. | |
| 3. Second paragraph: describe who it's perfect for and how it can be styled or worn. | |
| 4. Blank line. | |
| 5. A line reading exactly "Specifications" followed by a bullet list using "•" | |
| with exactly these fields, in this order: | |
| • Material | |
| • Finish | |
| • Stone | |
| • Weight | |
| • Closure | |
| Infer realistic values for Weight and Closure appropriate for this jewellery | |
| type when they are not explicitly given. Keep all specifications consistent | |
| with the design details above. | |
| Do not use markdown formatting such as bold, asterisks, or headings other than | |
| the word "Specifications". Return only the description text, nothing else. | |
| """.strip() | |
| def build_user_instruction_block(user_prompt: str = "") -> str: | |
| if not user_prompt or not user_prompt.strip(): | |
| return "" | |
| return f""" | |
| USER CREATIVE INSTRUCTIONS: | |
| {user_prompt} | |
| Apply user instructions only to: | |
| - background | |
| - model | |
| - lighting | |
| - mood | |
| - styling | |
| - pose | |
| - camera angle | |
| - composition | |
| Never apply user instructions to the jewellery design itself. | |
| """.strip() | |
| def build_base_product_lock( | |
| selected_campaign: dict, | |
| analysis: str, | |
| ) -> str: | |
| selected_name = selected_campaign.get("name", "Selected campaign") | |
| direction = selected_campaign.get("direction", {}) | |
| return f""" | |
| PRODUCT REFERENCE LOCK: | |
| Use the selected jewellery image as the exact locked product reference. | |
| The selected image is the approved final product design. | |
| PRODUCT ANALYSIS: | |
| {analysis} | |
| SELECTED DESIGN: | |
| {selected_name} | |
| DESIGN DETAILS: | |
| {direction.get("image_generation_prompt", "")} | |
| ABSOLUTE PRODUCT LOCK: | |
| - The jewellery must remain visually identical to the selected reference image | |
| - Do not redesign the jewellery | |
| - Do not create a new jewellery variant | |
| - Do not beautify or enhance the jewellery design | |
| - Do not add stones | |
| - Do not remove stones | |
| - Do not change gemstone color | |
| - Do not change metal color | |
| - Do not change shape, silhouette, dangling elements, hoop, clasp, chain, setting, engraving, motifs, or proportions | |
| - Do not make the product more detailed | |
| - Do not make the product more ornate | |
| - Treat the jewellery as the same real physical item photographed in a new scene | |
| """.strip() | |
| REALISM_BLOCK = """ | |
| REALISM REQUIREMENTS: | |
| - Photorealistic commercial photography | |
| - Real metal reflections | |
| - Real gemstone refraction | |
| - Natural shadows | |
| - Realistic contact shadows | |
| - Physically realistic lighting | |
| - Realistic depth of field | |
| - No CGI look | |
| - No cartoon look | |
| - No fantasy styling | |
| - No plastic skin | |
| - No artificial jewellery glow | |
| - No over-polished surfaces | |
| """.strip() | |
| FLAT_LAY_PRODUCT_RULES = """ | |
| FLAT LAY PRODUCT RULES: | |
| - The jewellery must look exactly like the selected reference image | |
| - Do not redesign the product | |
| - Do not create a new variant | |
| - Do not change stones | |
| - Do not change stone placement | |
| - Do not change metal color | |
| - Do not change shape | |
| - Do not change silhouette | |
| - Do not change engraving | |
| - Do not change proportions | |
| - Do not add new details | |
| - Do not remove existing details | |
| - Do not make the jewellery more decorative | |
| - Do not simplify the jewellery | |
| - Use the exact same product design from the selected image | |
| """.strip() | |
| FLAT_LAY_COMPOSITION_RULES = """ | |
| FLAT LAY COMPOSITION: | |
| - Product-only image | |
| - No model | |
| - No hands | |
| - No human body parts | |
| - No extra jewellery | |
| - Clean premium background | |
| - Soft luxury lighting | |
| - Elegant natural shadows | |
| - High-end jewellery catalogue photography | |
| - Jewellery clearly visible | |
| ONLY CHANGE: | |
| - background | |
| - lighting | |
| - shadows | |
| - camera angle | |
| - product placement | |
| - luxury catalogue composition | |
| """.strip() | |
| MODEL_REALISM_RULES = """ | |
| REALISTIC HUMAN REQUIREMENTS: | |
| - Real adult human model | |
| - Natural face, not fashion-doll-like | |
| - Natural skin texture with visible pores | |
| - Slight natural skin imperfections | |
| - Natural facial asymmetry | |
| - Natural eyelashes and eyebrows | |
| - Jewellery clearly visible and in focus | |
| - Realistic jewellery scale | |
| - Natural skin contact shadows | |
| - Natural neck and jawline anatomy | |
| """.strip() | |
| MODEL_PHOTOGRAPHY_RULES = """ | |
| MODEL PHOTOGRAPHY STYLE: | |
| - Real DSLR / mirrorless camera photograph | |
| - 85mm portrait lens look | |
| - Soft window light or softbox light | |
| - Realistic depth of field | |
| - Natural background blur | |
| - Realistic skin tones | |
| - Realistic shadows | |
| - Real metal reflections | |
| - Real gemstone reflections | |
| - Commercial jewellery product photography | |
| - Clean premium background | |
| - Sharp focus on jewellery, natural focus falloff on face | |
| """.strip() | |
| MODEL_AVOID_RULES = """ | |
| STRICTLY AVOID: | |
| - CGI face | |
| - 3D render | |
| - Plastic skin | |
| - Wax skin | |
| - Airbrushed skin | |
| - Overly smooth face | |
| - Perfect doll-like model | |
| - Emotionless model | |
| - Blank facial expression | |
| - Same expression across all model outputs | |
| - Fantasy beauty portrait | |
| - Glamour retouching | |
| - Artificial jewellery glow | |
| - Unrealistic jewellery size | |
| - Extra jewellery | |
| - Distorted ear | |
| - Cartoon look | |
| - Painting look | |
| - Illustration look | |
| - AI-generated fashion poster look | |
| """.strip() | |
| MODEL_PRODUCT_LOCK = """ | |
| MODEL PRODUCT LOCK: | |
| - The jewellery must match the selected reference image | |
| - Do not change the jewellery design | |
| - Do not change stone placement | |
| - Do not change metal color | |
| - Do not change gemstone color | |
| - Do not add details | |
| - Do not remove details | |
| - Do not make a new jewellery variant | |
| """.strip() | |
| FLAT_LAY_VARIATIONS = [ | |
| { | |
| "angle": "true overhead 90-degree flat lay", | |
| "composition": "jewellery centered with symmetrical spacing, clean premium catalogue layout", | |
| }, | |
| { | |
| "angle": "slightly angled 45-degree top-down flat lay", | |
| "composition": "jewellery placed diagonally across the frame with elegant negative space", | |
| }, | |
| { | |
| "angle": "low oblique side-angle flat lay, around 25-30 degrees from the surface", | |
| "composition": "jewellery positioned off-center with visible depth, soft foreground blur, and natural shadows", | |
| }, | |
| ] | |
| MODEL_VARIATIONS = [ | |
| { | |
| "emotion": "soft confident smile", | |
| "pose": "gentle three-quarter face angle with relaxed eyes and calm luxury expression", | |
| }, | |
| { | |
| "emotion": "serene romantic expression", | |
| "pose": "slightly lowered gaze, peaceful face, elegant bridal catalogue mood", | |
| }, | |
| { | |
| "emotion": "subtle joyful expression", | |
| "pose": "natural candid smile, light warmth in the eyes, premium lifestyle jewellery mood", | |
| }, | |
| ] | |
| def build_flat_lay_prompt( | |
| base_product_lock: str, | |
| user_instruction_block: str, | |
| variation: dict, | |
| index: int, | |
| ) -> str: | |
| return f""" | |
| {base_product_lock} | |
| IMAGE TYPE: | |
| Luxury flat lay jewellery product photograph. | |
| {user_instruction_block} | |
| {REALISM_BLOCK} | |
| {FLAT_LAY_PRODUCT_RULES} | |
| MANDATORY FLAT LAY VARIATION: | |
| - Camera angle: {variation["angle"]} | |
| - Composition: {variation["composition"]} | |
| - This flat lay must look visually different from the other flat lay outputs | |
| - Do not repeat the same angle, crop, placement, or background arrangement | |
| - Keep the product fully visible and recognizable | |
| {FLAT_LAY_COMPOSITION_RULES} | |
| FINAL OUTPUT: | |
| Output must look like the same selected product photographed in a new luxury flat lay scene. | |
| Flat lay variation {index} | |
| """.strip() | |
| def build_model_prompt( | |
| base_product_lock: str, | |
| user_instruction_block: str, | |
| variation: dict, | |
| index: int, | |
| ) -> str: | |
| return f""" | |
| {base_product_lock} | |
| IMAGE TYPE: | |
| Realistic close-up product photography image of a real person wearing the exact same jewellery. | |
| The image should look like it was captured with a real professional camera, not generated by AI. | |
| {user_instruction_block} | |
| MANDATORY MODEL EMOTION VARIATION: | |
| - Model emotion: {variation["emotion"]} | |
| - Pose direction: {variation["pose"]} | |
| - The model must visibly show this emotion through eyes, lips, and facial expression | |
| - Each model image must have a different emotional mood | |
| - Keep emotion natural, subtle, premium, and commercially realistic | |
| - Do not make the expression exaggerated, theatrical, or artificial | |
| {MODEL_REALISM_RULES} | |
| {MODEL_PHOTOGRAPHY_RULES} | |
| {MODEL_AVOID_RULES} | |
| {MODEL_PRODUCT_LOCK} | |
| FINAL OUTPUT: | |
| Output must look like a real close-up jewellery photograph taken on a model. | |
| Model variation {index} | |
| """.strip() | |
| def build_product_closeup_prompt( | |
| base_product_lock: str, | |
| user_instruction_block: str, | |
| ) -> str: | |
| return f""" | |
| {base_product_lock} | |
| IMAGE TYPE: | |
| Extreme close-up macro product-only jewellery photograph. | |
| {user_instruction_block} | |
| {REALISM_BLOCK} | |
| MACRO REQUIREMENTS: | |
| - Product-only image | |
| - No model | |
| - No hands | |
| - No human body parts | |
| - Show realistic metal texture | |
| - Show realistic gemstone reflections | |
| - Sharp focus on jewellery details | |
| - Natural focus falloff and depth of field | |
| - Premium catalogue macro photography | |
| - Clean luxury background | |
| - Do not add new details | |
| - Only photograph the same product closer | |
| FINAL OUTPUT: | |
| Output must look like a real macro product photograph of the exact same jewellery. | |
| """.strip() | |
| def build_model_closeup_prompt( | |
| base_product_lock: str, | |
| user_instruction_block: str, | |
| ) -> str: | |
| return f""" | |
| {base_product_lock} | |
| IMAGE TYPE: | |
| Ultra-realistic close-up photograph of a real person wearing the exact same jewellery. | |
| The result must look like a real camera photo, not CGI or AI art. | |
| {user_instruction_block} | |
| MODEL CLOSEUP COMPOSITION: | |
| - Close-up of ear and side of face | |
| - Hair tucked behind ear | |
| - Ear fully visible | |
| - Jewellery is the main subject | |
| - Jewellery sharp and clearly visible | |
| - Natural face partially visible | |
| - Clean background | |
| - Realistic jewellery scale on ear | |
| - Natural, premium expression | |
| - Subtle emotion, not blank or emotionless | |
| MODEL CLOSEUP REALISM: | |
| - Natural skin pores | |
| - Slight natural skin texture | |
| - Realistic ear anatomy | |
| - Realistic hair strands | |
| - Natural skin color variations | |
| - Realistic contact shadows | |
| - Real metal reflections | |
| - Real gemstone reflections | |
| - Soft natural photography lighting | |
| - DSLR portrait photo style | |
| - Natural depth of field | |
| STRICTLY AVOID: | |
| - Plastic skin | |
| - Over-smoothed skin | |
| - CGI render | |
| - Doll face | |
| - Unrealistic perfect model | |
| - Over-retouched beauty campaign look | |
| - Fantasy styling | |
| - Artificial shine | |
| - Extra jewellery | |
| - Changed jewellery design | |
| - Distorted ear | |
| - Unrealistic earring placement | |
| - Blank facial expression | |
| PRODUCT LOCK: | |
| - Jewellery must be identical to selected reference | |
| - Same shape | |
| - Same stones | |
| - Same metal | |
| - Same proportions | |
| - Same design structure | |
| - No redesign | |
| FINAL OUTPUT: | |
| Output must look like a real commercial jewellery close-up photograph. | |
| """.strip() | |
| def create_final_image_prompts( | |
| selected_campaign: dict, | |
| analysis: str, | |
| user_prompt: str = "", | |
| ) -> list[dict]: | |
| base_product_lock = build_base_product_lock( | |
| selected_campaign=selected_campaign, | |
| analysis=analysis, | |
| ) | |
| user_instruction_block = build_user_instruction_block(user_prompt) | |
| prompts = [] | |
| for index, variation in enumerate(FLAT_LAY_VARIATIONS, start=1): | |
| prompts.append( | |
| { | |
| "type": "Flat lay", | |
| "prompt": build_flat_lay_prompt( | |
| base_product_lock=base_product_lock, | |
| user_instruction_block=user_instruction_block, | |
| variation=variation, | |
| index=index, | |
| ), | |
| } | |
| ) | |
| for index, variation in enumerate(MODEL_VARIATIONS, start=1): | |
| prompts.append( | |
| { | |
| "type": "Model", | |
| "prompt": build_model_prompt( | |
| base_product_lock=base_product_lock, | |
| user_instruction_block=user_instruction_block, | |
| variation=variation, | |
| index=index, | |
| ), | |
| } | |
| ) | |
| prompts.append( | |
| { | |
| "type": "Product closeup", | |
| "prompt": build_product_closeup_prompt( | |
| base_product_lock=base_product_lock, | |
| user_instruction_block=user_instruction_block, | |
| ), | |
| } | |
| ) | |
| prompts.append( | |
| { | |
| "type": "Model closeup", | |
| "prompt": build_model_closeup_prompt( | |
| base_product_lock=base_product_lock, | |
| user_instruction_block=user_instruction_block, | |
| ), | |
| } | |
| ) | |
| return prompts |