htmlcsssvgbox-sizing

SVG with width 100% overflows its container


In the below snippet, adding the svg element causes a vertical scrollbar to appear. Removing the svg removes the scrollbar. I'd like to understand why its happening and whether there's a solution that isn't horrible (e.g. width:99%; height:98% solves it but thats a disgusting solution).

I can't really remove the upper DIV styling because other html structures also sit in these containers that need those to be there.

.menuquery {
  border: 1px solid #ccc;
  overflow: auto;
  box-sizing: border-box;
}

.xainnersubformdefault {
  /* allows the svg to autosize */
  width: 100%;
  height: 100%;
}

.xadatabox {
  height: 100%;
  /* essential for jtable to scroll and not leak */
}

.datachart {
  width: 100%;
  height: 100%;
  /* position:relative; */
  /* to make an svg fill its container, this is required, see stackoverflow 9566792 */
}

svg {
  width: 100%;
  height: 100%;
  border: 1px solid green;
  box-sizing: border-box;
}
<div class="menuquery" style="width:300px;height:200px">
  <div class="xa xafield xadatabox">
    <div class="xainnersubformdefault">
      <div class="datachart">
        <svg></svg>
      </div>
    </div>
  </div>
</div>

The green border and box sizing on the svg is only there so we can see the edge of the svg, it won't be needed in the end

If I change the svg to a div, and make the svg css apply to that div instead, no scrollbar appears, so there seems to be something different about the svg element.

I've tested this in firefox and IE. Both show a scrollbar, but IE shows slightly more scrollable content


Solution

  • Svg is inline element, setting font-size: 0; to .menuquery will solve this

    .menuquery {
        border: 1px solid #ccc;
        overflow: auto;
        box-sizing: border-box;
        font-size: 0;
    }
    .xainnersubformdefault {
      /* allows the svg to autosize */
      width: 100%;
      height: 100%;
    }
    
    .xadatabox {
      height: 100%;
      /* essential for jtable to scroll and not leak */
    }
    
    .datachart {
      width: 100%;
      height: 100%;
      /* position:relative; */
      /* to make an svg fill its container, this is required, see stackoverflow 9566792 */
    }
    
    svg {
      width: 100%;
      height: 100%;
      border: 1px solid green;
      box-sizing: border-box;
    }
    <div class="menuquery" style="width:300px;height:200px">
      <div class="xa xafield xadatabox">
        <div class="xainnersubformdefault">
          <div class="datachart">
            <svg></svg>
          </div>
        </div>
      </div>
    </div>


    Or you can set display:block to svg. Updated on your comment.

    .menuquery {
        border: 1px solid #ccc;
        overflow: auto;
        box-sizing: border-box;
    }
    .xainnersubformdefault {
      /* allows the svg to autosize */
      width: 100%;
      height: 100%;
    }
    
    .xadatabox {
      height: 100%;
      /* essential for jtable to scroll and not leak */
    }
    
    .datachart {
      width: 100%;
      height: 100%;
      /* position:relative; */
      /* to make an svg fill its container, this is required, see stackoverflow 9566792 */
    }
    
    svg {
      width: 100%;
      height: 100%;
      border: 1px solid green;
      box-sizing: border-box;
      display:block;
    }
    <div class="menuquery" style="width:300px;height:200px">
      <div class="xa xafield xadatabox">
        <div class="xainnersubformdefault">
          <div class="datachart">
            <svg></svg>
          </div>
        </div>
      </div>
    </div>