#193: New Colors in CSS and a CSS-Only Carousel

Howdy everyone! Welcome to issue #193. This week is all about CSS carousels, new colors available in CSS, and how centering is not a big deal anymore and we should all stop moaning about it. CSS is, in fact, awesome.

Let’s begin!

Robin: This week I wanted to learn how to make a CSS-only carousel and found it surprisingly easy. This is all thanks to the scroll-snap CSS property and the carousel happens to look something like this:

You can scroll on the right to see big new images click-clack into place and you can scroll on the left or click an image to jump to the larger image in the carousel. Here’s the demo, although make sure to check it out on larger displays.

The markup for the large image gallery on the right looks like this:

<div class="gallery">
  <img id="image-1" src="..." alt="..." />
  <img id="image-2" src="..." alt="..." />

And the left-hand side navigation:

  <a href="#image-1"><img src="..." alt="..."/></a>
  <a href="#image-2"><img src="..." alt="..."/></a>

With this we can simply use the id in the href to jump to each image. And with the following CSS…

.gallery {
  overflow: scroll;
  height: 100vh;
  scroll-snap-type: x mandatory;
  scroll-behavior: smooth;

…we can make sure the wrapping div is always the same height as the browser window with height: 100vh and make sure that each image clicks into place with scroll-snap. That last property, scroll-behavior ensures that when we click a link in the left nav, the whole thing will scroll much more smoothly rather than jumping to the selected image.

Here’s how that looks when it comes together:

Making this rather simple demo surprised me. First, it didn’t take long to make this at all. I didn’t need to reach for a jQuery plugin or an npm module just to make a carousel. Instead, I could simply use some newish CSS properties to get the exact effect I wanted.

I reckon this shows the vast amount of progress that’s been made to our experience as web developers — it reminds me that CSS has come such a long way over the years and the combination of all these properties has made this language easier to use. It’s genuinely amazing to me.

Centering in CSS is not difficult anymore

Benjamin De Cock mentioned that on Twitter the other day which I thought was buck wild because he’s right! Here’s what he suggests now:

.parent-element {
  display: grid;
  place-items: center;

It does get pretty complicated if you want to center some other things in CSS (and thankfully we have a guide all about that). But for the most part this is a pretty dang handy thing to remember.

Making inputs work for everyone

Here’s a great post about inclusive form inputs where Oscar writes:

Labelling and describing inputs is a low-hanging fruit. In most interfaces the elements are there, they just need to be structured properly. Still, it is virtually impossible to just make a website accessible. There is no just. Never. But you can work towards making it more accessible by the day (or sprint).

In this post, Oscar then looks at how to prevent many of these errors by ensuring that the HTML for our forms is correct. It only takes minutes for us to learn this stuff but our users will have a vastly improved experience. Although, as Oscar writes towards the end:

Accessibility is a team-sport. If you want to make lasting change in your company, your dev team, basically anywhere you need to get the team onboard. There’s a limit on flying undercover and there is also a risk, because individual change makes it very hard to have a lasting impact.

Anyway, I’ve struggled a lot with this in the past. When it comes to the community building side, it can be extremely difficult to make lasting change. But often I think it means setting a good example for others to follow. The smallest accessibility improvement you make today can impact others in your org to contribute or learn more about accessibility. And that’s powerful stuff.

Also, this riffs on the work that Austin Gil has been doing lately with his series on making great HTML forms.

HTML includes let you grab contents from a file

This is a smart post from Scott Jehl where he shows us how to import the contents of another file just like this:

  onload="this.before((this.contentDocument.body || this.contentDocument).children[0]);this.remove()">

Interesting! The iframe above uses the onload event to inject the contents of the iframe just outside it, before deleting itself. Scott writes why this technique is useful:

As long as I have been working on the web, I’ve desired a simple HTML-driven means of including the contents of another file directly into the page. For example, I often want to append additional HTML to a page after it is delivered, or embed the contents of an SVG file so that we can animate and style its elements. Typically here at Filament, we have achieved this embedding by either using JavaScript to fetch a file and append its contents to a particular element, or by including the file on the server side, but in many cases, neither of those approaches is quite what we want.

There are a bunch of new colors coming soon to CSS

The other day Lea Verou wrote about CSS color 4 and how soon we’ll get access to a ton of colors real soon in browsers:

Today, the gamut (range of possible colors displayed) of most monitors is closer to P3, which has a 50% larger volume than sRGB. CSS right now cannot access these colors at all. Let me repeat: We have no access to one third of the colors in most modern monitors. And these are not just any colors, but the most vivid colors the screen can display. Our websites are washed out because monitor hardware evolved faster than CSS specs and browser implementations.

There’s a ton of exciting work in this space and I’m super excited to see all these color improvements land in browsers soon. The web is about to get brighter, and more beautiful, too.

Building a design system? Here’s a mistake to avoid!

The other day I wrote about how to build a bad design system because in the past I’ve made this mistake that only makes things worse: asking for everyone’s opinion. In fact, when it comes to building a big design system it makes sense to reduce the number of people on your team and keep the conversation focused.

How many people are making decisions about your design system?

Are three people talking about the buttons in your design system? Wonderful. Are there 20? Woof! That’s a serious problem because it shows that far too much energy is being spent on the wrong things; it’s nothing short of mismanagement, in fact.

About a year into working on design systems I realized that their biggest advantage is all about keeping people focused on the big problems — and that picking the border-radius of cards or the background-color of buttons shouldn’t require the attention of so many gosh darn people.

So my advice would be: try and focus on much smaller teams. At least, that’s what I’m trying now.

There’s no :nth-child-of-class, although…

Mate Marschalko had this idea to use the ~ — or general sibling selector — to do something tricky such as “style the third element that has a class of .active.” Mate wrote the following CSS to do that:

.active ~ .active ~ .active {
  background: red;

That’s super smart! Just the other day I bumped into this issue and couldn’t for the life of me figure out how to style the :nth-child-of-class. Definitely adding this trick to the toolbox for later.

CSS transforms are neat

Dan Wilson wrote about the new transformation properties in CSS: translate, rotate, and scale. To see what’s new though we have to look at the old syntax.

To make changes to an element with the transform property we have to write something like the following:

.element {
  transform: rotate(10deg) scale(0.95) translate(10px, 10px);

As Dan mentions, this can be pretty annoying and hard to read if you want to only change the scale of the element and nothing else.

Soon we’ll be able to use the following syntax instead:

.element {
  rotate: 10deg;
  scale: 0.95;
  translate: 10px 10px;

So much cleaner! It’s sort of wild that I never complained about this before and would just let myself be confused and mildly annoyed by the old syntax. Either way, this is great. Make sure to check out Dan’s post as he goes into a lot more detail though.

Do you know about Array.flat(Infinity) in JavaScript?

Addy Osmani points out that this lets you flatten all the arrays that you pass into it, just like this:

const array = [1, 2, [3]];
// [1, 2, 3] 

Neat stuff!

Alfred keywords are super useful for web design work

The other day I sat down to improve my Alfred workflow — this is the super handy productivity app for Mac. It has this feature that lets you type something such as “\date” in any app and it will expand into “Sunday, April 5th, 2020”.

Ah! I thought loudly. There’s often times when I want to make a video that works like a gif and it requires a bunch of HTML attributes I can never remember. So I setup a keyword where all I type is \video into my text editor of choice and…

<video autoplay loop muted playsinline src="/uploads/"></video>

…just appears on screen for me. I don’t have to constantly go search for the syntax each time now! This technique was also super handy for my blog where I have the following HTML for images that are extra wide:

<div class="m-wrapper--full">
  <figure class="m-wrapper--unpadded">
    <img alt="" src="/uploads/" loading="lazy">

Now all I have to type is /figure and the HTML expands in place, ready for me to go. Of course, there are lots of apps that do this keyword and text-expansion stuff. And so if you’re using one today then I’d recommend you spend some time to make life easier for you!

How do we get data from CSS into JavaScript?

That might be hex values, text, or any kind of data really. Well, Marko Ilic has written all about CSS custom properties, Sass variables, and more.

The fancy part here for me is where Marko exports Sass variables and then imports them into a JavaScript file with webpack. You have to change your build step a little bit but I can see that being useful for a million different reasons.

Here’s a web performance checklist I’ve been using lately.

The other day I realized that I’m probably forgetting a ton of basic web performance things during my day-to-day work and so I setup a Notion doc with some of the most impactful things.

I’ve found this to be handy because you can fork this document whenever you start a new project and check things off as you go.


Jetpack brings loads of power to your self-hosted WordPress site. It takes all of the great things WordPress.com sites get — like a CDN for assets, SSL, single sign-on, and real-time monitoring just to name a few — and gives them to you on your own WordPress site. Heck, it even provides site backups and boasts an all-new powerful search feature. We use it at CSS-Tricks to power so many things, from Markdown to social sharing to improved image performance. You’d be wise to consider it for your own WordPress site.

Get Started Free →

  • “Jamstack” you say? Yep, rather than casing it like “JAMstack” or otherwise, the official discussion ended on Jamstack.
  • What if your Jamstack site needs an auth system, like where people (or even just admins) need to log in? Netlify has long offered that functionality and Brian Rinaldi from Stackbit explains how in Gating Content in Jamstack Sites.
  • Brian’s got another one, Creating a Jamstack Site with Open Authoring Using Netlify CMS, where he gets into Open Authoring. I think open authoring is a big deal as it allows anyone to suggest content changes in a way that classic CMSs never really have. These Git-backed CMSs can offer it because Git service providers, like GitHub, have the concept of Pull Requests which are perfect for the job. We’ve covered this as well.
  • While I’m linking to a million Brian links, here’s one he did on API-based CMSs, which are different than ones backed by Git in that the content is hosted in some cloud database that you don’t deal with directly, rather than in the files in the repo itself.
  • The last ShopTalk Show was with Divya Tagtachian and mostly about Jamstack stuff. She mentioned another podcast: That’s My Jamstack.