Written by
Update: In the name of performance and image quality, I decided to remove the texture background from the headings and links. It now uses a simple gradient.

If you’ve spent much time reading this blog, you’ve probably noticed the sexy rainbow texture on the text of the headers and links.

There are several ways to accomplish this, each with their own pros and cons. That’s what I’ll cover in this post.

First, you’ll need a texture that works well with your design.

After a lot of trial and error, I chose this texture because it was pretty and stood out against the light background.

ProTip: You may need to use a bolder font weight to let the texture shine through.

What It Looks Like

All of these methods should give you nearly identical results, but in the unlikely event your browser doesn’t support any of them, here you go:

Text clipping with CSS or SVG preview.

Method One

This is probably the most commonly-suggested way to clip text, but I feel there are better ways.

I ♥ CSS
Live demo

Pros

Cons

Usage

<style>
/* Remember to -vendor-prefix these properties! */

@supports (background-clip: text) and (text-fill-color: transparent) {
	.text-clip {
		color: #000000;
		background: transparent 50% 50% no-repeat;
		background-image: linear-gradient(transparent, transparent), url("/path/to/texture.jpg");
		background-clip: text;
		text-fill-color: transparent;
	}
}
</style>
<div class="text-clip">I ♥ CSS</div>

Method Two

This uses a <pattern> inside of a SVG element.

Assuming you’ll want to use this technique on more than one blog of text in a page, it would be ideal to separate the text from the texture.

I ♥ SVGI ♥ SVG
Live demo

Pros

Cons

Usage

<style>
text {
	/* To normalize text. Both text layers need to in the exact same position, and placed directly over the pattern. */
	font-family: inherit;
	font-weight: inherit;
	line-height: inherit;
	text-align: center;

	/* To center text within the viewing area. */
	alignment-baseline: central;
	dominant-baseline: central;
	text-anchor: middle;
}
</style>
<!-- Text -->
<svg class="text-clip" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 800 400" width="800" height="400" preserveAspectRatio="xMidYMid meet">
	<!-- Show text while image is downloading. Include a very small stroke matching the background if it’s a solid color; this will help prevent color bleed. -->
	<text x="50%" y="50%" fill="#000000" stroke="#FFFFFF" stroke-width="1">I ♥ SVG</text>

	<!-- Fill the text shape with the pattern. -->
	<text x="50%" y="50%" fill="url(#text-clip)">I ♥ SVG</text>
</svg>
<!-- Texture -->
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" viewBox="0 0 800 400" width="0" height="0" preserveAspectRatio="xMidYMid meet">
	<defs>
		<pattern id="text-clip" patternUnits="userSpaceOnUse" width="800" height="400">
			<image xlink:href="/path/to/texture.jpg" width="800" height="400" />
		</pattern>
	</defs>
</svg>

Method Three

This uses the new clip-path CSS property along with an image inside of a SVG element.

This was the most challenging of all to set up for the inline demo. Some property was clashing with the clipping of the element, preventing it from showing. When that finally worked, the text was incredibly small and I had to dramatically increase it to the same size as the others.

Hopefully, it will be easier for you, if you decide to use this method.

Live demo

Pros

Cons

Usage

<style>
/* Remember to -vendor-prefix this property! */

.text-clip {
	clip-path: url("#text-clip");
}
</style>
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" viewBox="0 0 800 400" width="800" height="400" preserveAspectRatio="xMidYMid slice">
	<defs>
		<clipPath id="text-clip" width="800" height="400">
			<text x="50%" y="50%">I ♥ SVG</text>
		</clipPath>
	</defs>
</svg>
<img class="text-clip" src="/path/to/texture.jpg" alt="I ♥ SVG" />

ProTip: Because of the hassle and drawbacks associated with this version, I would recommend you NOT use method three.

Method Four

I saved the best for last. A technique I pioneered myself; one that I’ve never seen anyone else do, so I’m really freakin’ happy about this! 😍

This is the technique I use on this very blog.

The trick is to trick the browser into blending the colors right out of the visible spectrum of light. This technique will progressively enhance your text with the new CSS mix-blend-mode property.

I ♥ CSS
Live demo

Pros

Cons

Usage

<style>
/* Remember to -vendor-prefix these properties! */

@supports (mix-blend-mode: lighten) and (mix-blend-mode: soft-light) {
	.text-clip {
		position: relative;
		display: block;
	}

	.text-clip:before,
	.text-clip:after {
		position: absolute;
		top: 0;
		right: 0;
		bottom: 0;
		left: 0;
		content: " ";
		display: block;
		width: 100%;
		height: 100%;
	}

	.text-clip:before {
		background: 50% 50% no-repeat url("/path/to/texture.jpg");
		background-size: cover;

		mix-blend-mode: lighten;
	}

	/* Improves legibility. Tweak this to fit your needs! */
	.text-clip:after {
		background: #000000;
		opacity: 0.2;

		mix-blend-mode: soft-light;
	}
}

/* Inversing the foreground and background colors will capture the texture automatically, inside the selected text. See method four "Pros" and remember to -vendor-prefix this as well. */
::selection {
	background: #F50808;
	color: #FDFCFB;
}
</style>
<div class="text-clip">I ♥ CSS</div>

Bonus Method

Naturally, you can do this with image editors like Adobe Photoshop or GIMP.

While this method is definitely the most compatible cross-browser, it is not true text clipping. I recommend it if the stylized text is essential for your message.

I ♥ CSS
Live demo

Pros

Cons

Usage

<style>
/* Remember to -vendor-prefix these properties! */

.text-clip {
	background: transparent 50% 50% no-repeat url("/path/to/texture.jpg");
	background-size: contain;

	/* Put text off screen for screen readers */
	direction: ltr;
	text-indent: -9999em;
	overflow: hidden;
}

/* To support high-density and Retina screens, include this @media query. */
@media (min-device-pixel-ratio: 2), (min-resolution: 192dpi), (min-resolution: 2dppx) {
	.text-clip {
		background-image: url("/path/to/texture@2x.jpg");
	}
}
</style>
<div class="text-clip">I ♥ CSS</div>

ProTip: Add the image using <img src="/path/to/texture.jpg" alt="I ♥ CSS" /> for 100% support, but slightly less flexibility.

Wrap Up

Some of these methods require a great deal of TLC when it comes to sizing the content inside, particularly the SVG examples.

If you use any of the above methods or if you have more to add to this list, leave a comment below or send me an email and I’ll be happy to add it to the list. :)

I ♥ SVG
Not every business needs a cutting edge experience, but when you want exceptional quality front-end web development work, remember me. Send me an email and we can talk about the details.

Get new posts by email 😎

Unsubscribe anytime. Privacy protected.