Loading source
Pulling the file list, source metadata, and syntax-aware rendering for this listing.
Source from repo
AI-powered design system generator that produces complete, tailored design systems from project requirements.
Files
Skill
Size
Entrypoint
Format
Open file
Syntax-highlighted preview of this file as included in the skill package.
scripts/search-slides.py
1#!/usr/bin/env python32# -*- coding: utf-8 -*-3"""4Slide Search CLI - Search slide design databases for strategies, layouts, copy, and charts5"""67import sys8import json9import argparse10from slide_search_core import (11search, search_all, AVAILABLE_DOMAINS,12search_with_context, get_layout_for_goal, get_typography_for_slide,13get_color_for_emotion, get_background_config14)151617def format_result(result, domain):18"""Format a single search result for display"""19output = []2021if domain == "strategy":22output.append(f"**{result.get('strategy_name', 'N/A')}**")23output.append(f" Slides: {result.get('slide_count', 'N/A')}")24output.append(f" Structure: {result.get('structure', 'N/A')}")25output.append(f" Goal: {result.get('goal', 'N/A')}")26output.append(f" Audience: {result.get('audience', 'N/A')}")27output.append(f" Tone: {result.get('tone', 'N/A')}")28output.append(f" Arc: {result.get('narrative_arc', 'N/A')}")29output.append(f" Source: {result.get('sources', 'N/A')}")3031elif domain == "layout":32output.append(f"**{result.get('layout_name', 'N/A')}**")33output.append(f" Use case: {result.get('use_case', 'N/A')}")34output.append(f" Zones: {result.get('content_zones', 'N/A')}")35output.append(f" Visual weight: {result.get('visual_weight', 'N/A')}")36output.append(f" CTA: {result.get('cta_placement', 'N/A')}")37output.append(f" Recommended: {result.get('recommended_for', 'N/A')}")38output.append(f" Avoid: {result.get('avoid_for', 'N/A')}")39output.append(f" CSS: {result.get('css_structure', 'N/A')}")4041elif domain == "copy":42output.append(f"**{result.get('formula_name', 'N/A')}**")43output.append(f" Components: {result.get('components', 'N/A')}")44output.append(f" Use case: {result.get('use_case', 'N/A')}")45output.append(f" Template: {result.get('example_template', 'N/A')}")46output.append(f" Emotion: {result.get('emotion_trigger', 'N/A')}")47output.append(f" Slide type: {result.get('slide_type', 'N/A')}")48output.append(f" Source: {result.get('source', 'N/A')}")4950elif domain == "chart":51output.append(f"**{result.get('chart_type', 'N/A')}**")52output.append(f" Best for: {result.get('best_for', 'N/A')}")53output.append(f" Data type: {result.get('data_type', 'N/A')}")54output.append(f" When to use: {result.get('when_to_use', 'N/A')}")55output.append(f" When to avoid: {result.get('when_to_avoid', 'N/A')}")56output.append(f" Max categories: {result.get('max_categories', 'N/A')}")57output.append(f" Slide context: {result.get('slide_context', 'N/A')}")58output.append(f" CSS: {result.get('css_implementation', 'N/A')}")59output.append(f" Accessibility: {result.get('accessibility_notes', 'N/A')}")6061return "\n".join(output)626364def format_context(context):65"""Format contextual recommendations for display."""66output = []67output.append(f"\n=== CONTEXTUAL RECOMMENDATIONS ===")68output.append(f"Inferred Goal: {context.get('inferred_goal', 'N/A')}")69output.append(f"Position: Slide {context.get('slide_position')} of {context.get('total_slides')}")7071if context.get('recommended_layout'):72output.append(f"\n📐 Layout: {context['recommended_layout']}")73output.append(f" Direction: {context.get('layout_direction', 'N/A')}")74output.append(f" Visual Weight: {context.get('visual_weight', 'N/A')}")7576if context.get('typography'):77typo = context['typography']78output.append(f"\n📝 Typography:")79output.append(f" Primary: {typo.get('primary_size', 'N/A')}")80output.append(f" Secondary: {typo.get('secondary_size', 'N/A')}")81output.append(f" Contrast: {typo.get('weight_contrast', 'N/A')}")8283if context.get('color_treatment'):84color = context['color_treatment']85output.append(f"\n🎨 Color Treatment:")86output.append(f" Background: {color.get('background', 'N/A')}")87output.append(f" Text: {color.get('text_color', 'N/A')}")88output.append(f" Accent: {color.get('accent_usage', 'N/A')}")8990if context.get('should_break_pattern'):91output.append(f"\n⚡ Pattern Break: YES (use contrasting layout)")9293if context.get('should_use_full_bleed'):94output.append(f"\n🖼️ Full Bleed: Recommended for emotional impact")9596if context.get('use_background_image') and context.get('background'):97bg = context['background']98output.append(f"\n📸 Background Image:")99output.append(f" Category: {bg.get('image_category', 'N/A')}")100output.append(f" Overlay: {bg.get('overlay_style', 'N/A')}")101output.append(f" Keywords: {bg.get('search_keywords', 'N/A')}")102103output.append(f"\n✨ Animation: {context.get('animation_class', 'animate-fade-up')}")104105return "\n".join(output)106107108def main():109parser = argparse.ArgumentParser(110description="Search slide design databases",111formatter_class=argparse.RawDescriptionHelpFormatter,112epilog="""113Examples:114search-slides.py "investor pitch" # Auto-detect domain (strategy)115search-slides.py "funnel conversion" -d chart116search-slides.py "headline hook" -d copy117search-slides.py "two column" -d layout118search-slides.py "startup funding" --all # Search all domains119search-slides.py "metrics dashboard" --json # JSON output120121Contextual Search (Premium System):122search-slides.py "problem slide" --context --position 2 --total 9123search-slides.py "cta" --context --position 9 --total 9 --prev-emotion frustration124"""125)126127parser.add_argument("query", help="Search query")128parser.add_argument("-d", "--domain", choices=AVAILABLE_DOMAINS,129help="Specific domain to search (auto-detected if not specified)")130parser.add_argument("-n", "--max-results", type=int, default=3,131help="Maximum results to return (default: 3)")132parser.add_argument("--all", action="store_true",133help="Search across all domains")134parser.add_argument("--json", action="store_true",135help="Output as JSON")136137# Contextual search options138parser.add_argument("--context", action="store_true",139help="Use contextual search with layout/typography/color recommendations")140parser.add_argument("--position", type=int, default=1,141help="Slide position in deck (1-based, default: 1)")142parser.add_argument("--total", type=int, default=9,143help="Total slides in deck (default: 9)")144parser.add_argument("--prev-emotion", type=str, default=None,145help="Previous slide's emotion for contrast calculation")146147args = parser.parse_args()148149# Contextual search mode150if args.context:151result = search_with_context(152args.query,153slide_position=args.position,154total_slides=args.total,155previous_emotion=args.prev_emotion156)157158if args.json:159print(json.dumps(result, indent=2))160else:161print(format_context(result['context']))162163# Also show base search results164if result.get('base_results'):165print("\n\n=== RELATED SEARCH RESULTS ===")166for domain, data in result['base_results'].items():167print(f"\n--- {domain.upper()} ---")168for item in data['results']:169print(format_result(item, domain))170print()171return172173if args.all:174results = search_all(args.query, args.max_results)175176if args.json:177print(json.dumps(results, indent=2))178else:179if not results:180print(f"No results found for: {args.query}")181return182183for domain, data in results.items():184print(f"\n=== {domain.upper()} ===")185print(f"File: {data['file']}")186print(f"Results: {data['count']}")187print()188for result in data['results']:189print(format_result(result, domain))190print()191else:192result = search(args.query, args.domain, args.max_results)193194if args.json:195print(json.dumps(result, indent=2))196else:197if result.get("error"):198print(f"Error: {result['error']}")199return200201print(f"Domain: {result['domain']}")202print(f"Query: {result['query']}")203print(f"File: {result['file']}")204print(f"Results: {result['count']}")205print()206207if result['count'] == 0:208print("No matching results found.")209return210211for i, item in enumerate(result['results'], 1):212print(f"--- Result {i} ---")213print(format_result(item, result['domain']))214print()215216217if __name__ == "__main__":218main()219