diff options
Diffstat (limited to 'vendor/oojs/oojs-ui/src/core.js')
-rw-r--r-- | vendor/oojs/oojs-ui/src/core.js | 286 |
1 files changed, 286 insertions, 0 deletions
diff --git a/vendor/oojs/oojs-ui/src/core.js b/vendor/oojs/oojs-ui/src/core.js new file mode 100644 index 00000000..1331f5cc --- /dev/null +++ b/vendor/oojs/oojs-ui/src/core.js @@ -0,0 +1,286 @@ +/** + * Namespace for all classes, static methods and static properties. + * + * @class + * @singleton + */ +OO.ui = {}; + +OO.ui.bind = $.proxy; + +/** + * @property {Object} + */ +OO.ui.Keys = { + UNDEFINED: 0, + BACKSPACE: 8, + DELETE: 46, + LEFT: 37, + RIGHT: 39, + UP: 38, + DOWN: 40, + ENTER: 13, + END: 35, + HOME: 36, + TAB: 9, + PAGEUP: 33, + PAGEDOWN: 34, + ESCAPE: 27, + SHIFT: 16, + SPACE: 32 +}; + +/** + * Check if an element is focusable. + * Inspired from :focusable in jQueryUI v1.11.4 - 2015-04-14 + * + * @param {jQuery} element Element to test + * @return {Boolean} [description] + */ +OO.ui.isFocusableElement = function ( $element ) { + var node = $element[0], + nodeName = node.nodeName.toLowerCase(), + // Check if the element have tabindex set + isInElementGroup = /^(input|select|textarea|button|object)$/.test( nodeName ), + // Check if the element is a link with href or if it has tabindex + isOtherElement = ( + ( nodeName === 'a' && node.href ) || + !isNaN( $element.attr( 'tabindex' ) ) + ), + // Check if the element is visible + isVisible = ( + // This is quicker than calling $element.is( ':visible' ) + $.expr.filters.visible( node ) && + // Check that all parents are visible + !$element.parents().addBack().filter( function () { + return $.css( this, 'visibility' ) === 'hidden'; + } ).length + ); + + return ( + ( isInElementGroup ? !node.disabled : isOtherElement ) && + isVisible + ); +}; + +/** + * Get the user's language and any fallback languages. + * + * These language codes are used to localize user interface elements in the user's language. + * + * In environments that provide a localization system, this function should be overridden to + * return the user's language(s). The default implementation returns English (en) only. + * + * @return {string[]} Language codes, in descending order of priority + */ +OO.ui.getUserLanguages = function () { + return [ 'en' ]; +}; + +/** + * Get a value in an object keyed by language code. + * + * @param {Object.<string,Mixed>} obj Object keyed by language code + * @param {string|null} [lang] Language code, if omitted or null defaults to any user language + * @param {string} [fallback] Fallback code, used if no matching language can be found + * @return {Mixed} Local value + */ +OO.ui.getLocalValue = function ( obj, lang, fallback ) { + var i, len, langs; + + // Requested language + if ( obj[ lang ] ) { + return obj[ lang ]; + } + // Known user language + langs = OO.ui.getUserLanguages(); + for ( i = 0, len = langs.length; i < len; i++ ) { + lang = langs[ i ]; + if ( obj[ lang ] ) { + return obj[ lang ]; + } + } + // Fallback language + if ( obj[ fallback ] ) { + return obj[ fallback ]; + } + // First existing language + for ( lang in obj ) { + return obj[ lang ]; + } + + return undefined; +}; + +/** + * Check if a node is contained within another node + * + * Similar to jQuery#contains except a list of containers can be supplied + * and a boolean argument allows you to include the container in the match list + * + * @param {HTMLElement|HTMLElement[]} containers Container node(s) to search in + * @param {HTMLElement} contained Node to find + * @param {boolean} [matchContainers] Include the container(s) in the list of nodes to match, otherwise only match descendants + * @return {boolean} The node is in the list of target nodes + */ +OO.ui.contains = function ( containers, contained, matchContainers ) { + var i; + if ( !Array.isArray( containers ) ) { + containers = [ containers ]; + } + for ( i = containers.length - 1; i >= 0; i-- ) { + if ( ( matchContainers && contained === containers[ i ] ) || $.contains( containers[ i ], contained ) ) { + return true; + } + } + return false; +}; + +/** + * Return a function, that, as long as it continues to be invoked, will not + * be triggered. The function will be called after it stops being called for + * N milliseconds. If `immediate` is passed, trigger the function on the + * leading edge, instead of the trailing. + * + * Ported from: http://underscorejs.org/underscore.js + * + * @param {Function} func + * @param {number} wait + * @param {boolean} immediate + * @return {Function} + */ +OO.ui.debounce = function ( func, wait, immediate ) { + var timeout; + return function () { + var context = this, + args = arguments, + later = function () { + timeout = null; + if ( !immediate ) { + func.apply( context, args ); + } + }; + if ( immediate && !timeout ) { + func.apply( context, args ); + } + clearTimeout( timeout ); + timeout = setTimeout( later, wait ); + }; +}; + +/** + * Reconstitute a JavaScript object corresponding to a widget created by + * the PHP implementation. + * + * This is an alias for `OO.ui.Element.static.infuse()`. + * + * @param {string|HTMLElement|jQuery} idOrNode + * A DOM id (if a string) or node for the widget to infuse. + * @return {OO.ui.Element} + * The `OO.ui.Element` corresponding to this (infusable) document node. + */ +OO.ui.infuse = function ( idOrNode ) { + return OO.ui.Element.static.infuse( idOrNode ); +}; + +( function () { + /** + * Message store for the default implementation of OO.ui.msg + * + * Environments that provide a localization system should not use this, but should override + * OO.ui.msg altogether. + * + * @private + */ + var messages = { + // Tool tip for a button that moves items in a list down one place + 'ooui-outline-control-move-down': 'Move item down', + // Tool tip for a button that moves items in a list up one place + 'ooui-outline-control-move-up': 'Move item up', + // Tool tip for a button that removes items from a list + 'ooui-outline-control-remove': 'Remove item', + // Label for the toolbar group that contains a list of all other available tools + 'ooui-toolbar-more': 'More', + // Label for the fake tool that expands the full list of tools in a toolbar group + 'ooui-toolgroup-expand': 'More', + // Label for the fake tool that collapses the full list of tools in a toolbar group + 'ooui-toolgroup-collapse': 'Fewer', + // Default label for the accept button of a confirmation dialog + 'ooui-dialog-message-accept': 'OK', + // Default label for the reject button of a confirmation dialog + 'ooui-dialog-message-reject': 'Cancel', + // Title for process dialog error description + 'ooui-dialog-process-error': 'Something went wrong', + // Label for process dialog dismiss error button, visible when describing errors + 'ooui-dialog-process-dismiss': 'Dismiss', + // Label for process dialog retry action button, visible when describing only recoverable errors + 'ooui-dialog-process-retry': 'Try again', + // Label for process dialog retry action button, visible when describing only warnings + 'ooui-dialog-process-continue': 'Continue' + }; + + /** + * Get a localized message. + * + * In environments that provide a localization system, this function should be overridden to + * return the message translated in the user's language. The default implementation always returns + * English messages. + * + * After the message key, message parameters may optionally be passed. In the default implementation, + * any occurrences of $1 are replaced with the first parameter, $2 with the second parameter, etc. + * Alternative implementations of OO.ui.msg may use any substitution system they like, as long as + * they support unnamed, ordered message parameters. + * + * @abstract + * @param {string} key Message key + * @param {Mixed...} [params] Message parameters + * @return {string} Translated message with parameters substituted + */ + OO.ui.msg = function ( key ) { + var message = messages[ key ], + params = Array.prototype.slice.call( arguments, 1 ); + if ( typeof message === 'string' ) { + // Perform $1 substitution + message = message.replace( /\$(\d+)/g, function ( unused, n ) { + var i = parseInt( n, 10 ); + return params[ i - 1 ] !== undefined ? params[ i - 1 ] : '$' + n; + } ); + } else { + // Return placeholder if message not found + message = '[' + key + ']'; + } + return message; + }; + + /** + * Package a message and arguments for deferred resolution. + * + * Use this when you are statically specifying a message and the message may not yet be present. + * + * @param {string} key Message key + * @param {Mixed...} [params] Message parameters + * @return {Function} Function that returns the resolved message when executed + */ + OO.ui.deferMsg = function () { + var args = arguments; + return function () { + return OO.ui.msg.apply( OO.ui, args ); + }; + }; + + /** + * Resolve a message. + * + * If the message is a function it will be executed, otherwise it will pass through directly. + * + * @param {Function|string} msg Deferred message, or message text + * @return {string} Resolved message + */ + OO.ui.resolveMsg = function ( msg ) { + if ( $.isFunction( msg ) ) { + return msg(); + } + return msg; + }; + +} )(); |