| <script lang="ts"> | |
| import type { MonsterWorkflowState } from '$lib/types'; | |
| interface Props { | |
| state: MonsterWorkflowState; | |
| onReset: () => void; | |
| } | |
| let { state, onReset }: Props = $props(); | |
| function downloadImage() { | |
| if (!state.monsterImage?.imageUrl) return; | |
| const link = document.createElement('a'); | |
| link.href = state.monsterImage.imageUrl; | |
| link.download = `monster-${Date.now()}.png`; | |
| link.click(); | |
| } | |
| function copyPrompt() { | |
| if (!state.imagePrompt) return; | |
| navigator.clipboard.writeText(state.imagePrompt); | |
| alert('Prompt copied to clipboard!'); | |
| } | |
| </script> | |
| <div class="result-container"> | |
| <h3>Your Monster Has Been Created!</h3> | |
| {#if state.monsterImage} | |
| <div class="monster-image-container"> | |
| <img | |
| src={state.monsterImage.imageUrl} | |
| alt="Generated Monster" | |
| class="monster-image" | |
| /> | |
| </div> | |
| {/if} | |
| <div class="results-grid"> | |
| <div class="result-section"> | |
| <h4>Original Description</h4> | |
| <div class="result-content"> | |
| <p>{state.imageCaption || 'No caption available'}</p> | |
| </div> | |
| </div> | |
| <div class="result-section"> | |
| <h4>Monster Concept</h4> | |
| <div class="result-content"> | |
| <p>{state.monsterConcept || 'No concept available'}</p> | |
| </div> | |
| </div> | |
| <div class="result-section"> | |
| <h4>Generation Prompt</h4> | |
| <div class="result-content"> | |
| <p>{state.imagePrompt || 'No prompt available'}</p> | |
| {#if state.imagePrompt} | |
| <button class="copy-button" onclick={copyPrompt}> | |
| <svg width="16" height="16" viewBox="0 0 16 16" fill="currentColor"> | |
| <path d="M4 2a2 2 0 0 1 2-2h8a2 2 0 0 1 2 2v8a2 2 0 0 1-2 2H6a2 2 0 0 1-2-2V2zm2 0v8h8V2H6zM2 6a2 2 0 0 0-2 2v6a2 2 0 0 0 2 2h6a2 2 0 0 0 2-2v-2h-2v2H2V8h2V6H2z"/> | |
| </svg> | |
| Copy | |
| </button> | |
| {/if} | |
| </div> | |
| </div> | |
| </div> | |
| <div class="action-buttons"> | |
| <button class="action-button download" onclick={downloadImage}> | |
| <svg width="20" height="20" viewBox="0 0 20 20" fill="currentColor"> | |
| <path d="M13 8V2H7v6H2l8 8 8-8h-5zM0 18h20v2H0v-2z"/> | |
| </svg> | |
| Download Monster | |
| </button> | |
| <button class="action-button reset" onclick={onReset}> | |
| <svg width="20" height="20" viewBox="0 0 20 20" fill="currentColor"> | |
| <path d="M4 2a1 1 0 011 1v2.101a7.002 7.002 0 0111.601 2.566 1 1 0 11-1.885.666A5.002 5.002 0 005.058 7.293a1 1 0 01-1.414 1.414l-2.35-2.35A1 1 0 011 5.648V3a1 1 0 011-1zm.008 9.057a1 1 0 011.276.61A5.002 5.002 0 0014.943 13H13a1 1 0 110-2h5a1 1 0 011 1v5a1 1 0 11-2 0v-2.101a7.002 7.002 0 01-11.601-2.566 1 1 0 01.61-1.276z"/> | |
| </svg> | |
| Create Another Monster | |
| </button> | |
| </div> | |
| </div> | |
| <style> | |
| .result-container { | |
| max-width: 900px; | |
| margin: 0 auto; | |
| padding: 2rem; | |
| } | |
| h3 { | |
| text-align: center; | |
| color: #333; | |
| margin-bottom: 2rem; | |
| } | |
| .monster-image-container { | |
| text-align: center; | |
| margin-bottom: 3rem; | |
| } | |
| .monster-image { | |
| max-width: 100%; | |
| max-height: 600px; | |
| border-radius: 12px; | |
| box-shadow: 0 4px 20px rgba(0, 0, 0, 0.1); | |
| } | |
| .results-grid { | |
| display: grid; | |
| gap: 1.5rem; | |
| margin-bottom: 3rem; | |
| } | |
| .result-section { | |
| background: #f8f9fa; | |
| padding: 1.5rem; | |
| border-radius: 8px; | |
| border: 1px solid #e9ecef; | |
| } | |
| .result-section h4 { | |
| margin: 0 0 1rem 0; | |
| color: #495057; | |
| font-size: 1.1rem; | |
| } | |
| .result-content { | |
| position: relative; | |
| } | |
| .result-content p { | |
| margin: 0; | |
| line-height: 1.6; | |
| color: #333; | |
| } | |
| .copy-button { | |
| position: absolute; | |
| top: -8px; | |
| right: -8px; | |
| background: #007bff; | |
| color: white; | |
| border: none; | |
| padding: 0.4rem 0.8rem; | |
| border-radius: 4px; | |
| font-size: 0.85rem; | |
| cursor: pointer; | |
| display: flex; | |
| align-items: center; | |
| gap: 0.3rem; | |
| transition: background 0.2s; | |
| } | |
| .copy-button:hover { | |
| background: #0056b3; | |
| } | |
| .action-buttons { | |
| display: flex; | |
| justify-content: center; | |
| gap: 1rem; | |
| flex-wrap: wrap; | |
| } | |
| .action-button { | |
| display: flex; | |
| align-items: center; | |
| gap: 0.5rem; | |
| padding: 0.8rem 1.5rem; | |
| border: none; | |
| border-radius: 6px; | |
| font-size: 1rem; | |
| font-weight: 500; | |
| cursor: pointer; | |
| transition: all 0.2s; | |
| } | |
| .action-button.download { | |
| background: #28a745; | |
| color: white; | |
| } | |
| .action-button.download:hover { | |
| background: #218838; | |
| } | |
| .action-button.reset { | |
| background: #6c757d; | |
| color: white; | |
| } | |
| .action-button.reset:hover { | |
| background: #5a6268; | |
| } | |
| @media (max-width: 768px) { | |
| .result-container { | |
| padding: 1rem; | |
| } | |
| .action-buttons { | |
| flex-direction: column; | |
| } | |
| .action-button { | |
| width: 100%; | |
| justify-content: center; | |
| } | |
| } | |
| </style> |