HTML&CSS

display noneのアニメーション方法まとめ|CSS・jQuery・JavaScriptで解説

display noneはアニメーションできない?CSSでフェード表示する方法を解説

display:none の要素をフェードインさせようとして、失敗したことはありませんか?.

理由は、display:none の要素はブラウザ上で描画されていないためです。
opacity はアニメーションできますが、display は通常の transition のように「0から1へなめらかに変化する」プロパティではありません。

この記事では、display:none の要素をフェードイン・フェードアウトさせる方法を、実用的なサンプル付きで紹介します。


display:noneの要素がtransitionでフェードインしない理由

opacity は、次のように数値が変化するプロパティです。

opacity: 0;
opacity: 0.5;
opacity: 1;

そのため、transition を使えばなめらかに変化させることができます。

一方で、display は次のように状態を切り替えるプロパティです。

display: none;
display: block;

noneblock の間には、中間の状態がありません。

そのため、単純に display:none から display:block に変えただけでは、opacity の変化をブラウザがうまくアニメーションとして扱えないことがあります。

つまり、display は表示・非表示の切り替え担当、opacity はフェードの見た目担当として分けて考えるのがポイントです。


方法1:CSSアニメーションでdisplay:noneの要素をフェードインする

まずは、CSSの @keyframes を使ってフェードインさせる方法です。

See the Pen Untitled by kokusyo (@kokusyo) on CodePen.

この方法では、表示するときに .is-show を付け、非表示にするときに .is-hide を付けています。

.fade-box.is-show {
  display: block;
  animation: fadeIn 0.5s ease forwards;
}

.fade-box.is-hide {
  display: block;
  animation: fadeOut 0.5s ease forwards;
}

フェードアウト中にすぐ display:none にすると、アニメーションが見えずに一瞬で消えてしまいます。

そのため、フェードアウト中は display:block のままにしておき、アニメーションが終わってから .is-hide を外します。

box.addEventListener('animationend', () => {
  box.classList.remove('is-hide');
}, { once: true });

.is-hide が外れると、元の .fade-box の状態に戻るため、結果的に display:none になります。


方法2:displayとopacityをJavaScriptで制御する方法

次に、フェードインだけでなくフェードアウトにも対応したサンプルです。

See the Pen Untitled by kokusyo (@kokusyo) on CodePen.

流れとしては、表示するときにまず display:block にして、その後に opacity:1 へ変更します。

box.style.display = 'block';

setTimeout(() => {
  box.style.opacity = '1';
}, 10);

非表示にするときは、先に opacity:0 へ変更し、フェードアウトが終わってから display:none にします。

box.style.opacity = '0';

setTimeout(() => {
  box.style.display = 'none';
}, 500);

CSSアニメーションよりJavaScriptの記述は少し増えますが、displayopacity の役割が分かりやすい方法です。


方法3:jQueryのfadeIn・fadeOutを使う

jQueryを使っているサイトであれば、もっと簡単に書けます。

See the Pen Untitled by kokusyo (@kokusyo) on CodePen.

表示の切り替えは、今回のように fadeToggle() を使うと簡単です。

$('#btn').on('click', function () {
  $('#box').fadeToggle(500);
});

jQueryの fadeIn()fadeOut() は、内部で displayopacity を調整してくれるため、display:none の要素でも簡単にフェード表示できます。


方法4:opacityとvisibilityでフェードさせる

もっと簡単にすませたい方は、opacityvisibility を使う方法もあります。

See the Pen Untitled by kokusyo (@kokusyo) on CodePen.

CSSの transition だけで自然にフェードイン・フェードアウトできます。

ただし、注意点があります。
visibility:hidden は要素を見えなくするだけなので、レイアウト上のスペースは残ります。

つまり、下の要素を詰めたい場合には向いていません。

display noneを使わずに高さが残ってるしまってる例

スペースを残したまま、モーダル・ツールチップ・固定表示のメニューなどをフェードさせたい場合には使いやすい方法です。


方法5:@starting-styleとtransition-behaviorを使う新しいCSSの方法

最近のCSSでは、@starting-styletransition-behavior: allow-discrete を使うことで、display:none を含む表示切り替えも扱いやすくなっています。

See the Pen Untitled by kokusyo (@kokusyo) on CodePen.

@starting-style は、要素が表示される最初の状態を指定するためのCSSです。
通常、display:none から display:block に切り替わると、ブラウザは開始状態をうまく取れません。
そこで @starting-style を使い、表示開始時のスタイルを明示します。

@starting-style {
  .fade-box.is-show {
    opacity: 0;
    transform: translateY(12px);
  }
}

また、display のように通常はなめらかに変化しないプロパティをトランジション対象にするために、allow-discrete を指定します。

transition:
  opacity 0.5s ease,
  transform 0.5s ease,
  display 0.5s ease allow-discrete;

この方法を使うと、JavaScript側ではクラスを付け外しするだけで済みます。

ただし、比較的新しいCSSの書き方なので、対応ブラウザを考慮する必要があります。


Web制作の独学が不安な人へ。ZeroPlus Gateを実際に受講してみました

独学だと、調べても解決できず手が止まる瞬間があります。
私も実際に登録して、カリキュラム内容と質問導線を一通り試しました。
0円で試せる学習環境を、メリット・注意点込みでレビューにまとめています。

✅ 調べても解決せず、学習が止まりがち
✅ 質問できる相手がいなくて不安
✅ 何から手を付けるべきか迷う
✅ 0円で質問できる環境を試してみたい

体験レビューを読む(無料の理由・注意点も)

まずは雰囲気を知りたい人向けに、体験レビューを用意しました。

-HTML&CSS
-, ,