CSS

CSSサイドバー付き2カラムレイアウトの作り方

CSSでメインコンテンツとサイドバーの2カラムレイアウトを作る方法を20パターンで解説します。Gridとflex、左サイドバー、sticky、スマホ1列、崩れ対策まで紹介します。

この記事の目次
  1. 1. Gridで作る基本の2カラム
  2. 2. 左サイドバーの2カラム
  3. 3. flexで作る2カラム
  4. 4. 70%と30%の比率で分ける
  5. 5. サイドバー幅をclampで可変にする
  6. 6. 最大幅つきの2カラム
  7. 7. stickyサイドバー
  8. 8. 固定ヘッダーがあるときのsticky位置
  9. 9. サイドバーをスマホでは下に回す
  10. 10. サイドバーをスマホでは上に出す
  11. 11. サイドバー内をカードで分ける
  12. 12. 目次サイドバー
  13. 13. 広告枠つきサイドバー
  14. 14. メインが狭くなりすぎない2カラム
  15. 15. 画像や長いURLではみ出すときの対策
  16. 16. サイドバーを非表示にするブレイクポイント
  17. 17. サイドバーを横スクロール領域にする
  18. 18. 3カラムに拡張できるGrid
  19. 19. CSS変数で幅と余白を管理する
  20. 20. 2カラムの最小テンプレート
  21. 2カラムレイアウトが崩れる原因
  22. まとめ

ブログ、メディア、管理画面では、メインコンテンツとサイドバーを並べる2カラムレイアウトがよく使われます。

この記事では、CSSで作るサイドバー付き2カラムレイアウトを20パターンに分けて紹介します。Grid、flex、左サイドバー、stickyサイドバー、スマホ1列、崩れ対策まで、コピーして使いやすい形にまとめます。

1. Gridで作る基本の2カラム

メインは可変、サイドバーは固定幅にする定番の形です。

<div class="layout-two-column">
  <main>メインコンテンツ</main>
  <aside>サイドバー</aside>
</div>
.layout-two-column {
  display: grid;
  gap: 32px;
}

@media (min-width: 960px) {
  .layout-two-column {
    grid-template-columns: minmax(0, 1fr) 300px;
  }
}

スマホでは1列、PCでは2カラムになります。

2. 左サイドバーの2カラム

サイドバーを左に置きたい場合は、列の順番を入れ替えます。

<div class="layout-left-sidebar">
  <aside>サイドバー</aside>
  <main>メインコンテンツ</main>
</div>
.layout-left-sidebar {
  display: grid;
  gap: 32px;
}

@media (min-width: 960px) {
  .layout-left-sidebar {
    grid-template-columns: 280px minmax(0, 1fr);
  }
}

HTMLの順番も左サイドバー、メインの順にすると理解しやすいです。

3. flexで作る2カラム

flexでもメインとサイドバーを横並びにできます。

<div class="layout-flex-column">
  <main>メインコンテンツ</main>
  <aside>サイドバー</aside>
</div>
.layout-flex-column {
  display: flex;
  gap: 32px;
}

.layout-flex-column main {
  flex: 1;
  min-width: 0;
}

.layout-flex-column aside {
  flex: 0 0 300px;
}

@media (max-width: 959px) {
  .layout-flex-column {
    flex-direction: column;
  }
}

flexでは、メイン側の min-width: 0; が崩れ対策として重要です。

4. 70%と30%の比率で分ける

サイドバー幅を固定せず、割合で分ける方法です。

.layout-ratio {
  display: grid;
  gap: 32px;
}

@media (min-width: 960px) {
  .layout-ratio {
    grid-template-columns: 7fr 3fr;
  }
}

比率指定は画面幅に応じて両方が伸びるため、固定幅より柔らかいレイアウトになります。

5. サイドバー幅をclampで可変にする

サイドバーを画面幅に合わせて少しだけ可変にしたい場合の例です。

.layout-clamp-sidebar {
  display: grid;
  gap: 32px;
}

@media (min-width: 960px) {
  .layout-clamp-sidebar {
    grid-template-columns: minmax(0, 1fr) clamp(240px, 28vw, 340px);
  }
}

clamp() を使うと、最小幅・可変幅・最大幅をまとめて指定できます。

6. 最大幅つきの2カラム

画面いっぱいに広げず、中央に最大幅を持たせる形です。

<div class="layout-container">
  <main>メイン</main>
  <aside>サイドバー</aside>
</div>
.layout-container {
  display: grid;
  gap: 32px;
  max-width: 1120px;
  margin: 0 auto;
  padding: 0 20px;
}

@media (min-width: 960px) {
  .layout-container {
    grid-template-columns: minmax(0, 1fr) 300px;
  }
}

実サイトでは、最大幅と左右余白をセットで考えると安定します。

7. stickyサイドバー

目次やプロフィールをスクロールに追従させたい場合は、position: sticky; を使います。

<aside class="sidebar">
  <div class="sidebar-sticky">目次</div>
</aside>
.sidebar-sticky {
  position: sticky;
  top: 24px;
}

親要素に overflow: hidden; などがあると、stickyが効かないことがあります。

8. 固定ヘッダーがあるときのsticky位置

固定ヘッダーがある場合は、ヘッダーの高さ分だけ top を空けます。

.sidebar-sticky-with-header {
  position: sticky;
  top: 88px;
}

固定ヘッダーと重ならないように、top を調整します。

9. サイドバーをスマホでは下に回す

HTMLでメインを先に書いておくと、スマホで本文の下にサイドバーが来ます。

<div class="layout-sidebar-bottom">
  <main>本文</main>
  <aside>関連記事</aside>
</div>
.layout-sidebar-bottom {
  display: grid;
  gap: 32px;
}

@media (min-width: 960px) {
  .layout-sidebar-bottom {
    grid-template-columns: minmax(0, 1fr) 300px;
  }
}

本文を優先して読ませたいブログでは、この順番が扱いやすいです。

10. サイドバーをスマホでは上に出す

検索や絞り込みを先に使わせたい場合は、スマホでサイドバーを上に出します。

<div class="layout-sidebar-top">
  <main>商品一覧</main>
  <aside>絞り込み</aside>
</div>
.layout-sidebar-top {
  display: grid;
  gap: 24px;
}

.layout-sidebar-top aside {
  order: -1;
}

@media (min-width: 960px) {
  .layout-sidebar-top {
    grid-template-columns: minmax(0, 1fr) 300px;
  }

  .layout-sidebar-top aside {
    order: 0;
  }
}

絞り込みUIでは、スマホで先に表示した方が使いやすい場合があります。

11. サイドバー内をカードで分ける

プロフィール、カテゴリ、人気記事などをカードとして並べる例です。

<aside class="sidebar-cards">
  <section>プロフィール</section>
  <section>カテゴリ</section>
  <section>人気記事</section>
</aside>
.sidebar-cards {
  display: grid;
  gap: 16px;
}

.sidebar-cards section {
  padding: 18px;
  background: #fff;
  border: 1px solid #e5e7eb;
  border-radius: 8px;
}

カード単体の装飾は、CSSカードデザイン集 に分けるとよいです。

12. 目次サイドバー

記事ページで使いやすい、目次用サイドバーの例です。

<aside class="toc-sidebar">
  <p>目次</p>
  <a href="#sec1">基本</a>
  <a href="#sec2">応用</a>
  <a href="#sec3">まとめ</a>
</aside>
.toc-sidebar {
  display: grid;
  gap: 10px;
  padding: 18px;
  background: #f8fafc;
  border-radius: 8px;
}

.toc-sidebar p {
  margin: 0;
  font-weight: 700;
}

.toc-sidebar a {
  color: #475569;
  text-decoration: none;
}

リンク数が多い場合は、余白を詰めすぎないようにします。

13. 広告枠つきサイドバー

広告やバナー枠を置く場合は、枠のサイズを安定させます。

<aside class="ad-sidebar">
  <div class="ad-box">広告枠</div>
</aside>
.ad-box {
  display: grid;
  place-items: center;
  min-height: 250px;
  color: #64748b;
  background: #f1f5f9;
  border: 1px dashed #cbd5e1;
  border-radius: 8px;
}

広告枠は高さが急に変わるとレイアウトが揺れるため、最小高さを決めておくと安心です。

14. メインが狭くなりすぎない2カラム

サイドバーが広すぎると本文が読みにくくなるため、メイン側に最小幅を意識します。

.layout-readable {
  display: grid;
  gap: 32px;
}

@media (min-width: 1040px) {
  .layout-readable {
    grid-template-columns: minmax(620px, 1fr) 280px;
  }
}

本文が主役のページでは、サイドバーよりメインの読みやすさを優先します。

15. 画像や長いURLではみ出すときの対策

メインカラム内の画像や長い文字が原因で、2カラムが崩れることがあります。

.layout-overflow-fix {
  display: grid;
  gap: 32px;
  grid-template-columns: minmax(0, 1fr) 300px;
}

.layout-overflow-fix main {
  min-width: 0;
}

.layout-overflow-fix img {
  max-width: 100%;
  height: auto;
}

.layout-overflow-fix p {
  overflow-wrap: anywhere;
}

minmax(0, 1fr)min-width: 0; が効きます。

16. サイドバーを非表示にするブレイクポイント

スマホではサイドバーを非表示にする設計もあります。

.layout-hide-sidebar {
  display: block;
}

.layout-hide-sidebar aside {
  display: none;
}

@media (min-width: 960px) {
  .layout-hide-sidebar {
    display: grid;
    grid-template-columns: minmax(0, 1fr) 300px;
    gap: 32px;
  }

  .layout-hide-sidebar aside {
    display: block;
  }
}

重要な情報をサイドバーだけに置くと、スマホで見えなくなるため注意します。

17. サイドバーを横スクロール領域にする

タグやカテゴリだけなら、スマホでは横スクロールにする方法もあります。

.mobile-filter-list {
  display: flex;
  gap: 8px;
  overflow-x: auto;
  padding-bottom: 8px;
  white-space: nowrap;
}

.mobile-filter-list a {
  flex: 0 0 auto;
  padding: 8px 12px;
  color: #334155;
  text-decoration: none;
  background: #f1f5f9;
  border-radius: 9999px;
}

カテゴリタグの見た目は、CSSバッジ・ラベル・タグデザイン集 と相性がよいです。

18. 3カラムに拡張できるGrid

将来、左右にサイドバーを置く可能性がある場合の土台です。

<div class="layout-three-ready">
  <aside>左</aside>
  <main>メイン</main>
  <aside>右</aside>
</div>
.layout-three-ready {
  display: grid;
  gap: 24px;
}

@media (min-width: 1120px) {
  .layout-three-ready {
    grid-template-columns: 220px minmax(0, 1fr) 280px;
  }
}

この記事の主役は2カラムですが、Gridなら3カラムへの拡張もしやすいです。

19. CSS変数で幅と余白を管理する

複数ページで使い回すなら、サイドバー幅や余白を変数にします。

.layout-variable {
  --sidebar-width: 300px;
  --layout-gap: 32px;

  display: grid;
  gap: var(--layout-gap);
}

@media (min-width: 960px) {
  .layout-variable {
    grid-template-columns: minmax(0, 1fr) var(--sidebar-width);
  }
}

ページごとに幅を変える場合も、変数なら調整しやすくなります。

20. 2カラムの最小テンプレート

最後に、まずコピーするならこの形です。

<div class="layout-template">
  <main>メインコンテンツ</main>
  <aside>サイドバー</aside>
</div>
.layout-template {
  display: grid;
  gap: 32px;
  max-width: 1120px;
  margin: 0 auto;
  padding: 0 20px;
}

@media (min-width: 960px) {
  .layout-template {
    grid-template-columns: minmax(0, 1fr) 300px;
  }
}

スマホ1列、PC2カラム、最大幅ありの実用的なテンプレートです。

2カラムレイアウトが崩れる原因

  • スマホでも2カラムのままにしている
  • サイドバー幅が広すぎて、メインが狭くなっている
  • メインカラムに長いURLや大きな画像が入っている
  • minmax(0, 1fr)min-width: 0; がない
  • 余白を含めた合計幅が親要素を超えている

まとめ

サイドバー付き2カラムは、スマホでは1列、PCではメインとサイドバーに分けるのが基本です。

Gridなら grid-template-columns: minmax(0, 1fr) 300px;、flexならメインに min-width: 0; を入れると崩れにくくなります。

Gridの詳しい使い方は CSS Gridの使い方、flexの詳しい使い方は CSS flexの使い方 に分けると記事同士の役割が明確になります。