Add comprehensive easter egg system with mobile optimization
Implement 6 interactive easter eggs: - "He Comes" mode (type "he comes" or "zalgo") - 404 Text Not Found (type "404") - Matrix red/blue pill modes - Developer credits (type "credits" or click title 10x) - Witching Hour (3:33 AM automatic activation) - Mobile shake detection with haptic feedback Fix easter egg trigger logic to prevent normal generation override. Add complete documentation of all easter eggs in README. 🤖 Generated with [Claude Code](https://claude.ai/code) Co-Authored-By: Claude <noreply@anthropic.com>
This commit is contained in:
parent
76da597a12
commit
41198a55ec
3 changed files with 335 additions and 3 deletions
34
README.md
34
README.md
|
|
@ -123,6 +123,40 @@ Each mode strategically applies different combinations for unique effects.
|
||||||
- ✅ Edge 88+
|
- ✅ Edge 88+
|
||||||
- ✅ Mobile browsers (iOS Safari, Chrome Mobile)
|
- ✅ Mobile browsers (iOS Safari, Chrome Mobile)
|
||||||
|
|
||||||
|
## 🥚 Hidden Easter Eggs
|
||||||
|
|
||||||
|
GlitchCraft contains several hidden easter eggs for the curious:
|
||||||
|
|
||||||
|
### 🌩️ "He Comes" Mode
|
||||||
|
- **Trigger**: Type `he comes` or `zalgo`
|
||||||
|
- **Effect**: Auto-switches to Heavy Corruption with max intensity + red flash
|
||||||
|
- **Reference**: Original zalgo creepypasta
|
||||||
|
|
||||||
|
### 🔍 404 Text Not Found
|
||||||
|
- **Trigger**: Type `404`
|
||||||
|
- **Effect**: Shows "T̷̢̧e̴̢̧x̷̰t̸̨̧ ̷̢̧n̴̢̧o̷̰t̸̨̧ ̷̢̧f̴̢̧o̷̰ų̸̧n̷̢̧d̴̢̧"
|
||||||
|
- **Bonus**: Copy notification says "Error copied successfully!"
|
||||||
|
|
||||||
|
### 💊 Matrix Mode
|
||||||
|
- **Red Pill**: Type `red pill` → Heavy corruption + red tint + "Welcome to the real world"
|
||||||
|
- **Blue Pill**: Type `blue pill` → Calm mode + blue tint + "You chose... wisely"
|
||||||
|
- **Reference**: The Matrix (1999)
|
||||||
|
|
||||||
|
### 👨💻 Developer Credits
|
||||||
|
- **Trigger**: Type `credits` OR click the title 10 times rapidly
|
||||||
|
- **Effect**: Shows corrupted developer credits
|
||||||
|
|
||||||
|
### 🌙 Witching Hour (3:33 AM)
|
||||||
|
- **Trigger**: Use the app at exactly 3:33 AM (any timezone)
|
||||||
|
- **Effect**: Dark theme + screen shake + subtitle becomes "T̷̢̧h̴̢̧ḛ̷ ̸̨̧w̷̢̧i̴̢̧t̷̰c̸̨̧h̷̢̧i̴̢̧n̷̰g̸̨̧ ̷̢̧h̴̢̧o̷̰ų̸̧r̷̢̧"
|
||||||
|
- **Duration**: Lasts for 1 minute
|
||||||
|
|
||||||
|
### 📱 Mobile Shake
|
||||||
|
- **Trigger**: Shake your phone/device
|
||||||
|
- **Effect**: Random corruption mode + intensity + haptic feedback
|
||||||
|
- **Message**: "S̷̢̧h̴̢̧a̷̰k̸̨̧e̷̢̧n̴̢̧,̷̰ ̸̨̧n̷̢̧o̴̢̧t̷̰ ̸̨̧s̷̢̧t̴̢̧ḭ̷r̸̨̧r̷̢̧e̴̢̧d̷̰"
|
||||||
|
- **Note**: Requires device motion permissions on iOS
|
||||||
|
|
||||||
## 🎨 Examples
|
## 🎨 Examples
|
||||||
|
|
||||||
Here are some z̴̳̈a̸̭̾l̵̰̔g̶̱̈ó̴̬ ̷̲̎t̸̰̄e̶̮̾x̷̲̄ẗ̴̰ examples:
|
Here are some z̴̳̈a̸̭̾l̵̰̔g̶̱̈ó̴̬ ̷̲̎t̸̰̄e̶̮̾x̷̲̄ẗ̴̰ examples:
|
||||||
|
|
|
||||||
290
app/app.js
290
app/app.js
|
|
@ -17,13 +17,33 @@ const zalgoModeSelect = document.getElementById('zalgoMode');
|
||||||
const clearBtn = document.getElementById('clearBtn');
|
const clearBtn = document.getElementById('clearBtn');
|
||||||
const copyNotification = document.getElementById('copyNotification');
|
const copyNotification = document.getElementById('copyNotification');
|
||||||
|
|
||||||
|
// Easter egg state
|
||||||
|
let titleClickCount = 0;
|
||||||
|
let titleClickTimer = null;
|
||||||
|
let isWitchingHour = false;
|
||||||
|
let lastShakeTime = 0;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Update the corrupted text output
|
* Update the corrupted text output
|
||||||
*/
|
*/
|
||||||
function updateOutput() {
|
function updateOutput() {
|
||||||
const text = inputText.value;
|
const text = inputText.value;
|
||||||
const intensity = parseInt(intensitySlider.value);
|
let intensity = parseInt(intensitySlider.value);
|
||||||
const mode = zalgoModeSelect.value;
|
let mode = zalgoModeSelect.value;
|
||||||
|
|
||||||
|
// Easter egg checks
|
||||||
|
const easterEggTriggered = checkEasterEggs(text);
|
||||||
|
|
||||||
|
// If easter egg was triggered, don't do normal generation
|
||||||
|
if (easterEggTriggered) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Apply witching hour effect
|
||||||
|
if (isWitchingHour) {
|
||||||
|
intensity = Math.max(intensity, 8);
|
||||||
|
mode = 'heavy';
|
||||||
|
}
|
||||||
|
|
||||||
if (text) {
|
if (text) {
|
||||||
outputText.value = zalgo.generate(text, intensity, mode);
|
outputText.value = zalgo.generate(text, intensity, mode);
|
||||||
|
|
@ -32,6 +52,44 @@ function updateOutput() {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Check for easter eggs in the input text
|
||||||
|
*/
|
||||||
|
function checkEasterEggs(text) {
|
||||||
|
const lowerText = text.toLowerCase().trim();
|
||||||
|
|
||||||
|
// "He Comes" Mode
|
||||||
|
if (lowerText === 'he comes' || lowerText === 'zalgo') {
|
||||||
|
triggerHeComes();
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
// 404 Text Not Found
|
||||||
|
if (lowerText === '404') {
|
||||||
|
trigger404();
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Matrix Mode
|
||||||
|
if (lowerText === 'red pill') {
|
||||||
|
triggerMatrixRed();
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (lowerText === 'blue pill') {
|
||||||
|
triggerMatrixBlue();
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Credits
|
||||||
|
if (lowerText === 'credits') {
|
||||||
|
triggerCredits();
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Copy text to clipboard and show notification
|
* Copy text to clipboard and show notification
|
||||||
*/
|
*/
|
||||||
|
|
@ -68,6 +126,186 @@ function clearAll() {
|
||||||
inputText.focus();
|
inputText.focus();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Easter Egg Functions
|
||||||
|
*/
|
||||||
|
|
||||||
|
// "He Comes" Mode
|
||||||
|
function triggerHeComes() {
|
||||||
|
zalgoModeSelect.value = 'heavy';
|
||||||
|
intensitySlider.value = 10;
|
||||||
|
intensityValue.textContent = '10';
|
||||||
|
|
||||||
|
// Flash effect
|
||||||
|
document.body.style.backgroundColor = '#330000';
|
||||||
|
setTimeout(() => {
|
||||||
|
document.body.style.backgroundColor = '';
|
||||||
|
}, 200);
|
||||||
|
|
||||||
|
// Update output after mode change
|
||||||
|
setTimeout(() => {
|
||||||
|
outputText.value = zalgo.generate(inputText.value, 10, 'heavy');
|
||||||
|
}, 100);
|
||||||
|
}
|
||||||
|
|
||||||
|
// 404 Text Not Found
|
||||||
|
function trigger404() {
|
||||||
|
outputText.value = 'T̷̢̧e̴̢̧x̷̰t̸̨̧ ̷̢̧n̴̢̧o̷̰t̸̨̧ ̷̢̧f̴̢̧o̷̰ų̸̧n̷̢̧d̴̢̧';
|
||||||
|
|
||||||
|
// Override copy notification
|
||||||
|
window.tempCopyFunction = async function () {
|
||||||
|
await navigator.clipboard.writeText(outputText.value);
|
||||||
|
copyNotification.textContent = 'Error copied successfully!';
|
||||||
|
copyNotification.classList.add('show');
|
||||||
|
setTimeout(() => {
|
||||||
|
copyNotification.classList.remove('show');
|
||||||
|
copyNotification.textContent = 'Copied!';
|
||||||
|
}, 3000);
|
||||||
|
};
|
||||||
|
|
||||||
|
// Restore original after 10 seconds
|
||||||
|
setTimeout(() => {
|
||||||
|
window.tempCopyFunction = null;
|
||||||
|
}, 10000);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Matrix Red Pill
|
||||||
|
function triggerMatrixRed() {
|
||||||
|
zalgoModeSelect.value = 'heavy';
|
||||||
|
intensitySlider.value = 9;
|
||||||
|
intensityValue.textContent = '9';
|
||||||
|
|
||||||
|
// Red tint effect
|
||||||
|
document.documentElement.style.filter = 'hue-rotate(0deg) saturate(150%) brightness(90%)';
|
||||||
|
document.documentElement.style.background =
|
||||||
|
'linear-gradient(rgba(255,0,0,0.1), rgba(255,0,0,0.05))';
|
||||||
|
|
||||||
|
outputText.value = zalgo.generate('Welcome to the real world', 9, 'heavy');
|
||||||
|
|
||||||
|
// Clear effect after 5 seconds
|
||||||
|
setTimeout(() => {
|
||||||
|
document.documentElement.style.filter = '';
|
||||||
|
document.documentElement.style.background = '';
|
||||||
|
}, 5000);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Matrix Blue Pill
|
||||||
|
function triggerMatrixBlue() {
|
||||||
|
zalgoModeSelect.value = 'mini';
|
||||||
|
intensitySlider.value = 1;
|
||||||
|
intensityValue.textContent = '1';
|
||||||
|
|
||||||
|
// Blue calm effect
|
||||||
|
document.documentElement.style.filter = 'hue-rotate(240deg) saturate(120%) brightness(110%)';
|
||||||
|
|
||||||
|
outputText.value = 'You chose... wisely';
|
||||||
|
|
||||||
|
setTimeout(() => {
|
||||||
|
document.documentElement.style.filter = '';
|
||||||
|
outputText.value = zalgo.generate('Back to the ordinary world', 1, 'mini');
|
||||||
|
}, 3000);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Developer Credits
|
||||||
|
function triggerCredits() {
|
||||||
|
const credits = 'Made with ❤️ and chaos by Ole-Morten Duesund';
|
||||||
|
outputText.value = zalgo.generate(credits, 7, 'full');
|
||||||
|
}
|
||||||
|
|
||||||
|
// Title Click Counter for Credits
|
||||||
|
function handleTitleClick() {
|
||||||
|
titleClickCount++;
|
||||||
|
|
||||||
|
if (titleClickTimer) {
|
||||||
|
clearTimeout(titleClickTimer);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (titleClickCount >= 10) {
|
||||||
|
triggerCredits();
|
||||||
|
titleClickCount = 0;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Reset counter after 3 seconds
|
||||||
|
titleClickTimer = setTimeout(() => {
|
||||||
|
titleClickCount = 0;
|
||||||
|
}, 3000);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Witching Hour Check (3:33 AM)
|
||||||
|
function checkWitchingHour() {
|
||||||
|
const now = new Date();
|
||||||
|
const hour = now.getHours();
|
||||||
|
const minute = now.getMinutes();
|
||||||
|
|
||||||
|
const isCurrentlyWitchingHour = hour === 3 && minute === 33;
|
||||||
|
|
||||||
|
if (isCurrentlyWitchingHour && !isWitchingHour) {
|
||||||
|
isWitchingHour = true;
|
||||||
|
|
||||||
|
// Dark theme effect
|
||||||
|
document.documentElement.style.filter = 'brightness(70%) contrast(120%)';
|
||||||
|
document.body.style.animation = 'subtle-shake 0.1s infinite';
|
||||||
|
|
||||||
|
// Show message
|
||||||
|
const originalSubtitle = document.querySelector('.subtitle').textContent;
|
||||||
|
document.querySelector('.subtitle').textContent = 'T̷̢̧h̴̢̧ḛ̷ ̸̨̧w̷̢̧i̴̢̧t̷̰c̸̨̧h̷̢̧i̴̢̧n̷̰g̸̨̧ ̷̢̧h̴̢̧o̷̰ų̸̧r̷̢̧';
|
||||||
|
|
||||||
|
// Restore after 1 minute
|
||||||
|
setTimeout(() => {
|
||||||
|
isWitchingHour = false;
|
||||||
|
document.documentElement.style.filter = '';
|
||||||
|
document.body.style.animation = '';
|
||||||
|
document.querySelector('.subtitle').textContent = originalSubtitle;
|
||||||
|
}, 60000);
|
||||||
|
} else if (!isCurrentlyWitchingHour && isWitchingHour) {
|
||||||
|
isWitchingHour = false;
|
||||||
|
document.documentElement.style.filter = '';
|
||||||
|
document.body.style.animation = '';
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Mobile Shake Detection
|
||||||
|
function handleDeviceMotion(event) {
|
||||||
|
const acceleration = event.accelerationIncludingGravity;
|
||||||
|
|
||||||
|
if (!acceleration) return;
|
||||||
|
|
||||||
|
// Throttle shake detection to prevent spam
|
||||||
|
const now = Date.now();
|
||||||
|
if (now - lastShakeTime < 1000) return;
|
||||||
|
|
||||||
|
const shake = Math.abs(acceleration.x) + Math.abs(acceleration.y) + Math.abs(acceleration.z);
|
||||||
|
|
||||||
|
if (shake > 30) {
|
||||||
|
lastShakeTime = now;
|
||||||
|
// Random mode and intensity
|
||||||
|
const modes = ['full', 'above', 'below', 'middle', 'mini', 'heavy'];
|
||||||
|
const randomMode = modes[Math.floor(Math.random() * modes.length)];
|
||||||
|
const randomIntensity = Math.floor(Math.random() * 10) + 1;
|
||||||
|
|
||||||
|
zalgoModeSelect.value = randomMode;
|
||||||
|
intensitySlider.value = randomIntensity;
|
||||||
|
intensityValue.textContent = randomIntensity;
|
||||||
|
|
||||||
|
// Haptic feedback if available
|
||||||
|
if (navigator.vibrate) {
|
||||||
|
navigator.vibrate(100);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Visual feedback
|
||||||
|
copyNotification.textContent = 'S̷̢̧h̴̢̧a̷̰k̸̨̧e̷̢̧n̴̢̧,̷̰ ̸̨̧n̷̢̧o̴̢̧t̷̰ ̸̨̧s̷̢̧t̴̢̧ḭ̷r̸̨̧r̷̢̧e̴̢̧d̷̰';
|
||||||
|
copyNotification.classList.add('show');
|
||||||
|
|
||||||
|
setTimeout(() => {
|
||||||
|
copyNotification.classList.remove('show');
|
||||||
|
copyNotification.textContent = 'Copied!';
|
||||||
|
}, 2000);
|
||||||
|
|
||||||
|
updateOutput();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// Event listeners
|
// Event listeners
|
||||||
inputText.addEventListener('input', updateOutput);
|
inputText.addEventListener('input', updateOutput);
|
||||||
|
|
||||||
|
|
@ -78,7 +316,14 @@ intensitySlider.addEventListener('input', () => {
|
||||||
|
|
||||||
zalgoModeSelect.addEventListener('change', updateOutput);
|
zalgoModeSelect.addEventListener('change', updateOutput);
|
||||||
|
|
||||||
outputText.addEventListener('click', copyToClipboard);
|
outputText.addEventListener('click', () => {
|
||||||
|
// Check for custom copy function (404 easter egg)
|
||||||
|
if (window.tempCopyFunction) {
|
||||||
|
window.tempCopyFunction();
|
||||||
|
} else {
|
||||||
|
copyToClipboard();
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
clearBtn.addEventListener('click', clearAll);
|
clearBtn.addEventListener('click', clearAll);
|
||||||
|
|
||||||
|
|
@ -123,4 +368,43 @@ window.addEventListener('beforeinstallprompt', e => {
|
||||||
// Focus input on load
|
// Focus input on load
|
||||||
window.addEventListener('load', () => {
|
window.addEventListener('load', () => {
|
||||||
inputText.focus();
|
inputText.focus();
|
||||||
|
|
||||||
|
// Set up easter egg event listeners
|
||||||
|
setupEasterEggs();
|
||||||
});
|
});
|
||||||
|
|
||||||
|
// Easter Egg Setup
|
||||||
|
function setupEasterEggs() {
|
||||||
|
// Title click for credits
|
||||||
|
const title = document.querySelector('h1');
|
||||||
|
title.addEventListener('click', handleTitleClick);
|
||||||
|
title.style.cursor = 'pointer';
|
||||||
|
|
||||||
|
// Witching hour check every minute
|
||||||
|
setInterval(checkWitchingHour, 60000);
|
||||||
|
checkWitchingHour(); // Initial check
|
||||||
|
|
||||||
|
// Mobile shake detection
|
||||||
|
if (window.DeviceMotionEvent) {
|
||||||
|
window.addEventListener('devicemotion', handleDeviceMotion);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Request device motion permission on iOS 13+
|
||||||
|
if (typeof DeviceMotionEvent.requestPermission === 'function') {
|
||||||
|
// We'll request permission on first user interaction
|
||||||
|
document.addEventListener('touchstart', requestMotionPermission, { once: true });
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Request motion permission for iOS
|
||||||
|
function requestMotionPermission() {
|
||||||
|
if (typeof DeviceMotionEvent.requestPermission === 'function') {
|
||||||
|
DeviceMotionEvent.requestPermission()
|
||||||
|
.then(permissionState => {
|
||||||
|
if (permissionState === 'granted') {
|
||||||
|
window.addEventListener('devicemotion', handleDeviceMotion);
|
||||||
|
}
|
||||||
|
})
|
||||||
|
.catch(console.error);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
|
||||||
|
|
@ -461,6 +461,20 @@ footer p {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* Shake animation for witching hour */
|
||||||
|
@keyframes subtle-shake {
|
||||||
|
0%,
|
||||||
|
100% {
|
||||||
|
transform: translateX(0);
|
||||||
|
}
|
||||||
|
25% {
|
||||||
|
transform: translateX(-1px);
|
||||||
|
}
|
||||||
|
75% {
|
||||||
|
transform: translateX(1px);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/* Print styles */
|
/* Print styles */
|
||||||
@media print {
|
@media print {
|
||||||
body {
|
body {
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue