import gradio as gr import os import tempfile from typing import List, Dict, Any import fitz # PyMuPDF for PDF processing from PIL import Image import pytesseract import io import json from datetime import datetime # Set up Tesseract OCR (make sure it's installed on your system) pytesseract.pytesseract.tesseract_cmd = '/usr/bin/tesseract' # Update this path as needed # Custom theme for a warm, loving interface custom_theme = gr.themes.Soft( primary_hue="pink", secondary_hue="red", neutral_hue="slate", font=gr.themes.GoogleFont("Inter"), text_size="lg", spacing_size="lg", radius_size="lg" ).set( button_primary_background_fill="*primary_600", button_primary_background_fill_hover="*primary_700", block_title_text_weight="600", ) def extract_text_from_pdf(pdf_path: str) -> str: """Extract text from PDF file using PyMuPDF""" try: doc = fitz.open(pdf_path) text = "" for page in doc: text += page.get_text() return text except Exception as e: raise gr.Error(f"Error processing PDF: {str(e)}") def extract_text_from_image(image_path: str) -> str: """Extract text from image using Tesseract OCR""" try: img = Image.open(image_path) text = pytesseract.image_to_string(img) return text except Exception as e: raise gr.Error(f"Error processing image: {str(e)}") def extract_text_from_txt(txt_path: str) -> str: """Extract text from TXT file""" try: with open(txt_path, 'r', encoding='utf-8') as f: return f.read() except Exception as e: raise gr.Error(f"Error reading text file: {str(e)}") def process_uploaded_files(files: List[Dict[str, Any]]) -> str: """Process all uploaded files and extract text content""" all_text = "" for file_data in files: file_path = file_data['name'] file_ext = os.path.splitext(file_path)[1].lower() if file_ext == '.pdf': text = extract_text_from_pdf(file_path) elif file_ext in ['.png', '.jpg', '.jpeg', '.gif', '.bmp']: text = extract_text_from_image(file_path) elif file_ext == '.txt': text = extract_text_from_txt(file_path) else: raise gr.Error(f"Unsupported file type: {file_ext}") all_text += f"\n\n=== Content from {os.path.basename(file_path)} ===\n\n" all_text += text return all_text def analyze_relationship(person_name: str, relationship_history: str) -> Dict[str, Any]: """ Analyze relationship history and generate a love guide. This is a mock function - in a real app, you would use an AI model here. """ if not person_name.strip(): raise gr.Error("Please enter the person's name") if not relationship_history.strip(): raise gr.Error("Please upload at least one document") # Mock analysis - replace with actual AI model calls analysis = { "person_name": person_name, "analysis_date": datetime.now().strftime("%Y-%m-%d %H:%M:%S"), "key_traits": [ "Loyal", "Affectionate", "Good listener", "Supportive", "Adventurous" ], "love_language": "Quality Time", "communication_style": "Open and honest", "conflict_resolution": "Calm discussion", "ideal_partner_traits": [ "Patient", "Understanding", "Communicative", "Supportive", "Trustworthy" ], "relationship_goals": [ "Build trust", "Improve communication", "Create shared experiences", "Support each other's growth" ], "love_guide": { "daily_affirmations": [ f"Tell {person_name} how much you appreciate them", "Give genuine compliments", "Show interest in their day" ], "quality_time": [ "Plan regular date nights", "Have deep conversations", "Create shared hobbies" ], "conflict_tips": [ "Stay calm and listen", "Use 'I' statements", "Focus on solutions" ] } } return analysis def generate_love_guide(person_name: str, files: List[Dict[str, Any]]) -> Dict[str, Any]: """Main function to process files and generate love guide""" try: # Process uploaded files relationship_history = process_uploaded_files(files) # Analyze relationship analysis = analyze_relationship(person_name, relationship_history) return analysis except Exception as e: raise gr.Error(f"Error generating love guide: {str(e)}") def format_analysis(analysis: Dict[str, Any]) -> str: """Format analysis results for display""" if not analysis: return "No analysis available" formatted = f""" # 💖 Love Guide for {analysis['person_name']} **Analysis Date:** {analysis['analysis_date']} ## 🎯 Key Traits {' • '.join(analysis['key_traits'])} ## 💬 Love Language **{analysis['love_language']}** - This person values meaningful time together and undivided attention. ## 🗣️ Communication Style **{analysis['communication_style']}** - They appreciate open, honest conversations. ## ✨ Ideal Partner Traits {' • '.join(analysis['ideal_partner_traits'])} ## 🎯 Relationship Goals {' • '.join(analysis['relationship_goals'])} ## 💡 Love Guide ### Daily Affirmations {' • '.join(analysis['love_guide']['daily_affirmations'])} ### Quality Time Ideas {' • '.join(analysis['love_guide']['quality_time'])} ### Conflict Resolution Tips {' • '.join(analysis['love_guide']['conflict_tips'])} --- **Remember:** Every relationship is unique. Use this guide as inspiration and adapt it to your specific situation. """ return formatted def save_analysis(analysis: Dict[str, Any]) -> str: """Save analysis to JSON file""" try: timestamp = datetime.now().strftime("%Y%m%d_%H%M%S") filename = f"love_guide_{analysis['person_name']}_{timestamp}.json" # Save to temporary file temp_dir = tempfile.gettempdir() file_path = os.path.join(temp_dir, filename) with open(file_path, 'w', encoding='utf-8') as f: json.dump(analysis, f, indent=2, ensure_ascii=False) return file_path except Exception as e: raise gr.Error(f"Error saving analysis: {str(e)}") # Create Gradio interface with gr.Blocks() as demo: gr.Markdown(""" # 💖 Love Guide Generator **Built with anycoder** - [Visit our Space](https://huggingface.co/spaces/akhaliq/anycoder) Upload documents from your relationship history (texts, PDFs, or images) and let AI analyze the patterns to create a personalized guide to loving your partner and understanding their ideal relationship. """) with gr.Row(): with gr.Column(scale=1): gr.Markdown("## 📁 Upload Relationship Documents") gr.Markdown("Upload transcripts, messages, or any documents that show your relationship history.") file_upload = gr.File( label="Upload Documents", file_types=["text", "pdf", "image"], file_count="multiple", type="filepath", height=150 ) person_name = gr.Textbox( label="Person's Name", placeholder="Enter the name of the person to analyze", lines=1 ) analyze_btn = gr.Button("💖 Generate Love Guide", variant="primary", size="lg") with gr.Column(scale=1): gr.Markdown("## 📊 Analysis Results") result_tabs = gr.Tabs() with result_tabs: with gr.Tab("📝 Love Guide"): love_guide_output = gr.Markdown() with gr.Tab("💾 Raw Analysis"): raw_analysis = gr.JSON(label="Raw Analysis Data") with gr.Tab("📥 Download"): download_output = gr.File(label="Download Love Guide") status_output = gr.Textbox(label="Status", interactive=False) # Event handlers analyze_btn.click( fn=generate_love_guide, inputs=[person_name, file_upload], outputs=[raw_analysis], api_visibility="public" ).then( fn=format_analysis, inputs=[raw_analysis], outputs=[love_guide_output] ).then( fn=save_analysis, inputs=[raw_analysis], outputs=[download_output] ).then( fn=lambda: "✅ Love guide generated successfully! You can now view the results and download the guide.", outputs=[status_output] ) gr.Markdown(""" ## 💡 Tips for Best Results - Upload multiple documents for more accurate analysis - Include both positive and challenging moments - Be specific about the person's name - The more context you provide, the better the guide will be ## ⚠️ Privacy Note All files are processed locally and not stored on our servers. Your relationship data remains private. """) # Launch the app with custom theme demo.launch( theme=custom_theme, footer_links=[ {"label": "Built with anycoder", "url": "https://huggingface.co/spaces/akhaliq/anycoder"}, {"label": "Gradio Documentation", "url": "https://www.gradio.app/docs"} ], title="Love Guide Generator", description="AI-powered relationship analysis and love guide generator" )