CSSで画像の横に文字を置けない!そんな時に試してほしい5つの方法
2021/04/14
2021/08/18
サイト作成では「画像の横に文字を配置する」というシーンに、多々遭遇します。
とても簡単なことのように思えますが、最初のうちはコレがなかなか上手くいきません。
たとえ画像の横に文字を並べることに成功したとしても、今度は画像とテキストのレイアウトが崩れてしまったり…。
今回は、そんなHTML・CSSで画像の横に文字を置く時に失敗しやすい問題と、その解決方法をまとめてみました。
ちなみに、画像の横に文字を置く方法は一つだけではありません。
例えば一般的な方法として、以下の5つが有名です。
- display: inline-block ←オーソドックスな方法
- display: flex ←初心者でも簡単
- 疑似要素 ←文頭や文末にアイコンを付けたい
- float ←紙媒体のようなレイアウトに
- table ←CSSが使えない人向け
初心者の方は、とりあえず「1」display: inline-block
か「2」display: flex
で画像の横に文字を置く方法がオススメです。
あとの「2」~「5」は状況や用途に応じて、使い分けてみてください。
もくじ
CSSで画像の横に文字を並べたい時に起きる問題
実は、画像・文字はブロック要素(p
やdiv
など)で囲まなければ、そのまま横に並びます。
これは、画像・文字そのものがインライン要素だからです。
1 2 |
<img src="./colosseum.jpg"> コロッセオは西暦80年にウェスパシアヌス帝、ティトゥス帝によって建てられた円形闘技場である。「コロッセオが立つ限り、ローマも立つ。コロッセオが倒れれば、ローマも倒れる。ローマが倒れれば、世界も倒れる。」と称えられているように、それはローマ帝国の繁栄を象徴するものであった。 |
結果は以下のように、一応、画像の隣からそのまま文字が続いていることがわかります。
しかし、画像と文字の大きさが不釣り合いの場合、このように大きな空間ができてしまったりします。
また、画像・文字をブロック要素で囲めば、当然、改行されてしまいます。
1 2 |
<figure><img src="./colosseum.jpg"></figure> <p>コロッセオは西暦80年にウェスパシアヌス帝、ティトゥス帝によって建てられた円形闘技場である。「コロッセオが立つ限り、ローマも立つ。コロッセオが倒れれば、ローマも倒れる。ローマが倒れれば、世界も倒れる。」と称えられているように、それはローマ帝国の繁栄を象徴するものであった。</p> |
そもそも画像の横に文字を配置できない原因の多くは、このように画像・文字ともに(あるいは片方が)ブロック要素に囲まれているためです。
とは言え、コードを管理しやすくするためにも、なるべくテキストや画像は異なるブロック要素でマークアップしておきたいもの。
では、ブロック要素同士をきれいに横並びにするにはどうしたら良いのでしょうか?
1.display: inline-blockで画像の横に文字を配置
ブロック要素とブロック要素を隣り合わせに配置するには、display
プロパティの値をblock
からinline-block
へ変更します。
inline-block
とは、ブロック要素のようにサイズ・余白の調整ができ、かつインライン要素のように改行されずに横に並ぶ性質をもった表示形式です。
よく「ブロック要素とインライン要素の中間」などと表現されます。
例えば、以下のようなHTMLを想定した場合、各ブロック要素にdisplay :inline-block
を適用します。
1 2 |
<figure class="side_image"><img src="./colosseum.jpg"></figure> <p class="side_text">コロッセオは西暦80年にウェスパシアヌス帝、ティトゥス帝によって建てられた円形闘技場である。「コロッセオが立つ限り、ローマも立つ。コロッセオが倒れれば、ローマも倒れる。ローマが倒れれば、世界も倒れる。」と称えられているように、それはローマ帝国の繁栄を象徴するものであった。</p> |
1 2 3 4 5 6 7 8 |
figure.side_image { display: inline-block; } p.side_text { display: inline-block; width: 300px; } |
すると、figure
やp
といったブロック要素であっても、横に並びます。
しかし、画像とテキスト全体の大きさが不釣り合いの場合、以下のようにレイアウトが崩れてしまいます。
きれいに「上端揃え」または「中央揃え」にする場合は、さらにvertical-align
を指定する必要があります。
vertical-align
は垂直方向の位置を調整するCSSプロパティです。
上端に揃えたい場合は値にtop
を、中央の場合はmiddle
を、下端の場合はbottom
を入力してください。
1 2 3 4 5 6 |
p.side_text { display: inline-block; width: 300px; margin-left: 20px; vertical-align: top; } |
また、画像と文字の間が狭い場合は上のコードのようにmargin
で調整してあげましょう。
これでようやくレイアウトが整いました。
ただし、横並びにした時に画面に収まりきらない場合は、自動的に改行されてしまうので注意が必要です。
この場合、横幅を固定した親要素で両ブロックを挟む等の横並びを維持する方法もあります。
1 2 3 4 |
<div style="width:650px"> <figure class="side_image"><img src="./colosseum.jpg"></figure> <p class="side_text">「コロッセオが立つ限り、ローマも立つ。コロッセオが倒れれば、ローマも倒れる。ローマが倒れれば、世界も倒れる。」</p> </div> |
しかし、主要ブラウザでレスポンシブが推奨される昨今は、@media screen
等で様々な画面に対応したほうが無難かもしれません。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 |
p,figure { margin-bottom: 20px; text-align: center; } @media screen and (min-width: 750px) { /* 750px以上の画面のみ横並びを適用 */ p,figure { margin-bottom: 0; text-align: left; } figure.side_image { display: inline-block; } p.side_text { display: inline-block; width: 300px; margin-left: 20px; vertical-align: top; } } |
こうすることで、広い画面で閲覧すると画像・文字を横並びになり、狭い画面だとそれぞれ中央&縦並びで表示されます。
2.display: flexで等間隔に横並べする
display
プロパティに新しく追加されたflex
は、まさにブロック要素同士の横並べに最適な表示形式です。
「要素同士の高さを揃えたい」「等間隔&中央に並べたい」といった細かいレイアウト調整も数行のコードで実現できます。
もちろん画像の横に文字を配置したい場合にも応用できるテクニックです。
しかし、ほとんどの主要ブラウザで対応が進められているものの、IE最新版ではバグが発生するなど完全な対応ではないことに注意してください。
(参考)display: flexの対応ブラウザ一覧(Can I use…)
では、display: flex
を使って画像の横に文字を配置してみましょう。
まず、事前に横並べしたい要素を親要素で囲んでおきます。
1 2 3 4 |
<div class="parent_box"> <figure class="side_image"><img src="./newyorkcity.jpg"></figure> <p class="side_text">「This is the city of dreamers and time and again it’s the place where the greatest dream of all, the American dream, has been tested and has triumphed.」</p> </div> |
前章でやったinline-block
では横並べする要素に直接指定していましたが、flex
の場合は親要素に指定します。
1 2 3 4 |
div.parent_box { width: 650px; display: flex; } |
たったこの一行で、子要素を横に並べることができます。
vertical-align
を操作しなくても上端揃えで表示されてますね。
display: flex
で垂直方向の位置を変えたい場合は、vertical-align
ではなくalign-items
プロパティを使ってください。
1 2 3 4 5 |
div.parent_box { width: 800px; display: flex; align-items: center; } |
上図のようにY軸の中央に配置したい場合はalign-items
プロパティをcenter
に、底辺に配置したい場合はend
に指定してください。
また、display: flex
はjustify-content
プロパティと組み合わせることで、柔軟なレイアウト調整が可能になります。
例えば、ある範囲の中で各ブロックを等間隔に並べたい時は、justify-content
にspace-between
を指定します。
1 2 3 4 5 6 7 8 9 10 |
div.parent_box { width: 1000px; display: flex; justify-content: space-between; } div.parent_box p { width: 300px; background-color: lightsteelblue; } |
横に並べる場合、テキストブロックも横幅を決めておかないと、レイアウトが崩れるので注意してください。
※各ブロックのサイズを把握できるよう、便宜上テキストに背景色を指定しています。
space-between
は両端を詰めたレイアウトですが、中央に寄せたい場合はspace-around
に変更してみてください。
1 2 3 4 5 |
div.parent_box { width: 1000px; display: flex; justify-content: space-around; } |
(※わかりやすいように画像・テキスト各ブロックの横幅を小さく設定しています)
space-arond
を指定すると、上図のように両端に等間隔の隙間が開き、space-between
よりも中央よりに配置されます。
このようにdisplay: flex
は、各ブロックを水平線上に並べるだけでなく、美しいレイアウトを効率的かつ簡単に実現できます。
3.::beforeで文字の横にアイコンを設置
小さな画像(アイコン)を文字の横に配置するなら、CSSの疑似要素::before
または::after
がオススメです。
上図のように記事内容と直接的な関係がないアイコンを表示したい時、疑似要素ならいちいちimg
を入力したりfigure
でマークアップしなくて済みます。
「疑似要素」と聞いてピンと来てない人も、とりあえずコピペだけで実装できるよう解説を進めますので、安心してください。
(※逆に、記事内容と関係が深い画像・図表は、疑似要素で表示させてしまうとクローラーが認識しないためオススメしません。「1.」または「2.」の方法をお試しください。)
まず、HTMLで画像を付けたいテキストを用意し、それぞれクラスを指定しておきましょう。
1 |
<p class="seasoning">しょうゆ:大さじ1 みりん:大さじ1 砂糖:小さじ2</p> |
次に、CSSで疑似要素の内容を作成していきます。
今回は、文頭に画像を配置したいので::before
で良いでしょう。
1 2 3 |
p.seasoning::before { content: url(./seasoning.png); } |
content
プロパティには、後から追加するコンテンツを入力します。
本来content: "調味料"
といった感じにテキストを指定するのが一般的ですが、上記のコードのようにcontent
で画像ファイルを呼び出すことも可能です。
しかし、上図のように画像と文字の大きさが不釣り合いです。
画像の大きさを調整したいところですが、残念ながらcontent
プロパティで追加した画像はCSSでサイズ変更できません。
編集ソフトで文字の高さに合わせて画像そのものをリサイズしてしまうのも一つの手ですが、どうにかCSSのみで解決したいところ。
そこで、疑似要素をinline-block
化し、背景画像としてアイコンを呼び出す方法を試してみましょう。
1 2 3 4 5 6 7 8 9 |
p.seasoning::before { content: ""; display: inline-block; width: 25px; height: 25px; background: url(./seasoning.png) no-repeat; background-size: contain; margin-right: 3px; } |
画像はbackground
で指定するため、content
の値は上記のように空にしてください。
width
、height
でリサイズした疑似要素内に、background-size
で背景画像が収まるよう指定しています。
無事、疑似要素で追加した画像のリサイズに成功しました。
しかし、今度はアイコンと文章との位置関係がちょっと歯がゆい感じです。
vertical-align
で調整することもできますが、より細かく位置を変更したい場合はtransform
プロパティも有効です。
1 2 3 4 5 6 7 8 9 10 |
p.seasoning::before { content: ""; display: inline-block; width: 25px; height: 25px; background: url(./seasoning.png) no-repeat; background-size: contain; margin-right: 3px; transform: translateY(6px); } |
translateY()
で縦軸の位置を調整できます。
画像を横軸にズラしたい時はtranslateX()
で指定してください。
あらかじめ使用頻度の高い画像を疑似要素として作っておけば、アイコンを付けたい段落にクラス指定するだけで良いので、使い回しも非常に楽です。
4.floatで画像の横に文字を回り込ませる
一昔前までは、画像の横に文字を並べる時にfloat
を使っていた人も多かったのではないでしょうか?
現在では、先ほど解説したinline-block
やflex
を使うのが主流になりつつありますが、float
も使えないわけではありません。
例えば、画像の右隣にテキストを配置したい場合は、img
セレクタのfloat
をleft
に指定します。
1 2 |
<img src="./sea.jpg" class="side_image"> <p>Whatever course you decide upon, there is always someone to tell you that you are wrong. There are always difficulties arising which tempt you to believe that your critics are right. To map out a course of action and follow it to an end requires courage.</p> |
1 2 3 4 |
img.side_image { float: left; margin-right: 10px; } |
すると以下のように、画像の横&上端からテキストが回り込むように表示されます。
「回り込む」と表現されるように、テキストの量が画像の高さを超えると、今度は画像の下に改行されます。
これは下図と比較してみるとわかる通り、inline-block
やflex
とは異なるレイアウトですね。
float: left
はタブロイド紙のような配置になり、スペースを余すことなくテキストで埋めたい場合に適しています。
一方、均整の取れたレイアウトや管理・調整のしやすさで言うとdisplay:inline-block
やflex
のほうが良いかもしれません。
ちなみに、画像の横に回り込ませたくない要素がある場合は、clear
プロパティを設定する必要があります。
例えば、以下のコードのうち2番目の段落(p.new_paragraph
)から回り込みを解除してみましょう。
1 2 3 |
<img src="./sea.jpg" class="side_image"> <p>Whatever course you decide upon, there is always someone to tell you that you are wrong. There are always difficulties arising which tempt you to believe that your critics are right. </p> <p class="new_paragraph">To map out a course of action and follow it to an end requires courage.</p> |
1 2 3 |
p.new_paragraph { clear: both; } |
clearの値をbothに指定することで、その段落以降のfloat
効果を解除できます。
この回り込みの解除し忘れによって、レイアウトが崩れてしまうことがあるので気を付けてください。
5.(CSS不要)tableで画像の隣のセルに文字を入力
あまり一般的ではないテクニックですが、tableタグを使って画像の横に文字を配置することも可能です。
ライティング案件の受注などで記事ごとの編集権限しか与えられておらず、CSSによるスタイル変更が許されていない場合など、tableタグでごり押しできるかもしれません^^;
1 2 3 4 5 6 7 8 9 10 11 12 13 14 |
<table cellpadding="5" border="0"> <tr> <td><img src="./seasoning.png"></td> <td>しょうゆ:大さじ1 みりん:大さじ1 砂糖:小さじ2</td> </tr> <tr> <td><img src="./nife.png"></td> <td>人参とジャガイモを乱切り</td> </tr> <tr> <td><img src="./pot.png"></td> <td>調味料と水200mlを合わせて沸騰するまで中火</td> </tr> </table> |
1列目に画像を、2列目にテキストを入れてみました。
border
を0
に指定しておくことで、表示上、テーブルを使っていないように見せます。
とは言え、レスポンシブ対応には不向きな方法なので、使うタイミングには注意してください。
まとめ
今回は、画像の横に文字を置く方法を解説しました。
単純な操作のように思えますが、初心者には躓きやすいポイントがたくさんあるテクニックでもあります。
何種類か方法を紹介しましたが、やはり基本的にはdisplay: inline-block
ないしflex
を使った方法をマスターしたほうが良いと思います。
基本を理解したうえで疑似要素やfloatを使った方法にチャレンジしてみると良いでしょう。