「ログイン済みの人だけにメッセージを出す」「キャンペーンバナーを一度閉じたら再表示しない」など、Cookieの有無で要素の表示・非表示を切り替えたい場面はよくあります。
やることはシンプルで、①Cookieを読み取る → ②有無に応じて要素のクラスを切り替えるだけです。ただし、Cookieの読み取りには意外な落とし穴があり、表示の切り替え方も一方通行だとタイトルどおりの「表示・非表示」になりません。この記事では、つまずきやすい点をつぶしながらそのまま動くコードで解説します。
getCookie(name) !== null で判定し、表示の切り替えは classList.toggle("hidden", 条件) で双方向に行います。実行は DOMContentLoaded で。さらに短く書くなら element.hidden 一行でも切り替えられます。HTMLとCSSの下準備(チラつき対策)
まず、表示を切り替える要素を用意します。ポイントは、CSSで最初から非表示にしておくことです。こうすると、本来見せたくないユーザーに要素が一瞬表示されてしまう「チラつき(ちらつき)」を防げます。
<div id="message" class="hidden"> このメッセージは特定のCookieがある場合に表示されます。 </div>
.hidden {
display: none;
}
Cookieを安全に読み取る(getCookie)
document.cookie は "key1=value1; key2=value2" という1本の文字列です。ここから目的のCookieを取り出す関数を作ります。
cookie.split("=") で分割すると、値に = が含まれるCookie(Base64エンコードした値など)が途中で切れてしまいます。最初の = の位置で区切るのが正解です。function getCookie(name) {
const cookies = document.cookie.split("; ");
for (const cookie of cookies) {
const eq = cookie.indexOf("="); // 最初の = だけで区切る
const key = decodeURIComponent(cookie.slice(0, eq));
if (key === name) {
return decodeURIComponent(cookie.slice(eq + 1));
}
}
return null; // 見つからなければ null
}
Cookieが存在するかどうかは、戻り値が null かどうかで判定します。if (getCookie("x")) のように真偽値で判定すると、値が "0" や空文字のCookieを「無い」と誤判定するため、!== null で判定するのが安全です。Cookieの取得・設定・削除の基本はCookieの取得・設定・削除の方法でまとめています。
Cookieの有無で表示を切り替える(双方向)
本題の切り替えです。Cookieがあれば表示・なければ非表示と双方向にするため、classList.toggle() の第2引数(強制フラグ)を使います。第2引数が true ならクラスを付け、false なら外します。
function applyVisibility() {
const hasCookie = getCookie("myCookie") !== null;
const el = document.getElementById("message");
// Cookieが無いとき hidden を付ける(= 表示する条件は付けない)
el.classList.toggle("hidden", !hasCookie);
}
// 画像などの読み込みを待たず、DOMが組み上がった時点で実行
document.addEventListener("DOMContentLoaded", applyVisibility);
window.onload ではなく DOMContentLoaded を使う点が重要です。window.onload は画像など全リソースの読み込み完了まで待つため発火が遅く、表示の切り替えが目に見えて遅れることがあります。classList の詳しい使い方はclassListの使い方完全ガイドを参照してください。
もっと短く書く(element.hidden)
専用のCSSクラスを用意せず、hiddenプロパティで切り替える方法もあります。element.hidden = true でHTML標準の hidden 属性が付き、要素が非表示になります。
const el = document.getElementById("message");
// Cookieが無ければ非表示、あれば表示
el.hidden = getCookie("myCookie") === null;
display を指定するCSS(例:#message { display: block; })があると、そちらが hidden 属性より優先され、非表示にならないことがあります。その場合は前述の .hidden クラス方式を使うか、CSSで[hidden] { display: none; } を明示してください。表示の前に:Cookieをセット・削除する
表示を切り替えるには、そもそも判定対象のCookieが必要です。ログインボタンやバナーの「閉じる」操作などに合わせて、次のようにセット・削除します。
// 30日間有効なCookieをセット
function setCookie(name, value, days) {
const maxAge = days * 24 * 60 * 60; // 秒数に変換
document.cookie =
`${encodeURIComponent(name)}=${encodeURIComponent(value)}` +
`; max-age=${maxAge}; path=/; SameSite=Lax`;
}
// Cookieを削除(max-age=0 で即時失効)
function deleteCookie(name) {
document.cookie = `${encodeURIComponent(name)}=; max-age=0; path=/`;
}
setCookie("myCookie", "1", 30); // → 以降 applyVisibility() で表示される
// deleteCookie("myCookie"); // → 次回から非表示に戻る
HttpOnly / Secure 属性を付けて発行してください。JavaScriptで扱ってよいのは「バナーを閉じたか」などの表示制御用の値に限ります。CookieとlocalStorageのどちらを使うべきか
「表示状態を覚えておく」だけが目的でサーバーに送る必要がないなら、localStorageの方が手軽な場合も多いです。判断の目安は次のとおりです。
- Cookie:サーバーにも値を送りたい/有効期限を細かく管理したいとき
- localStorage:クライアント側だけで使う表示状態の保存(容量も大きい)
localStorageでの実装はlocalStorageの使い方完全ガイド、保存期間の違いはlocalStorageとsessionStorageの違いと使い分けで詳しく解説しています。
よくある質問(FAQ)
document.cookie で "key=value; key=value" 形式の文字列が取得できます。split("; ") で分割し、最初の = の位置でキーと値に分けます。記述を簡単にしたい場合は js-cookie などのライブラリも使えます。HttpOnly Cookieが安全で、UIの表示状態の保存にはlocalStorageが向いています。DOMContentLoaded が推奨です。window.onload は画像など全リソースの読み込み完了を待つため発火が遅く、切り替えが目に見えて遅れることがあります。HTMLの構造さえ揃えばよい処理は DOMContentLoaded で十分です。Set-Cookie ヘッダーで HttpOnly(JSからのアクセス禁止)、Secure(HTTPS限定)、SameSite(CSRF対策)を設定します。JavaScriptからは HttpOnly を付けられないため、秘密情報のCookieはサーバーサイドで発行するのが原則です。まとめ
Cookieの有無で要素を表示・非表示するには、①最初は非表示にしておく(チラつき防止)→ ②getCookieで安全に読み取る → ③classList.toggle("hidden", !hasCookie)で双方向に切り替える、という流れが基本です。
読み取りは最初の = で区切る・存在判定は !== null・実行は DOMContentLoaded、という3点を押さえれば落とし穴を避けられます。短く書きたいときは element.hidden も便利です。サーバーに送らない表示状態の保存だけなら、localStorageの利用も検討してみてください。

