jquery-simulate

Simulate events to help unit test user interactions

Este script no debería instalarse directamente. Es una biblioteca que utilizan otros scripts mediante la meta-directiva de inclusión // @require https://update.greatest.deepsurf.us/scripts/24819/157606/jquery-simulate.js

  1. /*!
  2. * jQuery Simulate v@VERSION - simulate browser mouse and keyboard events
  3. *
  4. *
  5. * Copyright jQuery Foundation and other contributors
  6. * Released under the MIT license.
  7. * http://jquery.org/license
  8. *
  9. * Date: @DATE
  10. */
  11.  
  12. ;(function( $, undefined ) {
  13.  
  14. var rkeyEvent = /^key/,
  15. rmouseEvent = /^(?:mouse|contextmenu)|click/;
  16.  
  17. $.fn.simulate = function( type, options ) {
  18. return this.each(function() {
  19. new $.simulate( this, type, options );
  20. });
  21. };
  22.  
  23. $.simulate = function( elem, type, options ) {
  24. var method = $.camelCase( "simulate-" + type );
  25.  
  26. this.target = elem;
  27. this.options = options;
  28.  
  29. if ( this[ method ] ) {
  30. this[ method ]();
  31. } else {
  32. this.simulateEvent( elem, type, options );
  33. }
  34. };
  35.  
  36. $.extend( $.simulate, {
  37.  
  38. keyCode: {
  39. BACKSPACE: 8,
  40. COMMA: 188,
  41. DELETE: 46,
  42. DOWN: 40,
  43. END: 35,
  44. ENTER: 13,
  45. ESCAPE: 27,
  46. HOME: 36,
  47. LEFT: 37,
  48. NUMPAD_ADD: 107,
  49. NUMPAD_DECIMAL: 110,
  50. NUMPAD_DIVIDE: 111,
  51. NUMPAD_ENTER: 108,
  52. NUMPAD_MULTIPLY: 106,
  53. NUMPAD_SUBTRACT: 109,
  54. PAGE_DOWN: 34,
  55. PAGE_UP: 33,
  56. PERIOD: 190,
  57. RIGHT: 39,
  58. SPACE: 32,
  59. TAB: 9,
  60. UP: 38
  61. },
  62.  
  63. buttonCode: {
  64. LEFT: 0,
  65. MIDDLE: 1,
  66. RIGHT: 2
  67. }
  68. });
  69.  
  70. $.extend( $.simulate.prototype, {
  71.  
  72. simulateEvent: function( elem, type, options ) {
  73. var event = this.createEvent( type, options );
  74. this.dispatchEvent( elem, type, event, options );
  75. },
  76.  
  77. createEvent: function( type, options ) {
  78. if ( rkeyEvent.test( type ) ) {
  79. return this.keyEvent( type, options );
  80. }
  81.  
  82. if ( rmouseEvent.test( type ) ) {
  83. return this.mouseEvent( type, options );
  84. }
  85. },
  86.  
  87. mouseEvent: function( type, options ) {
  88. var event, eventDoc, doc, body;
  89. options = $.extend({
  90. bubbles: true,
  91. cancelable: (type !== "mousemove"),
  92. view: window,
  93. detail: 0,
  94. screenX: 0,
  95. screenY: 0,
  96. clientX: 1,
  97. clientY: 1,
  98. ctrlKey: false,
  99. altKey: false,
  100. shiftKey: false,
  101. metaKey: false,
  102. button: 0,
  103. relatedTarget: undefined
  104. }, options );
  105.  
  106. if ( document.createEvent ) {
  107. event = document.createEvent( "MouseEvents" );
  108. event.initMouseEvent( type, options.bubbles, options.cancelable,
  109. options.view, options.detail,
  110. options.screenX, options.screenY, options.clientX, options.clientY,
  111. options.ctrlKey, options.altKey, options.shiftKey, options.metaKey,
  112. options.button, options.relatedTarget || document.body.parentNode );
  113.  
  114. // IE 9+ creates events with pageX and pageY set to 0.
  115. // Trying to modify the properties throws an error,
  116. // so we define getters to return the correct values.
  117. if ( event.pageX === 0 && event.pageY === 0 && Object.defineProperty ) {
  118. eventDoc = event.relatedTarget.ownerDocument || document;
  119. doc = eventDoc.documentElement;
  120. body = eventDoc.body;
  121.  
  122. Object.defineProperty( event, "pageX", {
  123. get: function() {
  124. return options.clientX +
  125. ( doc && doc.scrollLeft || body && body.scrollLeft || 0 ) -
  126. ( doc && doc.clientLeft || body && body.clientLeft || 0 );
  127. }
  128. });
  129. Object.defineProperty( event, "pageY", {
  130. get: function() {
  131. return options.clientY +
  132. ( doc && doc.scrollTop || body && body.scrollTop || 0 ) -
  133. ( doc && doc.clientTop || body && body.clientTop || 0 );
  134. }
  135. });
  136. }
  137. } else if ( document.createEventObject ) {
  138. event = document.createEventObject();
  139. $.extend( event, options );
  140. // standards event.button uses constants defined here: http://msdn.microsoft.com/en-us/library/ie/ff974877(v=vs.85).aspx
  141. // old IE event.button uses constants defined here: http://msdn.microsoft.com/en-us/library/ie/ms533544(v=vs.85).aspx
  142. // so we actually need to map the standard back to oldIE
  143. event.button = {
  144. 0: 1,
  145. 1: 4,
  146. 2: 2
  147. }[ event.button ] || ( event.button === -1 ? 0 : event.button );
  148. }
  149.  
  150. return event;
  151. },
  152.  
  153. keyEvent: function( type, options ) {
  154. var event;
  155. options = $.extend({
  156. bubbles: true,
  157. cancelable: true,
  158. view: window,
  159. ctrlKey: false,
  160. altKey: false,
  161. shiftKey: false,
  162. metaKey: false,
  163. keyCode: 0,
  164. charCode: undefined
  165. }, options );
  166.  
  167. if ( document.createEvent ) {
  168. try {
  169. event = document.createEvent( "KeyEvents" );
  170. event.initKeyEvent( type, options.bubbles, options.cancelable, options.view,
  171. options.ctrlKey, options.altKey, options.shiftKey, options.metaKey,
  172. options.keyCode, options.charCode );
  173. // initKeyEvent throws an exception in WebKit
  174. // see: http://stackoverflow.com/questions/6406784/initkeyevent-keypress-only-works-in-firefox-need-a-cross-browser-solution
  175. // and also https://bugs.webkit.org/show_bug.cgi?id=13368
  176. // fall back to a generic event until we decide to implement initKeyboardEvent
  177. } catch( err ) {
  178. event = document.createEvent( "Events" );
  179. event.initEvent( type, options.bubbles, options.cancelable );
  180. $.extend( event, {
  181. view: options.view,
  182. ctrlKey: options.ctrlKey,
  183. altKey: options.altKey,
  184. shiftKey: options.shiftKey,
  185. metaKey: options.metaKey,
  186. keyCode: options.keyCode,
  187. charCode: options.charCode
  188. });
  189. }
  190. } else if ( document.createEventObject ) {
  191. event = document.createEventObject();
  192. $.extend( event, options );
  193. }
  194.  
  195. if ( !!/msie [\w.]+/.exec( navigator.userAgent.toLowerCase() ) || (({}).toString.call( window.opera ) === "[object Opera]") ) {
  196. event.keyCode = (options.charCode > 0) ? options.charCode : options.keyCode;
  197. event.charCode = undefined;
  198. }
  199.  
  200. return event;
  201. },
  202.  
  203. dispatchEvent: function( elem, type, event ) {
  204. if ( elem.dispatchEvent ) {
  205. elem.dispatchEvent( event );
  206. } else if ( type === "click" && elem.click && elem.nodeName.toLowerCase() === "input" ) {
  207. elem.click();
  208. } else if ( elem.fireEvent ) {
  209. elem.fireEvent( "on" + type, event );
  210. }
  211. },
  212.  
  213. simulateFocus: function() {
  214. var focusinEvent,
  215. triggered = false,
  216. element = $( this.target );
  217.  
  218. function trigger() {
  219. triggered = true;
  220. }
  221.  
  222. element.bind( "focus", trigger );
  223. element[ 0 ].focus();
  224.  
  225. if ( !triggered ) {
  226. focusinEvent = $.Event( "focusin" );
  227. focusinEvent.preventDefault();
  228. element.trigger( focusinEvent );
  229. element.triggerHandler( "focus" );
  230. }
  231. element.unbind( "focus", trigger );
  232. },
  233.  
  234. simulateBlur: function() {
  235. var focusoutEvent,
  236. triggered = false,
  237. element = $( this.target );
  238.  
  239. function trigger() {
  240. triggered = true;
  241. }
  242.  
  243. element.bind( "blur", trigger );
  244. element[ 0 ].blur();
  245.  
  246. // blur events are async in IE
  247. setTimeout(function() {
  248. // IE won't let the blur occur if the window is inactive
  249. if ( element[ 0 ].ownerDocument.activeElement === element[ 0 ] ) {
  250. element[ 0 ].ownerDocument.body.focus();
  251. }
  252.  
  253. // Firefox won't trigger events if the window is inactive
  254. // IE doesn't trigger events if we had to manually focus the body
  255. if ( !triggered ) {
  256. focusoutEvent = $.Event( "focusout" );
  257. focusoutEvent.preventDefault();
  258. element.trigger( focusoutEvent );
  259. element.triggerHandler( "blur" );
  260. }
  261. element.unbind( "blur", trigger );
  262. }, 1 );
  263. }
  264. });
  265.  
  266.  
  267.  
  268. /** complex events **/
  269.  
  270. function findCenter( elem ) {
  271. var offset,
  272. document = $( elem.ownerDocument );
  273. elem = $( elem );
  274. offset = elem.offset();
  275.  
  276. return {
  277. x: offset.left + elem.outerWidth() / 2 - document.scrollLeft(),
  278. y: offset.top + elem.outerHeight() / 2 - document.scrollTop()
  279. };
  280. }
  281.  
  282. function findCorner( elem ) {
  283. var offset,
  284. document = $( elem.ownerDocument );
  285. elem = $( elem );
  286. offset = elem.offset();
  287.  
  288. return {
  289. x: offset.left - document.scrollLeft(),
  290. y: offset.top - document.scrollTop()
  291. };
  292. }
  293.  
  294. $.extend( $.simulate.prototype, {
  295. simulateDrag: function() {
  296. var i = 0,
  297. target = this.target,
  298. eventDoc = target.ownerDocument,
  299. options = this.options,
  300. center = options.handle === "corner" ? findCorner( target ) : findCenter( target ),
  301. x = Math.floor( center.x ),
  302. y = Math.floor( center.y ),
  303. coord = { clientX: x, clientY: y },
  304. dx = options.dx || ( options.x !== undefined ? options.x - x : 0 ),
  305. dy = options.dy || ( options.y !== undefined ? options.y - y : 0 ),
  306. moves = options.moves || 3;
  307.  
  308. this.simulateEvent( target, "mousedown", coord );
  309.  
  310. for ( ; i < moves ; i++ ) {
  311. x += dx / moves;
  312. y += dy / moves;
  313.  
  314. coord = {
  315. clientX: Math.round( x ),
  316. clientY: Math.round( y )
  317. };
  318.  
  319. this.simulateEvent( eventDoc, "mousemove", coord );
  320. }
  321.  
  322. if ( $.contains( eventDoc, target ) ) {
  323. this.simulateEvent( target, "mouseup", coord );
  324. this.simulateEvent( target, "click", coord );
  325. } else {
  326. this.simulateEvent( eventDoc, "mouseup", coord );
  327. }
  328. }
  329. });
  330.  
  331. })( jQuery );