CSS Gridでカード一覧を作ったとき、「列はそろっているのにカードの高さがバラバラ」「ボタン位置がずれる」という悩みはよくあります。Gridは強力ですが、何もしなくても中身まできれいに揃えてくれるわけではありません。
この記事では、CSS Gridで高さが揃わない原因を5つに分けて、実務で使いやすい修正パターンまでまとめます。
CSS Gridの高さは何で決まる?
Gridの各行の高さは、基本的にその行の中で一番高いアイテムに合わせて決まります。ただし、カード内のボタン位置、画像比率、本文量、align-items、入れ子レイアウトの影響で「揃っていないように見える」ことがあります。
原因1:カード内の構造が揃っていない
カードそのものの高さは揃っていても、本文量が違うとボタンや日付の位置がズレます。この場合は、カードをFlexbox化して、最後の要素にmargin-top: autoを指定します。
<section class="cards">
<article class="card">
<p class="card__label">CSS GRID</p>
<h2>短いカード</h2>
<p>本文が短いカードです。</p>
<a href="#">詳しく見る</a>
</article>
<article class="card">
<p class="card__label">LAYOUT</p>
<h2>本文が長いカード</h2>
<p>本文量が増えると、カードの高さやボタン位置が揃わず、一覧の見た目が乱れることがあります。</p>
<a href="#">詳しく見る</a>
</article>
<article class="card">
<p class="card__label">UI</p>
<h2>画像付きカード</h2>
<p>高さを揃えるには、グリッドだけでなくカード内の構造も大切です。</p>
<a href="#">詳しく見る</a>
</article>
</section>.cards {
display: grid;
grid-template-columns: repeat(3, 1fr);
gap: 24px;
}
.card {
padding: 20px;
border: 2px solid #111;
background: #fff;
}.cards {
display: grid;
grid-template-columns: repeat(auto-fit, minmax(min(100%, 260px), 1fr));
gap: 24px;
align-items: stretch;
}
.card {
display: flex;
flex-direction: column;
min-height: 100%;
padding: 20px;
border: 2px solid #111;
background: #fff;
}
.card a {
width: fit-content;
margin-top: auto;
padding: 10px 16px;
border-radius: 999px;
background: #111;
color: #fff;
text-decoration: none;
}原因2:align-items:start を指定している
Gridコンテナにalign-items: startを指定すると、各アイテムは中身の高さのままになります。カードの背景や枠線を同じ高さに見せたい場合は、align-items: stretchに戻します。
.cards {
display: grid;
align-items: stretch;
}
原因3:画像の高さや比率がバラバラ
カード上部の画像サイズが揃っていないと、その下の本文位置もズレます。画像にはaspect-ratioとobject-fitをセットで指定すると安定します。
.card img {
width: 100%;
aspect-ratio: 16 / 9;
object-fit: cover;
}
原因4:grid-auto-rowsの意図が違う
grid-auto-rows: 1frを使うと行の高さを揃えやすくなりますが、複数行のグリッドでは全行が同じ高さになり、余白が増えすぎることがあります。カード一覧では、まずカード内部をFlexboxで整える方が扱いやすいです。
原因5:min-heightだけで解決しようとしている
min-heightは最低限の高さを確保する指定です。本文量が増えたカードには追従しますが、ボタン位置までは揃えてくれません。高さを固定するより、内部レイアウトで押し下げる考え方の方が破綻しにくいです。
実務で使うならこの形
カード一覧では、Gridで列を作り、カード内部はFlexboxで縦に積む構成が安定します。
.cards {
display: grid;
grid-template-columns: repeat(auto-fit, minmax(min(100%, 280px), 1fr));
gap: 24px;
}
.card {
display: flex;
flex-direction: column;
min-height: 100%;
}
.card__footer {
margin-top: auto;
}
CodePen埋め込み用エリア
CodePenでは、上のindex.htmlをHTMLパネルへ、bad.cssとgood.cssをCSSパネルへ貼り替えてください。本文量が違うカードで、ボタン位置が揃うかを見ると理解しやすいです。
まとめ
CSS Gridで高さが揃わないときは、Gridだけを疑うのではなく、カード内の縦並び、画像比率、align-items、min-heightの使い方を順番に確認しましょう。Gridで外側、Flexboxで内側を整えるのが、いちばん現場向きです。
