Commit 90e35a3
Changed files (5)
007.FLAMES/index.html
@@ -0,0 +1,85 @@
+<!DOCTYPE html>
+<html lang="en">
+ <head>
+ <meta charset="UTF-8" />
+ <meta name="viewport" content="width=device-width, initial-scale=1.0" />
+ <title>007.FLAMES</title>
+ <link rel="stylesheet" href="./style.css" />
+ <link rel="stylesheet" href="../assets/common.css" />
+ <link rel="shortcut icon" href="../assets/favicon.png" type="image/png" />
+ <script src="../assets/common.js"></script>
+ </head>
+
+ <body data-disable-warning="true">
+ <!-- Modal Section -->
+ <input class="modal-state" id="modal" type="checkbox" />
+ <div class="modal">
+ <label class="modal__bg" for="modal"></label>
+ <div class="modal__inner" style="width: 30%">
+ <label class="modal__close" for="modal"></label>
+ <h2>007.FLAMES</h2>
+ <div class="modal__p">
+ <ul>
+ <li>
+ Five letters deciding your future. Because who needs
+ <span style="color: var(--lightGold)"> emotional stability? </span>
+ </li>
+ <li>
+ Just type two names, and let the
+ <span style="color: var(--lightGold)">mystical powers of math and childhood chaos</span> reveal
+ your relationship status.
+ </li>
+ <li>
+ Will you be Friends, Lovers, or sworn Enemies?
+ <span style="color: var(--lightGold)">FLAMES never lies*</span> (*except when it totally does).
+ </li>
+ </ul>
+ </div>
+ </div>
+ </div>
+
+ <!-- Main Content -->
+ <h1 id="flamesContainer">
+ <span class="flame-letter">F</span>
+ <span class="flame-letter">L</span>
+ <span class="flame-letter">A</span>
+ <span class="flame-letter">M</span>
+ <span class="flame-letter">E</span>
+ <span class="flame-letter">S</span>
+ </h1>
+ <p id="tooltip">Dare to play !!</p>
+ <div class="container">
+ <div class="group">
+ <label for="p1">P1:</label>
+ <input type="text" id="p1" name="p1" placeholder="Peter Parker" />
+ </div>
+ <div class="group">
+ <label for="p2">P2:</label>
+ <input type="text" id="p2" name="p2" placeholder="Gwen Stacy" />
+ </div>
+ <button id="calcBtn" class="calc">BRING IT ON!!</button>
+ <svg
+ class="hidden"
+ id="reload"
+ onclick="window.location.reload();clearName()"
+ style="margin-top: 25px; cursor: pointer"
+ fill="var(--lightGold)"
+ width="45px"
+ height="45px"
+ viewBox="0 0 24 24"
+ xmlns="http://www.w3.org/2000/svg"
+ >
+ <path
+ d="M19.146 4.854l-1.489 1.489A8 8 0 1 0 12 20a8.094 8.094 0 0 0 7.371-4.886 1 1 0 1 0-1.842-.779A6.071 6.071 0 0 1 12 18a6 6 0 1 1 4.243-10.243l-1.39 1.39a.5.5 0 0 0 .354.854H19.5A.5.5 0 0 0 20 9.5V5.207a.5.5 0 0 0-.854-.353z"
+ />
+ </svg>
+ </div>
+
+ <!-- Footer -->
+ <div class="footer">
+ <label for="modal">(i)</label>
+ <a class="arrow" href="../"></a>
+ </div>
+ </body>
+ <script src="./script.js"></script>
+</html>
007.FLAMES/script.js
@@ -0,0 +1,164 @@
+const ANIMATION_DELAY_MS = 250;
+const calcBtn = document.querySelector("#calcBtn");
+const tooltip = document.getElementById("tooltip");
+const reloadBtn = document.getElementById("reload");
+const p1Node = document.querySelector("#p1");
+const p2Node = document.querySelector("#p2");
+
+const QUOTES = {
+ F: [
+ "Oof! They friendzoned you faster than Wi-Fi connects.",
+ "You're giving off strong 'let's grab coffee... as friends' energy.",
+ "They said you're like a bruhhh... awkward.",
+ "Congrats! You're now the president of the Friendzone Association.",
+ "Even Cupid said, 'Nah, y'all better off as besties.'",
+ ],
+
+ L: [
+ "Look at you, catching feelings like it's a sport.",
+ "Someone's heart just got stolen — and it's definitely not theirs.",
+ "They're blushing. You're dangerous.",
+ "Cupid called. He wants to put you on speed dial.",
+ "If this was a K-drama, y'all just hit Episode 12: The Confession.",
+ ],
+
+ A: [
+ "They don't love you… but they definitely wouldn't swipe left.",
+ "You're not the one… but you're definitely the one before the one.",
+ "You're in their 'late night thoughts' playlist.",
+ "They flirt with you like it's their part-time job.",
+ "You're like that mystery snack they crave but won't admit to.",
+ ],
+
+ M: [
+ "Get the wedding playlist ready — it's happening!",
+ "You've unlocked the 'Eternal Drama Partner' level.",
+ "They're picturing you in matching pajamas already.",
+ "It's giving 'Netflix, kids, and a shared mortgage' vibes.",
+ "Hope you like joint bank accounts — you're headed for 'I Do'.",
+ ],
+
+ E: [
+ "Oof — they're plotting your downfall like it's a hobby.",
+ "They love to hate you. Emphasis on both.",
+ "You two have that enemies-to-lovers arc… just missing the lovers part.",
+ "They'd unplug your phone charger just out of spite.",
+ "It's less 'spark' and more 'burn.'",
+ ],
+
+ S: [
+ "You've unlocked the 'ew, that's like my sibling' zone.",
+ "They said you're like family… which is code for 'nope'.",
+ "Better start calling each other 'bro' — it's over.",
+ "You're so deep in the sibling zone, even ancestry.com is confused.",
+ "You're one DNA test away from this being weird.",
+ ],
+ SAME_NAME_QUOTES: [
+ "Dating yourself? Love the confidence, narcissist.",
+ "Well well well, someone clearly thinks they're their own soulmate.",
+ "You're so single, even your name is matching.",
+ "Mirror, mirror on the wall… you just fell for yourself after all.",
+ "Self-love is great, but this might be a *little* too literal.",
+ ],
+ ZERO_MAGIC_QUOTES: [
+ "Whoa. You broke the game. That's how rare your connection is.",
+ "There's no number for this vibe — you two are beyond calculation.",
+ "Some things can't be measured. Like how special you are.",
+ "Magic number? Nah, you *are* the magic.",
+ "When the universe glitches just for you — yeah, it's giving soulmate energy.",
+ ],
+};
+
+function clearName() {
+ p1Node.value = "";
+ p2Node.value = "";
+}
+
+async function playFlames(magicNumber) {
+ let FLAMES = ["F", "L", "A", "M", "E", "S"];
+ let current = 0;
+
+ let flamesContainer = Array.from(document.querySelectorAll(".flame-letter"));
+ while (FLAMES.length > 1) {
+ let count = 1;
+
+ while (count < magicNumber) {
+ flamesContainer[current].classList.add("highlight");
+ await sleep(ANIMATION_DELAY_MS);
+ flamesContainer[current].classList.remove("highlight");
+
+ current = (current + 1) % FLAMES.length;
+ count++;
+ }
+
+ flamesContainer[current].classList.add("highlight");
+ await sleep(ANIMATION_DELAY_MS);
+ flamesContainer[current].classList.remove("highlight");
+
+ console.log(`Removing "${FLAMES[current]}" at position ${current}`);
+ flamesContainer[current].classList.add("removed");
+
+ FLAMES.splice(current, 1);
+ flamesContainer.splice(current, 1);
+
+ if (current >= FLAMES.length) {
+ current = 0;
+ }
+
+ await sleep(ANIMATION_DELAY_MS);
+ }
+
+ flamesContainer[0].classList.add("highlight");
+ return FLAMES[0];
+}
+
+async function calculateFlames() {
+ const p1 = p1Node.value.toUpperCase().trim();
+ const p2 = p2Node.value.toUpperCase().trim();
+
+ if (p1 == "" || p2 == "") {
+ return;
+ }
+
+ calcBtn.disabled = true;
+ p1Node.disabled = true;
+ p2Node.disabled = true;
+ reloadBtn.classList.remove("hidden");
+
+ if (p1 == p2) {
+ tooltip.innerHTML = QUOTES["SAME_NAME_QUOTES"][Math.floor(Math.random() * 5)];
+ return;
+ }
+
+ let p1HashMap = {};
+ let p2HashMap = {};
+ let finalMap = {};
+ let magicNumber = 0;
+
+ for (let ch of p1) p1HashMap[ch] = (p1HashMap[ch] || 0) + 1;
+ for (let ch of p2) p2HashMap[ch] = (p2HashMap[ch] || 0) + 1;
+
+ let allKeys = new Set([...Object.keys(p1HashMap), ...Object.keys(p2HashMap)]);
+
+ for (let key of allKeys) {
+ const count1 = p1HashMap[key] || 0;
+ const count2 = p2HashMap[key] || 0;
+ finalMap[key] = Math.abs(count1 - count2);
+ }
+
+ for (let k in finalMap) {
+ magicNumber += finalMap[k];
+ }
+
+ if (magicNumber == 0) {
+ tooltip.innerHTML = QUOTES["ZERO_MAGIC_QUOTES"][Math.floor(Math.random() * 5)];
+ return;
+ }
+
+ const finalLetter = await playFlames(magicNumber);
+
+ let quote = QUOTES[finalLetter][Math.floor(Math.random() * 5)];
+ tooltip.innerHTML = quote;
+}
+
+calcBtn.onclick = calculateFlames;
007.FLAMES/style.css
@@ -0,0 +1,76 @@
+input,
+textarea,
+select {
+ font-size: 16px;
+}
+
+#tooltip {
+ color: var(--gold);
+ margin-top: 25px;
+ margin-bottom: 25px;
+ text-align: center;
+}
+
+.container {
+ display: flex;
+ flex-direction: column;
+ justify-content: center;
+ align-items: center;
+ position: relative;
+ height: fit-content;
+ z-index: 10;
+}
+
+.group {
+ display: flex;
+ flex-direction: row;
+ justify-content: space-between;
+ align-items: center;
+ width: 300px;
+ font-size: 20px;
+}
+
+.flame-letter {
+ display: inline-block;
+ padding: 3px 5px;
+ border-radius: 4px;
+ font-size: 1.7rem;
+ transition: all 0.3s;
+}
+
+.highlight {
+ background: var(--lightGold);
+ box-shadow: 0 0 0.5em var(--lightGold);
+ border-radius: 5px;
+ scale: 1.5;
+}
+
+.removed {
+ opacity: 50%;
+}
+
+.calc {
+ margin-top: 30px;
+ background: transparent;
+ border: 1px solid var(--lightGold);
+ border-radius: 5px;
+ padding: 10px 30px;
+ color: var(--gold);
+ cursor: pointer;
+}
+
+.calc:hover {
+ background: var(--lightGold);
+ color: white;
+}
+
+.calc:disabled {
+ opacity: 50%;
+ cursor: not-allowed;
+ background: transparent;
+ color: var(--gold);
+}
+
+.hidden {
+ display: none;
+}
assets/common.js
@@ -1,26 +1,30 @@
function getDeviceType() {
- const ua = navigator.userAgent;
+ const ua = navigator.userAgent;
- if (/mobile/i.test(ua)) {
- return "Mobile";
- } else if (/tablet/i.test(ua)) {
- return "Tablet";
- } else {
- return "Desktop";
- }
+ if (/mobile/i.test(ua)) {
+ return "Mobile";
+ } else if (/tablet/i.test(ua)) {
+ return "Tablet";
+ } else {
+ return "Desktop";
+ }
}
-if (getDeviceType() !== "Desktop") {
+document.addEventListener("DOMContentLoaded", () => {
+ if (getDeviceType() !== "Desktop") {
+ const disableWarning = document.body.getAttribute("data-disable-warning");
+ if (disableWarning === "true") return;
+
if (location.pathname !== "/") {
- location.href = "/";
+ location.href = "/";
}
-}
-
-document.addEventListener("DOMContentLoaded", () => {
- if (getDeviceType() !== "Desktop") {
- const warning = document.getElementById("warning");
- if (warning) {
- warning.checked = true;
- }
+ const warning = document.getElementById("warning");
+ if (warning) {
+ warning.checked = true;
}
-});
\ No newline at end of file
+ }
+});
+
+async function sleep(ms) {
+ return new Promise((resolve) => setTimeout(resolve, ms));
+}
index.html
@@ -34,7 +34,8 @@
<a href="./004.Maze-Runner/" class="opacity-75 hover:opacity-100 hover:text-yellow-400">004.Maze-Runner</a>
<a href="./005.MiniMax/" class="opacity-75 hover:opacity-100 hover:text-yellow-400">005.MiniMax</a>
<a href="./006.GamePad/" class="opacity-75 hover:opacity-100 hover:text-yellow-400">006.GamePad</a>
- </div>
+ <a href="./007.FLAMES/" class="opacity-75 hover:opacity-100 hover:text-yellow-400">007.FLAMES</a>
+ </div>
<!-- Footer -->
<div class="footer">