not really known
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

3420 lines
103 KiB

  1. /*!
  2. * TweenJS
  3. * Visit http://createjs.com/ for documentation, updates and examples.
  4. *
  5. * Copyright (c) 2010 gskinner.com, inc.
  6. *
  7. * Permission is hereby granted, free of charge, to any person
  8. * obtaining a copy of this software and associated documentation
  9. * files (the "Software"), to deal in the Software without
  10. * restriction, including without limitation the rights to use,
  11. * copy, modify, merge, publish, distribute, sublicense, and/or sell
  12. * copies of the Software, and to permit persons to whom the
  13. * Software is furnished to do so, subject to the following
  14. * conditions:
  15. *
  16. * The above copyright notice and this permission notice shall be
  17. * included in all copies or substantial portions of the Software.
  18. *
  19. * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
  20. * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
  21. * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
  22. * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
  23. * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
  24. * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
  25. * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
  26. * OTHER DEALINGS IN THE SOFTWARE.
  27. */
  28. //##############################################################################
  29. // extend.js
  30. //##############################################################################
  31. this.createjs = this.createjs||{};
  32. /**
  33. * @class Utility Methods
  34. */
  35. /**
  36. * Sets up the prototype chain and constructor property for a new class.
  37. *
  38. * This should be called right after creating the class constructor.
  39. *
  40. * function MySubClass() {}
  41. * createjs.extend(MySubClass, MySuperClass);
  42. * MySubClass.prototype.doSomething = function() { }
  43. *
  44. * var foo = new MySubClass();
  45. * console.log(foo instanceof MySuperClass); // true
  46. * console.log(foo.prototype.constructor === MySubClass); // true
  47. *
  48. * @method extend
  49. * @param {Function} subclass The subclass.
  50. * @param {Function} superclass The superclass to extend.
  51. * @return {Function} Returns the subclass's new prototype.
  52. */
  53. createjs.extend = function(subclass, superclass) {
  54. "use strict";
  55. function o() { this.constructor = subclass; }
  56. o.prototype = superclass.prototype;
  57. return (subclass.prototype = new o());
  58. };
  59. //##############################################################################
  60. // promote.js
  61. //##############################################################################
  62. this.createjs = this.createjs||{};
  63. /**
  64. * @class Utility Methods
  65. */
  66. /**
  67. * Promotes any methods on the super class that were overridden, by creating an alias in the format `prefix_methodName`.
  68. * It is recommended to use the super class's name as the prefix.
  69. * An alias to the super class's constructor is always added in the format `prefix_constructor`.
  70. * This allows the subclass to call super class methods without using `function.call`, providing better performance.
  71. *
  72. * For example, if `MySubClass` extends `MySuperClass`, and both define a `draw` method, then calling `promote(MySubClass, "MySuperClass")`
  73. * would add a `MySuperClass_constructor` method to MySubClass and promote the `draw` method on `MySuperClass` to the
  74. * prototype of `MySubClass` as `MySuperClass_draw`.
  75. *
  76. * This should be called after the class's prototype is fully defined.
  77. *
  78. * function ClassA(name) {
  79. * this.name = name;
  80. * }
  81. * ClassA.prototype.greet = function() {
  82. * return "Hello "+this.name;
  83. * }
  84. *
  85. * function ClassB(name, punctuation) {
  86. * this.ClassA_constructor(name);
  87. * this.punctuation = punctuation;
  88. * }
  89. * createjs.extend(ClassB, ClassA);
  90. * ClassB.prototype.greet = function() {
  91. * return this.ClassA_greet()+this.punctuation;
  92. * }
  93. * createjs.promote(ClassB, "ClassA");
  94. *
  95. * var foo = new ClassB("World", "!?!");
  96. * console.log(foo.greet()); // Hello World!?!
  97. *
  98. * @method promote
  99. * @param {Function} subclass The class to promote super class methods on.
  100. * @param {String} prefix The prefix to add to the promoted method names. Usually the name of the superclass.
  101. * @return {Function} Returns the subclass.
  102. */
  103. createjs.promote = function(subclass, prefix) {
  104. "use strict";
  105. var subP = subclass.prototype, supP = (Object.getPrototypeOf&&Object.getPrototypeOf(subP))||subP.__proto__;
  106. if (supP) {
  107. subP[(prefix+="_") + "constructor"] = supP.constructor; // constructor is not always innumerable
  108. for (var n in supP) {
  109. if (subP.hasOwnProperty(n) && (typeof supP[n] == "function")) { subP[prefix + n] = supP[n]; }
  110. }
  111. }
  112. return subclass;
  113. };
  114. //##############################################################################
  115. // Event.js
  116. //##############################################################################
  117. this.createjs = this.createjs||{};
  118. (function() {
  119. "use strict";
  120. // constructor:
  121. /**
  122. * Contains properties and methods shared by all events for use with
  123. * {{#crossLink "EventDispatcher"}}{{/crossLink}}.
  124. *
  125. * Note that Event objects are often reused, so you should never
  126. * rely on an event object's state outside of the call stack it was received in.
  127. * @class Event
  128. * @param {String} type The event type.
  129. * @param {Boolean} bubbles Indicates whether the event will bubble through the display list.
  130. * @param {Boolean} cancelable Indicates whether the default behaviour of this event can be cancelled.
  131. * @constructor
  132. **/
  133. function Event(type, bubbles, cancelable) {
  134. // public properties:
  135. /**
  136. * The type of event.
  137. * @property type
  138. * @type String
  139. **/
  140. this.type = type;
  141. /**
  142. * The object that generated an event.
  143. * @property target
  144. * @type Object
  145. * @default null
  146. * @readonly
  147. */
  148. this.target = null;
  149. /**
  150. * The current target that a bubbling event is being dispatched from. For non-bubbling events, this will
  151. * always be the same as target. For example, if childObj.parent = parentObj, and a bubbling event
  152. * is generated from childObj, then a listener on parentObj would receive the event with
  153. * target=childObj (the original target) and currentTarget=parentObj (where the listener was added).
  154. * @property currentTarget
  155. * @type Object
  156. * @default null
  157. * @readonly
  158. */
  159. this.currentTarget = null;
  160. /**
  161. * For bubbling events, this indicates the current event phase:<OL>
  162. * <LI> capture phase: starting from the top parent to the target</LI>
  163. * <LI> at target phase: currently being dispatched from the target</LI>
  164. * <LI> bubbling phase: from the target to the top parent</LI>
  165. * </OL>
  166. * @property eventPhase
  167. * @type Number
  168. * @default 0
  169. * @readonly
  170. */
  171. this.eventPhase = 0;
  172. /**
  173. * Indicates whether the event will bubble through the display list.
  174. * @property bubbles
  175. * @type Boolean
  176. * @default false
  177. * @readonly
  178. */
  179. this.bubbles = !!bubbles;
  180. /**
  181. * Indicates whether the default behaviour of this event can be cancelled via
  182. * {{#crossLink "Event/preventDefault"}}{{/crossLink}}. This is set via the Event constructor.
  183. * @property cancelable
  184. * @type Boolean
  185. * @default false
  186. * @readonly
  187. */
  188. this.cancelable = !!cancelable;
  189. /**
  190. * The epoch time at which this event was created.
  191. * @property timeStamp
  192. * @type Number
  193. * @default 0
  194. * @readonly
  195. */
  196. this.timeStamp = (new Date()).getTime();
  197. /**
  198. * Indicates if {{#crossLink "Event/preventDefault"}}{{/crossLink}} has been called
  199. * on this event.
  200. * @property defaultPrevented
  201. * @type Boolean
  202. * @default false
  203. * @readonly
  204. */
  205. this.defaultPrevented = false;
  206. /**
  207. * Indicates if {{#crossLink "Event/stopPropagation"}}{{/crossLink}} or
  208. * {{#crossLink "Event/stopImmediatePropagation"}}{{/crossLink}} has been called on this event.
  209. * @property propagationStopped
  210. * @type Boolean
  211. * @default false
  212. * @readonly
  213. */
  214. this.propagationStopped = false;
  215. /**
  216. * Indicates if {{#crossLink "Event/stopImmediatePropagation"}}{{/crossLink}} has been called
  217. * on this event.
  218. * @property immediatePropagationStopped
  219. * @type Boolean
  220. * @default false
  221. * @readonly
  222. */
  223. this.immediatePropagationStopped = false;
  224. /**
  225. * Indicates if {{#crossLink "Event/remove"}}{{/crossLink}} has been called on this event.
  226. * @property removed
  227. * @type Boolean
  228. * @default false
  229. * @readonly
  230. */
  231. this.removed = false;
  232. }
  233. var p = Event.prototype;
  234. /**
  235. * <strong>REMOVED</strong>. Removed in favor of using `MySuperClass_constructor`.
  236. * See {{#crossLink "Utility Methods/extend"}}{{/crossLink}} and {{#crossLink "Utility Methods/promote"}}{{/crossLink}}
  237. * for details.
  238. *
  239. * There is an inheritance tutorial distributed with EaselJS in /tutorials/Inheritance.
  240. *
  241. * @method initialize
  242. * @protected
  243. * @deprecated
  244. */
  245. // p.initialize = function() {}; // searchable for devs wondering where it is.
  246. // public methods:
  247. /**
  248. * Sets {{#crossLink "Event/defaultPrevented"}}{{/crossLink}} to true if the event is cancelable.
  249. * Mirrors the DOM level 2 event standard. In general, cancelable events that have `preventDefault()` called will
  250. * cancel the default behaviour associated with the event.
  251. * @method preventDefault
  252. **/
  253. p.preventDefault = function() {
  254. this.defaultPrevented = this.cancelable&&true;
  255. };
  256. /**
  257. * Sets {{#crossLink "Event/propagationStopped"}}{{/crossLink}} to true.
  258. * Mirrors the DOM event standard.
  259. * @method stopPropagation
  260. **/
  261. p.stopPropagation = function() {
  262. this.propagationStopped = true;
  263. };
  264. /**
  265. * Sets {{#crossLink "Event/propagationStopped"}}{{/crossLink}} and
  266. * {{#crossLink "Event/immediatePropagationStopped"}}{{/crossLink}} to true.
  267. * Mirrors the DOM event standard.
  268. * @method stopImmediatePropagation
  269. **/
  270. p.stopImmediatePropagation = function() {
  271. this.immediatePropagationStopped = this.propagationStopped = true;
  272. };
  273. /**
  274. * Causes the active listener to be removed via removeEventListener();
  275. *
  276. * myBtn.addEventListener("click", function(evt) {
  277. * // do stuff...
  278. * evt.remove(); // removes this listener.
  279. * });
  280. *
  281. * @method remove
  282. **/
  283. p.remove = function() {
  284. this.removed = true;
  285. };
  286. /**
  287. * Returns a clone of the Event instance.
  288. * @method clone
  289. * @return {Event} a clone of the Event instance.
  290. **/
  291. p.clone = function() {
  292. return new Event(this.type, this.bubbles, this.cancelable);
  293. };
  294. /**
  295. * Provides a chainable shortcut method for setting a number of properties on the instance.
  296. *
  297. * @method set
  298. * @param {Object} props A generic object containing properties to copy to the instance.
  299. * @return {Event} Returns the instance the method is called on (useful for chaining calls.)
  300. * @chainable
  301. */
  302. p.set = function(props) {
  303. for (var n in props) { this[n] = props[n]; }
  304. return this;
  305. };
  306. /**
  307. * Returns a string representation of this object.
  308. * @method toString
  309. * @return {String} a string representation of the instance.
  310. **/
  311. p.toString = function() {
  312. return "[Event (type="+this.type+")]";
  313. };
  314. createjs.Event = Event;
  315. }());
  316. //##############################################################################
  317. // EventDispatcher.js
  318. //##############################################################################
  319. this.createjs = this.createjs||{};
  320. (function() {
  321. "use strict";
  322. // constructor:
  323. /**
  324. * EventDispatcher provides methods for managing queues of event listeners and dispatching events.
  325. *
  326. * You can either extend EventDispatcher or mix its methods into an existing prototype or instance by using the
  327. * EventDispatcher {{#crossLink "EventDispatcher/initialize"}}{{/crossLink}} method.
  328. *
  329. * Together with the CreateJS Event class, EventDispatcher provides an extended event model that is based on the
  330. * DOM Level 2 event model, including addEventListener, removeEventListener, and dispatchEvent. It supports
  331. * bubbling / capture, preventDefault, stopPropagation, stopImmediatePropagation, and handleEvent.
  332. *
  333. * EventDispatcher also exposes a {{#crossLink "EventDispatcher/on"}}{{/crossLink}} method, which makes it easier
  334. * to create scoped listeners, listeners that only run once, and listeners with associated arbitrary data. The
  335. * {{#crossLink "EventDispatcher/off"}}{{/crossLink}} method is merely an alias to
  336. * {{#crossLink "EventDispatcher/removeEventListener"}}{{/crossLink}}.
  337. *
  338. * Another addition to the DOM Level 2 model is the {{#crossLink "EventDispatcher/removeAllEventListeners"}}{{/crossLink}}
  339. * method, which can be used to listeners for all events, or listeners for a specific event. The Event object also
  340. * includes a {{#crossLink "Event/remove"}}{{/crossLink}} method which removes the active listener.
  341. *
  342. * <h4>Example</h4>
  343. * Add EventDispatcher capabilities to the "MyClass" class.
  344. *
  345. * EventDispatcher.initialize(MyClass.prototype);
  346. *
  347. * Add an event (see {{#crossLink "EventDispatcher/addEventListener"}}{{/crossLink}}).
  348. *
  349. * instance.addEventListener("eventName", handlerMethod);
  350. * function handlerMethod(event) {
  351. * console.log(event.target + " Was Clicked");
  352. * }
  353. *
  354. * <b>Maintaining proper scope</b><br />
  355. * Scope (ie. "this") can be be a challenge with events. Using the {{#crossLink "EventDispatcher/on"}}{{/crossLink}}
  356. * method to subscribe to events simplifies this.
  357. *
  358. * instance.addEventListener("click", function(event) {
  359. * console.log(instance == this); // false, scope is ambiguous.
  360. * });
  361. *
  362. * instance.on("click", function(event) {
  363. * console.log(instance == this); // true, "on" uses dispatcher scope by default.
  364. * });
  365. *
  366. * If you want to use addEventListener instead, you may want to use function.bind() or a similar proxy to manage
  367. * scope.
  368. *
  369. * <b>Browser support</b>
  370. * The event model in CreateJS can be used separately from the suite in any project, however the inheritance model
  371. * requires modern browsers (IE9+).
  372. *
  373. *
  374. * @class EventDispatcher
  375. * @constructor
  376. **/
  377. function EventDispatcher() {
  378. // private properties:
  379. /**
  380. * @protected
  381. * @property _listeners
  382. * @type Object
  383. **/
  384. this._listeners = null;
  385. /**
  386. * @protected
  387. * @property _captureListeners
  388. * @type Object
  389. **/
  390. this._captureListeners = null;
  391. }
  392. var p = EventDispatcher.prototype;
  393. /**
  394. * <strong>REMOVED</strong>. Removed in favor of using `MySuperClass_constructor`.
  395. * See {{#crossLink "Utility Methods/extend"}}{{/crossLink}} and {{#crossLink "Utility Methods/promote"}}{{/crossLink}}
  396. * for details.
  397. *
  398. * There is an inheritance tutorial distributed with EaselJS in /tutorials/Inheritance.
  399. *
  400. * @method initialize
  401. * @protected
  402. * @deprecated
  403. */
  404. // p.initialize = function() {}; // searchable for devs wondering where it is.
  405. // static public methods:
  406. /**
  407. * Static initializer to mix EventDispatcher methods into a target object or prototype.
  408. *
  409. * EventDispatcher.initialize(MyClass.prototype); // add to the prototype of the class
  410. * EventDispatcher.initialize(myObject); // add to a specific instance
  411. *
  412. * @method initialize
  413. * @static
  414. * @param {Object} target The target object to inject EventDispatcher methods into. This can be an instance or a
  415. * prototype.
  416. **/
  417. EventDispatcher.initialize = function(target) {
  418. target.addEventListener = p.addEventListener;
  419. target.on = p.on;
  420. target.removeEventListener = target.off = p.removeEventListener;
  421. target.removeAllEventListeners = p.removeAllEventListeners;
  422. target.hasEventListener = p.hasEventListener;
  423. target.dispatchEvent = p.dispatchEvent;
  424. target._dispatchEvent = p._dispatchEvent;
  425. target.willTrigger = p.willTrigger;
  426. };
  427. // public methods:
  428. /**
  429. * Adds the specified event listener. Note that adding multiple listeners to the same function will result in
  430. * multiple callbacks getting fired.
  431. *
  432. * <h4>Example</h4>
  433. *
  434. * displayObject.addEventListener("click", handleClick);
  435. * function handleClick(event) {
  436. * // Click happened.
  437. * }
  438. *
  439. * @method addEventListener
  440. * @param {String} type The string type of the event.
  441. * @param {Function | Object} listener An object with a handleEvent method, or a function that will be called when
  442. * the event is dispatched.
  443. * @param {Boolean} [useCapture] For events that bubble, indicates whether to listen for the event in the capture or bubbling/target phase.
  444. * @return {Function | Object} Returns the listener for chaining or assignment.
  445. **/
  446. p.addEventListener = function(type, listener, useCapture) {
  447. var listeners;
  448. if (useCapture) {
  449. listeners = this._captureListeners = this._captureListeners||{};
  450. } else {
  451. listeners = this._listeners = this._listeners||{};
  452. }
  453. var arr = listeners[type];
  454. if (arr) { this.removeEventListener(type, listener, useCapture); }
  455. arr = listeners[type]; // remove may have deleted the array
  456. if (!arr) { listeners[type] = [listener]; }
  457. else { arr.push(listener); }
  458. return listener;
  459. };
  460. /**
  461. * A shortcut method for using addEventListener that makes it easier to specify an execution scope, have a listener
  462. * only run once, associate arbitrary data with the listener, and remove the listener.
  463. *
  464. * This method works by creating an anonymous wrapper function and subscribing it with addEventListener.
  465. * The wrapper function is returned for use with `removeEventListener` (or `off`).
  466. *
  467. * <b>IMPORTANT:</b> To remove a listener added with `on`, you must pass in the returned wrapper function as the listener, or use
  468. * {{#crossLink "Event/remove"}}{{/crossLink}}. Likewise, each time you call `on` a NEW wrapper function is subscribed, so multiple calls
  469. * to `on` with the same params will create multiple listeners.
  470. *
  471. * <h4>Example</h4>
  472. *
  473. * var listener = myBtn.on("click", handleClick, null, false, {count:3});
  474. * function handleClick(evt, data) {
  475. * data.count -= 1;
  476. * console.log(this == myBtn); // true - scope defaults to the dispatcher
  477. * if (data.count == 0) {
  478. * alert("clicked 3 times!");
  479. * myBtn.off("click", listener);
  480. * // alternately: evt.remove();
  481. * }
  482. * }
  483. *
  484. * @method on
  485. * @param {String} type The string type of the event.
  486. * @param {Function | Object} listener An object with a handleEvent method, or a function that will be called when
  487. * the event is dispatched.
  488. * @param {Object} [scope] The scope to execute the listener in. Defaults to the dispatcher/currentTarget for function listeners, and to the listener itself for object listeners (ie. using handleEvent).
  489. * @param {Boolean} [once=false] If true, the listener will remove itself after the first time it is triggered.
  490. * @param {*} [data] Arbitrary data that will be included as the second parameter when the listener is called.
  491. * @param {Boolean} [useCapture=false] For events that bubble, indicates whether to listen for the event in the capture or bubbling/target phase.
  492. * @return {Function} Returns the anonymous function that was created and assigned as the listener. This is needed to remove the listener later using .removeEventListener.
  493. **/
  494. p.on = function(type, listener, scope, once, data, useCapture) {
  495. if (listener.handleEvent) {
  496. scope = scope||listener;
  497. listener = listener.handleEvent;
  498. }
  499. scope = scope||this;
  500. return this.addEventListener(type, function(evt) {
  501. listener.call(scope, evt, data);
  502. once&&evt.remove();
  503. }, useCapture);
  504. };
  505. /**
  506. * Removes the specified event listener.
  507. *
  508. * <b>Important Note:</b> that you must pass the exact function reference used when the event was added. If a proxy
  509. * function, or function closure is used as the callback, the proxy/closure reference must be used - a new proxy or
  510. * closure will not work.
  511. *
  512. * <h4>Example</h4>
  513. *
  514. * displayObject.removeEventListener("click", handleClick);
  515. *
  516. * @method removeEventListener
  517. * @param {String} type The string type of the event.
  518. * @param {Function | Object} listener The listener function or object.
  519. * @param {Boolean} [useCapture] For events that bubble, indicates whether to listen for the event in the capture or bubbling/target phase.
  520. **/
  521. p.removeEventListener = function(type, listener, useCapture) {
  522. var listeners = useCapture ? this._captureListeners : this._listeners;
  523. if (!listeners) { return; }
  524. var arr = listeners[type];
  525. if (!arr) { return; }
  526. for (var i=0,l=arr.length; i<l; i++) {
  527. if (arr[i] == listener) {
  528. if (l==1) { delete(listeners[type]); } // allows for faster checks.
  529. else { arr.splice(i,1); }
  530. break;
  531. }
  532. }
  533. };
  534. /**
  535. * A shortcut to the removeEventListener method, with the same parameters and return value. This is a companion to the
  536. * .on method.
  537. *
  538. * <b>IMPORTANT:</b> To remove a listener added with `on`, you must pass in the returned wrapper function as the listener. See
  539. * {{#crossLink "EventDispatcher/on"}}{{/crossLink}} for an example.
  540. *
  541. * @method off
  542. * @param {String} type The string type of the event.
  543. * @param {Function | Object} listener The listener function or object.
  544. * @param {Boolean} [useCapture] For events that bubble, indicates whether to listen for the event in the capture or bubbling/target phase.
  545. **/
  546. p.off = p.removeEventListener;
  547. /**
  548. * Removes all listeners for the specified type, or all listeners of all types.
  549. *
  550. * <h4>Example</h4>
  551. *
  552. * // Remove all listeners
  553. * displayObject.removeAllEventListeners();
  554. *
  555. * // Remove all click listeners
  556. * displayObject.removeAllEventListeners("click");
  557. *
  558. * @method removeAllEventListeners
  559. * @param {String} [type] The string type of the event. If omitted, all listeners for all types will be removed.
  560. **/
  561. p.removeAllEventListeners = function(type) {
  562. if (!type) { this._listeners = this._captureListeners = null; }
  563. else {
  564. if (this._listeners) { delete(this._listeners[type]); }
  565. if (this._captureListeners) { delete(this._captureListeners[type]); }
  566. }
  567. };
  568. /**
  569. * Dispatches the specified event to all listeners.
  570. *
  571. * <h4>Example</h4>
  572. *
  573. * // Use a string event
  574. * this.dispatchEvent("complete");
  575. *
  576. * // Use an Event instance
  577. * var event = new createjs.Event("progress");
  578. * this.dispatchEvent(event);
  579. *
  580. * @method dispatchEvent
  581. * @param {Object | String | Event} eventObj An object with a "type" property, or a string type.
  582. * While a generic object will work, it is recommended to use a CreateJS Event instance. If a string is used,
  583. * dispatchEvent will construct an Event instance if necessary with the specified type. This latter approach can
  584. * be used to avoid event object instantiation for non-bubbling events that may not have any listeners.
  585. * @param {Boolean} [bubbles] Specifies the `bubbles` value when a string was passed to eventObj.
  586. * @param {Boolean} [cancelable] Specifies the `cancelable` value when a string was passed to eventObj.
  587. * @return {Boolean} Returns false if `preventDefault()` was called on a cancelable event, true otherwise.
  588. **/
  589. p.dispatchEvent = function(eventObj, bubbles, cancelable) {
  590. if (typeof eventObj == "string") {
  591. // skip everything if there's no listeners and it doesn't bubble:
  592. var listeners = this._listeners;
  593. if (!bubbles && (!listeners || !listeners[eventObj])) { return true; }
  594. eventObj = new createjs.Event(eventObj, bubbles, cancelable);
  595. } else if (eventObj.target && eventObj.clone) {
  596. // redispatching an active event object, so clone it:
  597. eventObj = eventObj.clone();
  598. }
  599. // TODO: it would be nice to eliminate this. Maybe in favour of evtObj instanceof Event? Or !!evtObj.createEvent
  600. try { eventObj.target = this; } catch (e) {} // try/catch allows redispatching of native events
  601. if (!eventObj.bubbles || !this.parent) {
  602. this._dispatchEvent(eventObj, 2);
  603. } else {
  604. var top=this, list=[top];
  605. while (top.parent) { list.push(top = top.parent); }
  606. var i, l=list.length;
  607. // capture & atTarget
  608. for (i=l-1; i>=0 && !eventObj.propagationStopped; i--) {
  609. list[i]._dispatchEvent(eventObj, 1+(i==0));
  610. }
  611. // bubbling
  612. for (i=1; i<l && !eventObj.propagationStopped; i++) {
  613. list[i]._dispatchEvent(eventObj, 3);
  614. }
  615. }
  616. return !eventObj.defaultPrevented;
  617. };
  618. /**
  619. * Indicates whether there is at least one listener for the specified event type.
  620. * @method hasEventListener
  621. * @param {String} type The string type of the event.
  622. * @return {Boolean} Returns true if there is at least one listener for the specified event.
  623. **/
  624. p.hasEventListener = function(type) {
  625. var listeners = this._listeners, captureListeners = this._captureListeners;
  626. return !!((listeners && listeners[type]) || (captureListeners && captureListeners[type]));
  627. };
  628. /**
  629. * Indicates whether there is at least one listener for the specified event type on this object or any of its
  630. * ancestors (parent, parent's parent, etc). A return value of true indicates that if a bubbling event of the
  631. * specified type is dispatched from this object, it will trigger at least one listener.
  632. *
  633. * This is similar to {{#crossLink "EventDispatcher/hasEventListener"}}{{/crossLink}}, but it searches the entire
  634. * event flow for a listener, not just this object.
  635. * @method willTrigger
  636. * @param {String} type The string type of the event.
  637. * @return {Boolean} Returns `true` if there is at least one listener for the specified event.
  638. **/
  639. p.willTrigger = function(type) {
  640. var o = this;
  641. while (o) {
  642. if (o.hasEventListener(type)) { return true; }
  643. o = o.parent;
  644. }
  645. return false;
  646. };
  647. /**
  648. * @method toString
  649. * @return {String} a string representation of the instance.
  650. **/
  651. p.toString = function() {
  652. return "[EventDispatcher]";
  653. };
  654. // private methods:
  655. /**
  656. * @method _dispatchEvent
  657. * @param {Object | String | Event} eventObj
  658. * @param {Object} eventPhase
  659. * @protected
  660. **/
  661. p._dispatchEvent = function(eventObj, eventPhase) {
  662. var l, listeners = (eventPhase==1) ? this._captureListeners : this._listeners;
  663. if (eventObj && listeners) {
  664. var arr = listeners[eventObj.type];
  665. if (!arr||!(l=arr.length)) { return; }
  666. try { eventObj.currentTarget = this; } catch (e) {}
  667. try { eventObj.eventPhase = eventPhase; } catch (e) {}
  668. eventObj.removed = false;
  669. arr = arr.slice(); // to avoid issues with items being removed or added during the dispatch
  670. for (var i=0; i<l && !eventObj.immediatePropagationStopped; i++) {
  671. var o = arr[i];
  672. if (o.handleEvent) { o.handleEvent(eventObj); }
  673. else { o(eventObj); }
  674. if (eventObj.removed) {
  675. this.off(eventObj.type, o, eventPhase==1);
  676. eventObj.removed = false;
  677. }
  678. }
  679. }
  680. };
  681. createjs.EventDispatcher = EventDispatcher;
  682. }());
  683. //##############################################################################
  684. // Ticker.js
  685. //##############################################################################
  686. this.createjs = this.createjs||{};
  687. (function() {
  688. "use strict";
  689. // constructor:
  690. /**
  691. * The Ticker provides a centralized tick or heartbeat broadcast at a set interval. Listeners can subscribe to the tick
  692. * event to be notified when a set time interval has elapsed.
  693. *
  694. * Note that the interval that the tick event is called is a target interval, and may be broadcast at a slower interval
  695. * when under high CPU load. The Ticker class uses a static interface (ex. `Ticker.framerate = 30;`) and
  696. * can not be instantiated.
  697. *
  698. * <h4>Example</h4>
  699. *
  700. * createjs.Ticker.addEventListener("tick", handleTick);
  701. * function handleTick(event) {
  702. * // Actions carried out each tick (aka frame)
  703. * if (!event.paused) {
  704. * // Actions carried out when the Ticker is not paused.
  705. * }
  706. * }
  707. *
  708. * @class Ticker
  709. * @uses EventDispatcher
  710. * @static
  711. **/
  712. function Ticker() {
  713. throw "Ticker cannot be instantiated.";
  714. }
  715. // constants:
  716. /**
  717. * In this mode, Ticker uses the requestAnimationFrame API, but attempts to synch the ticks to target framerate. It
  718. * uses a simple heuristic that compares the time of the RAF return to the target time for the current frame and
  719. * dispatches the tick when the time is within a certain threshold.
  720. *
  721. * This mode has a higher variance for time between frames than {{#crossLink "Ticker/TIMEOUT:property"}}{{/crossLink}},
  722. * but does not require that content be time based as with {{#crossLink "Ticker/RAF:property"}}{{/crossLink}} while
  723. * gaining the benefits of that API (screen synch, background throttling).
  724. *
  725. * Variance is usually lowest for framerates that are a divisor of the RAF frequency. This is usually 60, so
  726. * framerates of 10, 12, 15, 20, and 30 work well.
  727. *
  728. * Falls back to {{#crossLink "Ticker/TIMEOUT:property"}}{{/crossLink}} if the requestAnimationFrame API is not
  729. * supported.
  730. * @property RAF_SYNCHED
  731. * @static
  732. * @type {String}
  733. * @default "synched"
  734. * @readonly
  735. **/
  736. Ticker.RAF_SYNCHED = "synched";
  737. /**
  738. * In this mode, Ticker passes through the requestAnimationFrame heartbeat, ignoring the target framerate completely.
  739. * Because requestAnimationFrame frequency is not deterministic, any content using this mode should be time based.
  740. * You can leverage {{#crossLink "Ticker/getTime"}}{{/crossLink}} and the {{#crossLink "Ticker/tick:event"}}{{/crossLink}}
  741. * event object's "delta" properties to make this easier.
  742. *
  743. * Falls back on {{#crossLink "Ticker/TIMEOUT:property"}}{{/crossLink}} if the requestAnimationFrame API is not
  744. * supported.
  745. * @property RAF
  746. * @static
  747. * @type {String}
  748. * @default "raf"
  749. * @readonly
  750. **/
  751. Ticker.RAF = "raf";
  752. /**
  753. * In this mode, Ticker uses the setTimeout API. This provides predictable, adaptive frame timing, but does not
  754. * provide the benefits of requestAnimationFrame (screen synch, background throttling).
  755. * @property TIMEOUT
  756. * @static
  757. * @type {String}
  758. * @default "timeout"
  759. * @readonly
  760. **/
  761. Ticker.TIMEOUT = "timeout";
  762. // static events:
  763. /**
  764. * Dispatched each tick. The event will be dispatched to each listener even when the Ticker has been paused using
  765. * {{#crossLink "Ticker/setPaused"}}{{/crossLink}}.
  766. *
  767. * <h4>Example</h4>
  768. *
  769. * createjs.Ticker.addEventListener("tick", handleTick);
  770. * function handleTick(event) {
  771. * console.log("Paused:", event.paused, event.delta);
  772. * }
  773. *
  774. * @event tick
  775. * @param {Object} target The object that dispatched the event.
  776. * @param {String} type The event type.
  777. * @param {Boolean} paused Indicates whether the ticker is currently paused.
  778. * @param {Number} delta The time elapsed in ms since the last tick.
  779. * @param {Number} time The total time in ms since Ticker was initialized.
  780. * @param {Number} runTime The total time in ms that Ticker was not paused since it was initialized. For example,
  781. * you could determine the amount of time that the Ticker has been paused since initialization with `time-runTime`.
  782. * @since 0.6.0
  783. */
  784. // public static properties:
  785. /**
  786. * Deprecated in favour of {{#crossLink "Ticker/timingMode"}}{{/crossLink}}, and will be removed in a future version. If true, timingMode will
  787. * use {{#crossLink "Ticker/RAF_SYNCHED"}}{{/crossLink}} by default.
  788. * @deprecated Deprecated in favour of {{#crossLink "Ticker/timingMode"}}{{/crossLink}}.
  789. * @property useRAF
  790. * @static
  791. * @type {Boolean}
  792. * @default false
  793. **/
  794. Ticker.useRAF = false;
  795. /**
  796. * Specifies the timing api (setTimeout or requestAnimationFrame) and mode to use. See
  797. * {{#crossLink "Ticker/TIMEOUT"}}{{/crossLink}}, {{#crossLink "Ticker/RAF"}}{{/crossLink}}, and
  798. * {{#crossLink "Ticker/RAF_SYNCHED"}}{{/crossLink}} for mode details.
  799. * @property timingMode
  800. * @static
  801. * @type {String}
  802. * @default Ticker.TIMEOUT
  803. **/
  804. Ticker.timingMode = null;
  805. /**
  806. * Specifies a maximum value for the delta property in the tick event object. This is useful when building time
  807. * based animations and systems to prevent issues caused by large time gaps caused by background tabs, system sleep,
  808. * alert dialogs, or other blocking routines. Double the expected frame duration is often an effective value
  809. * (ex. maxDelta=50 when running at 40fps).
  810. *
  811. * This does not impact any other values (ex. time, runTime, etc), so you may experience issues if you enable maxDelta
  812. * when using both delta and other values.
  813. *
  814. * If 0, there is no maximum.
  815. * @property maxDelta
  816. * @static
  817. * @type {number}
  818. * @default 0
  819. */
  820. Ticker.maxDelta = 0;
  821. /**
  822. * When the ticker is paused, all listeners will still receive a tick event, but the <code>paused</code> property
  823. * of the event will be `true`. Also, while paused the `runTime` will not increase. See {{#crossLink "Ticker/tick:event"}}{{/crossLink}},
  824. * {{#crossLink "Ticker/getTime"}}{{/crossLink}}, and {{#crossLink "Ticker/getEventTime"}}{{/crossLink}} for more
  825. * info.
  826. *
  827. * <h4>Example</h4>
  828. *
  829. * createjs.Ticker.addEventListener("tick", handleTick);
  830. * createjs.Ticker.paused = true;
  831. * function handleTick(event) {
  832. * console.log(event.paused,
  833. * createjs.Ticker.getTime(false),
  834. * createjs.Ticker.getTime(true));
  835. * }
  836. *
  837. * @property paused
  838. * @static
  839. * @type {Boolean}
  840. * @default false
  841. **/
  842. Ticker.paused = false;
  843. // mix-ins:
  844. // EventDispatcher methods:
  845. Ticker.removeEventListener = null;
  846. Ticker.removeAllEventListeners = null;
  847. Ticker.dispatchEvent = null;
  848. Ticker.hasEventListener = null;
  849. Ticker._listeners = null;
  850. createjs.EventDispatcher.initialize(Ticker); // inject EventDispatcher methods.
  851. Ticker._addEventListener = Ticker.addEventListener;
  852. Ticker.addEventListener = function() {
  853. !Ticker._inited&&Ticker.init();
  854. return Ticker._addEventListener.apply(Ticker, arguments);
  855. };
  856. // private static properties:
  857. /**
  858. * @property _inited
  859. * @static
  860. * @type {Boolean}
  861. * @protected
  862. **/
  863. Ticker._inited = false;
  864. /**
  865. * @property _startTime
  866. * @static
  867. * @type {Number}
  868. * @protected
  869. **/
  870. Ticker._startTime = 0;
  871. /**
  872. * @property _pausedTime
  873. * @static
  874. * @type {Number}
  875. * @protected
  876. **/
  877. Ticker._pausedTime=0;
  878. /**
  879. * The number of ticks that have passed
  880. * @property _ticks
  881. * @static
  882. * @type {Number}
  883. * @protected
  884. **/
  885. Ticker._ticks = 0;
  886. /**
  887. * The number of ticks that have passed while Ticker has been paused
  888. * @property _pausedTicks
  889. * @static
  890. * @type {Number}
  891. * @protected
  892. **/
  893. Ticker._pausedTicks = 0;
  894. /**
  895. * @property _interval
  896. * @static
  897. * @type {Number}
  898. * @protected
  899. **/
  900. Ticker._interval = 50;
  901. /**
  902. * @property _lastTime
  903. * @static
  904. * @type {Number}
  905. * @protected
  906. **/
  907. Ticker._lastTime = 0;
  908. /**
  909. * @property _times
  910. * @static
  911. * @type {Array}
  912. * @protected
  913. **/
  914. Ticker._times = null;
  915. /**
  916. * @property _tickTimes
  917. * @static
  918. * @type {Array}
  919. * @protected
  920. **/
  921. Ticker._tickTimes = null;
  922. /**
  923. * Stores the timeout or requestAnimationFrame id.
  924. * @property _timerId
  925. * @static
  926. * @type {Number}
  927. * @protected
  928. **/
  929. Ticker._timerId = null;
  930. /**
  931. * True if currently using requestAnimationFrame, false if using setTimeout. This may be different than timingMode
  932. * if that property changed and a tick hasn't fired.
  933. * @property _raf
  934. * @static
  935. * @type {Boolean}
  936. * @protected
  937. **/
  938. Ticker._raf = true;
  939. // static getter / setters:
  940. /**
  941. * Use the {{#crossLink "Ticker/interval:property"}}{{/crossLink}} property instead.
  942. * @method setInterval
  943. * @static
  944. * @param {Number} interval
  945. * @deprecated
  946. **/
  947. Ticker.setInterval = function(interval) {
  948. Ticker._interval = interval;
  949. if (!Ticker._inited) { return; }
  950. Ticker._setupTick();
  951. };
  952. /**
  953. * Use the {{#crossLink "Ticker/interval:property"}}{{/crossLink}} property instead.
  954. * @method getInterval
  955. * @static
  956. * @return {Number}
  957. * @deprecated
  958. **/
  959. Ticker.getInterval = function() {
  960. return Ticker._interval;
  961. };
  962. /**
  963. * Use the {{#crossLink "Ticker/framerate:property"}}{{/crossLink}} property instead.
  964. * @method setFPS
  965. * @static
  966. * @param {Number} value
  967. * @deprecated
  968. **/
  969. Ticker.setFPS = function(value) {
  970. Ticker.setInterval(1000/value);
  971. };
  972. /**
  973. * Use the {{#crossLink "Ticker/framerate:property"}}{{/crossLink}} property instead.
  974. * @method getFPS
  975. * @static
  976. * @return {Number}
  977. * @deprecated
  978. **/
  979. Ticker.getFPS = function() {
  980. return 1000/Ticker._interval;
  981. };
  982. /**
  983. * Indicates the target time (in milliseconds) between ticks. Default is 50 (20 FPS).
  984. * Note that actual time between ticks may be more than specified depending on CPU load.
  985. * This property is ignored if the ticker is using the `RAF` timing mode.
  986. * @property interval
  987. * @static
  988. * @type {Number}
  989. **/
  990. /**
  991. * Indicates the target frame rate in frames per second (FPS). Effectively just a shortcut to `interval`, where
  992. * `framerate == 1000/interval`.
  993. * @property framerate
  994. * @static
  995. * @type {Number}
  996. **/
  997. try {
  998. Object.defineProperties(Ticker, {
  999. interval: { get: Ticker.getInterval, set: Ticker.setInterval },
  1000. framerate: { get: Ticker.getFPS, set: Ticker.setFPS }
  1001. });
  1002. } catch (e) { console.log(e); }
  1003. // public static methods:
  1004. /**
  1005. * Starts the tick. This is called automatically when the first listener is added.
  1006. * @method init
  1007. * @static
  1008. **/
  1009. Ticker.init = function() {
  1010. if (Ticker._inited) { return; }
  1011. Ticker._inited = true;
  1012. Ticker._times = [];
  1013. Ticker._tickTimes = [];
  1014. Ticker._startTime = Ticker._getTime();
  1015. Ticker._times.push(Ticker._lastTime = 0);
  1016. Ticker.interval = Ticker._interval;
  1017. };
  1018. /**
  1019. * Stops the Ticker and removes all listeners. Use init() to restart the Ticker.
  1020. * @method reset
  1021. * @static
  1022. **/
  1023. Ticker.reset = function() {
  1024. if (Ticker._raf) {
  1025. var f = window.cancelAnimationFrame || window.webkitCancelAnimationFrame || window.mozCancelAnimationFrame || window.oCancelAnimationFrame || window.msCancelAnimationFrame;
  1026. f&&f(Ticker._timerId);
  1027. } else {
  1028. clearTimeout(Ticker._timerId);
  1029. }
  1030. Ticker.removeAllEventListeners("tick");
  1031. Ticker._timerId = Ticker._times = Ticker._tickTimes = null;
  1032. Ticker._startTime = Ticker._lastTime = Ticker._ticks = 0;
  1033. Ticker._inited = false;
  1034. };
  1035. /**
  1036. * Returns the average time spent within a tick. This can vary significantly from the value provided by getMeasuredFPS
  1037. * because it only measures the time spent within the tick execution stack.
  1038. *
  1039. * Example 1: With a target FPS of 20, getMeasuredFPS() returns 20fps, which indicates an average of 50ms between
  1040. * the end of one tick and the end of the next. However, getMeasuredTickTime() returns 15ms. This indicates that
  1041. * there may be up to 35ms of "idle" time between the end of one tick and the start of the next.
  1042. *
  1043. * Example 2: With a target FPS of 30, getFPS() returns 10fps, which indicates an average of 100ms between the end of
  1044. * one tick and the end of the next. However, getMeasuredTickTime() returns 20ms. This would indicate that something
  1045. * other than the tick is using ~80ms (another script, DOM rendering, etc).
  1046. * @method getMeasuredTickTime
  1047. * @static
  1048. * @param {Number} [ticks] The number of previous ticks over which to measure the average time spent in a tick.
  1049. * Defaults to the number of ticks per second. To get only the last tick's time, pass in 1.
  1050. * @return {Number} The average time spent in a tick in milliseconds.
  1051. **/
  1052. Ticker.getMeasuredTickTime = function(ticks) {
  1053. var ttl=0, times=Ticker._tickTimes;
  1054. if (!times || times.length < 1) { return -1; }
  1055. // by default, calculate average for the past ~1 second:
  1056. ticks = Math.min(times.length, ticks||(Ticker.getFPS()|0));
  1057. for (var i=0; i<ticks; i++) { ttl += times[i]; }
  1058. return ttl/ticks;
  1059. };
  1060. /**
  1061. * Returns the actual frames / ticks per second.
  1062. * @method getMeasuredFPS
  1063. * @static
  1064. * @param {Number} [ticks] The number of previous ticks over which to measure the actual frames / ticks per second.
  1065. * Defaults to the number of ticks per second.
  1066. * @return {Number} The actual frames / ticks per second. Depending on performance, this may differ
  1067. * from the target frames per second.
  1068. **/
  1069. Ticker.getMeasuredFPS = function(ticks) {
  1070. var times = Ticker._times;
  1071. if (!times || times.length < 2) { return -1; }
  1072. // by default, calculate fps for the past ~1 second:
  1073. ticks = Math.min(times.length-1, ticks||(Ticker.getFPS()|0));
  1074. return 1000/((times[0]-times[ticks])/ticks);
  1075. };
  1076. /**
  1077. * Use the {{#crossLink "Ticker/paused:property"}}{{/crossLink}} property instead.
  1078. * @method setPaused
  1079. * @static
  1080. * @param {Boolean} value
  1081. * @deprecated
  1082. **/
  1083. Ticker.setPaused = function(value) {
  1084. // TODO: deprecated.
  1085. Ticker.paused = value;
  1086. };
  1087. /**
  1088. * Use the {{#crossLink "Ticker/paused:property"}}{{/crossLink}} property instead.
  1089. * @method getPaused
  1090. * @static
  1091. * @return {Boolean}
  1092. * @deprecated
  1093. **/
  1094. Ticker.getPaused = function() {
  1095. // TODO: deprecated.
  1096. return Ticker.paused;
  1097. };
  1098. /**
  1099. * Returns the number of milliseconds that have elapsed since Ticker was initialized via {{#crossLink "Ticker/init"}}.
  1100. * Returns -1 if Ticker has not been initialized. For example, you could use
  1101. * this in a time synchronized animation to determine the exact amount of time that has elapsed.
  1102. * @method getTime
  1103. * @static
  1104. * @param {Boolean} [runTime=false] If true only time elapsed while Ticker was not paused will be returned.
  1105. * If false, the value returned will be total time elapsed since the first tick event listener was added.
  1106. * @return {Number} Number of milliseconds that have elapsed since Ticker was initialized or -1.
  1107. **/
  1108. Ticker.getTime = function(runTime) {
  1109. return Ticker._startTime ? Ticker._getTime() - (runTime ? Ticker._pausedTime : 0) : -1;
  1110. };
  1111. /**
  1112. * Similar to the {{#crossLink "Ticker/getTime"}}{{/crossLink}} method, but returns the time on the most recent {{#crossLink "Ticker/tick:event"}}{{/crossLink}}
  1113. * event object.
  1114. * @method getEventTime
  1115. * @static
  1116. * @param runTime {Boolean} [runTime=false] If true, the runTime property will be returned instead of time.
  1117. * @returns {number} The time or runTime property from the most recent tick event or -1.
  1118. */
  1119. Ticker.getEventTime = function(runTime) {
  1120. return Ticker._startTime ? (Ticker._lastTime || Ticker._startTime) - (runTime ? Ticker._pausedTime : 0) : -1;
  1121. };
  1122. /**
  1123. * Returns the number of ticks that have been broadcast by Ticker.
  1124. * @method getTicks
  1125. * @static
  1126. * @param {Boolean} pauseable Indicates whether to include ticks that would have been broadcast
  1127. * while Ticker was paused. If true only tick events broadcast while Ticker is not paused will be returned.
  1128. * If false, tick events that would have been broadcast while Ticker was paused will be included in the return
  1129. * value. The default value is false.
  1130. * @return {Number} of ticks that have been broadcast.
  1131. **/
  1132. Ticker.getTicks = function(pauseable) {
  1133. return Ticker._ticks - (pauseable ? Ticker._pausedTicks : 0);
  1134. };
  1135. // private static methods:
  1136. /**
  1137. * @method _handleSynch
  1138. * @static
  1139. * @protected
  1140. **/
  1141. Ticker._handleSynch = function() {
  1142. Ticker._timerId = null;
  1143. Ticker._setupTick();
  1144. // run if enough time has elapsed, with a little bit of flexibility to be early:
  1145. if (Ticker._getTime() - Ticker._lastTime >= (Ticker._interval-1)*0.97) {
  1146. Ticker._tick();
  1147. }
  1148. };
  1149. /**
  1150. * @method _handleRAF
  1151. * @static
  1152. * @protected
  1153. **/
  1154. Ticker._handleRAF = function() {
  1155. Ticker._timerId = null;
  1156. Ticker._setupTick();
  1157. Ticker._tick();
  1158. };
  1159. /**
  1160. * @method _handleTimeout
  1161. * @static
  1162. * @protected
  1163. **/
  1164. Ticker._handleTimeout = function() {
  1165. Ticker._timerId = null;
  1166. Ticker._setupTick();
  1167. Ticker._tick();
  1168. };
  1169. /**
  1170. * @method _setupTick
  1171. * @static
  1172. * @protected
  1173. **/
  1174. Ticker._setupTick = function() {
  1175. if (Ticker._timerId != null) { return; } // avoid duplicates
  1176. var mode = Ticker.timingMode||(Ticker.useRAF&&Ticker.RAF_SYNCHED);
  1177. if (mode == Ticker.RAF_SYNCHED || mode == Ticker.RAF) {
  1178. var f = window.requestAnimationFrame || window.webkitRequestAnimationFrame || window.mozRequestAnimationFrame || window.oRequestAnimationFrame || window.msRequestAnimationFrame;
  1179. if (f) {
  1180. Ticker._timerId = f(mode == Ticker.RAF ? Ticker._handleRAF : Ticker._handleSynch);
  1181. Ticker._raf = true;
  1182. return;
  1183. }
  1184. }
  1185. Ticker._raf = false;
  1186. Ticker._timerId = setTimeout(Ticker._handleTimeout, Ticker._interval);
  1187. };
  1188. /**
  1189. * @method _tick
  1190. * @static
  1191. * @protected
  1192. **/
  1193. Ticker._tick = function() {
  1194. var paused = Ticker.paused;
  1195. var time = Ticker._getTime();
  1196. var elapsedTime = time-Ticker._lastTime;
  1197. Ticker._lastTime = time;
  1198. Ticker._ticks++;
  1199. if (paused) {
  1200. Ticker._pausedTicks++;
  1201. Ticker._pausedTime += elapsedTime;
  1202. }
  1203. if (Ticker.hasEventListener("tick")) {
  1204. var event = new createjs.Event("tick");
  1205. var maxDelta = Ticker.maxDelta;
  1206. event.delta = (maxDelta && elapsedTime > maxDelta) ? maxDelta : elapsedTime;
  1207. event.paused = paused;
  1208. event.time = time;
  1209. event.runTime = time-Ticker._pausedTime;
  1210. Ticker.dispatchEvent(event);
  1211. }
  1212. Ticker._tickTimes.unshift(Ticker._getTime()-time);
  1213. while (Ticker._tickTimes.length > 100) { Ticker._tickTimes.pop(); }
  1214. Ticker._times.unshift(time);
  1215. while (Ticker._times.length > 100) { Ticker._times.pop(); }
  1216. };
  1217. /**
  1218. * @method _getTime
  1219. * @static
  1220. * @protected
  1221. **/
  1222. var now = window.performance && (performance.now || performance.mozNow || performance.msNow || performance.oNow || performance.webkitNow);
  1223. Ticker._getTime = function() {
  1224. return ((now&&now.call(performance))||(new Date().getTime())) - Ticker._startTime;
  1225. };
  1226. createjs.Ticker = Ticker;
  1227. }());
  1228. //##############################################################################
  1229. // Tween.js
  1230. //##############################################################################
  1231. // TODO: possibly add a END actionsMode (only runs actions that == position)?
  1232. // TODO: evaluate a way to decouple paused from tick registration.
  1233. this.createjs = this.createjs||{};
  1234. (function() {
  1235. "use strict";
  1236. // constructor
  1237. /**
  1238. * A Tween instance tweens properties for a single target. Instance methods can be chained for easy construction and sequencing:
  1239. *
  1240. * <h4>Example</h4>
  1241. *
  1242. * target.alpha = 1;
  1243. * createjs.Tween.get(target)
  1244. * .wait(500)
  1245. * .to({alpha:0, visible:false}, 1000)
  1246. * .call(handleComplete);
  1247. * function handleComplete() {
  1248. * //Tween complete
  1249. * }
  1250. *
  1251. * Multiple tweens can point to the same instance, however if they affect the same properties there could be unexpected
  1252. * behaviour. To stop all tweens on an object, use {{#crossLink "Tween/removeTweens"}}{{/crossLink}} or pass `override:true`
  1253. * in the props argument.
  1254. *
  1255. * createjs.Tween.get(target, {override:true}).to({x:100});
  1256. *
  1257. * Subscribe to the {{#crossLink "Tween/change:event"}}{{/crossLink}} event to get notified when a property of the
  1258. * target is changed.
  1259. *
  1260. * createjs.Tween.get(target, {override:true}).to({x:100}).addEventListener("change", handleChange);
  1261. * function handleChange(event) {
  1262. * // The tween changed.
  1263. * }
  1264. *
  1265. * See the Tween {{#crossLink "Tween/get"}}{{/crossLink}} method for additional param documentation.
  1266. * @class Tween
  1267. * @param {Object} target The target object that will have its properties tweened.
  1268. * @param {Object} [props] The configuration properties to apply to this tween instance (ex. `{loop:true, paused:true}`.
  1269. * All properties default to false. Supported props are:<UL>
  1270. * <LI> loop: sets the loop property on this tween.</LI>
  1271. * <LI> useTicks: uses ticks for all durations instead of milliseconds.</LI>
  1272. * <LI> ignoreGlobalPause: sets the {{#crossLink "Tween/ignoreGlobalPause:property"}}{{/crossLink}} property on this tween.</LI>
  1273. * <LI> override: if true, `Tween.removeTweens(target)` will be called to remove any other tweens with the same target.
  1274. * <LI> paused: indicates whether to start the tween paused.</LI>
  1275. * <LI> position: indicates the initial position for this tween.</LI>
  1276. * <LI> onChange: specifies a listener for the "change" event.</LI>
  1277. * </UL>
  1278. * @param {Object} [pluginData] An object containing data for use by installed plugins. See individual
  1279. * plugins' documentation for details.
  1280. * @extends EventDispatcher
  1281. * @constructor
  1282. */
  1283. function Tween(target, props, pluginData) {
  1284. // public properties:
  1285. /**
  1286. * Causes this tween to continue playing when a global pause is active. For example, if TweenJS is using {{#crossLink "Ticker"}}{{/crossLink}},
  1287. * then setting this to true (the default) will cause this tween to be paused when <code>Ticker.setPaused(true)</code>
  1288. * is called. See the Tween {{#crossLink "Tween/tick"}}{{/crossLink}} method for more info. Can be set via the props
  1289. * parameter.
  1290. * @property ignoreGlobalPause
  1291. * @type Boolean
  1292. * @default false
  1293. */
  1294. this.ignoreGlobalPause = false;
  1295. /**
  1296. * If true, the tween will loop when it reaches the end. Can be set via the props param.
  1297. * @property loop
  1298. * @type {Boolean}
  1299. * @default false
  1300. */
  1301. this.loop = false;
  1302. /**
  1303. * Specifies the total duration of this tween in milliseconds (or ticks if useTicks is true).
  1304. * This value is automatically updated as you modify the tween. Changing it directly could result in unexpected
  1305. * behaviour.
  1306. * @property duration
  1307. * @type {Number}
  1308. * @default 0
  1309. * @readonly
  1310. */
  1311. this.duration = 0;
  1312. /**
  1313. * Allows you to specify data that will be used by installed plugins. Each plugin uses this differently, but in general
  1314. * you specify data by setting it to a property of pluginData with the same name as the plugin class.
  1315. * @example
  1316. * myTween.pluginData.PluginClassName = data;
  1317. * <br/>
  1318. * Also, most plugins support a property to enable or disable them. This is typically the plugin class name followed by "_enabled".<br/>
  1319. * @example
  1320. * myTween.pluginData.PluginClassName_enabled = false;<br/>
  1321. * <br/>
  1322. * Some plugins also store instance data in this object, usually in a property named _PluginClassName.
  1323. * See the documentation for individual plugins for more details.
  1324. * @property pluginData
  1325. * @type {Object}
  1326. */
  1327. this.pluginData = pluginData || {};
  1328. /**
  1329. * The target of this tween. This is the object on which the tweened properties will be changed. Changing
  1330. * this property after the tween is created will not have any effect.
  1331. * @property target
  1332. * @type {Object}
  1333. * @readonly
  1334. */
  1335. this.target = target;
  1336. /**
  1337. * The current normalized position of the tween. This will always be a value between 0 and duration.
  1338. * Changing this property directly will have no effect.
  1339. * @property position
  1340. * @type {Object}
  1341. * @readonly
  1342. */
  1343. this.position = null;
  1344. /**
  1345. * Indicates the tween's current position is within a passive wait.
  1346. * @property passive
  1347. * @type {Boolean}
  1348. * @default false
  1349. * @readonly
  1350. **/
  1351. this.passive = false;
  1352. // private properties:
  1353. /**
  1354. * @property _paused
  1355. * @type {Boolean}
  1356. * @default false
  1357. * @protected
  1358. */
  1359. this._paused = false;
  1360. /**
  1361. * @property _curQueueProps
  1362. * @type {Object}
  1363. * @protected
  1364. */
  1365. this._curQueueProps = {};
  1366. /**
  1367. * @property _initQueueProps
  1368. * @type {Object}
  1369. * @protected
  1370. */
  1371. this._initQueueProps = {};
  1372. /**
  1373. * @property _steps
  1374. * @type {Array}
  1375. * @protected
  1376. */
  1377. this._steps = [];
  1378. /**
  1379. * @property _actions
  1380. * @type {Array}
  1381. * @protected
  1382. */
  1383. this._actions = [];
  1384. /**
  1385. * Raw position.
  1386. * @property _prevPosition
  1387. * @type {Number}
  1388. * @default 0
  1389. * @protected
  1390. */
  1391. this._prevPosition = 0;
  1392. /**
  1393. * The position within the current step.
  1394. * @property _stepPosition
  1395. * @type {Number}
  1396. * @default 0
  1397. * @protected
  1398. */
  1399. this._stepPosition = 0; // this is needed by MovieClip.
  1400. /**
  1401. * Normalized position.
  1402. * @property _prevPos
  1403. * @type {Number}
  1404. * @default -1
  1405. * @protected
  1406. */
  1407. this._prevPos = -1;
  1408. /**
  1409. * @property _target
  1410. * @type {Object}
  1411. * @protected
  1412. */
  1413. this._target = target;
  1414. /**
  1415. * @property _useTicks
  1416. * @type {Boolean}
  1417. * @default false
  1418. * @protected
  1419. */
  1420. this._useTicks = false;
  1421. /**
  1422. * @property _inited
  1423. * @type {boolean}
  1424. * @default false
  1425. * @protected
  1426. */
  1427. this._inited = false;
  1428. /**
  1429. * Indicates whether the tween is currently registered with Tween.
  1430. * @property _registered
  1431. * @type {boolean}
  1432. * @default false
  1433. * @protected
  1434. */
  1435. this._registered = false;
  1436. if (props) {
  1437. this._useTicks = props.useTicks;
  1438. this.ignoreGlobalPause = props.ignoreGlobalPause;
  1439. this.loop = props.loop;
  1440. props.onChange && this.addEventListener("change", props.onChange);
  1441. if (props.override) { Tween.removeTweens(target); }
  1442. }
  1443. if (props&&props.paused) { this._paused=true; }
  1444. else { createjs.Tween._register(this,true); }
  1445. if (props&&props.position!=null) { this.setPosition(props.position, Tween.NONE); }
  1446. };
  1447. var p = createjs.extend(Tween, createjs.EventDispatcher);
  1448. // TODO: deprecated
  1449. // p.initialize = function() {}; // searchable for devs wondering where it is. REMOVED. See docs for details.
  1450. // static properties
  1451. /**
  1452. * Constant defining the none actionsMode for use with setPosition.
  1453. * @property NONE
  1454. * @type Number
  1455. * @default 0
  1456. * @static
  1457. */
  1458. Tween.NONE = 0;
  1459. /**
  1460. * Constant defining the loop actionsMode for use with setPosition.
  1461. * @property LOOP
  1462. * @type Number
  1463. * @default 1
  1464. * @static
  1465. */
  1466. Tween.LOOP = 1;
  1467. /**
  1468. * Constant defining the reverse actionsMode for use with setPosition.
  1469. * @property REVERSE
  1470. * @type Number
  1471. * @default 2
  1472. * @static
  1473. */
  1474. Tween.REVERSE = 2;
  1475. /**
  1476. * Constant returned by plugins to tell the tween not to use default assignment.
  1477. * @property IGNORE
  1478. * @type Object
  1479. * @static
  1480. */
  1481. Tween.IGNORE = {};
  1482. /**
  1483. * @property _listeners
  1484. * @type Array[Tween]
  1485. * @static
  1486. * @protected
  1487. */
  1488. Tween._tweens = [];
  1489. /**
  1490. * @property _plugins
  1491. * @type Object
  1492. * @static
  1493. * @protected
  1494. */
  1495. Tween._plugins = {};
  1496. // static methods
  1497. /**
  1498. * Returns a new tween instance. This is functionally identical to using "new Tween(...)", but looks cleaner
  1499. * with the chained syntax of TweenJS.
  1500. * <h4>Example</h4>
  1501. *
  1502. * var tween = createjs.Tween.get(target);
  1503. *
  1504. * @method get
  1505. * @param {Object} target The target object that will have its properties tweened.
  1506. * @param {Object} [props] The configuration properties to apply to this tween instance (ex. `{loop:true, paused:true}`).
  1507. * All properties default to `false`. Supported props are:
  1508. * <UL>
  1509. * <LI> loop: sets the loop property on this tween.</LI>
  1510. * <LI> useTicks: uses ticks for all durations instead of milliseconds.</LI>
  1511. * <LI> ignoreGlobalPause: sets the {{#crossLink "Tween/ignoreGlobalPause:property"}}{{/crossLink}} property on
  1512. * this tween.</LI>
  1513. * <LI> override: if true, `createjs.Tween.removeTweens(target)` will be called to remove any other tweens with
  1514. * the same target.
  1515. * <LI> paused: indicates whether to start the tween paused.</LI>
  1516. * <LI> position: indicates the initial position for this tween.</LI>
  1517. * <LI> onChange: specifies a listener for the {{#crossLink "Tween/change:event"}}{{/crossLink}} event.</LI>
  1518. * </UL>
  1519. * @param {Object} [pluginData] An object containing data for use by installed plugins. See individual plugins'
  1520. * documentation for details.
  1521. * @param {Boolean} [override=false] If true, any previous tweens on the same target will be removed. This is the
  1522. * same as calling `Tween.removeTweens(target)`.
  1523. * @return {Tween} A reference to the created tween. Additional chained tweens, method calls, or callbacks can be
  1524. * applied to the returned tween instance.
  1525. * @static
  1526. */
  1527. Tween.get = function(target, props, pluginData, override) {
  1528. if (override) { Tween.removeTweens(target); }
  1529. return new Tween(target, props, pluginData);
  1530. };
  1531. /**
  1532. * Advances all tweens. This typically uses the {{#crossLink "Ticker"}}{{/crossLink}} class, but you can call it
  1533. * manually if you prefer to use your own "heartbeat" implementation.
  1534. * @method tick
  1535. * @param {Number} delta The change in time in milliseconds since the last tick. Required unless all tweens have
  1536. * `useTicks` set to true.
  1537. * @param {Boolean} paused Indicates whether a global pause is in effect. Tweens with {{#crossLink "Tween/ignoreGlobalPause:property"}}{{/crossLink}}
  1538. * will ignore this, but all others will pause if this is `true`.
  1539. * @static
  1540. */
  1541. Tween.tick = function(delta, paused) {
  1542. var tweens = Tween._tweens.slice(); // to avoid race conditions.
  1543. for (var i=tweens.length-1; i>=0; i--) {
  1544. var tween = tweens[i];
  1545. if ((paused && !tween.ignoreGlobalPause) || tween._paused) { continue; }
  1546. tween.tick(tween._useTicks?1:delta);
  1547. }
  1548. };
  1549. /**
  1550. * Handle events that result from Tween being used as an event handler. This is included to allow Tween to handle
  1551. * {{#crossLink "Ticker/tick:event"}}{{/crossLink}} events from the createjs {{#crossLink "Ticker"}}{{/crossLink}}.
  1552. * No other events are handled in Tween.
  1553. * @method handleEvent
  1554. * @param {Object} event An event object passed in by the {{#crossLink "EventDispatcher"}}{{/crossLink}}. Will
  1555. * usually be of type "tick".
  1556. * @private
  1557. * @static
  1558. * @since 0.4.2
  1559. */
  1560. Tween.handleEvent = function(event) {
  1561. if (event.type == "tick") {
  1562. this.tick(event.delta, event.paused);
  1563. }
  1564. };
  1565. /**
  1566. * Removes all existing tweens for a target. This is called automatically by new tweens if the `override`
  1567. * property is `true`.
  1568. * @method removeTweens
  1569. * @param {Object} target The target object to remove existing tweens from.
  1570. * @static
  1571. */
  1572. Tween.removeTweens = function(target) {
  1573. if (!target.tweenjs_count) { return; }
  1574. var tweens = Tween._tweens;
  1575. for (var i=tweens.length-1; i>=0; i--) {
  1576. var tween = tweens[i];
  1577. if (tween._target == target) {
  1578. tween._paused = true;
  1579. tweens.splice(i, 1);
  1580. }
  1581. }
  1582. target.tweenjs_count = 0;
  1583. };
  1584. /**
  1585. * Stop and remove all existing tweens.
  1586. * @method removeAllTweens
  1587. * @static
  1588. * @since 0.4.1
  1589. */
  1590. Tween.removeAllTweens = function() {
  1591. var tweens = Tween._tweens;
  1592. for (var i= 0, l=tweens.length; i<l; i++) {
  1593. var tween = tweens[i];
  1594. tween._paused = true;
  1595. tween.target&&(tween.target.tweenjs_count = 0);
  1596. }
  1597. tweens.length = 0;
  1598. };
  1599. /**
  1600. * Indicates whether there are any active tweens (and how many) on the target object (if specified) or in general.
  1601. * @method hasActiveTweens
  1602. * @param {Object} [target] The target to check for active tweens. If not specified, the return value will indicate
  1603. * if there are any active tweens on any target.
  1604. * @return {Boolean} If there are active tweens.
  1605. * @static
  1606. */
  1607. Tween.hasActiveTweens = function(target) {
  1608. if (target) { return target.tweenjs_count != null && !!target.tweenjs_count; }
  1609. return Tween._tweens && !!Tween._tweens.length;
  1610. };
  1611. /**
  1612. * Installs a plugin, which can modify how certain properties are handled when tweened. See the {{#crossLink "CSSPlugin"}}{{/crossLink}}
  1613. * for an example of how to write TweenJS plugins.
  1614. * @method installPlugin
  1615. * @static
  1616. * @param {Object} plugin The plugin class to install
  1617. * @param {Array} properties An array of properties that the plugin will handle.
  1618. */
  1619. Tween.installPlugin = function(plugin, properties) {
  1620. var priority = plugin.priority;
  1621. if (priority == null) { plugin.priority = priority = 0; }
  1622. for (var i=0,l=properties.length,p=Tween._plugins;i<l;i++) {
  1623. var n = properties[i];
  1624. if (!p[n]) { p[n] = [plugin]; }
  1625. else {
  1626. var arr = p[n];
  1627. for (var j=0,jl=arr.length;j<jl;j++) {
  1628. if (priority < arr[j].priority) { break; }
  1629. }
  1630. p[n].splice(j,0,plugin);
  1631. }
  1632. }
  1633. };
  1634. /**
  1635. * Registers or unregisters a tween with the ticking system.
  1636. * @method _register
  1637. * @param {Tween} tween The tween instance to register or unregister.
  1638. * @param {Boolean} value If `true`, the tween is registered. If `false` the tween is unregistered.
  1639. * @static
  1640. * @protected
  1641. */
  1642. Tween._register = function(tween, value) {
  1643. var target = tween._target;
  1644. var tweens = Tween._tweens;
  1645. if (value && !tween._registered) {
  1646. // TODO: this approach might fail if a dev is using sealed objects in ES5
  1647. if (target) { target.tweenjs_count = target.tweenjs_count ? target.tweenjs_count+1 : 1; }
  1648. tweens.push(tween);
  1649. if (!Tween._inited && createjs.Ticker) { createjs.Ticker.addEventListener("tick", Tween); Tween._inited = true; }
  1650. } else if (!value && tween._registered) {
  1651. if (target) { target.tweenjs_count--; }
  1652. var i = tweens.length;
  1653. while (i--) {
  1654. if (tweens[i] == tween) {
  1655. tweens.splice(i, 1);
  1656. break;
  1657. }
  1658. }
  1659. }
  1660. tween._registered = value;
  1661. };
  1662. // events:
  1663. /**
  1664. * Called whenever the tween's position changes.
  1665. * @event change
  1666. * @since 0.4.0
  1667. **/
  1668. // public methods:
  1669. /**
  1670. * Queues a wait (essentially an empty tween).
  1671. * <h4>Example</h4>
  1672. *
  1673. * //This tween will wait 1s before alpha is faded to 0.
  1674. * createjs.Tween.get(target).wait(1000).to({alpha:0}, 1000);
  1675. *
  1676. * @method wait
  1677. * @param {Number} duration The duration of the wait in milliseconds (or in ticks if `useTicks` is true).
  1678. * @param {Boolean} [passive] Tween properties will not be updated during a passive wait. This
  1679. * is mostly useful for use with {{#crossLink "Timeline"}}{{/crossLink}} instances that contain multiple tweens
  1680. * affecting the same target at different times.
  1681. * @return {Tween} This tween instance (for chaining calls).
  1682. **/
  1683. p.wait = function(duration, passive) {
  1684. if (duration == null || duration <= 0) { return this; }
  1685. var o = this._cloneProps(this._curQueueProps);
  1686. return this._addStep({d:duration, p0:o, e:this._linearEase, p1:o, v:passive});
  1687. };
  1688. /**
  1689. * Queues a tween from the current values to the target properties. Set duration to 0 to jump to these value.
  1690. * Numeric properties will be tweened from their current value in the tween to the target value. Non-numeric
  1691. * properties will be set at the end of the specified duration.
  1692. * <h4>Example</h4>
  1693. *
  1694. * createjs.Tween.get(target).to({alpha:0}, 1000);
  1695. *
  1696. * @method to
  1697. * @param {Object} props An object specifying property target values for this tween (Ex. `{x:300}` would tween the x
  1698. * property of the target to 300).
  1699. * @param {Number} [duration=0] The duration of the wait in milliseconds (or in ticks if `useTicks` is true).
  1700. * @param {Function} [ease="linear"] The easing function to use for this tween. See the {{#crossLink "Ease"}}{{/crossLink}}
  1701. * class for a list of built-in ease functions.
  1702. * @return {Tween} This tween instance (for chaining calls).
  1703. */
  1704. p.to = function(props, duration, ease) {
  1705. if (isNaN(duration) || duration < 0) { duration = 0; }
  1706. return this._addStep({d:duration||0, p0:this._cloneProps(this._curQueueProps), e:ease, p1:this._cloneProps(this._appendQueueProps(props))});
  1707. };
  1708. /**
  1709. * Queues an action to call the specified function.
  1710. * <h4>Example</h4>
  1711. *
  1712. * //would call myFunction() after 1 second.
  1713. * myTween.wait(1000).call(myFunction);
  1714. *
  1715. * @method call
  1716. * @param {Function} callback The function to call.
  1717. * @param {Array} [params]. The parameters to call the function with. If this is omitted, then the function
  1718. * will be called with a single param pointing to this tween.
  1719. * @param {Object} [scope]. The scope to call the function in. If omitted, it will be called in the target's
  1720. * scope.
  1721. * @return {Tween} This tween instance (for chaining calls).
  1722. */
  1723. p.call = function(callback, params, scope) {
  1724. return this._addAction({f:callback, p:params ? params : [this], o:scope ? scope : this._target});
  1725. };
  1726. // TODO: add clarification between this and a 0 duration .to:
  1727. /**
  1728. * Queues an action to set the specified props on the specified target. If target is null, it will use this tween's
  1729. * target.
  1730. * <h4>Example</h4>
  1731. *
  1732. * myTween.wait(1000).set({visible:false},foo);
  1733. *
  1734. * @method set
  1735. * @param {Object} props The properties to set (ex. `{visible:false}`).
  1736. * @param {Object} [target] The target to set the properties on. If omitted, they will be set on the tween's target.
  1737. * @return {Tween} This tween instance (for chaining calls).
  1738. */
  1739. p.set = function(props, target) {
  1740. return this._addAction({f:this._set, o:this, p:[props, target ? target : this._target]});
  1741. };
  1742. /**
  1743. * Queues an action to play (unpause) the specified tween. This enables you to sequence multiple tweens.
  1744. * <h4>Example</h4>
  1745. *
  1746. * myTween.to({x:100},500).play(otherTween);
  1747. *
  1748. * @method play
  1749. * @param {Tween} tween The tween to play.
  1750. * @return {Tween} This tween instance (for chaining calls).
  1751. */
  1752. p.play = function(tween) {
  1753. if (!tween) { tween = this; }
  1754. return this.call(tween.setPaused, [false], tween);
  1755. };
  1756. /**
  1757. * Queues an action to pause the specified tween.
  1758. * @method pause
  1759. * @param {Tween} tween The tween to pause. If null, it pauses this tween.
  1760. * @return {Tween} This tween instance (for chaining calls)
  1761. */
  1762. p.pause = function(tween) {
  1763. if (!tween) { tween = this; }
  1764. return this.call(tween.setPaused, [true], tween);
  1765. };
  1766. /**
  1767. * Advances the tween to a specified position.
  1768. * @method setPosition
  1769. * @param {Number} value The position to seek to in milliseconds (or ticks if useTicks is true).
  1770. * @param {Number} [actionsMode=1] Specifies how actions are handled (ie. call, set, play, pause):
  1771. * <ul>
  1772. * <li>{{#crossLink "Tween/NONE:property"}}{{/crossLink}} (0) - run no actions.</li>
  1773. * <li>{{#crossLink "Tween/LOOP:property"}}{{/crossLink}} (1) - if new position is less than old, then run all
  1774. * actions between old and duration, then all actions between 0 and new.</li>
  1775. * <li>{{#crossLink "Tween/REVERSE:property"}}{{/crossLink}} (2) - if new position is less than old, run all
  1776. * actions between them in reverse.</li>
  1777. * </ul>
  1778. * @return {Boolean} Returns `true` if the tween is complete (ie. the full tween has run & {{#crossLink "Tween/loop:property"}}{{/crossLink}}
  1779. * is `false`).
  1780. */
  1781. p.setPosition = function(value, actionsMode) {
  1782. if (value < 0) { value = 0; }
  1783. if (actionsMode == null) { actionsMode = 1; }
  1784. // normalize position:
  1785. var t = value;
  1786. var end = false;
  1787. if (t >= this.duration) {
  1788. if (this.loop) { t = t%this.duration; }
  1789. else {
  1790. t = this.duration;
  1791. end = true;
  1792. }
  1793. }
  1794. if (t == this._prevPos) { return end; }
  1795. var prevPos = this._prevPos;
  1796. this.position = this._prevPos = t; // set this in advance in case an action modifies position.
  1797. this._prevPosition = value;
  1798. // handle tweens:
  1799. if (this._target) {
  1800. if (end) {
  1801. // addresses problems with an ending zero length step.
  1802. this._updateTargetProps(null,1);
  1803. } else if (this._steps.length > 0) {
  1804. // find our new tween index:
  1805. for (var i=0, l=this._steps.length; i<l; i++) {
  1806. if (this._steps[i].t > t) { break; }
  1807. }
  1808. var step = this._steps[i-1];
  1809. this._updateTargetProps(step,(this._stepPosition = t-step.t)/step.d);
  1810. }
  1811. }
  1812. // run actions:
  1813. if (actionsMode != 0 && this._actions.length > 0) {
  1814. if (this._useTicks) {
  1815. // only run the actions we landed on.
  1816. this._runActions(t,t);
  1817. } else if (actionsMode == 1 && t<prevPos) {
  1818. if (prevPos != this.duration) { this._runActions(prevPos, this.duration); }
  1819. this._runActions(0, t, true);
  1820. } else {
  1821. this._runActions(prevPos, t);
  1822. }
  1823. }
  1824. if (end) { this.setPaused(true); }
  1825. this.dispatchEvent("change");
  1826. return end;
  1827. };
  1828. /**
  1829. * Advances this tween by the specified amount of time in milliseconds (or ticks if`useTicks` is `true`).
  1830. * This is normally called automatically by the Tween engine (via {{#crossLink "Tween/tick"}}{{/crossLink}}), but is
  1831. * exposed for advanced uses.
  1832. * @method tick
  1833. * @param {Number} delta The time to advance in milliseconds (or ticks if `useTicks` is `true`).
  1834. */
  1835. p.tick = function(delta) {
  1836. if (this._paused) { return; }
  1837. this.setPosition(this._prevPosition+delta);
  1838. };
  1839. /**
  1840. * Pauses or plays this tween.
  1841. * @method setPaused
  1842. * @param {Boolean} [value=true] Indicates whether the tween should be paused (`true`) or played (`false`).
  1843. * @return {Tween} This tween instance (for chaining calls)
  1844. */
  1845. p.setPaused = function(value) {
  1846. if (this._paused === !!value) { return this; }
  1847. this._paused = !!value;
  1848. Tween._register(this, !value);
  1849. return this;
  1850. };
  1851. // tiny api (primarily for tool output):
  1852. p.w = p.wait;
  1853. p.t = p.to;
  1854. p.c = p.call;
  1855. p.s = p.set;
  1856. /**
  1857. * Returns a string representation of this object.
  1858. * @method toString
  1859. * @return {String} a string representation of the instance.
  1860. */
  1861. p.toString = function() {
  1862. return "[Tween]";
  1863. };
  1864. /**
  1865. * @method clone
  1866. * @protected
  1867. */
  1868. p.clone = function() {
  1869. throw("Tween can not be cloned.")
  1870. };
  1871. // private methods:
  1872. /**
  1873. * @method _updateTargetProps
  1874. * @param {Object} step
  1875. * @param {Number} ratio
  1876. * @protected
  1877. */
  1878. p._updateTargetProps = function(step, ratio) {
  1879. var p0,p1,v,v0,v1,arr;
  1880. if (!step && ratio == 1) {
  1881. // GDS: when does this run? Just at the very end? Shouldn't.
  1882. this.passive = false;
  1883. p0 = p1 = this._curQueueProps;
  1884. } else {
  1885. this.passive = !!step.v;
  1886. if (this.passive) { return; } // don't update props.
  1887. // apply ease to ratio.
  1888. if (step.e) { ratio = step.e(ratio,0,1,1); }
  1889. p0 = step.p0;
  1890. p1 = step.p1;
  1891. }
  1892. for (var n in this._initQueueProps) {
  1893. if ((v0 = p0[n]) == null) { p0[n] = v0 = this._initQueueProps[n]; }
  1894. if ((v1 = p1[n]) == null) { p1[n] = v1 = v0; }
  1895. if (v0 == v1 || ratio == 0 || ratio == 1 || (typeof(v0) != "number")) {
  1896. // no interpolation - either at start, end, values don't change, or the value is non-numeric.
  1897. v = ratio == 1 ? v1 : v0;
  1898. } else {
  1899. v = v0+(v1-v0)*ratio;
  1900. }
  1901. var ignore = false;
  1902. if (arr = Tween._plugins[n]) {
  1903. for (var i=0,l=arr.length;i<l;i++) {
  1904. var v2 = arr[i].tween(this, n, v, p0, p1, ratio, !!step&&p0==p1, !step);
  1905. if (v2 == Tween.IGNORE) { ignore = true; }
  1906. else { v = v2; }
  1907. }
  1908. }
  1909. if (!ignore) { this._target[n] = v; }
  1910. }
  1911. };
  1912. /**
  1913. * @method _runActions
  1914. * @param {Number} startPos
  1915. * @param {Number} endPos
  1916. * @param {Boolean} includeStart
  1917. * @protected
  1918. */
  1919. p._runActions = function(startPos, endPos, includeStart) {
  1920. var sPos = startPos;
  1921. var ePos = endPos;
  1922. var i = -1;
  1923. var j = this._actions.length;
  1924. var k = 1;
  1925. if (startPos > endPos) {
  1926. // running backwards, flip everything:
  1927. sPos = endPos;
  1928. ePos = startPos;
  1929. i = j;
  1930. j = k = -1;
  1931. }
  1932. while ((i+=k) != j) {
  1933. var action = this._actions[i];
  1934. var pos = action.t;
  1935. if (pos == ePos || (pos > sPos && pos < ePos) || (includeStart && pos == startPos) ) {
  1936. action.f.apply(action.o, action.p);
  1937. }
  1938. }
  1939. };
  1940. /**
  1941. * @method _appendQueueProps
  1942. * @param {Object} o
  1943. * @protected
  1944. */
  1945. p._appendQueueProps = function(o) {
  1946. var arr,oldValue,i, l, injectProps;
  1947. for (var n in o) {
  1948. if (this._initQueueProps[n] === undefined) {
  1949. oldValue = this._target[n];
  1950. // init plugins:
  1951. if (arr = Tween._plugins[n]) {
  1952. for (i=0,l=arr.length;i<l;i++) {
  1953. oldValue = arr[i].init(this, n, oldValue);
  1954. }
  1955. }
  1956. this._initQueueProps[n] = this._curQueueProps[n] = (oldValue===undefined) ? null : oldValue;
  1957. } else {
  1958. oldValue = this._curQueueProps[n];
  1959. }
  1960. }
  1961. for (var n in o) {
  1962. oldValue = this._curQueueProps[n];
  1963. if (arr = Tween._plugins[n]) {
  1964. injectProps = injectProps||{};
  1965. for (i=0, l=arr.length;i<l;i++) {
  1966. // TODO: remove the check for .step in the next version. It's here for backwards compatibility.
  1967. if (arr[i].step) { arr[i].step(this, n, oldValue, o[n], injectProps); }
  1968. }
  1969. }
  1970. this._curQueueProps[n] = o[n];
  1971. }
  1972. if (injectProps) { this._appendQueueProps(injectProps); }
  1973. return this._curQueueProps;
  1974. };
  1975. /**
  1976. * @method _cloneProps
  1977. * @param {Object} props
  1978. * @protected
  1979. */
  1980. p._cloneProps = function(props) {
  1981. var o = {};
  1982. for (var n in props) {
  1983. o[n] = props[n];
  1984. }
  1985. return o;
  1986. };
  1987. /**
  1988. * @method _addStep
  1989. * @param {Object} o
  1990. * @protected
  1991. */
  1992. p._addStep = function(o) {
  1993. if (o.d > 0) {
  1994. this._steps.push(o);
  1995. o.t = this.duration;
  1996. this.duration += o.d;
  1997. }
  1998. return this;
  1999. };
  2000. /**
  2001. * @method _addAction
  2002. * @param {Object} o
  2003. * @protected
  2004. */
  2005. p._addAction = function(o) {
  2006. o.t = this.duration;
  2007. this._actions.push(o);
  2008. return this;
  2009. };
  2010. /**
  2011. * @method _set
  2012. * @param {Object} props
  2013. * @param {Object} o
  2014. * @protected
  2015. */
  2016. p._set = function(props, o) {
  2017. for (var n in props) {
  2018. o[n] = props[n];
  2019. }
  2020. };
  2021. createjs.Tween = createjs.promote(Tween, "EventDispatcher");
  2022. }());
  2023. //##############################################################################
  2024. // Timeline.js
  2025. //##############################################################################
  2026. this.createjs = this.createjs||{};
  2027. (function() {
  2028. "use strict";
  2029. // constructor
  2030. /**
  2031. * The Timeline class synchronizes multiple tweens and allows them to be controlled as a group. Please note that if a
  2032. * timeline is looping, the tweens on it may appear to loop even if the "loop" property of the tween is false.
  2033. * @class Timeline
  2034. * @param {Array} tweens An array of Tweens to add to this timeline. See {{#crossLink "Timeline/addTween"}}{{/crossLink}}
  2035. * for more info.
  2036. * @param {Object} labels An object defining labels for using {{#crossLink "Timeline/gotoAndPlay"}}{{/crossLink}}/{{#crossLink "Timeline/gotoAndStop"}}{{/crossLink}}.
  2037. * See {{#crossLink "Timeline/setLabels"}}{{/crossLink}}
  2038. * for details.
  2039. * @param {Object} props The configuration properties to apply to this tween instance (ex. `{loop:true}`). All properties
  2040. * default to false. Supported props are:<UL>
  2041. * <LI> loop: sets the loop property on this tween.</LI>
  2042. * <LI> useTicks: uses ticks for all durations instead of milliseconds.</LI>
  2043. * <LI> ignoreGlobalPause: sets the ignoreGlobalPause property on this tween.</LI>
  2044. * <LI> paused: indicates whether to start the tween paused.</LI>
  2045. * <LI> position: indicates the initial position for this timeline.</LI>
  2046. * <LI> onChange: specifies a listener to add for the {{#crossLink "Timeline/change:event"}}{{/crossLink}} event.</LI>
  2047. * </UL>
  2048. * @extends EventDispatcher
  2049. * @constructor
  2050. **/
  2051. function Timeline(tweens, labels, props) {
  2052. this.EventDispatcher_constructor();
  2053. // public properties:
  2054. /**
  2055. * Causes this timeline to continue playing when a global pause is active.
  2056. * @property ignoreGlobalPause
  2057. * @type Boolean
  2058. **/
  2059. this.ignoreGlobalPause = false;
  2060. /**
  2061. * The total duration of this timeline in milliseconds (or ticks if `useTicks `is `true`). This value is usually
  2062. * automatically updated as you modify the timeline. See {{#crossLink "Timeline/updateDuration"}}{{/crossLink}}
  2063. * for more information.
  2064. * @property duration
  2065. * @type Number
  2066. * @default 0
  2067. * @readonly
  2068. **/
  2069. this.duration = 0;
  2070. /**
  2071. * If true, the timeline will loop when it reaches the end. Can be set via the props param.
  2072. * @property loop
  2073. * @type Boolean
  2074. **/
  2075. this.loop = false;
  2076. /**
  2077. * The current normalized position of the timeline. This will always be a value between 0 and
  2078. * {{#crossLink "Timeline/duration:property"}}{{/crossLink}}.
  2079. * Changing this property directly will have no effect.
  2080. * @property position
  2081. * @type Object
  2082. * @readonly
  2083. **/
  2084. this.position = null;
  2085. // private properties:
  2086. /**
  2087. * @property _paused
  2088. * @type Boolean
  2089. * @protected
  2090. **/
  2091. this._paused = false;
  2092. /**
  2093. * @property _tweens
  2094. * @type Array[Tween]
  2095. * @protected
  2096. **/
  2097. this._tweens = [];
  2098. /**
  2099. * @property _labels
  2100. * @type Object
  2101. * @protected
  2102. **/
  2103. this._labels = null;
  2104. /**
  2105. * @property _labelList
  2106. * @type Array[Object]
  2107. * @protected
  2108. **/
  2109. this._labelList = null;
  2110. /**
  2111. * @property _prevPosition
  2112. * @type Number
  2113. * @default 0
  2114. * @protected
  2115. **/
  2116. this._prevPosition = 0;
  2117. /**
  2118. * @property _prevPos
  2119. * @type Number
  2120. * @default -1
  2121. * @protected
  2122. **/
  2123. this._prevPos = -1;
  2124. /**
  2125. * @property _useTicks
  2126. * @type Boolean
  2127. * @default false
  2128. * @protected
  2129. **/
  2130. this._useTicks = false;
  2131. /**
  2132. * Indicates whether the timeline is currently registered with Tween.
  2133. * @property _registered
  2134. * @type {boolean}
  2135. * @default false
  2136. * @protected
  2137. */
  2138. this._registered = false;
  2139. if (props) {
  2140. this._useTicks = props.useTicks;
  2141. this.loop = props.loop;
  2142. this.ignoreGlobalPause = props.ignoreGlobalPause;
  2143. props.onChange&&this.addEventListener("change", props.onChange);
  2144. }
  2145. if (tweens) { this.addTween.apply(this, tweens); }
  2146. this.setLabels(labels);
  2147. if (props&&props.paused) { this._paused=true; }
  2148. else { createjs.Tween._register(this,true); }
  2149. if (props&&props.position!=null) { this.setPosition(props.position, createjs.Tween.NONE); }
  2150. };
  2151. var p = createjs.extend(Timeline, createjs.EventDispatcher);
  2152. // TODO: deprecated
  2153. // p.initialize = function() {}; // searchable for devs wondering where it is. REMOVED. See docs for details.
  2154. // events:
  2155. /**
  2156. * Called whenever the timeline's position changes.
  2157. * @event change
  2158. * @since 0.5.0
  2159. **/
  2160. // public methods:
  2161. /**
  2162. * Adds one or more tweens (or timelines) to this timeline. The tweens will be paused (to remove them from the
  2163. * normal ticking system) and managed by this timeline. Adding a tween to multiple timelines will result in
  2164. * unexpected behaviour.
  2165. * @method addTween
  2166. * @param {Tween} ...tween The tween(s) to add. Accepts multiple arguments.
  2167. * @return {Tween} The first tween that was passed in.
  2168. **/
  2169. p.addTween = function(tween) {
  2170. var l = arguments.length;
  2171. if (l > 1) {
  2172. for (var i=0; i<l; i++) { this.addTween(arguments[i]); }
  2173. return arguments[0];
  2174. } else if (l == 0) { return null; }
  2175. this.removeTween(tween);
  2176. this._tweens.push(tween);
  2177. tween.setPaused(true);
  2178. tween._paused = false;
  2179. tween._useTicks = this._useTicks;
  2180. if (tween.duration > this.duration) { this.duration = tween.duration; }
  2181. if (this._prevPos >= 0) { tween.setPosition(this._prevPos, createjs.Tween.NONE); }
  2182. return tween;
  2183. };
  2184. /**
  2185. * Removes one or more tweens from this timeline.
  2186. * @method removeTween
  2187. * @param {Tween} ...tween The tween(s) to remove. Accepts multiple arguments.
  2188. * @return Boolean Returns `true` if all of the tweens were successfully removed.
  2189. **/
  2190. p.removeTween = function(tween) {
  2191. var l = arguments.length;
  2192. if (l > 1) {
  2193. var good = true;
  2194. for (var i=0; i<l; i++) { good = good && this.removeTween(arguments[i]); }
  2195. return good;
  2196. } else if (l == 0) { return false; }
  2197. var tweens = this._tweens;
  2198. var i = tweens.length;
  2199. while (i--) {
  2200. if (tweens[i] == tween) {
  2201. tweens.splice(i, 1);
  2202. if (tween.duration >= this.duration) { this.updateDuration(); }
  2203. return true;
  2204. }
  2205. }
  2206. return false;
  2207. };
  2208. /**
  2209. * Adds a label that can be used with {{#crossLink "Timeline/gotoAndPlay"}}{{/crossLink}}/{{#crossLink "Timeline/gotoAndStop"}}{{/crossLink}}.
  2210. * @method addLabel
  2211. * @param {String} label The label name.
  2212. * @param {Number} position The position this label represents.
  2213. **/
  2214. p.addLabel = function(label, position) {
  2215. this._labels[label] = position;
  2216. var list = this._labelList;
  2217. if (list) {
  2218. for (var i= 0,l=list.length; i<l; i++) { if (position < list[i].position) { break; } }
  2219. list.splice(i, 0, {label:label, position:position});
  2220. }
  2221. };
  2222. /**
  2223. * Defines labels for use with gotoAndPlay/Stop. Overwrites any previously set labels.
  2224. * @method setLabels
  2225. * @param {Object} o An object defining labels for using {{#crossLink "Timeline/gotoAndPlay"}}{{/crossLink}}/{{#crossLink "Timeline/gotoAndStop"}}{{/crossLink}}
  2226. * in the form `{labelName:time}` where time is in milliseconds (or ticks if `useTicks` is `true`).
  2227. **/
  2228. p.setLabels = function(o) {
  2229. this._labels = o ? o : {};
  2230. };
  2231. /**
  2232. * Returns a sorted list of the labels defined on this timeline.
  2233. * @method getLabels
  2234. * @return {Array[Object]} A sorted array of objects with label and position properties.
  2235. **/
  2236. p.getLabels = function() {
  2237. var list = this._labelList;
  2238. if (!list) {
  2239. list = this._labelList = [];
  2240. var labels = this._labels;
  2241. for (var n in labels) {
  2242. list.push({label:n, position:labels[n]});
  2243. }
  2244. list.sort(function (a,b) { return a.position- b.position; });
  2245. }
  2246. return list;
  2247. };
  2248. /**
  2249. * Returns the name of the label on or immediately before the current position. For example, given a timeline with
  2250. * two labels, "first" on frame index 4, and "second" on frame 8, getCurrentLabel would return:
  2251. * <UL>
  2252. * <LI>null if the current position is 2.</LI>
  2253. * <LI>"first" if the current position is 4.</LI>
  2254. * <LI>"first" if the current position is 7.</LI>
  2255. * <LI>"second" if the current position is 15.</LI>
  2256. * </UL>
  2257. * @method getCurrentLabel
  2258. * @return {String} The name of the current label or null if there is no label
  2259. **/
  2260. p.getCurrentLabel = function() {
  2261. var labels = this.getLabels();
  2262. var pos = this.position;
  2263. var l = labels.length;
  2264. if (l) {
  2265. for (var i = 0; i<l; i++) { if (pos < labels[i].position) { break; } }
  2266. return (i==0) ? null : labels[i-1].label;
  2267. }
  2268. return null;
  2269. };
  2270. /**
  2271. * Unpauses this timeline and jumps to the specified position or label.
  2272. * @method gotoAndPlay
  2273. * @param {String|Number} positionOrLabel The position in milliseconds (or ticks if `useTicks` is `true`)
  2274. * or label to jump to.
  2275. **/
  2276. p.gotoAndPlay = function(positionOrLabel) {
  2277. this.setPaused(false);
  2278. this._goto(positionOrLabel);
  2279. };
  2280. /**
  2281. * Pauses this timeline and jumps to the specified position or label.
  2282. * @method gotoAndStop
  2283. * @param {String|Number} positionOrLabel The position in milliseconds (or ticks if `useTicks` is `true`) or label
  2284. * to jump to.
  2285. **/
  2286. p.gotoAndStop = function(positionOrLabel) {
  2287. this.setPaused(true);
  2288. this._goto(positionOrLabel);
  2289. };
  2290. /**
  2291. * Advances the timeline to the specified position.
  2292. * @method setPosition
  2293. * @param {Number} value The position to seek to in milliseconds (or ticks if `useTicks` is `true`).
  2294. * @param {Number} [actionsMode] parameter specifying how actions are handled. See the Tween {{#crossLink "Tween/setPosition"}}{{/crossLink}}
  2295. * method for more details.
  2296. * @return {Boolean} Returns `true` if the timeline is complete (ie. the full timeline has run & {{#crossLink "Timeline/loop:property"}}{{/crossLink}}
  2297. * is `false`).
  2298. **/
  2299. p.setPosition = function(value, actionsMode) {
  2300. var t = this._calcPosition(value);
  2301. var end = !this.loop && value >= this.duration;
  2302. if (t == this._prevPos) { return end; }
  2303. this._prevPosition = value;
  2304. this.position = this._prevPos = t; // in case an action changes the current frame.
  2305. for (var i=0, l=this._tweens.length; i<l; i++) {
  2306. this._tweens[i].setPosition(t, actionsMode);
  2307. if (t != this._prevPos) { return false; } // an action changed this timeline's position.
  2308. }
  2309. if (end) { this.setPaused(true); }
  2310. this.dispatchEvent("change");
  2311. return end;
  2312. };
  2313. /**
  2314. * Pauses or plays this timeline.
  2315. * @method setPaused
  2316. * @param {Boolean} value Indicates whether the tween should be paused (`true`) or played (`false`).
  2317. **/
  2318. p.setPaused = function(value) {
  2319. this._paused = !!value;
  2320. createjs.Tween._register(this, !value);
  2321. };
  2322. /**
  2323. * Recalculates the duration of the timeline. The duration is automatically updated when tweens are added or removed,
  2324. * but this method is useful if you modify a tween after it was added to the timeline.
  2325. * @method updateDuration
  2326. **/
  2327. p.updateDuration = function() {
  2328. this.duration = 0;
  2329. for (var i=0,l=this._tweens.length; i<l; i++) {
  2330. var tween = this._tweens[i];
  2331. if (tween.duration > this.duration) { this.duration = tween.duration; }
  2332. }
  2333. };
  2334. /**
  2335. * Advances this timeline by the specified amount of time in milliseconds (or ticks if `useTicks` is `true`).
  2336. * This is normally called automatically by the Tween engine (via the {{#crossLink "Tween/tick:event"}}{{/crossLink}}
  2337. * event), but is exposed for advanced uses.
  2338. * @method tick
  2339. * @param {Number} delta The time to advance in milliseconds (or ticks if useTicks is true).
  2340. **/
  2341. p.tick = function(delta) {
  2342. this.setPosition(this._prevPosition+delta);
  2343. };
  2344. /**
  2345. * If a numeric position is passed, it is returned unchanged. If a string is passed, the position of the
  2346. * corresponding frame label will be returned, or `null` if a matching label is not defined.
  2347. * @method resolve
  2348. * @param {String|Number} positionOrLabel A numeric position value or label string.
  2349. **/
  2350. p.resolve = function(positionOrLabel) {
  2351. var pos = Number(positionOrLabel);
  2352. if (isNaN(pos)) { pos = this._labels[positionOrLabel]; }
  2353. return pos;
  2354. };
  2355. /**
  2356. * Returns a string representation of this object.
  2357. * @method toString
  2358. * @return {String} a string representation of the instance.
  2359. **/
  2360. p.toString = function() {
  2361. return "[Timeline]";
  2362. };
  2363. /**
  2364. * @method clone
  2365. * @protected
  2366. **/
  2367. p.clone = function() {
  2368. throw("Timeline can not be cloned.")
  2369. };
  2370. // private methods:
  2371. /**
  2372. * @method _goto
  2373. * @param {String | Number} positionOrLabel
  2374. * @protected
  2375. **/
  2376. p._goto = function(positionOrLabel) {
  2377. var pos = this.resolve(positionOrLabel);
  2378. if (pos != null) { this.setPosition(pos); }
  2379. };
  2380. /**
  2381. * @method _calcPosition
  2382. * @param {Number} value
  2383. * @return {Number}
  2384. * @protected
  2385. **/
  2386. p._calcPosition = function(value) {
  2387. if (value < 0) { return 0; }
  2388. if (value < this.duration) { return value; }
  2389. return this.loop ? value%this.duration : this.duration;
  2390. };
  2391. createjs.Timeline = createjs.promote(Timeline, "EventDispatcher");
  2392. }());
  2393. //##############################################################################
  2394. // Ease.js
  2395. //##############################################################################
  2396. this.createjs = this.createjs||{};
  2397. (function() {
  2398. "use strict";
  2399. /**
  2400. * The Ease class provides a collection of easing functions for use with TweenJS. It does not use the standard 4 param
  2401. * easing signature. Instead it uses a single param which indicates the current linear ratio (0 to 1) of the tween.
  2402. *
  2403. * Most methods on Ease can be passed directly as easing functions:
  2404. *
  2405. * Tween.get(target).to({x:100}, 500, Ease.linear);
  2406. *
  2407. * However, methods beginning with "get" will return an easing function based on parameter values:
  2408. *
  2409. * Tween.get(target).to({y:200}, 500, Ease.getPowIn(2.2));
  2410. *
  2411. * Please see the <a href="http://www.createjs.com/Demos/TweenJS/Tween_SparkTable">spark table demo</a> for an
  2412. * overview of the different ease types on <a href="http://tweenjs.com">TweenJS.com</a>.
  2413. *
  2414. * <em>Equations derived from work by Robert Penner.</em>
  2415. * @class Ease
  2416. * @static
  2417. **/
  2418. function Ease() {
  2419. throw "Ease cannot be instantiated.";
  2420. }
  2421. // static methods and properties
  2422. /**
  2423. * @method linear
  2424. * @param {Number} t
  2425. * @static
  2426. * @return {Number}
  2427. **/
  2428. Ease.linear = function(t) { return t; };
  2429. /**
  2430. * Identical to linear.
  2431. * @method none
  2432. * @param {Number} t
  2433. * @static
  2434. * @return {Number}
  2435. **/
  2436. Ease.none = Ease.linear;
  2437. /**
  2438. * Mimics the simple -100 to 100 easing in Flash Pro.
  2439. * @method get
  2440. * @param {Number} amount A value from -1 (ease in) to 1 (ease out) indicating the strength and direction of the ease.
  2441. * @static
  2442. * @return {Function}
  2443. **/
  2444. Ease.get = function(amount) {
  2445. if (amount < -1) { amount = -1; }
  2446. if (amount > 1) { amount = 1; }
  2447. return function(t) {
  2448. if (amount==0) { return t; }
  2449. if (amount<0) { return t*(t*-amount+1+amount); }
  2450. return t*((2-t)*amount+(1-amount));
  2451. };
  2452. };
  2453. /**
  2454. * Configurable exponential ease.
  2455. * @method getPowIn
  2456. * @param {Number} pow The exponent to use (ex. 3 would return a cubic ease).
  2457. * @static
  2458. * @return {Function}
  2459. **/
  2460. Ease.getPowIn = function(pow) {
  2461. return function(t) {
  2462. return Math.pow(t,pow);
  2463. };
  2464. };
  2465. /**
  2466. * Configurable exponential ease.
  2467. * @method getPowOut
  2468. * @param {Number} pow The exponent to use (ex. 3 would return a cubic ease).
  2469. * @static
  2470. * @return {Function}
  2471. **/
  2472. Ease.getPowOut = function(pow) {
  2473. return function(t) {
  2474. return 1-Math.pow(1-t,pow);
  2475. };
  2476. };
  2477. /**
  2478. * Configurable exponential ease.
  2479. * @method getPowInOut
  2480. * @param {Number} pow The exponent to use (ex. 3 would return a cubic ease).
  2481. * @static
  2482. * @return {Function}
  2483. **/
  2484. Ease.getPowInOut = function(pow) {
  2485. return function(t) {
  2486. if ((t*=2)<1) return 0.5*Math.pow(t,pow);
  2487. return 1-0.5*Math.abs(Math.pow(2-t,pow));
  2488. };
  2489. };
  2490. /**
  2491. * @method quadIn
  2492. * @param {Number} t
  2493. * @static
  2494. * @return {Number}
  2495. **/
  2496. Ease.quadIn = Ease.getPowIn(2);
  2497. /**
  2498. * @method quadOut
  2499. * @param {Number} t
  2500. * @static
  2501. * @return {Number}
  2502. **/
  2503. Ease.quadOut = Ease.getPowOut(2);
  2504. /**
  2505. * @method quadInOut
  2506. * @param {Number} t
  2507. * @static
  2508. * @return {Number}
  2509. **/
  2510. Ease.quadInOut = Ease.getPowInOut(2);
  2511. /**
  2512. * @method cubicIn
  2513. * @param {Number} t
  2514. * @static
  2515. * @return {Number}
  2516. **/
  2517. Ease.cubicIn = Ease.getPowIn(3);
  2518. /**
  2519. * @method cubicOut
  2520. * @param {Number} t
  2521. * @static
  2522. * @return {Number}
  2523. **/
  2524. Ease.cubicOut = Ease.getPowOut(3);
  2525. /**
  2526. * @method cubicInOut
  2527. * @param {Number} t
  2528. * @static
  2529. * @return {Number}
  2530. **/
  2531. Ease.cubicInOut = Ease.getPowInOut(3);
  2532. /**
  2533. * @method quartIn
  2534. * @param {Number} t
  2535. * @static
  2536. * @return {Number}
  2537. **/
  2538. Ease.quartIn = Ease.getPowIn(4);
  2539. /**
  2540. * @method quartOut
  2541. * @param {Number} t
  2542. * @static
  2543. * @return {Number}
  2544. **/
  2545. Ease.quartOut = Ease.getPowOut(4);
  2546. /**
  2547. * @method quartInOut
  2548. * @param {Number} t
  2549. * @static
  2550. * @return {Number}
  2551. **/
  2552. Ease.quartInOut = Ease.getPowInOut(4);
  2553. /**
  2554. * @method quintIn
  2555. * @param {Number} t
  2556. * @static
  2557. * @return {Number}
  2558. **/
  2559. Ease.quintIn = Ease.getPowIn(5);
  2560. /**
  2561. * @method quintOut
  2562. * @param {Number} t
  2563. * @static
  2564. * @return {Number}
  2565. **/
  2566. Ease.quintOut = Ease.getPowOut(5);
  2567. /**
  2568. * @method quintInOut
  2569. * @param {Number} t
  2570. * @static
  2571. * @return {Number}
  2572. **/
  2573. Ease.quintInOut = Ease.getPowInOut(5);
  2574. /**
  2575. * @method sineIn
  2576. * @param {Number} t
  2577. * @static
  2578. * @return {Number}
  2579. **/
  2580. Ease.sineIn = function(t) {
  2581. return 1-Math.cos(t*Math.PI/2);
  2582. };
  2583. /**
  2584. * @method sineOut
  2585. * @param {Number} t
  2586. * @static
  2587. * @return {Number}
  2588. **/
  2589. Ease.sineOut = function(t) {
  2590. return Math.sin(t*Math.PI/2);
  2591. };
  2592. /**
  2593. * @method sineInOut
  2594. * @param {Number} t
  2595. * @static
  2596. * @return {Number}
  2597. **/
  2598. Ease.sineInOut = function(t) {
  2599. return -0.5*(Math.cos(Math.PI*t) - 1);
  2600. };
  2601. /**
  2602. * Configurable "back in" ease.
  2603. * @method getBackIn
  2604. * @param {Number} amount The strength of the ease.
  2605. * @static
  2606. * @return {Function}
  2607. **/
  2608. Ease.getBackIn = function(amount) {
  2609. return function(t) {
  2610. return t*t*((amount+1)*t-amount);
  2611. };
  2612. };
  2613. /**
  2614. * @method backIn
  2615. * @param {Number} t
  2616. * @static
  2617. * @return {Number}
  2618. **/
  2619. Ease.backIn = Ease.getBackIn(1.7);
  2620. /**
  2621. * Configurable "back out" ease.
  2622. * @method getBackOut
  2623. * @param {Number} amount The strength of the ease.
  2624. * @static
  2625. * @return {Function}
  2626. **/
  2627. Ease.getBackOut = function(amount) {
  2628. return function(t) {
  2629. return (--t*t*((amount+1)*t + amount) + 1);
  2630. };
  2631. };
  2632. /**
  2633. * @method backOut
  2634. * @param {Number} t
  2635. * @static
  2636. * @return {Number}
  2637. **/
  2638. Ease.backOut = Ease.getBackOut(1.7);
  2639. /**
  2640. * Configurable "back in out" ease.
  2641. * @method getBackInOut
  2642. * @param {Number} amount The strength of the ease.
  2643. * @static
  2644. * @return {Function}
  2645. **/
  2646. Ease.getBackInOut = function(amount) {
  2647. amount*=1.525;
  2648. return function(t) {
  2649. if ((t*=2)<1) return 0.5*(t*t*((amount+1)*t-amount));
  2650. return 0.5*((t-=2)*t*((amount+1)*t+amount)+2);
  2651. };
  2652. };
  2653. /**
  2654. * @method backInOut
  2655. * @param {Number} t
  2656. * @static
  2657. * @return {Number}
  2658. **/
  2659. Ease.backInOut = Ease.getBackInOut(1.7);
  2660. /**
  2661. * @method circIn
  2662. * @param {Number} t
  2663. * @static
  2664. * @return {Number}
  2665. **/
  2666. Ease.circIn = function(t) {
  2667. return -(Math.sqrt(1-t*t)- 1);
  2668. };
  2669. /**
  2670. * @method circOut
  2671. * @param {Number} t
  2672. * @static
  2673. * @return {Number}
  2674. **/
  2675. Ease.circOut = function(t) {
  2676. return Math.sqrt(1-(--t)*t);
  2677. };
  2678. /**
  2679. * @method circInOut
  2680. * @param {Number} t
  2681. * @static
  2682. * @return {Number}
  2683. **/
  2684. Ease.circInOut = function(t) {
  2685. if ((t*=2) < 1) return -0.5*(Math.sqrt(1-t*t)-1);
  2686. return 0.5*(Math.sqrt(1-(t-=2)*t)+1);
  2687. };
  2688. /**
  2689. * @method bounceIn
  2690. * @param {Number} t
  2691. * @static
  2692. * @return {Number}
  2693. **/
  2694. Ease.bounceIn = function(t) {
  2695. return 1-Ease.bounceOut(1-t);
  2696. };
  2697. /**
  2698. * @method bounceOut
  2699. * @param {Number} t
  2700. * @static
  2701. * @return {Number}
  2702. **/
  2703. Ease.bounceOut = function(t) {
  2704. if (t < 1/2.75) {
  2705. return (7.5625*t*t);
  2706. } else if (t < 2/2.75) {
  2707. return (7.5625*(t-=1.5/2.75)*t+0.75);
  2708. } else if (t < 2.5/2.75) {
  2709. return (7.5625*(t-=2.25/2.75)*t+0.9375);
  2710. } else {
  2711. return (7.5625*(t-=2.625/2.75)*t +0.984375);
  2712. }
  2713. };
  2714. /**
  2715. * @method bounceInOut
  2716. * @param {Number} t
  2717. * @static
  2718. * @return {Number}
  2719. **/
  2720. Ease.bounceInOut = function(t) {
  2721. if (t<0.5) return Ease.bounceIn (t*2) * .5;
  2722. return Ease.bounceOut(t*2-1)*0.5+0.5;
  2723. };
  2724. /**
  2725. * Configurable elastic ease.
  2726. * @method getElasticIn
  2727. * @param {Number} amplitude
  2728. * @param {Number} period
  2729. * @static
  2730. * @return {Function}
  2731. **/
  2732. Ease.getElasticIn = function(amplitude,period) {
  2733. var pi2 = Math.PI*2;
  2734. return function(t) {
  2735. if (t==0 || t==1) return t;
  2736. var s = period/pi2*Math.asin(1/amplitude);
  2737. return -(amplitude*Math.pow(2,10*(t-=1))*Math.sin((t-s)*pi2/period));
  2738. };
  2739. };
  2740. /**
  2741. * @method elasticIn
  2742. * @param {Number} t
  2743. * @static
  2744. * @return {Number}
  2745. **/
  2746. Ease.elasticIn = Ease.getElasticIn(1,0.3);
  2747. /**
  2748. * Configurable elastic ease.
  2749. * @method getElasticOut
  2750. * @param {Number} amplitude
  2751. * @param {Number} period
  2752. * @static
  2753. * @return {Function}
  2754. **/
  2755. Ease.getElasticOut = function(amplitude,period) {
  2756. var pi2 = Math.PI*2;
  2757. return function(t) {
  2758. if (t==0 || t==1) return t;
  2759. var s = period/pi2 * Math.asin(1/amplitude);
  2760. return (amplitude*Math.pow(2,-10*t)*Math.sin((t-s)*pi2/period )+1);
  2761. };
  2762. };
  2763. /**
  2764. * @method elasticOut
  2765. * @param {Number} t
  2766. * @static
  2767. * @return {Number}
  2768. **/
  2769. Ease.elasticOut = Ease.getElasticOut(1,0.3);
  2770. /**
  2771. * Configurable elastic ease.
  2772. * @method getElasticInOut
  2773. * @param {Number} amplitude
  2774. * @param {Number} period
  2775. * @static
  2776. * @return {Function}
  2777. **/
  2778. Ease.getElasticInOut = function(amplitude,period) {
  2779. var pi2 = Math.PI*2;
  2780. return function(t) {
  2781. var s = period/pi2 * Math.asin(1/amplitude);
  2782. if ((t*=2)<1) return -0.5*(amplitude*Math.pow(2,10*(t-=1))*Math.sin( (t-s)*pi2/period ));
  2783. return amplitude*Math.pow(2,-10*(t-=1))*Math.sin((t-s)*pi2/period)*0.5+1;
  2784. };
  2785. };
  2786. /**
  2787. * @method elasticInOut
  2788. * @param {Number} t
  2789. * @static
  2790. * @return {Number}
  2791. **/
  2792. Ease.elasticInOut = Ease.getElasticInOut(1,0.3*1.5);
  2793. createjs.Ease = Ease;
  2794. }());
  2795. //##############################################################################
  2796. // MotionGuidePlugin.js
  2797. //##############################################################################
  2798. this.createjs = this.createjs||{};
  2799. (function() {
  2800. "use strict";
  2801. /**
  2802. * A TweenJS plugin for working with motion guides.
  2803. *
  2804. * To use, install the plugin after TweenJS has loaded. Next tween the 'guide' property with an object as detailed below.
  2805. *
  2806. * createjs.MotionGuidePlugin.install();
  2807. *
  2808. * <h4>Example</h4>
  2809. *
  2810. * // Using a Motion Guide
  2811. * createjs.Tween.get(target).to({guide:{ path:[0,0, 0,200,200,200, 200,0,0,0] }},7000);
  2812. * // Visualizing the line
  2813. * graphics.moveTo(0,0).curveTo(0,200,200,200).curveTo(200,0,0,0);
  2814. *
  2815. * Each path needs pre-computation to ensure there's fast performance. Because of the pre-computation there's no
  2816. * built in support for path changes mid tween. These are the Guide Object's properties:<UL>
  2817. * <LI> path: Required, Array : The x/y points used to draw the path with a moveTo and 1 to n curveTo calls.</LI>
  2818. * <LI> start: Optional, 0-1 : Initial position, default 0 except for when continuing along the same path.</LI>
  2819. * <LI> end: Optional, 0-1 : Final position, default 1 if not specified.</LI>
  2820. * <LI> orient: Optional, string : "fixed"/"auto"/"cw"/"ccw"<UL>
  2821. * <LI>"fixed" forces the object to face down the path all movement (relative to start rotation),</LI>
  2822. * <LI>"auto" rotates the object along the path relative to the line.</LI>
  2823. * <LI>"cw"/"ccw" force clockwise or counter clockwise rotations including flash like behaviour</LI>
  2824. * </UL></LI>
  2825. * </UL>
  2826. * Guide objects should not be shared between tweens even if all properties are identical, the library stores
  2827. * information on these objects in the background and sharing them can cause unexpected behaviour. Values
  2828. * outside 0-1 range of tweens will be a "best guess" from the appropriate part of the defined curve.
  2829. *
  2830. * @class MotionGuidePlugin
  2831. * @constructor
  2832. **/
  2833. function MotionGuidePlugin() {
  2834. throw("MotionGuidePlugin cannot be instantiated.")
  2835. };
  2836. // static properties:
  2837. /**
  2838. * @property priority
  2839. * @protected
  2840. * @static
  2841. **/
  2842. MotionGuidePlugin.priority = 0; // high priority, should run sooner
  2843. /**
  2844. * @property temporary variable storage
  2845. * @private
  2846. * @static
  2847. */
  2848. MotionGuidePlugin._rotOffS;
  2849. /**
  2850. * @property temporary variable storage
  2851. * @private
  2852. * @static
  2853. */
  2854. MotionGuidePlugin._rotOffE;
  2855. /**
  2856. * @property temporary variable storage
  2857. * @private
  2858. * @static
  2859. */
  2860. MotionGuidePlugin._rotNormS;
  2861. /**
  2862. * @property temporary variable storage
  2863. * @private
  2864. * @static
  2865. */
  2866. MotionGuidePlugin._rotNormE;
  2867. // static methods
  2868. /**
  2869. * Installs this plugin for use with TweenJS. Call this once after TweenJS is loaded to enable this plugin.
  2870. * @method install
  2871. * @static
  2872. **/
  2873. MotionGuidePlugin.install = function() {
  2874. createjs.Tween.installPlugin(MotionGuidePlugin, ["guide", "x", "y", "rotation"]);
  2875. return createjs.Tween.IGNORE;
  2876. };
  2877. /**
  2878. * @method init
  2879. * @protected
  2880. * @static
  2881. **/
  2882. MotionGuidePlugin.init = function(tween, prop, value) {
  2883. var target = tween.target;
  2884. if(!target.hasOwnProperty("x")){ target.x = 0; }
  2885. if(!target.hasOwnProperty("y")){ target.y = 0; }
  2886. if(!target.hasOwnProperty("rotation")){ target.rotation = 0; }
  2887. if(prop=="rotation"){ tween.__needsRot = true; }
  2888. return prop=="guide"?null:value;
  2889. };
  2890. /**
  2891. * @method step
  2892. * @protected
  2893. * @static
  2894. **/
  2895. MotionGuidePlugin.step = function(tween, prop, startValue, endValue, injectProps) {
  2896. // other props
  2897. if(prop == "rotation"){
  2898. tween.__rotGlobalS = startValue;
  2899. tween.__rotGlobalE = endValue;
  2900. MotionGuidePlugin.testRotData(tween, injectProps);
  2901. }
  2902. if(prop != "guide"){ return endValue; }
  2903. // guide only information - Start -
  2904. var temp, data = endValue;
  2905. if(!data.hasOwnProperty("path")){ data.path = []; }
  2906. var path = data.path;
  2907. if(!data.hasOwnProperty("end")){ data.end = 1; }
  2908. if(!data.hasOwnProperty("start")){
  2909. data.start = (startValue&&startValue.hasOwnProperty("end")&&startValue.path===path)?startValue.end:0;
  2910. }
  2911. // Figure out subline information
  2912. if(data.hasOwnProperty("_segments") && data._length){ return endValue; }
  2913. var l = path.length;
  2914. var accuracy = 10; // Adjust to improve line following precision but sacrifice performance (# of seg)
  2915. if(l >= 6 && (l-2) % 4 == 0){ // Enough points && contains correct number per entry ignoring start
  2916. data._segments = [];
  2917. data._length = 0;
  2918. for(var i=2; i<l; i+=4){
  2919. var sx = path[i-2], sy = path[i-1];
  2920. var cx = path[i+0], cy = path[i+1];
  2921. var ex = path[i+2], ey = path[i+3];
  2922. var oldX = sx, oldY = sy;
  2923. var tempX, tempY, total = 0;
  2924. var sublines = [];
  2925. for(var j=1; j<=accuracy; j++){
  2926. var t = j/accuracy;
  2927. var inv = 1 - t;
  2928. tempX = inv*inv * sx + 2 * inv * t * cx + t*t * ex;
  2929. tempY = inv*inv * sy + 2 * inv * t * cy + t*t * ey;
  2930. total += sublines[sublines.push(Math.sqrt((temp=tempX-oldX)*temp + (temp=tempY-oldY)*temp))-1];
  2931. oldX = tempX;
  2932. oldY = tempY;
  2933. }
  2934. data._segments.push(total);
  2935. data._segments.push(sublines);
  2936. data._length += total;
  2937. }
  2938. } else {
  2939. throw("invalid 'path' data, please see documentation for valid paths");
  2940. }
  2941. // Setup x/y tweens
  2942. temp = data.orient;
  2943. data.orient = true;
  2944. var o = {};
  2945. MotionGuidePlugin.calc(data, data.start, o);
  2946. tween.__rotPathS = Number(o.rotation.toFixed(5));
  2947. MotionGuidePlugin.calc(data, data.end, o);
  2948. tween.__rotPathE = Number(o.rotation.toFixed(5));
  2949. data.orient = false; //here and now we don't know if we need to
  2950. MotionGuidePlugin.calc(data, data.end, injectProps);
  2951. data.orient = temp;
  2952. // Setup rotation properties
  2953. if(!data.orient){ return endValue; }
  2954. tween.__guideData = data;
  2955. MotionGuidePlugin.testRotData(tween, injectProps);
  2956. return endValue;
  2957. };
  2958. /**
  2959. * @method testRotData
  2960. * @protected
  2961. * @static
  2962. **/
  2963. MotionGuidePlugin.testRotData = function(tween, injectProps){
  2964. // no rotation informat? if we need it come back, if we don't use 0 & ensure we have guide data
  2965. if(tween.__rotGlobalS === undefined || tween.__rotGlobalE === undefined){
  2966. if(tween.__needsRot){ return; }
  2967. if(tween._curQueueProps.rotation !== undefined){
  2968. tween.__rotGlobalS = tween.__rotGlobalE = tween._curQueueProps.rotation;
  2969. } else {
  2970. tween.__rotGlobalS = tween.__rotGlobalE = injectProps.rotation = tween.target.rotation || 0;
  2971. }
  2972. }
  2973. if(tween.__guideData === undefined){ return; }
  2974. // Process rotation properties
  2975. var data = tween.__guideData;
  2976. var rotGlobalD = tween.__rotGlobalE - tween.__rotGlobalS;
  2977. var rotPathD = tween.__rotPathE - tween.__rotPathS;
  2978. var rot = rotGlobalD - rotPathD;
  2979. if(data.orient == "auto"){
  2980. if(rot > 180){ rot -= 360; }
  2981. else if(rot < -180){ rot += 360; }
  2982. } else if(data.orient == "cw"){
  2983. while(rot < 0){ rot += 360; }
  2984. if(rot == 0 && rotGlobalD > 0 && rotGlobalD != 180){ rot += 360; }
  2985. } else if(data.orient == "ccw"){
  2986. rot = rotGlobalD - ((rotPathD > 180)?(360-rotPathD):(rotPathD)); // sign flipping on path
  2987. while(rot > 0){ rot -= 360; }
  2988. if(rot == 0 && rotGlobalD < 0 && rotGlobalD != -180){ rot -= 360; }
  2989. }
  2990. data.rotDelta = rot;
  2991. data.rotOffS = tween.__rotGlobalS - tween.__rotPathS;
  2992. // reset
  2993. tween.__rotGlobalS = tween.__rotGlobalE = tween.__guideData = tween.__needsRot = undefined;
  2994. };
  2995. /**
  2996. * @method tween
  2997. * @protected
  2998. * @static
  2999. **/
  3000. MotionGuidePlugin.tween = function(tween, prop, value, startValues, endValues, ratio, wait, end) {
  3001. var data = endValues.guide;
  3002. if(data == undefined || data === startValues.guide){ return value; }
  3003. if(data.lastRatio != ratio){
  3004. // first time through so calculate what I need to
  3005. var t = ((data.end-data.start)*(wait?data.end:ratio)+data.start);
  3006. MotionGuidePlugin.calc(data, t, tween.target);
  3007. switch(data.orient){
  3008. case "cw": // mix in the original rotation
  3009. case "ccw":
  3010. case "auto": tween.target.rotation += data.rotOffS + data.rotDelta*ratio; break;
  3011. case "fixed": // follow fixed behaviour to solve potential issues
  3012. default: tween.target.rotation += data.rotOffS; break;
  3013. }
  3014. data.lastRatio = ratio;
  3015. }
  3016. if(prop == "rotation" && ((!data.orient) || data.orient == "false")){ return value; }
  3017. return tween.target[prop];
  3018. };
  3019. /**
  3020. * Determine the appropriate x/y/rotation information about a path for a given ratio along the path.
  3021. * Assumes a path object with all optional parameters specified.
  3022. * @param data Data object you would pass to the "guide:" property in a Tween
  3023. * @param ratio 0-1 Distance along path, values outside 0-1 are "best guess"
  3024. * @param target Object to copy the results onto, will use a new object if not supplied.
  3025. * @return {Object} The target object or a new object w/ the tweened properties
  3026. * @static
  3027. */
  3028. MotionGuidePlugin.calc = function(data, ratio, target) {
  3029. if(data._segments == undefined){ throw("Missing critical pre-calculated information, please file a bug"); }
  3030. if(target == undefined){ target = {x:0, y:0, rotation:0}; }
  3031. var seg = data._segments;
  3032. var path = data.path;
  3033. // find segment
  3034. var pos = data._length * ratio;
  3035. var cap = seg.length - 2;
  3036. var n = 0;
  3037. while(pos > seg[n] && n < cap){
  3038. pos -= seg[n];
  3039. n+=2;
  3040. }
  3041. // find subline
  3042. var sublines = seg[n+1];
  3043. var i = 0;
  3044. cap = sublines.length-1;
  3045. while(pos > sublines[i] && i < cap){
  3046. pos -= sublines[i];
  3047. i++;
  3048. }
  3049. var t = (i/++cap)+(pos/(cap*sublines[i]));
  3050. // find x/y
  3051. n = (n*2)+2;
  3052. var inv = 1 - t;
  3053. target.x = inv*inv * path[n-2] + 2 * inv * t * path[n+0] + t*t * path[n+2];
  3054. target.y = inv*inv * path[n-1] + 2 * inv * t * path[n+1] + t*t * path[n+3];
  3055. // orientation
  3056. if(data.orient){
  3057. target.rotation = 57.2957795 * Math.atan2(
  3058. (path[n+1]-path[n-1])*inv + (path[n+3]-path[n+1])*t,
  3059. (path[n+0]-path[n-2])*inv + (path[n+2]-path[n+0])*t);
  3060. }
  3061. return target;
  3062. };
  3063. createjs.MotionGuidePlugin = MotionGuidePlugin;
  3064. }());
  3065. //##############################################################################
  3066. // version.js
  3067. //##############################################################################
  3068. this.createjs = this.createjs || {};
  3069. (function() {
  3070. "use strict";
  3071. /**
  3072. * Static class holding library specific information such as the version and buildDate of
  3073. * the library.
  3074. * @class TweenJS
  3075. **/
  3076. var s = createjs.TweenJS = createjs.TweenJS || {};
  3077. /**
  3078. * The version string for this release.
  3079. * @property version
  3080. * @type String
  3081. * @static
  3082. **/
  3083. s.version = /*=version*/"0.6.2"; // injected by build process
  3084. /**
  3085. * The build date for this release in UTC format.
  3086. * @property buildDate
  3087. * @type String
  3088. * @static
  3089. **/
  3090. s.buildDate = /*=date*/"Thu, 26 Nov 2015 20:44:31 GMT"; // injected by build process
  3091. })();