こんにちは!のせっちです!
モーダル内のコンテンツがスクロールするときでも背景を画面いっぱいにする方法をご紹介します。
通常の書き方
まずは、通常の書き方を抑えておきます。
基本がわかっていないと、理解できないからです。
See the Pen modal by Yuki Nose (@yukinouz1) on CodePen.
// モーダル展開時の背景部分
.modal__bg{
background: rgba(#000, 0.8);
height: 100vh;
position: absolute;
width: 100%;
}
モーダル展開時の黒背景部分のみ抜粋です。height: 100vh;
で高さを画面いっぱいにしています。
$(()=> {
const modal = $(".js-modal");
const modalOpen = $(".js-modal-open");
const modalClose = $(".js-modal-close");
modalOpen.on("click", function() {
modal.fadeIn();
});
modalClose.on("click", function() {
modal.fadeOut();
});
});
ボタンクリックでモーダルを展開、閉じるボタンか黒背景をクリックで閉じる、という単純なjQueryを書いています。
()=>
はアロー関数といい、今回のケースではfunction()
と書いているのと同じです。
モーダル内のコンテンツがスクロールする場合
次に、モーダル内のコンテンツがスクロールする場合を見てみます。
See the Pen modal-overflow-y by Yuki Nose (@yukinouz1) on CodePen.
ボタンクリックでモーダルを開くのは同じです。
今回はコンテンツがY方向にoverflowしていて、縦スクロールが発生していますね!
それでも、黒背景はコンテンツの最後まで広がっています。
height: 100vh;
だと画面の表示部分しか確保できないので、スクロールしていくと黒背景は途切れるはずです。
どうやってコンテンツ全体を黒背景で覆っているのでしょうか?
解説
簡単に解説します。
まずはCSSです。
.modal__bg{
background: rgba(#000, 0.8);
min-height: 100vh;
position: absolute;
width: 100%;
}
height: 100vh;
ではなく、min-height: 100vh;
としました。
height: 100vh;
では、表示領域分しか高さが取れないので、スクロールしていくと黒背景は途切れます。
なので高さはjavascriptで計算します。
min-height: 100vh;
とした理由は、ワイドスクリーンというか、縦長スクリーン対応です。縦長でスクロールがなくなる可能性があるので、そのときは100vhが適用されるようにしてあげます。
$(() => {
const modal = $(".js-modal");
const modalContent = $(".js-modal-content");
const modalBg = $(".js-modal-bg");
const modalOpen = $(".js-modal-open");
const modalClose = $(".js-modal-close");
const body = $("body");
modalOpen.on("click", function() {
modal.fadeIn();
body.css({
overflow: "hidden",
});
let formheight = modalContent.outerHeight();
modalBg.css({
height: formheight
});
});
modalClose.on("click", function() {
modal.fadeOut();
body.css({
overflow: "auto",
});
modalBg.css({
height: "auto"
});
});
});
こちらは分解して細かく解説します。
// 定義省略
modalOpen.on("click", function() {
modal.fadeIn();
body.css({
overflow: "hidden",
});
formheight = modalContent.outerHeight();
modalBg.css({
height: formheight
});
});
クリックでモーダルをfadeIn()
させるところまでは基本形と同じです。
body.css({overflow: "hidden",});
としているのはモーダルオープン時にページ全体がスクロールしないようにするためです。
「モーダル展開時 ページスクロールしない」とかでググると沢山出てくるやり方です。
formheight = modalContent.outerHeight();
でコンテンツの高さを取得して、formheight
という変数に代入しました。
modalBg.css({height: formheight});
で先ほど計算した黒背景部分のcssでheightをformheight
にしてあげます。
こうすることで、クリックしたときの高さを黒背景の高さにすることができます。
次は閉じる動作をしたときの処理です。
modalClose.on("click", function() {
modal.fadeOut();
body.css({
overflow: "auto",
});
modalBg.css({
height: "auto"
});
});
モーダルを閉じるときは、bodyのoverflowを元に戻す、黒背景の高さもautoに戻す、という処理です。
基本全部元に戻す処理をしてあげているだけです!
最後です。
// 定義省略
$(window).on("resize", function() {
formheight = modalContent.outerHeight();
modalBg.css({
height: formheight
});
});
$(window).on("resize", function()...
でウィンドウのリサイズを検知できます。
スマホサイズ、タブレットサイズ、PCサイズでコンテンツの高さは違いますので、windowのサイズ変更にも対応できるようにしています。
モーダル展開時にもformheight
を取得しますが、modalOpen.on("click", function()...
なので、クリックしたとき1回だけ取得します。リサイズに対応するには、別で処理を書かないといけません。
お疲れ様でした。
まとめ
・モーダル内のコンテンツがスクロールする場合はjsで高さを計算する。
・ワイドスクリーン(縦長スクリーン)に対応するために、min-height: 100vh;
を書いておく。
・widnowサイズの変更にも対応する。