Phramer_AI / professional_photography.py
Malaji71's picture
Update professional_photography.py
aedfa8a verified
"""
Professional Photography Knowledge Base
Advanced camera settings, lighting, and composition rules from expert photography practice
Extracted from 30+ years of professional photography experience
"""
import re
from typing import Dict, List, Optional, Tuple, Any
# =====================================================
# PARTE 1: CONFIGURACIONES BASE Y TIPOS DE ESCENA
# =====================================================
EXPERT_PHOTOGRAPHY_KNOWLEDGE = {
# TIPOS DE ESCENA Y CONFIGURACIONES PROFESIONALES
"scene_types": {
"portrait_studio": {
"description": "Professional studio portrait photography",
"camera_settings": {
"mode": "AV/A",
"aperture": "f/2.8",
"iso": "100-400",
"focus": "single point AF on eyes",
"metering": "spot or center-weighted"
},
"equipment": {
"camera": "Canon EOS R5",
"lens": "85mm f/1.4",
"alternative_lens": "105mm f/2.8"
},
"lighting": {
"primary": "3-point studio lighting setup",
"key_light": "large softbox at 45 degrees",
"fill_light": "reflector or secondary softbox",
"rim_light": "subtle rim light for separation"
},
"composition": [
"rule of thirds for eye placement",
"shallow depth of field to isolate subject",
"focus on nearest eye for sharpness",
"leave breathing room in frame direction"
]
},
"portrait_exterior": {
"description": "Natural light outdoor portrait photography",
"camera_settings": {
"mode": "AV/A",
"aperture": "f/2.8-f/4",
"iso": "100-800",
"focus": "continuous AF for moving subjects",
"exposure_compensation": "+0.3 to +0.7 for faces"
},
"equipment": {
"camera": "Canon EOS R6",
"lens": "85mm f/1.4",
"alternative_lens": "70-200mm f/2.8"
},
"lighting": {
"preferred": "soft natural light",
"golden_hour": "best for warm, flattering light",
"overcast": "natural diffusion, even lighting",
"open_shade": "avoid harsh direct sunlight",
"reflector": "use to fill shadows when needed"
},
"composition": [
"environmental context for storytelling",
"rule of thirds with subject placement",
"watch background for distractions",
"use natural leading lines"
]
},
"street_photography": {
"description": "Spontaneous urban and documentary photography",
"camera_settings": {
"mode": "TV/S or Program",
"shutter_speed": "1/125s minimum for sharp subjects",
"aperture": "f/5.6-f/8 for sufficient depth of field",
"iso": "400-1600 adaptive to lighting",
"focus": "zone focusing or continuous AF"
},
"equipment": {
"camera": "Leica M11",
"lens": "35mm f/1.4",
"alternative_lens": "50mm f/2.8"
},
"lighting": {
"available_light": "work with existing conditions",
"dramatic_contrast": "use shadows and highlights",
"window_light": "exploit urban light sources",
"golden_hour": "warm street lighting mix"
},
"composition": [
"anticipation of decisive moments",
"rule of Z for visual flow",
"layered composition with depth",
"leading lines from urban architecture",
"respect distance and privacy"
]
},
"landscape": {
"description": "Natural landscape and scenic photography",
"camera_settings": {
"mode": "AV/A or Manual",
"aperture": "f/8-f/11 for maximum sharpness",
"iso": "100-400 for lowest noise",
"focus": "hyperfocal distance or infinity",
"exposure": "often requires bracketing"
},
"equipment": {
"camera": "Phase One XT",
"lens": "24-70mm f/4",
"wide_alternative": "16-35mm f/2.8",
"telephoto_alternative": "70-200mm f/4"
},
"lighting": {
"golden_hour": "optimal warm light",
"blue_hour": "dramatic twilight colors",
"overcast": "even light for forests/waterfalls",
"side_lighting": "enhance texture and depth"
},
"composition": [
"rule of thirds for horizon placement",
"foreground, middle ground, background layers",
"leading lines from natural features",
"point of interest as focal anchor",
"patience for optimal light conditions"
]
},
"architecture": {
"description": "Building and structural photography",
"camera_settings": {
"mode": "AV/A",
"aperture": "f/8-f/11 for sharp details",
"iso": "100-400",
"focus": "single point AF on key details",
"perspective_correction": "use tilt-shift when available"
},
"equipment": {
"camera": "Canon EOS R5",
"lens": "24-70mm f/2.8",
"wide_lens": "16-35mm f/2.8",
"tilt_shift": "24mm f/3.5 TS-E for correction"
},
"lighting": {
"side_lighting": "reveal texture and form",
"golden_hour": "warm light on facades",
"blue_hour": "interior lights vs exterior",
"overcast": "even light for details"
},
"composition": [
"strong geometric lines and patterns",
"symmetry and balance",
"leading lines and vanishing points",
"watch for converging verticals",
"isolate key architectural elements"
]
},
"action_sports": {
"description": "High-speed movement and sports photography",
"camera_settings": {
"mode": "TV/S",
"shutter_speed": "1/500s+ to freeze motion",
"aperture": "f/2.8-f/4 for subject isolation",
"iso": "800-3200 adaptive",
"focus": "continuous AF with tracking",
"burst_mode": "high speed continuous"
},
"equipment": {
"camera": "Sony A1",
"lens": "70-200mm f/2.8",
"longer_lens": "300mm f/2.8",
"wide_lens": "24-70mm f/2.8 for close action"
},
"lighting": {
"fast_shutter": "freeze motion priority",
"available_light": "work with venue lighting",
"iso_performance": "accept higher ISO for speed"
},
"composition": [
"anticipate action and peak moments",
"leave space in direction of movement",
"fill frame with subject",
"capture emotion and intensity",
"continuous focus tracking"
]
}
},
# PRINCIPIOS DE ILUMINACIÓN PROFESIONAL
"lighting_principles": {
"natural_light_types": {
"golden_hour": {
"timing": "first hour after sunrise, last hour before sunset",
"characteristics": "warm, soft, directional",
"best_for": "portraits, landscapes, architecture",
"camera_settings": "lower ISO, wider aperture possible"
},
"blue_hour": {
"timing": "20-30 minutes after sunset",
"characteristics": "even blue light, dramatic mood",
"best_for": "cityscapes, architecture with lights",
"camera_settings": "tripod required, longer exposures"
},
"overcast": {
"characteristics": "soft, even, diffused light",
"best_for": "portraits, forests, waterfalls",
"advantage": "no harsh shadows",
"camera_settings": "watch for flat contrast"
},
"open_shade": {
"characteristics": "soft directional light",
"best_for": "outdoor portraits",
"advantage": "avoids harsh sun",
"camera_settings": "may need exposure compensation"
}
},
"artificial_light_setups": {
"three_point_lighting": {
"key_light": "primary light source at 45 degrees",
"fill_light": "softer light to reduce shadows",
"rim_light": "separation from background",
"ratio": "3:1 or 2:1 key to fill for drama"
},
"window_lighting": {
"side_lighting": "place subject 90 degrees to window",
"frontal": "face window directly for even light",
"reflector_use": "bounce light back to fill shadows"
}
},
"lighting_directions": {
"frontal": {
"effect": "even illumination, minimal shadows",
"mood": "clean, professional, safe",
"best_for": "corporate portraits, documentation"
},
"side_lateral": {
"effect": "dramatic shadows, depth and texture",
"mood": "artistic, mysterious, powerful",
"best_for": "creative portraits, artistic work"
},
"backlighting": {
"effect": "rim lighting, silhouettes",
"mood": "dreamy, romantic, dramatic",
"technical": "watch for exposure compensation"
},
"top_lighting": {
"effect": "dramatic shadows under eyes",
"mood": "harsh, dramatic, theatrical",
"use_carefully": "can be unflattering for portraits"
}
}
},
# =====================================================
# PARTE 2: REGLAS DE COMPOSICIÓN Y TÉCNICAS AVANZADAS
# =====================================================
# REGLAS DE COMPOSICIÓN PROFESIONAL
"composition_rules": {
"rule_of_thirds": {
"principle": "divide frame into 9 equal sections",
"application": "place key elements on intersection points",
"subject_placement": "eyes on upper third line for portraits",
"horizon_placement": "upper or lower third for landscapes",
"when_to_break": "center composition for symmetry or impact"
},
"rule_of_z": {
"principle": "visual examination technique following Z pattern",
"purpose": "eliminate distracting elements systematically",
"application": "scan image from top-left to bottom-right",
"focus_check": "ensure sharp focus where intended",
"composition_check": "verify all elements contribute to story"
},
"leading_lines": {
"purpose": "guide viewer's eye through the image",
"types": ["diagonal lines", "curved lines", "converging lines"],
"sources": ["roads", "rivers", "architecture", "shadows"],
"technique": "use lines to lead to main subject"
},
"vanishing_points": {
"single_point": "all lines converge to one point",
"two_point": "vertical lines stay vertical, horizontals converge",
"application": "create depth and draw attention",
"photography_use": "architecture, streets, interiors"
},
"fibonacci_spiral": {
"mathematical_basis": "golden ratio spiral",
"composition_tool": "place subject at spiral intersection",
"relationship_to_thirds": "refined version of rule of thirds",
"application": "when precise composition balance needed"
},
"symmetry_and_patterns": {
"perfect_symmetry": "exact mirror image composition",
"near_symmetry": "almost symmetrical with subtle variation",
"pattern_breaking": "disruption in regular pattern creates focus",
"application": "architecture, reflections, nature patterns"
},
"depth_layers": {
"foreground": "nearest elements to camera",
"middle_ground": "main subject area typically here",
"background": "context and environment",
"technique": "create separation between layers",
"depth_cues": "overlapping, size variation, atmospheric perspective"
}
},
# ÁNGULOS Y PERSPECTIVAS
"camera_angles": {
"eye_level_normal": {
"description": "camera at subject's eye level",
"effect": "neutral, natural perspective",
"psychological_impact": "equality, relatability",
"best_for": "portraits, documentary, street photography"
},
"low_angle_worms_eye": {
"description": "camera below subject looking up",
"effect": "subject appears larger, more powerful",
"psychological_impact": "dominance, strength, heroic",
"technical": "watch for distortion with wide lenses",
"best_for": "architecture, powerful portraits, dramatic scenes"
},
"high_angle_birds_eye": {
"description": "camera above subject looking down",
"effect": "subject appears smaller, vulnerable",
"psychological_impact": "submission, overview, context",
"aerial_version": "complete overhead view",
"best_for": "environmental context, patterns, vulnerability"
},
"dutch_angle": {
"description": "camera tilted off horizontal",
"effect": "dynamic tension, unease",
"psychological_impact": "instability, energy, confusion",
"use_sparingly": "can become gimmicky if overused",
"best_for": "creative portraits, dynamic scenes"
}
},
# PLANOS FOTOGRÁFICOS
"photographic_planes": {
"extreme_wide_shot": {
"framing": "subject very small in environment",
"purpose": "establish location and context",
"best_for": "landscapes, establishing shots",
"composition_focus": "environment tells the story"
},
"wide_shot": {
"framing": "full body visible with environment",
"purpose": "show subject in context",
"best_for": "environmental portraits, action",
"composition_balance": "subject and environment both important"
},
"medium_shot": {
"framing": "from waist up approximately",
"purpose": "balance between subject and environment",
"best_for": "conversation, interaction, casual portraits",
"composition_focus": "subject is primary, environment secondary"
},
"close_up": {
"framing": "head and shoulders, tight on face",
"purpose": "show emotion and expression clearly",
"best_for": "emotional portraits, interviews",
"technical_focus": "eyes must be perfectly sharp"
},
"extreme_close_up": {
"framing": "part of face or specific detail",
"purpose": "intense emotion or specific detail",
"best_for": "artistic portraits, product details",
"technical_challenge": "depth of field very shallow"
},
"detail_shot": {
"framing": "specific small element",
"purpose": "highlight particular aspect",
"best_for": "hands, jewelry, textures, products",
"technical_requirements": "macro capabilities often needed"
}
},
# TÉCNICAS DE ENFOQUE Y PROFUNDIDAD DE CAMPO
"focus_techniques": {
"shallow_depth_of_field": {
"aperture_range": "f/1.4 - f/2.8",
"effect": "subject sharp, background blurred",
"best_for": "portraits, product photography, subject isolation",
"technical_consideration": "precise focus critical",
"creative_use": "bokeh quality becomes important"
},
"deep_depth_of_field": {
"aperture_range": "f/8 - f/16",
"effect": "everything sharp from front to back",
"best_for": "landscapes, architecture, group photos",
"technical_consideration": "diffraction at very small apertures",
"hyperfocal_distance": "maximize sharp zone"
},
"selective_focus": {
"technique": "choose specific focal plane",
"creative_control": "direct viewer attention",
"applications": ["isolate subject", "hide distractions", "create mood"],
"lens_choice": "longer focal lengths enhance effect"
},
"focus_stacking": {
"technique": "multiple shots at different focus points",
"purpose": "extend depth of field beyond single shot",
"best_for": "macro photography, product shots",
"post_processing": "requires blending software"
}
},
# MODO DE CÁMARA Y CONFIGURACIONES
"camera_modes": {
"program_mode": {
"description": "camera selects aperture and shutter speed",
"when_to_use": "quick shooting, changing conditions",
"photographer_control": "ISO, exposure compensation, focus",
"advantage": "fast response to opportunities",
"limitation": "less creative control over depth of field"
},
"aperture_priority": {
"mode_designation": "AV (Canon) / A (Nikon)",
"photographer_sets": "aperture value",
"camera_sets": "shutter speed for correct exposure",
"best_for": "controlling depth of field",
"applications": ["portraits", "landscapes", "creative control"],
"watch_for": "shutter speed dropping too low"
},
"shutter_priority": {
"mode_designation": "TV (Canon) / S (Nikon)",
"photographer_sets": "shutter speed",
"camera_sets": "aperture for correct exposure",
"best_for": "controlling motion",
"applications": ["sports", "action", "panning techniques"],
"watch_for": "aperture limits at extreme speeds"
},
"manual_mode": {
"photographer_sets": "both aperture and shutter speed",
"when_to_use": ["consistent lighting", "studio work", "long exposures"],
"requires": "good understanding of exposure triangle",
"advantage": "complete creative control",
"tools": "light meter, histogram, experience"
}
},
# TÉCNICAS DE MOVIMIENTO Y ACCIÓN
"movement_techniques": {
"freeze_motion": {
"shutter_speed": "1/250s or faster",
"applications": ["sports", "action", "sharp movement"],
"considerations": ["adequate light needed", "higher ISO may be required"],
"focus_mode": "continuous AF with tracking"
},
"motion_blur_panning": {
"shutter_speed": "1/15s - 1/60s typically",
"technique": "follow subject smoothly while shooting",
"effect": "sharp subject with blurred background",
"creates": "sense of speed and movement",
"requires": "practice and smooth camera movement"
},
"intentional_camera_movement": {
"technique": "deliberate camera shake during exposure",
"creative_effect": "abstract, artistic blur patterns",
"shutter_speed": "1/4s - 2s typically",
"applications": ["creative landscapes", "abstract art", "impressionistic effects"]
}
},
# =====================================================
# PARTE 3: CONFIGURACIONES ISO Y CONDICIONES DE LUZ
# =====================================================
# CONFIGURACIONES ISO PROFESIONALES
"iso_guidelines": {
"base_iso": {
"range": "100-200",
"quality": "maximum image quality, lowest noise",
"lighting_needed": "bright daylight, studio lighting",
"best_for": "landscapes, studio portraits, product photography"
},
"low_iso": {
"range": "400-800",
"quality": "excellent quality, minimal noise",
"lighting_needed": "good available light",
"best_for": "outdoor portraits, street photography, indoor with windows"
},
"medium_iso": {
"range": "1600-3200",
"quality": "good quality, manageable noise",
"lighting_needed": "indoor available light, overcast outdoor",
"best_for": "event photography, indoor sports, available light portraits"
},
"high_iso": {
"range": "6400-12800",
"quality": "acceptable quality, visible noise",
"lighting_needed": "low light situations",
"best_for": "concerts, nighttime events, astrophotography",
"post_processing": "noise reduction recommended"
}
},
# SITUACIONES DE LUZ ESPECÍFICAS
"lighting_situations": {
"bright_daylight": {
"iso": "100-200",
"aperture_considerations": "can use smaller apertures for sharpness",
"challenge": "harsh shadows",
"solutions": ["use reflectors", "find open shade", "use fill flash"]
},
"overcast_day": {
"iso": "200-400",
"characteristics": "soft, even light but dimmer",
"advantage": "natural diffusion",
"watch_for": "flat contrast, may need post-processing boost"
},
"indoor_natural_light": {
"iso": "800-1600",
"window_light": "excellent for portraits",
"technique": "position subject relative to window",
"tools": "reflectors to control shadow fill"
},
"low_light_available": {
"iso": "1600-6400",
"stabilization": "essential for sharp images",
"technique": "wider apertures, slower movements",
"creative_opportunities": "dramatic lighting, mood"
},
"night_photography": {
"iso": "3200-12800",
"equipment": "tripod usually required",
"techniques": ["long exposures", "image stacking", "noise reduction"],
"subjects": ["cityscapes", "astrophotography", "light trails"]
}
},
# TÉCNICAS ESPECIALIZADAS
"specialized_techniques": {
"macro_photography": {
"equipment": "macro lens or extension tubes",
"camera_settings": {
"aperture": "f/8-f/16 for adequate depth of field",
"iso": "200-800",
"focus": "manual focus recommended",
"stabilization": "tripod essential"
},
"lighting": "ring flash or diffused lighting",
"challenges": ["shallow depth of field", "camera shake", "subject movement"]
},
"long_exposure": {
"equipment": "tripod, neutral density filters",
"camera_settings": {
"mode": "Manual or Bulb",
"aperture": "f/8-f/16",
"iso": "100-200",
"shutter_speed": "30s to several minutes"
},
"subjects": ["waterfalls", "clouds", "star trails", "traffic"],
"technique": "use timer or remote to avoid camera shake"
},
"high_key_photography": {
"lighting": "bright, even, minimal shadows",
"exposure": "intentionally overexposed by 1-2 stops",
"post_processing": "maintain detail in highlights",
"mood": "clean, optimistic, airy",
"subjects": ["fashion", "beauty", "products"]
},
"low_key_photography": {
"lighting": "dramatic, contrasty, deep shadows",
"exposure": "underexposed to maintain shadow detail",
"technique": "single light source often",
"mood": "mysterious, dramatic, moody",
"subjects": ["portraits", "still life", "artistic work"]
}
}
}
# =====================================================
# PARTE 4: CLASES DE ANÁLISIS PROFESIONAL
# =====================================================
class ProfessionalPhotoAnalyzer:
"""Expert photography context provider for intelligent prompt enhancement"""
def __init__(self):
self.knowledge = EXPERT_PHOTOGRAPHY_KNOWLEDGE
def detect_scene_type(self, description: str) -> str:
"""Detect primary scene type from image description"""
description_lower = description.lower()
# Scene type detection patterns
scene_patterns = {
"portrait_studio": ["studio", "portrait", "professional lighting", "controlled lighting"],
"portrait_exterior": ["portrait", "person", "outdoor", "natural light", "exterior"],
"street_photography": ["street", "urban", "candid", "documentary", "city"],
"landscape": ["landscape", "nature", "mountain", "horizon", "scenic", "outdoor scene"],
"architecture": ["building", "architecture", "structure", "geometric", "facade"],
"action_sports": ["action", "sport", "movement", "running", "dynamic", "motion"]
}
# Score each scene type based on keyword matches
scene_scores = {}
for scene_type, keywords in scene_patterns.items():
score = sum(1 for keyword in keywords if keyword in description_lower)
if score > 0:
scene_scores[scene_type] = score
# Return highest scoring scene type, default to general if none match
if scene_scores:
return max(scene_scores.items(), key=lambda x: x[1])[0]
else:
return "general"
def analyze_lighting_conditions(self, description: str) -> Dict[str, Any]:
"""Analyze lighting conditions from description"""
description_lower = description.lower()
lighting_analysis = {
"type": "unknown",
"quality": "unknown",
"direction": "unknown",
"recommendations": []
}
# Detect lighting type
if any(term in description_lower for term in ["studio", "controlled", "professional lighting"]):
lighting_analysis["type"] = "studio"
lighting_analysis["recommendations"].append("3-point lighting setup")
elif any(term in description_lower for term in ["natural", "daylight", "outdoor", "sun"]):
lighting_analysis["type"] = "natural"
lighting_analysis["recommendations"].append("consider time of day for optimal light")
elif any(term in description_lower for term in ["low light", "dark", "night", "dim"]):
lighting_analysis["type"] = "low_light"
lighting_analysis["recommendations"].append("higher ISO and stabilization needed")
# Detect lighting quality
if any(term in description_lower for term in ["soft", "diffused", "even"]):
lighting_analysis["quality"] = "soft"
elif any(term in description_lower for term in ["harsh", "dramatic", "contrasty"]):
lighting_analysis["quality"] = "hard"
# Detect lighting direction
if any(term in description_lower for term in ["side lit", "lateral", "from side"]):
lighting_analysis["direction"] = "side"
elif any(term in description_lower for term in ["backlit", "rim light", "silhouette"]):
lighting_analysis["direction"] = "back"
elif any(term in description_lower for term in ["front lit", "frontal"]):
lighting_analysis["direction"] = "front"
return lighting_analysis
def get_camera_recommendations(self, scene_type: str, lighting_conditions: Dict[str, Any]) -> Dict[str, Any]:
"""Get professional camera setup recommendations"""
if scene_type not in self.knowledge["scene_types"]:
scene_type = "portrait_exterior" # Default fallback
scene_config = self.knowledge["scene_types"][scene_type]
recommendations = {
"camera_body": scene_config["equipment"]["camera"],
"primary_lens": scene_config["equipment"]["lens"],
"camera_settings": scene_config["camera_settings"].copy(),
"lighting_setup": scene_config["lighting"],
"composition_tips": scene_config["composition"]
}
# Adjust ISO based on lighting conditions
if lighting_conditions["type"] == "low_light":
recommendations["camera_settings"]["iso"] = "1600-6400"
elif lighting_conditions["type"] == "studio":
recommendations["camera_settings"]["iso"] = "100-200"
elif lighting_conditions["type"] == "natural":
recommendations["camera_settings"]["iso"] = "200-800"
return recommendations
def get_composition_guidance(self, scene_type: str, description: str) -> List[str]:
"""Get composition recommendations based on scene type and content"""
guidance = []
description_lower = description.lower()
# Base composition rules
guidance.append("apply rule of thirds for key element placement")
# Scene-specific composition
if scene_type == "portrait_studio" or scene_type == "portrait_exterior":
guidance.extend([
"focus on nearest eye for maximum sharpness",
"use shallow depth of field to isolate subject",
"leave appropriate headroom and breathing space"
])
elif scene_type == "landscape":
guidance.extend([
"place horizon on upper or lower third line",
"create depth with foreground, middle ground, background",
"use leading lines to guide viewer's eye"
])
elif scene_type == "street_photography":
guidance.extend([
"apply rule of Z for comprehensive composition check",
"anticipate decisive moments",
"maintain respectful distance while capturing authenticity"
])
elif scene_type == "architecture":
guidance.extend([
"watch for converging verticals",
"use strong geometric lines and patterns",
"consider symmetry and balance"
])
# Motion-specific guidance
if any(term in description_lower for term in ["movement", "motion", "running", "action"]):
guidance.extend([
"leave space in direction of movement",
"consider panning technique for motion blur",
"use continuous autofocus for tracking"
])
return guidance
def get_technical_context(self, scene_type: str, lighting_conditions: Dict[str, Any]) -> str:
"""Generate technical context string for prompt enhancement"""
recommendations = self.get_camera_recommendations(scene_type, lighting_conditions)
context_parts = []
# Camera and lens
context_parts.append(f"Professional setup: {recommendations['camera_body']}")
context_parts.append(f"with {recommendations['primary_lens']}")
# Key settings
settings = recommendations['camera_settings']
if 'mode' in settings:
context_parts.append(f"shot in {settings['mode']} mode")
if 'aperture' in settings:
context_parts.append(f"at {settings['aperture']}")
if 'iso' in settings:
context_parts.append(f"ISO {settings['iso']}")
# Lighting insight
if lighting_conditions["type"] != "unknown":
if lighting_conditions["type"] == "studio":
context_parts.append("professional studio lighting")
elif lighting_conditions["type"] == "natural":
context_parts.append("natural lighting conditions")
elif lighting_conditions["type"] == "low_light":
context_parts.append("available light photography")
return ", ".join(context_parts)
def _generate_professional_insight(self, scene_type: str, lighting_conditions: Dict[str, Any]) -> str:
"""Generate professional photography insight based on scene and lighting"""
insights = []
# Scene-specific professional insights
if scene_type == "portrait_studio":
insights.append("Professional studio portraiture requires precise lighting control")
insights.append("3-point lighting setup ensures dimensional modeling of facial features")
elif scene_type == "portrait_exterior":
insights.append("Natural light portraiture benefits from soft, directional lighting")
insights.append("Golden hour provides optimal warmth and flattering illumination")
elif scene_type == "street_photography":
insights.append("Street photography requires anticipation and quick technical adaptation")
insights.append("Available light mastery is essential for authentic documentary capture")
elif scene_type == "landscape":
insights.append("Landscape photography demands patience for optimal natural lighting")
insights.append("Hyperfocal distance technique maximizes front-to-back sharpness")
elif scene_type == "architecture":
insights.append("Architectural photography emphasizes form, texture, and geometric precision")
insights.append("Side lighting reveals dimensional qualities and surface textures")
# Lighting-specific insights
if lighting_conditions["type"] == "studio":
insights.append("Controlled studio environment allows precise mood and contrast control")
elif lighting_conditions["type"] == "natural":
insights.append("Natural lighting varies continuously, requiring adaptive technical approach")
elif lighting_conditions["type"] == "low_light":
insights.append("Low light conditions demand technical precision and creative interpretation")
return ". ".join(insights)
def generate_enhanced_context(self, bagel_description: str) -> Dict[str, Any]:
"""
Main method: Generate professional photography context for BAGEL enhancement
NON-INVASIVE: Provides guidance without overriding BAGEL's creativity
"""
# Analyze the image description from BAGEL
scene_type = self.detect_scene_type(bagel_description)
lighting_conditions = self.analyze_lighting_conditions(bagel_description)
composition_guidance = self.get_composition_guidance(scene_type, bagel_description)
technical_context = self.get_technical_context(scene_type, lighting_conditions)
enhanced_context = {
"scene_type": scene_type,
"lighting_analysis": lighting_conditions,
"technical_context": technical_context,
"composition_guidance": composition_guidance,
"professional_insight": self._generate_professional_insight(scene_type, lighting_conditions),
"equipment_recommendation": self.get_camera_recommendations(scene_type, lighting_conditions)
}
return enhanced_context
def format_bagel_enhancement_prompt(self, base_prompt: str, enhanced_context: Dict[str, Any]) -> str:
"""
Format enhanced prompt for BAGEL while preserving its creative freedom
"""
context_guidance = f"""
PROFESSIONAL PHOTOGRAPHY CONTEXT:
Scene Type: {enhanced_context['scene_type'].replace('_', ' ').title()}
Technical Setup: {enhanced_context['technical_context']}
COMPOSITION CONSIDERATIONS:
{' • '.join(enhanced_context['composition_guidance'])}
PROFESSIONAL INSIGHT:
{enhanced_context['professional_insight']}
Apply these principles flexibly to enhance your creative analysis.
"""
return base_prompt + context_guidance
# =====================================================
# PARTE 5: FUNCIONES DE INTEGRACIÓN Y UTILIDADES
# =====================================================
class ProfessionalScoring:
"""Enhanced scoring system incorporating professional photography principles"""
def __init__(self):
self.analyzer = ProfessionalPhotoAnalyzer()
def calculate_professional_score(self, prompt: str, analysis_data: Optional[Dict[str, Any]] = None) -> Tuple[int, Dict[str, int]]:
"""
Calculate enhanced quality score incorporating professional photography principles
"""
breakdown = {}
# 1. TECHNICAL EXCELLENCE (0-30 points)
technical_score = 0
# Professional camera bodies
professional_cameras = [
'canon eos r5', 'canon eos r6', 'sony a1', 'sony a7r',
'leica m11', 'phase one', 'hasselblad', 'fujifilm gfx'
]
if any(camera in prompt.lower() for camera in professional_cameras):
technical_score += 10
# Professional lens specifications
lens_pattern = r'\d+mm.*f/[\d.]+'
if re.search(lens_pattern, prompt.lower()):
technical_score += 8
# Specific aperture settings
aperture_pattern = r'f/[\d.]+'
if re.search(aperture_pattern, prompt.lower()):
technical_score += 6
# ISO considerations
iso_pattern = r'iso\s*\d+'
if re.search(iso_pattern, prompt.lower()):
technical_score += 6
breakdown["technical_excellence"] = min(30, technical_score)
# 2. LIGHTING MASTERY (0-25 points)
lighting_score = 0
# Professional lighting terms
lighting_terms = [
'studio lighting', 'natural lighting', 'golden hour', 'blue hour',
'side lighting', 'rim lighting', 'dramatic lighting', 'soft lighting',
'3-point lighting', 'key light', 'fill light', 'diffused light'
]
lighting_matches = sum(1 for term in lighting_terms if term in prompt.lower())
lighting_score += min(15, lighting_matches * 3)
# Advanced lighting concepts
advanced_lighting = [
'lighting ratio', 'hard light', 'soft light', 'directional light',
'ambient light', 'available light', 'controlled lighting'
]
advanced_matches = sum(1 for term in advanced_lighting if term in prompt.lower())
lighting_score += min(10, advanced_matches * 2)
breakdown["lighting_mastery"] = min(25, lighting_score)
# 3. COMPOSITION EXPERTISE (0-25 points)
composition_score = 0
# Classic composition rules
composition_rules = [
'rule of thirds', 'leading lines', 'depth of field', 'shallow depth',
'bokeh', 'symmetry', 'balance', 'framing', 'perspective'
]
rule_matches = sum(1 for rule in composition_rules if rule in prompt.lower())
composition_score += min(15, rule_matches * 2)
# Advanced composition concepts
advanced_composition = [
'vanishing point', 'fibonacci', 'golden ratio', 'dynamic composition',
'layered composition', 'negative space', 'visual flow'
]
advanced_comp_matches = sum(1 for concept in advanced_composition if concept in prompt.lower())
composition_score += min(10, advanced_comp_matches * 2)
breakdown["composition_expertise"] = min(25, composition_score)
# 4. PROFESSIONAL TERMINOLOGY (0-20 points)
terminology_score = 0
# Professional photography terms
pro_terms = [
'professional photography', 'commercial photography', 'editorial',
'documentary style', 'photojournalism', 'fine art photography',
'architectural photography', 'landscape photography', 'portraiture'
]
term_matches = sum(1 for term in pro_terms if term in prompt.lower())
terminology_score += min(12, term_matches * 2)
# Technical photography terms
technical_terms = [
'hyperfocal distance', 'exposure triangle', 'metering', 'focus stacking',
'bracketing', 'tilt-shift', 'macro photography', 'telephoto compression'
]
tech_matches = sum(1 for term in technical_terms if term in prompt.lower())
terminology_score += min(8, tech_matches * 2)
breakdown["professional_terminology"] = min(20, terminology_score)
# Calculate total score
total_score = sum(breakdown.values())
return total_score, breakdown
def get_professional_camera_setup(scene_description: str) -> Dict[str, str]:
"""
Quick function to get camera setup recommendation based on scene description
"""
analyzer = ProfessionalPhotoAnalyzer()
scene_type = analyzer.detect_scene_type(scene_description)
lighting_conditions = analyzer.analyze_lighting_conditions(scene_description)
recommendations = analyzer.get_camera_recommendations(scene_type, lighting_conditions)
# Format as simple dictionary for easy use
return {
"camera": recommendations["camera_body"],
"lens": recommendations["primary_lens"],
"aperture": recommendations["camera_settings"].get("aperture", "f/4"),
"mode": recommendations["camera_settings"].get("mode", "AV"),
"iso": recommendations["camera_settings"].get("iso", "400"),
"scene_type": scene_type
}
def enhance_flux_prompt_with_professional_knowledge(original_prompt: str, image_analysis: str = "") -> str:
"""
Main integration function: Enhance FLUX prompts with professional photography knowledge
PRESERVES CREATIVITY while adding technical expertise
"""
analyzer = ProfessionalPhotoAnalyzer()
# Use image analysis if provided, otherwise use the prompt itself
analysis_text = image_analysis if image_analysis else original_prompt
# Get professional context
enhanced_context = analyzer.generate_enhanced_context(analysis_text)
# Build enhancement that supplements rather than replaces
enhancement_parts = []
# Add technical context naturally
technical_context = enhanced_context["technical_context"]
if technical_context:
enhancement_parts.append(f"Shot on {technical_context}")
# Add composition guidance as suggestion
composition_tips = enhanced_context["composition_guidance"]
if composition_tips:
# Pick most relevant composition tip
primary_tip = composition_tips[0] if composition_tips else ""
if "rule of thirds" in primary_tip:
enhancement_parts.append("composed using rule of thirds")
elif "shallow depth" in primary_tip:
enhancement_parts.append("with shallow depth of field")
# Add lighting enhancement
lighting_analysis = enhanced_context["lighting_analysis"]
if lighting_analysis["type"] == "studio":
enhancement_parts.append("professional studio lighting")
elif lighting_analysis["type"] == "natural":
enhancement_parts.append("natural lighting")
elif lighting_analysis["type"] == "low_light":
enhancement_parts.append("available light photography")
# Combine original prompt with enhancements
if enhancement_parts:
enhanced_prompt = f"{original_prompt}, {', '.join(enhancement_parts)}"
else:
enhanced_prompt = f"{original_prompt}, professional photography"
return enhanced_prompt
def get_scene_specific_camera_config(scene_keywords: List[str]) -> Dict[str, Any]:
"""
Get camera configuration based on scene keywords
Useful for quick scene-based recommendations
"""
scene_mappings = {
"portrait": "portrait_studio",
"person": "portrait_exterior",
"street": "street_photography",
"urban": "street_photography",
"landscape": "landscape",
"nature": "landscape",
"building": "architecture",
"architecture": "architecture",
"action": "action_sports",
"sport": "action_sports",
"movement": "action_sports"
}
# Find matching scene type
scene_type = "portrait_exterior" # default
for keyword in scene_keywords:
if keyword.lower() in scene_mappings:
scene_type = scene_mappings[keyword.lower()]
break
# Get configuration from knowledge base
if scene_type in EXPERT_PHOTOGRAPHY_KNOWLEDGE["scene_types"]:
config = EXPERT_PHOTOGRAPHY_KNOWLEDGE["scene_types"][scene_type]
return {
"scene_type": scene_type,
"equipment": config["equipment"],
"settings": config["camera_settings"],
"lighting": config["lighting"],
"composition": config["composition"]
}
return {}
# =====================================================
# UTILIDADES DE EXPORTACIÓN
# =====================================================
def export_professional_prompt_enhancement(bagel_output: str, bagel_metadata: Dict[str, Any] = None) -> Dict[str, Any]:
"""
Complete integration function for use in your existing pipeline
Returns enhanced prompt and metadata for seamless integration
"""
analyzer = ProfessionalPhotoAnalyzer()
scorer = ProfessionalScoring()
# Generate professional context
enhanced_context = analyzer.generate_enhanced_context(bagel_output)
# Create enhanced prompt
enhanced_prompt = enhance_flux_prompt_with_professional_knowledge(bagel_output)
# Calculate professional score
score, score_breakdown = scorer.calculate_professional_score(enhanced_prompt, bagel_metadata)
# Prepare metadata
enhanced_metadata = bagel_metadata.copy() if bagel_metadata else {}
enhanced_metadata.update({
"professional_enhancement": True,
"scene_type": enhanced_context["scene_type"],
"professional_score": score,
"score_breakdown": score_breakdown,
"technical_context": enhanced_context["technical_context"],
"professional_insights": enhanced_context["professional_insight"]
})
return {
"enhanced_prompt": enhanced_prompt,
"metadata": enhanced_metadata,
"original_prompt": bagel_output,
"enhancement_context": enhanced_context
}
# Global analyzer instance for easy access
professional_analyzer = ProfessionalPhotoAnalyzer()
professional_scorer = ProfessionalScoring()
# Export main functions for integration
__all__ = [
"ProfessionalPhotoAnalyzer",
"ProfessionalScoring",
"enhance_flux_prompt_with_professional_knowledge",
"get_professional_camera_setup",
"export_professional_prompt_enhancement",
"professional_analyzer",
"professional_scorer",
"EXPERT_PHOTOGRAPHY_KNOWLEDGE"
]