padaria / index.html
Chipema's picture
Create a workflow where:
7f46c2a verified
Raw
History Blame Contribute Delete
20.7 kB
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Photo Theme Transformer</title>
<script src="https://cdn.tailwindcss.com"></script>
<link href="https://unpkg.com/aos@2.3.1/dist/aos.css" rel="stylesheet">
<script src="https://unpkg.com/aos@2.3.1/dist/aos.js"></script>
<script src="https://cdn.jsdelivr.net/npm/feather-icons/dist/feather.min.js"></script>
<script src="https://unpkg.com/feather-icons"></script>
<style>
.dropzone {
border: 2px dashed #6366f1;
border-radius: 0.75rem;
transition: all 0.3s ease;
}
.dropzone.active {
border-color: #4f46e5;
background-color: #eef2ff;
}
.theme-card {
transition: all 0.3s ease;
cursor: pointer;
}
.theme-card:hover {
transform: translateY(-5px);
}
.theme-card.selected {
border-color: #6366f1;
box-shadow: 0 10px 15px -3px rgba(99, 102, 241, 0.2);
}
.preview-image {
max-height: 400px;
object-fit: contain;
}
.result-image {
max-height: 500px;
object-fit: contain;
box-shadow: 0 20px 25px -5px rgba(0, 0, 0, 0.1);
}
</style>
</head>
<body class="bg-gray-50 min-h-screen">
<div class="container mx-auto px-4 py-12">
<!-- Header -->
<header class="text-center mb-12" data-aos="fade-down">
<h1 class="text-4xl font-bold text-indigo-600 mb-3">Photo Theme Transformer</h1>
<p class="text-lg text-gray-600 max-w-2xl mx-auto">Turn your photos into beautiful themed illustrations with custom text overlays</p>
</header>
<!-- Workflow Steps -->
<div class="max-w-4xl mx-auto bg-white rounded-xl shadow-md overflow-hidden">
<!-- Step 1: Upload Photo -->
<div id="step-1" class="p-8" data-aos="fade-up">
<div class="flex items-center mb-6">
<div class="flex items-center justify-center w-10 h-10 rounded-full bg-indigo-100 text-indigo-600 font-bold mr-4">1</div>
<h2 class="text-2xl font-semibold text-gray-800">Upload Your Photo</h2>
</div>
<div class="dropzone p-12 text-center mb-6" id="dropzone">
<div class="flex flex-col items-center justify-center">
<i data-feather="upload" class="w-12 h-12 text-indigo-500 mb-4"></i>
<p class="text-lg text-gray-600 mb-2">Drag & drop your photo here</p>
<p class="text-sm text-gray-500 mb-4">or</p>
<label for="file-upload" class="cursor-pointer bg-indigo-600 text-white px-6 py-2 rounded-lg hover:bg-indigo-700 transition">
Select from device
</label>
<input id="file-upload" type="file" accept="image/*" class="hidden">
</div>
</div>
<div id="preview-container" class="hidden">
<h3 class="text-lg font-medium text-gray-700 mb-3">Your Photo Preview</h3>
<div class="flex justify-center">
<img id="preview-image" class="preview-image rounded-lg border border-gray-200" src="" alt="Preview">
</div>
<div class="flex justify-center mt-4">
<button id="change-photo" class="text-indigo-600 hover:text-indigo-800 flex items-center">
<i data-feather="refresh-cw" class="w-4 h-4 mr-1"></i> Change Photo
</button>
</div>
</div>
<div class="flex justify-end mt-6">
<button id="next-to-step-2" class="bg-indigo-600 text-white px-6 py-2 rounded-lg hover:bg-indigo-700 transition disabled:opacity-50" disabled>
Next <i data-feather="arrow-right" class="w-4 h-4 ml-1"></i>
</button>
</div>
</div>
<!-- Step 2: Choose Theme -->
<div id="step-2" class="p-8 hidden" data-aos="fade-up">
<div class="flex items-center mb-6">
<div class="flex items-center justify-center w-10 h-10 rounded-full bg-indigo-100 text-indigo-600 font-bold mr-4">2</div>
<h2 class="text-2xl font-semibold text-gray-800">Choose Your Theme</h2>
</div>
<div class="grid grid-cols-1 md:grid-cols-2 gap-6 mb-8">
<div class="theme-card p-6 border-2 border-gray-200 rounded-xl" data-theme="child">
<div class="flex items-center mb-4">
<div class="w-10 h-10 rounded-full bg-yellow-100 flex items-center justify-center mr-3">
<i data-feather="smile" class="text-yellow-500"></i>
</div>
<h3 class="text-xl font-medium text-gray-800">Child Theme</h3>
</div>
<p class="text-gray-600 mb-4">Playful, colorful illustrations with cartoon-style elements perfect for kids.</p>
<div class="flex justify-center">
<img src="http://static.photos/education/640x360/1" alt="Child Theme Example" class="rounded-lg h-40 object-cover">
</div>
</div>
<div class="theme-card p-6 border-2 border-gray-200 rounded-xl" data-theme="adult">
<div class="flex items-center mb-4">
<div class="w-10 h-10 rounded-full bg-blue-100 flex items-center justify-center mr-3">
<i data-feather="feather" class="text-blue-500"></i>
</div>
<h3 class="text-xl font-medium text-gray-800">Adult Theme</h3>
</div>
<p class="text-gray-600 mb-4">Elegant, refined illustrations with sophisticated styling for adults.</p>
<div class="flex justify-center">
<img src="http://static.photos/minimal/640x360/2" alt="Adult Theme Example" class="rounded-lg h-40 object-cover">
</div>
</div>
</div>
<div class="flex justify-between mt-6">
<button id="back-to-step-1" class="text-gray-600 hover:text-gray-800 flex items-center">
<i data-feather="arrow-left" class="w-4 h-4 mr-1"></i> Back
</button>
<button id="next-to-step-3" class="bg-indigo-600 text-white px-6 py-2 rounded-lg hover:bg-indigo-700 transition disabled:opacity-50" disabled>
Next <i data-feather="arrow-right" class="w-4 h-4 ml-1"></i>
</button>
</div>
</div>
<!-- Step 3: Add Text -->
<div id="step-3" class="p-8 hidden" data-aos="fade-up">
<div class="flex items-center mb-6">
<div class="flex items-center justify-center w-10 h-10 rounded-full bg-indigo-100 text-indigo-600 font-bold mr-4">3</div>
<h2 class="text-2xl font-semibold text-gray-800">Add Your Text</h2>
</div>
<div class="mb-6">
<label for="custom-text" class="block text-sm font-medium text-gray-700 mb-2">Enter your text (max 100 characters)</label>
<textarea id="custom-text" rows="3" maxlength="100" class="w-full px-4 py-2 border border-gray-300 rounded-lg focus:ring-indigo-500 focus:border-indigo-500" placeholder="E.g., Happy Birthday!"></textarea>
<div class="text-right text-sm text-gray-500 mt-1"><span id="char-count">0</span>/100</div>
</div>
<div class="mb-6">
<label class="block text-sm font-medium text-gray-700 mb-2">Text Style</label>
<div class="grid grid-cols-2 md:grid-cols-4 gap-3">
<button class="text-style-btn px-4 py-2 border rounded-lg hover:bg-gray-50" data-style="playful">
<span class="text-yellow-500 font-bold">Playful</span>
</button>
<button class="text-style-btn px-4 py-2 border rounded-lg hover:bg-gray-50" data-style="elegant">
<span class="text-blue-500 font-serif italic">Elegant</span>
</button>
<button class="text-style-btn px-4 py-2 border rounded-lg hover:bg-gray-50" data-style="bold">
<span class="text-gray-800 font-bold">Bold</span>
</button>
<button class="text-style-btn px-4 py-2 border rounded-lg hover:bg-gray-50" data-style="handwritten">
<span class="text-pink-500 font-sans" style="font-family: 'Comic Sans MS', cursive">Handwritten</span>
</button>
</div>
</div>
<div class="flex justify-between mt-6">
<button id="back-to-step-2" class="text-gray-600 hover:text-gray-800 flex items-center">
<i data-feather="arrow-left" class="w-4 h-4 mr-1"></i> Back
</button>
<button id="generate-result" class="bg-indigo-600 text-white px-6 py-2 rounded-lg hover:bg-indigo-700 transition">
Generate Result <i data-feather="wand" class="w-4 h-4 ml-1"></i>
</button>
</div>
</div>
<!-- Step 4: Results -->
<div id="step-4" class="p-8 hidden" data-aos="fade-up">
<div class="flex items-center mb-6">
<div class="flex items-center justify-center w-10 h-10 rounded-full bg-indigo-100 text-indigo-600 font-bold mr-4">4</div>
<h2 class="text-2xl font-semibold text-gray-800">Your Transformed Photo</h2>
</div>
<div class="flex flex-col items-center mb-8">
<div class="relative mb-6">
<img id="result-image" class="result-image rounded-lg" src="" alt="Transformed Photo">
<div id="text-overlay" class="absolute inset-0 flex items-center justify-center pointer-events-none"></div>
</div>
<div class="flex flex-wrap justify-center gap-4">
<button id="download-btn" class="bg-indigo-600 text-white px-6 py-2 rounded-lg hover:bg-indigo-700 transition flex items-center">
<i data-feather="download" class="w-4 h-4 mr-2"></i> Download
</button>
<button id="share-btn" class="bg-green-600 text-white px-6 py-2 rounded-lg hover:bg-green-700 transition flex items-center">
<i data-feather="share-2" class="w-4 h-4 mr-2"></i> Share
</button>
<button id="new-transformation" class="bg-gray-200 text-gray-800 px-6 py-2 rounded-lg hover:bg-gray-300 transition flex items-center">
<i data-feather="repeat" class="w-4 h-4 mr-2"></i> New Transformation
</button>
</div>
</div>
</div>
</div>
</div>
<!-- Loading Modal -->
<div id="loading-modal" class="fixed inset-0 bg-black bg-opacity-50 flex items-center justify-center hidden z-50">
<div class="bg-white p-8 rounded-xl max-w-md text-center">
<div class="animate-spin rounded-full h-16 w-16 border-t-2 border-b-2 border-indigo-500 mx-auto mb-4"></div>
<h3 class="text-xl font-semibold text-gray-800 mb-2">Transforming Your Photo</h3>
<p class="text-gray-600">This may take a few moments...</p>
</div>
</div>
<script>
// Initialize AOS and Feather Icons
AOS.init();
feather.replace();
// DOM Elements
const dropzone = document.getElementById('dropzone');
const fileInput = document.getElementById('file-upload');
const previewContainer = document.getElementById('preview-container');
const previewImage = document.getElementById('preview-image');
const changePhotoBtn = document.getElementById('change-photo');
const nextToStep2Btn = document.getElementById('next-to-step-2');
const step1 = document.getElementById('step-1');
const step2 = document.getElementById('step-2');
const step3 = document.getElementById('step-3');
const step4 = document.getElementById('step-4');
const backToStep1Btn = document.getElementById('back-to-step-1');
const nextToStep3Btn = document.getElementById('next-to-step-3');
const backToStep2Btn = document.getElementById('back-to-step-2');
const generateResultBtn = document.getElementById('generate-result');
const themeCards = document.querySelectorAll('.theme-card');
const customText = document.getElementById('custom-text');
const charCount = document.getElementById('char-count');
const textStyleBtns = document.querySelectorAll('.text-style-btn');
const resultImage = document.getElementById('result-image');
const textOverlay = document.getElementById('text-overlay');
const downloadBtn = document.getElementById('download-btn');
const shareBtn = document.getElementById('share-btn');
const newTransformationBtn = document.getElementById('new-transformation');
const loadingModal = document.getElementById('loading-modal');
// State
let selectedFile = null;
let selectedTheme = null;
let selectedTextStyle = 'playful';
// Event Listeners
// File upload handling
dropzone.addEventListener('click', () => fileInput.click());
dropzone.addEventListener('dragover', (e) => {
e.preventDefault();
dropzone.classList.add('active');
});
dropzone.addEventListener('dragleave', () => {
dropzone.classList.remove('active');
});
dropzone.addEventListener('drop', (e) => {
e.preventDefault();
dropzone.classList.remove('active');
if (e.dataTransfer.files.length) {
handleFileUpload(e.dataTransfer.files[0]);
}
});
fileInput.addEventListener('change', () => {
if (fileInput.files.length) {
handleFileUpload(fileInput.files[0]);
}
});
changePhotoBtn.addEventListener('click', () => {
previewContainer.classList.add('hidden');
nextToStep2Btn.disabled = true;
fileInput.value = '';
selectedFile = null;
});
// Navigation
nextToStep2Btn.addEventListener('click', () => {
step1.classList.add('hidden');
step2.classList.remove('hidden');
});
backToStep1Btn.addEventListener('click', () => {
step2.classList.add('hidden');
step1.classList.remove('hidden');
});
nextToStep3Btn.addEventListener('click', () => {
step2.classList.add('hidden');
step3.classList.remove('hidden');
});
backToStep2Btn.addEventListener('click', () => {
step3.classList.add('hidden');
step2.classList.remove('hidden');
});
// Theme selection
themeCards.forEach(card => {
card.addEventListener('click', () => {
themeCards.forEach(c => c.classList.remove('selected'));
card.classList.add('selected');
selectedTheme = card.dataset.theme;
nextToStep3Btn.disabled = false;
});
});
// Text handling
customText.addEventListener('input', () => {
charCount.textContent = customText.value.length;
});
textStyleBtns.forEach(btn => {
btn.addEventListener('click', () => {
selectedTextStyle = btn.dataset.style;
textStyleBtns.forEach(b => b.classList.remove('bg-gray-100'));
btn.classList.add('bg-gray-100');
});
});
// Generate result
generateResultBtn.addEventListener('click', () => {
loadingModal.classList.remove('hidden');
// Simulate processing delay
setTimeout(() => {
loadingModal.classList.add('hidden');
step3.classList.add('hidden');
step4.classList.remove('hidden');
// In a real app, this would be the AI-generated image
// For demo, we'll just use the original with a filter
resultImage.src = selectedFile ? URL.createObjectURL(selectedFile) : '';
// Apply text overlay
textOverlay.innerHTML = '';
if (customText.value.trim()) {
const textElement = document.createElement('div');
textElement.textContent = customText.value;
textElement.className = 'text-3xl font-bold p-4 text-center';
// Apply selected style
switch(selectedTextStyle) {
case 'playful':
textElement.className += ' text-yellow-500 font-bold';
break;
case 'elegant':
textElement.className += ' text-blue-500 font-serif italic';
break;
case 'bold':
textElement.className += ' text-gray-800 font-extrabold';
break;
case 'handwritten':
textElement.className += ' text-pink-500';
textElement.style.fontFamily = "'Comic Sans MS', cursive";
break;
}
textOverlay.appendChild(textElement);
}
}, 3000);
});
// Result actions
downloadBtn.addEventListener('click', () => {
// In a real app, this would download the actual transformed image
alert('Download functionality would be implemented here');
});
shareBtn.addEventListener('click', () => {
// In a real app, this would share the image
alert('Share functionality would be implemented here');
});
newTransformationBtn.addEventListener('click', () => {
step4.classList.add('hidden');
step1.classList.remove('hidden');
previewContainer.classList.add('hidden');
fileInput.value = '';
selectedFile = null;
selectedTheme = null;
selectedTextStyle = 'playful';
customText.value = '';
charCount.textContent = '0';
nextToStep2Btn.disabled = true;
nextToStep3Btn.disabled = true;
themeCards.forEach(c => c.classList.remove('selected'));
textStyleBtns.forEach(b => b.classList.remove('bg-gray-100'));
textStyleBtns[0].classList.add('bg-gray-100');
});
// Helper functions
function handleFileUpload(file) {
if (!file.type.match('image.*')) {
alert('Please upload an image file');
return;
}
selectedFile = file;
const reader = new FileReader();
reader.onload = (e) => {
previewImage.src = e.target.result;
previewContainer.classList.remove('hidden');
nextToStep2Btn.disabled = false;
};
reader.readAsDataURL(file);
}
</script>
</body>
</html>