class CSSStyles: """ CSS styling configuration for the SceneWeaver application. Professional design system with clean typography and modern aesthetics. """ @staticmethod def get_main_css() -> str: """ Get the main CSS styling for the application. Returns: Complete CSS string for Gradio interface styling """ return """ /* Import professional fonts */ @import url('https://fonts.googleapis.com/css2?family=Inter:wght@300;400;500;600;700&family=JetBrains+Mono:wght@400;500&display=swap'); /* CSS Variables - Professional color system */ :root { /* Primary brand colors */ --primary-color: #1e3a5f; --primary-hover: #2d5a8a; --primary-light: #e8f4fd; /* Accent colors */ --accent-color: #3b82f6; --accent-hover: #2563eb; --accent-light: #dbeafe; /* Status colors */ --success-color: #10b981; --warning-color: #f59e0b; --error-color: #ef4444; /* Neutral colors */ --bg-primary: #ffffff; --bg-secondary: #f8fafc; --bg-tertiary: #f1f5f9; --text-primary: #1e293b; --text-secondary: #475569; --text-muted: #94a3b8; --border-color: #e2e8f0; --border-light: #f1f5f9; /* Shadows */ --shadow-sm: 0 1px 2px 0 rgba(0, 0, 0, 0.05); --shadow-md: 0 4px 6px -1px rgba(0, 0, 0, 0.1), 0 2px 4px -2px rgba(0, 0, 0, 0.1); --shadow-lg: 0 10px 15px -3px rgba(0, 0, 0, 0.1), 0 4px 6px -4px rgba(0, 0, 0, 0.1); --shadow-xl: 0 20px 25px -5px rgba(0, 0, 0, 0.1), 0 8px 10px -6px rgba(0, 0, 0, 0.1); /* Border radius */ --radius-sm: 6px; --radius-md: 8px; --radius-lg: 12px; --radius-xl: 16px; /* Transitions */ --transition-fast: 150ms ease; --transition-normal: 250ms ease; --transition-slow: 350ms ease; } /* Global styles */ * { font-family: 'Inter', -apple-system, BlinkMacSystemFont, 'Segoe UI', sans-serif !important; -webkit-font-smoothing: antialiased !important; -moz-osx-font-smoothing: grayscale !important; } /* Main container */ .gradio-container { background: linear-gradient(180deg, #f8fafc 0%, #f1f5f9 100%) !important; min-height: 100vh !important; padding: 24px !important; } /* ===== HEADER SECTION ===== */ .main-header { text-align: center !important; padding: 48px 32px 40px !important; margin-bottom: 32px !important; background: linear-gradient(135deg, var(--bg-primary) 0%, var(--bg-secondary) 100%) !important; border-radius: var(--radius-xl) !important; box-shadow: var(--shadow-md) !important; border: 1px solid var(--border-light) !important; } .main-title { font-size: 2.75rem !important; font-weight: 700 !important; color: var(--primary-color) !important; margin: 0 0 12px 0 !important; letter-spacing: -0.03em !important; display: flex !important; align-items: center !important; justify-content: center !important; gap: 14px !important; line-height: 1.2 !important; } .title-emoji { font-size: 2.5rem !important; filter: drop-shadow(0 2px 4px rgba(0,0,0,0.15)) !important; transition: transform var(--transition-normal) !important; } .title-emoji:hover { transform: scale(1.1) rotate(-5deg) !important; } .main-subtitle { font-size: 1.1rem !important; color: var(--text-secondary) !important; font-weight: 400 !important; margin: 0 !important; line-height: 1.5 !important; max-width: 700px !important; margin: 0 auto !important; } /* ===== CARD SYSTEM ===== */ .feature-card { background: var(--bg-primary) !important; border: 1px solid var(--border-color) !important; border-radius: var(--radius-lg) !important; padding: 24px !important; margin-bottom: 20px !important; box-shadow: var(--shadow-sm) !important; transition: all var(--transition-normal) !important; position: relative !important; } .feature-card:hover { border-color: var(--accent-color) !important; box-shadow: var(--shadow-lg) !important; /* Removed transform to fix dropdown positioning issue in Gradio 5.x */ /* transform: translateY(-2px) !important; */ } .card-title { font-size: 1.25rem !important; font-weight: 600 !important; color: var(--text-primary) !important; margin-bottom: 16px !important; display: flex !important; align-items: center !important; gap: 10px !important; } .section-emoji { font-size: 1.2rem !important; filter: drop-shadow(0 1px 2px rgba(0,0,0,0.1)) !important; } /* ===== INPUT COMPONENTS ===== */ .input-field { border: 1px solid var(--border-color) !important; border-radius: var(--radius-md) !important; background: var(--bg-primary) !important; transition: all var(--transition-fast) !important; } .input-field:focus-within { border-color: var(--accent-color) !important; box-shadow: 0 0 0 3px var(--accent-light) !important; } /* ===== BUTTONS ===== */ .primary-button { background: linear-gradient(135deg, var(--accent-color) 0%, var(--accent-hover) 100%) !important; color: white !important; border: none !important; border-radius: var(--radius-md) !important; padding: 14px 28px !important; font-size: 1rem !important; font-weight: 600 !important; cursor: pointer !important; transition: all var(--transition-normal) !important; box-shadow: var(--shadow-md) !important; } .primary-button:hover { transform: translateY(-2px) !important; box-shadow: var(--shadow-lg) !important; filter: brightness(1.05) !important; } .secondary-button { background: var(--bg-primary) !important; color: var(--accent-color) !important; border: 1.5px solid var(--accent-color) !important; border-radius: var(--radius-md) !important; padding: 12px 20px !important; font-size: 0.95rem !important; font-weight: 500 !important; cursor: pointer !important; transition: all var(--transition-fast) !important; } .secondary-button:hover { background: var(--accent-light) !important; transform: translateY(-1px) !important; } /* ===== RESULTS GALLERY ===== */ #results-gallery-centered { display: flex !important; flex-direction: column !important; align-items: center !important; } #results-gallery-centered .gradio-tabs { width: 100% !important; } .result-gallery { border-radius: var(--radius-lg) !important; overflow: hidden !important; border: 1px solid var(--border-color) !important; box-shadow: var(--shadow-md) !important; } .result-gallery img { width: 100% !important; height: auto !important; object-fit: contain !important; } /* ===== STATUS PANEL ===== */ .status-panel { background: var(--bg-secondary) !important; border: 1px solid var(--border-color) !important; border-radius: var(--radius-md) !important; padding: 12px 16px !important; margin: 16px 0 !important; } .status-ready { color: var(--success-color) !important; font-weight: 500 !important; } /* ===== LOADING NOTICE ===== */ .loading-notice { background: linear-gradient(135deg, #fef3c7 0%, #fde68a 100%) !important; border: 1px solid #f59e0b !important; border-radius: var(--radius-md) !important; padding: 14px 18px !important; margin: 16px 0 !important; display: flex !important; align-items: center !important; gap: 12px !important; } .loading-notice-icon { font-size: 1.3rem !important; flex-shrink: 0 !important; } .loading-notice-text { color: #92400e !important; font-size: 0.9rem !important; font-weight: 500 !important; line-height: 1.5 !important; } /* ===== QUICK START GUIDE ===== */ .user-guidance-panel { background: var(--bg-secondary) !important; border: 1px solid var(--border-color) !important; border-radius: var(--radius-md) !important; margin: 16px 0 !important; overflow: hidden !important; } .guidance-summary { background: var(--bg-primary) !important; padding: 12px 16px !important; cursor: pointer !important; font-weight: 500 !important; color: var(--text-primary) !important; transition: background var(--transition-fast) !important; list-style: none !important; display: flex !important; align-items: center !important; gap: 8px !important; border-bottom: 1px solid var(--border-color) !important; } .guidance-summary:hover { background: var(--accent-light) !important; } .guidance-summary::-webkit-details-marker { display: none !important; } .guidance-content { padding: 16px !important; color: var(--text-secondary) !important; line-height: 1.6 !important; } .guidance-content p { margin: 8px 0 !important; font-size: 0.9rem !important; } .guidance-content strong { color: var(--primary-color) !important; font-weight: 600 !important; } /* ===== FOOTER ===== */ .app-footer { background: var(--bg-primary) !important; border: 1px solid var(--border-color) !important; border-radius: var(--radius-lg) !important; padding: 32px !important; margin-top: 32px !important; text-align: center !important; } .footer-powered { margin-bottom: 20px !important; } .footer-powered-title { font-size: 0.85rem !important; font-weight: 500 !important; color: var(--text-muted) !important; text-transform: uppercase !important; letter-spacing: 0.1em !important; margin-bottom: 16px !important; } .footer-tech-grid { display: flex !important; flex-wrap: wrap !important; justify-content: center !important; gap: 12px !important; margin-bottom: 24px !important; } .footer-tech-item { background: var(--bg-secondary) !important; border: 1px solid var(--border-color) !important; border-radius: var(--radius-sm) !important; padding: 8px 16px !important; font-size: 0.85rem !important; font-weight: 500 !important; color: var(--text-secondary) !important; transition: all var(--transition-fast) !important; } .footer-tech-item:hover { background: var(--accent-light) !important; border-color: var(--accent-color) !important; color: var(--accent-color) !important; } .footer-divider { height: 1px !important; background: var(--border-color) !important; margin: 20px auto !important; max-width: 400px !important; } .footer-copyright { font-size: 0.85rem !important; color: var(--text-muted) !important; font-weight: 400 !important; } .footer-copyright a { color: var(--accent-color) !important; text-decoration: none !important; font-weight: 500 !important; } .footer-copyright a:hover { text-decoration: underline !important; } /* ===== TABS STYLING ===== */ .gradio-tabs { border: none !important; } .gradio-tabs > .tab-nav { background: var(--bg-secondary) !important; border-radius: var(--radius-md) !important; padding: 4px !important; gap: 4px !important; border: 1px solid var(--border-color) !important; margin-bottom: 16px !important; } .gradio-tabs > .tab-nav > button { border-radius: var(--radius-sm) !important; padding: 10px 20px !important; font-weight: 500 !important; font-size: 0.9rem !important; transition: all var(--transition-fast) !important; border: none !important; background: transparent !important; color: var(--text-secondary) !important; } .gradio-tabs > .tab-nav > button.selected { background: var(--bg-primary) !important; color: var(--accent-color) !important; box-shadow: var(--shadow-sm) !important; } .gradio-tabs > .tab-nav > button:hover:not(.selected) { background: var(--bg-primary) !important; color: var(--text-primary) !important; } /* ===== ACCORDION ===== */ .gradio-accordion { border: 1px solid var(--border-color) !important; border-radius: var(--radius-md) !important; overflow: hidden !important; margin-top: 12px !important; } .gradio-accordion > .label-wrap { background: var(--bg-secondary) !important; padding: 12px 16px !important; font-weight: 500 !important; } .gradio-accordion > .label-wrap:hover { background: var(--bg-tertiary) !important; } /* ===== RESPONSIVE ===== */ @media (max-width: 768px) { .main-title { font-size: 2rem !important; } .main-subtitle { font-size: 1rem !important; } .footer-tech-grid { gap: 8px !important; } .footer-tech-item { padding: 6px 12px !important; font-size: 0.8rem !important; } } /* ===== EMOJI ENHANCEMENT ===== */ .emoji-enhanced { display: inline-block !important; font-style: normal !important; filter: drop-shadow(0 1px 2px rgba(0,0,0,0.1)) !important; transition: transform var(--transition-fast) !important; } .emoji-enhanced:hover { transform: scale(1.1) !important; } /* ===== IMAGE DISPLAY FIX ===== */ .gradio-image { min-height: 200px !important; } .gradio-image img { max-height: 500px !important; object-fit: contain !important; } /* ===== SCENE TEMPLATE DROPDOWN ===== */ .template-dropdown { margin: 8px 0 !important; } .template-dropdown select, .template-dropdown input { font-size: 0.95rem !important; padding: 10px 14px !important; border-radius: var(--radius-md) !important; border: 1px solid var(--border-color) !important; background: var(--bg-primary) !important; transition: all var(--transition-fast) !important; } .template-dropdown select:hover, .template-dropdown input:hover { border-color: var(--accent-color) !important; } .template-dropdown select:focus, .template-dropdown input:focus { border-color: var(--accent-color) !important; box-shadow: 0 0 0 3px var(--accent-light) !important; outline: none !important; } /* Dropdown option styling */ .template-dropdown option { padding: 8px 12px !important; font-size: 0.95rem !important; } /* ===== INPAINTING UI STYLES ===== */ .inpainting-header { text-align: center !important; padding: 16px !important; margin-bottom: 16px !important; background: linear-gradient(135deg, var(--primary-light) 0%, var(--accent-light) 100%) !important; border-radius: var(--radius-lg) !important; border: 1px solid var(--border-color) !important; } .inpainting-header h3 { font-size: 1.4rem !important; font-weight: 600 !important; color: var(--primary-color) !important; margin: 0 0 8px 0 !important; } .inpainting-header p { font-size: 0.95rem !important; color: var(--text-secondary) !important; margin: 0 !important; } /* Main mode tabs styling */ #main-mode-tabs { margin-bottom: 16px !important; } #main-mode-tabs > .tab-nav { background: var(--bg-secondary) !important; border-radius: var(--radius-lg) !important; padding: 6px !important; gap: 6px !important; border: 1px solid var(--border-color) !important; } #main-mode-tabs > .tab-nav > button { border-radius: var(--radius-md) !important; padding: 12px 24px !important; font-weight: 600 !important; font-size: 1rem !important; transition: all var(--transition-normal) !important; border: none !important; background: transparent !important; color: var(--text-secondary) !important; } #main-mode-tabs > .tab-nav > button.selected { background: linear-gradient(135deg, var(--accent-color) 0%, var(--accent-hover) 100%) !important; color: white !important; box-shadow: var(--shadow-md) !important; } #main-mode-tabs > .tab-nav > button:hover:not(.selected) { background: var(--bg-primary) !important; color: var(--text-primary) !important; } /* Mask editor styling */ .mask-editor-container { border: 2px dashed var(--border-color) !important; border-radius: var(--radius-lg) !important; padding: 8px !important; background: var(--bg-secondary) !important; transition: border-color var(--transition-fast) !important; } .mask-editor-container:hover { border-color: var(--accent-color) !important; } /* Inpainting template cards */ .inpainting-gallery { margin: 16px 0 !important; } .inpainting-category { margin-bottom: 20px !important; } .inpainting-category-title { font-size: 0.9rem !important; font-weight: 600 !important; color: var(--text-secondary) !important; margin-bottom: 12px !important; padding-bottom: 8px !important; border-bottom: 1px solid var(--border-color) !important; } .inpainting-grid { display: grid !important; grid-template-columns: repeat(auto-fill, minmax(120px, 1fr)) !important; gap: 10px !important; } .inpainting-card { display: flex !important; flex-direction: column !important; align-items: center !important; justify-content: center !important; padding: 14px 10px !important; background: var(--bg-primary) !important; border: 1px solid var(--border-color) !important; border-radius: var(--radius-md) !important; cursor: pointer !important; transition: all var(--transition-normal) !important; min-height: 80px !important; } .inpainting-card:hover { background: var(--accent-light) !important; border-color: var(--accent-color) !important; transform: translateY(-2px) !important; box-shadow: var(--shadow-md) !important; } .inpainting-card.selected { background: var(--accent-light) !important; border-color: var(--accent-color) !important; box-shadow: 0 0 0 2px var(--accent-color) !important; } .inpainting-icon { font-size: 1.6rem !important; margin-bottom: 6px !important; } .inpainting-name { font-size: 0.8rem !important; font-weight: 500 !important; color: var(--text-primary) !important; text-align: center !important; line-height: 1.2 !important; } .inpainting-desc { font-size: 0.7rem !important; color: var(--text-muted) !important; text-align: center !important; margin-top: 4px !important; } /* ControlNet mode toggle */ .controlnet-mode-toggle { display: flex !important; gap: 8px !important; margin: 8px 0 !important; } .controlnet-mode-btn { flex: 1 !important; padding: 10px 16px !important; border: 1px solid var(--border-color) !important; border-radius: var(--radius-md) !important; background: var(--bg-primary) !important; color: var(--text-secondary) !important; font-weight: 500 !important; cursor: pointer !important; transition: all var(--transition-fast) !important; } .controlnet-mode-btn:hover { border-color: var(--accent-color) !important; color: var(--accent-color) !important; } .controlnet-mode-btn.active { background: var(--accent-color) !important; border-color: var(--accent-color) !important; color: white !important; } /* Preview badge */ .preview-badge { display: inline-flex !important; align-items: center !important; gap: 4px !important; padding: 4px 10px !important; background: var(--warning-color) !important; color: white !important; font-size: 0.75rem !important; font-weight: 600 !important; border-radius: var(--radius-sm) !important; text-transform: uppercase !important; } /* Quality score display */ .quality-score { display: inline-flex !important; align-items: center !important; gap: 6px !important; padding: 6px 12px !important; border-radius: var(--radius-md) !important; font-weight: 500 !important; font-size: 0.9rem !important; } .quality-score.excellent { background: rgba(16, 185, 129, 0.1) !important; color: var(--success-color) !important; } .quality-score.good { background: rgba(59, 130, 246, 0.1) !important; color: var(--accent-color) !important; } .quality-score.warning { background: rgba(245, 158, 11, 0.1) !important; color: var(--warning-color) !important; } .quality-score.poor { background: rgba(239, 68, 68, 0.1) !important; color: var(--error-color) !important; } /* Responsive adjustments for inpainting */ @media (max-width: 768px) { .inpainting-grid { grid-template-columns: repeat(2, 1fr) !important; } #main-mode-tabs > .tab-nav > button { padding: 10px 16px !important; font-size: 0.9rem !important; } } /* ===== DROPDOWN POSITIONING FIX FOR GRADIO 4.x/5.x ===== */ /* Fix dropdown list positioning issue in left column */ .feature-card { overflow: visible !important; } /* Ensure dropdown portal/overlay renders correctly */ .gradio-dropdown, .gradio-dropdown > div, [data-testid="dropdown"] { position: relative !important; } /* Fix dropdown listbox positioning */ .gradio-dropdown ul, .gradio-dropdown [role="listbox"], [data-testid="dropdown"] ul { position: absolute !important; z-index: 9999 !important; left: 0 !important; top: 100% !important; width: 100% !important; max-height: 300px !important; overflow-y: auto !important; background: var(--bg-primary) !important; border: 1px solid var(--border-color) !important; border-radius: var(--radius-md) !important; box-shadow: var(--shadow-lg) !important; margin-top: 4px !important; } """