Modify Guacamole.Touchscreen to play nicely with other gesture-handling objects. Send click only on touchend. Move mouse only if related to a drag.

This commit is contained in:
Michael Jumper
2014-03-04 13:42:14 -08:00
parent f0c62ff82a
commit 6d1c9ba550

View File

@@ -699,12 +699,36 @@ Guacamole.Mouse.Touchscreen = function(element) {
*/ */
var guac_touchscreen = this; var guac_touchscreen = this;
/**
* The start X location of a click (tap) gesture.
* @private
*/
var click_start_x = null;
/**
* The start Y location of a click (tap) gesture.
* @private
*/
var click_start_y = null;
/** /**
* The distance a two-finger touch must move per scrollwheel event, in * The distance a two-finger touch must move per scrollwheel event, in
* pixels. * pixels.
*/ */
this.scrollThreshold = 20 * (window.devicePixelRatio || 1); this.scrollThreshold = 20 * (window.devicePixelRatio || 1);
/**
* The maximum number of milliseconds to wait for a touch to end for the
* gesture to be considered a click.
*/
this.clickTimingThreshold = 250;
/**
* The maximum number of pixels to allow a touch to move for the gesture to
* be considered a click.
*/
this.clickMoveThreshold = 10 * (window.devicePixelRatio || 1);
/** /**
* The current mouse state. The properties of this state are updated when * The current mouse state. The properties of this state are updated when
* mouse events fire. This state object is also passed in as a parameter to * mouse events fire. This state object is also passed in as a parameter to
@@ -753,18 +777,31 @@ Guacamole.Mouse.Touchscreen = function(element) {
element.addEventListener("touchend", function(e) { element.addEventListener("touchend", function(e) {
// Ignore if more than one touch // Ignore if more than one touch
if (e.touches.length + e.changedTouches.length !== 1) if (e.touches.length !== 0 || e.changedTouches.length !== 1)
return; return;
e.stopPropagation(); // If finger hasn't moved enough to cancel the click
e.preventDefault(); var touch = e.changedTouches[0];
if ( Math.abs(touch.clientX - click_start_x) < guac_touchscreen.clickMoveThreshold
&& Math.abs(touch.clientY - click_start_y) < guac_touchscreen.clickMoveThreshold) {
// Release button e.preventDefault();
guac_touchscreen.currentState.left = false;
// Fire release event when the last touch is released, if event defined // Press button
if (e.touches.length === 0 && guac_touchscreen.onmouseup) guac_touchscreen.currentState.left = true;
guac_touchscreen.onmouseup(guac_touchscreen.currentState);
// Fire press event, if defined
if (guac_touchscreen.onmousedown)
guac_touchscreen.onmousedown(guac_touchscreen.currentState);
// Release button
guac_touchscreen.currentState.left = false;
// Fire release event when the last touch is released, if event defined
if (guac_touchscreen.onmouseup)
guac_touchscreen.onmouseup(guac_touchscreen.currentState);
}
}, false); }, false);
@@ -774,19 +811,14 @@ Guacamole.Mouse.Touchscreen = function(element) {
if (e.touches.length !== 1) if (e.touches.length !== 1)
return; return;
e.stopPropagation();
e.preventDefault(); e.preventDefault();
// Get touch
var touch = e.touches[0];
// Update state // Update state
guac_touchscreen.currentState.left = true; var touch = e.touches[0];
guac_touchscreen.currentState.fromClientPosition(element, touch.clientX, touch.clientY); guac_touchscreen.currentState.fromClientPosition(element, touch.clientX, touch.clientY);
// Fire press event, if defined click_start_x = touch.clientX;
if (guac_touchscreen.onmousedown) click_start_y = touch.clientY;
guac_touchscreen.onmousedown(guac_touchscreen.currentState);
}, false); }, false);
@@ -796,18 +828,22 @@ Guacamole.Mouse.Touchscreen = function(element) {
if (e.touches.length !== 1) if (e.touches.length !== 1)
return; return;
e.stopPropagation(); // Only handle move if in process of drag
e.preventDefault(); if (guac_touchscreen.currentState.left) {
// Get touch e.preventDefault();
var touch = e.touches[0];
// Update state // Get touch
guac_touchscreen.currentState.fromClientPosition(element, touch.clientX, touch.clientY); var touch = e.touches[0];
// Fire movement event, if defined // Update state
if (guac_touchscreen.onmousemove) guac_touchscreen.currentState.fromClientPosition(element, touch.clientX, touch.clientY);
guac_touchscreen.onmousemove(guac_touchscreen.currentState);
// Fire movement event, if defined
if (guac_touchscreen.onmousemove)
guac_touchscreen.onmousemove(guac_touchscreen.currentState);
}
}, false); }, false);