I was trying to achieve smooth and snappy scrolling while having anchor navigation at an HTML component. Only one "tab" should be visible at a time. The user would have to click in the tab name in order to change the current "tab".
The problem I am facing is that I can not have both features at the same time. If the scrolling is snappy, then the smooth animation is not carried out and vice versa.
I will also want to make that the user can drag the tab content in order to change the current tab, but this is for another question.
Code: (Uses tailwind, but it is not relevant)
<script src="https://cdn.tailwindcss.com/3.4.5"></script>
<html lang="en-GB">
<body>
<main>
<div class="flex flex-row gap-2 bg-red-500">
<a aria-label="Lorem ipsum" href="#lorem-ipsum">Lorem ipsum</a>
<a aria-label="Amet porttitor" href="#amet-porttitor">Amet porttitor</a>
<a aria-label="Blandit turpis" href="#blandit-turpis">Blandit turpis</a>
</div>
<div class="flex flex-row snap-x snap-mandatory overflow-x-auto overflow-y-auto max-h-[100vh]">
<div class="min-w-[100vw] min-h-[80vh] snap-start">
<p id="lorem-ipsum">
Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Suscipit adipiscing bibendum est ultricies integer quis.
</p>
</div>
<div class="min-w-[100vw] min-h-[80vh] snap-start">
<p id="amet-porttitor">
Amet porttitor eget dolor morbi. Ullamcorper eget nulla facilisi etiam dignissim diam quis enim. Cras tincidunt lobortis feugiat vivamus at. Eleifend donec pretium vulputate sapien
</p>
</div>
<div class="min-w-[100vw] min-h-[80vh] snap-start">
<p id="blandit-turpis">
Blandit turpis cursus in hac habitasse platea. Egestas tellus rutrum tellus pellentesque eu. In eu s augue neque gravida. Tristique nulla aliquet enim tortor at auctor. A
</p>
</div>
</div>
</main>
<style is:global>
html {
scroll-behavior: smooth;
}
@media (prefers-reduced-motion: reduce) {
html {
scroll-behavior: auto;
}
}
</style>
</body>
</html>
With a bit of JavaScript, it's possible:
document.querySelectorAll('main > div a').forEach(anchor => {
anchor.addEventListener('click', function(e) {
e.preventDefault(); // Prevent default anchor click behavior
const targetId = this.getAttribute('href').substring(1); // Get the target ID
const targetElement = document.getElementById(targetId);
if (targetElement) {
targetElement.scrollIntoView({
behavior: 'smooth',
block: 'start',
inline: 'nearest'
});
}
});
});
<script src="https://cdn.tailwindcss.com/3.4.5"></script>
<html lang="en-GB">
<body>
<main>
<div class="flex flex-row gap-2 bg-red-500">
<a aria-label="Lorem ipsum" href="#lorem-ipsum">Lorem ipsum</a>
<a aria-label="Amet porttitor" href="#amet-porttitor">Amet porttitor</a>
<a aria-label="Blandit turpis" href="#blandit-turpis">Blandit turpis</a>
</div>
<div class="flex flex-row snap-x snap-mandatory overflow-x-auto overflow-y-auto max-h-[100vh]">
<div class="min-w-[100vw] min-h-[80vh] snap-start">
<p id="lorem-ipsum">
Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Suscipit adipiscing bibendum est ultricies integer quis.
</p>
</div>
<div class="min-w-[100vw] min-h-[80vh] snap-start">
<p id="amet-porttitor">
Amet porttitor eget dolor morbi. Ullamcorper eget nulla facilisi etiam dignissim diam quis enim. Cras tincidunt lobortis feugiat vivamus at. Eleifend donec pretium vulputate sapien
</p>
</div>
<div class="min-w-[100vw] min-h-[80vh] snap-start">
<p id="blandit-turpis">
Blandit turpis cursus in hac habitasse platea. Egestas tellus rutrum tellus pellentesque eu. In eu s augue neque gravida. Tristique nulla aliquet enim tortor at auctor. A
</p>
</div>
</div>
</main>
<style is:global>
html {
scroll-behavior: smooth;
}
@media (prefers-reduced-motion: reduce) {
html {
scroll-behavior: auto;
}
}
</style>
</body>
</html>