Daphta
Daphta

Reputation: 25

Transition not firing on hover

I'm trying to implement a sliding sidebar that activates when user hovers over .sb-toggle item. Hovering over it will cause the sidebar which is located just outside the view to slide in 10ems while also making the .content div shift to the right. But I can't get it to work properly. Transition fires for the .sb-toggle and .content items but sidebar isn't showing up.

html,
body {
  width: 100%;
  height: 100%;
  margin: 0;
  padding: 0;
}

.navbar {
  z-index: 1;
  position: fixed;
  top: 0%;
  background-color: #333;
  height: 3em;
  width: 100%;
  overflow: hidden;
  border-bottom: 1px solid grey;
}

.sidebar {
  background-color: #404040;
  width: 10em;
  height: 100%;
  position: fixed;
  margin-left: -10em;
  top: 3em;
  bottom: 0;
  -moz-transition: margin-left 0.5s ease;
  transition: margin-left 0.5s ease-in-out;
}

.sb-toggle {
  background-color: #404040;
  width: 1.5em;
  height: 100%;
  position: fixed;
  top: 3em;
  left: 0;
  -moz-transition: margin-left 0.5s ease;
  transition: margin-left 0.5s ease-in-out;
}

.content {
  margin-top: 3em;
  margin-left: 10em;
  height: inherit;
  width: inherit;
  transition: margin-left 0.5s ease-in-out;
}

.sb-toggle:hover {
  margin-left: 10em;
}

.sb-toggle:hover ~ .sidebar {
  margin-left: 0;
}

.sb-toggle:hover ~ .content {
  margin-left: 20em;
}

Edit: Here's the HTML:

<body>
    <div class="navbar"></div>
    <div class="sidebar"></div>
    <div class="sb-toggle"></div>
    <div class="content"></div>
  </body>

Upvotes: 1

Views: 224

Answers (3)

Billie Bobbel
Billie Bobbel

Reputation: 334

The sibling selector ~ is only looking forwards in the DOM and not backwards. hence the line .sb-toggle ~ .sidebar will never be executed.

From the MDN docs:

"The ~ combinator selects siblings. This means that the second element follows the first (though not necessarily immediately), and both share the same parent."

Made a tiny demo to show the mentioned behaviour: https://codepen.io/anon/pen/jREMmb

You'd either have to swap order of DOM nodes or find another route to trigger the transition

Upvotes: 0

Nikola Kirincic
Nikola Kirincic

Reputation: 3757

Place the .sb-toggle div within .sidebar, and change :hover from .sb-toggle to .sidebar.

html,
body {
  width: 100%;
  height: 100%;
  margin: 0;
  padding: 0;
}

.navbar {
  z-index: 1;
  position: fixed;
  top: 0%;
  background-color: #333;
  height: 3em;
  width: 100%;
  overflow: hidden;
  border-bottom: 1px solid grey;
}

.sidebar {
  background-color: #404040;
  width: 10em;
  height: 100%;
  position: fixed;
  margin-left: -10em;
  top: 3em;
  bottom: 0;
  -moz-transition: margin-left 0.5s ease;
  transition: margin-left 0.5s ease-in-out;
}

.sb-toggle {
  background-color: #404040;
  width: 1.5em;
  height: 100%;
  position: fixed;
  top: 3em;
  left: 0;
  -moz-transition: margin-left 0.5s ease;
  transition: margin-left 0.5s ease-in-out;
}

.content {
  margin-top: 3em;
  margin-left: 10em;
  height: inherit;
  width: inherit;
  transition: margin-left 0.5s ease-in-out;
}

.sb-toggle:hover {
  margin-left: 10em;
}

.sidebar:hover {
  margin-left: 0;
}

.sidebar:hover ~ .content {
  margin-left: 20em;
}
<body>
    <div class="navbar"></div>
    <div class="sidebar">
     <div class="sb-toggle"></div>
    </div>
   
    <div class="content"></div>
  </body>

Upvotes: 1

g-dg
g-dg

Reputation: 283

You need to explicitly specify the starting point as well as the ending point.

For example:

.sb-toggle {
  /* other stuff */
  margin-left: 0; /* <-- You need to add this */
  -moz-transition: margin-left 0.5s ease;
  transition: margin-left 0.5s ease-in-out;
}

Upvotes: 0

Related Questions