-
-
Save tmcw/4067674 to your computer and use it in GitHub Desktop.
| <!DOCTYPE html> | |
| <html> | |
| <head> | |
| <script src="http://d3js.org/d3.v3.min.js"></script> | |
| <style> | |
| body { margin:0; padding:0; } | |
| #map { width:960px; height:500px; background:cyan; } | |
| </style> | |
| </head> | |
| <body> | |
| <div id='map'></div> | |
| <script> | |
| function clickcancel() { | |
| var event = d3.dispatch('click', 'dblclick'); | |
| function cc(selection) { | |
| var down, | |
| tolerance = 5, | |
| last, | |
| wait = null; | |
| // euclidean distance | |
| function dist(a, b) { | |
| return Math.sqrt(Math.pow(a[0] - b[0], 2), Math.pow(a[1] - b[1], 2)); | |
| } | |
| selection.on('mousedown', function() { | |
| down = d3.mouse(document.body); | |
| last = +new Date(); | |
| }); | |
| selection.on('mouseup', function() { | |
| if (dist(down, d3.mouse(document.body)) > tolerance) { | |
| return; | |
| } else { | |
| if (wait) { | |
| window.clearTimeout(wait); | |
| wait = null; | |
| event.dblclick(d3.event); | |
| } else { | |
| wait = window.setTimeout((function(e) { | |
| return function() { | |
| event.click(e); | |
| wait = null; | |
| }; | |
| })(d3.event), 300); | |
| } | |
| } | |
| }); | |
| }; | |
| return d3.rebind(cc, event, 'on'); | |
| } | |
| var cc = clickcancel(); | |
| d3.select('#map').call(cc); | |
| cc.on('click', function() { | |
| d3.select('#map').text(d3.select('#map').text() + 'click, '); | |
| }); | |
| cc.on('dblclick', function() { | |
| d3.select('#map').text(d3.select('#map').text() + 'dblclick, '); | |
| }); | |
| </script> | |
| </body> | |
| </html> |
selection.on("click", function(d, i) {
dispatch.custom.apply(this, arguments);
});
This way the argument can also be passed
It looks like the last variable is redundant?
@pkolanda: At what line did you insert the snippet you posted? Thanks!
I updated this snippet for d3v4 and v5
you first have to put the rebind function back into d3 which can be found here https://github.com/d3/d3/blob/v3.5.17/src/core/rebind.js
function clickCancel() {
var event = d3.dispatch('click', 'dblclick');
function cc(selection) {
var down,
tolerance = 5,
last,
wait = null;
// euclidean distance
function dist(a, b) {
return Math.sqrt(Math.pow(a[0] - b[0], 2), Math.pow(a[1] - b[1], 2));
}
selection.on('mousedown', function() {
down = d3.mouse(document.body);
last = +new Date();
});
selection.on('mouseup', function() {
if (dist(down, d3.mouse(document.body)) > tolerance) {
return;
} else {
if (wait) {
window.clearTimeout(wait);
wait = null;
event.call('dblclick',d3.event)
//event.dblclick(d3.event);
} else {
wait = window.setTimeout((function(e) {
return function() {
event.call('click',e)
//event.click(e);
wait = null;
};
})(d3.event), 300);
}
}
});
};
return d3.rebind(cc, event, 'on');
}
Also if you want the mouse event to go into both the double click and the single click you have to pass it down through the anonymous functions
Hey!
I created a fork of your snippet to stretch your euclidean distance to another dimension, when I learned, that a comment might be a better way to fight against discrimination of the vertical movement.
Math.sqrt(Math.pow(...) + Math.pow(...))
Don't just drop her into the void, please.
Your snippet helped me so much. Thank you.
Thanks, this is awesome. You might want to change
+new Date()tonew Date().getTime(), though; see http://jsperf.com/new-date-timing.