3 * Guacamole - Clientless Remote Desktop
4 * Copyright (C) 2010 Michael Jumper
6 * This program is free software: you can redistribute it and/or modify
7 * it under the terms of the GNU Affero General Public License as published by
8 * the Free Software Foundation, either version 3 of the License, or
9 * (at your option) any later version.
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU Affero General Public License for more details.
16 * You should have received a copy of the GNU Affero General Public License
17 * along with this program. If not, see <http://www.gnu.org/licenses/>.
20 // Guacamole namespace
21 var Guacamole = Guacamole || {};
24 * Provides cross-browser mouse events for a given element. The events of
25 * the given element are automatically populated with handlers that translate
26 * mouse events into a non-browser-specific event provided by the
27 * Guacamole.Mouse instance.
29 * Touch event support is planned, but currently only in testing (translate
30 * touch events into mouse events).
33 * @param {Element} element The Element to use to provide mouse events.
35 Guacamole.Mouse = function(element) {
38 * Reference to this Guacamole.Mouse.
41 var guac_mouse = this;
44 * The current mouse state. The properties of this state are updated when
45 * mouse events fire. This state object is also passed in as a parameter to
46 * the handler of any mouse events.
48 * @type Guacamole.Mouse.State
50 this.currentState = new Guacamole.Mouse.State(
52 false, false, false, false, false
56 * Fired whenever the user presses a mouse button down over the element
57 * associated with this Guacamole.Mouse.
60 * @param {Guacamole.Mouse.State} state The current mouse state.
62 this.onmousedown = null;
65 * Fired whenever the user releases a mouse button down over the element
66 * associated with this Guacamole.Mouse.
69 * @param {Guacamole.Mouse.State} state The current mouse state.
71 this.onmouseup = null;
74 * Fired whenever the user moves the mouse over the element associated with
75 * this Guacamole.Mouse.
78 * @param {Guacamole.Mouse.State} state The current mouse state.
80 this.onmousemove = null;
82 // Block context menu so right-click gets sent properly
83 element.oncontextmenu = function(e) {
87 element.onmousemove = function(e) {
91 var absoluteMouseX = e.pageX;
92 var absoluteMouseY = e.pageY;
94 guac_mouse.currentState.x = absoluteMouseX - element.offsetLeft;
95 guac_mouse.currentState.y = absoluteMouseY - element.offsetTop;
97 // This is all JUST so we can get the mouse position within the element
98 var parent = element.offsetParent;
100 if (parent.offsetLeft && parent.offsetTop) {
101 guac_mouse.currentState.x -= parent.offsetLeft;
102 guac_mouse.currentState.y -= parent.offsetTop;
104 parent = parent.offsetParent;
107 if (guac_mouse.onmousemove)
108 guac_mouse.onmousemove(guac_mouse.currentState);
113 element.onmousedown = function(e) {
119 guac_mouse.currentState.left = true;
122 guac_mouse.currentState.middle = true;
125 guac_mouse.currentState.right = true;
129 if (guac_mouse.onmousedown)
130 guac_mouse.onmousedown(guac_mouse.currentState);
135 element.onmouseup = function(e) {
141 guac_mouse.currentState.left = false;
144 guac_mouse.currentState.middle = false;
147 guac_mouse.currentState.right = false;
151 if (guac_mouse.onmouseup)
152 guac_mouse.onmouseup(guac_mouse.currentState);
156 element.onmouseout = function(e) {
160 // Release all buttons
161 if (guac_mouse.currentState.left
162 || guac_mouse.currentState.middle
163 || guac_mouse.currentState.right) {
165 guac_mouse.currentState.left = false;
166 guac_mouse.currentState.middle = false;
167 guac_mouse.currentState.right = false;
169 if (guac_mouse.onmouseup)
170 guac_mouse.onmouseup(guac_mouse.currentState);
175 // Override selection on mouse event element.
176 element.onselectstart = function() {
180 // Scroll wheel support
181 function handleScroll(e) {
186 else if (e.wheelDelta)
187 delta = -event.wheelDelta;
191 if (guac_mouse.onmousedown) {
192 guac_mouse.currentState.up = true;
193 guac_mouse.onmousedown(guac_mouse.currentState);
196 if (guac_mouse.onmouseup) {
197 guac_mouse.currentState.up = false;
198 guac_mouse.onmouseup(guac_mouse.currentState);
204 if (guac_mouse.onmousedown) {
205 guac_mouse.currentState.down = true;
206 guac_mouse.onmousedown(guac_mouse.currentState);
209 if (guac_mouse.onmouseup) {
210 guac_mouse.currentState.down = false;
211 guac_mouse.onmouseup(guac_mouse.currentState);
215 if (e.preventDefault)
218 e.returnValue = false;
221 element.addEventListener('DOMMouseScroll', handleScroll, false);
223 element.onmousewheel = function(e) {
230 * Simple container for properties describing the state of a mouse.
233 * @param {Number} x The X position of the mouse pointer in pixels.
234 * @param {Number} y The Y position of the mouse pointer in pixels.
235 * @param {Boolean} left Whether the left mouse button is pressed.
236 * @param {Boolean} middle Whether the middle mouse button is pressed.
237 * @param {Boolean} right Whether the right mouse button is pressed.
238 * @param {Boolean} up Whether the up mouse button is pressed (the fourth
239 * button, usually part of a scroll wheel).
240 * @param {Boolean} down Whether the down mouse button is pressed (the fifth
241 * button, usually part of a scroll wheel).
243 Guacamole.Mouse.State = function(x, y, left, middle, right, up, down) {
246 * The current X position of the mouse pointer.
252 * The current Y position of the mouse pointer.
258 * Whether the left mouse button is currently pressed.
264 * Whether the middle mouse button is currently pressed.
270 * Whether the right mouse button is currently pressed.
276 * Whether the up mouse button is currently pressed. This is the fourth
277 * mouse button, associated with upward scrolling of the mouse scroll
284 * Whether the down mouse button is currently pressed. This is the fifth
285 * mouse button, associated with downward scrolling of the mouse scroll