CSS / paddingとmargin:余白の指定・幅の計算・マージンの相殺
CSSの padding は内容と境界線の間にある内側の余白で、margin は境界線の外側の余白です。背景を含む要素の内側を広げるにはpaddingを、周囲の要素との間隔を調整するにはmarginを使います。実際の幅は box-sizing によって変わり、条件を満たす縦方向のマージンは単純に加算されず相殺される場合があります。
paddingとmarginの違い
要素のボックスは、内側から外側に向かって、コンテンツ、パディング、ボーダー、マージンで構成されます。背景は通常パディングまで広がりますが、マージンは透明です。ボタンのパディングを増やすと、背景とクリック可能なボックスが通常拡大します。マージンを追加しても、その外側の空白はクリック可能になりません。
| 特徴 | パディング | マージン |
|---|---|---|
| 位置 | コンテンツとボーダーの間 | ボーダーの外側 |
| 通常の背景色 | パディングにも塗られる | 透明 |
| 負の値 | 許可されていません | 許可されています |
| auto | 許可されていません | 許可されている; レイアウト規則に応じて計算されます |
両方のプロパティはpx、rem、%のような値を受け入れますが、padding: autoや負のパディングは無効です。通常の横書きモードでの物理的な間隔プロパティの場合、パーセンテージ値は上下の値を含む包含ブロックの幅を指します。それらは高さのパーセンテージではありません。W3Cボックスモデルと間隔の定義
一つから四つの値の方向を読む
四つの値の省略形は上から始まり、時計回りに進みます:右、下、左。二つの値は縦と横を意味し、三つの値は上、横、下を意味します。同じルールがパディングとマージンにも適用されます。
| 例 | 上 | 右 | 下 | 左 |
|---|---|---|---|---|
padding: 10px |
10px | 10px | 10px | 10px |
padding: 10px 20px |
10px | 20px | 10px | 20px |
padding: 10px 20px 30px |
10px | 20px | 30px | 20px |
padding: 10px 20px 30px 40px |
10px | 20px | 30px | 40px |
片側については、padding-top や margin-left のようなプロパティを使用してください。後に padding や margin のショートハンドが以前に宣言された側の値を上書きすることがあるため、ルールの順序を確認してください。
完全な例で実際の幅を確認する
以下の完全なコードを spacing.html として UTF-8 で保存し、ブラウザで開いてください。ライブラリやサーバーは必要ありません。Alpha、Beta、その他の単語は比較ラベルです。編集後は保存して再読み込みしてください。開発者ツールで各 .box を選択し、ボックスモデルの図や計算済みスタイルを確認して幅や間隔をチェックしてください。
<!doctype html>
<html lang="ja">
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1">
<title>paddingとmarginの比較</title>
<style>
body { font-family: sans-serif; max-width: 640px; margin: 0 auto; padding: 16px; }
h2 { font-size: 1.1rem; }
.stage { padding: 12px; border: 1px dashed #777; overflow-x: auto; }
.box { width: 200px; padding: 16px; border: 4px solid #17324d; margin: 24px; background: #dcefff; }
.content-box { box-sizing: content-box; }
.border-box { box-sizing: border-box; }
.asymmetric { box-sizing: border-box; padding: 8px 16px 24px 32px; margin: 10px 20px 30px 40px; }
.center { box-sizing: border-box; margin: 0 auto; }
.collapse-demo { display: flow-root; border: 1px dashed #777; }
.item { height: 30px; background: #dcefff; }
.first { margin: 0 0 24px; }
.second { margin: 16px 0 0; }
</style>
</head>
<body>
<h1>paddingとmarginの比較</h1>
<h2>content-box</h2>
<div class="stage"><div class="box content-box">Alpha</div></div>
<h2>border-box</h2>
<div class="stage"><div class="box border-box">Beta</div></div>
<h2>padding / margin</h2>
<div class="stage"><div class="box asymmetric">Gamma</div></div>
<h2>margin: 0 auto</h2>
<div class="stage"><div class="box center">Delta</div></div>
<h2>margin-bottom / margin-top</h2>
<div class="collapse-demo">
<div class="item first">A</div>
<div class="item second">B</div>
</div>
</body>
</html>
Alpha の border-box 幅は 200 + 16 × 2 + 4 × 2 = 240px です。水平マージンを含めると、占有する幅は 240 + 24 × 2 = 288px です。Beta は border-box サイズを使用しているため、その border-box 幅は 200px で、コンテンツ幅は 200 - 16 × 2 - 4 × 2 = 160px です。これらの計算には、周囲のstage要素のパディングとボーダーは含まれていません。
Gamma は上に 8px、右に 16px、下に 24px、左に 32px のパディングがあります。マージンは同じ順で 10px、20px、30px、40px です。上記の省略形の方向と比較して、視覚的な違いを確認してください。
box-sizingで幅の計算方法を指定する
content-boxでは、widthはコンテンツの幅を指定し、その外側にパディングとボーダーが追加されます。border-boxでは、指定した幅にはコンテンツ、パディング、ボーダーが含まれます。どちらのサイズ指定方法でも、幅にはマージンは含まれません。通常のdiv要素は初期状態でcontent-boxを使用しますが、サイトのリセットCSSによってこれが変更される場合があります。計算済みの値を確認してください。
例の.content-boxルールを次のものに置き換えます。Alphaのborder-boxの幅は240pxから200pxに変わります。他の値はそのままにして、比較し、content-boxを元に戻してください。パディングとボーダーの合計が指定した幅を超える場合でも、コンテンツ幅がマイナスにはならないため、結果としてボックスは期待よりも広くなることがあります。
.content-box {
box-sizing: border-box;
}
autoマージンで中央に配置する
通常のフローでブロックを水平に中央に配置するには、ボックスが親要素で利用可能な幅よりも狭く、左右のマージンが自動(auto)である必要があります。Delta の幅は200pxで margin: 0 auto、残りの水平スペースは両側で均等に分配されます。ブロックの中央配置だけでは、親要素が狭すぎる場合のオーバーフローは解決できません。
自動幅の通常のブロックがすでに利用可能な水平スペースを埋めている場合、左右の自動マージンを追加しても目に見える中央配置の効果はありません。通常のフローでは、margin-top: auto および margin-bottom: auto は垂直方向に中央配置を行いません。Flexbox や Grid では自動マージンのレイアウトルールは異なるため、それらの文脈を区別してください。
マージンの相殺と負の値に注意する
通常のブロックレイアウトでは、隣接する縦方向のマージンは相殺される場合があります。最後の例では、Aの下マージン24pxとBの上マージン16pxはどちらも正の値なので、それらの間隔は大きい方の値である24pxになり、40pxにはなりません。この例では、親要素のボーダーが親と子の間のマージンの相殺を防いでいます。
例の.collapse-demoルールを以下のように変更します。子要素はフレックスアイテムになり、お互いのマージンは相殺されなくなるので、間隔は24 + 16 = 40pxになります。display: flow-rootを比較して復元してください。親にflow-rootを適用するだけでは、兄弟ブロック間のすべてのマージン相殺はなくなりません。
.collapse-demo {
display: flex;
flex-direction: column;
border: 1px dashed #777;
}
この例のような横書きでは、左右のマージンはこのようには相殺されません。マージンの相殺に正の値と負の値が含まれる場合、最も大きい正の値に絶対値が最大の負の値を加えます:24px と -8px は 16px になります。すべてが負の場合は、最も小さい負の値を使用します;-8px と -16px は -16px になります。margin-left: -8px のような宣言は有効ですが、重なりを引き起こしたりコンテンツを親の外に移動させたりする可能性があります。狭い画面やキーボードフォーカスインジケーターを確認してください。負のパディングは同じ効果を生みません。W3C マージン相殺ルール
想定どおりに表示されない場合の確認事項
- ブラウザのデフォルト設定を確認してください。デフォルトのボディマージンや p および h1 のデフォルトの垂直マージンは、宣言した値よりも余白を大きく見せることがあります。無闇にすべての余白を削除するのではなく、該当する要素をリセットしてください。
- span のような通常の置換されないインライン要素では、垂直マージンは行のレイアウトに影響しません。インラインパディングは、隣接する行を予想通りに押し離すことなく描画されます。ボックスに独立したサイズや余白が必要な場合は、inline-block や他のレイアウトモードを検討してください。
- 開発者ツールを使用して、セレクタが一致しているか、宣言が有効か、優先度が高いルールや後から書かれたショートハンドによって上書きされていないかを確認してください。狭い幅でも比較し、オーバーフローやパディングが幅に与える影響も確認してください。
書字方向に対して間隔を定義するには、padding-inlineやmargin-blockのような論理プロパティを使用します。通常の水平書きの場合、インライン軸は水平方向で、ブロック軸は垂直方向です。縦書きではこれらの軸が変化するため、常に物理的な左右に対応するわけではありません。




