b40f2958d4
Before it was not possible to add values to anything except leafs of the namespace structure.
149 lines
No EOL
4.1 KiB
JavaScript
149 lines
No EOL
4.1 KiB
JavaScript
Elm.Native.Touch = {};
|
|
Elm.Native.Touch.make = function(elm) {
|
|
|
|
elm.Native = elm.Native || {};
|
|
elm.Native.Touch = elm.Native.Touch || {};
|
|
if (elm.Native.Touch.values) return elm.Native.Touch.values;
|
|
|
|
var Signal = Elm.Signal.make(elm);
|
|
var JS = Elm.JavaScript.make(elm);
|
|
var _ = Elm.Native.Utils.make(elm);
|
|
|
|
function Dict() {
|
|
this.keys = [];
|
|
this.values = [];
|
|
|
|
this.insert = function(key,value) {
|
|
this.keys.push(key);
|
|
this.values.push(value);
|
|
};
|
|
this.lookup = function(key) {
|
|
var i = this.keys.indexOf(key)
|
|
return i >= 0 ? this.values[i] : {x:0,y:0,t:0};
|
|
};
|
|
this.remove = function(key) {
|
|
var i = this.keys.indexOf(key);
|
|
if (i < 0) return;
|
|
var t = this.values[i];
|
|
this.keys.splice(i,1);
|
|
this.values.splice(i,1);
|
|
return t;
|
|
};
|
|
this.clear = function() {
|
|
this.keys = [];
|
|
this.values = [];
|
|
};
|
|
}
|
|
|
|
var root = Signal.constant([]),
|
|
tapTime = 500,
|
|
hasTap = false,
|
|
tap = {_:{},x:0,y:0},
|
|
dict = new Dict();
|
|
|
|
function touch(t) {
|
|
var r = dict.lookup(t.identifier);
|
|
return {_ : {},
|
|
id: t.identifier,
|
|
x : t.pageX - elm.node.offsetX,
|
|
y : t.pageY - elm.node.offsetY,
|
|
x0: r.x,
|
|
y0: r.y,
|
|
t0: r.t
|
|
};
|
|
}
|
|
|
|
var node = elm.display === ElmRuntime.Display.FULLSCREEN ? document : elm.node;
|
|
|
|
function start(e) {
|
|
dict.insert(e.identifier,
|
|
{x: e.pageX - elm.node.offsetX,
|
|
y: e.pageY - elm.node.offsetY,
|
|
t: Date.now()});
|
|
}
|
|
function end(e) {
|
|
var t = dict.remove(e.identifier);
|
|
if (Date.now() - t.t < tapTime) {
|
|
hasTap = true;
|
|
tap = {_:{}, x:t.x, y:t.y};
|
|
}
|
|
}
|
|
|
|
function listen(name, f) {
|
|
function update(e) {
|
|
for (var i = e.changedTouches.length; i--; ) { f(e.changedTouches[i]); }
|
|
var ts = new Array(e.touches.length);
|
|
for (var i = e.touches.length; i--; ) { ts[i] = touch(e.touches[i]); }
|
|
elm.notify(root.id, ts);
|
|
e.preventDefault();
|
|
}
|
|
elm.addListener([root.id], node, name, update);
|
|
}
|
|
|
|
listen("touchstart", start);
|
|
listen("touchmove", function(_){});
|
|
listen("touchend", end);
|
|
listen("touchcancel", end);
|
|
listen("touchleave", end);
|
|
|
|
var mouseID = -1;
|
|
function move(e) {
|
|
for (var i = root.value.length; i--; ) {
|
|
if (root.value[i].id === mouseID) {
|
|
root.value[i].x = e.pageX - elm.node.offsetX;
|
|
root.value[i].y = e.pageY - elm.node.offsetY;
|
|
elm.notify(root.id, root.value);
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
elm.addListener([root.id], node, "mousedown", function down(e) {
|
|
node.addEventListener("mousemove", move);
|
|
e.identifier = mouseID;
|
|
start(e);
|
|
root.value.push(touch(e));
|
|
elm.notify(root.id, root.value);
|
|
});
|
|
elm.addListener([root.id], node, "mouseup", function up(e) {
|
|
node.removeEventListener("mousemove", move);
|
|
e.identifier = mouseID;
|
|
end(e);
|
|
for (var i = root.value.length; i--; ) {
|
|
if (root.value[i].id === mouseID) {
|
|
root.value.splice(i, 1);
|
|
--mouseID;
|
|
break;
|
|
}
|
|
}
|
|
elm.notify(root.id, root.value);
|
|
});
|
|
elm.addListener([root.id], node, "blur", function blur(e) {
|
|
node.removeEventListener("mousemove", move);
|
|
if (root.value.length > 0) {
|
|
elm.notify(root.id, []);
|
|
--mouseID;
|
|
}
|
|
dict.clear();
|
|
});
|
|
|
|
function dependency(f) {
|
|
var sig = A2( Signal.lift, f, root );
|
|
root.defaultNumberOfKids += 1;
|
|
sig.defaultNumberOfKids = 0;
|
|
return sig;
|
|
}
|
|
|
|
var touches = dependency(JS.toList);
|
|
|
|
var taps = function() {
|
|
var sig = dependency(function(_) { return tap; });
|
|
sig.defaultNumberOfKids = 1;
|
|
function pred(_) { var b = hasTap; hasTap = false; return b; }
|
|
var sig2 = A3( Signal.keepIf, pred, {_:{},x:0,y:0}, sig);
|
|
sig2.defaultNumberOfKids = 0;
|
|
return sig2;
|
|
}();
|
|
|
|
return elm.Native.Touch.values = { touches: touches, taps: taps };
|
|
|
|
}; |