The IBM Carbon Design System, built on the principles of the IBM Design Language, is driven by precision and scalability. At the core of this system is the 2x Grid, which dictates the structure and rhythm of all visual elements. One of the most intriguing components within this system is the aspect ratio card — cards that maintain a consistent aspect ratio while flexibly adapting to their content. These cards are vital in ensuring design integrity and visual rhythm across varying layouts, devices, and screen sizes.
I’ve always been fascinated by how aspect ratio cards keep their shape while expanding with the content inside them. This ability to dynamically grow based on content needs is essential for readability and usability. I first set out to solve this in Figma, and later decided to bring the concept to life in code for my own learning.
The Problem: Maintaining Aspect Ratios Without Truncation or Overflow
Aspect ratio cards are crucial for creating fluid layouts while maintaining visual consistency. The challenge is ensuring the cards are responsive enough to adapt to growing content without causing overflow.
In Figma, this problem is particularly tricky because Figma doesn’t natively support aspect ratios. In Figma, there isn’t a native feature for aspect ratios, which presents a challenge when designing responsive layouts. I knew I needed to get creative and was familiar with the aspect ratio component by Vitalii from the Figma community. It became my starting point.
My first attempt was to absolute position the content on top of the aspect ratio. While this approach maintained the ratio, it didn’t allow the card to grow as the content inside expanded, which was a crucial requirement. The card’s height needed to dynamically adapt to its content while preserving its aspect ratio — an essential feature for creating fluid, scalable, and accessible designs.
In code, maintaining aspect ratios while balancing dynamic content is much simpler with technologies like CSS Grid and Flexbox, but is still not without its challenges, especially when dealing with cross-browser inconsistencies — looking at you, Safari!
The Goal: A Scalable Solution in Figma
The primary objective was to create a scalable aspect ratio card solution in Figma that would adapt dynamically to its content without losing its shape or causing the contents to overflow. I wanted the cards to grow in height based on their content, but still maintain their defined aspect ratio — something Figma’s native tools don’t directly offer.
The Figma Approach: Using Negative Space Between
After realizing the limitations of my first approach, I experimented with various methods and stumbled upon an underutilized technique in Figma — negative space between. By strategically adding negative space between, I discovered that the contents inside the container would overlap, aligning to the top as their limit, allowing the card to expand in height as necessary based on the tallest element inside. This element would of course be the height of the content, or the height of the aspect ratio, based on the aspect ratio’s width.
This solution was perfect. It preserved the aspect ratio and enabled the content to influence the card’s height without breaking the layout. The flexibility it offered made it versatile enough for a variety of use cases, and I was quite proud of the final outcome.
Check out the Figma file here.
The Code Approach: A Learning Experience
Since solving this challenge in Figma, I’ve had the urge to challenge myself and bring this concept to life in code. This behavior already exists in Carbon, but I wanted to do it without looking at any of their code to test my own hypothesis. As someone with a passion for both design and front-end development, I wanted to see how my assumptions played out in a live environment. I built the cards using CSS Grid and Flexbox, and worked out a few kinks to ensure the aspect ratios stayed intact as the content grew. I specifically needed to include an @supports for Safari. This CSS is essential for Safari, but breaks the working cards in Chrom and Firefox. Targeting Safari was critical. Thanks for the help targeting Safari exclusively, Wojtek Witkowski.
@supports (hanging-punctuation: first) and (font: -apple-system-body) and
(-webkit-appearance: none) {
.card {
min-height: fit-content;
height: calc(100% - 2rem);
}
}
Getting the Cards to Be the Same Height Throughout the Grid
The HTML and CSS approach alone is great, but doesn’t only equalizes the height of the cards per row. This may be enough for some systems, but for Carbon, it’s essential that the height of all cards in the grid be equalized. I added some JavaScript to ensure the cards in the grid row maintained a consistent height.
Check out the code here.
Final Thoughts: Bridging Design and Development
This project was a great opportunity to blend my skills as both a designer and developer. I love finding creative ways to solve design challenges in Figma and then translating those solutions into code to test their real-world viability. If you’re a designer or developer facing similar challenges, I hope this post provides some inspiration and practical insight.
Check out the CodePen here and the Figma file here.
Happy designing and coding!