diff --git a/EndGate/EndGate.Core.JS/Input/Mouse/MouseHandler.js b/EndGate/EndGate.Core.JS/Input/Mouse/MouseHandler.js
index 6e107387..9918e9a1 100644
--- a/EndGate/EndGate.Core.JS/Input/Mouse/MouseHandler.js
+++ b/EndGate/EndGate.Core.JS/Input/Mouse/MouseHandler.js
@@ -2,6 +2,7 @@ var EndGate;
(function (EndGate) {
///
///
+ ///
///
///
///
@@ -18,6 +19,7 @@ var EndGate;
function MouseHandler(target) {
var _this = this;
this._target = target;
+ this._disposed = false;
this._onClick = new EndGate.EventHandler1();
this._onDoubleClick = new EndGate.EventHandler1();
@@ -153,29 +155,72 @@ var EndGate;
configurable: true
});
+ /**
+ * Disposes the MouseHandler and unbinds all bound events.
+ */
+ MouseHandler.prototype.Dispose = function () {
+ if (!this._disposed) {
+ this._disposed = true;
+
+ this._onClick.Dispose();
+ this._onDoubleClick.Dispose();
+ this._onDown.Dispose();
+ this._onMove.Dispose();
+ this._onScroll.Dispose();
+ this._onUp.Dispose();
+
+ this.Unwire();
+
+ this._target = null;
+ } else {
+ throw new Error("MouseHandler cannot be disposed more than once");
+ }
+ };
+
MouseHandler.prototype.Wire = function () {
var _this = this;
- this._target.addEventListener("click", this._target.oncontextmenu = this.BuildEvent(this._onClick, this.BuildMouseClickEvent), false);
- this._target.addEventListener("dblclick", this.BuildEvent(this._onDoubleClick, this.BuildMouseClickEvent), false);
- this._target.addEventListener("mousedown", this.BuildEvent(this._onDown, this.BuildMouseClickEvent), false);
- this._target.addEventListener("mouseup", this.BuildEvent(this._onUp, this.BuildMouseClickEvent), false);
- this._target.addEventListener("mousemove", this.BuildEvent(this._onMove, this.BuildMouseEvent), false);
+ this._clickWire = this._contextMenuWire = this.BuildEvent(this._onClick, this.BuildMouseClickEvent);
+ this._dblClickWire = this.BuildEvent(this._onDoubleClick, this.BuildMouseClickEvent);
+ this._mouseDownWire = this.BuildEvent(this._onDown, this.BuildMouseClickEvent);
+ this._mouseUpWire = this.BuildEvent(this._onUp, this.BuildMouseClickEvent);
+ this._mouseMoveWire = this.BuildEvent(this._onMove, this.BuildMouseEvent);
if ((/MSIE/i.test(navigator.userAgent))) {
- this._target.addEventListener("wheel", this.BuildEvent(this._onScroll, function (e) {
+ this._mouseWheelWireName = "wheel";
+ this._mouseWheelWire = this.BuildEvent(this._onScroll, function (e) {
e.wheelDeltaX = -e.deltaX;
e.wheelDeltaY = -e.deltaY;
return _this.BuildMouseScrollEvent(e);
- }), false);
+ });
} else if ((/Firefox/i.test(navigator.userAgent))) {
- this._target.addEventListener("DOMMouseScroll", this.BuildEvent(this._onScroll, function (e) {
+ this._mouseWheelWireName = "DOMMouseScroll";
+ this._mouseWheelWire = this.BuildEvent(this._onScroll, function (e) {
e.wheelDeltaX = e.axis === 1 ? -e.detail : 0;
e.wheelDeltaY = e.axis === 2 ? -e.detail : 0;
return _this.BuildMouseScrollEvent(e);
- }), false);
+ });
} else {
- this._target.addEventListener("mousewheel", this.BuildEvent(this._onScroll, this.BuildMouseScrollEvent), false);
+ this._mouseWheelWireName = "mousewheel";
+ this._mouseWheelWire = this.BuildEvent(this._onScroll, this.BuildMouseScrollEvent);
}
+
+ this._target.addEventListener("click", this._clickWire, false);
+ this._target.addEventListener("contextmenu", this._contextMenuWire, false);
+ this._target.addEventListener("dblclick", this._dblClickWire, false);
+ this._target.addEventListener("mousedown", this._mouseDownWire, false);
+ this._target.addEventListener("mouseup", this._mouseUpWire, false);
+ this._target.addEventListener("mousemove", this._mouseMoveWire, false);
+ this._target.addEventListener(this._mouseWheelWireName, this._mouseWheelWire, false);
+ };
+
+ MouseHandler.prototype.Unwire = function () {
+ this._target.removeEventListener("click", this._clickWire, false);
+ this._target.removeEventListener("contextmenu", this._contextMenuWire, false);
+ this._target.removeEventListener("dblclick", this._dblClickWire, false);
+ this._target.removeEventListener("mousedown", this._mouseDownWire, false);
+ this._target.removeEventListener("mouseup", this._mouseUpWire, false);
+ this._target.removeEventListener("mousemove", this._mouseMoveWire, false);
+ this._target.removeEventListener(this._mouseWheelWireName, this._mouseWheelWire, false);
};
MouseHandler.prototype.BuildEvent = function (eventHandler, mouseEventBuilder, returnValue) {
diff --git a/EndGate/EndGate.Core.JS/Input/Mouse/MouseHandler.ts b/EndGate/EndGate.Core.JS/Input/Mouse/MouseHandler.ts
index 5058e4a4..a2cd9ef7 100644
--- a/EndGate/EndGate.Core.JS/Input/Mouse/MouseHandler.ts
+++ b/EndGate/EndGate.Core.JS/Input/Mouse/MouseHandler.ts
@@ -1,5 +1,6 @@
///
///
+///
///
///
///
@@ -10,7 +11,7 @@ module EndGate.Input {
/**
* Defines a handler that will monitor mouse events over a specified area and will execute appropriate functions based on the events.
*/
- export class MouseHandler {
+ export class MouseHandler implements IDisposable {
// Used to determine mouse buttons without using extra conditional statements, performance enhancer
private static MouseButtonArray = [null, _.MouseButton.Left, _.MouseButton.Middle, _.MouseButton.Right];
@@ -30,12 +31,24 @@ module EndGate.Input {
private _target: HTMLElement;
+ // For disposing
+ private _contextMenuWire: (e: MouseEvent) => void;
+ private _clickWire: (e: MouseEvent) => void;
+ private _dblClickWire: (e: MouseEvent) => void;
+ private _mouseDownWire: (e: MouseEvent) => void;
+ private _mouseUpWire: (e: MouseEvent) => void;
+ private _mouseMoveWire: (e: MouseEvent) => void;
+ private _mouseWheelWireName: string;
+ private _mouseWheelWire: (e: MouseEvent) => void;
+ private _disposed: boolean;
+
/**
* Creates a new instance of the MouseHandler object.
* @param target The object to monitor mouse events for.
*/
constructor(target: HTMLElement) {
this._target = target;
+ this._disposed = false;
this._onClick = new EventHandler1();
this._onDoubleClick = new EventHandler1();
@@ -46,7 +59,7 @@ module EndGate.Input {
// Generic flags to check mouse state
this._leftIsDown = false;
- this._middleIsDown= false;
+ this._middleIsDown = false;
this._rightIsDown = false;
this.Wire();
@@ -132,32 +145,76 @@ module EndGate.Input {
return this._onScroll;
}
+ /**
+ * Disposes the MouseHandler and unbinds all bound events.
+ */
+ public Dispose(): void {
+ if (!this._disposed) {
+ this._disposed = true;
+
+ this._onClick.Dispose();
+ this._onDoubleClick.Dispose();
+ this._onDown.Dispose();
+ this._onMove.Dispose();
+ this._onScroll.Dispose();
+ this._onUp.Dispose();
+
+ this.Unwire();
+
+ this._target = null;
+ }
+ else {
+ throw new Error("MouseHandler cannot be disposed more than once");
+ }
+ }
+
private Wire(): void {
- this._target.addEventListener("click",this._target.oncontextmenu = this.BuildEvent(this._onClick, this.BuildMouseClickEvent),false);
- this._target.addEventListener("dblclick", this.BuildEvent(this._onDoubleClick, this.BuildMouseClickEvent), false);
- this._target.addEventListener("mousedown", this.BuildEvent(this._onDown, this.BuildMouseClickEvent), false);
- this._target.addEventListener("mouseup", this.BuildEvent(this._onUp, this.BuildMouseClickEvent), false);
- this._target.addEventListener("mousemove", this.BuildEvent(this._onMove, this.BuildMouseEvent), false);
+ this._clickWire = this._contextMenuWire = this.BuildEvent(this._onClick, this.BuildMouseClickEvent);
+ this._dblClickWire = this.BuildEvent(this._onDoubleClick, this.BuildMouseClickEvent);
+ this._mouseDownWire = this.BuildEvent(this._onDown, this.BuildMouseClickEvent);
+ this._mouseUpWire = this.BuildEvent(this._onUp, this.BuildMouseClickEvent)
+ this._mouseMoveWire = this.BuildEvent(this._onMove, this.BuildMouseEvent);
// OnScroll, in order to detect horizontal scrolling need to hack a bit (browser sniffing)
// if we were just doing vertical scrolling we could settle with the else statement in this block
if ((/MSIE/i.test(navigator.userAgent))) {
- this._target.addEventListener("wheel", this.BuildEvent(this._onScroll, (e: any) => {
+ this._mouseWheelWireName = "wheel";
+ this._mouseWheelWire = this.BuildEvent(this._onScroll, (e: any) => {
e.wheelDeltaX = -e.deltaX;
e.wheelDeltaY = -e.deltaY;
return this.BuildMouseScrollEvent(e);
- }), false);
+ });
}
else if ((/Firefox/i.test(navigator.userAgent))) {
- this._target.addEventListener("DOMMouseScroll", this.BuildEvent(this._onScroll, (e: any) => {
+ this._mouseWheelWireName = "DOMMouseScroll";
+ this._mouseWheelWire = this.BuildEvent(this._onScroll, (e: any) => {
e.wheelDeltaX = e.axis === 1 ? -e.detail : 0;
e.wheelDeltaY = e.axis === 2 ? -e.detail : 0;
return this.BuildMouseScrollEvent(e);
- }), false);
+ });
}
else {
- this._target.addEventListener("mousewheel", this.BuildEvent(this._onScroll, this.BuildMouseScrollEvent), false);
+ this._mouseWheelWireName = "mousewheel";
+ this._mouseWheelWire = this.BuildEvent(this._onScroll, this.BuildMouseScrollEvent);
}
+
+ this._target.addEventListener("click", this._clickWire, false);
+ this._target.addEventListener("contextmenu", this._contextMenuWire, false);
+ this._target.addEventListener("dblclick", this._dblClickWire, false);
+ this._target.addEventListener("mousedown", this._mouseDownWire, false);
+ this._target.addEventListener("mouseup", this._mouseUpWire, false);
+ this._target.addEventListener("mousemove", this._mouseMoveWire, false);
+ this._target.addEventListener(this._mouseWheelWireName, this._mouseWheelWire, false);
+ }
+
+ private Unwire(): void {
+ this._target.removeEventListener("click", this._clickWire, false);
+ this._target.removeEventListener("contextmenu", this._contextMenuWire, false);
+ this._target.removeEventListener("dblclick", this._dblClickWire, false);
+ this._target.removeEventListener("mousedown", this._mouseDownWire, false);
+ this._target.removeEventListener("mouseup", this._mouseUpWire, false);
+ this._target.removeEventListener("mousemove", this._mouseMoveWire, false);
+ this._target.removeEventListener(this._mouseWheelWireName, this._mouseWheelWire, false);
}
private BuildEvent(eventHandler: EventHandler1, mouseEventBuilder: (mouseEvent: MouseEvent) => IMouseEvent, returnValue: boolean = false): (e: MouseEvent) => void {
@@ -195,7 +252,7 @@ module EndGate.Input {
return new Vector2d(
event.offsetX ? (event.offsetX) : event.pageX - this._target.offsetLeft,
event.offsetY ? (event.offsetY) : event.pageY - this._target.offsetTop
- );
+ );
}
private GetMouseButton(event: MouseEvent): string {
@@ -206,7 +263,7 @@ module EndGate.Input {
return _.MouseButton.Right;
}
- private GetMouseScrollDierction(event: any): Vector2d{
+ private GetMouseScrollDierction(event: any): Vector2d {
return new Vector2d(-Math.max(-1, Math.min(1, event.wheelDeltaX)), -Math.max(-1, Math.min(1, event.wheelDeltaY)));
}
}