{"id":1295,"date":"2024-03-19T16:44:42","date_gmt":"2024-03-19T22:44:42","guid":{"rendered":"https:\/\/frontendmasters.com\/blog\/?p=1295"},"modified":"2024-03-19T16:44:44","modified_gmt":"2024-03-19T22:44:44","slug":"chill-scroll-snapping-article-headers","status":"publish","type":"post","link":"https:\/\/frontendmasters.com\/blog\/chill-scroll-snapping-article-headers\/","title":{"rendered":"Chill Scroll Snapping: Article Headers"},"content":{"rendered":"\n<p>CSS has a feature called <a href=\"https:\/\/developer.mozilla.org\/en-US\/docs\/Web\/CSS\/CSS_scroll_snap\">scroll snapping<\/a>. A lot of the demos and examples, rightfully so, focus around things that benefit highly from it. For instance, <a href=\"https:\/\/tannerhodges.github.io\/snap-slider\/\">an image slider<\/a>, carousel, or <a href=\"https:\/\/12daysofweb.dev\/2022\/css-scroll-snap\/\">grid of things<\/a> that just beg to be aligned after scrolling. <\/p>\n\n\n\n<p>But you don&#8217;t have to be in such a strict and rigid situation for scroll snapping to just be <em>a nice touch.<\/em> Instead you can think: <em>is there anything on this page that would look or feel nice if when you scrolled nearby it would snap into place?<\/em><\/p>\n\n\n\n<p>Maybe you have one of those &#8220;full viewport filling&#8221; headers to a page. If you added a scroll snapping point to the first element after that (e.g. <code>.article-header + :first-child<\/code>) then you could help users scroll right to it, whooshing past the giant header. Like:<\/p>\n\n\n\n\t\t<figure class=\"wp-block-jetpack-videopress jetpack-videopress-player aligncenter wp-block-jetpack-videopress--has-max-width\" style=\"max-width: 421px;\" >\n\t\t\t<div class=\"jetpack-videopress-player__wrapper\"> <iframe title=\"VideoPress Video Player\" aria-label='VideoPress Video Player' width='491' height='750' src='https:\/\/videopress.com\/embed\/AdmF0zMo?cover=1&amp;autoPlay=0&amp;controls=1&amp;loop=0&amp;muted=0&amp;persistVolume=1&amp;playsinline=0&amp;preloadContent=metadata&amp;useAverageColor=1&amp;hd=0' frameborder='0' allowfullscreen data-resize-to-parent=\"true\" allow='clipboard-write'><\/iframe><script src='https:\/\/v0.wordpress.com\/js\/next\/videopress-iframe.js?m=1674852142'><\/script><\/div>\n\t\t\t\n\t\t\t\n\t\t<\/figure>\n\t\t\n\n\n<p>Love it? Hate it? It&#8217;s just an idea. Some people really bristle against things that seem to take scrolling control away from them. <\/p>\n\n\n\n<p>We could go a bit more chill. <\/p>\n\n\n\n<p>What if just the headers of an article had scroll snapping points? That looks something like this, by the way:<\/p>\n\n\n<pre class=\"wp-block-code\" aria-describedby=\"shcb-language-1\" data-shcb-language-name=\"CSS\" data-shcb-language-slug=\"css\"><span><code class=\"hljs language-css\"><span class=\"hljs-selector-tag\">html<\/span> {\n  <span class=\"hljs-attribute\">scroll-snap-type<\/span>: y mandatory;\n}\n\n<span class=\"hljs-selector-tag\">main<\/span> {\n  h2, h3 {\n    <span class=\"hljs-attribute\">scroll-snap-stop<\/span>: normal;\n    <span class=\"hljs-attribute\">scroll-snap-align<\/span>: start;\n  }\n}<\/code><\/span><small class=\"shcb-language\" id=\"shcb-language-1\"><span class=\"shcb-language__label\">Code language:<\/span> <span class=\"shcb-language__name\">CSS<\/span> <span class=\"shcb-language__paren\">(<\/span><span class=\"shcb-language__slug\">css<\/span><span class=\"shcb-language__paren\">)<\/span><\/small><\/pre>\n\n\n<p>Now you&#8217;ve got these headers that just so happen to line up very nicely at the top of the screen when you get close to them:<\/p>\n\n\n\n\t\t<figure class=\"wp-block-jetpack-videopress jetpack-videopress-player aligncenter wp-block-jetpack-videopress--has-max-width\" style=\"max-width: 405px;\" >\n\t\t\t<div class=\"jetpack-videopress-player__wrapper\"> <iframe title=\"VideoPress Video Player\" aria-label='VideoPress Video Player' width='500' height='482' src='https:\/\/videopress.com\/embed\/f7hte0cS?cover=1&amp;autoPlay=0&amp;controls=1&amp;loop=0&amp;muted=0&amp;persistVolume=1&amp;playsinline=0&amp;preloadContent=metadata&amp;useAverageColor=1&amp;hd=0' frameborder='0' allowfullscreen data-resize-to-parent=\"true\" allow='clipboard-write'><\/iframe><script src='https:\/\/v0.wordpress.com\/js\/next\/videopress-iframe.js?m=1674852142'><\/script><\/div>\n\t\t\t\n\t\t\t\n\t\t<\/figure>\n\t\t\n\n\n<p>Gotta tell ya there: don&#8217;t hate it.<\/p>\n\n\n\n<p>Here&#8217;s a demo where the headers are scroll snap points, plus the header itself, plus the very first thing after the header. I&#8217;ve also used a smidge of <code>scroll-margin-block-start<\/code> to push the snap point a little bit away from the header giving it some breathing room.<\/p>\n\n\n<pre class=\"wp-block-code\" aria-describedby=\"shcb-language-2\" data-shcb-language-name=\"CSS\" data-shcb-language-slug=\"css\"><span><code class=\"hljs language-css\"><span class=\"hljs-selector-tag\">main<\/span> {\n  <span class=\"hljs-attribute\">max-width<\/span>: <span class=\"hljs-number\">60ch<\/span>;\n  <span class=\"hljs-attribute\">margin-inline<\/span>: auto;\n  h1,\n  h2,\n  &gt; h1 + * {\n    <span class=\"hljs-attribute\">scroll-snap-stop<\/span>: normal;\n    <span class=\"hljs-attribute\">scroll-snap-align<\/span>: start;\n  }\n  &gt; <span class=\"hljs-selector-tag\">h1<\/span> + *,\n  <span class=\"hljs-selector-tag\">h2<\/span> {\n    <span class=\"hljs-attribute\">scroll-margin-block-start<\/span>: <span class=\"hljs-number\">0.5rem<\/span>;\n  }\n}\n\n<span class=\"hljs-selector-tag\">html<\/span> {\n  <span class=\"hljs-attribute\">scroll-snap-type<\/span>: y mandatory;\n}<\/code><\/span><small class=\"shcb-language\" id=\"shcb-language-2\"><span class=\"shcb-language__label\">Code language:<\/span> <span class=\"shcb-language__name\">CSS<\/span> <span class=\"shcb-language__paren\">(<\/span><span class=\"shcb-language__slug\">css<\/span><span class=\"shcb-language__paren\">)<\/span><\/small><\/pre>\n\n\n<div class=\"wp-block-cp-codepen-gutenberg-embed-block cp_embed_wrapper\"><iframe id=\"cp_embed_MWRyYde\" src=\"\/\/codepen.io\/anon\/embed\/MWRyYde?height=450&amp;theme-id=47434&amp;slug-hash=MWRyYde&amp;default-tab=result\" height=\"450\" scrolling=\"no\" frameborder=\"0\" allowfullscreen allowpaymentrequest name=\"CodePen Embed MWRyYde\" title=\"CodePen Embed MWRyYde\" class=\"cp_embed_iframe\" style=\"width:100%;overflow:hidden\">CodePen Embed Fallback<\/iframe><\/div>\n\n\n\n<p>My main point isn&#8217;t &#8220;do exactly this&#8221;, it&#8217;s just that thinking about scroll snapping points in a design doesn&#8217;t have to be relegated to carousels. There is likely smaller and more chill opportunities to slap in snap point just to make something feel a bit more polished.<\/p>\n","protected":false},"excerpt":{"rendered":"<p>CSS has a feature called scroll snapping. A lot of the demos and examples, rightfully so, focus around things that benefit highly from it. For instance, an image slider, carousel, or grid of things that just beg to be aligned after scrolling. But you don&#8217;t have to be in such a strict and rigid situation [&hellip;]<\/p>\n","protected":false},"author":1,"featured_media":1357,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"_acf_changed":false,"sig_custom_text":"","sig_image_type":"featured-image","sig_custom_image":0,"sig_is_disabled":false,"inline_featured_image":false,"_jetpack_memberships_contains_paid_content":false,"footnotes":""},"categories":[1],"tags":[7,92],"class_list":["post-1295","post","type-post","status-publish","format-standard","has-post-thumbnail","hentry","category-blog-post","tag-css","tag-scrolling"],"acf":[],"jetpack_featured_media_url":"https:\/\/i0.wp.com\/frontendmasters.com\/blog\/wp-content\/uploads\/2024\/03\/snap-thumb.jpg?fit=1000%2C500&ssl=1","jetpack_sharing_enabled":true,"_links":{"self":[{"href":"https:\/\/frontendmasters.com\/blog\/wp-json\/wp\/v2\/posts\/1295","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/frontendmasters.com\/blog\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/frontendmasters.com\/blog\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/frontendmasters.com\/blog\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/frontendmasters.com\/blog\/wp-json\/wp\/v2\/comments?post=1295"}],"version-history":[{"count":3,"href":"https:\/\/frontendmasters.com\/blog\/wp-json\/wp\/v2\/posts\/1295\/revisions"}],"predecessor-version":[{"id":1358,"href":"https:\/\/frontendmasters.com\/blog\/wp-json\/wp\/v2\/posts\/1295\/revisions\/1358"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/frontendmasters.com\/blog\/wp-json\/wp\/v2\/media\/1357"}],"wp:attachment":[{"href":"https:\/\/frontendmasters.com\/blog\/wp-json\/wp\/v2\/media?parent=1295"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/frontendmasters.com\/blog\/wp-json\/wp\/v2\/categories?post=1295"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/frontendmasters.com\/blog\/wp-json\/wp\/v2\/tags?post=1295"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}