HTML
<div class="price-stage">
<div class="price-card" id="price-card">
<div class="price-top">
<div class="price-symbol">BTC · USD</div>
<div class="price-live-dot">Live · 3s</div>
</div>
<div class="price-value" id="price-value">$67,420.58</div>
<div class="price-change">
<span class="price-delta price-up" id="price-delta">+$234.12</span>
<span class="price-delta price-up" id="price-pct">(+0.35%)</span>
<span class="price-arrow" id="price-arrow">▲</span>
</div>
<svg class="price-sparkline" viewBox="0 0 200 36" preserveAspectRatio="none" aria-hidden="true">
<defs>
<linearGradient id="price-spark-grad" x1="0" y1="0" x2="0" y2="1">
<stop offset="0%" stop-color="#0cce6b" stop-opacity="0.3"/>
<stop offset="100%" stop-color="#0cce6b" stop-opacity="0"/>
</linearGradient>
</defs>
<path id="price-spark-area" fill="url(#price-spark-grad)" opacity="0.6"/>
<polyline id="price-spark-line" class="price-sparkline-path" stroke="#0cce6b"/>
</svg>
<div class="price-footer">
<span id="price-updated">Updated just now</span>
<span>24h Vol $42.8B</span>
</div>
</div>
</div> CSS
.price-stage {
background: #0d1117;
padding: 48px 36px;
display: flex;
justify-content: center;
align-items: center;
min-height: 360px;
}
.price-card {
background: #161b22;
border: 1px solid #30363d;
border-radius: 8px;
padding: 22px 24px;
width: 100%;
max-width: 380px;
position: relative;
overflow: hidden;
font-family: ui-monospace, "JetBrains Mono", monospace;
}
.price-card.is-flash-up { animation: price-flash-up 0.65s ease-out; }
.price-card.is-flash-down { animation: price-flash-down 0.65s ease-out; }
@keyframes price-flash-up { 0% { background: rgba(12,206,107,0.2); } 100% { background: #161b22; } }
@keyframes price-flash-down { 0% { background: rgba(255,78,66,0.2); } 100% { background: #161b22; } }
@media (prefers-reduced-motion: reduce) {
.price-card.is-flash-up, .price-card.is-flash-down { animation: none; }
}
.price-top {
display: flex;
justify-content: space-between;
align-items: flex-start;
margin-bottom: 8px;
}
.price-symbol {
font-size: 11px;
letter-spacing: 0.18em;
color: #8b949e;
text-transform: uppercase;
}
.price-live-dot {
display: flex;
align-items: center;
gap: 6px;
font-family: system-ui, "Bricolage Grotesque", sans-serif;
font-size: 9px;
letter-spacing: 0.2em;
text-transform: uppercase;
color: #8b949e;
}
.price-live-dot::before {
content: '';
display: block;
width: 6px;
height: 6px;
border-radius: 50%;
background: #0cce6b;
box-shadow: 0 0 6px #0cce6b;
animation: price-pulse 2s infinite;
}
@keyframes price-pulse { 0%, 100% { opacity: 1; } 50% { opacity: 0.4; } }
.price-value {
font-size: 36px;
font-weight: 700;
color: #e6edf3;
letter-spacing: -0.02em;
margin-bottom: 6px;
line-height: 1;
}
.price-change {
display: flex;
align-items: center;
gap: 8px;
margin-bottom: 14px;
}
.price-delta {
font-size: 13px;
font-weight: 600;
}
.price-up { color: #0cce6b; }
.price-down { color: #ff4e42; }
.price-arrow { font-size: 12px; }
.price-sparkline { width: 100%; height: 36px; }
.price-sparkline-path {
fill: none;
stroke-width: 1.5;
stroke-linecap: round;
stroke-linejoin: round;
}
.price-footer {
display: flex;
justify-content: space-between;
margin-top: 10px;
padding-top: 10px;
border-top: 1px solid #21262d;
font-size: 9px;
letter-spacing: 0.1em;
color: #8b949e;
text-transform: uppercase;
} JS
// Live price ticker — random-walks BTC around $67k. Every 3s the
// price moves, the delta + sparkline update, and the background
// flashes green or red depending on direction.
(function () {
var price = 67420.58;
var openPrice = 67186.46;
var history = [];
for (var k = 0; k < 24; k++) {
history.push(67186 + Math.sin(k * 0.7) * 180 + k * 9.8 + Math.random() * 60);
}
history.push(price);
var card = document.getElementById('price-card');
var valEl = document.getElementById('price-value');
var deltaEl = document.getElementById('price-delta');
var pctEl = document.getElementById('price-pct');
var arrowEl = document.getElementById('price-arrow');
var lineEl = document.getElementById('price-spark-line');
var areaEl = document.getElementById('price-spark-area');
var updEl = document.getElementById('price-updated');
function fmt(n) {
return n.toLocaleString('en-US', { minimumFractionDigits: 2, maximumFractionDigits: 2 });
}
function redrawSpark() {
var W = 200, H = 36, pad = 2;
var min = Math.min.apply(null, history);
var max = Math.max.apply(null, history);
var range = max - min || 1;
var pts = history.map(function (v, i) {
var x = (i / (history.length - 1)) * (W - 2 * pad) + pad;
var y = H - pad - ((v - min) / range) * (H - 2 * pad);
return x.toFixed(1) + ',' + y.toFixed(1);
}).join(' ');
lineEl.setAttribute('points', pts);
var areaD = 'M ' + pad + ' ' + H + ' L ' + history.map(function (v, i) {
var x = (i / (history.length - 1)) * (W - 2 * pad) + pad;
var y = H - pad - ((v - min) / range) * (H - 2 * pad);
return x.toFixed(1) + ' ' + y.toFixed(1);
}).join(' L ') + ' L ' + (W - pad) + ' ' + H + ' Z';
areaEl.setAttribute('d', areaD);
}
function updatePrice() {
var prev = price;
price += (Math.random() - 0.47) * 110;
price = Math.max(64000, Math.min(72000, price));
history.push(price);
if (history.length > 24) history.shift();
var isUp = price >= prev;
var totalChange = price - openPrice;
var totalPct = (totalChange / openPrice) * 100;
valEl.textContent = '$' + fmt(price);
deltaEl.textContent = (totalChange >= 0 ? '+$' : '-$') + fmt(Math.abs(totalChange));
pctEl.textContent = '(' + (totalPct >= 0 ? '+' : '') + totalPct.toFixed(2) + '%)';
arrowEl.textContent = isUp ? '▲' : '▼';
arrowEl.style.color = isUp ? '#0cce6b' : '#ff4e42';
var cls = isUp ? 'price-up' : 'price-down';
deltaEl.className = 'price-delta ' + cls;
pctEl.className = 'price-delta ' + cls;
document.querySelectorAll('#price-spark-grad stop').forEach(function (s) {
s.setAttribute('stop-color', isUp ? '#0cce6b' : '#ff4e42');
});
lineEl.setAttribute('stroke', isUp ? '#0cce6b' : '#ff4e42');
card.classList.remove('is-flash-up', 'is-flash-down');
void card.offsetWidth;
card.classList.add(isUp ? 'is-flash-up' : 'is-flash-down');
updEl.textContent = 'Updated just now';
redrawSpark();
}
redrawSpark();
setInterval(updatePrice, 3000);
})();