CSS
content_copy コピー
html, body { height: 100%; margin: 0; }
body { display: grid; place-items: center; background: #111; }
/* 画面の箱(比を保ったまま、ウィンドウに収まる大きさにする) */
.ecv-stage {
--accent: #2563eb;
--ar: 16 / 9;
position: relative;
overflow: hidden;
aspect-ratio: var(--ar);
width: min(100vw, calc(100vh * (var(--ar))));
container-type: size;
background: #e4e7ec;
color: #1f2937;
font-family: system-ui, -apple-system, "Hiragino Sans", "Noto Sans JP", sans-serif;
}
:where(.ecv-stage p, .ecv-stage ol, .ecv-stage ul) { margin: 0; padding: 0; }
.ecv-stage li { list-style: none; }
/* カット:同じ場所に重ね、決まった時間だけ見せる(次のカットは前のカットが消えきる少し前から出し、何もない画面を挟まない) */
.ecv-scene {
position: absolute;
inset: 0;
display: flex;
flex-direction: column;
align-items: center;
justify-content: center;
gap: 4cqmin;
padding: 6cqmin;
box-sizing: border-box;
text-align: center;
opacity: 0;
}
/* 縦長の画面:上 10%・下 20% には SNS のボタンや投稿の文字が重なるので、中身を置かない */
@container (max-aspect-ratio: 3 / 4) {
.ecv-scene { padding: 12cqh 6cqmin 22cqh; }
}
/* 速さの変わり方は2種類:出るとき(--ease)と、カットの切り替え(ease) */
.ecv-stage { --ease: cubic-bezier(0.22, 1, 0.36, 1); }
@keyframes ecv-fade-in { from { opacity: 0; } to { opacity: 1; } }
@keyframes ecv-fade-out { from { opacity: 1; } to { opacity: 0; } }
@keyframes ecv-up { from { opacity: 0; transform: translateY(4cqmin); } to { opacity: 1; transform: none; } }
@keyframes ecv-pop { from { opacity: 0; transform: scale(0.6); } to { opacity: 1; transform: none; } }
/* 最後のカード:名前・値段・行き先の帯・小さな注記 */
.ecv-end { font-size: 7.5cqmin; font-weight: 900; white-space: nowrap; }
.ecv-price { font-size: 5.5cqmin; font-weight: 800; white-space: nowrap; }
.ecv-cta { padding: 2cqmin 4.5cqmin; background: var(--accent); color: #fff; font-size: 3.8cqmin; font-weight: 700; white-space: nowrap; }
.ecv-pnote { font-size: 2.8cqmin; color: #6b7280; white-space: nowrap; }
/* 全体の長さ(16秒)。最後のカードを止めて見せる時間も含む */
.ecv-stage { animation: ecv-clock 16s linear both; }
@keyframes ecv-clock { to { --ecv-t: 1; } }
/* 0.0〜2.4秒:色の数と商品の名前 */
.ecv-s0 { gap: 2cqmin; animation: ecv-fade-in 0.01s 0s both, ecv-fade-out 0.3s 2.15s forwards; }
.ecv-count { font-size: 4.4cqmin; font-weight: 800; color: var(--accent); letter-spacing: 0.1em; white-space: nowrap; animation: ecv-up 0.6s var(--ease) 0.05s both; }
.ecv-name { font-size: 8.5cqmin; font-weight: 900; white-space: nowrap; animation: ecv-up 0.6s var(--ease) 0.2s both; }
/* 商品の形:正方形の中を clip-path で切り抜く。色は1色ずつ重ねる */
.ecv-box { position: relative; width: 40cqmin; aspect-ratio: 1; flex: none; }
.ecv-layer { position: absolute; inset: 0; background: var(--c); }
.ecv-tee .ecv-layer { clip-path: polygon(30% 6%, 40% 6%, 50% 13%, 60% 6%, 70% 6%, 96% 24%, 86% 42%, 76% 36%, 76% 96%, 24% 96%, 24% 36%, 14% 42%, 4% 24%); }
.ecv-mug .ecv-layer { clip-path: polygon(evenodd, 14% 18%, 70% 18%, 70% 34%, 86% 34%, 92% 40%, 92% 62%, 86% 68%, 70% 68%, 70% 60%, 83% 60%, 85% 57%, 85% 45%, 83% 42%, 70% 42%, 70% 88%, 64% 92%, 20% 92%, 14% 88%); }
.ecv-bottle .ecv-layer { clip-path: polygon(40% 4%, 60% 4%, 60% 36%, 74% 40%, 80% 48%, 80% 92%, 20% 92%, 20% 48%, 26% 40%, 40% 36%); }
.ecv-bottle::after { content: ""; position: absolute; z-index: 1; left: 40%; right: 40%; top: 4%; height: 31%; background: #2b2b2b; }
/* 2.3〜12.4秒:1色ずつ切り替える。商品の色・色の名前・丸の輪を同じ瞬間に替える */
.ecv-s1 { gap: 3.5cqmin; animation: ecv-fade-in 0.3s 2.3s both, ecv-fade-out 0.3s 12.15s forwards; }
.ecv-s1 .ecv-box { animation: ecv-pop 0.6s var(--ease) 2.35s both; }
.ecv-l2 { animation: ecv-fade-in 0.35s ease 4.8s both; }
.ecv-l3 { animation: ecv-fade-in 0.35s ease 7.2s both; }
.ecv-l4 { animation: ecv-fade-in 0.35s ease 9.6s both; }
.ecv-names { display: grid; place-items: center; }
.ecv-cn { grid-area: 1 / 1; font-size: 6cqmin; font-weight: 900; white-space: nowrap; }
.ecv-k1 { animation: ecv-up 0.4s var(--ease) 2.5s both, ecv-fade-out 0.2s 4.7s forwards; }
.ecv-k2 { animation: ecv-up 0.4s var(--ease) 4.85s both, ecv-fade-out 0.2s 7.1s forwards; }
.ecv-k3 { animation: ecv-up 0.4s var(--ease) 7.25s both, ecv-fade-out 0.2s 9.5s forwards; }
.ecv-k4 { animation: ecv-up 0.4s var(--ease) 9.65s both; }
.ecv-dots { display: flex; gap: 4cqmin; }
.ecv-dots li { width: 6cqmin; height: 6cqmin; border-radius: 50%; background: var(--c); box-shadow: 0 0 0 0.4cqmin rgba(0, 0, 0, 0.1); }
@keyframes ecv-on { from { transform: none; box-shadow: 0 0 0 0.4cqmin rgba(0, 0, 0, 0.1); } to { transform: scale(1.15); box-shadow: 0 0 0 0.8cqmin #e4e7ec, 0 0 0 1.4cqmin #1f2937; } }
@keyframes ecv-off { from { transform: scale(1.15); box-shadow: 0 0 0 0.8cqmin #e4e7ec, 0 0 0 1.4cqmin #1f2937; } to { transform: none; box-shadow: 0 0 0 0.4cqmin rgba(0, 0, 0, 0.1); } }
.ecv-dots li:nth-child(1) { animation: ecv-on 0.25s ease 2.5s both, ecv-off 0.25s ease 4.8s forwards; }
.ecv-dots li:nth-child(2) { animation: ecv-on 0.25s ease 4.8s both, ecv-off 0.25s ease 7.2s forwards; }
.ecv-dots li:nth-child(3) { animation: ecv-on 0.25s ease 7.2s both, ecv-off 0.25s ease 9.6s forwards; }
.ecv-dots li:nth-child(4) { animation: ecv-on 0.25s ease 9.6s both; }
/* 12.2〜16.0秒:最後のカード(ここが最後の状態なので、最初から見える形で書く)。出そろってから2秒以上止める */
.ecv-s2 { opacity: 1; gap: 2.8cqmin; animation: ecv-fade-in 0.3s 12.2s both; }
.ecv-row { display: flex; gap: 2cqmin; }
.ecv-row .ecv-box { width: 14cqmin; animation: ecv-pop 0.45s var(--ease) both; }
.ecv-row .ecv-box:nth-child(1) { animation-delay: 12.25s; }
.ecv-row .ecv-box:nth-child(2) { animation-delay: 12.35s; }
.ecv-row .ecv-box:nth-child(3) { animation-delay: 12.45s; }
.ecv-row .ecv-box:nth-child(4) { animation-delay: 12.55s; }
.ecv-end { animation: ecv-up 0.6s var(--ease) 12.7s both; }
.ecv-price { animation: ecv-up 0.6s var(--ease) 12.85s both; }
.ecv-cta { animation: ecv-up 0.6s var(--ease) 13s both; }
.ecv-pnote { animation: ecv-up 0.6s var(--ease) 13.15s both; }
/* 動きを控える設定:動かさず、最後のカードだけを見せる */
@media (prefers-reduced-motion: reduce) {
.ecv-stage, .ecv-stage * { animation: none !important; }
}