title: Why is a margin-top percentage using height and how can I work around it?
body: <p>I have a CSS slide down menu that can vary in the number of elements displayed.</p>
  
  <p>I use an <code>overflow: hidden</code> wrapper and <code>margin-top: -100%</code> to hide the menu, and a CSS transition with <code>margin-top: 0</code> to animate the slide down.</p>
  
  <p>The problem appears to be that <code>margin-top: -100%</code> seems to be picking up the explicit <code>width</code> of any parent element and ignoring the content height.</p>
  
  <p><div class="snippet" data-lang="js" data-hide="false" data-console="true" data-babel="false">
  <div class="snippet-code">
  <pre class="snippet-code-css lang-css prettyprint-override"><code>.outer {
    overflow: hidden;
    border: 10px solid red;
    cursor: pointer;
  }
  .outer &gt; .slide {
    margin-top: -100%;
    transition-property: margin-top;
    transition-duration: 1s;
  }
  .outer:hover &gt; .slide {
    margin-top: 0;
  }
  .outer.bug {
    width: 100px;
  }</code></pre>
  <pre class="snippet-code-html lang-html prettyprint-override"><code>&lt;div class="outer"&gt;
    &lt;div class="slide"&gt;
      &lt;ul&gt;
        &lt;li&gt;
          Ayy
        &lt;/li&gt;
        &lt;li&gt;
          Bee
        &lt;/li&gt;
        &lt;li&gt;
          See
        &lt;/li&gt;
        &lt;li&gt;
          Dee
        &lt;/li&gt;
        &lt;li&gt;
          Eee
        &lt;/li&gt;
        &lt;li&gt;
          Eff
        &lt;/li&gt;
        &lt;li&gt;
          Gee
        &lt;/li&gt;
      &lt;/ul&gt;
    &lt;/div&gt;
  &lt;/div&gt;
  
  &lt;div class="outer bug"&gt;
    &lt;div class="slide"&gt;
      &lt;ul&gt;
        &lt;li&gt;
          Ayy
        &lt;/li&gt;
        &lt;li&gt;
          Bee
        &lt;/li&gt;
        &lt;li&gt;
          See
        &lt;/li&gt;
        &lt;li&gt;
          Dee
        &lt;/li&gt;
        &lt;li&gt;
          Eee
        &lt;/li&gt;
        &lt;li&gt;
          Eff
        &lt;/li&gt;
        &lt;li&gt;
          Gee
        &lt;/li&gt;
      &lt;/ul&gt;
    &lt;/div&gt;
  &lt;/div&gt;</code></pre>
  </div>
  </div>
  </p>
  
  <p>Run that snippet and you should see two red boxes, mouse over either to get the slide down menu.</p>
  
  <p>The problem is the second box - the only difference is that the parent has <code>width: 100px;</code> set. </p>
  
  <p>If you inspect the second box you should see that the <code>margin-top: -100%;</code> has been calculated as -100px. </p>
  
  <p>In fact any explicit or inherited width against the parent div will become the negative margin.</p>
  
  <p>The only way I've found round it is to explicitly set the <code>margin-top</code> to be the same as the height of the sliding menu, but that involves DOM layout and JS that I don't really want to do for each menu.</p>
  
  <p>Is this a bug in how browsers handle negative percentages on margin-top? IE11, Chrome and FX all seem to treat it the same way.</p>
  
  <p>Is there a better way around it that doesn't require an explicit height calculation and additional Javascript?</p>