モーダルウィンドウ


## クラス化する

デモ：http://mo49.tokyo/qiita/20160519/

これにスクロール対応したのがベストプラクティスかな。

```javascript:Modal.js
export default class Modal {
    
    constructor (opts = {}) {}

    open() {
        this.genOverlay();
        this.genPopup();
     }

    close() {
        $(".popup, #overlay").fadeOut(function(){
            $(this).remove();
        });
    }

    genPopup() {
        const $open = $('#open');
        const $popup = $('<div class="popup">');
        const $txt = $('<p class="txt">HELLO WORLD.</p>');
        const $close = $('<div id="close" class="btn close">CLOSE</div>');
        
        $popup.hide();
        
        $open.after($popup);
        $popup.append($txt);
        $popup.append($close);
        
        $popup.fadeIn();
    }

    genOverlay() {
        const $overlay = $('<div id="overlay"></div>');
        $overlay.hide();
        $('body').prepend($overlay);
        $overlay.fadeIn();
    }

}
```

```javascript:index.js
import Modal from './lib/Modal';

const modal = new Modal();

$('#open').on('click', () => {
	modal.open();

	$('#close, #overlay').on('click', () => {
		modal.close();
	})

})
```


## 基本形

デモ：http://mo49.tokyo/jQuery_sdl/11/

クリックされる'a href'にモーダルで表示する'img src'を予め入れておくというテクニック。

```html:html
<a href="img/img1.jpg"><img src="img/thumb1.jpg" alt="Photo1"></a>
```

モーダルウィンドウがfadeOut後にremoveされている点も良い。


```javascript:javascript
$(function(){
	// サムネールをクリック
	$("a").click(function(){
		// body要素の最後にdiv#bgを追加
		$("body").append('<div id="bg">');
		
		// body要素の最後にdiv#photoを追加
		$("body").append('<div id="photo">');

		// それぞれ非表示にする
		$("#bg").hide();
		$("#photo").hide();
		
		// #photoの中にimg要素を追加
		$("#photo").html("<img>");
		
		// img要素にsrc属性を設定
		$("#photo img").attr("src",  $(this).attr("href"));
		console.log($(this).attr("href"));
		
		// img要素にwidth、height、alt属性を設定
		$("#photo img").attr("width", 640);
		$("#photo img").attr("height", 420);
		$("#photo img").attr("alt", "Photo");
		
		// #bgと#photoをフェードイン   
		$("#bg").fadeIn();
		$("#photo").fadeIn();
		
		// 背景をクリック   
		$("#bg").click(function(){
			// 背景（自分自身）をフェードアウト、完了したら削除
			$(this).fadeOut(function(){
				$(this).remove();
			});
		
			// 画像をフェードアウト、完了したら削除
			$("#photo").fadeOut(function(){
				$(this).remove();
			});
		});

		
		return false;
	});


});
```

## スクロール量からちょうど良い位置に表示

実際に使う機会が多いのはこちら。

デモ：http://mo49.tokyo/qiita/20160416/

クリックした瞬間のscrollTopを取得して、常に上から指定の位置に表示する。

```
$(".btn").click(function(){

    modalGen();

	// 位置の調整
    var scrollTop = window.scrollY;
    $('#modal-img').css("margin-top", scrollTop + 100);

    return false;
});

function modalGen(){

    // 大枠
    $("body").append('<div id="overlay">');
    $("body").append('<div id="modal-img">');

    $("#overlay").hide();
    $("#modal-img").hide();

    $("#overlay").fadeIn();
    $("#modal-img").fadeIn();

    // 大枠の中身
    var img = new Image();
    img.id = "sample-img";
    var imgClose = new Image();
    imgClose.id = "close-img";

    // pc or sp
    if ($('body').hasClass('env-pc')) {
        img.src = "http://placehold.it/640x340/27709b/ffffff";
        imgClose.src = "img/close.png";
    }else{
        img.src = "http://placehold.it/320x170/27709b/ffffff";
        imgClose.src = "img/close.png";
    }
    $('#modal-img').append(img);
    $('#modal-img').append(imgClose);

    // 削除
    $("#overlay, #close-img").click(function(){
        $("#overlay").fadeOut(function(){
            $(this).remove();
        });

        $("#modal-img").fadeOut(function(){
            $(this).remove();
        });
    });
}
```


> 引用
[jQuery標準デザイン講座](http://www.amazon.co.jp/jQuery%E6%A8%99%E6%BA%96%E3%83%87%E3%82%B6%E3%82%A4%E3%83%B3%E8%AC%9B%E5%BA%A7-%E7%A5%9E%E7%94%B0-%E5%B9%B8%E6%81%B5/dp/4798136220/ref=sr_1_5?ie=UTF8&qid=1456056520&sr=8-5&keywords=jquery)lesson11

### バグ

IEでscrollYが効かないとき・・・

```javascript:javascript
var scrollTop = window.scrollY;
if (!scrollTop) {
	// ie
	scrollTop = window.pageYOffset;
}
```