diff --git a/app/static/css/style.css b/app/static/css/style.css index 5696c1b..9593222 100755 --- a/app/static/css/style.css +++ b/app/static/css/style.css @@ -252,237 +252,102 @@ body { - Clean Inner Letter Sheet ========================================= */ -.envelope-outer-wrap { - width: 100%; - max-width: 480px; - margin: 15px auto 25px; -} +/* ========================================= + CODEPEN POCKET GEOMETRY + MAJESTIC SLIDE-OUT ANIMATION + - Real 4-Flap Envelope Fold Geometry (from CodePen) + - Left, Right, Bottom and Top Flaps meeting at Center (50% 50%) + - Authentic Hogwarts Wax Seal in the Exact Mitte + - Subtle Handwriting Return Address (Top-Left) + - Clean Inner Letter Sheet (No Text Walls) + - Majestic Rise-Out Opening Animation with Space Creation + ========================================= */ -.envelope-form { - width: 100%; - perspective: 1200px; -} - -.env-wrap { +.antique-envelope-scene { position: relative; - overflow: hidden; - width: 100%; - padding-top: 86%; /* Aspect ratio for envelope body + rising letter */ - background: transparent; + width: min(480px, 94vw); + height: min(280px, 60vw); + margin: 25px auto 35px; + perspective: 1200px; + perspective-origin: center top; + transition: margin-top 0.8s cubic-bezier(0.25, 1, 0.5, 1); } -/* Interior Back Wall of the Envelope (Bottom 55%) */ -.env-body-back { - position: absolute; - bottom: 0; - left: 0; +.antique-envelope-scene.envelope-opened, +.antique-envelope-scene:has(.envelope-opened) { + margin-top: 155px; + margin-bottom: 25px; +} + +.envelope-base { + position: relative; width: 100%; - height: 55%; - background-color: #2e2014; + height: 100%; + border-radius: 6px; + box-shadow: + 0 20px 45px rgba(0, 0, 0, 0.75), + 0 4px 14px rgba(0, 0, 0, 0.5); +} + +/* Interior Back Wall of the Envelope */ +.envelope-interior { + position: absolute; + inset: 0; + border-radius: 6px; + background-color: #2b1d12; background-image: - radial-gradient(ellipse at 50% 50%, rgba(0, 0, 0, 0.35) 0%, rgba(0, 0, 0, 0.8) 100%), + radial-gradient(circle at 50% 50%, rgba(0, 0, 0, 0.35) 0%, rgba(0, 0, 0, 0.8) 100%), url('/static/img/parchment_texture.jpg'); background-size: cover; - border-radius: 0 0 6px 6px; - border: 1.5px solid #6b4a24; - box-shadow: 0 16px 36px rgba(0, 0, 0, 0.75); + border: 2px solid #7a5c36; z-index: 1; } -/* Top V-Flap (Hinged at 45% Top Edge of Envelope Body) */ -.env-top { +/* The Letter Sheet (Slides Up Out of the Envelope Pocket) */ +.letter-sheet { position: absolute; - width: 100%; - height: 33%; - top: 45%; - z-index: 8; - transform-origin: top center; - transition: transform 0.6s cubic-bezier(0.4, 0, 0.2, 1), z-index 0s 0.25s; -} - -.env-top:before { - content: ''; - position: absolute; - width: 100%; - height: 100%; - background-color: #ebd8ae; - background-image: - radial-gradient(ellipse at 50% 20%, rgba(255, 255, 255, 0.3) 0%, rgba(130, 95, 45, 0.2) 100%), - url('/static/img/parchment_texture.jpg'); - background-size: cover; - clip-path: polygon(50% 100%, 0 0, 100% 0); - filter: drop-shadow(0px 8px 12px rgba(35, 18, 5, 0.6)); - border-top: 1px solid #7c5830; -} - -/* Sketched Dashed Line on Top Flap */ -.env-top:after { - content: ''; - position: absolute; - top: 2px; + top: 10px; left: 4%; width: 92%; - height: 94%; - clip-path: polygon(50% 96%, 2% 2%, 98% 2%); - border-top: 1.5px dashed rgba(110, 75, 35, 0.4); - pointer-events: none; -} - -/* Bottom Pocket Wrap */ -.env-bottom-wrap { - height: 55%; - width: 100%; - z-index: 4; - bottom: 0; - position: absolute; - filter: drop-shadow(0px -4px 6px rgba(30, 15, 5, 0.3)); -} - -/* Bottom Flap */ -.env-bottom { - clip-path: polygon(50% 50%, 100% 0, 100% 100%, 0 100%, 0 0); - background-color: #e5cf9f; + height: 380px; + max-height: 65vh; + background-color: #f7f0df; background-image: - radial-gradient(ellipse at 50% 80%, rgba(255, 255, 255, 0.25) 0%, rgba(120, 85, 40, 0.25) 100%), - url('/static/img/parchment_texture.jpg'); - background-size: cover; - width: 100%; - height: 100%; - position: relative; - border-radius: 0 0 6px 6px; -} - -/* Side Flaps Inside Bottom Pocket */ -.env-bottom:before, .env-bottom:after { - content: ''; - position: absolute; - width: 50%; - height: 100%; - background-size: cover; -} - -/* Left Side Flap */ -.env-bottom:before { - left: 0; - clip-path: polygon(100% 50%, 0 0, 0 100%); - background-color: #dfc794; - background-image: - linear-gradient(135deg, rgba(0, 0, 0, 0.12) 0%, rgba(255, 255, 255, 0.15) 100%), - url('/static/img/parchment_texture.jpg'); - box-shadow: inset -2px 0 6px rgba(60, 40, 15, 0.2); -} - -/* Right Side Flap */ -.env-bottom:after { - right: 0; - clip-path: polygon(0 50%, 100% 0, 100% 100%); - background-color: #dbc38f; - background-image: - linear-gradient(-135deg, rgba(0, 0, 0, 0.12) 0%, rgba(255, 255, 255, 0.15) 100%), - url('/static/img/parchment_texture.jpg'); - box-shadow: inset 2px 0 6px rgba(60, 40, 15, 0.2); -} - -/* Small Handwriting Return Address in Top Left ("Abs.: Hogwarts Schule...") */ -.env-sender-line { - position: absolute; - top: 47%; - left: 14px; - font-family: 'Caveat', 'Marck Script', cursive; - font-size: clamp(0.76rem, 2.1vw, 0.88rem); - color: #0d3820; /* Authentic Hogwarts Emerald Ink */ - font-weight: 600; - z-index: 7; - pointer-events: none; - letter-spacing: 0.2px; - text-shadow: 0 0 1px rgba(13, 56, 32, 0.25); - transition: opacity 0.4s ease; - white-space: nowrap; -} - -/* Hand-Sketched Hogwarts Wax Seal in the Exact Mitte (Center) */ -.sketched-wax-seal { - position: absolute; - top: 72.5%; /* Exact point where top flap and pocket meet */ - left: 50%; - transform: translate(-50%, -50%) rotate(-3deg); - width: 68px; - height: 68px; - border-radius: 50%; - cursor: pointer; - z-index: 9; - transition: transform 0.3s cubic-bezier(0.34, 1.56, 0.64, 1), box-shadow 0.3s ease, opacity 0.4s ease; - box-shadow: - 0 8px 20px rgba(0, 0, 0, 0.75), - 0 2px 5px rgba(0, 0, 0, 0.5); -} - -.sketched-wax-seal:hover { - transform: translate(-50%, -50%) rotate(0deg) scale(1.1); - box-shadow: - 0 12px 26px rgba(0, 0, 0, 0.85), - 0 0 16px rgba(218, 165, 32, 0.5); -} - -.seal-crest-img { - width: 100%; - height: 100%; - border-radius: 50%; - object-fit: cover; - display: block; - border: 2.5px solid #4a0d0d; - box-shadow: inset 0 0 10px rgba(0, 0, 0, 0.7); -} - -.seal-emboss-ring { - position: absolute; - inset: 2px; - border-radius: 50%; - border: 1.5px solid rgba(255, 215, 0, 0.25); - box-shadow: inset 0 2px 4px rgba(255, 255, 255, 0.2), inset 0 -3px 6px rgba(0, 0, 0, 0.6); - pointer-events: none; -} - -.seal-glow { - position: absolute; - inset: -6px; - border-radius: 50%; - background: radial-gradient(circle, rgba(255, 215, 0, 0.35) 0%, transparent 70%); - opacity: 0; - transition: opacity 0.3s ease; - pointer-events: none; -} - -.sketched-wax-seal:hover .seal-glow { - opacity: 1; -} - -/* Inner Letter Sheet (Clean, No Distracting Text - "Den Text lassen wir erstmal weg") */ -.env-letter-sheet { - width: calc(100% - 2.5rem); - left: 1.25rem; - position: absolute; - height: 68%; - top: 46%; /* Tucked safely inside pocket when closed */ - background-color: #f7f0de; - background-image: - radial-gradient(ellipse at 50% 30%, rgba(255, 255, 255, 0.7) 0%, rgba(140, 100, 50, 0.15) 100%), + radial-gradient(ellipse at 50% 25%, rgba(255, 255, 255, 0.6) 0%, rgba(140, 100, 50, 0.15) 100%), url('/static/img/parchment_texture.jpg'); background-size: cover; + background-position: center; border-radius: 5px; - border: 1px solid #8e6c43; + border: 1.5px solid #8e6c43; outline: 1px dashed rgba(130, 95, 55, 0.4); outline-offset: -5px; - z-index: 3; /* Behind bottom pocket (z-index: 4), in front of interior back (z-index: 1) */ - transition: transform 0.7s cubic-bezier(0.2, 0.85, 0.25, 1) 0.15s, box-shadow 0.6s ease; - transform: translateY(0); + padding: 16px 20px; + box-shadow: 0 4px 12px rgba(0, 0, 0, 0.35); + z-index: 3; + /* Closed state: tucked completely inside the pocket, hidden */ + visibility: hidden; + opacity: 0; + transform: translateY(40px) scale(0.92); + pointer-events: none; + transition: transform 0.85s cubic-bezier(0.2, 0.85, 0.25, 1) 0.3s, + opacity 0.5s ease 0.3s, + visibility 0.5s ease 0.3s, + box-shadow 0.8s ease; display: flex; flex-direction: column; align-items: center; justify-content: center; - padding: 16px 20px; text-align: center; - box-shadow: 0 4px 12px rgba(0, 0, 0, 0.3); +} + +.envelope-opened .letter-sheet { + visibility: visible; + opacity: 1; + pointer-events: auto; + transform: translateY(-145px) scale(1.02); + z-index: 10; + box-shadow: + 0 24px 60px rgba(0, 0, 0, 0.85), + 0 0 35px rgba(201, 168, 106, 0.4); } .letter-crest-small { @@ -535,38 +400,192 @@ body { color: #ffffff; } -/* ========================================= - OPENED STATE (via .envelope-opened class OR hover) - ========================================= */ - -.envelope-opened .env-top, -.envelope-form:hover .env-top { - transform: rotateX(-180deg); - z-index: 2; - transition-delay: 0s; +/* Top V-Flap (Folds Down from Top Edge to Apex at 54%) */ +.env-top-flap { + position: absolute; + top: 0; + left: 0; + width: 100%; + height: 100%; + z-index: 18; + transform-origin: top center; + transform-style: preserve-3d; + clip-path: polygon(50% 54%, 0 0, 100% 0); + background-color: #ebd8ae; + background-image: + radial-gradient(ellipse at 50% 20%, rgba(255, 255, 255, 0.35) 0%, rgba(130, 95, 45, 0.25) 100%), + url('/static/img/parchment_texture.jpg'); + background-size: cover; + border-top: 2px solid #7c5830; + filter: drop-shadow(0 8px 14px rgba(35, 18, 5, 0.65)); + transition: transform 0.8s cubic-bezier(0.4, 0, 0.2, 1), z-index 0s 0.35s; } -.envelope-opened .sketched-wax-seal { - opacity: 0; - transform: translate(-50%, -50%) scale(0.3) rotate(25deg); +.envelope-opened .env-top-flap { + transform: rotateX(180deg); + z-index: 2; + filter: drop-shadow(0 -4px 6px rgba(50, 35, 10, 0.4)); +} + +.env-top-sketch-line { + position: absolute; + top: 3px; + left: 3%; + width: 94%; + height: 94%; + clip-path: polygon(50% 51%, 2% 2%, 98% 2%); + border-top: 1.5px dashed rgba(110, 75, 35, 0.45); pointer-events: none; } -.envelope-form:hover .sketched-wax-seal { - opacity: 0.2; - transform: translate(-50%, -50%) scale(0.85); +/* CodePen Envelope Pocket (Meeting at Exact Center 50% 50%) */ +.envelope-pocket { + position: absolute; + inset: 0; + z-index: 14; + pointer-events: none; + border-radius: 6px; + overflow: hidden; + border-bottom: 2px solid #7c5830; + border-left: 2px solid #7c5830; + border-right: 2px solid #7c5830; } -.envelope-opened .env-letter-sheet, -.envelope-form:hover .env-letter-sheet { - transform: translateY(-56%); - box-shadow: 0 18px 40px rgba(0, 0, 0, 0.8), 0 0 25px rgba(218, 165, 32, 0.35); +.envelope-pocket-flaps { + position: absolute; + inset: 0; + /* CodePen Bottom Flap Geometry */ + clip-path: polygon(50% 50%, 100% 0, 100% 100%, 0 100%, 0 0); + background-color: #e5cf9f; + background-image: + radial-gradient(ellipse at 50% 80%, rgba(255, 255, 255, 0.25) 0%, rgba(120, 85, 40, 0.25) 100%), + url('/static/img/parchment_texture.jpg'); + background-size: cover; + filter: drop-shadow(0px -4px 6px rgba(30, 15, 5, 0.3)); +} + +/* CodePen Left Side Flap */ +.envelope-pocket-flaps:before { + content: ''; + position: absolute; + left: 0; + width: 50%; + height: 100%; + clip-path: polygon(100% 50%, 0 0, 0 100%); + background-color: #dfc794; + background-image: + linear-gradient(135deg, rgba(0, 0, 0, 0.12) 0%, rgba(255, 255, 255, 0.15) 100%), + url('/static/img/parchment_texture.jpg'); + background-size: cover; + box-shadow: inset -2px 0 6px rgba(60, 40, 15, 0.2); +} + +/* CodePen Right Side Flap */ +.envelope-pocket-flaps:after { + content: ''; + position: absolute; + right: 0; + width: 50%; + height: 100%; + clip-path: polygon(0 50%, 100% 0, 100% 100%); + background-color: #dbc38f; + background-image: + linear-gradient(-135deg, rgba(0, 0, 0, 0.12) 0%, rgba(255, 255, 255, 0.15) 100%), + url('/static/img/parchment_texture.jpg'); + background-size: cover; + box-shadow: inset 2px 0 6px rgba(60, 40, 15, 0.2); +} + +/* Small Handwriting Return Address in Top-Left ("Abs.: Hogwarts...") */ +.env-sender-line { + position: absolute; + top: 12px; + left: 14px; + font-family: 'Caveat', 'Marck Script', cursive; + font-size: clamp(0.76rem, 2.1vw, 0.88rem); + color: #0d3820; /* Authentic Hogwarts Emerald Ink */ + font-weight: 600; + z-index: 16; + pointer-events: none; + letter-spacing: 0.2px; + text-shadow: 0 0 1px rgba(13, 56, 32, 0.25); + transition: opacity 0.4s ease; + white-space: nowrap; } .envelope-opened .env-sender-line { opacity: 0; } +/* Hand-Sketched Hogwarts Wax Seal in the Exact Mitte (Center 50% 50%) */ +.sketched-wax-seal { + position: absolute; + top: 50%; /* Center of envelope */ + left: 50%; + transform: translate(-50%, -50%) rotate(-3deg); + width: 72px; + height: 72px; + border-radius: 50%; + cursor: pointer; + z-index: 20; + transition: transform 0.3s cubic-bezier(0.34, 1.56, 0.64, 1), box-shadow 0.3s ease, opacity 0.4s ease; + box-shadow: + 0 8px 22px rgba(0, 0, 0, 0.75), + 0 2px 6px rgba(0, 0, 0, 0.45); +} + +.sketched-wax-seal:hover { + transform: translate(-50%, -50%) rotate(0deg) scale(1.1); + box-shadow: + 0 12px 28px rgba(0, 0, 0, 0.8), + 0 0 16px rgba(218, 165, 32, 0.45); +} + +.seal-crest-img { + width: 100%; + height: 100%; + border-radius: 50%; + object-fit: cover; + display: block; + border: 2.5px solid #4a0d0d; + box-shadow: inset 0 0 10px rgba(0, 0, 0, 0.7); +} + +.seal-emboss-ring { + position: absolute; + inset: 2px; + border-radius: 50%; + border: 1.5px solid rgba(255, 215, 0, 0.25); + box-shadow: inset 0 2px 4px rgba(255, 255, 255, 0.2), inset 0 -3px 6px rgba(0, 0, 0, 0.6); + pointer-events: none; +} + +.seal-glow { + position: absolute; + inset: -6px; + border-radius: 50%; + background: radial-gradient(circle, rgba(255, 215, 0, 0.35) 0%, transparent 70%); + opacity: 0; + transition: opacity 0.3s ease; + pointer-events: none; +} + +.sketched-wax-seal:hover .seal-glow { + opacity: 1; +} + +/* Seal Break Golden Animation */ +.envelope-opened .sketched-wax-seal { + animation: breakSealAnim 0.7s forwards; + pointer-events: none; +} + +@keyframes breakSealAnim { + 0% { transform: translate(-50%, -50%) rotate(-3deg) scale(1); opacity: 1; filter: none; } + 50% { transform: translate(-50%, -50%) rotate(10deg) scale(1.2); opacity: 0.8; filter: drop-shadow(0 0 25px #ffd700); } + 100% { transform: translate(-50%, -50%) rotate(25deg) scale(0.3); opacity: 0; filter: drop-shadow(0 0 40px #ffd700); } +} + /* Controls Below Parchment */ .intro-controls-panel { margin-top: 20px; @@ -662,33 +681,45 @@ body { } @media (max-width: 480px) { - .envelope-outer-wrap { - max-width: 360px; - margin: 10px auto 20px; + .antique-envelope-scene { + width: min(360px, 94vw); + height: min(210px, 58vw); + margin: 15px auto 25px; + } + .antique-envelope-scene.envelope-opened, + .antique-envelope-scene:has(.envelope-opened) { + margin-top: 115px; + margin-bottom: 20px; + } + .envelope-opened .letter-sheet { + transform: translateY(-110px) scale(1.02); + height: 310px; + padding: 12px 14px; } .sketched-wax-seal { - width: 58px; - height: 58px; + width: 56px; + height: 56px; } .env-sender-line { font-size: 0.72rem; left: 10px; + top: 8px; } .letter-crest-small { - width: 40px; - height: 40px; - margin-bottom: 6px; + width: 38px; + height: 38px; + margin-bottom: 5px; } .letter-title { - font-size: 0.96rem; + font-size: 0.94rem; } .letter-subtitle { - font-size: 0.76rem; + font-size: 0.74rem; margin-bottom: 10px; } .btn-launch-express { - padding: 7px 14px; - font-size: 0.76rem; + padding: 7px 13px; + font-size: 0.75rem; } .btn-launch-quiz { padding: 12px 18px; diff --git a/app/static/js/quiz.js b/app/static/js/quiz.js index 7591ce8..19b663a 100755 --- a/app/static/js/quiz.js +++ b/app/static/js/quiz.js @@ -251,10 +251,12 @@ function saveRecentQuestions(ids) { function breakSealAndOpenLetter() { const envelope = document.getElementById("envelope"); + const scene = document.getElementById("envelopeScene"); if (!envelope || envelope.classList.contains("envelope-opened")) return; playSound('magic'); envelope.classList.add("envelope-opened"); + if (scene) scene.classList.add("envelope-opened"); // Start background music if enabled or first click const bgm = document.getElementById("bgm"); @@ -289,9 +291,11 @@ function breakSealAndOpenLetter() { function closeLetter() { const envelope = document.getElementById("envelope"); + const scene = document.getElementById("envelopeScene"); if (!envelope) return; envelope.classList.remove("envelope-opened"); + if (scene) scene.classList.remove("envelope-opened"); const breakSealBtn = document.getElementById("breakSealBtn"); const startBtn = document.getElementById("startBtn"); diff --git a/app/templates/base.html b/app/templates/base.html index 51e333c..d2359b4 100755 --- a/app/templates/base.html +++ b/app/templates/base.html @@ -8,7 +8,7 @@ - + {% block head %}{% endblock %} diff --git a/app/templates/index.html b/app/templates/index.html index 016bb2b..ffbc7db 100755 --- a/app/templates/index.html +++ b/app/templates/index.html @@ -12,44 +12,42 @@
- -
-
-
+ +
+
+ +
- -
+ +
+ Hogwarts-Wappen +

Hogwarts-Schule

+

für Hexerei und Zauberei

+ +
- -
- Hogwarts-Wappen -

Hogwarts-Schule

-

für Hexerei und Zauberei

- -
+ +
+
+
- -
+ +
+
+
- -
-
-
- - -
- Abs.: Hogwarts Schule für Hexerei und Zauberei -
- - -
- Hogwarts-Wappen Siegel -
-
-
+ +
+ Abs.: Hogwarts Schule für Hexerei und Zauberei +
+ +
+ Hogwarts-Wappen Siegel +
+
@@ -158,5 +156,5 @@ {% endblock %} {% block scripts %} - + {% endblock %}