Grow your CSS skills. Land your dream job.

Body Border, Rounded Inside

Published by Chris Coyier

Reader Arun wrote in with a question on how to make a body border that was rounded where the edges met on the inside. Like this. We've covered body borders before, but this was slightly different.

It does look rather confusing at first. You can't do bizarro inside-y rounded-ness like with CSS, that's crazy talk. But then, if you just look at it as a normal rounded corner element sitting on top of a square element, it looks less weird. So that's attempt #1:

Check out this Pen!

But if that extra element just-for-design-reasons bothers us, we actually could pull this off using border-image on the <body> element. Remember border-image is just "nine slice" scaling essentially. Four fixed size corners, four repeating-on-one-axis edges, and a stretchy middle.

Pretty easy:

body {
  border-image: url(rounded-edge.png) 25% repeat;
  border-width: 25px;
}

Note that IE (any version) doesn't do border-image.

Check out this Pen!

But but but scrolling

We'd need to ask how important it is that the "body border" always has visible bottom border. If it's OK that the bottom part can scroll away when the page is longer than the viewport, that's easy.

We just make sure the body is at least that big, but can get bigger:

* { box-sizing: border-box; }
html { height: 100%; }
body { min-height: 100%; }
Check out this Pen!

If it's not OK that the bottom border scrolls aways (it must be seen at all times) we're going to have to use that extra element again. Only we'll make sure that it can scroll vertically. That scrollbar might screw with the rounded-corner-ness though, unless we're in WebKit and then we can fiddle with the look of the scrollbars to make sure it's OK.

body {
  background: #5bb0ff;
}

.page-wrap {
  position: fixed;
  top: 10px;
  right: 10px;
  left: 10px;
  bottom: 10px;
  background: white;
  border-radius: 10px;
  padding: 20px;
  overflow-y: scroll;
}

::-webkit-scrollbar-track {
  background: none;
}
::-webkit-scrollbar {
  width: 10px;
  height: 10px;
}
::-webkit-scrollbar-thumb {
  background: #ccc;
  border-radius: 5px;
}
Check out this Pen!

That's all I got.

Comments

  1. One addition: add -webkit-overflow-scrolling: touch; to the .page-wrap class to retain inertial scrolling on iOS devices.

  2. Rob Warren
    Permalink to comment#

    Using a psuedo element so it can be used anywhere in a site here

    • Ryan McKay
      Permalink to comment#

      This works, unless you want the scrollbar showing inside the border….then it gets a bit tricky and needs more CSS or another element

  3. James
    Permalink to comment#

    Firefox does support border image :)

  4. Firefox doesn’t do border-image? Since when did that happen? I mean, I don’t really care, since it’s a pretty useless feature, but according to MDN and caniuse.com, it’s supported unprefixed since version 15.

    However, from testing, you’re right, it doesn’t work. But what’s the deal with that? I don’t remember seeing anything about that….?

    • I had to play around with it a bit and it turns out it does support border-image, it’s just a little more picky about it. I updated the article.

      Doesn’t work:

      border-image: url(img.png) 25% repeat;
      border-width: 25px;
      

      Does work:

      border: 25px solid;
      border-image: url(img.png) 25% repeat;
      

      I guess Firefox needs border-style in addition to border-width before it will do its thing.

      And I think border-image is a little useful, its just a bad name. I think more people would get it and like/use it if it was something closer to:

      background: nine-slice-scaling(args);
      
    • Peter Mumford
      Permalink to comment#

      border-image has a ways to go before its useful. It doesn’t work well with svgs, and implementation, even for regular png images, is inconsistent across browsers. Its just not worth it.

  5. Permalink to comment#

    What about without border image, using drop shadow:

  6. Wow!! very nice tip. thank you.

  7. I try to win originality contest by using display: table;

    Too bad it’s IE9+ only (also meaning latest Firefox, Chrome and Opera all work fine).

  8. Third and (I hope) final version:

    http://codepen.io/Merri/full/ucEmg

    Awful lot of CSS, but gives a very nice transparency effect for the body border. You can see body content scroll behind the border, including the rounded corners.

  9. Great instructions! Thank you a lot!

  10. Great example of the power of CSS. Since it was introduced, I thought that this is one of the best think that ever happen to web designers and developers. Great tutorial!

  11. Another method using a border & box-shadow

  12. Thank you Chris for clearing my doubt and finding time to write a tutorial on the same..

  13. Ramesh Chowdarapally
    Permalink to comment#

    Wow… nice chris…
    really its having fun and learn.

  14. Philipp
    Permalink to comment#

    Why not use a before element? http://dabblet.com/gist/5346231 This should work on the body aswell.

  15. Tim
    Permalink to comment#

    What about this?

    Thanks.

  16. Isn’t it easy to just use two div’s? First one would act as the container, and second as the content holder. That way you remove image completely and everything is CSS based.

    • Yes. That was Chris’ first example.

    • Yes, but he is still using the background image.

    • You don’t need two divs. There are enough elements in a regular page to do it all with just those elements and a few pseudo elements. I posted my “third attempt” above in the comments that does it all without images and with no additional HTML markup while also adding some cool additional features like ability to have semitransparency for the entire border including the rounded corner areas while still maintaining clickability of the content.

      You can throw the code on about any page on the web and it gives the body border effect on the site, although on * { box-sizing: border-box; } like on this site is poison to it and you need to add a few box-sizing: content-box; rules to make things work properly.

  17. What about taking advantage of the fact that outlines aren’t rounded and shadows are, and do something like this? http://dabblet.com/gist/5377617

    • Permalink to comment#

      There actually isn’t a need for the outline rule as what we want to do here is to wrap it around the viewport. The box-shadow would work but the downside of any single element solution is that the border should be above content, but we don’t want to block access to the content. Unfortunatenaly there is no way in CSS to force transparent background of an element to be ignored.

      Here is CodePen on the issue based on your box-shadow suggestion: http://codepen.io/Merri/pen/KGqsh

  18. The demos for this weren’t working in Firefox. So I added the rule:

        html {
            background: transparent;
        }
    

    Adding that to the demos in codepen makes them work in Firefox too.

This comment thread is closed. If you have important information to share, you can always contact me.

*May or may not contain any actual "CSS" or "Tricks".