I have a canvas element inside a flexbox that may be resized. How do I get the canvas to fill the available space without losing its aspect ratio (2/3), and without being cut off?
(I want to change the CSS dimensions, not the canvas resolution).
I've tried using object-fit: contain and clamp(...), but I can't get the results I want. Either the canvas doesn't maintain its aspect ratio, or it grows outside its container.
body {
margin: 0;
}
#mainContent {
background: grey;
height: 100vh;
display: flex;
flex-wrap: nowrap;
align-items: center;
}
#someOtherElem {
background: red;
width: 200px;
height: 200px;
margin-left: 1rem;
}
#canvasContainer {
display: flex;
flex: 1;
height: 100%;
justify-content: center;
align-items: center;
}
canvas {
width: calc(100% - 2rem);
height: calc(100% - 2rem);
background: green;
object-fit: contain;
}
<div id="mainContent">
<div id="someOtherElem"></div>
<div id="canvasContainer">
<canvas height="300" width="200"></canvas>
</div>
</div>
Here's a stripped-down version of what I've been trying: https://jsfiddle.net/mwq4502v/.
I'm not sure what the best way to achieve this is, so any help would be greatly appreciated!
You can specify an
aspect-ratioof2 / 3forcanvasand a width of100%or<parent-height> * 2 / 3, whichever smaller.Some math:
Let the width and height of the container be
wandh, correspondingly. Since the canvas needs to be as large as possible it will always touch at least two borders of the container (or all 4), which means its size can be eitherw / (w / (2 / 3))or(h * 2 / 3) / h, depends on the size of the container.w / h>2 / 3:w / h<2 / 3:This means the width needs to be
min(w, h * 2 / 3)or, in CSS,min(100%, 100vh * 2 / 3).Try it: