🦴 Description
A playful 404 Error Page designed using pure CSS animations. This project features two cavemen characters facing each other, swinging clubs endlessly, creating a humorous and eye‑catching error screen.
🤔 Why This 404 Page?
Most 404 pages are boring and forgettable. This one:
- Keeps users engaged even on error pages
- Shows off advanced CSS skills
- Works without JavaScript animations
- Perfect for portfolios and fun projects
🧱 Project Structure
index.html→ Markup for cavemen charactersstyle.css→ All shapes, colors, and animations
🧩 Complete Code
1<!DOCTYPE html>
2<html lang="en">
3
4 <head>
5 <meta charset="UTF-8">
6 <title>code for fun (day02): 404 error page, Caveman mode - pure CSS</title>
7 <link href="https://fonts.googleapis.com/css?family=Concert+One" rel="stylesheet"><link rel="stylesheet" href="./style.css">
8
9 </head>
10
11 <body>
12 <div class="text"><p>404</p></div>
13<div class="container">
14 <!-- caveman left -->
15 <div class="caveman">
16 <div class="leg">
17 <div class="foot"><div class="fingers"></div></div>
18 </div>
19 <div class="leg">
20 <div class="foot"><div class="fingers"></div></div>
21 </div>
22 <div class="shape">
23 <div class="circle"></div>
24 <div class="circle"></div>
25 </div>
26 <div class="head">
27 <div class="eye"><div class="nose"></div></div>
28 <div class="mouth"></div>
29 </div>
30 <div class="arm-right"><div class="club"></div></div>
31 </div>
32 <!-- caveman right -->
33 <div class="caveman">
34 <div class="leg">
35 <div class="foot"><div class="fingers"></div></div>
36 </div>
37 <div class="leg">
38 <div class="foot"><div class="fingers"></div></div>
39 </div>
40 <div class="shape">
41 <div class="circle"></div>
42 <div class="circle"></div>
43 </div>
44 <div class="head">
45 <div class="eye"><div class="nose"></div></div>
46 <div class="mouth"></div>
47 </div>
48 <div class="arm-right"><div class="club"></div></div>
49 </div>
50</div>
51
52
53 </body>
54
55</html>
56
🧠 Explanation of the Code
🧱 HTML Structure
- Two identical
.cavemanblocks - Each caveman built from divs (head, arm, legs, club)
- No images or SVGs used
🎨 CSS Shapes & Styling
- Rounded divs create body parts
- Pseudo‑elements used for details (eyes, fingers, shadows)
- Different color palettes to distinguish characters
🎥 Animations
🪓 Arm Rotation
- Continuous 360° rotation using
@keyframes arm-anima - Offset delays for alternating motion
👀 Eye Blink
- Eye height animated to simulate blinking
🗿 Head Bounce
- Head moves down briefly during swing
🌑 Ground Shadow
- Expands and contracts for depth illusion
📱 Responsive Behavior
- Centered using
transform: translate(-50%, -50%) - Scales well on different screen sizes
🚀 Use Cases
- Custom 404 page for websites
- CSS animation showcase
- Fun portfolio project
- Blog or tutorial content
💡 Pro Tips
- Add text like “Page Not Found” below
- Replace colors for dark mode
- Convert to SVG or React component
CSS Code
1body { 2 background-color: #FF7F2E; 3 font-family: "Concert One", cursive; 4 margin: 0; 5 overflow: hidden; 6 padding: 0; 7} 8 9/*/////////////////// rules */ 10/*/////////////////// scene */ 11.text { 12 left: 50%; 13 position: absolute; 14 top: 50%; 15 transform: translate(-50%, -50%); 16 color: rgba(19, 31, 36, 0.183); 17 font-size: 30em; 18 text-align: center; 19 top: 40%; 20} 21 22.container { 23 left: 50%; 24 position: absolute; 25 top: 50%; 26 transform: translate(-50%, -50%); 27 height: 300px; 28 width: 500px; 29} 30.container:after { 31 position: absolute; 32 content: ""; 33 background-color: rgba(19, 36, 44, 0.1); 34 border-radius: 12px; 35 bottom: 40px; 36 height: 12px; 37 left: 80px; 38 width: 350px; 39 z-index: -1; 40} 41 42/*/////////////////// caveman */ 43.caveman { 44 height: 300px; 45 position: absolute; 46 width: 250px; 47} 48 49.caveman:nth-child(1) { 50 right: 20px; 51} 52 53.caveman:nth-child(2) { 54 left: 20px; 55 transform: rotateY(180deg); 56} 57 58.head { 59 position: absolute; 60 background-color: #13242C; 61 border-radius: 50px; 62 height: 140px; 63 left: 60px; 64 top: 25px; 65 width: 65px; 66} 67.head:after, .head:before { 68 content: ""; 69 position: absolute; 70 background-color: #13242C; 71 border-radius: 10px; 72 height: 20px; 73 width: 7px; 74} 75.head:after { 76 left: 35px; 77 top: -8px; 78 transform: rotate(20deg); 79} 80.head:before { 81 left: 30px; 82 top: -8px; 83 transform: rotate(-20deg); 84} 85.head .eye { 86 left: 50%; 87 position: absolute; 88 transform: translateX(-50%); 89 background-color: #EAB08C; 90 border-radius: 50px; 91 height: 16px; 92 left: 45%; 93 top: 40px; 94 width: 48px; 95} 96.head .eye:after, .head .eye:before { 97 content: ""; 98 position: absolute; 99 top: 50%; 100 transform: translateY(-50%); 101 background-color: #13242C; 102 border-radius: 50%; 103 height: 5px; 104 width: 5px; 105} 106.head .eye:after { 107 left: 5px; 108} 109.head .eye:before { 110 right: 9px; 111} 112.head .eye .nose { 113 left: 50%; 114 position: absolute; 115 top: 50%; 116 transform: translate(-50%, -50%); 117 background-color: #D9766C; 118 border-left: 8px solid rgba(19, 36, 44, 0.1); 119 border-radius: 10px; 120 box-sizing: border-box; 121 height: 35px; 122 left: 45%; 123 top: 12px; 124 width: 15px; 125} 126 127.shape { 128 left: 50%; 129 position: absolute; 130 transform: translateX(-50%); 131 border-radius: 50%; 132 height: 140px; 133 overflow: hidden; 134 top: 70px; 135 width: 140px; 136} 137.shape .circle { 138 position: absolute; 139 border-radius: 50%; 140 height: 60px; 141 width: 60px; 142} 143.shape .circle:after, .shape .circle:before { 144 content: ""; 145 position: absolute; 146 border-radius: 50%; 147 height: 20px; 148 width: 20px; 149} 150.shape .circle:after { 151 left: 50px; 152 top: 10px; 153} 154.shape .circle:before { 155 left: 60px; 156 top: 45px; 157} 158.shape .circle:nth-child(1) { 159 left: -12px; 160 top: 80px; 161} 162.shape .circle:nth-child(2) { 163 right: 10px; 164 top: 0px; 165 transform: rotate(90deg); 166} 167.shape .circle:nth-child(2):after { 168 left: 65px; 169 top: 10px; 170} 171.shape .circle:nth-child(2):before { 172 display: none; 173} 174 175.caveman:nth-child(1) .shape { 176 background-color: #D13433; 177} 178.caveman:nth-child(1) .shape .circle { 179 background-color: #932422; 180} 181.caveman:nth-child(1) .shape .circle:after, .caveman:nth-child(1) .shape .circle:before { 182 background-color: #932422; 183} 184 185.caveman:nth-child(2) .shape { 186 background-color: #932422; 187} 188.caveman:nth-child(2) .shape .circle { 189 background-color: #D13433; 190} 191.caveman:nth-child(2) .shape .circle:after, .caveman:nth-child(2) .shape .circle:before { 192 background-color: #D13433; 193} 194 195.arm-right { 196 position: absolute; 197 background-color: #EAB08C; 198 border-left: 8px solid rgba(19, 36, 44, 0.1); 199 border-radius: 50px; 200 box-sizing: border-box; 201 height: 180px; 202 left: 135px; 203 top: 80px; 204 transform-origin: 30px 30px; 205 width: 60px; 206 z-index: 1; 207} 208.arm-right .club { 209 position: absolute; 210 border-bottom: 110px solid #601513; 211 border-left: 10px solid transparent; 212 border-right: 10px solid transparent; 213 height: 0; 214 left: -60px; 215 top: 120px; 216 transform: rotate(70deg); 217 width: 20px; 218} 219.arm-right .club:after, .arm-right .club:before { 220 position: absolute; 221 content: ""; 222 background-color: #601513; 223 border-radius: 50%; 224 left: 0; 225} 226.arm-right .club:after { 227 height: 20px; 228 width: 20px; 229 top: -10px; 230} 231.arm-right .club:before { 232 height: 40px; 233 width: 40px; 234 left: -10px; 235 top: 90px; 236} 237 238.leg { 239 position: absolute; 240 border-radius: 10px; 241 height: 55px; 242 top: 200px; 243 width: 10px; 244} 245.leg:after { 246 position: absolute; 247 content: ""; 248 border-radius: 50%; 249 height: 10px; 250 left: -5px; 251 top: 15px; 252 width: 10px; 253} 254.leg .foot { 255 position: absolute; 256 border-radius: 25px 25px 0 0; 257 height: 25px; 258 left: -38px; 259 top: 30px; 260 width: 50px; 261} 262.leg .foot:after, .leg .foot:before, .leg .foot .fingers, .leg .foot .fingers:after { 263 position: absolute; 264 background-color: #EAB08C; 265 border-radius: 50%; 266 bottom: 0px; 267 height: 15px; 268 transform-origin: bottom; 269 width: 15px; 270} 271.leg .foot:after { 272 left: -6px; 273 content: ""; 274} 275.leg .foot:before { 276 left: 8px; 277 transform: scale(0.6); 278 content: ""; 279} 280.leg .foot .fingers { 281 left: 15px; 282 transform: scale(0.6); 283} 284.leg .foot .fingers:after { 285 left: 11px; 286 content: ""; 287} 288 289.leg:nth-child(1) { 290 background-color: #B2524D; 291 left: 95px; 292} 293.leg:nth-child(1):after { 294 background-color: #B2524D; 295} 296.leg:nth-child(1) .foot { 297 background-color: #B2524D; 298} 299.leg:nth-child(1) .foot:after { 300 background-color: #B2524D; 301} 302.leg:nth-child(1) .foot:before { 303 display: none; 304} 305 306.leg:nth-child(2) { 307 background-color: #D9766C; 308 left: 115px; 309} 310.leg:nth-child(2):after { 311 background-color: #D9766C; 312} 313.leg:nth-child(2) .foot { 314 background-color: #D9766C; 315} 316 317/*/////////////////// animation */ 318.caveman:nth-child(1) .arm-right { 319 animation: arm-anima 1.2s infinite cubic-bezier(0.55, 0.01, 0.16, 1.34); 320} 321 322.caveman:nth-child(2) .arm-right { 323 animation: arm-anima 1.2s infinite cubic-bezier(0.55, 0.01, 0.16, 1.34); 324 animation-delay: 0.6s; 325} 326 327@keyframes arm-anima { 328 0% { 329 transform: rotate(0); 330 } 331 100% { 332 transform: rotate(-360deg); 333 } 334} 335.caveman:nth-child(2) .head { 336 animation: head-anima 1.2s infinite cubic-bezier(0.55, 0.01, 0.16, 1.34); 337} 338 339.caveman:nth-child(1) .head { 340 animation: head-anima 1.2s infinite cubic-bezier(0.55, 0.01, 0.16, 1.34); 341 animation-delay: 0.6s; 342} 343 344@keyframes head-anima { 345 0% { 346 top: 25px; 347 } 348 42% { 349 top: 25px; 350 } 351 45% { 352 top: 50px; 353 } 354 100% { 355 top: 25px; 356 } 357} 358.caveman:nth-child(2) .eye:after, 359.caveman:nth-child(2) .eye:before { 360 animation: eye-anima 1.2s infinite cubic-bezier(0.55, 0.01, 0.16, 1.34); 361} 362 363.caveman:nth-child(1) .eye:after, 364.caveman:nth-child(1) .eye:before { 365 animation: eye-anima 1.2s infinite cubic-bezier(0.55, 0.01, 0.16, 1.34); 366 animation-delay: 0.6s; 367} 368 369@keyframes eye-anima { 370 0% { 371 height: 5px; 372 } 373 42% { 374 height: 5px; 375 } 376 45% { 377 height: 1px; 378 } 379 100% { 380 height: 5px; 381 } 382} 383.container:after { 384 animation: shadow-anima 1.2s infinite cubic-bezier(0.55, 0.01, 0.16, 1.34); 385 animation-delay: 0.1s; 386} 387 388@keyframes shadow-anima { 389 0% { 390 width: 350px; 391 left: 80px; 392 } 393 25% { 394 width: 450px; 395 left: 80px; 396 } 397 50% { 398 width: 350px; 399 left: 80px; 400 } 401 75% { 402 width: 450px; 403 left: 0px; 404 } 405 100% { 406 width: 350px; 407 left: 80px; 408 } 409}
✨ Pure CSS proves that even error pages can have personality!
