4 changed files with 166 additions and 95 deletions
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
@ -1,124 +1,191 @@ |
|||
$z-main: 20000; |
|||
$z-scanline: 10000; |
|||
$z-3: 30000; |
|||
|
|||
.crt-screen { |
|||
.crt-fallout { |
|||
position: relative; |
|||
background: #001100; /* Тёмно-зелёный фон */ |
|||
color: #00ff00; /* Ярко-зелёный текст */ |
|||
overflow: hidden; |
|||
background: #000 !important; |
|||
color: #0F0 !important; |
|||
image-rendering: pixelated; |
|||
image-rendering: crisp-edges; |
|||
} |
|||
|
|||
.crt-screen::before { |
|||
content: " "; |
|||
display: block; |
|||
/* 16-битная палитра с ограниченными цветами */ |
|||
.crt-fallout::before { |
|||
content: ""; |
|||
position: absolute; |
|||
top: 0; |
|||
left: 0; |
|||
bottom: 0; |
|||
right: 0; |
|||
background: linear-gradient( |
|||
rgba(18, 16, 16, 0) 50%, |
|||
rgba(0, 0, 0, 0.25) 50% |
|||
); |
|||
background-size: 100% 12px; |
|||
z-index: $z-main; |
|||
width: 100%; |
|||
height: 100%; |
|||
background: |
|||
repeating-linear-gradient( |
|||
0deg, |
|||
rgba(0, 32, 0, 0.8) 0px, |
|||
rgba(0, 32, 0, 0.8) 1px, |
|||
transparent 1px, |
|||
transparent 2px |
|||
), |
|||
repeating-linear-gradient( |
|||
90deg, |
|||
rgba(0, 16, 0, 0.4) 0px, |
|||
rgba(0, 16, 0, 0.4) 1px, |
|||
transparent 1px, |
|||
transparent 2px |
|||
); |
|||
pointer-events: none; |
|||
z-index: $z-scanline; |
|||
} |
|||
|
|||
.crt-screen::after { |
|||
content: " "; |
|||
display: block; |
|||
/* Полосы развёртки (оптимизированные под 24 FPS) */ |
|||
.crt-fallout::after { |
|||
content: ""; |
|||
position: absolute; |
|||
top: 0; |
|||
left: 0; |
|||
bottom: 0; |
|||
right: 0; |
|||
background: rgba(0, 255, 0, 0.05); |
|||
opacity: 0.1; |
|||
width: 100%; |
|||
height: 100%; |
|||
background: linear-gradient( |
|||
rgba(0, 255, 0, 0.06) 50%, |
|||
transparent 50% |
|||
); |
|||
background-size: 100% 3px; |
|||
z-index: $z-main; |
|||
pointer-events: none; |
|||
animation: flicker 0.15s infinite; |
|||
animation: scanlines 0.666s linear infinite; |
|||
/* 1 / 24 FPS * 16 кадров = 0.666s */ |
|||
} |
|||
|
|||
/* Эффект виньетирования */ |
|||
.crt-screen { |
|||
box-shadow: |
|||
inset 0 0 60px rgba(0, 255, 0, 0.1), |
|||
inset 0 0 100px rgba(0, 20, 0, 0.8), |
|||
inset 0 0 150px rgba(0, 10, 0, 0.9); |
|||
/* 16-битное свечение текста */ |
|||
.crt-fallout .text { |
|||
color: #0F0; |
|||
text-shadow: |
|||
0 0 2px #0F0, |
|||
0 0 4px #0C0, |
|||
0 0 6px #090; |
|||
font-smooth: never; |
|||
-webkit-font-smoothing: none; |
|||
} |
|||
|
|||
/* Эффект сканирования */ |
|||
.scanline { |
|||
width: 100%; |
|||
height: 100px; |
|||
background: linear-gradient( |
|||
0deg, |
|||
rgba(0, 255, 0, 0) 0%, |
|||
rgba(0, 255, 0, 0.1) 50%, |
|||
rgba(0, 255, 0, 0) 100% |
|||
); |
|||
position: absolute; |
|||
animation: scan 32s linear infinite; |
|||
z-index: $z-scanline; |
|||
pointer-events: none; |
|||
/* 16-битный фильтр для изображений */ |
|||
.crt-fallout img, |
|||
.crt-fallout video, |
|||
.crt-fallout canvas { |
|||
filter: |
|||
brightness(0.7) |
|||
contrast(1.3) |
|||
hue-rotate(90deg) |
|||
saturate(0.6) |
|||
url('#crtFilter'); |
|||
} |
|||
|
|||
/* Свечение для текста */ |
|||
.crt-text { |
|||
text-shadow: |
|||
0 0 5px #00ff00, |
|||
0 0 10px #00ff00, |
|||
0 0 15px #00ff00; |
|||
/* SVG фильтр для 16-битного эффекта */ |
|||
.filter-svg { |
|||
position: absolute; |
|||
width: 0; |
|||
height: 0; |
|||
} |
|||
|
|||
/* Эффект мерцания */ |
|||
@keyframes flicker { |
|||
0% { opacity: 0.1; } |
|||
5% { opacity: 0.1; } |
|||
10% { opacity: 0.2; } |
|||
15% { opacity: 0.1; } |
|||
20% { opacity: 0.3; } |
|||
25% { opacity: 0.1; } |
|||
30% { opacity: 0.2; } |
|||
35% { opacity: 0.1; } |
|||
40% { opacity: 0.25; } |
|||
45% { opacity: 0.1; } |
|||
50% { opacity: 0.15; } |
|||
55% { opacity: 0.1; } |
|||
60% { opacity: 0.2; } |
|||
65% { opacity: 0.1; } |
|||
70% { opacity: 0.3; } |
|||
75% { opacity: 0.1; } |
|||
80% { opacity: 0.25; } |
|||
85% { opacity: 0.1; } |
|||
90% { opacity: 0.2; } |
|||
95% { opacity: 0.1; } |
|||
100% { opacity: 0.15; } |
|||
/* Статический шум с пониженной частотой */ |
|||
.noise-layer { |
|||
position: absolute; |
|||
top: 0; |
|||
left: 0; |
|||
width: 100%; |
|||
height: 100%; |
|||
background-image: |
|||
url("data:image/svg+xml,%3Csvg viewBox='0 0 256 256' xmlns='http://www.w3.org/2000/svg'%3E%3Cfilter id='noise'%3E%3CfeTurbulence type='fractalNoise' baseFrequency='0.65' numOctaves='1' stitchTiles='stitch'/%3E%3CfeColorMatrix type='matrix' values='0 0 0 0 0 0 1 0 0 0 0 0 0 0 0 0 0 0 0.08 0'/%3E%3C/filter%3E%3Crect width='256' height='256' filter='url(%23noise)' opacity='0.15'/%3E%3C/svg%3E"); |
|||
background-repeat: repeat; |
|||
opacity: 0.1; |
|||
animation: noise 2s steps(24) infinite; |
|||
z-index: $z-3; |
|||
pointer-events: none; |
|||
} |
|||
|
|||
/* Движение сканирующей линии */ |
|||
@keyframes scan { |
|||
/* Анимации, синхронизированные с 24 FPS */ |
|||
@keyframes scanlines { |
|||
0% { |
|||
top: -100px; |
|||
transform: translateY(0px); |
|||
} |
|||
100% { |
|||
top: 100%; |
|||
transform: translateY(3px); |
|||
} |
|||
} |
|||
|
|||
/* Дополнительные эффекты для контента */ |
|||
.crt-screen img, |
|||
.crt-screen video { |
|||
filter: |
|||
contrast(1.2) |
|||
brightness(0.8) |
|||
hue-rotate(90deg) |
|||
saturate(0.5); |
|||
@keyframes flicker { |
|||
0%, 100% { opacity: 0.97; } |
|||
4.166% { opacity: 0.95; } /* 1/24 кадра */ |
|||
8.333% { opacity: 0.93; } /* 2/24 кадра */ |
|||
12.5% { opacity: 0.95; } /* 3/24 кадра */ |
|||
16.666% { opacity: 0.97; } /* 4/24 кадра */ |
|||
20.833% { opacity: 0.94; } /* 5/24 кадра */ |
|||
25% { opacity: 0.96; } /* 6/24 кадра */ |
|||
29.166% { opacity: 0.95; } /* 7/24 кадра */ |
|||
33.333% { opacity: 0.97; } /* 8/24 кадра */ |
|||
37.5% { opacity: 0.93; } /* 9/24 кадра */ |
|||
41.666% { opacity: 0.96; } /* 10/24 кадра */ |
|||
45.833% { opacity: 0.95; } /* 11/24 кадра */ |
|||
50% { opacity: 0.97; } /* 12/24 кадра */ |
|||
54.166% { opacity: 0.94; } /* 13/24 кадра */ |
|||
58.333% { opacity: 0.96; } /* 14/24 кадра */ |
|||
62.5% { opacity: 0.95; } /* 15/24 кадра */ |
|||
66.666% { opacity: 0.97; } /* 16/24 кадра */ |
|||
70.833% { opacity: 0.93; } /* 17/24 кадра */ |
|||
75% { opacity: 0.95; } /* 18/24 кадра */ |
|||
79.166% { opacity: 0.96; } /* 19/24 кадра */ |
|||
83.333% { opacity: 0.94; } /* 20/24 кадра */ |
|||
87.5% { opacity: 0.97; } /* 21/24 кадра */ |
|||
91.666% { opacity: 0.95; } /* 22/24 кадра */ |
|||
95.833% { opacity: 0.96; } /* 23/24 кадра */ |
|||
} |
|||
|
|||
@keyframes noise { |
|||
0% { background-position: 0 0; } |
|||
100% { background-position: 256px 256px; } |
|||
} |
|||
|
|||
/* Эффект низкого FPS и ограниченной палитры */ |
|||
.fps-24 { |
|||
animation-duration: 0.041666s; /* 24 FPS */ |
|||
animation-timing-function: steps(1, end); |
|||
} |
|||
|
|||
/* Пиксельный эффект для 16-битной графики */ |
|||
.pixel-grid { |
|||
position: absolute; |
|||
top: 0; |
|||
left: 0; |
|||
width: 100%; |
|||
height: 100%; |
|||
background-image: |
|||
linear-gradient(rgba(0, 16, 0, 0.1) 1px, transparent 1px), |
|||
linear-gradient(90deg, rgba(0, 16, 0, 0.1) 1px, transparent 1px); |
|||
background-size: 4px 4px; |
|||
pointer-events: none; |
|||
z-index: $z-scanline; |
|||
} |
|||
|
|||
/* Упрощённый эффект виньетирования для 16-бит */ |
|||
.vignette-16bit { |
|||
position: absolute; |
|||
top: 0; |
|||
left: 0; |
|||
width: 100%; |
|||
height: 100%; |
|||
box-shadow: |
|||
inset 0 0 40px #000, |
|||
inset 0 0 60px rgba(0, 32, 0, 0.5), |
|||
inset 0 0 80px #000; |
|||
pointer-events: none; |
|||
z-index: $z-main; |
|||
} |
|||
|
|||
/* Мерцание (оптимизированное под 24 FPS) */ |
|||
.crt-fallout { |
|||
animation: flicker 1s infinite; |
|||
} |
|||
|
|||
/* Эффект кривизны экрана (опционально) */ |
|||
.crt-curve { |
|||
transform: perspective(500px) rotateX(2deg); |
|||
transform-origin: center top; |
|||
/* Оптимизация производительности */ |
|||
.crt-fallout * { |
|||
will-change: transform, opacity; |
|||
backface-visibility: hidden; |
|||
} |
|||
|
|||
Loading…
Reference in new issue