Rounded rectangles with a non-repeating background

May 25th, 2009

One problem I have come across on several occasions is creating a fixed-width rounded rectangle that, in addition to its rounded-ness, has a non-repeating backgrund image. Here is an example of what I'm talking about:

a rounded rectangle with a non repeating bg

So lets start with the rounded rectangle part.  This is the typical html that I might use:

<div class="rect_wrap">
  <div class="rect_top"></div>
  <div class="rect_body">Lorem ipsum dolor sit amet, consectetur adipiscing elit. Ut cursus justo eget leo vehicula vel consequat massa vulputate. Pellentesque mollis pharetra sagittis.</div>
  <div class="rect_bottom"></div>
</div>

I use CSS to give "rect_top" and "rect_bottom" a height of 10px and a non-repeating background image. Also, "rect_body" gets a background image that repeats vertically. Like this:

.rect_top{
  height: 10px;
  background: url(/images/rounded_bg_top.png) no-repeat center top;
}

.rect_bottom{
  height: 10px;
  background: url(/images/rounded_bg_bottom.png) no-repeat center top;
}

.rect_body{
  background: url(/images/rounded_bg.png) repeat-y center top;
}

Simple right? Well what about that quotation mark? I can't make it part of the "body" background image because that image needs to keep repeating in the y direction in case there is tons of text. And I can't make it part of the "top" background image because the quotation mark is too large. Here is the key: first, add one more <div> to our html:

<div class="rect_wrap">
  <div class="rect_top"></div>
  <div class="rect_body_wrap">
    <div class="rect_body">Lorem ipsum dolor sit amet, consectetur adipiscing elit. Ut cursus justo eget leo vehicula vel consequat massa vulputate. Pellentesque mollis pharetra sagittis.</div>
  </div>
  <div class="rect_bottom"></div>
</div>

and now we add a bit of css and change a bit of css to finish the job:

/* note this style used to be the .rect_body style*/
.rect_body_wrap{
  background: url(/images/rounded_bg.png) repeat-y center top;
}

.rect_body{
  backgorund: url(/images/quotation_mark.png) no-repeat  5px 5px;
}

That's it. Well… not quite. What happens when the non-repeating background image needs to be part of "top" background? Something like this (note the gradient):

a rounded rectangle with a non repeating bg

In this case, we start with the exact same html:

<div class="rect_wrap">
  <div class="rect_top"></div>
  <div class="rect_body_wrap">
    <div class="rect_body">Lorem ipsum dolor sit amet, consectetur adipiscing elit. Ut cursus justo eget leo vehicula vel consequat massa vulputate. Pellentesque mollis pharetra sagittis.</div>
  </div>
  <div class="rect_bottom"></div>
</div>

Now we change a couple of our styles:

.rect_top{
  height: 100px;
  background: url(/images/rounded_bg_top_with_gradient.png) no-repeat center top;
}

.rect_body{
  margin-top: -80px;
}

.rect_body_wrap{
  background: url(/images/rounded_bg.png) repeat-y center top;
}