diff --git a/__init__.py b/__init__.py new file mode 100644 index 0000000..deef1c1 --- /dev/null +++ b/__init__.py @@ -0,0 +1,3 @@ +from .magic_photo_prompt import NODE_CLASS_MAPPINGS + +__all__ = ['NODE_CLASS_MAPPINGS'] diff --git a/magic_options.json b/magic_options.json new file mode 100644 index 0000000..10dc8d8 --- /dev/null +++ b/magic_options.json @@ -0,0 +1,265 @@ +{ + "camera": { + "None": "", + "Canon EOS R6 Mark II": "shot on Canon EOS R6 Mark II", + "Sony A7 IV": "shot on Sony A7 IV", + "Nikon Z9": "shot on Nikon Z9", + "Fujifilm X-T5": "shot on Fujifilm X-T5", + "Panasonic Lumix S5 II": "shot on Panasonic Lumix S5 II", + "Canon EOS R5": "shot on Canon EOS R5", + "Sony A7R V": "shot on Sony A7R V", + "Nikon Z7 II": "shot on Nikon Z7 II", + "Fujifilm X-H2S": "shot on Fujifilm X-H2S", + "Canon EOS R3": "shot on Canon EOS R3", + "Sony A1": "shot on Sony A1", + "Nikon D850": "shot on Nikon D850", + "Canon EOS 5D Mark IV": "shot on Canon EOS 5D Mark IV", + "Sony A9 II": "shot on Sony A9 II", + "Fujifilm GFX 100S": "shot on Fujifilm GFX 100S", + "Leica Q2": "shot on Leica Q2", + "Canon EOS R7": "shot on Canon EOS R7", + "Sony A6700": "shot on Sony A6700", + "Nikon Z6 II": "shot on Nikon Z6 II", + "Panasonic Lumix GH6": "shot on Panasonic Lumix GH6", + "Olympus OM-D E-M1 Mark III": "shot on Olympus OM-D E-M1 Mark III", + "Canon EOS R10": "shot on Canon EOS R10", + "Sony RX100 VII": "shot on Sony RX100 VII", + "Nikon Z50": "shot on Nikon Z50", + "Fujifilm X-S20": "shot on Fujifilm X-S20", + "Canon PowerShot G7 X Mark III": "shot on Canon PowerShot G7 X Mark III", + "Sony ZV-1": "shot on Sony ZV-1", + "GoPro Hero12 Black": "shot on GoPro Hero12 Black", + "DJI Osmo Pocket 3": "shot on DJI Osmo Pocket 3", + "iPhone 15 Pro Max": "shot on iPhone 15 Pro Max", + "Samsung Galaxy S24 Ultra": "shot on Samsung Galaxy S24 Ultra", + "Google Pixel 8 Pro": "shot on Google Pixel 8 Pro", + "Hasselblad X2D 100C": "shot on Hasselblad X2D 100C", + "Phase One XF IQ4 150MP": "shot on Phase One XF IQ4 150MP", + "Leica M11": "shot on Leica M11", + "Canon AE-1": "shot on Canon AE-1", + "Nikon F3": "shot on Nikon F3", + "Polaroid SX-70": "shot on Polaroid SX-70", + "Hasselblad 500C": "shot on Hasselblad 500C", + "Leica M3": "shot on Leica M3", + "Kodak Brownie": "shot on Kodak Brownie", + "Pentax K1000": "shot on Pentax K1000", + "Olympus OM-1": "shot on Olympus OM-1", + "Mamiya RB67": "shot on Mamiya RB67", + "Rolleiflex 2.8F": "shot on Rolleiflex 2.8F", + "Nikon F": "shot on Nikon F", + "Canon F-1": "shot on Canon F-1", + "Minolta X-700": "shot on Minolta X-700", + "Yashica Mat-124G": "shot on Yashica Mat-124G", + "Contax T2": "shot on Contax T2", + "Fujifilm X100V": "shot on Fujifilm X100V" +}, + "composition_shot": { + "None": "", + "Rule of Thirds": "balanced rule of thirds composition", + "Leading Lines": "compelling leading lines composition", + "Symmetry": "perfect symmetrical composition", + "Framing": "natural framing composition", + "Golden Ratio": "harmonious golden ratio composition", + "Diagonal Lines": "dynamic diagonal lines composition", + "Centered Composition": "bold centered composition", + "Triangular Composition": "stable triangular composition", + "Fill the Frame": "impactful fill the frame composition", + "Negative Space": "minimalist negative space composition", + "Foreground Interest": "engaging foreground interest composition", + "Patterns and Repetition": "mesmerizing patterns and repetition composition", + "Juxtaposition": "thought-provoking juxtaposition composition", + "S-Curve": "flowing s-curve composition", + "Rule of Odds": "intriguing rule of odds composition", + "Layering": "complex layered composition", + "Radial Composition": "eye-catching radial composition", + "Golden Triangle": "balanced golden triangle composition", + "Rule of Space": "dynamic rule of space composition", + "Viewpoint": "unique viewpoint composition", + "Depth of Field": "selective focus depth of field composition", + "Silhouette": "dramatic silhouette composition", + "Reflection": "captivating reflection composition", + "Panoramic": "expansive panoramic composition", + "Minimalism": "elegant minimalist composition", + "Texture": "rich textural composition", + "Color Theory": "harmonious color theory composition", + "Balance": "perfectly balanced composition", + "Contrast": "high-contrast composition", + "Gestalt Principles": "unified gestalt principles composition", + "Fibonacci Spiral": "natural fibonacci spiral composition", + "Vanishing Point": "perspective-driven vanishing point composition", + "Rule of Sevenths": "subtle rule of sevenths composition", + "Stacking": "layered stacking composition", + "Asymmetry": "intriguing asymmetrical composition", + "Frame Within a Frame": "creative frame within a frame composition", + "Converging Lines": "powerful converging lines composition", + "Rhythm": "visual rhythm composition", + "Scale": "impressive scale composition", + "Selective Color": "striking selective color composition", + "Forced Perspective": "playful forced perspective composition", + "Bokeh": "dreamy bokeh composition", + "Chiaroscuro": "dramatic chiaroscuro lighting composition", + "Triptych": "narrative triptych composition", + "Vignette": "subtle vignette composition", + "Low Angle": "imposing low angle composition", + "High Angle": "revealing high angle composition", + "Bird's Eye View": "expansive bird's eye view composition", + "Worm's Eye View": "unique worm's eye view composition", + "Macro": "detailed macro composition" +}, + "time_of_day": { + "None": "", + "Golden Hour": "during golden hour", + "Blue Hour": "in the serene blue hour", + "Midnight": "at the stroke of midnight", + "Sunrise": "at the break of dawn", + "Early Morning": "in the crisp early morning", + "Mid-Morning": "during bright mid-morning", + "High Noon": "under the harsh high noon sun", + "Early Afternoon": "in the warm early afternoon", + "Late Afternoon": "during the mellow late afternoon", + "Sunset": "at the colorful sunset", + "Twilight": "in the mystical twilight", + "Dusk": "at the fading dusk", + "Early Evening": "in the calm early evening", + "Late Evening": "during the quiet late evening", + "Night": "in the dark of night", + "Pre-Dawn": "in the still pre-dawn hours", + "Civil Twilight": "during civil twilight", + "Nautical Twilight": "in the dim nautical twilight", + "Astronomical Twilight": "at astronomical twilight", + "Solar Noon": "at precise solar noon", + "Magic Hour": "in the enchanting magic hour", + "First Light": "at first light", + "Last Light": "at last light", + "Midday": "in the bright midday", + "Witching Hour": "during the eerie witching hour", + "Golden Moment": "capturing the fleeting golden moment", + "Blue Moment": "in the tranquil blue moment", + "Moonrise": "during the ethereal moonrise", + "Moonset": "at the subtle moonset", + "Full Moon": "under the luminous full moon" +}, + "color_grading": { + "None": "", + "Warm": "with warm color grading", + "Cool": "using cool tones", + "High Contrast": "high contrast color palette", + "Low Contrast": "soft low contrast look", + "Monochromatic": "in striking monochromatic tones", + "Sepia": "with nostalgic sepia toning", + "Cross-Processed": "using cross-processed effect", + "Bleach Bypass": "with gritty bleach bypass look", + "Cinematic Teal and Orange": "in cinematic teal and orange", + "Vintage": "with retro vintage color grading", + "Pastel": "using soft pastel colors", + "Neon": "with vibrant neon color palette", + "Desaturated": "in muted desaturated tones", + "Vivid": "with highly saturated vivid colors", + "Film Emulation": "using classic film stock emulation", + "Split-Toning": "with creative split-toning technique", + "Duotone": "in bold duotone color scheme", + "Complementary Colors": "using complementary color contrast", + "Analogous Colors": "with harmonious analogous colors", + "Black and White": "in timeless black and white", + "HDR": "with high dynamic range color grading", + "Matte": "using flat matte color profile", + "Lomo": "with quirky lomo-inspired colors", + "Cyberpunk": "in futuristic cyberpunk color scheme", + "Earthy": "using natural earthy tones", + "Moody": "with atmospheric moody color grading", + "Faded": "in trendy faded color style", + "Technicolor": "with vibrant technicolor-inspired palette", + "Noir": "in classic film noir style", + "Infrared": "using surreal infrared color effect", + "Solarized": "with artistic solarization effect", + "Day for Night": "using day for night color grading" +}, + + "lighting": { + "None": "", + "Natural Light": "using soft, ambient daylight", + "Golden Hour": "with warm, golden sunlight just before sunset", + "Blue Hour": "utilizing cool, diffused light after sunset", + "Harsh Sunlight": "with strong, contrasty midday sun", + "Overcast": "using soft, diffused light on a cloudy day", + "Window Light": "utilizing directional light from a window", + "Backlight": "with light source behind the subject, creating a halo effect", + "Rim Light": "using light to outline the edges of the subject", + "Silhouette": "creating a dark subject against a bright background", + "Spotlight": "with a focused beam of light on the subject", + "Soft Box": "using diffused, even light from a soft box", + "Beauty Dish": "with flattering, wraparound light for portraits", + "Ring Light": "utilizing circular light for even, shadowless illumination", + "Umbrella Lighting": "with soft, bounced light from an umbrella", + "Rembrandt Lighting": "creating a triangle of light on the cheek", + "Butterfly Lighting": "with light above and in front, casting a nose shadow", + "Loop Lighting": "creating a small shadow loop on the side of the nose", + "Split Lighting": "illuminating half of the face dramatically", + "Broad Lighting": "with light on the side of the face toward the camera", + "Short Lighting": "illuminating the side of the face away from the camera", + "Clamshell Lighting": "using two lights, one above and one below the subject", + "Three-Point Lighting": "with key, fill, and back lights for balanced illumination", + "Low-Key Lighting": "creating a dark, moody atmosphere with minimal light", + "High-Key Lighting": "using bright, even lighting for a clean, airy look", + "Bounce Flash": "with flash bounced off surfaces for softer light", + "Gel Lighting": "using colored gels on lights for creative effects", + "Gobo Lighting": "projecting patterns or shapes onto the subject", + "Practical Lighting": "incorporating visible light sources within the scene", + "Candlelight": "using warm, flickering light from candles", + "Light Painting": "creating unique effects with moving lights in long exposures" + }, + + "environment": { + "None": "", + "Medieval": "set in a historical Middle Ages atmosphere", + "Fantasy": "in a magical, otherworldly realm", + "Futuristic": "depicting an advanced technological future", + "Post-Apocalyptic": "in a world devastated by catastrophe", + "Steampunk": "blending Victorian aesthetics with steam-powered technology", + "Cyberpunk": "in a high-tech, low-life dystopian future", + "Ancient Egypt": "set among pyramids and pharaohs of ancient times", + "Wild West": "in the rugged American frontier of the 19th century", + "Tropical Paradise": "on a lush, exotic island setting", + "Arctic Tundra": "in a stark, frozen landscape", + "Underwater": "submerged in an aquatic environment", + "Space Station": "aboard an orbiting facility in outer space", + "Alien Planet": "on a strange, extraterrestrial world", + "Urban Metropolis": "in a bustling, modern city center", + "Rural Countryside": "amidst peaceful, pastoral farmlands", + "Haunted House": "inside a spooky, paranormal dwelling", + "Jungle": "within a dense, tropical rainforest", + "Desert Oasis": "at a lush haven amidst arid dunes", + "Ancient Rome": "in the glory days of the Roman Empire", + "Industrial Revolution": "during the rise of factories and machines", + "Prehistoric": "set in the time of dinosaurs and early humans", + "Atlantis": "in a mythical underwater civilization", + "Feudal Japan": "during the era of samurai and shoguns", + "Viking Age": "among Norse warriors and longships", + "1920s Art Deco": "in the glamorous Roaring Twenties", + "1950s Retro": "with mid-century modern aesthetics", + "Fairy Tale": "in a whimsical, storybook setting", + "Dystopian": "in an oppressive, controlled society", + "Floating Sky Islands": "among mystical landmasses in the clouds", + "Underground Cavern": "within vast, subterranean cave systems", + "Dark Theme": "in a gloomy, shadowy atmosphere", + "Heavenly": "set in a celestial, paradisiacal realm", + "Forest": "amidst lush, verdant woodlands", + "Neon City": "in a vibrant, colorfully lit urban landscape", + "Abandoned Amusement Park": "among decaying rides and eerie silence", + "Volcanic": "in a fiery landscape of lava and ash", + "Clockwork World": "where everything is powered by intricate gears", + "Bioluminescent": "glowing with natural, living light", + "Frozen Kingdom": "in an eternally winter-bound realm", + "Swamp": "set in murky, mysterious wetlands", + "Lunar Colony": "on a futuristic moon base", + "Parallel Universe": "in an alternate version of reality", + "Micro World": "set in a tiny, microscopic environment", + "Dreamscape": "within a surreal, subconscious realm", + "Utopian": "in an idealized, perfect society", + "Noir": "with shadowy, high-contrast urban atmosphere", + "Cosmic Horror": "facing incomprehensible, terrifying entities", + "Elemental Planes": "in realms of pure earth, air, fire, or water", + "Time Travel Hub": "at a nexus of different historical periods", + "Pocket Dimension": "within a small, self-contained universe" + } +} \ No newline at end of file diff --git a/magic_photo_prompt.py b/magic_photo_prompt.py new file mode 100644 index 0000000..d0f45fe --- /dev/null +++ b/magic_photo_prompt.py @@ -0,0 +1,59 @@ +import json +import os + +class MagicPhotoPrompter: + @classmethod + def INPUT_TYPES(s): + # Load options from JSON file + options = s.load_options() + return { + "optional": { + "prompt": ("STRING", {"multiline": True}), + "camera": (list(options["camera"].keys()),), + "composition_shot": (list(options["composition_shot"].keys()),), + "time_of_day": (list(options["time_of_day"].keys()),), + "color_grading": (list(options["color_grading"].keys()),), + "lighting": (list(options["lighting"].keys()),), + "environment": (list(options["environment"].keys()),), + }, + } + + RETURN_TYPES = ("STRING",) + FUNCTION = "generate_prompt" + CATEGORY = "Prompter" + + @staticmethod + def load_options(): + # Load the JSON file containing the options and prompts + json_path = os.path.join(os.path.dirname(__file__), "magic_options.json") + with open(json_path, 'r') as file: + return json.load(file) + + def generate_prompt(self, prompt, camera, composition_shot, time_of_day, color_grading, lighting, environment): + options = self.load_options() + + # Concatenate the prompts for each selected option + prompt_parts = [ + part for part in [ + prompt, + options["composition_shot"].get(composition_shot, ""), + options["environment"].get(environment, ""), + options["time_of_day"].get(time_of_day, ""), + options["lighting"].get(lighting, ""), + options["camera"].get(camera, ""), + options["color_grading"].get(color_grading, "") + ] if part.strip() != "" + ] + # Join the prompt parts with commas + final_prompt = ". ".join(prompt_parts) + + return ("Photograph of " + final_prompt,) + +# Node class mappings +NODE_CLASS_MAPPINGS = { + "Magic Photo Prompter 🪄": MagicPhotoPrompter +} + +NODE_DISPLAY_NAME_MAPPINGS = { + "Magic Photo Prompter 🪄": "Magic Photo Prompter" +} \ No newline at end of file