aタグのクリックする範囲がズレたり、想像以上にクリックできる範囲(当たり判定)がオカシい!そんなお悩み解決します。
そこで、今回はaタグのクリックできる範囲のズレを直す方法をご紹介します。
aタグ(リンク)にまつわるお困りごと3つ
この記事では初心者がつまずきがちの3つのお困りごとの解消法と原因をご紹介します
- ナビゲーションをクリックしても反応しない!?
- aタグの中に画像を配 置して下側にできたアキをどうにかしたい!!
- リンクのど真ん中に文字や画像を配置したい
かみーゆ/フロントエンドエンジニア
お困りごと1・あれ?!ナビゲーションをクリックしても反応しない!?
こんなナビを作ってみたものの、見た目はキレイにできているのにクリックしてもテキスト部分しかリンクが反応しない。。。。
そんなことあります。
このようにナビゲーションを配置したい時に書きがちなコードです。
display: flex
でナビのliタグを横方向に並べ、幅を均等に振り分けます。
<ul>
<li><a href="/">ホーム</a></li>
<li><a href="blog/">ブログ</a></li>
<li><a href="profile/">プロフィール</a></li>
<li><a href="contact/">お問合わせ</a></li>
</ul>
* {
box-sizing: border-box;
}
ul {
display: flex;
flex-wrap: wrap;
}
li {
width: 25%;
text-align: center;
border-left: 1px solid #fff;
}
li:first-child {
border-left: none;
}
a {
padding-top: 20px;
padding-bottom: 20px;
}
解決法:CSSでaタグにプロパティdisplay:blockをセットするだけ
ではどうすればいいのか。
解決方法はカンタンです。
aタグにCSSでプロパティdisplay:block
をセットするだけです。
原因の解説
理由はaタグの初期値はdisplay: inline
、つまりaタグがインラインレベルの要素だからです。
displayは要素の表示形式を指定するプロパティでinline
を指定すると通常、内側のコンテンツ(テキストなど)以上のサイズに大きくなることはありません。
そのためliタグの中にインラインレベルの要素をおくからアキができてしまうわけです。
プロパティdisplay
を活用して表示形式を変えましょう。
お困りごと2・aタグの中に画像を配置して下側にできたアキをどうにかしたい!!
画像を入れ子にしたら下の方にこんな感じのアキが!!
解決法:CSSでimgタグにプロパティvertical-align: bottomをセット
この現象は初心者あるあるです。
解消法はCSSでimgタグにvertical-align: bottom
をセットするだけです。
<a href="/"><img src="images/hogehoge.jpg" alt="hogehoge" width="200" height="200"></a>
a {
display: block;
width: 300px;
height: 300px;
border: 2px solid #333;
}
img {
width: 100%;
height: auto;
vertical-align: bottom;/* ←これが重要 */}
原因の解説
プロパティvertical-align
はインライン要素の縦方向の位置を調整するプロパティです。
アイコンの位置上付、下付きなどの文字位置の調整もプロパティvertical-align
を使います。
imgタグの下になぜ余白ができるのか。
インラインレベルの要素はアルファベットをベースに作られているからです。
vertical-align: baseline;
HTMLはもともと英語圏の人が作ったものなので、文字にはベースラインが基準になるようにセットされてます。小文字の「g」や「j」下に突き抜けます。
imgタグなどのインラインレベルの要素はこれらの文字と同じ振る舞いをするので下に変なアキができてしまうのです。
画像の位置のたての位置の基準を一番下に変えれば良いだけです。
vertical-align: bottom;
お困りごと3・リンクの範囲を縦方向にも広げて文字位置を縦横方向真ん中に配置したい
なのにpadding
やheight
を駆使してもなぜかうまくいかないことってありませんか?
解決法:aタグにプロパティdisplay:flexをセットして配置を調整
解決法はdisplay: flexを使い倒します。
- aタグに高さをセットする
display: flex
justify-content: center
align-items: center
* {
box-sizing: border-box;
line-height: 1.8;
}
ul {
display: flex;
flex-wrap: wrap;
background: #4D4D4D;
list-style: none;
}
li {
width: 25%;
text-align: center;
border-left: 1px solid #fff;
}
li:first-child {
border-left: none;
}
a {
height: 70px;
text-decoration: none;
color: #fff;
display: flex;
justify-content: center;
align-items: center;
}
原因と解説
プロパティdisplayをflexにすると子要素やコンテンツの縦方向や横方向並びと位置をコントロールできます。
flex-directionというプロパティをセットで使うのですが、初期値はrowがセットされており子要素は横並びになります。なので縦方向に並べたい時はcolumnをセットしておきます。
並べていく方向のコンテンツの位置をコントロールできるのがjustify-contentで、centerにするとこの場合、コンテンツは横方向にセンタリングされます。
縦方向に対しての位置をコントロールするプロパティがalign-itemsで す。値をcenterにするとaタグの縦方向に対し真ん中にコンテンツを配置できます。
おまけ・HTML5の要素について要素がどうカテゴライズされているか知っておこう
インライン、ブロック要素という言い方はHTML5ではなくなりました。
ただ、この記事では便宜上aタグとimgタグをインラインレベルの要素と説明しています。
インライン、ブロックの解説は難しいですね。
要素は分類できる
要素(HTLMタグ)、つまりコンテンツは7つに分類できます。
- メタデータ・コンテンツ … 文書情報や別文書との関係などを定義するコンテンツ
- フロー・コンテンツ … 文書の本体に現れる一般的なコンテンツ
- セクショニング・コンテンツ … セクションの範囲を定義するコンテンツ
- ヘッディング・コンテンツ … 見出しを表すコンテンツ
- フレージング・コンテンツ … 段落内で使用するようなコンテンツ
- エンベッディッド・コンテンツ … 文書内に埋め込みを行うコンテンツ
- インタラクティブ・コンテンツ … ユーザーが操作可能なコンテンツ
aタグやimgタグは、HTML5では主にフレージングコンテンツの一種ですが同時にユーザーが操作可能なのでインタラクティブコンテンツでもあります。
さらに、imgタグは「画像を埋め込む」コンテンツでもあるのでエンベッディッド・コンテンツにも属します。
とても複雑ですね。
要素の特性を知る上では重要ですが、こんなことイチイチ気にしていたらコーディングできないです。
たとえはフレージング・コンテンツであるspanや、strongの中にpタグやdivタグを入れたら文書構造が破綻するぐらいは知っておいた方がいいですが、気になったら都度調べる程度で十分です。
種類 | タグ | 備考 |
---|---|---|
フ ローコンテンツ | <a> , <abbr> , <address> ,<area> (map要素内にある場合)<article> , <aside> ,<audio> ,<br> , <b> , <bdi> , <bdo> , <blockquote> ,<br> , <button> ,<br> <canvas> , <cite> , <code> , <data> , <datalist> , <del> ,<details> , <dfn> , <div> ,<dl> ,<br> , <em> ,<embed> , <fieldset> , <figure> ,<footer> , <form> ,<br> , <h1> -<h6> ,<header> ,<hr> , <i> , <iframe> ,<img> ,<input> ,<br> <ins> , <kbd> , <keygen> , <br> , <label> , <main> , <map> ,<mark> ,<menu> , <meter> , <nav> ,<noscript> ,<br> , <object> , <ol> ,<output> , <p> , <picture> , <pre> , <br> , <progress> , <q> , <ruby> , <s> ,<br> , <samp> , <script> ,<section> , <select> ,<small> , <span> , <strong> , <sub> , <sup> ,<br> , <table> , <template> ,<textarea> ,<br> <time> ,<u> , <ul> , <var> , <video> , <wbr> , テキスト | |
メタデータコンテンツ | <base> , <link> , <meta> , <noscript> ,<script> , <style> , <template> , <title> | |
ヘッディングコンテンツ | <h1> ~ <h6> | 見出し |
セクショニングコンテンツ | <article> , <aside> , <nav> , <section> | |
フレージングコンテンツ | <a> , <abbr> , <area> (map要素内にある場合)<br> <audio> , <b> , <bdi> , <bdo> , <br> , <button> ,<br> <canvas> , <cite> , <code> , <data> ,<br> <datalist> , <del> , <dfn> , <em> , <embed> ,<br> <i> , <iframe> , <img> , <input> , <ins> , <kbd> ,<br> <keygen> , <label> , <map> , <mark> , <meter> ,<br> <noscript> , <object> , <output> , <picture> ,<br> <progress> , <q> , <ruby> , <s> ,<br> <samp> , <script> , <select> , <small> ,<br> <span> , <strong> , <sub> , <sup> ,<br> <template> , <textarea> , <time> ,<br> <u> , <var> ,<video> , <wbr> , テキスト | |
エンベディッドコンテンツ | <audio> , <canvas> , <embed> , <iframe> , <img> , <object> , <picture> , <video> | |
インタラクティブコンテンツ | <a> (HTML 5.1ではhref属性がある場合に限る),<br> , <audio> (controls属性がある場合),<br> , <button> , <details> , <embed> , <iframe> ,<br> , <img> (usemap属性がある場合),<br> , <input> (type=“hidden”の場合は除く),<br> , <<keygen> , <label> ,<br> <object> <br> (usemap属性がある場合)(HTML 5.1では除外),<br> , <select> , <textarea> ,<video> (controls属性がある場合) |
まとめ・この記事を読んでくださった方へ
この記事は私がブログを始めた頃、2014年に書いたものです。
ありがたいことに、いまだに毎月たくさんの人に読んでもらっています。 きっとコーディングで行き詰ってこの記事にたどり着いていると思うので、少しでもわかりやすくなるよう何度もメンテナンスしています。お役に立てたら幸いです^ ^。
最後まで、お読みいただきありがとうございました。