'use strict'; exports.__esModule = true; /** * Copyright 2013-2014, Facebook, Inc. * All rights reserved. * * This file contains a modified version of: * https://github.com/facebook/react/blob/v0.12.0/src/addons/transitions/ReactTransitionEvents.js * * This source code is licensed under the BSD-style license found here: * https://github.com/facebook/react/blob/v0.12.0/LICENSE * An additional grant of patent rights can be found here: * https://github.com/facebook/react/blob/v0.12.0/PATENTS */ var canUseDOM = !!(typeof window !== 'undefined' && window.document && window.document.createElement); /** * EVENT_NAME_MAP is used to determine which event fired when a * transition/animation ends, based on the style property used to * define that event. */ var EVENT_NAME_MAP = { transitionend: { 'transition': 'transitionend', 'WebkitTransition': 'webkitTransitionEnd', 'MozTransition': 'mozTransitionEnd', 'OTransition': 'oTransitionEnd', 'msTransition': 'MSTransitionEnd' }, animationend: { 'animation': 'animationend', 'WebkitAnimation': 'webkitAnimationEnd', 'MozAnimation': 'mozAnimationEnd', 'OAnimation': 'oAnimationEnd', 'msAnimation': 'MSAnimationEnd' } }; var endEvents = []; function detectEvents() { var testEl = document.createElement('div'); var style = testEl.style; // On some platforms, in particular some releases of Android 4.x, // the un-prefixed "animation" and "transition" properties are defined on the // style object but the events that fire will still be prefixed, so we need // to check if the un-prefixed events are useable, and if not remove them // from the map if (!('AnimationEvent' in window)) { delete EVENT_NAME_MAP.animationend.animation; } if (!('TransitionEvent' in window)) { delete EVENT_NAME_MAP.transitionend.transition; } for (var baseEventName in EVENT_NAME_MAP) { // eslint-disable-line guard-for-in var baseEvents = EVENT_NAME_MAP[baseEventName]; for (var styleName in baseEvents) { if (styleName in style) { endEvents.push(baseEvents[styleName]); break; } } } } if (canUseDOM) { detectEvents(); } // We use the raw {add|remove}EventListener() call because EventListener // does not know how to remove event listeners and we really should // clean up. Also, these events are not triggered in older browsers // so we should be A-OK here. function addEventListener(node, eventName, eventListener) { node.addEventListener(eventName, eventListener, false); } function removeEventListener(node, eventName, eventListener) { node.removeEventListener(eventName, eventListener, false); } var ReactTransitionEvents = { addEndEventListener: function addEndEventListener(node, eventListener) { if (endEvents.length === 0) { // If CSS transitions are not supported, trigger an "end animation" // event immediately. window.setTimeout(eventListener, 0); return; } endEvents.forEach(function (endEvent) { addEventListener(node, endEvent, eventListener); }); }, removeEndEventListener: function removeEndEventListener(node, eventListener) { if (endEvents.length === 0) { return; } endEvents.forEach(function (endEvent) { removeEventListener(node, endEvent, eventListener); }); } }; exports['default'] = ReactTransitionEvents; module.exports = exports['default'];