How can we not apply opacity to a child element?

Asked

Viewed 16,498 times

10

I have a div with applied opacity, but this div has child element. I don’t want to apply opacity to those child elements, I would have some way of solving that?

Example: http://jsfiddle.net/qSsC3/1/

Link code:

.div-pai{
  width: 400px;
  height: 400px;
  background-color: black;
  position: fixed;
  opacity: 0.7;
}
 .div-filho{
  width: 150px;
  height: 150px;
  position:absolute;
  top: 50%;
  left: 50%;
  background: blue;
  margin-top: -75px;
  margin-left: -75px;
  opacity: 1;
}
<div class="div-pai">
    <div class="div-filho"></div>
</div>

5 answers

12


I don’t think it’s possible, but there is workarounds.

If you need opacity only in the background, you can apply a color rgba:

background-color: rgba(0,0,0,.7);

Fiddle. Note that there is no support for IE<=8.

If you need to apply opacity to every element and not only in the background, you will have to break the hierarchy and turn them into brothers.

There is a third way, which works if you are seeking an effect overlay. It would create a pseudo-element ::before covering every element .div-pai and is below the .div-filho:

.div-pai:before {
    content: '';
    position: absolute;
    top: 0; bottom: 0;
    left: 0; right: 0;
    background: white;
    opacity: 0.3;
}

Fiddle.

Thus the :before is a brother of .div-filho and is below this without the need to z-index due to the order of the elements. Note that the .div-pai needs a position other than static, I didn’t add this to the code because your .div-pai already is fixed.
To .div-filho also needs a position other than static to appear on the :before. Otherwise, positioned elements always appear on static elements (see Stacking without z-indexin English).


For IE8 support, it is possible to use a .gif/.png with transparency as background, or apply the property filter owner of IE5-8. I was unsuccessful in applying the filter is a pseudo-element, but it works if we pollute the marking a little (by adding a div).

To test on IE8: http://jsfiddle.net/qSsC3/12/show/

<div class="div-pai">
    <div class="overlay"></div>
    <div class="div-filho"></div>
</div>

.overlay {
    content: '';
    position: absolute;
    top: 0; bottom: 0;
    left: 0; right: 0;
    background: white;

    filter: alpha(opacity=30); /* IE5-8 */
    opacity: 0.3; /* IE9+ e todos browsers modernos */
}

Or, without creating any other element, another way that works cross-browser (IE8+), using an image as background: http://jsfiddle.net/qSsC3/17/show

.div-pai:before {
    content: '';
    position: absolute;
    top: 0; bottom: 0;
    left: 0; right: 0;

    background: url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAEAAAABCAYAAAAfFcSJAAAABHNCSVQICAgIfAhkiAAAAAlwSFlzAAALEgAACxIB0t1+/AAAABx0RVh0U29mdHdhcmUAQWRvYmUgRmlyZXdvcmtzIENTNXG14zYAAAAWdEVYdENyZWF0aW9uIFRpbWUAMDIvMDMvMTSFgaz/AAAADUlEQVQImWP4//+/LwAJSQNLpIypVwAAAABJRU5ErkJggg==);
}

I encoded the image as Data-URI to make it easier to put in the answer, but it won’t make a difference linking to a file .png/.gif (except that it would generate an extra request). I will also note that IE<8 does not support Data-Uris, although I believe that few people still care about support for IE<=7.

  • worked very well your suggestions, but in ie8 I did not succeed... It would be the only solution for ie8 a background image?

  • @Denisbernardo yes, um .gif/.png with transparency would work well. Give me a second, it is possible to use the filter ie’s too.

  • 1

    Excellent solution, worked perfectly. Thanks for the help, I will no longer need to use images... !

3

It is not possible, the opacity of the children will always be relative to that of the parents. If you are needing to change only the background color, it could instead of opacity. modify the background attribute:

.div-pai {width: 400px;height: 400px; position: fixed; background-color: rgba(0, 0, 0, 0.7); }

3

In that case, I would advise using an image in . png with background opacity in the parent element, a 1px image by 1px repeating, is very light, some older browsers do not support this property.

0

Well, it’s not possible to do it the way you want, but a suggestion is to remove the div.pai and only use the div.filho and put an edge on it, which would result in the same thing, but its "central" child element would not be opaque, see the example I did on Jsfiddle

I used the following CSS code:

.div-filho{
    width: 150px;
    height: 150px;
    position:absolute;
    background: blue;
    border: 150px solid rgba(0,0,0,0.75);
}

And I re-moved the div.pai of HTML.

0

I’ve been through a similar case, but Opacity in Javascript is always inherited by the elements, there’s no way you can remove it, so what I usually do is create an element that stays exactly in the same position and dimension of the element that would be the parent with transparency, but that element is not son, is after the transparent element and contains what would be his children.

The result can be seen in this jsfiddle.

It will be compatible with all browsers and can be applied to any element.

Example:

<div class='div_transparente'></div>
<div class='div_opaca_sem_fundo_por_cima_da_div_transparente'>
    <div class='div_filho_opaca_com_preenchimento'></div>
</div>

There are several solutions to get around the problem when it’s background, but if your div is on top of an image, video, or something like that, I personally prefer this solution because it’s generic to all cases.

Browser other questions tagged

You are not signed in. Login or sign up in order to post.