border-image is a tricky beastie of a property. It has dependencies, it’s barely out of vendor prefixation, and while
border-image itself is a shorthand code, the individual properties are scarely implemented. Also, while the fallback is simple enough,
border-image isn’t at all supported in IE, relegating this property to more of a novelty than a viable design element.
Still, the rest of the world supports it, including iOS, Android, and even Blackberry. So there’s some merit.
Let’s break down the property. The below is the core CSS of the demo seen here.
border-width:77px 75px 75px 74px; border-image:url(frame.png) 77 75 75 74 fill stretch;
First, note the aforementioned dependency above in line 1.
border-image needs a
border-width specified, otherwise it will not render. Easy enough. Added bonus — if
border-image is not supported, the browser just falls back to the basic border. So just add a
border-style to that code and you’ll be set.
border-image is a shorthand property for the following fields:
url()property. Use like any other in CSS.
Imagine four lines cutting the image: top, right, bottom and left. These lines cut the image into nine pieces.
border-image-slicedefines, by number or percentage, determine the size of those slices.
Jamy Golden over at Unmatched Style does a great job of explaining the slices as ratios to border width:
In effect, you can scale the size of the border image relative to its base width. This accepts one to four values, working just like the other CSS clockwise shorthands.
Lastly, note the keyword
fill. That refers to the centermost slice. You can toggle the center as a pseudo-background image by specifying
border-image-outsetdetermines how far from the border position the border image should render. The property accepts either an integer used as a multiplier or a direct pixel length. The default is 0, as in, the border image should appear right where the border is.
If the border width is set to 60px, a
border-image-outsetof 1 will render the border image 60px from the border origin. It’s interesting to note that
border-image-outset doesn’t affect the box model at all. Even though the expansion of the border greatly increases the element size visually, the element will still maintain the original DOM width.
The special thing about
border-imageis that the image changes to fit the content. How it changes is defined here. The value can be any one or two of:
- The single image fills the gap between two borders.
- The image repeats itself, without scaling, to fill the gap. The image will simply trim off the end to fit.
- Similar to repeat, but the image will scale itself to fit, rather than clip.
- Instead of scaling the image to fill the gap, the browser will simply distribute the repeated image with whitespace in between.
The previous property,
border-image-slice, defined the “slices” of the image. That is, how the image gets cut and applied as a border.
border-image-width defines the height of the image in the allotted space. A simple integer acts as multiplier — the default setting, not needed above, is 1. Pixel values and percentages can also be used.
For example, this setting:
border-width:60px; border-image:url(frame.png) 60;
is the same, visually, as
border-width:60px; border-image:url(frame.png) 120/2;
/2 is the
border-image-width specified. Again, it’s a multiplier. Where the border width/slice ratio is 60px/120px, or one-half, the
border-image-width of 2 doubles that ratio back to 1.
One more note — remember the keyword
fill is part of the previous property,
border-image-slice, so using it in the shorthand looks like this:
border-image:url(frame.png) 60 75 fill/1;
It’s easy to want to set
/2 immediately after the integers, but as that’s not valid, the border won’t render.