daveycroqet
daveycroqet

Reputation: 2727

Overflowing Underline While Being Responsive to Text Length

I'm trying to emulate this effect via CSS:

enter image description here

The reason this is an issue is because it needs to be re-usable. The red underline's size should be dictated by the text length, but also overflow its container in a predictable manner, e.g.:

<div>
    <h1>This</h1>
    <h1>Cool</h1>
    <h1>Effect</h1>
</div>

The red underline should extend outside the div by 10px on the left, and then also overflow the text itself by roughly 50px on the right. So, all told, the red line is +60 pixels wider than the text itself.

How can I achieve this effect without doing it manually each time? I've had no success with pseudo elements, and box-shadow won't extend on the left and right as I need it to.

Upvotes: 1

Views: 1947

Answers (3)

Celso Soares
Celso Soares

Reputation: 627

All this examples mentioned above by lalit bhakuni and JasonB work really well, but only when you don't have any section with a background behind this underlined text.

The z-index: -1 will put the line you want behind the text like you want and also behind any other parent sections. In case any of these parent sections have a background, the line will be hidden (behind).

Other solution, not so clean, but solves all our problems is by adding an extra element inside of your heading:

HTML

<div class="div-with-background">
  <h1><span>This</span></h1>
  <br />
  <h1><span>Cool</span></h1>
  <br />
  <h1><span>Effect</span></h1>
</div>

CSS

.div-with-background {
  background-color: #333;
}

h1 {
  position: relative;
  display: inline-block;
  color: #fff;
  font-family: sans-serif;
  font-size: 100px;
  font-weight: 300;
  margin: 0;
}

h1::before {
  content: "";
  background: red;
  height: .25em;
  width: calc( 100% + 60px);
  position: absolute;
  bottom: .15em;
  left: -10px;
}

h1 > span {
  position: relative;
}

In this case, we don't even need to use the z-index property.

Upvotes: 0

lalit bhakuni
lalit bhakuni

Reputation: 627

use <h1><span>This</span></h1> make effect in span and adjust red box to use padding to were's you want :

   h1 span {
      position: relative;
      font-size: 100px;
      font-weight: 300;
      margin: 0;
      padding:0 0 0 20px;
    }  
h1 span::before {
  content: "";
  background: red;
  height: .25em;
  position: absolute;
  bottom: .15em;
  z-index: -1;
  width: 100%;
  left: 0;
}

like: https://jsfiddle.net/bdmpqkme/1/

Upvotes: 0

JasonB
JasonB

Reputation: 6368

Pseudo elements was the answer for me. Setting z-index on the :after element to get it positioned behind the parent element is a neat trick. The elements can't be block elements, but other than that it seemed straightforward.

html {
  min-height: 100%;
}

body {
  min-height: 100%;
  background: linear-gradient(to bottom, #0b122f 0%, #17457d 100%);
  padding: 20px;
}

h1 {
  position: relative;
  display: inline-block;
  color: #fff;
  font-family: sans-serif;
  font-size: 100px;
  font-weight: 300;
  margin: 0;
}

h1:before {
  content: "";
  background: red;
  height: .25em;
  width: calc( 100% + 60px);
  position: absolute;
  bottom: .15em;
  left: -10px;
  z-index: -1;
}
<div>
  <h1>This</h1>
  <br />
  <h1>Cool</h1>
  <br />
  <h1>Effect</h1>
</div>

Upvotes: 2

Related Questions