AutorÃa | Ultima modificación | Ver Log |
var H5P = window.H5P = window.H5P || {};/*** The Event class for the EventDispatcher.** @class* @param {string} type* @param {*} data* @param {Object} [extras]* @param {boolean} [extras.bubbles]* @param {boolean} [extras.external]*/H5P.Event = function (type, data, extras) {this.type = type;this.data = data;var bubbles = false;// Is this an external event?var external = false;// Is this event scheduled to be sent externally?var scheduledForExternal = false;if (extras === undefined) {extras = {};}if (extras.bubbles === true) {bubbles = true;}if (extras.external === true) {external = true;}/*** Prevent this event from bubbling up to parent*/this.preventBubbling = function () {bubbles = false;};/*** Get bubbling status** @returns {boolean}* true if bubbling false otherwise*/this.getBubbles = function () {return bubbles;};/*** Try to schedule an event for externalDispatcher** @returns {boolean}* true if external and not already scheduled, otherwise false*/this.scheduleForExternal = function () {if (external && !scheduledForExternal) {scheduledForExternal = true;return true;}return false;};};/*** Callback type for event listeners.** @callback H5P.EventCallback* @param {H5P.Event} event*/H5P.EventDispatcher = (function () {/*** The base of the event system.* Inherit this class if you want your H5P to dispatch events.** @class* @memberof H5P*/function EventDispatcher() {var self = this;/*** Keep track of listeners for each event.** @private* @type {Object}*/var triggers = {};/*** Add new event listener.** @throws {TypeError}* listener must be a function* @param {string} type* Event type* @param {H5P.EventCallback} listener* Event listener* @param {Object} [thisArg]* Optionally specify the this value when calling listener.*/this.on = function (type, listener, thisArg) {if (typeof listener !== 'function') {throw TypeError('listener must be a function');}// Trigger event before adding to avoid recursionself.trigger('newListener', {'type': type, 'listener': listener});var trigger = {'listener': listener, 'thisArg': thisArg};if (!triggers[type]) {// Firsttriggers[type] = [trigger];}else {// Appendtriggers[type].push(trigger);}};/*** Add new event listener that will be fired only once.** @throws {TypeError}* listener must be a function* @param {string} type* Event type* @param {H5P.EventCallback} listener* Event listener* @param {Object} thisArg* Optionally specify the this value when calling listener.*/this.once = function (type, listener, thisArg) {if (!(listener instanceof Function)) {throw TypeError('listener must be a function');}var once = function (event) {self.off(event.type, once);listener.call(this, event);};self.on(type, once, thisArg);};/*** Remove event listener.* If no listener is specified, all listeners will be removed.** @throws {TypeError}* listener must be a function* @param {string} type* Event type* @param {H5P.EventCallback} listener* Event listener*/this.off = function (type, listener) {if (listener !== undefined && !(listener instanceof Function)) {throw TypeError('listener must be a function');}if (triggers[type] === undefined) {return;}if (listener === undefined) {// Remove all listenersdelete triggers[type];self.trigger('removeListener', type);return;}// Find specific listenerfor (var i = 0; i < triggers[type].length; i++) {if (triggers[type][i].listener === listener) {triggers[type].splice(i, 1);self.trigger('removeListener', type, {'listener': listener});break;}}// Clean up empty arraysif (!triggers[type].length) {delete triggers[type];}};/*** Try to call all event listeners for the given event type.** @private* @param {string} Event type*/var call = function (type, event) {if (triggers[type] === undefined) {return;}// Clone array (prevents triggers from being modified during the event)var handlers = triggers[type].slice();// Call all listenersfor (var i = 0; i < handlers.length; i++) {var trigger = handlers[i];var thisArg = (trigger.thisArg ? trigger.thisArg : this);trigger.listener.call(thisArg, event);}};/*** Dispatch event.** @param {string|H5P.Event} event* Event object or event type as string* @param {*} [eventData]* Custom event data(used when event type as string is used as first* argument).* @param {Object} [extras]* @param {boolean} [extras.bubbles]* @param {boolean} [extras.external]*/this.trigger = function (event, eventData, extras) {if (event === undefined) {return;}if (event instanceof String || typeof event === 'string') {event = new H5P.Event(event, eventData, extras);}else if (eventData !== undefined) {event.data = eventData;}// Check to see if this event should go externally after all triggering and bubbling is donevar scheduledForExternal = event.scheduleForExternal();// Call all listenerscall.call(this, event.type, event);// Call all * listenerscall.call(this, '*', event);// Bubbleif (event.getBubbles() && self.parent instanceof H5P.EventDispatcher &&(self.parent.trigger instanceof Function || typeof self.parent.trigger === 'function')) {self.parent.trigger(event);}if (scheduledForExternal) {H5P.externalDispatcher.trigger.call(this, event);}};}return EventDispatcher;})();