HTMLの<button>タグは、単なるフォーム送信だけでなく、JavaScriptと連携したUI構築に欠かせない要素です。
本記事では、初心者が見落としがちなtype属性のミスや<a>タグの使い分けから、CSSによるモダンなデザイン装飾、実践的なJavaScriptの組み込み方を解説します。
HTMLの<button>タグ(ボタン)の使い方
Webサイトにおいて、ユーザーがアクションを起こす要素が「<button>タグ(ボタン)」です。
<button>タグは、フォームの送信やJavaScriptを用いたポップアップ開閉など、ページ内で何らかの処理を実行する際に使用します。
buttonタグとinputタグの違い- リンク(
aタグ)との使い分け
buttonタグとinputタグの違い
Web制作を学び始めた人がつまずくのが「<button>と<input type="button">(またはtype="submit")のどちらを使えばいいのか?」という疑問です。
結論から言うと、実務においては<button>タグが推奨されます。
<input>タグは「空要素」と呼ばれ、閉じタグ(</input>)が存在しません。
そのため、ボタンに表示する文字はvalue="送信"のように属性として指定するしかなく、中に他のHTMLタグ(画像やアイコンなど)を入れることができません。
一方、<button>タグは開始タグと終了タグ(</button>)を持つため、テキストだけでなく、Font Awesomeなどのアイコンタグ(<i>や<span>)や画像(<img>)を入れ子にして、リッチなデザインを作ることができます。
value=”<span>🚀</span> 送信する”>
※inputタグは内部にHTMLを持てないため、タグがそのまま文字として見えてしまいます。
HTMLコード表示
<div class="hbt1-wrapper">
<input type="radio" name="hbt1-state" id="hbt1-input" class="hbt1-radio" checked>
<input type="radio" name="hbt1-state" id="hbt1-button" class="hbt1-radio">
<div class="hbt1-controls">
<label for="hbt1-input" class="hbt1-btn">❌ inputタグ (アイコン不可)</label>
<label for="hbt1-button" class="hbt1-btn">⭕️ buttonタグ (アイコン可能)</label>
</div>
<div class="hbt1-demo-area">
<div class="hbt1-box target-input-hbt1">
<div class="hbt1-code-preview">
<input type="submit"<br>
value="<span>🚀</span> 送信する">
</div>
<div class="hbt1-render-area">
<input type="submit" class="hbt1-ui-btn" value="<span>🚀</span> 送信する">
</div>
<p class="hbt1-note">※inputタグは内部にHTMLを持てないため、タグがそのまま文字として見えてしまいます。</p>
</div>
<div class="hbt1-box target-button-hbt1">
<div class="hbt1-code-preview hbt1-code-ok">
<button type="submit"><br>
<span>🚀</span> 送信する<br>
</button>
</div>
<div class="hbt1-render-area">
<button type="submit" class="hbt1-ui-btn hbt1-ui-ok">
<span>🚀</span> 送信する
</button>
</div>
<p class="hbt1-note hbt1-note-ok">※buttonタグは開始と終了の間に自由に要素を配置できるため、リッチなボタンが作れます。</p>
</div>
</div>
</div>CSSコード表示
.hbt1-wrapper {
background-color: #f8f9fa;
padding: 20px;
border: 1px solid #dee2e6;
border-radius: 4px;
font-family: sans-serif;
}
.hbt1-radio { display: none; }
.hbt1-controls {
display: flex;
justify-content: center;
gap: 10px;
margin-bottom: 20px;
flex-wrap: wrap;
}
.hbt1-btn {
background-color: #e9ecef;
padding: 10px 15px;
border-radius: 4px;
cursor: pointer;
font-weight: bold;
color: #495057;
transition: 0.2s;
font-size: 14px;
}
#hbt1-input:checked ~ .hbt1-controls [for="hbt1-input"] { background-color: #dc3545; color: white; }
#hbt1-button:checked ~ .hbt1-controls [for="hbt1-button"] { background-color: #198754; color: white; }
.hbt1-demo-area {
background-color: #ffffff;
border: 2px dashed #adb5bd;
padding: 30px 20px;
display: flex;
justify-content: center;
}
.hbt1-box {
width: 100%;
max-width: 400px;
}
.hbt1-code-preview {
background-color: #f8d7da;
color: #842029;
font-family: monospace;
padding: 15px;
border-radius: 4px;
font-size: 14px;
border-left: 4px solid #dc3545;
margin-bottom: 20px;
}
.hbt1-code-ok {
background-color: #d1e7dd;
color: #0f5132;
border-left: 4px solid #198754;
}
.hbt1-render-area {
text-align: center;
margin-bottom: 20px;
}
/* WordPressテーマの干渉を防ぐ強力なリセットをかけたボタンデザイン */
.hbt1-ui-btn {
all: unset !important;
display: inline-flex !important;
align-items: center !important;
justify-content: center !important;
gap: 8px !important;
background-color: #dc3545 !important;
color: white !important;
font-size: 16px !important;
font-weight: bold !important;
padding: 12px 24px !important;
border-radius: 6px !important;
cursor: pointer !important;
box-sizing: border-box !important;
}
.hbt1-ui-ok {
background-color: #198754 !important;
}
.hbt1-note {
font-size: 13px;
color: #dc3545;
font-weight: bold;
line-height: 1.5;
}
.hbt1-note-ok { color: #198754; }
/* 表示切替 */
.target-button-hbt1 { display: none; }
#hbt1-input:checked ~ .hbt1-demo-area .target-button-hbt1 { display: none; }
#hbt1-input:checked ~ .hbt1-demo-area .target-input-hbt1 { display: block; }
#hbt1-button:checked ~ .hbt1-demo-area .target-input-hbt1 { display: none; }
#hbt1-button:checked ~ .hbt1-demo-area .target-button-hbt1 { display: block; }リンク(aタグ)との使い分け
HTMLのマークアップにおいて、<button>タグと<a>タグ(リンク)の使い分けは重要です。
見た目をCSSで「ボタン風のデザイン」にしてしまうと、画面上ではどちらも同じボタンに見えます。
しかし、HTMLのセマンティクス(意味論)とWebアクセシビリティにおいては、両者には明確な役割の違いがあります。
<a>タグ:「移動」
別のページへ遷移する、または同じページ内の別の場所へスクロールする場合に使用します。<button>タグ:「アクション」
フォームのデータを送信する、画面上にポップアップメニューを開く、アコーディオンメニューを開閉するなどページ遷移を伴わない処理に使用します。
初心者がよくやるNG例が「別のページに飛ぶリンクなのに、ボタンっぽい見た目を理由に<button>タグを使ってしまい、JavaScript(onclick="location.href=...")でページ遷移させる」という実装です。
これをすると、検索エンジンのクローラー(Googleボットなど)が「リンク(別のページへの繋がり)」として認識できず、SEOの評価(内部リンクの巡回)に悪影響を及ぼします。
また、視覚障害者向けのスクリーンリーダーを使用しているユーザーにも、「リンク」なのか「ボタン」なのか正しく伝わりません。
「見た目がボタンであっても、別のURLに移動するなら<a>タグを使う」のがよいでしょう。
詳細ページへ移動する
</a>
別のURLへ移動する場合は、CSSでボタン風のデザインにしたとしても、HTMLは必ず「aタグ」を使用します。
ポップアップを開く
</button>
ページ遷移を伴わず、その場でJavaScriptなどを実行させる場合は「buttonタグ」を使用します。
HTMLコード表示
<div class="hbt2-wrapper">
<input type="radio" name="hbt2-state" id="hbt2-link" class="hbt2-radio" checked>
<input type="radio" name="hbt2-state" id="hbt2-action" class="hbt2-radio">
<div class="hbt2-controls">
<label for="hbt2-link" class="hbt2-btn">別ページへ移動する (aタグ)</label>
<label for="hbt2-action" class="hbt2-btn">メニューを開く (buttonタグ)</label>
</div>
<div class="hbt2-demo-area">
<div class="hbt2-box target-link-hbt2">
<div class="hbt2-render-area">
<a href="#dummy" class="hbt2-ui-btn hbt2-color-blue">詳細ページへ移動する</a>
</div>
<div class="hbt2-code-explain">
<span class="hbt2-tag"><a href="/detail.html" class="btn"></span><br>
詳細ページへ移動する<br>
<span class="hbt2-tag"></a></span>
</div>
<p class="hbt2-note">別のURLへ移動する場合は、CSSでボタン風のデザインにしたとしても、HTMLは必ず「aタグ」を使用します。</p>
</div>
<div class="hbt2-box target-action-hbt2">
<div class="hbt2-render-area">
<button type="button" class="hbt2-ui-btn hbt2-color-green">ポップアップを開く</button>
</div>
<div class="hbt2-code-explain">
<span class="hbt2-tag"><button type="button" class="btn"></span><br>
ポップアップを開く<br>
<span class="hbt2-tag"></button></span>
</div>
<p class="hbt2-note">ページ遷移を伴わず、その場でJavaScriptなどを実行させる場合は「buttonタグ」を使用します。</p>
</div>
</div>
</div>CSSコード表示
.hbt2-wrapper {
background-color: #f8f9fa;
padding: 20px;
border: 1px solid #dee2e6;
border-radius: 4px;
font-family: sans-serif;
}
.hbt2-radio { display: none; }
.hbt2-controls {
display: flex;
justify-content: center;
gap: 10px;
margin-bottom: 20px;
flex-wrap: wrap;
}
.hbt2-btn {
background-color: #e9ecef;
padding: 10px 15px;
border-radius: 4px;
cursor: pointer;
font-weight: bold;
color: #495057;
transition: 0.2s;
font-size: 14px;
}
#hbt2-link:checked ~ .hbt2-controls [for="hbt2-link"] { background-color: #0d6efd; color: white; }
#hbt2-action:checked ~ .hbt2-controls [for="hbt2-action"] { background-color: #198754; color: white; }
.hbt2-demo-area {
background-color: #ffffff;
border: 2px dashed #adb5bd;
padding: 30px 20px;
display: flex;
justify-content: center;
}
.hbt2-box {
width: 100%;
max-width: 400px;
}
.hbt2-render-area {
text-align: center;
margin-bottom: 20px;
}
/* aタグとbuttonタグを完全に同じ「ボタン風」デザインにするCSS */
.hbt2-ui-btn {
all: unset !important; /* 既存装飾リセット */
display: inline-block !important;
color: white !important;
font-size: 16px !important;
font-weight: bold !important;
padding: 15px 40px !important;
border-radius: 30px !important;
text-align: center !important;
text-decoration: none !important;
cursor: pointer !important;
box-shadow: 0 4px 6px rgba(0,0,0,0.1) !important;
box-sizing: border-box !important;
}
.hbt2-color-blue { background-color: #0d6efd !important; }
.hbt2-color-green { background-color: #198754 !important; }
.hbt2-code-explain {
background-color: #282c34;
color: #abb2bf;
padding: 15px;
border-radius: 4px;
font-family: monospace;
font-size: 14px;
margin-bottom: 15px;
line-height: 1.6;
}
.hbt2-tag { color: #e5c07b; }
.hbt2-note {
font-size: 13px;
color: #333;
line-height: 1.5;
font-weight: bold;
padding-top: 10px;
border-top: 1px dashed #ccc;
}
/* 表示切替 */
.target-action-hbt2 { display: none; }
#hbt2-link:checked ~ .hbt2-demo-area .target-action-hbt2 { display: none; }
#hbt2-link:checked ~ .hbt2-demo-area .target-link-hbt2 { display: block; }
#hbt2-action:checked ~ .hbt2-demo-area .target-link-hbt2 { display: none; }
#hbt2-action:checked ~ .hbt2-demo-area .target-action-hbt2 { display: block; }リンクである<a>タグの使い方を詳しく知りたい人は「【html&css】リンク<a>タグの使い方とWebデザインによる装飾」を一読ください。
buttonのtype属性における種類と役割
HTMLの<button>タグを使用する際、忘れてはならないのが「type属性」の指定です。
type属性は主に3つの種類があり、それぞれブラウザに対する命令(役割)が異なります。
初心者が陥りやすいのが、「type属性を省略した際の初期値の誤解」です。
これを理解していないと、「ボタンを押したら画面が真っ白」「意図せずページがリロード」といった予期せぬバグを引き起こします。
各種類の正しい役割と実務での注意点を見ていきましょう。
- フォームを送信する(
type="submit") - 単なるボタンとして使う(
type="button") - 入力内容をリセットする(
type="reset")
フォームを送信する(type=”submit”)
type="submit"は、<form>タグで囲まれた入力データをサーバーへ送信するボタンです。
<form>タグに設定されたaction属性のURLに向かってデータを送るといったWebサービスにおいて重要な役割を担います。
<button>タグにtype属性を書き忘れた場合、ブラウザは自動的にtype="submit"として扱います。
実務でよくある失敗は、フォームの中に「入力欄を追加する」といったJavaScriptを動かすボタンを配置した際、type属性を書き忘れることです。
ユーザーがボタンを押すと、JSが動く前に「フォームの送信処理」が走ってしまい、ページが強制的にリロードされて入力内容が消えます。
※type属性を省略すると自動的に「submit」になるため、押すとフォームが送信されてしまいます。
※データを送る役割を持つボタンには、必ず明示的に type=”submit” を記述します。
HTMLコード表示
<div class="htyp1-wrapper">
<input type="radio" name="htyp1-state" id="htyp1-bad" class="htyp1-radio" checked>
<input type="radio" name="htyp1-state" id="htyp1-good" class="htyp1-radio">
<div class="htyp1-controls">
<label for="htyp1-bad" class="htyp1-btn">❌ type指定なしのボタン</label>
<label for="htyp1-good" class="htyp1-btn">⭕️ type="submit"のボタン</label>
</div>
<div class="htyp1-demo-area">
<div class="htyp1-box target-bad-htyp1">
<form onsubmit="event.preventDefault(); alert('意図せずフォームが送信(リロード)されました!');" class="htyp1-form">
<p class="htyp1-desc">何かのアクションを起こすつもりで置いたtype指定のないボタン</p>
<div class="htyp1-code"><button>ただのボタンのつもり</button></div>
<button class="htyp1-ui-btn htyp1-ui-ng">ただのボタンのつもり</button>
</form>
<p class="htyp1-note">※type属性を省略すると自動的に「submit」になるため、押すとフォームが送信されてしまいます。</p>
</div>
<div class="htyp1-box target-good-htyp1">
<form onsubmit="event.preventDefault(); alert('サーバーへデータを送信しました!');" class="htyp1-form">
<p class="htyp1-desc">データを送信するための正しいボタン</p>
<div class="htyp1-code"><button type="submit">データを送信する</button></div>
<button type="submit" class="htyp1-ui-btn htyp1-ui-ok">データを送信する</button>
</form>
<p class="htyp1-note">※データを送る役割を持つボタンには、必ず明示的に type="submit" を記述します。</p>
</div>
</div>
</div>CSSコード表示
.htyp1-wrapper {
background-color: #f8f9fa;
padding: 20px;
border: 1px solid #dee2e6;
border-radius: 4px;
font-family: sans-serif;
}
.htyp1-radio { display: none; }
.htyp1-controls {
display: flex;
justify-content: center;
gap: 10px;
margin-bottom: 20px;
flex-wrap: wrap;
}
.htyp1-btn {
background-color: #e9ecef;
padding: 10px 15px;
border-radius: 4px;
cursor: pointer;
font-weight: bold;
color: #495057;
transition: 0.2s;
font-size: 14px;
}
#htyp1-bad:checked ~ .htyp1-controls [for="htyp1-bad"] { background-color: #dc3545; color: white; }
#htyp1-good:checked ~ .htyp1-controls [for="htyp1-good"] { background-color: #198754; color: white; }
.htyp1-demo-area {
background-color: #ffffff;
border: 2px dashed #adb5bd;
padding: 30px 20px;
display: flex;
justify-content: center;
}
.htyp1-box {
width: 100%;
max-width: 400px;
}
.htyp1-form {
background-color: #f1f3f5;
padding: 20px;
border-radius: 4px;
text-align: center;
border: 1px solid #ccc;
}
.htyp1-desc {
font-size: 14px;
font-weight: bold;
margin: 0 0 10px 0;
color: #333;
}
.htyp1-code {
background-color: #282c34;
color: #abb2bf;
padding: 10px;
font-family: monospace;
font-size: 13px;
border-radius: 4px;
margin-bottom: 15px;
}
/* WordPressテーマの干渉リセット */
.htyp1-ui-btn {
all: unset !important;
display: inline-block !important;
color: white !important;
font-size: 15px !important;
font-weight: bold !important;
padding: 10px 20px !important;
border-radius: 4px !important;
cursor: pointer !important;
box-sizing: border-box !important;
}
.htyp1-ui-ng { background-color: #dc3545 !important; }
.htyp1-ui-ok { background-color: #198754 !important; }
.htyp1-note {
font-size: 13px;
color: #666;
margin-top: 15px;
line-height: 1.5;
}
.target-good-htyp1 { display: none; }
#htyp1-bad:checked ~ .htyp1-demo-area .target-bad-htyp1 { display: block; }
#htyp1-good:checked ~ .htyp1-demo-area .target-bad-htyp1 { display: none; }
#htyp1-good:checked ~ .hytp1-demo-area .target-good-htyp1 { display: block; } /* fallback */
#htyp1-good:checked ~ .htyp1-demo-area .target-good-htyp1 { display: block; }単なるボタンとして使う(type=”button”)
フォームの送信機能を持たせず、JavaScriptを起動する「単なるボタン」として使いたい場合は、type="button"を指定します。
ハンバーガーメニューの開閉、モーダル(ポップアップ)の表示、アコーディオンメニューの操作などWebサイトにおけるリッチなUIは、type="button"によって制御されています。
<button>の初期値はsubmitになるため、送信以外の目的でtype="button" は記述するのがよいです。
詳細を開く
</button>
HTMLコード表示
<div class="htyp2-wrapper">
<div class="htyp2-demo-area">
<div class="htyp2-box">
<div class="htyp2-code">
<button type="button" onclick="toggleMessage()"><br>
詳細を開く<br>
</button>
</div>
<div class="htyp2-action-area">
<button type="button" class="htyp2-ui-btn" onclick="document.getElementById('htyp2-secret').style.display = 'block';">
詳細を開く ▼
</button>
<div id="htyp2-secret" class="htyp2-secret-msg" style="display: none;">
<strong>【限定情報】</strong><br>
type="button" を指定しているため、画面がリロードされることなく、その場で安全にこのメッセージを表示(JavaScriptを実行)できています。
</div>
</div>
</div>
</div>
</div>CSSコード表示
.htyp2-wrapper {
background-color: #f8f9fa;
padding: 20px;
border: 1px solid #dee2e6;
border-radius: 4px;
font-family: sans-serif;
}
.htyp2-demo-area {
background-color: #ffffff;
border: 2px dashed #adb5bd;
padding: 30px 20px;
display: flex;
justify-content: center;
}
.htyp2-box {
width: 100%;
max-width: 400px;
}
.htyp2-code {
background-color: #282c34;
color: #abb2bf;
padding: 15px;
font-family: monospace;
font-size: 13px;
border-radius: 4px;
margin-bottom: 20px;
line-height: 1.5;
}
.htyp2-action-area {
text-align: center;
}
/* WordPressテーマの干渉リセット */
.htyp2-ui-btn {
all: unset !important;
display: inline-block !important;
background-color: #0d6efd !important;
color: white !important;
font-size: 15px !important;
font-weight: bold !important;
padding: 10px 25px !important;
border-radius: 30px !important;
cursor: pointer !important;
box-sizing: border-box !important;
transition: 0.2s !important;
}
.htyp2-ui-btn:hover { background-color: #0b5ed7 !important; }
.htyp2-secret-msg {
margin-top: 15px;
background-color: #fff3cd;
color: #856404;
padding: 15px;
border-radius: 4px;
border-left: 4px solid #ffc107;
font-size: 14px;
line-height: 1.6;
text-align: left;
animation: fadeIn 0.5s ease-in;
}
@keyframes fadeIn {
from { opacity: 0; transform: translateY(-10px); }
to { opacity: 1; transform: translateY(0); }
}入力内容をリセットする(type=”reset”)
type="reset"は、ボタンが属する<form>内の全ての入力内容を、初期状態(空っぽ)に戻すボタンです。
HTMLの機能として存在しますが、Webデザイン・実務においてtype="reset"を使用することはほぼ無いと断言できます。
※送信ボタンのすぐ横に目立つリセットボタンがあると、誤操作でデータが全消去される悲劇を生みます。
※どうしても必要な場合は、ボタンっぽく見せない「テキストリンク風」のデザインにして誤操作を防ぎます。
HTMLコード表示
<div class="htyp3-wrapper">
<input type="radio" name="htyp3-state" id="htyp3-bad" class="htyp3-radio" checked>
<input type="radio" name="htyp3-state" id="htyp3-good" class="htyp3-radio">
<div class="htyp3-controls">
<label for="htyp3-bad" class="htyp3-btn">❌ 誤操作を招く配置 (NG)</label>
<label for="htyp3-good" class="hhtyp3-btn" style="display:none;"></label> <label for="htyp3-good" class="htyp3-btn">⭕️ 目立たせない配置 (OK)</label>
</div>
<div class="htyp3-demo-area">
<div class="htyp3-box target-bad-htyp3">
<form onsubmit="event.preventDefault(); alert('送信しました');" class="htyp3-form">
<input type="text" value="一生懸命書いた長文のメッセージ..." class="htyp3-input" readonly>
<div class="htyp3-action-group-ng">
<button type="submit" class="htyp3-submit-btn">送信する</button>
<button type="reset" class="htyp3-reset-btn-danger">リセット</button>
</div>
</form>
<p class="htyp3-note">※送信ボタンのすぐ横に目立つリセットボタンがあると、誤操作でデータが全消去される悲劇を生みます。</p>
</div>
<div class="htyp3-box target-good-htyp3">
<form onsubmit="event.preventDefault(); alert('送信しました');" class="htyp3-form">
<input type="text" value="一生懸命書いた長文のメッセージ..." class="htyp3-input" readonly>
<div class="htyp3-action-group-ok">
<button type="submit" class="htyp3-submit-btn">送信する</button>
<button type="reset" class="htyp3-reset-btn-safe">入力内容をクリア</button>
</div>
</form>
<p class="htyp3-note htyp3-note-ok">※どうしても必要な場合は、ボタンっぽく見せない「テキストリンク風」のデザインにして誤操作を防ぎます。</p>
</div>
</div>
</div>CSSコード表示
.htyp3-wrapper {
background-color: #f8f9fa;
padding: 20px;
border: 1px solid #dee2e6;
border-radius: 4px;
font-family: sans-serif;
}
.htyp3-radio { display: none; }
.htyp3-controls {
display: flex;
justify-content: center;
gap: 10px;
margin-bottom: 20px;
flex-wrap: wrap;
}
.htyp3-btn {
background-color: #e9ecef;
padding: 10px 15px;
border-radius: 4px;
cursor: pointer;
font-weight: bold;
color: #495057;
transition: 0.2s;
font-size: 14px;
}
#htyp3-bad:checked ~ .htyp3-controls [for="htyp3-bad"] { background-color: #dc3545; color: white; }
#htyp3-good:checked ~ .htyp3-controls [for="htyp3-good"] { background-color: #198754; color: white; }
.htyp3-demo-area {
background-color: #ffffff;
border: 2px dashed #adb5bd;
padding: 30px 20px;
display: flex;
justify-content: center;
}
.htyp3-box {
width: 100%;
max-width: 400px;
}
.htyp3-form {
background-color: #f1f3f5;
padding: 20px;
border-radius: 4px;
border: 1px solid #ccc;
}
.htyp3-input {
width: 100%;
padding: 10px;
margin-bottom: 20px;
border: 1px solid #ced4da;
border-radius: 4px;
box-sizing: border-box;
color: #333;
}
/* ❌ NGのアクショングループ:横並びで同じようなデザイン */
.htyp3-action-group-ng {
display: flex;
gap: 10px;
}
/* ⭕️ OKのアクショングループ:縦並びで明確な主従関係 */
.htyp3-action-group-ok {
display: flex;
flex-direction: column;
align-items: center;
gap: 15px;
}
/* 送信ボタン(共通) */
.htyp3-submit-btn {
all: unset !important;
flex: 1;
text-align: center !important;
background-color: #0d6efd !important;
color: white !important;
font-size: 15px !important;
font-weight: bold !important;
padding: 12px 20px !important;
border-radius: 4px !important;
cursor: pointer !important;
box-sizing: border-box !important;
}
/* ❌ 危険なリセットボタン:送信ボタンと似たUI */
.htyp3-reset-btn-danger {
all: unset !important;
flex: 1;
text-align: center !important;
background-color: #6c757d !important;
color: white !important;
font-size: 15px !important;
font-weight: bold !important;
padding: 12px 20px !important;
border-radius: 4px !important;
cursor: pointer !important;
box-sizing: border-box !important;
}
/* ⭕️ 安全なリセットボタン:リンク風の控えめなUI */
.htyp3-reset-btn-safe {
all: unset !important;
color: #6c757d !important;
font-size: 13px !important;
text-decoration: underline !important;
cursor: pointer !important;
}
.htyp3-note {
font-size: 13px;
color: #dc3545;
font-weight: bold;
margin-top: 15px;
line-height: 1.5;
}
.htyp3-note-ok { color: #198754; }
.target-good-htyp3 { display: none; }
#htyp3-bad:checked ~ .htyp3-demo-area .target-bad-htyp3 { display: block; }
#htyp3-good:checked ~ .htyp3-demo-area .target-bad-htyp3 { display: none; }
#htyp3-good:checked ~ .htyp3-demo-area .target-good-htyp3 { display: block; }ボタンをクリックして画面遷移・リンクさせる方法
Webサイト制作において、ボタンを押した時に別のページへ移動させる実装は頻繁に行われます。
単なるページ移動には<a>タグを使用するのがSEOの基本ですが、システム上の処理を挟んでから遷移させたい場合やブラウザの履歴を操作したい場合は、JavaScriptと組み合わせた<button>タグが活躍します。
onclickを使って指定URLへ飛ぶ- 別タブ(新しいウィンドウ)で開く方法
- 前のページに戻るボタンを作る
onclickを使って指定URLへ飛ぶ
<button>タグ自体にはhrefのようなリンク先を指定する属性がありません。
そのため、ボタンをクリックして別のURLへ飛ばすには、JavaScriptのonclickイベントを使用します。
ボタンのタグ内にonclick="location.href='遷移先のURL'"と記述することで、指定したページへリダイレクトできます。
クローラーがリンクを認識できない可能性があるため、「データの送信や計算が不要なリンク」は<a>タグを使用してください。
詳細ページへ
</button>
※右クリックしても「新しいタブで開く」メニューが出ず、クローラーもリンク先を辿れません。
HTMLコード表示
<div class="hbl1-wrapper">
<input type="radio" name="hbl1-state" id="hbl1-bad" class="hbl1-radio" checked>
<input type="radio" name="hbl1-state" id="hbl1-good" class="hbl1-radio">
<div class="hbl1-controls">
<label for="hbl1-bad" class="hbl1-btn">❌ onclickで遷移 (SEO悪化)</label>
<label for="hbl1-good" class="hbl1-btn">⭕️ aタグで遷移 (SEO最適)</label>
</div>
<div class="hbl1-demo-area">
<div class="hbl1-box target-bad-hbl1">
<div class="hbl1-code">
<button onclick="location.href='https://...'"><br>
詳細ページへ<br>
</button>
</div>
<div class="hbl1-action">
<button onclick="alert('JSによる遷移処理が実行されました');" class="hbl1-ui-btn hbl1-ui-ng">詳細ページへ</button>
</div>
<p class="hbl1-note">※右クリックしても「新しいタブで開く」メニューが出ず、クローラーもリンク先を辿れません。</p>
</div>
<div class="hbl1-box target-good-hbl1">
<div class="hbl1-code hbl1-code-ok">
<a href="https://..." class="btn"><br>
詳細ページへ<br>
</a>
</div>
<div class="hbl1-action">
<a href="javascript:void(0);" onclick="alert('aタグによる遷移処理が実行されました');" class="hbl1-ui-btn hbl1-ui-ok">詳細ページへ</a>
</div>
<p class="hbl1-note hbl1-note-ok">※右クリックメニューが正常に機能し、検索エンジンもリンク構造を正しく理解できます。</p>
</div>
</div>
</div>CSSコード表示
.hbl1-wrapper {
background-color: #f8f9fa;
padding: 20px;
border: 1px solid #dee2e6;
border-radius: 4px;
font-family: sans-serif;
}
.hbl1-radio { display: none; }
.hbl1-controls {
display: flex;
justify-content: center;
gap: 10px;
margin-bottom: 20px;
flex-wrap: wrap;
}
.hbl1-btn {
background-color: #e9ecef;
padding: 10px 15px;
border-radius: 4px;
cursor: pointer;
font-weight: bold;
color: #495057;
transition: 0.2s;
font-size: 14px;
}
#hbl1-bad:checked ~ .hbl1-controls [for="hbl1-bad"] { background-color: #dc3545; color: white; }
#hbl1-good:checked ~ .hbl1-controls [for="hbl1-good"] { background-color: #198754; color: white; }
.hbl1-demo-area {
background-color: #ffffff;
border: 2px dashed #adb5bd;
padding: 30px 20px;
display: flex;
justify-content: center;
}
.hbl1-box {
width: 100%;
max-width: 400px;
}
.hbl1-code {
background-color: #f8d7da;
color: #842029;
padding: 15px;
font-family: monospace;
font-size: 13px;
border-radius: 4px;
border-left: 4px solid #dc3545;
margin-bottom: 20px;
}
.hbl1-code-ok {
background-color: #d1e7dd;
color: #0f5132;
border-left: 4px solid #198754;
}
.hbl1-action { text-align: center; margin-bottom: 20px; }
/* aタグとbuttonタグを同じ見た目にするリセットCSS */
.hbl1-ui-btn {
all: unset !important;
display: inline-block !important;
color: white !important;
font-size: 15px !important;
font-weight: bold !important;
padding: 12px 30px !important;
border-radius: 6px !important;
cursor: pointer !important;
text-decoration: none !important;
box-sizing: border-box !important;
}
.hbl1-ui-ng { background-color: #dc3545 !important; }
.hbl1-ui-ok { background-color: #198754 !important; }
.hbl1-note { font-size: 13px; color: #dc3545; font-weight: bold; line-height: 1.5; }
.hbl1-note-ok { color: #198754; }
.target-good-hbl1 { display: none; }
#hbl1-bad:checked ~ .hbl1-demo-area .target-bad-hbl1 { display: block; }
#hbl1-good:checked ~ .hbl1-demo-area .target-bad-hbl1 { display: none; }
#hbl1-good:checked ~ .hbl1-demo-area .target-good-hbl1 { display: block; }別タブ(新しいウィンドウ)で開く方法
外部サイトのリンクやPDF資料を開く際、現在のページを残したまま新しいタブで開きたい場合があります。
<button>タグを使って実現するには、onclick内でwindow.open('URL', '_blank')というJavaScriptのメソッドを使用します。
実務においてwindow.open()を使う際に注意すべきは、ブラウザの「ポップアップブロッカー」です。
ユーザーがボタンをクリックした瞬間にwindow.open()が実行される場合は問題ありませんが、API通信(サーバーとのデータ送受信)を待ってから別タブを開こうとすると、ブラウザが「ユーザーの意図しない迷惑なポップアップ」と判定し、別タブ展開をブロックすることがあります。
単なる別タブ展開であれば<a>タグにtarget="_blank"を指定するのが安全な方法です。
Googleを別タブで開く
</button>
Googleを別タブで開く
</a>
HTMLコード表示
<div class="hbl2-wrapper">
<input type="radio" name="hbl2-state" id="hbl2-js" class="hbl2-radio" checked>
<input type="radio" name="hbl2-state" id="hbl2-a" class="hbl2-radio">
<div class="hbl2-controls">
<label for="hbl2-js" class="hbl2-btn">JS (window.open)</label>
<label for="hbl2-a" class="hbl2-btn">aタグ (target="_blank")</label>
</div>
<div class="hbl2-demo-area">
<div class="hbl2-box target-js-hbl2">
<div class="hbl2-code">
<button onclick="window.open('https://google.com', '_blank')"><br>
Googleを別タブで開く<br>
</button>
</div>
<div class="hbl2-action">
<button onclick="window.open('https://google.com', '_blank')" class="hbl2-ui-btn">Googleを別タブで開く</button>
</div>
</div>
<div class="hbl2-box target-a-hbl2">
<div class="hbl2-code">
<a href="https://google.com" target="_blank" rel="noopener noreferrer"><br>
Googleを別タブで開く<br>
</a>
</div>
<div class="hbl2-action">
<a href="https://google.com" target="_blank" rel="noopener noreferrer" class="hbl2-ui-btn hbl2-ui-alt">Googleを別タブで開く</a>
</div>
</div>
</div>
</div>CSSコード表示
.hbl2-wrapper {
background-color: #f8f9fa;
padding: 20px;
border: 1px solid #dee2e6;
border-radius: 4px;
font-family: sans-serif;
}
.hbl2-radio { display: none; }
.hbl2-controls {
display: flex;
justify-content: center;
gap: 10px;
margin-bottom: 20px;
flex-wrap: wrap;
}
.hbl2-btn {
background-color: #e9ecef;
padding: 10px 15px;
border-radius: 4px;
cursor: pointer;
font-weight: bold;
color: #495057;
transition: 0.2s;
font-size: 14px;
}
#hbl2-js:checked ~ .hbl2-controls [for="hbl2-js"] { background-color: #6f42c1; color: white; }
#hbl2-a:checked ~ .hbl2-controls [for="hbl2-a"] { background-color: #0dcaf0; color: #000; }
.hbl2-demo-area {
background-color: #ffffff;
border: 2px dashed #adb5bd;
padding: 30px 20px;
display: flex;
justify-content: center;
}
.hbl2-box { width: 100%; max-width: 450px; }
.hbl2-code {
background-color: #282c34;
color: #abb2bf;
padding: 15px;
font-family: monospace;
font-size: 13px;
border-radius: 4px;
margin-bottom: 20px;
line-height: 1.5;
}
.hbl2-action { text-align: center; }
.hbl2-ui-btn {
all: unset !important;
display: inline-block !important;
background-color: #6f42c1 !important;
color: white !important;
font-size: 15px !important;
font-weight: bold !important;
padding: 12px 30px !important;
border-radius: 6px !important;
cursor: pointer !important;
text-decoration: none !important;
box-sizing: border-box !important;
}
.hbl2-ui-alt { background-color: #0dcaf0 !important; color: #000 !important; }
.target-a-hbl2 { display: none; }
#hbl2-js:checked ~ .hbl2-demo-area .target-a-hbl2 { display: none; }
#hbl2-js:checked ~ .hbl2-demo-area .target-js-hbl2 { display: block; }
#hbl2-a:checked ~ .hbl2-demo-area .target-js-hbl2 { display: none; }
#hbl2-a:checked ~ .hbl2-demo-area .target-a-hbl2 { display: block; }前のページに戻るボタンを作る
確認画面から入力画面に戻る際や詳細ページから一覧ページへ戻る際など、ブラウザの「戻る」機能を持たせたボタンを作りたい場合は、JavaScriptのhistory.back()メソッドを使用します。
ボタンのタグにonclick="history.back()"と記述するだけでユーザーのブラウザ履歴を一つ遡り、前のページへ戻ります。
実務において「戻るボタンが効かない!」というクレームに繋がる代表的な原因です。
ユーザーがSNSのリンクや検索結果から「新しいタブ」でページを直接開いた場合、タブのブラウザ履歴は「ゼロ」です。
履歴がないため、history.back()を実行しても何も起きません。
実務ではhistory.back()だけに頼るのではなく、「戻る履歴が存在しない場合は、指定したトップページへ遷移させる」といったJavaScriptを組むか、最初から<a>タグを使って「一覧ページへ戻る」という固定リンクにしておくのが安全な設計です。
◀ 前のページへ戻る
</button>
※新しいタブでこの記事を開いている場合、履歴がないためクリックしても反応しません。これが history.back() の最大の弱点です。
HTMLコード表示
<div class="hbl3-wrapper">
<div class="hbl3-demo-area">
<div class="hbl3-box">
<div class="hbl3-code">
<button type="button" onclick="history.back()"><br>
◀ 前のページへ戻る<br>
</button>
</div>
<div class="hbl3-action">
<button type="button" onclick="history.back()" class="hbl3-ui-btn">
◀ 前のページへ戻る
</button>
</div>
<p class="hbl3-note">※新しいタブでこの記事を開いている場合、履歴がないためクリックしても反応しません。これが history.back() の最大の弱点です。</p>
</div>
</div>
</div>CSSコード表示
.hbl3-wrapper {
background-color: #f8f9fa;
padding: 20px;
border: 1px solid #dee2e6;
border-radius: 4px;
font-family: sans-serif;
}
.hbl3-demo-area {
background-color: #ffffff;
border: 2px dashed #adb5bd;
padding: 30px 20px;
display: flex;
justify-content: center;
}
.hbl3-box { width: 100%; max-width: 400px; }
.hbl3-code {
background-color: #282c34;
color: #abb2bf;
padding: 15px;
font-family: monospace;
font-size: 13px;
border-radius: 4px;
margin-bottom: 20px;
line-height: 1.5;
}
.hbl3-action { text-align: center; margin-bottom: 20px; }
.hbl3-ui-btn {
all: unset !important;
display: inline-block !important;
background-color: #6c757d !important;
color: white !important;
font-size: 15px !important;
font-weight: bold !important;
padding: 12px 30px !important;
border-radius: 30px !important;
cursor: pointer !important;
box-shadow: 0 4px 6px rgba(0,0,0,0.1) !important;
box-sizing: border-box !important;
}
.hbl3-note {
font-size: 13px;
color: #dc3545;
font-weight: bold;
line-height: 1.5;
padding-top: 15px;
border-top: 1px dashed #ccc;
}CSSでボタンをおしゃれにデザイン・装飾する
HTMLで記述しただけの標準ボタンは、ブラウザやOS(WindowsやMacなど)に依存した古いデザインで表示されます。
クリック率を上げるためには、CSSを用いてボタンをオリジナルのおしゃれなデザインへとカスタマイズする必要があります。
ここでは、CSSを使ったボタンの装飾や美化の基本プロパティと初心者が実務でつまずく「位置の調整」や「アクセシビリティ(使いやすさ)」について解説します。
- ボタンの大きさ(幅・高さ)と位置(中央寄せ・右寄せ)
- 背景色・文字色を変える
- 枠線を消す・角を丸くする
- マウスホバー(hover)時の色変更や3Dエフェクト
- 画像をボタンにする方法
ボタンの大きさ(幅・高さ)と位置(中央寄せ・右寄せ)
ボタンの大きさを決める際、横幅(width)や高さ(height)をwidth: 200px;のように絶対値で固定することも可能です。
しかし、テキストの長さに応じて余白を設けるpaddingプロパティを使って内側から広げるのが標準的です。
初心者がボタンの位置を中央や右寄せにしようとして、ボタンのCSSにtext-align: center;やmargin: 0 auto;を書いて「動かない!」とパニックになるのはよくあるミスです。
<button>タグは「インラインブロック要素」として振る舞うため、ボタンの位置を動かすにはボタンを囲んでいる親要素に対してtext-align: center;やtext-align: right;を指定する必要があります。
text-align: left;
HTMLコード表示
<div class="hdbt1-wrapper">
<input type="radio" name="hdbt1-state" id="hdbt1-left" class="hdbt1-radio" checked>
<input type="radio" name="hdbt1-state" id="hdbt1-center" class="hdbt1-radio">
<input type="radio" name="hdbt1-state" id="hdbt1-right" class="hdbt1-radio">
<div class="hdbt1-controls">
<label for="hdbt1-left" class="hdbt1-btn">左寄せ (デフォルト)</label>
<label for="hdbt1-center" class="hdbt1-btn">中央寄せ (親要素で制御)</label>
<label for="hdbt1-right" class="hdbt1-btn">右寄せ (親要素で制御)</label>
</div>
<div class="hdbt1-demo-area">
<div class="hdbt1-parent target-parent">
<button class="hdbt1-ui-btn">詳細を見る</button>
</div>
</div>
<div class="hdbt1-code-preview">
<span class="hdbt1-code-label">現在の親要素のCSS:</span>
<code class="hdbt1-code-text" id="hdbt1-code-view">text-align: left;</code>
</div>
</div>CSSコード表示
.hdbt1-wrapper {
background-color: #f8f9fa;
padding: 20px;
border: 1px solid #dee2e6;
border-radius: 4px;
font-family: sans-serif;
}
.hdbt1-radio { display: none; }
.hdbt1-controls {
display: flex;
justify-content: center;
gap: 10px;
margin-bottom: 20px;
flex-wrap: wrap;
}
.hdbt1-btn {
background-color: #e9ecef;
padding: 10px 15px;
border-radius: 4px;
cursor: pointer;
font-weight: bold;
color: #495057;
transition: 0.2s;
font-size: 14px;
}
#hdbt1-left:checked ~ .hdbt1-controls [for="hdbt1-left"],
#hdbt1-center:checked ~ .hdbt1-controls [for="hdbt1-center"],
#hdbt1-right:checked ~ .hdbt1-controls [for="hdbt1-right"] {
background-color: #0d6efd;
color: white;
}
.hdbt1-demo-area {
background-color: #ffffff;
border: 2px dashed #adb5bd;
padding: 30px 20px;
margin-bottom: 15px;
}
/* ボタン自体の装飾(widthではなくpaddingで大きさを決める) */
.hdbt1-ui-btn {
all: unset !important;
display: inline-block !important;
background-color: #0d6efd !important;
color: white !important;
font-size: 16px !important;
font-weight: bold !important;
padding: 15px 40px !important; /* 内側の余白で大きさを出す */
border-radius: 4px !important;
cursor: pointer !important;
box-sizing: border-box !important;
}
/* 親要素の制御 */
.hdbt1-parent {
width: 100%;
transition: text-align 0.3s ease;
}
#hdbt1-left:checked ~ .hdbt1-demo-area .hdbt1-parent { text-align: left; }
#hdbt1-center:checked ~ .hdbt1-demo-area .hdbt1-parent { text-align: center; }
#hdbt1-right:checked ~ .hdbt1-demo-area .hdbt1-parent { text-align: right; }
/* コード表示エリア */
.hdbt1-code-preview {
background-color: #282c34;
padding: 15px;
border-radius: 4px;
color: #abb2bf;
font-family: monospace;
font-size: 14px;
}
.hdbt1-code-label { color: #e5c07b; margin-right: 10px; }
.hdbt1-code-text { color: #98c379; }
#hdbt1-left:checked ~ .hdbt1-code-preview .hdbt1-code-text::before { content: "text-align: left;"; }
#hdbt1-center:checked ~ .hdbt1-code-preview .hdbt1-code-text::before { content: "text-align: center;"; }
#hdbt1-right:checked ~ .hdbt1-code-preview .hdbt1-code-text::before { content: "text-align: right;"; }widthやheightの設定を詳しく知りたい人は「【html&css】width(横幅)とheight(高さ)の指定とボックスモデル」を一読ください。
また、paddingやmarginの設定を詳しく知りたい人は「【html&css】paddingとmarginの違いは?上下左右の余白と順番」を一読ください。
背景色・文字色を変える
ボタンの色をサイトのテーマカラーに合わせるには、CSSのbackground-colorと文字色を変更するcolorを使用します。
コントラスト比の問題として、ブラウザ標準のグレーベースのボタンは視認性が低いため、独自の色スタイルを適用するのが一般的です。
「背景色に対して文字色が読みやすいか」を意識しないと、ユーザビリティの低いボタンになります。
※「暗い背景に暗い文字」「明るい背景に明るい文字」を設定すると、文字が背景に同化してしまい、ユーザーに多大なストレスを与えます。
※「暗い背景には白文字」「明るい背景には黒や濃いグレーの文字」をセットで指定することで、視認性が劇的に向上します。
HTMLコード表示
<div class="hdbc1-wrapper">
<input type="radio" name="hdbc1-state" id="hdbc1-bad" class="hdbc1-radio" checked>
<input type="radio" name="hdbc1-state" id="hdbc1-good" class="hdbc1-radio">
<div class="hdbc1-controls">
<label for="hdbc1-bad" class="hdbc1-btn">❌ コントラスト無視 (読みにくい)</label>
<label for="hdbc1-good" class="hdbc1-btn">⭕️ コントラスト確保 (読みやすい)</label>
</div>
<div class="hdbc1-demo-area">
<div class="hdbc1-box target-bad-hdbc1">
<div class="hdbc1-btn-group">
<button class="hdbc1-ui-btn hdbc1-bg-dark hdbc1-text-dark">購入手続きへ</button>
<button class="hdbc1-ui-btn hdbc1-bg-light hdbc1-text-light">キャンセル</button>
</div>
<p class="hdbc1-note">※「暗い背景に暗い文字」「明るい背景に明るい文字」を設定すると、文字が背景に同化してしまい、ユーザーに多大なストレスを与えます。</p>
</div>
<div class="hdbc1-box target-good-hdbc1">
<div class="hdbc1-btn-group">
<button class="hdbc1-ui-btn hdbc1-bg-dark hdbc1-text-white">購入手続きへ</button>
<button class="hdbc1-ui-btn hdbc1-bg-light hdbc1-text-black">キャンセル</button>
</div>
<p class="hdbc1-note hdbc1-note-ok">※「暗い背景には白文字」「明るい背景には黒や濃いグレーの文字」をセットで指定することで、視認性が劇的に向上します。</p>
</div>
</div>
</div>CSSコード表示
.hdbc1-wrapper {
background-color: #f8f9fa;
padding: 20px;
border: 1px solid #dee2e6;
border-radius: 4px;
font-family: sans-serif;
}
.hdbc1-radio { display: none; }
.hdbc1-controls {
display: flex;
justify-content: center;
gap: 10px;
margin-bottom: 20px;
flex-wrap: wrap;
}
.hdbc1-btn {
background-color: #e9ecef;
padding: 10px 15px;
border-radius: 4px;
cursor: pointer;
font-weight: bold;
color: #495057;
transition: 0.2s;
font-size: 14px;
}
#hdbc1-bad:checked ~ .hdbc1-controls [for="hdbc1-bad"] { background-color: #dc3545; color: white; }
#hdbc1-good:checked ~ .hdbc1-controls [for="hdbc1-good"] { background-color: #198754; color: white; }
.hdbc1-demo-area {
background-color: #ffffff;
border: 2px dashed #adb5bd;
padding: 40px 20px;
display: flex;
justify-content: center;
}
.hdbc1-box { width: 100%; max-width: 400px; text-align: center; }
.hdbc1-btn-group {
display: flex;
flex-direction: column;
gap: 15px;
margin-bottom: 25px;
align-items: center;
}
/* 共通のボタンリセットとベーススタイル */
.hdbc1-ui-btn {
all: unset !important;
display: inline-block !important;
font-size: 16px !important;
font-weight: bold !important;
padding: 15px 40px !important;
border-radius: 6px !important;
cursor: pointer !important;
box-sizing: border-box !important;
width: 80% !important; /* 幅を揃える */
text-align: center !important;
}
/* 背景色の設定 */
.hdbc1-bg-dark { background-color: #343a40 !important; } /* ダークグレー */
.hdbc1-bg-light { background-color: #ffc107 !important; } /* 明るいイエロー */
/* ❌ NG用の文字色設定 */
.hdbc1-text-dark { color: #6c757d !important; } /* 背景が暗いのに文字も暗い */
.hdbc1-text-light { color: #ffffff !important; } /* 背景が明るいのに文字も明るい */
/* ⭕️ OK用の文字色設定 */
.hdbc1-text-white { color: #ffffff !important; } /* 暗い背景には白文字 */
.hdbc1-text-black { color: #212529 !important; } /* 明るい背景には黒文字 */
.hdbc1-note {
font-size: 13px;
color: #dc3545;
font-weight: bold;
line-height: 1.5;
border-top: 1px dashed #ccc;
padding-top: 15px;
text-align: left;
}
.hdbc1-note-ok { color: #198754; }
/* 表示の切り替え */
.target-good-hdbc1 { display: none; }
#hdbc1-bad:checked ~ .hdbc1-demo-area .target-good-hdbc1 { display: none; }
#hdbc1-bad:checked ~ .hdbc1-demo-area .target-bad-hdbc1 { display: block; }
#hdbc1-good:checked ~ .hdbc1-demo-area .target-bad-hdbc1 { display: none; }
#hdbc1-good:checked ~ .hdbc1-demo-area .target-good-hdbc1 { display: block; }枠線を消す・角を丸くする
ボタンをおしゃれに見せる簡単な方法が「枠線の消去」と「角丸の適用」です。
標準の<button>には、立体感を出すための古い枠線が設定されています。
モダンなフラットデザインにするには、border: none;で枠線を消すことが必須です。
その後、border-radiusプロパティを使って角を丸くすることでクリックしやすい印象を与えます。
ブラウザ標準のダサい枠線が残っています。
border: none; で枠線を消し、フラットにしました。
border-radius: 30px; で角を丸くし、モダンな印象に!
HTMLコード表示
<div class="hdbt2-wrapper">
<input type="radio" name="hdbt2-state" id="hdbt2-step1" class="hdbt2-radio" checked>
<input type="radio" name="hdbt2-state" id="hdbt2-step2" class="hdbt2-radio">
<input type="radio" name="hdbt2-state" id="hdbt2-step3" class="hdbt2-radio">
<div class="hdbt2-controls">
<label for="hdbt2-step1" class="hdbt2-btn">1. デフォルト</label>
<label for="hdbt2-step2" class="hdbt2-btn">2. 枠線を消す</label>
<label for="hdbt2-step3" class="hdbt2-btn">3. 角を丸くする</label>
</div>
<div class="hdbt2-demo-area">
<div class="hdbt2-btn-container target-step1">
<button class="hdbt2-ui-btn hdbt2-style-1">クリック!</button>
<p class="hdbt2-note">ブラウザ標準のダサい枠線が残っています。</p>
</div>
<div class="hdbt2-btn-container target-step2">
<button class="hdbt2-ui-btn hdbt2-style-2">クリック!</button>
<p class="hdbt2-note">border: none; で枠線を消し、フラットにしました。</p>
</div>
<div class="hdbt2-btn-container target-step3">
<button class="hdbt2-ui-btn hdbt2-style-3">クリック!</button>
<p class="hdbt2-note">border-radius: 30px; で角を丸くし、モダンな印象に!</p>
</div>
</div>
</div>CSSコード表示
.hdbt2-wrapper {
background-color: #f8f9fa;
padding: 20px;
border: 1px solid #dee2e6;
border-radius: 4px;
font-family: sans-serif;
}
.hdbt2-radio { display: none; }
.hdbt2-controls {
display: flex;
justify-content: center;
gap: 10px;
margin-bottom: 20px;
flex-wrap: wrap;
}
.hdbt2-btn {
background-color: #e9ecef;
padding: 10px 15px;
border-radius: 4px;
cursor: pointer;
font-weight: bold;
color: #495057;
transition: 0.2s;
font-size: 14px;
}
#hdbt2-step1:checked ~ .hdbt2-controls [for="hdbt2-step1"],
#hdbt2-step2:checked ~ .hdbt2-controls [for="hdbt2-step2"],
#hdbt2-step3:checked ~ .hdbt2-controls [for="hdbt2-step3"] {
background-color: #198754;
color: white;
}
.hdbt2-demo-area {
background-color: #ffffff;
border: 2px dashed #adb5bd;
padding: 40px 20px;
display: flex;
justify-content: center;
text-align: center;
}
.hdbt2-btn-container { width: 100%; max-width: 300px; }
.hdbt2-note { margin-top: 15px; font-size: 13px; color: #555; font-weight: bold; line-height: 1.5; }
/* 共通ベーススタイル(SWELLリセット) */
.hdbt2-ui-btn {
background-color: #198754 !important;
color: white !important;
font-size: 18px !important;
font-weight: bold !important;
padding: 15px 40px !important;
cursor: pointer !important;
}
/* 1. デフォルト(意図的に古いborderをつける) */
.hdbt2-style-1 { border: 3px outset #ccc !important; border-radius: 0 !important; }
/* 2. 枠線を消す */
.hdbt2-style-2 { border: none !important; border-radius: 0 !important; }
/* 3. 角丸 */
.hdbt2-style-3 { border: none !important; border-radius: 30px !important; }
.target-step2, .target-step3 { display: none; }
#hdbt2-step1:checked ~ .hdbt2-demo-area .target-step1 { display: block; }
#hdbt2-step2:checked ~ .hdbt2-demo-area .target-step1 { display: none; }
#hdbt2-step2:checked ~ .hdbt2-demo-area .target-step2 { display: block; }
#hdbt2-step3:checked ~ .hdbt2-demo-area .target-step1 { display: none; }
#hdbt2-step3:checked ~ .hdbt2-demo-area .target-step3 { display: block; }文字装飾に関するborderやfont-sizeなどの内容を知りたい人は「【html&css】文字装飾に関するWebデザインまとめ」を一読ください。
マウスホバー(hover)時の色変更や3Dエフェクト
ユーザーがボタンの上にマウスを乗せた際に色を変えるには、CSSの:hover疑似クラスを使用します。
さらに、影(box-shadow)とY軸の移動(transform: translateY)を組み合わせることで、実際に押し込めるような立体的・3Dなボタンを実装できます。
初心者が「3Dボタン」を作ろうとした際、影をつけるところまでは上手くいくのですが、「押した時の沈み込み」を忘れてしまうことがあります。
押した時に影を消し、ボタン自体を下にズラす(:active疑似クラスの使用)ことで、「リアルな押し心地」のUXが実現できます。
※クリックした瞬間(:active状態)に、box-shadow(影)を消して、transformで下方向に移動させています。
HTMLコード表示
<div class="hdbt3-wrapper">
<div class="hdbt3-demo-area">
<div class="hdbt3-box">
<button class="hdbt3-ui-3d-btn">購入画面へ進む</button>
<p class="hdbt3-note">※クリックした瞬間(:active状態)に、box-shadow(影)を消して、transformで下方向に移動させています。</p>
</div>
</div>
</div>CSSコード表示
.hdbt3-wrapper {
background-color: #f8f9fa;
padding: 20px;
border: 1px solid #dee2e6;
border-radius: 4px;
font-family: sans-serif;
}
.hdbt3-demo-area {
background-color: #ffffff;
border: 2px dashed #adb5bd;
padding: 50px 20px;
display: flex;
justify-content: center;
text-align: center;
}
.hdbt3-box { width: 100%; max-width: 400px; }
/* 3Dボタンの強力なCSS */
.hdbt3-ui-3d-btn {
all: unset !important;
display: inline-block !important;
background-color: #ff9800 !important; /* オレンジの背景 */
color: white !important;
font-size: 18px !important;
font-weight: bold !important;
padding: 15px 40px !important;
border-radius: 8px !important;
cursor: pointer !important;
box-sizing: border-box !important;
/* 影を使って立体感を出す魔法(下に5pxの濃いオレンジの影) */
box-shadow: 0 5px 0 #e65100 !important;
transition: all 0.1s ease !important; /* スピードを速めにするとリアル */
position: relative !important;
top: 0 !important;
}
/* マウスオーバー時(少し明るくする) */
.hdbt3-ui-3d-btn:hover {
background-color: #ffa726 !important;
}
/* クリック時(沈み込むエフェクト) */
.hdbt3-ui-3d-btn:active {
box-shadow: 0 0 0 transparent !important; /* 影を消す */
top: 5px !important; /* 影の分だけ下に移動させる */
}
.hdbt3-note {
margin-top: 30px;
font-size: 13px;
color: #666;
line-height: 1.5;
border-top: 1px dashed #ccc;
padding-top: 15px;
}画像をボタンにする方法
テキストの代わりに、デザインツールで作成した画像をボタンとして使用したい場合があります。
これには、<button>タグの中に<img>タグを入れる方法とCSSのbackground-imageを使って背景として画像を使う方法の2種類があります。
よくあるミスが「<button>タグを空っぽにして、CSSのbackground-imageで画像を表示させる」という実装です。
この方法だと、視覚障害者の方が利用するスクリーンリーダー(音声読み上げソフト)がボタンに到達した際、「何もないボタン」として読み上げられてしまい、機能が伝わりません。
また、SEOの観点でもマイナスです。
画像をボタンにする場合は、「<button>の中に<img>タグを配置し、alt属性(代替テキスト)に『送信する』などの目的をしっかり記述する」のが使いやすいでしょう。
<img src=”button-banner.png” alt=”無料トライアルに申し込む”>
</button>
※CSSの背景画像ではなく、imgタグ(ここではダミーdiv)を中に入れ、alt属性を持たせることがSEOとアクセシビリティの観点で重要です。
HTMLコード表示
<div class="hdbt4-wrapper">
<div class="hdbt4-demo-area">
<div class="hdbt4-box">
<div class="hdbt4-code">
<button type="button" class="image-btn"><br>
<img src="button-banner.png" alt="無料トライアルに申し込む"><br>
</button>
</div>
<button type="button" class="hdbt4-ui-image-btn" onclick="alert('画像ボタンがクリックされました')">
<div class="hdbt4-dummy-image">
✨ 無料トライアルに申し込む
</div>
</button>
<p class="hdbt4-note">※CSSの背景画像ではなく、imgタグ(ここではダミーdiv)を中に入れ、alt属性を持たせることがSEOとアクセシビリティの観点で重要です。</p>
</div>
</div>
</div>CSSコード表示
.hdbt4-wrapper {
background-color: #f8f9fa;
padding: 20px;
border: 1px solid #dee2e6;
border-radius: 4px;
font-family: sans-serif;
}
.hdbt4-demo-area {
background-color: #ffffff;
border: 2px dashed #adb5bd;
padding: 30px 20px;
display: flex;
justify-content: center;
}
.hdbt4-box { width: 100%; max-width: 450px; text-align: center; }
.hdbt4-code {
background-color: #282c34;
color: #abb2bf;
padding: 15px;
font-family: monospace;
font-size: 13px;
border-radius: 4px;
margin-bottom: 25px;
line-height: 1.5;
text-align: left;
}
/* 画像ボタンのリセットCSS */
.hdbt4-ui-image-btn {
all: unset !important;
display: inline-block !important;
cursor: pointer !important;
transition: opacity 0.2s ease !important;
padding: 0 !important;
}
.hdbt4-ui-image-btn:hover {
opacity: 0.8 !important; /* マウスオーバーで少し薄くしてクリック感を出す */
}
/* 画像の代わりに使用しているダミーブロック(グラデーションでバナーっぽく) */
.hdbt4-dummy-image {
background: linear-gradient(135deg, #f093fb 0%, #f5576c 100%);
color: white;
font-weight: bold;
font-size: 18px;
padding: 20px 40px;
border-radius: 10px;
box-shadow: 0 4px 10px rgba(0,0,0,0.15);
}
.hdbt4-note {
margin-top: 25px;
font-size: 13px;
color: #333;
line-height: 1.5;
text-align: left;
border-top: 1px dashed #ccc;
padding-top: 15px;
}ボタンを無効化(非活性)・非表示にする方法
Webアプリケーションやフォーム画面において、「必須項目が入力されるまで送信できない」「権限がないユーザーには操作させない」といった制御はよく行われます。
ボタンを操作できない状態にするには、ボタンをクリックできないようにする方法とボタン自体を画面から消す方法の2パターンがあります。
disabled属性でクリックできないようにする- ボタンそのものを非表示にする
disabled属性でクリックできないようにする
ボタンをクリックできない状態にするには、<button>タグにdisabled属性を付与します。
ブラウザはボタンを非活性状態として扱い、クリックイベントが一切発生しなくなります。
送信する
</button>
※通常のボタンです。クリックすると処理(アラート)が実行されます。
送信する
</button>
※disabled属性によりクリックが無効化されています。CSSの :disabled 疑似クラスでグレーアウトさせ、押せないことを視覚的に伝えています。
HTMLコード表示
<div class="hbdis1-wrapper">
<input type="radio" name="hbdis1-state" id="hbdis1-active" class="hbdis1-radio" checked>
<input type="radio" name="hbdis1-state" id="hbdis1-disabled" class="hbdis1-radio">
<div class="hbdis1-controls">
<label for="hbdis1-active" class="hbdis1-btn">⭕️ 活性状態 (クリック可)</label>
<label for="hbdis1-disabled" class="hbdis1-btn">❌ 非活性状態 (disabled)</label>
</div>
<div class="hbdis1-demo-area">
<div class="hbdis1-box target-active-hbdis1">
<div class="hbdis1-code">
<button class="btn"><br>
送信する<br>
</button>
</div>
<div class="hbdis1-action">
<button class="hbdis1-ui-btn" onclick="alert('送信処理を実行しました!')">送信する</button>
</div>
<p class="hbdis1-note">※通常のボタンです。クリックすると処理(アラート)が実行されます。</p>
</div>
<div class="hbdis1-box target-disabled-hbdis1">
<div class="hbdis1-code hbdis1-code-disabled">
<button class="btn" <span class="hbdis1-highlight">disabled</span>><br>
送信する<br>
</button>
</div>
<div class="hbdis1-action">
<button class="hbdis1-ui-btn" disabled onclick="alert('これは実行されません')">送信する</button>
</div>
<p class="hbdis1-note hbdis1-note-disabled">※disabled属性によりクリックが無効化されています。CSSの :disabled 疑似クラスでグレーアウトさせ、押せないことを視覚的に伝えています。</p>
</div>
</div>
</div>CSSコード表示
.hbdis1-wrapper {
background-color: #f8f9fa;
padding: 20px;
border: 1px solid #dee2e6;
border-radius: 4px;
font-family: sans-serif;
}
.hbdis1-radio { display: none; }
.hbdis1-controls {
display: flex;
justify-content: center;
gap: 10px;
margin-bottom: 20px;
flex-wrap: wrap;
}
.hbdis1-btn {
background-color: #e9ecef;
padding: 10px 15px;
border-radius: 4px;
cursor: pointer;
font-weight: bold;
color: #495057;
transition: 0.2s;
font-size: 14px;
}
#hbdis1-active:checked ~ .hbdis1-controls [for="hbdis1-active"] { background-color: #198754; color: white; }
#hbdis1-disabled:checked ~ .hbdis1-controls [for="hbdis1-disabled"] { background-color: #6c757d; color: white; }
.hbdis1-demo-area {
background-color: #ffffff;
border: 2px dashed #adb5bd;
padding: 30px 20px;
display: flex;
justify-content: center;
}
.hbdis1-box { width: 100%; max-width: 400px; }
.hbdis1-code {
background-color: #282c34;
color: #abb2bf;
padding: 15px;
font-family: monospace;
font-size: 13px;
border-radius: 4px;
margin-bottom: 20px;
line-height: 1.5;
}
.hbdis1-highlight { color: #e06c75; font-weight: bold; }
.hbdis1-action { text-align: center; margin-bottom: 20px; }
/* 共通ボタンの基本スタイル(SWELLリセット含む) */
.hbdis1-ui-btn {
all: unset !important;
display: inline-block !important;
background-color: #0d6efd !important;
color: white !important;
font-size: 16px !important;
font-weight: bold !important;
padding: 15px 40px !important;
border-radius: 6px !important;
cursor: pointer !important;
box-sizing: border-box !important;
text-align: center !important;
transition: 0.2s !important;
}
.hbdis1-ui-btn:hover { background-color: #0b5ed7 !important; }
/* ★disabled属性が付いているボタン専用のスタイル(グレーアウトしてカーソルを変える) */
.hbdis1-ui-btn:disabled {
background-color: #e9ecef !important;
color: #adb5bd !important;
cursor: not-allowed !important; /* カーソルを禁止マークにする */
border: 1px solid #ced4da !important;
}
.hbdis1-note { font-size: 13px; color: #198754; font-weight: bold; line-height: 1.5; }
.hbdis1-note-disabled { color: #6c757d; }
.target-disabled-hbdis1 { display: none; }
#hbdis1-active:checked ~ .hbdis1-demo-area .target-disabled-hbdis1 { display: none; }
#hbdis1-active:checked ~ .hbdis1-demo-area .target-active-hbdis1 { display: block; }
#hbdis1-disabled:checked ~ .hbdis1-demo-area .target-active-hbdis1 { display: none; }
#hbdis1-disabled:checked ~ .hbdis1-demo-area .target-disabled-hbdis1 { display: block; }ボタンそのものを非表示にする
画面上からボタンを消したい場合は、CSSのdisplay: none;を使用します。
また、HTML5から追加されたhidden属性をタグに直接書き込むことでも同様に非表示可能です。
条件によって再び表示させたい場合は、CSSでdisplay: block;等に戻す処理を行います。
この文章の位置に注目してください。
現在は表示状態です。
HTMLコード表示
<div class="hbdis2-wrapper">
<input type="radio" name="hbdis2-state" id="hbdis2-visible" class="hbdis2-radio" checked>
<input type="radio" name="hbdis2-state" id="hbdis2-none" class="hbdis2-radio">
<input type="radio" name="hbdis2-state" id="hbdis2-hidden" class="hbdis2-radio">
<div class="hbdis2-controls">
<label for="hbdis2-visible" class="hbdis2-btn">通常表示</label>
<label for="hbdis2-none" class="hbdis2-btn">⭕️ display: none;</label>
<label for="hbdis2-hidden" class="hbdis2-btn">❌ visibility: hidden;</label>
</div>
<div class="hbdis2-demo-area">
<div class="hbdis2-box">
<div class="hbdis2-content">上の文章です。</div>
<div class="hbdis2-btn-container">
<button class="hbdis2-ui-btn target-btn-hbdis2">消えるボタン</button>
</div>
<div class="hbdis2-content">下の文章です。<br>この文章の位置に注目してください。</div>
</div>
</div>
<div class="hbdis2-explanation">
<p class="hbdis2-desc" id="desc-visible">現在は表示状態です。</p>
<p class="hbdis2-desc" id="desc-none" style="display:none; color:#198754;"><strong>【display: none;】</strong><br>ボタンの空間ごと完全に消滅するため、下の文章が自然に上に詰まりました。</p>
<p class="hbdis2-desc" id="desc-hidden" style="display:none; color:#dc3545;"><strong>【visibility: hidden;】</strong><br>ボタンは見えなくなりましたが、透明な箱として空間が残るため、不自然な空白(隙間)ができてしまいました。</p>
</div>
</div>CSSコード表示
.hbdis2-wrapper {
background-color: #f8f9fa;
padding: 20px;
border: 1px solid #dee2e6;
border-radius: 4px;
font-family: sans-serif;
}
.hbdis2-radio { display: none; }
.hbdis2-controls {
display: flex;
justify-content: center;
gap: 10px;
margin-bottom: 20px;
flex-wrap: wrap;
}
.hbdis2-btn {
background-color: #e9ecef;
padding: 10px 15px;
border-radius: 4px;
cursor: pointer;
font-weight: bold;
color: #495057;
transition: 0.2s;
font-size: 14px;
}
#hbdis2-visible:checked ~ .hbdis2-controls [for="hbdis2-visible"] { background-color: #6c757d; color: white; }
#hbdis2-none:checked ~ .hbdis2-controls [for="hbdis2-none"] { background-color: #198754; color: white; }
#hbdis2-hidden:checked ~ .hbdis2-controls [for="hbdis2-hidden"] { background-color: #dc3545; color: white; }
.hbdis2-demo-area {
background-color: #ffffff;
border: 2px dashed #adb5bd;
padding: 30px 20px;
display: flex;
justify-content: center;
margin-bottom: 15px;
}
.hbdis2-box { width: 100%; max-width: 300px; text-align: center; }
.hbdis2-content {
background-color: #e9ecef;
padding: 15px;
border-radius: 4px;
font-size: 14px;
color: #333;
}
.hbdis2-btn-container {
margin: 15px 0; /* ボタンの上下の余白 */
}
/* ボタンの基本スタイル */
.hbdis2-ui-btn {
all: unset !important;
display: inline-block !important;
background-color: #0d6efd !important;
color: white !important;
font-weight: bold !important;
padding: 15px 40px !important;
border-radius: 6px !important;
box-sizing: border-box !important;
text-align: center !important;
}
/* ラジオボタンの状態に応じたCSSの切り替え */
#hbdis2-none:checked ~ .hbdis2-demo-area .target-btn-hbdis2 {
display: none !important; /* 空間ごと消す */
}
#hbdis2-hidden:checked ~ .hbdis2-demo-area .target-btn-hbdis2 {
visibility: hidden !important; /* 透明にするだけ(空間は残る) */
}
/* 説明文の切り替え */
.hbdis2-explanation {
background-color: #fff;
padding: 15px;
border: 1px solid #ccc;
border-radius: 4px;
}
.hbdis2-desc { margin: 0; font-size: 14px; line-height: 1.5; }
#hbdis2-visible:checked ~ .hbdis2-explanation #desc-visible { display: block !important; }
#hbdis2-none:checked ~ .hbdis2-explanation #desc-visible { display: none !important; }
#hbdis2-none:checked ~ .hbdis2-explanation #desc-none { display: block !important; }
#hbdis2-hidden:checked ~ .hbdis2-explanation #desc-visible { display: none !important; }
#hbdis2-hidden:checked ~ .hbdis2-explanation #desc-hidden { display: block !important; }ブロック要素に関するdisplayプロパティを詳しく知りたい人は「【html&css】displayの種類は?flexやinline-blockの違い」を一読ください。
JavaScript連動!onclickイベントと値の取得
HTMLの<button>タグが真価を発揮するのは、JavaScriptと連動させた時です。
ボタンがクリックされたという動作を合図に、様々な処理を実行させる仕組みを「イベント」と呼びます。
- onclickで関数を呼び出す(イベントリスナー)
- ボタンの値(value)を取得・設定する
- 意図しないsubmit(送信)を防ぐ方法
onclickで関数を呼び出す(イベントリスナー)
ボタンをクリックした際にJavaScriptの関数を呼び出す方法は、HTMLタグの中にonclick属性を記述することです。
実行する
</button>
※HTMLが汚れ、複雑なプログラムになった時にどこでエラーが起きているか探しにくくなります。
<button id=”myBtn”>実行する</button>
// JS側で動作を付与する(addEventListener)
const btn = document.getElementById(‘myBtn’);
btn.addEventListener(‘click’, () => {
alert(‘処理を実行’);
});
※HTML(構造)とJS(動作)が完全に分離され、プロらしい保守性の高いコードになります。
HTMLコード表示
<div class="hjev1-wrapper">
<input type="radio" name="hjev1-state" id="hjev1-bad" class="hjev1-radio" checked>
<input type="radio" name="hjev1-state" id="hjev1-good" class="hjev1-radio">
<div class="hjev1-controls">
<label for="hjev1-bad" class="hjev1-btn">❌ HTMLに直接書く (古い手法)</label>
<label for="hjev1-good" class="hjev1-btn">⭕️ addEventListener (モダンな手法)</label>
</div>
<div class="hjev1-demo-area">
<div class="hjev1-box target-bad-hjev1">
<div class="hjev1-code-editor">
<span class="hjev1-tag"><button <span class="hjev1-highlight">onclick="alert('処理を実行')"</span>></span><br>
実行する<br>
<span class="hjev1-tag"></button></span>
</div>
<div class="hjev1-action">
<button class="hjev1-ui-btn hjev1-ui-ng" onclick="alert('インラインで記述された処理です')">実行する</button>
</div>
<p class="hjev1-note">※HTMLが汚れ、複雑なプログラムになった時にどこでエラーが起きているか探しにくくなります。</p>
</div>
<div class="hjev1-box target-good-hjev1">
<div class="hjev1-code-editor">
<span class="hjev1-comment">// HTML側はidをつけるだけ</span><br>
<span class="hjev1-tag"><button id="myBtn"></span>実行する<span class="hjev1-tag"></button></span><br><br>
<span class="hjev1-comment">// JS側で動作を付与する(addEventListener)</span><br>
const btn = document.getElementById('myBtn');<br>
btn.<span class="hjev1-highlight">addEventListener</span>('click', () => {<br>
alert('処理を実行');<br>
});
</div>
<div class="hjev1-action">
<button class="hjev1-ui-btn hjev1-ui-ok" id="hjev1-modern-btn">実行する</button>
</div>
<p class="hjev1-note hjev1-note-ok">※HTML(構造)とJS(動作)が完全に分離され、プロらしい保守性の高いコードになります。</p>
</div>
</div>
</div>CSSコード表示
.hjev1-wrapper { background-color: #f8f9fa; padding: 20px; border: 1px solid #dee2e6; border-radius: 4px; font-family: sans-serif; }
.hjev1-radio { display: none; }
.hjev1-controls { display: flex; justify-content: center; gap: 10px; margin-bottom: 20px; flex-wrap: wrap; }
.hjev1-btn { background-color: #e9ecef; padding: 10px 15px; border-radius: 4px; cursor: pointer; font-weight: bold; color: #495057; transition: 0.2s; font-size: 14px; }
#hjev1-bad:checked ~ .hjev1-controls [for="hjev1-bad"] { background-color: #dc3545; color: white; }
#hjev1-good:checked ~ .hjev1-controls [for="hjev1-good"] { background-color: #198754; color: white; }
.hjev1-demo-area { background-color: #ffffff; border: 2px dashed #adb5bd; padding: 30px 20px; display: flex; justify-content: center; }
.hjev1-box { width: 100%; max-width: 450px; }
.hjev1-code-editor { background-color: #282c34; color: #abb2bf; padding: 15px; font-family: monospace; font-size: 13px; border-radius: 4px; margin-bottom: 20px; line-height: 1.6; }
.hjev1-tag { color: #e5c07b; }
.hjev1-highlight { color: #61afef; font-weight: bold; }
.hjev1-comment { color: #5c6370; font-style: italic; }
.hjev1-action { text-align: center; margin-bottom: 20px; }
.hjev1-ui-btn { all: unset !important; display: inline-block !important; color: white !important; font-size: 15px !important; font-weight: bold !important; padding: 12px 30px !important; border-radius: 6px !important; cursor: pointer !important; box-sizing: border-box !important; }
.hjev1-ui-ng { background-color: #dc3545 !important; }
.hjev1-ui-ok { background-color: #198754 !important; }
.hjev1-note { font-size: 13px; color: #dc3545; font-weight: bold; line-height: 1.5; }
.hjev1-note-ok { color: #198754; }
.target-good-hjev1 { display: none; }
#hjev1-bad:checked ~ .hjev1-demo-area .target-bad-hjev1 { display: block; }
#hjev1-good:checked ~ .hjev1-demo-area .target-bad-hjev1 { display: none; }
#hjev1-good:checked ~ .hjev1-demo-area .target-good-hjev1 { display: block; }JavaScriptコード表示
// OK例のモダンなボタンへのイベント付与
document.addEventListener('DOMContentLoaded', () => {
const modernBtn = document.getElementById('hjev1-modern-btn');
if(modernBtn) {
modernBtn.addEventListener('click', () => {
alert('addEventListenerで登録された処理です');
});
}
});ボタンの値(value)を取得・設定する
<button>タグには、画面に表示されるテキストとは別に裏側でシステムに渡すデータを持たせるvalue属性を設定できます。
例えば、ECサイトで「カートに入れる」というボタンがあった際、ユーザーに見せる文字は共通でも裏側では「商品ID」などの一意のデータをvalueに忍ばせ、クリックされた時に値を取り出すといった使い方が実務では頻出します。
カートに入れる
</button>
HTMLコード表示
<div class="hjev2-wrapper">
<div class="hjev2-demo-area">
<div class="hjev2-box">
<div class="hjev2-code">
<button id="itemBtn" <span class="hjev2-highlight">value="ITEM_999"</span>><br>
カートに入れる<br>
</button>
</div>
<div class="hjev2-action">
<button id="hjev2-target-btn" value="ITEM_999" class="hjev2-ui-btn">カートに入れる</button>
</div>
<div class="hjev2-data-panel">
<div class="hjev2-data-row">
<span>表側のテキスト (innerText):</span>
<span id="hjev2-display-text" class="hjev2-data-val">---</span>
</div>
<div class="hjev2-data-row">
<span>裏側のデータ (value):</span>
<span id="hjev2-display-value" class="hjev2-data-val hjev2-data-important">---</span>
</div>
</div>
</div>
</div>
</div>CSSコード表示
.hjev2-wrapper { background-color: #f8f9fa; padding: 20px; border: 1px solid #dee2e6; border-radius: 4px; font-family: sans-serif; }
.hjev2-demo-area { background-color: #ffffff; border: 2px dashed #adb5bd; padding: 30px 20px; display: flex; justify-content: center; }
.hjev2-box { width: 100%; max-width: 400px; text-align: center; }
.hjev2-code { background-color: #282c34; color: #abb2bf; padding: 15px; font-family: monospace; font-size: 13px; border-radius: 4px; margin-bottom: 20px; line-height: 1.5; text-align: left; }
.hjev2-highlight { color: #98c379; font-weight: bold; }
.hjev2-action { margin-bottom: 20px; }
.hjev2-ui-btn { all: unset !important; display: inline-block !important; background-color: #f39c12 !important; color: white !important; font-size: 16px !important; font-weight: bold !important; padding: 12px 40px !important; border-radius: 30px !important; cursor: pointer !important; box-shadow: 0 4px 6px rgba(0,0,0,0.1) !important; }
.hjev2-data-panel { background-color: #f1f3f5; padding: 15px; border-radius: 4px; text-align: left; border: 1px solid #ccc; }
.hjev2-data-row { margin-bottom: 10px; font-size: 14px; color: #333; font-weight: bold; display: flex; justify-content: space-between; }
.hjev2-data-row:last-child { margin-bottom: 0; }
.hjev2-data-val { font-family: monospace; background-color: #fff; padding: 2px 8px; border-radius: 3px; border: 1px solid #ccc; color: #666; }
.hjev2-data-important { color: #dc3545; border-color: #dc3545; background-color: #f8d7da; }JavaScriptコード表示
document.addEventListener('DOMContentLoaded', () => {
const btn = document.getElementById('hjev2-target-btn');
const textDisplay = document.getElementById('hjev2-display-text');
const valDisplay = document.getElementById('hjev2-display-value');
if(btn && textDisplay && valDisplay) {
btn.addEventListener('click', () => {
textDisplay.textContent = btn.innerText; // 表側の文字
valDisplay.textContent = btn.value; // 裏側のデータ
});
}
});意図しないsubmit(送信)を防ぐ方法
フォーム(<form>)内でボタンをトリガーとして使おうとした際、ボタンをクリックした瞬間に「画面がチカッと一瞬リロードされて、入力した内容が全部消える」という現象に、誰もが一度は遭遇します。
前述した「<button>タグの初期値がtype="submit"(送信)であること」が原因です。
これを防ぐには、以下の2つのアプローチが必須になります。
- HTML側で防ぐ
<button type="button">を明記し単なるボタンにする。 - JS側で防ぐ
type="submit"のまま送信前のチェック処理などを挟みたい場合は、関数内でevent.preventDefault()を呼び出す。
HTMLコード表示
<div class="hjev3-wrapper">
<input type="radio" name="hjev3-state" id="hjev3-bad" class="hjev3-radio" checked>
<input type="radio" name="hjev3-state" id="hjev3-good" class="hjev3-radio">
<div class="hjev3-controls">
<label for="hjev3-bad" class="hjev3-btn">❌ 対策なし (入力が消える)</label>
<label for="hjev3-good" class="hjev3-btn">⭕️ preventDefault (入力保持)</label>
</div>
<div class="hjev3-demo-area">
<div class="hjev3-box target-bad-hjev3">
<form class="hjev3-form">
<label>お名前(文字を入力してボタンを押してください)</label>
<input type="text" placeholder="山田 太郎" class="hjev3-input">
<button class="hjev3-ui-btn hjev3-ui-ng" onclick="alert('JSの処理が動いた直後、画面がリロードされて入力が消えます!')">チェックする</button>
</form>
</div>
<div class="hjev3-box target-good-hjev3">
<form class="hjev3-form">
<label>お名前(文字を入力してボタンを押してください)</label>
<input type="text" placeholder="山田 太郎" class="hjev3-input">
<button class="hjev3-ui-btn hjev3-ui-ok" onclick="event.preventDefault(); alert('送信をブロックしました!入力内容は消えずに保持されます。')">チェックする</button>
</form>
</div>
</div>
</div>CSSコード表示
.hjev3-wrapper { background-color: #f8f9fa; padding: 20px; border: 1px solid #dee2e6; border-radius: 4px; font-family: sans-serif; }
.hjev3-radio { display: none; }
.hjev3-controls { display: flex; justify-content: center; gap: 10px; margin-bottom: 20px; flex-wrap: wrap; }
.hjev3-btn { background-color: #e9ecef; padding: 10px 15px; border-radius: 4px; cursor: pointer; font-weight: bold; color: #495057; transition: 0.2s; font-size: 14px; }
#hjev3-bad:checked ~ .hjev3-controls [for="hjev3-bad"] { background-color: #dc3545; color: white; }
#hjev3-good:checked ~ .hjev3-controls [for="hjev3-good"] { background-color: #198754; color: white; }
.hjev3-demo-area { background-color: #ffffff; border: 2px dashed #adb5bd; padding: 30px 20px; display: flex; justify-content: center; }
.hjev3-box { width: 100%; max-width: 400px; }
.hjev3-form { background-color: #f1f3f5; padding: 20px; border-radius: 4px; border: 1px solid #ccc; display: flex; flex-direction: column; gap: 15px; }
.hjev3-form label { font-size: 13px; font-weight: bold; color: #333; }
.hjev3-input { padding: 10px; border: 1px solid #adb5bd; border-radius: 4px; font-size: 14px; }
.hjev3-ui-btn { all: unset !important; display: block !important; color: white !important; font-size: 15px !important; font-weight: bold !important; padding: 12px !important; border-radius: 4px !important; cursor: pointer !important; text-align: center !important; }
.hjev3-ui-ng { background-color: #dc3545 !important; }
.hjev3-ui-ok { background-color: #198754 !important; }
.target-good-hjev3 { display: none; }
#hjev3-bad:checked ~ .hjev3-demo-area .target-bad-hjev3 { display: block; }
#hjev3-good:checked ~ .hjev3-demo-area .target-bad-hjev3 { display: none; }
#hjev3-good:checked ~ .hjev3-demo-area .target-good-hjev3 { display: block; }ラジオボタンや特殊なボタンの実装
アンケートや設定画面で使われる「ラジオボタン」や複数の選択肢から1つを選ばせる機能は、正確なデータを取得するために欠かせません。
ここでは、ラジオボタンの正しいグループ化の方法からECサイトで必須の数量変更ボタンなど実務で頻出するボタンの実装方法を解説します。
- ラジオボタンのグループ化と初期選択
- 数量変更(プラスマイナス)ボタン
- Googleログインや翻訳・トップへ戻るボタンなど
ラジオボタンのグループ化と初期選択
複数の選択肢の中から「1つだけ」を選ばせるには、<input type="radio">を使用します。
予め特定の選択肢を選んだ状態にしておくには、該当のタグにchecked属性を付与します。
好きなフルーツは?(NG例)
※文字をクリックしても反応せず、丸ポチを複数選択できてしまうバグが発生しています。
好きなフルーツは?(OK例)
※文字部分をクリックしても選択でき、1つしか選べない正しい挙動になっています。
HTMLコード表示
<div class="hrbt1-wrapper">
<input type="radio" name="hrbt1-state" id="hrbt1-bad" class="hrbt1-radio" checked>
<input type="radio" name="hrbt1-state" id="hrbt1-good" class="hrbt1-radio">
<div class="hrbt1-controls">
<label for="hrbt1-bad" class="hrbt1-btn">❌ name不一致&labelなし</label>
<label for="hrbt1-good" class="hrbt1-btn">⭕️ 正しいグループ化&labelあり</label>
</div>
<div class="hrbt1-demo-area">
<div class="hrbt1-box target-bad-hrbt1">
<p class="hrbt1-q-title">好きなフルーツは?(NG例)</p>
<div class="hrbt1-form-group">
<div class="hrbt1-radio-item">
<input type="radio" name="fruit1"> りんご
</div>
<div class="hrbt1-radio-item">
<input type="radio" name="fruit2"> みかん
</div>
<div class="hrbt1-radio-item">
<input type="radio" name="fruit3"> バナナ
</div>
</div>
<p class="hrbt1-note">※文字をクリックしても反応せず、丸ポチを複数選択できてしまうバグが発生しています。</p>
</div>
<div class="hrbt1-box target-good-hrbt1">
<p class="hrbt1-q-title">好きなフルーツは?(OK例)</p>
<div class="hrbt1-form-group">
<label class="hrbt1-radio-item hrbt1-label-ok">
<input type="radio" name="fruit_ok" value="apple"> りんご
</label>
<label class="hrbt1-radio-item hrbt1-label-ok">
<input type="radio" name="fruit_ok" value="orange" checked> みかん
</label>
<label class="hrbt1-radio-item hrbt1-label-ok">
<input type="radio" name="fruit_ok" value="banana"> バナナ
</label>
</div>
<p class="hrbt1-note hrbt1-note-ok">※文字部分をクリックしても選択でき、1つしか選べない正しい挙動になっています。</p>
</div>
</div>
</div>CSSコード表示
.hrbt1-wrapper { background-color: #f8f9fa; padding: 20px; border: 1px solid #dee2e6; border-radius: 4px; font-family: sans-serif; }
.hrbt1-radio { display: none; }
.hrbt1-controls { display: flex; justify-content: center; gap: 10px; margin-bottom: 20px; flex-wrap: wrap; }
.hrbt1-btn { background-color: #e9ecef; padding: 10px 15px; border-radius: 4px; cursor: pointer; font-weight: bold; color: #495057; transition: 0.2s; font-size: 14px; }
#hrbt1-bad:checked ~ .hrbt1-controls [for="hrbt1-bad"] { background-color: #dc3545; color: white; }
#hrbt1-good:checked ~ .hrbt1-controls [for="hrbt1-good"] { background-color: #198754; color: white; }
.hrbt1-demo-area { background-color: #ffffff; border: 2px dashed #adb5bd; padding: 30px 20px; display: flex; justify-content: center; }
.hrbt1-box { width: 100%; max-width: 400px; background-color: #f1f3f5; padding: 20px; border-radius: 8px; border: 1px solid #ccc; }
.hrbt1-q-title { font-size: 16px; font-weight: bold; margin: 0 0 15px 0; color: #333; }
.hrbt1-form-group { display: flex; flex-direction: column; gap: 10px; margin-bottom: 20px; }
.hrbt1-radio-item { font-size: 15px; color: #333; display: flex; align-items: center; gap: 8px; padding: 5px 0; }
.hrbt1-label-ok { cursor: pointer; } /* labelにはカーソルを指マークにする */
.hrbt1-label-ok:hover { color: #198754; }
.hrbt1-note { font-size: 13px; color: #dc3545; font-weight: bold; line-height: 1.5; margin: 0; padding-top: 15px; border-top: 1px dashed #ccc; }
.hrbt1-note-ok { color: #198754; }
.target-good-hrbt1 { display: none; }
#hrbt1-bad:checked ~ .hrbt1-demo-area .target-bad-hrbt1 { display: block; }
#hrbt1-good:checked ~ .hrbt1-demo-area .target-bad-hrbt1 { display: none; }
#hrbt1-good:checked ~ .hrbt1-demo-area .target-good-hrbt1 { display: block; }数量変更(プラスマイナス)ボタン
ECサイトのカート画面などで、「購入する個数」を変更するためのボタンは、標準の<input type="number">だけではデザインが小さくスマホでは操作しづらいという難点があります。
実務では、左右に独立した「マイナスボタン」と「プラスボタン」を配置し、JavaScriptを使って中央の数値を増減させるUIが好まれます。
購入数量
※JavaScriptにより「1」未満には下がらないようにガードをかけています。また、readonly属性で直接文字を入力されるリスクを排除しています。
HTMLコード表示
<div class="hqtb-wrapper">
<div class="hqtb-demo-area">
<div class="hqtb-box">
<p class="hqtb-label">購入数量</p>
<div class="hqtb-control-group">
<button type="button" class="hqtb-ui-btn hqtb-btn-minus" id="hqtb-minus" onclick="updateQty(-1)">ー</button>
<input type="number" id="hqtb-input" class="hqtb-input-field" value="1" readonly>
<button type="button" class="hqtb-ui-btn hqtb-btn-plus" id="hqtb-plus" onclick="updateQty(1)">+</button>
</div>
<p class="hqtb-note">※JavaScriptにより「1」未満には下がらないようにガードをかけています。また、readonly属性で直接文字を入力されるリスクを排除しています。</p>
</div>
</div>
</div>CSSコード表示
.hqtb-wrapper { background-color: #f8f9fa; padding: 20px; border: 1px solid #dee2e6; border-radius: 4px; font-family: sans-serif; }
.hqtb-demo-area { background-color: #ffffff; border: 2px dashed #adb5bd; padding: 40px 20px; display: flex; justify-content: center; }
.hqtb-box { width: 100%; max-width: 350px; text-align: center; }
.hqtb-label { font-size: 15px; font-weight: bold; color: #333; margin: 0 0 15px 0; }
/* 数量変更UIのレイアウト */
.hqtb-control-group {
display: flex;
align-items: center;
justify-content: center;
margin-bottom: 25px;
}
/* 共通ボタンスタイル */
.hqtb-ui-btn {
all: unset !important;
display: flex !important;
align-items: center !important;
justify-content: center !important;
width: 45px !important;
height: 45px !important;
background-color: #f1f3f5 !important;
color: #333 !important;
font-size: 18px !important;
font-weight: bold !important;
border: 1px solid #ccc !important;
cursor: pointer !important;
box-sizing: border-box !important;
transition: 0.2s !important;
}
.hqtb-ui-btn:hover { background-color: #e9ecef !important; }
.hqtb-btn-minus { border-radius: 4px 0 0 4px !important; border-right: none !important; }
.hqtb-btn-plus { border-radius: 0 4px 4px 0 !important; border-left: none !important; }
/* 押せない状態のスタイル */
.hqtb-btn-disabled {
color: #adb5bd !important;
cursor: not-allowed !important;
background-color: #f8f9fa !important;
}
/* 入力欄スタイル */
.hqtb-input-field {
width: 60px;
height: 45px;
text-align: center;
font-size: 16px;
font-weight: bold;
border: 1px solid #ccc;
border-radius: 0;
box-sizing: border-box;
color: #333;
/* input[type=number] の矢印を消すCSS */
-moz-appearance: textfield;
}
.hqtb-input-field::-webkit-outer-spin-button,
.hqtb-input-field::-webkit-inner-spin-button {
-webkit-appearance: none;
margin: 0;
}
.hqtb-note { font-size: 13px; color: #666; font-weight: bold; line-height: 1.5; border-top: 1px dashed #ccc; padding-top: 15px; text-align: left;}JavaScriptコード表示
function updateQty(change) {
const input = document.getElementById('hqtb-input');
const minusBtn = document.getElementById('hqtb-minus');
let currentVal = parseInt(input.value);
// 新しい値を計算
let newVal = currentVal + change;
// 値が1未満にならないようにガード
if(newVal < 1) {
newVal = 1;
}
// 入力欄を更新
input.value = newVal;
// 1の時はマイナスボタンをグレーアウト(視覚的なフィードバック)
if(newVal === 1) {
minusBtn.classList.add('hqtb-btn-disabled');
} else {
minusBtn.classList.remove('hqtb-btn-disabled');
}
}
// 初期状態のボタン色設定
document.addEventListener('DOMContentLoaded', () => {
const minusBtn = document.getElementById('hqtb-minus');
if(minusBtn) minusBtn.classList.add('hqtb-btn-disabled');
});Googleログインや翻訳・トップへ戻るボタンなど
Webサイトには、単なるフォーム送信とは異なる特殊な役割を持ったボタンが多数存在します。
例えば、ユーザーの利便性を高める「Googleでログイン」ボタンやアプリストアへ誘導する「Google Play)」のボタンは、公式のロゴとブランドカラーを使ったデザインが求められます。
また、長い記事を読んだ後に画面の一番上までスクロールさせる「トップへ戻る」ボタンや多言語サイトにおける「翻訳」ボタンなどもサイトのUXにおいて重要な要素です。
↑ トップへ
</button>
※URLを汚すことなく、滑らかなスクロール(アニメーション)で上部へ戻ります。
HTMLコード表示
<div class="hgtp-wrapper">
<input type="radio" name="hgtp-state" id="hgtp-bad" class="hgtp-radio" checked>
<input type="radio" name="hgtp-state" id="hgtp-good" class="hgtp-radio">
<div class="hgtp-controls">
<label for="hgtp-bad" class="hgtp-btn">❌ aタグの「#」で戻る</label>
<label for="hgtp-good" class="hgtp-btn">⭕️ JSでスムーススクロール</label>
</div>
<div class="hgtp-demo-area">
<div class="hgtp-box target-bad-hgtp">
<div class="hgtp-code">
<a href="#" class="top-btn"><br>
↑ トップへ<br>
</a>
</div>
<div class="hgtp-action">
<a href="#dummy-top" onclick="alert('ページ上部に一瞬で飛びますが、実際の環境ではURLの末尾に「#」が付いてしまいます。')" class="hgtp-ui-btn hgtp-ui-ng">↑ トップへ戻る</a>
</div>
<p class="hgtp-note">※スクロールが一瞬で味気なく、ブラウザのURLバーが「#」で汚れてしまいます。</p>
</div>
<div class="hgtp-box target-good-hgtp">
<div class="hgtp-code hgtp-code-ok">
<button onclick="window.scrollTo({ top: 0, behavior: 'smooth' })"><br>
↑ トップへ<br>
</button>
</div>
<div class="hgtp-action">
<button onclick="window.scrollTo({ top: 0, behavior: 'smooth' })" class="hgtp-ui-btn hgtp-ui-ok">↑ トップへ戻る</button>
</div>
<p class="hgtp-note hgtp-note-ok">※URLを汚すことなく、滑らかなスクロール(アニメーション)で上部へ戻ります。</p>
</div>
</div>
</div>CSSコード表示
.hgtp-wrapper { background-color: #f8f9fa; padding: 20px; border: 1px solid #dee2e6; border-radius: 4px; font-family: sans-serif; }
.hgtp-radio { display: none; }
.hgtp-controls { display: flex; justify-content: center; gap: 10px; margin-bottom: 20px; flex-wrap: wrap; }
.hgtp-btn { background-color: #e9ecef; padding: 10px 15px; border-radius: 4px; cursor: pointer; font-weight: bold; color: #495057; transition: 0.2s; font-size: 14px; }
#hgtp-bad:checked ~ .hgtp-controls [for="hgtp-bad"] { background-color: #dc3545; color: white; }
#hgtp-good:checked ~ .hgtp-controls [for="hgtp-good"] { background-color: #198754; color: white; }
.hgtp-demo-area { background-color: #ffffff; border: 2px dashed #adb5bd; padding: 30px 20px; display: flex; justify-content: center; }
.hgtp-box { width: 100%; max-width: 400px; text-align: center; }
.hgtp-code { background-color: #f8d7da; color: #842029; padding: 15px; font-family: monospace; font-size: 13px; border-radius: 4px; border-left: 4px solid #dc3545; margin-bottom: 20px; text-align: left; }
.hgtp-code-ok { background-color: #d1e7dd; color: #0f5132; border-left: 4px solid #198754; }
/* 共通ボタンスタイル */
.hgtp-ui-btn {
all: unset !important;
display: inline-block !important;
color: white !important;
font-size: 14px !important;
font-weight: bold !important;
padding: 12px 30px !important;
border-radius: 30px !important;
cursor: pointer !important;
text-decoration: none !important;
box-shadow: 0 4px 6px rgba(0,0,0,0.1) !important;
}
.hgtp-ui-ng { background-color: #6c757d !important; }
.hgtp-ui-ok { background-color: #212529 !important; }
.hgtp-note { font-size: 13px; color: #dc3545; font-weight: bold; line-height: 1.5; margin-top: 20px; text-align: left;}
.hgtp-note-ok { color: #198754; }
.target-good-hgtp { display: none; }
#hgtp-bad:checked ~ .hgtp-demo-area .target-bad-hgtp { display: block; }
#hgtp-good:checked ~ .hgtp-demo-area .target-bad-hgtp { display: none; }
#hgtp-good:checked ~ .hgtp-demo-area .target-good-hgtp { display: block; }まとめ
分かりやすいようにまとめを記載します。
<input type="button">と異なり、内部にアイコンや画像などのHTML要素を配置できる。- 「ページ遷移」には
<a>タグ、「アクション」には<button>タグを使用するのがSEO・アクセシビリティの基本。 type="submit":フォームデータを送信する。type="button":送信を行わず、JSなどを起動する単なるボタンとして機能する。- 属性を省略すると
submit扱いとなり、予期せぬ画面リロードのバグを引き起こす。 - ボタンの大きさは
paddingで内側の余白を取って調整する。 - 中央寄せ・右寄せは、ボタン自身ではなく親要素に対して
text-alignを指定する。 border: none;でブラウザ標準の枠線を消去し、必要に応じてborder-radiusで角を丸くする。:hoverや:activeを用い、ホバー時の色変化やクリック時の沈み込みを実装する。- クリックさせない場合は
disable属性を付与し、CSS(:disabled)でグレーアウトさせ視覚的に伝える。 - 画面から消し去る場合は、
display: none;を使用する。 - HTMLに
onclickを書く古い手法は避け、JSファイル側でaddEventListenerを用いてイベントを登録する。 - システムへ渡す裏側のデータは、テキストではなく
value属性に持たせて取得する。 - 意図しないフォーム送信(画面リロード)を防ぐには、JS内で
event.preventDefault()を実行する。
よくある質問(FAQ)
HTMLでボタンをクリックしたら別のページに飛ぶにはどうすればいいですか?
推奨されるのは、<button>タグではなく<a>タグ(リンク)を使用し、CSSでボタンのような見た目に装飾する方法です。
<button>タグで画面遷移させたい場合は、JavaScriptを用いて<button onclick="location.href='遷移先のURL'"> のように記述します。
<button>タグと<input type=”button”>の違いは何ですか?
デザインの「自由度」が異なります。
<button>タグは開始タグと終了タグ(</button>)を持つため、文字だけでなくアイコン画像などを中に入れることができます。
一方、<input>タグは中にHTMLを含めることができず、テキストしか表示できません。
Web制作では、柔軟な<button>タグの使用が主流です。
ボタンを画面の中央に配置(中央寄せ)するにはどうすればいいですか?
ボタンのタグにtext-align: center;を指定しても中央には寄りません。
ボタンは標準で「インラインブロック要素」として扱われるため、ボタンを囲んでいる「親要素(<div>タグなど)」に対して、CSSでtext-align: center;を指定してください。
ボタンを押すと勝手に画面がリロード(再読み込み)されてしまうのはなぜですか?
<button>タグにtype属性を指定していないことが原因です。
HTMLの仕様上、typeを書き忘れると「データを送信するボタン(type="submit")」として扱われます。
フォームの送信ではなく、単なるクリックイベントとして使いたい場合は、<button type="button">と明記してください。
ボタンの色や枠線のデザインを変えるにはどうすればいいですか?
HTMLに直接書き込むのではなく、CSSのプロパティを使用します。
背景色はbackground-color、文字色はcolorで変更します。
また、ブラウザ標準の立体的な枠線を消したい場合はborder: none;を指定し、角を丸くしたい場合はborder-radiusを使用してモダンなデザインに整えます。

