Mar Dev Mar Dev - 2 months ago 7
HTML Question

How does changing the display attribute in the styling of an element hide/show it?

I'm following this tutorial on how to create a CSS dropdown menu. Currently the method stated does not use any JavaScript (only HTML and CSS). Here is the method suggested, excluding the color/background color/font/etc.



.dropdown {
position: relative;
display: inline-block;
}

.dropdown-content {
display: none;
position: absolute;
}

.dropdown-content a {
display: block;
}

.dropdown:hover .dropdown-content {
display: block;
}

<div class="dropdown">
<button class="dropbtn">Dropdown</button>
<div class="dropdown-content">
<a href="#">Link 1</a>
<a href="#">Link 2</a>
<a href="#">Link 3</a>
</div>
</div>




As you can see, the Dropdown button appears, and when one hovers over it, the list items are shown. The only styling applied when an element is hovered over is

.dropdown:hover .dropdown-content {
display: block;
}


How does this work? (the w3schools tutorial did not describe the reasoning behind the display styling)

When I ran the above snippet, I was expecting the list items to be shown inline and then, when the button is hovered over, to be shown as a block under the button (thus I was expecting the list items to never be hidden). What is making these list items hidden by default?

Furthermore, if I am applying the
display: block
styling on the div element (the one with the class dropdown), then how come when I hover over the empty space still physically under the button, however to the right of the list text, the
display: block
styling is undone (and the list items vanish)? I would expect the div element to take up an area in the shape of a rectangle (where even hovering over the white part of the rectangle would trigger :hover). *

* I may need to clarify this entire part of my question, please say so if I need to.

Answer

The .dropdown-content is hidden by default:

.dropdown-content {
  display: none;
}

The later rule overrides that and shows the content when the pointer hovers over the parent .dropdown:

.dropdown:hover .dropdown-content {
  display: block;
}

This rule applies to any .dropdown-content within a .dropdown that is in the hover state.

To answer the second question, it's because of the position: absolute that the white-space next to the child items don't maintain the hover state. See the snippet below, which includes outlines to show the boundaries of each element. As long as the pointer is within the blue (parent) box or the red (child) box, the hover state is maintained.

.dropdown {
    position: relative;
    display: inline-block;
    outline: solid 1px blue;
}

.dropdown-content {
    display: none;
    position: absolute;
    outline: solid 1px red;
}

.dropdown-content a {
    display: block;
    background: yellow;
}

.dropdown:hover .dropdown-content {
    display: block;
}
<div class="dropdown">
    <button class="dropbtn">Dropdown</button>
    <div class="dropdown-content">
        <a href="#">Link 1</a>
        <a href="#">Link 2</a>
        <a href="#">Link 3</a>
    </div>
</div>

Comments