--- /dev/null
+/* Copyright (c) 2007 Eduardo Lundgren (eduardolundgren@gmail.com)
+ * Dual licensed under the MIT (http://www.opensource.org/licenses/mit-license.php)
+ * and GPL (http://www.opensource.org/licenses/gpl-license.php) licenses.
+ *
+ * Version: 0.1a
+ * Requires jQuery 1.2.x+
+ * Docs: http://docs.jquery.com/Plugins/userAction
+ */
+
+;(function($) {
+
+$.fn.extend({
+ userAction: function(type) {
+ var args = arguments, opts = {}, a1 = args[1], a2 = args[2];
+
+ // transfer center offset
+ if (a1 && a1.length) {
+ opts.center = [a1[0], a1[1]];
+ }
+ // set x and y
+ else if (typeof a1 == StringPool.NUMBER) {
+ opts.x = a1; options.y = a2;
+ }
+ // extend options
+ else {
+ $.extend(opts, a1);
+ }
+
+ return this.each(function() {
+ new $.userAction(this, type, opts);
+ });
+ }
+});
+
+$.userAction = function(el, type, options) {
+ this.type = type;
+ this.options = $.extend({}, $.userAction.defaults, options || {});
+ this.target = $(this.options.target || el)[0];
+
+ var self = this, o = this.options, c = o.center, xy = this.findCenter(
+ c && c.length ? c : [0, 0]
+ );
+ // if x and y not set, get the center of the element
+ o.x = o.x || xy.x; o.y = o.y || xy.y;
+
+ var EVENT_DEFAULT = {
+ view: window,
+ detail: 0,
+ isTrusted: false,
+ bubbles: o.bubbles || true,
+ cancelable: o.cancelable || false,
+ ctrlKey: o.ctrlKey || false,
+ altKey: o.altKey || false,
+ shiftKey: o.shiftKey || false,
+ metaKey: o.metaKey || false
+ },
+
+ isMouse = /^mouse(over|out|down|up|move)|(dbl)?click$/i.test(type),
+ isKeyboard = /^textevent|key(up|down|press)$/i.test(type);
+
+ var EVT = isMouse ?
+ $.extend({}, EVENT_DEFAULT, {
+ clientX: o.x, clientY: o.y,
+ screenX: o.screenX || 0, screenY: o.screenY || 0,
+ relatedTarget: $(o.relatedTarget)[0] || null,
+ button: o.button || ($.browser.msie ? 1 : 0)
+ }) :
+ $.extend({}, EVENT_DEFAULT, {
+ keyCode: o.keyCode || 0, charCode: o.charCode || 0
+ });
+
+ if (o.before) o.before.apply(this.target, [
+ // simulate correct target before the event fire
+ // the browser just set the correct EVT.target after dispatchment
+ $.event.fix(EVT).target = this.target, o.x, o.y, this]);
+
+ // check event type for mouse events
+ if (isMouse) {
+ // simulating mouse event
+ EVT = this.mouseEvent(EVT)
+ }
+
+ // check event type for key events
+ if (isKeyboard) {
+ // simulating keuboard event
+ EVT = this.keyboardEvent(EVT);
+ }
+
+ if (o.after) o.after.apply(this.target, [EVT, o.x, o.y, this]);
+};
+
+$.extend($.userAction.prototype, {
+
+ mouseEvent: function(EVT) {
+ var evt, type = this.type, o = this.options;
+
+ //check for DOM-compliant browsers
+ if ($.isFunction(document.createEvent)) {
+ evt = document.createEvent(StringPool.MOUSE_EVENTS);
+
+ //Safari 2.x doesn't implement initMouseEvent()
+ if ($.isFunction(evt.initMouseEvent)) {
+ evt.initMouseEvent(type,
+ EVT.bubbles, EVT.cancelable, EVT.view, EVT.detail,
+ EVT.screenX, EVT.screenY, EVT.clientX, EVT.clientY,
+ EVT.ctrlKey, EVT.altKey, EVT.shiftKey, EVT.metaKey,
+ EVT.button, EVT.relatedTarget);
+ } else {
+ // Safari
+ evt = document.createEvent(StringPool.UI_EVENTS);
+ customEvent.initEvent(type, EVT.bubbles, EVT.cancelable);
+ $.extend(evt, EVT);
+ }
+
+ // check to see if relatedTarget has been assigned
+ if (EVT.relatedTarget && !evt.relatedTarget){
+ if (type == StringPool.MOUSEOUT) {
+ evt.toElement = EVT.relatedTarget;
+ } else if (type == StringPool.MOUSEOVER) {
+ evt.fromElement = EVT.relatedTarget;
+ }
+ }
+ // fire the event
+ this.target.dispatchEvent(evt);
+
+ } else if (document.createEventObject) {
+ evt = document.createEventObject();
+ $.extend(evt, EVT)
+ // IE won't allow assignment to toElement or fromElement
+ evt.relatedTarget = EVT.relatedTarget;
+ // fire the event
+ this.target.fireEvent(StringPool.ON + type, evt);
+ }
+
+ return evt;
+ },
+
+ keyboardEvent: function(EVT) {
+ var evt, type = this.type, o = this.options;
+
+ //Safari 2.x doesn't implement initMouseEvent()
+ if ($.isFunction(document.createEvent)) {
+
+ try {
+ // try to create key event
+ evt = document.createEvent("KeyEvents");
+
+ evt.initKeyEvent(type,
+ EVT.bubbles, EVT.cancelable, EVT.view, EVT.ctrlKey,
+ EVT.altKey, EVT.shiftKey, EVT.metaKey, EVT.keyCode, EVT.charCode);
+
+ } catch (err) {
+ // we need another try-catch for Safari 2.x
+ try {
+ // generic event, will fail in Safari 2.x
+ evt = document.createEvent("Events");
+ } catch (uierror){
+ // create a UIEvent for Safari 2.x
+ evt = document.createEvent("UIEvents");
+ } finally {
+ evt.initEvent(type, EVT.bubbles, EVT.cancelable);
+ // initialize
+ $.extend(evt, EVT);
+ }
+ }
+
+ // fire the event
+ this.target.dispatchEvent(evt);
+
+ } else if (document.createEventObject) {
+ // create an IE event object
+ evt = document.createEventObject();
+
+ // assign available properties
+ $.extend(evt, EVT);
+
+ // IE doesn't support charCode explicitly
+ evt.keyCode = (EVT.charCode > 0) ? EVT.charCode : EVT.keyCode;
+
+ // fire the event
+ this.target.fireEvent("on" + type, evt);
+ }
+
+ return evt;
+ },
+
+ findCenter: function(offset) {
+ var el = $(this.target), o = el.offset();
+ return {
+ x: o.left + (((offset||[0, 0])[0]) || 0) + el.width() / 2,
+ y: o.top + (((offset||[0, 0])[1]) || 0) + el.height() / 2
+ };
+ }
+});
+
+$.extend($.userAction, {
+ defaults: {
+ center: true
+ }
+});
+
+var StringPool = {
+ ON: 'on',
+ NUMBER: 'number',
+ MOUSEOVER: 'mouseover',
+ MOUSEOUT: 'mouseout',
+ MOUSE_EVENTS: "MouseEvents",
+ UIU_EVENTS: "UIEvents"
+};
+
+})(jQuery);
\ No newline at end of file