我找到了一种修补 Hammer.JS 的方法,以便它可以检测到卡住的指针。我不知道这是否是错误的,但显然它有效!
在 HammerJS PointerEvents 处理程序上,有一个数组this.store
保存所有当前的指针事件。它就在那里,当我们平移出窗口并释放触摸时,卡住的事件将永远保留。
清除此数组会导致 Hammer 再次恢复正常。
我刚刚添加了一个条件,如果我们正在处理主要触摸(手势开始?),并且存储不是空的,它会自动清除存储。
它的工作原理是,在与卡住的锤子实例的下一次交互中,内部存储被重置并且手势被正确解释。
在 Hammer.js 2.0.6 上,大约第 885 行
/**
* handle mouse events
* @param {Object} ev
*/
handler: function PEhandler(ev) {
var store = this.store;
var removePointer = false;
var eventTypeNormalized = ev.type.toLowerCase().replace('ms', '');
var eventType = POINTER_INPUT_MAP[eventTypeNormalized];
var pointerType = IE10_POINTER_TYPE_ENUM[ev.pointerType] || ev.pointerType;
var isTouch = (pointerType == INPUT_TYPE_TOUCH);
// get index of the event in the store
var storeIndex = inArray(store, ev.pointerId, 'pointerId');
// start and mouse must be down
if (eventType & INPUT_START && (ev.button === 0 || isTouch)) {
// NEW CONDITION: Check the store is empty on a new gesture
// http://stackoverflow.com/questions/35618107/cross-frame-events-on-ie-edge-break-hammerjs-v2
if (ev.isPrimary && store.length) {
window.console.warn ("Store should be 0 on a primary touch! Clearing Stuck Event!");
this.reset();
}
if (storeIndex < 0) {
store.push(ev);
storeIndex = store.length - 1;
}
} else if (eventType & (INPUT_END | INPUT_CANCEL)) {
removePointer = true;
}
// it not found, so the pointer hasn't been down (so it's probably a hover)
if (storeIndex < 0) {
return;
}
// update the event in the store
store[storeIndex] = ev;
this.callback(this.manager, eventType, {
pointers: store,
changedPointers: [ev],
pointerType: pointerType,
srcEvent: ev
});
if (removePointer) {
// remove from the store
store.splice(storeIndex, 1);
}
}
});
我还定义了“重置”功能:
/**
* Reset internal state
*/
reset: function() {
this.store = (this.manager.session.pointerEvents = []);
},