Don't store touch events. The same event is used between touchstart, touchmove, and touchend. Instead, we store event details on the handler and use those when needed. p=bbinet, r=me (closes #3120)

git-svn-id: http://svn.openlayers.org/trunk/openlayers@11507 dc9f47b5-9b13-0410-9fdd-eb0c1a62fdaf
This commit is contained in:
Tim Schaub
2011-02-25 14:52:56 +00:00
parent b34dbcb903
commit 960ef3de18
2 changed files with 52 additions and 23 deletions
+46 -17
View File
@@ -85,23 +85,22 @@ OpenLayers.Handler.Click = OpenLayers.Class(OpenLayers.Handler, {
/** /**
* Property: down * Property: down
* {<OpenLayers.Pixel>} The pixel location of the last mousedown. * {Object} Object that store relevant information about the last
* mousedown or touchstart. Its 'xy' OpenLayers.Pixel property gives
* the average location of the mouse/touch event. Its 'touches'
* property records clientX/clientY of each touches.
*/ */
down: null, down: null,
/** /**
* Property: last * Property: last
* {<OpenLayers.Pixel>} The pixel for the last touchmove. This is * {Object} Object that store relevant information about the last
* used to * touchmove. Its 'xy' OpenLayers.Pixel property gives
* the average location of the mouse/touch event. Its 'touches'
* property records clientX/clientY of each touches.
*/ */
last: null, last: null,
/**
* Property: touch
* {Boolean} Are we on a touch enabled device? Default is false.
*/
touch: false,
/** /**
* Property: rightclickTimerId * Property: rightclickTimerId
* {Number} The id of the right mouse timeout waiting to clear the * {Number} The id of the right mouse timeout waiting to clear the
@@ -130,7 +129,7 @@ OpenLayers.Handler.Click = OpenLayers.Class(OpenLayers.Handler, {
// optionally register for mouseup and mousedown // optionally register for mouseup and mousedown
if(this.pixelTolerance != null) { if(this.pixelTolerance != null) {
this.mousedown = function(evt) { this.mousedown = function(evt) {
this.down = evt; this.down = this.getEventInfo(evt);
return true; return true;
}; };
} }
@@ -154,8 +153,7 @@ OpenLayers.Handler.Click = OpenLayers.Class(OpenLayers.Handler, {
* {Boolean} Continue propagating this event. * {Boolean} Continue propagating this event.
*/ */
touchstart: function(evt) { touchstart: function(evt) {
this.touch = true; this.down = this.getEventInfo(evt);
this.down = evt;
this.last = null; this.last = null;
return true; return true;
}, },
@@ -244,8 +242,9 @@ OpenLayers.Handler.Click = OpenLayers.Class(OpenLayers.Handler, {
dblclick: function(evt) { dblclick: function(evt) {
// for touch devices trigger dblclick only for // for touch devices trigger dblclick only for
// "one finger" touch // "one finger" touch
if(this.passesTolerance(evt) && var last = this.down || this.last;
(!evt.lastTouches || evt.lastTouches.length == 1)) { if (this.passesTolerance(evt) &&
(!last || !last.touches || last.touches.length == 1)) {
if(this["double"]) { if(this["double"]) {
this.callback('dblclick', [evt]); this.callback('dblclick', [evt]);
} }
@@ -260,7 +259,7 @@ OpenLayers.Handler.Click = OpenLayers.Class(OpenLayers.Handler, {
* an empty "touches" property. * an empty "touches" property.
*/ */
touchmove: function(evt) { touchmove: function(evt) {
this.last = evt; this.last = this.getEventInfo(evt);
}, },
/** /**
@@ -287,13 +286,14 @@ OpenLayers.Handler.Click = OpenLayers.Class(OpenLayers.Handler, {
*/ */
click: function(evt) { click: function(evt) {
// Sencha Touch emulates click events, see ticket 3079 for more info // Sencha Touch emulates click events, see ticket 3079 for more info
if (this.touch === true && evt.type === "click") { if (this.down && this.down.touches && evt.type === "click") {
return !this.stopSingle; return !this.stopSingle;
} }
if(this.passesTolerance(evt)) { if(this.passesTolerance(evt)) {
if(this.timerId != null) { if(this.timerId != null) {
// already received a click // already received a click
if(evt.lastTouches) { var last = this.down || this.last;
if (last && last.touches && last.touches.length > 0) {
// touch device - we may trigger dblclick // touch device - we may trigger dblclick
this.dblclick(evt); this.dblclick(evt);
} else { } else {
@@ -366,6 +366,35 @@ OpenLayers.Handler.Click = OpenLayers.Class(OpenLayers.Handler, {
} }
}, },
/**
* Method: getEventInfo
* This method allows us to store event information without storing the
* actual event. In touch devices (at least), the same event is
* modified between touchstart, touchmove, and touchend.
*
* Returns:
* {Object} An object with event related info.
*/
getEventInfo: function(evt) {
var touches;
if (evt.touches) {
var len = evt.touches.length;
touches = new Array(len);
var touch;
for (var i=0; i<len; i++) {
touch = evt.touches[i];
touches[i] = {
clientX: touch.clientX,
clientY: touch.clientY
};
}
}
return {
xy: evt.xy,
touches: touches
};
},
/** /**
* APIMethod: deactivate * APIMethod: deactivate
* Deactivate the handler. * Deactivate the handler.
+6 -6
View File
@@ -316,14 +316,14 @@
log = null; log = null;
handler.touchstart({xy: {x: 1, y: 1}, touches: ["foo"]}); handler.touchstart({xy: {x: 1, y: 1}, touches: ["foo"]});
handler.touchend({}); handler.touchend({touches: ["foo"]});
t.delay_call(1, function() { t.delay_call(1, function() {
t.ok(log != null, "click callback called"); t.ok(log != null, "click callback called");
if(log != null) { if(log != null) {
t.eq(log.x, 1, "evt.xy.x as expected"); t.eq(log.x, 1, "evt.xy.x as expected");
t.eq(log.y, 1, "evt.xy.y as expected"); t.eq(log.y, 1, "evt.xy.y as expected");
t.eq(log.lastTouches, ["foo"], "evt.lastTouches as expected"); t.ok(log.lastTouches, "evt.lastTouches as expected");
} }
// tear down // tear down
map.destroy(); map.destroy();
@@ -359,7 +359,7 @@
handler.touchstart({xy: {x: 1, y: 1}, touches: ["foo"]}); handler.touchstart({xy: {x: 1, y: 1}, touches: ["foo"]});
handler.touchend({type: "click"}); handler.touchend({type: "click"});
t.eq(handler.touch, true, "Touch property should be true"); t.eq(!!handler.down.touches, true, "Handler down touches property should be truthy");
t.ok(log.dblclick == undefined, "dblclick callback not called with simulated click"); t.ok(log.dblclick == undefined, "dblclick callback not called with simulated click");
@@ -395,9 +395,9 @@
// test // test
log = {}; log = {};
handler.touchstart({xy: {x: 1, y: 1}, touches: ["foo"]}); handler.touchstart({xy: {x: 1, y: 1}, touches: [{clientX:0, clientY:10}]});
handler.touchend({}); handler.touchend({});
handler.touchstart({xy: {x: 1, y: 1}, touches: ["foo"]}); handler.touchstart({xy: {x: 1, y: 1}, touches: [{clientX:0, clientY:10}]});
handler.touchend({}); handler.touchend({});
t.eq(log.click, undefined, "click callback not called"); t.eq(log.click, undefined, "click callback not called");
@@ -405,7 +405,7 @@
if(log.dblclick != undefined) { if(log.dblclick != undefined) {
t.eq(log.dblclick.x, 1, "evt.xy.x as expected"); t.eq(log.dblclick.x, 1, "evt.xy.x as expected");
t.eq(log.dblclick.y, 1, "evt.xy.y as expected"); t.eq(log.dblclick.y, 1, "evt.xy.y as expected");
t.eq(log.dblclick.lastTouches, ["foo"], "evt.lastTouches as expected"); t.ok(log.dblclick.lastTouches, "evt.lastTouches on evt");
} }
// tear down // tear down