CSS: Prevent parent element getting :active pseudoclass when child element is clicked

后端 未结 12 826
暖寄归人
暖寄归人 2021-01-07 16:19

JSFiddle

When you click the button, you see that :active pseudoclass is triggered for the parent div. Is ther

相关标签:
12条回答
  • 2021-01-07 16:51

    Instead of div:active {...} you should code div:active:not(:hover) {...} and the background-color stays untouched.

    (old snippet removed)

    UPDATE

    To keep the main div behaviour intact and a more generic approach I usually create several layers.

    Check the snippet below, toggling to green is just to prove that it works while position and abolute are just quick and dirty for now:

    #layer-data {
      width: 200px;
      height: 200px;
      background-color: #eee;
      border: 1px solid black;
    }
    #layer-data:active {
      background-color: red
    }
    #layer-btns:active {
      background-color: green
    }
    #layer-btns {
      z-index: 1;
      position: absolute;
      top: 1px;
      left: 1px;
      background: transparent;
      padding: 5px;
      width: auto;
      height: auto
    }
    #layer-data {
      z-index: 0;
      position: absolute;
      top: 0;
      left: 0;
      text-align: center;
      line-height: 200px
    }
    <div id="layer-btns">
      <button>Qlick me</button>
      <br/>
      <button>Qlick me too</button>
      <br/>
      <button>Qlick me three</button>
    </div>
    
    <div id="layer-data">
      some data-layer
    </div>

    0 讨论(0)
  • 2021-01-07 16:57

    From the spec:

    Selectors doesn't define if the parent of an element that is ‘:active’ or ‘:hover’ is also in that state.

    That means it's implementation dependent. If an implementation chose to act this way (as current browsers obviously do), there's nothing in the standard that can change that.

    With CSS4, you might be able to do:

    .parent:active:not(:has(:active)) {
       color: red;
    }
    

    but that is neither available nor finalized yet.

    0 讨论(0)
  • 2021-01-07 16:57

    As far as I know, the the active state will bubble up. So all parent nodes will have an active state.

    Therefore, I don't now of a pure CSS solution. You can avoid a javascript solution (which I assume is what you're really after), by altering the markup so that the div that has an active state is no longer a parent of the button. You can make them siblings, for example.

    The CSS part of that solution is then fixing the layout so it appears the same now that they are sibilings as what it did when they were parent>child.

    Without seeing a fiddle of what you're working with, I can't offer you a more specific solution I'm afraid.

    0 讨论(0)
  • 2021-01-07 17:00

    here's a jquery solution instead of using the css pseudo class :active

    $(document).ready(function() {
        $('button').mousedown(function(e){
            e.stopPropagation();
            console.log('i got clicked');
        });
    
        $('div').mousedown(function(e){
            $('div').css('background', 'red')
        }).mouseup(function(e){
            $('div').css('background', '#eee')
        });
        $(document).mouseup(function(e){
            $('div').css('background', '#eee')
        });
    });
    div {
      width: 200px;
      height: 200px;
      background-color: #eee;
      border: 1px solid black;
    }
    <script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
    <div>
      <button>Qlick me</button>
    </div>

    0 讨论(0)
  • 2021-01-07 17:00

    CSS pseudo-elements are incredibly useful -- they allow us to create CSS triangles for tooltips and perform a number of other simple tasks while preventing the need for additional HTML elements. To this point, these pseudo-element CSS properties have been unreachable by JavaScript but now there's a method for getting them!

    Check this:

    http://davidwalsh.name/pseudo-element

    http://davidwalsh.name/ways-css-javascript-interact

    0 讨论(0)
  • 2021-01-07 17:01

    There doesn't seem to any CSS way to handle this case. (not sure about CSS4, the way Amit has suggested.) So here is JQuery way.

    The idea is you handle mousedown and mouseup events at 3 levels:

    1. the parent div
    2. the button where you don't want the active state propagated to parent div (".btn1" in the example below)
    3. any other children except the button in second condition. (".btn2" in the example below)

    JS Fiddle

    HTML:

    <div>
      <button class="btn1">Qlick me1</button>
      <button class="btn2">Qlick me2</button>
    </div>
    

    JQuery:

    $(function(){
        $('div').each(function(e){
            $(this).mousedown(function(e){
                $(this).addClass("activeClass");
            }).mouseup(function(e){
                $(this).removeClass("activeClass");
            });
        });
        $('div .btn1').each(function(e){
            $(this).mousedown(function(e){
                e.stopPropagation();
            }).mouseup(function(e){
                e.stopPropagation();
            });
        });
        $('div :not(.btn1)').each(function(e){
            $(this).mousedown(function(e){
                $(this).parent().addClass("activeClass");
            }).mouseup(function(e){
                $(this).parent().removeClass("activeClass");
            });
        });
    });
    

    CSS:

    div {
      width: 200px;
      height: 200px;
      background-color: #eee;
      border: 1px solid black;
    }
    .activeClass {
      background-color: red;
    }
    
    0 讨论(0)
提交回复
热议问题