【JS】 JavaScript のダブルクリックイベントについて考える

 ■ はじめに

JavaScript のダブルクリックについて、色々と調べてみたら
意外とややっこしかったので、メモ。

目次

【案1】 dblclickイベントで実装する
【案2】 clickイベントとsetTimeoutで実装する
【案3】 mousedownイベントとsetTimeoutで実装する

【案1】 dblclickイベントで実装する

 * dblclickでダブルクリックイベントを拾う

 問題点
https://qiita.com/sashim1343/items/e3728bea913cadab677d

で言っている通り、
シングルクリックとダブルクリックが共存できない

 => 両方のイベント登録しても、
 シングルクリックが先に拾ってしまうだけで
    ダブルクリックまでイベントが拾えない

 サンプル

<!DOCTYPE html>
<html lang="ja">
<head>
<meta charset="utf-8">
<title>Demo</title>
<style type="text/css">
div{
  width:100px;
  height:100px;
  display: flex;
  align-items: center;
  justify-content: center;
  background-color: orange;
  margin:10px 0;
}
</style>
</head>
<body>
<h1>[1] dblclick</h1>
<div id="target01">ダブルクリック([1-1] dblclick)</div>
<div ondblclick="ondblclickEvent();">ダブルクリック([1-2] ondblclick)</div>
<hr>
<h1>[問題] シングルクリックとダブルクリックは共存できない</h1>
<div id="target02">シングルクリック・ダブルクリック</div>
</body>
<script>
// [1-1] dblclick
var target1_1 = document.getElementById('target01');
target1_1.addEventListener('dblclick', function() {
  alert("double click! ([1-1] dblclick)");
}, false);

// [1-2] ondblclick
function ondblclickEvent() {
  alert("double click! ([1-2] ondblclick)");
}

var target2_1 = document.getElementById('target02');
target2_1.addEventListener('dblclick', function() {
  alert("double click! ([2-1] dblclick)");
}, false);

target2_1.addEventListener('click', function() {
  alert("single click! ([2-1] click)");
}, false);
</script>
</html>

【案2】 clickイベントとsetTimeoutで実装する

 * setTimeoutを使って、シングルクリックとダブルクリックを振り分ける

 問題点
https://lab.syncer.jp/Web/JavaScript/Snippet/14/

で言っている通り、ダブルクリックの途中でテキストが選択されてしまう
 => 気にしないならいいのだが...

 サンプル

<!DOCTYPE html>
<html lang="ja">
<head>
<meta charset="utf-8">
<title>Demo</title>
<style type="text/css">
div{
  width:100px;
  height:100px;
  display: flex;
  align-items: center;
  justify-content: center;
  background-color: orange;
  margin:10px 0;
}
</style>
</head>
<body>
<h1>[2] clickイベントとsetTimeoutで実装する</h1>
<div id="target02">シングルクリック・ダブルクリック</div>
</body>
<script>
var isClicked = false;
var target2 = document.getElementById('target02');
target2.addEventListener('click', function() {
  // ダブルクリック
  if (isClicked) {
    alert("double click!!");
    isClicked = false;
    return;
  }

  // シングルクリック
  isClicked = true;
  setTimeout(function () {
    if (isClicked) {
      alert("single click!");
    }
    isClicked = false;
  }, 350);
}, false);
</script>
</html>

【案3】 mousedownイベントとsetTimeoutで実装する

 * clickイベントの代わりにmousedownイベントとし、
   setTimeoutを使って、シングルクリックとダブルクリックを振り分ける

 サンプル

<!DOCTYPE html>
<html lang="ja">
<head>
<meta charset="utf-8">
<title>Demo</title>
<style type="text/css">
div{
  width:100px;
  height:100px;
  display: flex;
  align-items: center;
  justify-content: center;
  background-color: orange;
  margin:10px 0;
}
</style>
</head>
<body>
<h1>[3] mousedownイベントとsetTimeoutで実装する</h1>
<div id="target03">シングルクリック・ダブルクリック</div>
</body>
<script>
var isClicked = false;
var target3 = document.getElementById('target03');
target3.addEventListener('mousedown', function(event) {
  // ダブルクリック
  if (isClicked) {
    // !重要!
    event.preventDefault();
    
    alert("double click!!");
    isClicked = false;
    return;
  }

  // シングルクリック
  isClicked = true;
  setTimeout(function () {
    if (isClicked) {
      alert("single click!");
    }
    isClicked = false;
  }, 350);
}, false);
</script>
</html>

 参考文献

案1
https://naruhodo.repop.jp/javascript-doubleclick-event/
https://javascript.programmer-reference.com/js-event-ondblclick/
案2
https://qiita.com/sashim1343/items/e3728bea913cadab677d
案3
https://lab.syncer.jp/Web/JavaScript/Snippet/14/