A continuation of ch07-compression.html. The complete source identity, every recorded occurrence, and linked equations are on its first page.
Source transcript · continued
Download complete source text ↓1,579 lines · 42.3 KB
const y = (i / numNodes) * 100;
const phase = (i / numNodes) * Math.PI * 4;
// Left node
const leftNode = document.createElement('div');
leftNode.className = 'helix-node left';
leftNode.style.top = y + '%';
leftNode.style.transform = `translateX(${Math.sin(phase) * 80 - 50}px)`;
helixStrand.appendChild(leftNode);
// Right node
const rightNode = document.createElement('div');
rightNode.className = 'helix-node right';
rightNode.style.top = y + '%';
rightNode.style.transform = `translateX(${-Math.sin(phase) * 80 + 50}px)`;
helixStrand.appendChild(rightNode);
// Connector
const connector = document.createElement('div');
connector.className = 'helix-connector';
connector.style.top = y + '%';
connector.style.width = Math.abs(Math.sin(phase)) * 160 + 'px';
helixStrand.appendChild(connector);
}
// Animate DNA helix
let helixPhase = 0;
function animateHelix() {
helixPhase += 0.02;
const nodes = helixStrand.querySelectorAll('.helix-node');
const connectors = helixStrand.querySelectorAll('.helix-connector');
for (let i = 0; i < numNodes; i++) {
const phase = (i / numNodes) * Math.PI * 4 + helixPhase;
const leftNode = nodes[i * 2];
const rightNode = nodes[i * 2 + 1];
const connector = connectors[i];
if (leftNode && rightNode) {
leftNode.style.transform = `translateX(${Math.sin(phase) * 80 - 50}px)`;
rightNode.style.transform = `translateX(${-Math.sin(phase) * 80 + 50}px)`;
connector.style.width = Math.abs(Math.sin(phase)) * 160 + 'px';
}
}
requestAnimationFrame(animateHelix);
}
animateHelix();
// Size bars animation
const sizeBars = document.querySelectorAll('.size-bar-fill');
const byteSizes = [8, 8, 1, 1, 4, 4, 8];
ScrollTrigger.create({
trigger: '.structure-card',
start: 'top 70%',
onEnter: () => {
sizeBars.forEach((bar, i) => {
setTimeout(() => {
bar.style.width = (byteSizes[i] / 8 * 100) + '%';
}, i * 150);
});
},
once: true
});
// Smooth scroll
document.querySelectorAll('a[href^="#"]').forEach(anchor => {
anchor.addEventListener('click', function(e) {
e.preventDefault();
document.querySelector(this.getAttribute('href')).scrollIntoView({
behavior: 'smooth'
});
});
});
</script>
</body>
</html>