using DramaLing.Api.Models.DTOs; using DramaLing.Api.Models.Entities; namespace DramaLing.Api.Services.AI.Gemini; /// /// 圖片描述生成服務實作 /// public class ImageDescriptionGenerator : IImageDescriptionGenerator { private readonly IGeminiClient _geminiClient; private readonly ILogger _logger; public ImageDescriptionGenerator( IGeminiClient geminiClient, ILogger logger) { _geminiClient = geminiClient ?? throw new ArgumentNullException(nameof(geminiClient)); _logger = logger ?? throw new ArgumentNullException(nameof(logger)); } public async Task GenerateImageDescriptionAsync(Flashcard flashcard, GenerationOptionsDto options) { try { _logger.LogInformation("Starting image description generation for flashcard {FlashcardId}", flashcard.Id); var prompt = BuildImageDescriptionPrompt(flashcard, options); var response = await _geminiClient.CallGeminiAPIAsync(prompt); if (string.IsNullOrWhiteSpace(response)) { throw new InvalidOperationException("Gemini API returned empty response"); } var description = ExtractImageDescription(response); var optimizedPrompt = OptimizeForReplicate(description, options); _logger.LogInformation("Image description generated successfully for flashcard {FlashcardId}", flashcard.Id); return optimizedPrompt; } catch (Exception ex) { _logger.LogError(ex, "Image description generation failed for flashcard {FlashcardId}", flashcard.Id); throw; } } private string BuildImageDescriptionPrompt(Flashcard flashcard, GenerationOptionsDto options) { return $@"# 總覽 你是一位專業插畫設計師兼職英文老師,專門為英語學習教材製作插畫圖卡,用來幫助學生理解英文例句的意思。 # 例句資訊 例句:{flashcard.Example} # SOP 1. 根據上述英文例句,請撰寫一段圖像描述提示詞,用於提供圖片生成AI作為生成圖片的提示詞 2. 請將下方「風格指南」的所有要求加入提示詞中 3. 並於圖片提示詞最後加上:「Absolutely no visible text, characters, letters, numbers, symbols, handwriting, labels, or any form of writing anywhere in the image — including on signs, books, clothing, screens, or backgrounds.」 # 圖片提示詞規範 ## 情境清楚 1. 角色描述具體清楚 2. 動作明確具象 3. 場景明確具體 4. 物品明確具體 5. 語意需與原句一致 6. 避免過於抽象或象徵性符號 ## 風格指南 - 風格類型:扁平插畫(Flat Illustration) - 線條特徵:無描邊線條(outline-less) - 色調:暖色調、柔和、低飽和 - 人物樣式:簡化卡通人物,表情自然,不誇張 - 背景構成:圖形簡化,使用色塊區分層次 - 整體氛圍:溫馨、平靜、適合教育情境 - 技術風格:無紋理、無漸層、無光影寫實感 請根據以上規範,為這個英文例句生成圖片描述提示詞,並確保完全符合風格指南要求。"; } private string ExtractImageDescription(string geminiResponse) { // 從 Gemini 回應中提取圖片描述 var description = geminiResponse.Trim(); // 移除可能的 markdown 標記 if (description.StartsWith("```")) { var lines = description.Split('\n'); description = string.Join('\n', lines.Skip(1).SkipLast(1)); } return description.Trim(); } private string OptimizeForReplicate(string description, GenerationOptionsDto options) { var optimizedPrompt = description; // 確保包含扁平插畫風格要求 if (!optimizedPrompt.Contains("flat illustration")) { optimizedPrompt += ". Style guide: flat illustration style, outline-less shapes, warm and soft color tones, low saturation, cartoon-style characters with natural expressions, simplified background with color blocks, cozy and educational atmosphere, no texture, no gradients, no photorealism, no fantasy elements."; } // 強制加入禁止文字的規則 if (!optimizedPrompt.Contains("Absolutely no visible text")) { optimizedPrompt += " Absolutely no visible text, characters, letters, numbers, symbols, handwriting, labels, or any form of writing anywhere in the image — including on signs, books, clothing, screens, or backgrounds."; } return optimizedPrompt; } }