
2020
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Aenean diam dolor, accumsan sed rutrum vel, dapibus et leo.

2022
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Aenean diam dolor, accumsan sed rutrum vel, dapibus et leo.

2024
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Aenean diam dolor, accumsan sed rutrum vel, dapibus et leo.

2026
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Aenean diam dolor, accumsan sed rutrum vel, dapibus et leo.
Place the below code in your header script area this delete this block.
<script>/* Scroll-drawn timeline */
(function () {
var DRAW_POINT = 0.6; // the tip of the line follows a spot 60% down the screen
var timelines = [];
var ticking = false;
var reduce = window.matchMedia('(prefers-reduced-motion: reduce)').matches;
function build(wrap) {
var items = Array.prototype.slice.call(wrap.querySelectorAll('.cc-tl-item'));
if (items.length < 2) return null;
var line = document.createElement('div');
line.className = 'cc-tl-line';
line.setAttribute('aria-hidden', 'true');
var fill = document.createElement('div');
fill.className = 'cc-tl-fill';
line.appendChild(fill);
wrap.appendChild(line);
var dots = items.map(function (item) {
var dot = document.createElement('span');
dot.className = 'cc-tl-dot';
dot.setAttribute('aria-hidden', 'true');
item.appendChild(dot);
return dot;
});
wrap.classList.add('cc-tl-ready');
return { wrap: wrap, items: items, dots: dots, line: line, fill: fill, top: 0, height: 0, dotYs: [] };
}
// Size and place the line from the first dot's center to the last dot's center
function measure(t) {
var w = t.wrap.getBoundingClientRect();
var first = t.dots[0].getBoundingClientRect();
var last = t.dots[t.dots.length - 1].getBoundingClientRect();
var centerX = first.left + first.width / 2 - w.left;
t.top = first.top + first.height / 2 - w.top;
t.height = last.top + last.height / 2 - w.top - t.top;
t.line.style.left = centerX - t.line.offsetWidth / 2 + 'px';
t.line.style.top = t.top + 'px';
t.line.style.height = t.height + 'px';
t.dotYs = t.dots.map(function (d) {
var r = d.getBoundingClientRect();
return r.top + r.height / 2 - w.top;
});
}
function update(t) {
var w = t.wrap.getBoundingClientRect();
var drawY = window.innerHeight * DRAW_POINT - w.top; // draw point inside the timeline
var p = reduce ? 1 : Math.min(1, Math.max(0, (drawY - t.top) / t.height));
t.fill.style.transform = 'scaleY(' + p.toFixed(4) + ')';
t.items.forEach(function (item, i) {
item.classList.toggle('is-active', reduce || drawY >= t.dotYs[i] - 2);
});
}
function updateAll() {
timelines.forEach(update);
ticking = false;
}
function measureAll() {
timelines.forEach(measure);
updateAll();
}
function onScroll() {
if (!ticking) {
ticking = true;
requestAnimationFrame(updateAll);
}
}
function init() {
document.querySelectorAll('.cc-timeline').forEach(function (wrap) {
var t = build(wrap);
if (t) timelines.push(t);
});
if (!timelines.length) return;
measureAll(); // correct state right away on load
window.addEventListener('scroll', onScroll, { passive: true });
window.addEventListener('resize', measureAll);
window.addEventListener('load', measureAll); // re-measure after images and fonts settle
if ('ResizeObserver' in window) {
var ro = new ResizeObserver(measureAll);
timelines.forEach(function (t) { ro.observe(t.wrap); });
}
}
if (document.readyState === 'loading') {
document.addEventListener('DOMContentLoaded', init);
} else {
init();
}
})();</script>