<!DOCTYPE html>
<html lang="es">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<!-- MODIFICAR: Título de la pestaña del navegador -->
<title>Un Mensaje para Ti</title>
<link rel="stylesheet" href="style.css">
</head>
<body>
<div id="petals-container"></div>
<div class="card-container" onclick="animateCard(event)">
<div class="card" id="card">
<div class="page page-back">
<div class="page-content front-face image-page">
</div>
<div class="page-content back-face">
<!--Significa paz-->
<div class="kanji-text">平和</div>
<div class="romaji-text">Heiwa</div>
<!-- MODIFICAR: Mensaje de la parte trasera de la carta -->
<p class="message-text">
Que la paz y la belleza llenen tu corazón.
</p>
<!-- MODIFICAR: Firma o dedicatoria -->
<div class="signature">Con cariño 💕</div>
</div>
</div>
<div class="page page-front">
<div class="page-content front-face">
<div class="sakura-decoration">🌸</div>
<h1 class="cover-title">花見</h1>
<p class="cover-subtitle">Hanami</p>
<p class="click-hint" id="hint-text">Toca para abrir la hoja ✨</p>
</div>
<div class="page-content back-face">
<!-- MODIFICAR: Mensaje principal (parte central de la carta) -->
<p class="message-text">
Como los pétalos de sakura<br>
que danzan en el viento,<br>
disfruta de la belleza efímera<br>
de cada momento.
</p>
</div>
</div>
</div>
</div>
<script src="script.js"></script>
</body>
</html>
@import url('https://fonts.googleapis.com/css2?family=Noto+Sans+JP:wght@300;400;500&family=Dancing+Script:wght@400;500;600&display=swap');
* {
margin: 0;
padding: 0;
box-sizing: border-box;
}
body {
/* MODIFICAR: Color de fondo de la página */
background: linear-gradient(135deg, #fdf2f8 0%, #fce7f3 50%, #f3e8ff 100%);
min-height: 100vh;
display: flex;
justify-content: center;
align-items: center;
font-family: 'Noto Sans JP', sans-serif;
overflow: hidden;
position: relative;
}
#petals-container {
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
pointer-events: none;
}
.petal {
position: absolute;
width: 10px;
height: 10px;
/* MODIFICAR: Colores de los pétalos */
background: radial-gradient(ellipse at center, #ffc0cb 0%, #ffb6c1 50%, #ff91a4 100%);
border-radius: 0 100% 0 100%;
opacity: 0.8;
animation: fall linear infinite;
}
@keyframes fall {
from {
transform: translateY(-10vh) rotate(0deg);
}
to {
transform: translateY(110vh) rotate(360deg);
}
}
.sparkle {
position: absolute;
transform: translate(-50%, -50%);
width: 8px;
height: 8px;
/* MODIFICAR: Color de las partículas al hacer clic */
background: #ffc700;
border-radius: 50%;
pointer-events: none;
z-index: 9999;
opacity: 1;
transition: transform 0.8s cubic-bezier(.17, .67, .83, .67), opacity 0.8s ease-out;
}
.card-container {
width: 300px;
height: 400px;
perspective: 1500px;
cursor: pointer;
filter:
drop-shadow(0px 10px 10px rgba(236, 72, 153, 0.15))
drop-shadow(0px 20px 25px rgba(168, 85, 247, 0.15));
transition: filter 0.4s ease-out;
}
.card-container:hover {
filter:
drop-shadow(0px 10px 10px rgba(236, 72, 153, 0.15))
drop-shadow(0px 20px 25px rgba(168, 85, 247, 0.15))
drop-shadow(0 0 20px rgba(236, 72, 153, 0.5));
}
.card {
width: 100%;
height: 100%;
position: relative;
transform-style: preserve-3d;
transition: transform 1.2s cubic-bezier(0.25, 0.46, 0.45, 0.94);
}
.card.leaf-opened { transform: translateX(50%); }
.card.flipped-over { transform: translateX(50%) rotateY(-180deg); }
.card.leaf-opened .page-front { transform: rotateY(-180deg); }
.card.flipped-over .page-front { z-index: 0; }
.page {
position: absolute;
width: 100%;
height: 100%;
top: 0;
left: 0;
border-radius: 8px;
background: #fff;
transform-style: preserve-3d;
backface-visibility: hidden;
}
.page-front { transform-origin: left center; transition: transform 1.2s cubic-bezier(0.25, 0.46, 0.45, 0.94); z-index: 2; }
.page-back { z-index: 1; }
.page-content {
padding: 40px 30px;
height: 100%;
display: flex;
flex-direction: column;
justify-content: center;
align-items: center;
text-align: center;
position: absolute;
width: 100%;
height: 100%;
backface-visibility: hidden;
background: linear-gradient(135deg, #ffffff 0%, #fef7ff 100%);
border: 1px solid rgba(255, 182, 193, 0.3);
border-radius: 8px;
}
.back-face { transform: rotateY(180deg); }
/* MODIFICAR: Colores de los textos en la tarjeta */
.sakura-decoration { font-size: 100px; color: #ff91a4; margin-bottom: 20px; }
.cover-title { font-size: 42px; color: #7c2d92; font-weight: 500; margin-bottom: 15px; }
.cover-subtitle { font-size: 18px; color: #a855f7; font-weight: 300; margin-bottom: 40px; }
.click-hint { font-size: 16px; color: #ec4899; font-style: italic; animation: pulse 2s infinite; }
@keyframes pulse { 0%, 100% { opacity: 0.7; } 50% { opacity: 1; } }
.kanji-text { font-size: 56px; color: #7c2d92; margin-bottom: 25px; font-weight: 300; }
.romaji-text { font-size: 28px; color: #a855f7; margin-bottom: 30px; font-style: italic; }
.message-text { font-family: 'Dancing Script', cursive; font-size: 22px; color: #6b21a8; line-height: 1.7; }
.signature { font-size: 16px; color: #ec4899; font-style: italic; opacity: 0.8; margin-top: 20px; }
.page-front .back-face .message-text { font-size: 24px; }
.card.is-closing .page-front .back-face { opacity: 0; }
.image-page {
/* MODIFICAR: Imagen de la contraportada */
background-image: url('https://res.cloudinary.com/dsgtnbq6l/image/upload/v1752005839/ref_2_teorng.png');
background-size: contain;
background-position: center;
background-repeat: no-repeat;
padding: 40px;
background-clip: content-box;
}
@media (max-width: 650px) { .card-container { width: 250px; height: 350px; } .cover-title { font-size: 36px; } .kanji-text { font-size: 48px; } .page-content { padding: 30px 20px; } .page-front .back-face .message-text { font-size: 20px; } .message-text { font-size: 19px; } .signature { margin-top: 15px; } }
@media (max-width: 520px) { .card-container { width: 200px; height: 300px; } .cover-title { font-size: 32px; } .kanji-text { font-size: 40px; } .page-content { padding: 25px 15px; } .page-front .back-face .message-text { font-size: 16px; } .message-text { font-size: 17px; } .signature { margin-top: 10px; } }
let cardState = 0;
const card = document.getElementById('card');
const hintText = document.getElementById('hint-text');
const petalsContainer = document.getElementById('petals-container');
/**
* @param {MouseEvent} e
*/
function createClickParticles(e) {
const x = e.clientX;
const y = e.clientY;
const particleCount = 20;
for (let i = 0; i < particleCount; i++) {
const sparkle = document.createElement('div');
sparkle.className = 'sparkle';
sparkle.style.left = `${x}px`;
sparkle.style.top = `${y}px`;
const angle = Math.random() * 2 * Math.PI;
const distance = Math.random() * 50 + 50;
const targetX = Math.cos(angle) * distance;
const targetY = Math.sin(angle) * distance;
requestAnimationFrame(() => {
sparkle.style.transform = `translate(${targetX}px, ${targetY}px) scale(0)`;
sparkle.style.opacity = '0';
});
petalsContainer.appendChild(sparkle);
setTimeout(() => { sparkle.remove(); }, 800);
}
}
function animateCard(event) {
createClickParticles(event);
if (cardState === 2) {
card.classList.add('is-closing');
}
cardState = (cardState + 1) % 3;
card.classList.remove('leaf-opened', 'flipped-over');
switch (cardState) {
case 0:
hintText.textContent = 'Toca para abrir la hoja ✨';
setTimeout(() => { card.classList.remove('is-closing'); }, 1200);
break;
case 1:
card.classList.add('leaf-opened');
hintText.textContent = 'Toca para dar la vuelta 💖';
break;
case 2:
card.classList.add('flipped-over');
hintText.textContent = 'Toca para cerrar 🌸';
break;
}
}
function createPetal() {
const petal = document.createElement('div');
petal.className = 'petal';
petal.style.left = Math.random() * 100 + 'vw';
petal.style.animationDuration = (Math.random() * 5 + 8) + 's';
petal.style.animationDelay = (Math.random() * 2) + 's';
const size = Math.random() * 8 + 6;
petal.style.width = size + 'px';
petal.style.height = size + 'px';
petalsContainer.appendChild(petal);
setTimeout(() => { petal.remove(); }, 10000);
}
// MODIFICAR: Frecuencia con la que aparecen nuevos pétalos (en milisegundos). Menor número = más pétalos.
setInterval(createPetal, 300);