A method to fit every picture aesthetically pleasing in a predefined space in your layout
Recently at work I was tasked to implement an image into a profile page. Said image would live in a predefined container, that had a rigid aspect ratio. Only problem being that the images, coming in from the various owners of the profiles, would all have varying aspect ratios. Some would only display one person, while other profiles belonged to groups of people that, in return, had the requirement to fit them all on the picture.
My CSS3-soaked thoughts obviously ventured to object-fit: cover;
first, but this time that wouldn’t have been the right choice as I had to make shure that all important facial features made it into the frame, every time.
While the group-image turned out servicable, the single-person portrait gets chopped to an almost brutal extend, losing the forehead and parts of the hand on the chin.
To solve this problem we simply steal a rather old trick from desperate documentary-filmmakers that have to fit really old footage into modern aspect ratios. We object-fit: contain
the image in question (CSS3-soaked thoughts, see?). Then we fill the inevitable black bars with a darkned and more importantly blurred version of the image:
The markup to do this is as follows:
<div class="imgcontainer">
<img src="path/to/img" class="objectfitcover withfilters" />
<img src="path/to/img" class="objectfitcontain" />
</div>
The .imgcontainer
holds it all togther and defines the overal space the composition inhabits.
.imgcontainer {
width: 100%;
height: 18rem;
overflow: hidden;
position: relative;
}
The images within the container both have to be positioned absolute and adjusted in with and height.
.imgcontainer {
img {
width: 100%;
height: 100%;
position: absolute;
}
}
We now have to give them thier respective object-fit
properties. The second image in the markup should be the one to recieve the contain
value, unless you want to invite some z-index-trickery to your code.
.objectfitcover {
object-fit: cover;
}
.objectfitcontain {
object-fit: contain;
}
After that, there’s only one fun thing to do. Apply all the filters!
.objectfitcover.withfilters {
filter: blur(15px) brightness(70%);
transform: scale(1.1);
}
I’ve chosen to blur with 15px
and to reduce the brightness to 70%
, but you should play around with your code to fit it to your usecase and desing! We also scale the blurred image by 110% (i.e. we ‘zoom in’ a bit) to get rid of the blurred border that would otherwise be occurring.
And even performance wise we don’t have to worry. As we are requesting the exact same image twice, the browser is caching the image and simply reapeating it out of memory (given your site has cooperating caching headers, which it should).
One last warning though: If you have to support older browsers, this might not be for you, as some of them are not able to handle object-fit
properties.
As always if you want to have a look at the code from the images above or fork my CodePen, you are very much welcome to! Have a good one!
CodePen Embed
Klick below to show the CodePen as an embed. CodePen will set set several Cookies in your Browser.