Emoji Silhouettes with CSS, a second approach

Every now and again it’s useful to display single-colour emoji on a web page; all the colours in those little emoji symbols are nice and all, but it does occasionally make your formal document look a bit like an angry fruit salad. I’ve seen a technique for this before (in particular from Bram van Damme, but searching for “emoji silhouettes” finds lots of other people doing it too), where you set the text colour to transparent and then set a text-shadow, and you’re done. This is nice, but it doesn’t work for me in Firefox, sadly; if you set the text color to transparent then indeed your emoji disappear, but if you set a text shadow they come right back, and in full colour.

So, I do it a different way, akin to the ancient and well-known image replacement method; set a text-indent on the element containing your emoji and then reverse that text indent in the text-shadows offset-x position. So you set text-indent to something massive and negative like -2000em so it’s definitely off the page to the left, and then a text-shadow (which, we recall, is specified as text-shadow: offset-x offset-y blur-radius color) of plus 2000em to put the text shadow back where the original characters were before they were indented miles to the left.

span.emoji {
    text-indent: -2000em;
    text-shadow: 2000em 0 0 red;
<p>And here are some emoji silhouettes:
    <span class="emoji">🚀 🎭 </span>.
    Aren't they nice!<p>

And here are some emoji silhouettes: 🚀 🎭 . Aren’t they nice!

You have to wrap your Unicode characters in their own little span, which is a bit unfortunate, but then you have to with other approaches too. (And your span has to be display: inline-block or block too, otherwise the text-indent gets ignored.) Anyway, not earth-shattering, but I quite like it.

After this was originally posted, Garrett LeSage suggested a different approach, using CSS filters. These are quite a lot more powerful than one might think. His approach applies a set of CSS filters in concert, like this:

Set the contrast on your emoji to high with CSS filter: contrast(0): 🚀 🎭

Use a sepia(100%) filter to colorise: 🚀 🎭

Set the colour to one of your choice with hue-rotate(180deg): 🚀 🎭

And finally pump up the saturation with saturate(1000%): 🚀 🎭

The up-side of this approach is that it’s one line of CSS; you don’t need to set inline-block, or worry about defining a width on your “emoji” element. The down-side is… well, you may be thinking, “where do we specify that we want the final colour of the emoji to be red in that code above?” And you would be right. You have to do some crazy maths calculations to actually work out how to set your emoji to the colour you want. Barrett Sonntag wrote an interactive filter generator to calculate the set of filters required to set your colour to the thing you choose, based on some Stack Overflow answers. I think this downside is enough to lean me away from this method, personally, but it’s another approach if you prefer it!

I'm currently available for hire, to help you plan, architect, and build new systems, and for technical writing and articles. You can take a look at some projects I've worked on and some of my writing. If you'd like to talk about your upcoming project, do get in touch.

More in the discussion (powered by webmentions)

  • Bramus! responded at twitter.com Emoji silhouettes in CSS; @bramus's approach of setting color: transparent and then using a text-shadow is nice but sadly doesn't work for
  • Gamer Geek responded at twitter.com Stuart Langridge: Emoji Silhouettes with CSS, a second approach kryogenix.org/days/2018/08/2…
  • Bramus! responded at twitter.com
  • Christian Dywan responded at twitter.com
  • Garrett LeSage responded at twitter.com Simpler emoji silhouettes in CSS: filter with high contrast, sepia to colorize, hue shift to taste, pump up saturation. filter: contrast(0) sepia(100…
  • Garrett LeSage responded at twitter.com (Disclaimer: This *should* work cross-browser, but it's after midnight and I only tested it in Firefox on my phone, in bed. 😉)
  • Stuart Langridge responded at twitter.com oooh, posh. I didn't think of filters. Nice work! That works well! MDN claims it's supported everywhere, too (well, except IE, but one can live with t…
  • Birmingham.IO responded at twitter.com Stuart Langridge: Emoji Silhouettes with CSS, a second approach by @sil buff.ly/2BYg1D0 #PlanetBirmingham
  • Stuart Langridge responded at twitter.com I've updated the original piece to add this approach too. Now that I've looked into it properly, I don't like it as much: setting the silhouettes to c…
  • Garrett LeSage responded at twitter.com Yeah, I guess saying "simpler" might be misleading. 😉 It's probably not bad once someone figures out some calculation with SASS or such. (It probably…
  • Garrett LeSage responded at twitter.com Aha! Use variables ("custom properties") which are supported everywhere but IE anyway. Then specify the color in HSL variables, but use offsets in th…
  • Stuart Langridge responded at twitter.com Yeah, it's kinda doable (and CSS vars are the way to do it, not SASS), but it's hard. What one actually wants is to say "color: red" (although I'd set…
  • Stuart Langridge responded at twitter.com actually, I'm wrong; this should be SASS or the like. No need to calculate it on everyone's computer at runtime, rather than once at build time. I jus…
  • Garrett LeSage responded at twitter.com Just realized this is also a great technique for an icon library based on SVGs for optional recoloring to symbic icons with color highlights. (Droppin…
  • Stuart Langridge responded at twitter.com ya! Although if you've got actual SVGs then you can just set fill from CSS directly :) But being able to retheme a whole set with filters is nice.
  • Haroen Viaene responded at twitter.com
  • Terence Eden responded at twitter.com Glad it isn't just me!