(function webpackUniversalModuleDefinition(root, factory) {
	if(typeof exports === 'object' && typeof module === 'object')
		module.exports = factory();
	else if(typeof define === 'function' && define.amd)
		define([], factory);
	else if(typeof exports === 'object')
		exports["rup"] = factory();
	else
		root["rup"] = factory();
})(this, function() {
return /******/ (function(modules) { // webpackBootstrap
/******/ 	// The module cache
/******/ 	var installedModules = {};
/******/
/******/ 	// The require function
/******/ 	function __webpack_require__(moduleId) {
/******/
/******/ 		// Check if module is in cache
/******/ 		if(installedModules[moduleId]) {
/******/ 			return installedModules[moduleId].exports;
/******/ 		}
/******/ 		// Create a new module (and put it into the cache)
/******/ 		var module = installedModules[moduleId] = {
/******/ 			i: moduleId,
/******/ 			l: false,
/******/ 			exports: {}
/******/ 		};
/******/
/******/ 		// Execute the module function
/******/ 		modules[moduleId].call(module.exports, module, module.exports, __webpack_require__);
/******/
/******/ 		// Flag the module as loaded
/******/ 		module.l = true;
/******/
/******/ 		// Return the exports of the module
/******/ 		return module.exports;
/******/ 	}
/******/
/******/
/******/ 	// expose the modules object (__webpack_modules__)
/******/ 	__webpack_require__.m = modules;
/******/
/******/ 	// expose the module cache
/******/ 	__webpack_require__.c = installedModules;
/******/
/******/ 	// identity function for calling harmony imports with the correct context
/******/ 	__webpack_require__.i = function(value) { return value; };
/******/
/******/ 	// define getter function for harmony exports
/******/ 	__webpack_require__.d = function(exports, name, getter) {
/******/ 		if(!__webpack_require__.o(exports, name)) {
/******/ 			Object.defineProperty(exports, name, {
/******/ 				configurable: false,
/******/ 				enumerable: true,
/******/ 				get: getter
/******/ 			});
/******/ 		}
/******/ 	};
/******/
/******/ 	// getDefaultExport function for compatibility with non-harmony modules
/******/ 	__webpack_require__.n = function(module) {
/******/ 		var getter = module && module.__esModule ?
/******/ 			function getDefault() { return module['default']; } :
/******/ 			function getModuleExports() { return module; };
/******/ 		__webpack_require__.d(getter, 'a', getter);
/******/ 		return getter;
/******/ 	};
/******/
/******/ 	// Object.prototype.hasOwnProperty.call
/******/ 	__webpack_require__.o = function(object, property) { return Object.prototype.hasOwnProperty.call(object, property); };
/******/
/******/ 	// __webpack_public_path__
/******/ 	__webpack_require__.p = "";
/******/
/******/ 	// Load entry module and return exports
/******/ 	return __webpack_require__(__webpack_require__.s = 212);
/******/ })
/************************************************************************/
/******/ ([
/* 0 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*!
 * jQuery JavaScript Library v1.12.4
 * http://jquery.com/
 *
 * Includes Sizzle.js
 * http://sizzlejs.com/
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license
 * http://jquery.org/license
 *
 * Date: 2016-05-20T17:17Z
 */

(function( global, factory ) {

	if ( typeof module === "object" && typeof module.exports === "object" ) {
		// For CommonJS and CommonJS-like environments where a proper `window`
		// is present, execute the factory and get jQuery.
		// For environments that do not have a `window` with a `document`
		// (such as Node.js), expose a factory as module.exports.
		// This accentuates the need for the creation of a real `window`.
		// e.g. var jQuery = require("jquery")(window);
		// See ticket #14549 for more info.
		module.exports = global.document ?
			factory( global, true ) :
			function( w ) {
				if ( !w.document ) {
					throw new Error( "jQuery requires a window with a document" );
				}
				return factory( w );
			};
	} else {
		factory( global );
	}

// Pass this if window is not defined yet
}(typeof window !== "undefined" ? window : this, function( window, noGlobal ) {

// Support: Firefox 18+
// Can't be in strict mode, several libs including ASP.NET trace
// the stack via arguments.caller.callee and Firefox dies if
// you try to trace through "use strict" call chains. (#13335)
//"use strict";
var deletedIds = [];

var document = window.document;

var slice = deletedIds.slice;

var concat = deletedIds.concat;

var push = deletedIds.push;

var indexOf = deletedIds.indexOf;

var class2type = {};

var toString = class2type.toString;

var hasOwn = class2type.hasOwnProperty;

var support = {};



var
	version = "1.12.4",

	// Define a local copy of jQuery
	jQuery = function( selector, context ) {

		// The jQuery object is actually just the init constructor 'enhanced'
		// Need init if jQuery is called (just allow error to be thrown if not included)
		return new jQuery.fn.init( selector, context );
	},

	// Support: Android<4.1, IE<9
	// Make sure we trim BOM and NBSP
	rtrim = /^[\s\uFEFF\xA0]+|[\s\uFEFF\xA0]+$/g,

	// Matches dashed string for camelizing
	rmsPrefix = /^-ms-/,
	rdashAlpha = /-([\da-z])/gi,

	// Used by jQuery.camelCase as callback to replace()
	fcamelCase = function( all, letter ) {
		return letter.toUpperCase();
	};

jQuery.fn = jQuery.prototype = {

	// The current version of jQuery being used
	jquery: version,

	constructor: jQuery,

	// Start with an empty selector
	selector: "",

	// The default length of a jQuery object is 0
	length: 0,

	toArray: function() {
		return slice.call( this );
	},

	// Get the Nth element in the matched element set OR
	// Get the whole matched element set as a clean array
	get: function( num ) {
		return num != null ?

			// Return just the one element from the set
			( num < 0 ? this[ num + this.length ] : this[ num ] ) :

			// Return all the elements in a clean array
			slice.call( this );
	},

	// Take an array of elements and push it onto the stack
	// (returning the new matched element set)
	pushStack: function( elems ) {

		// Build a new jQuery matched element set
		var ret = jQuery.merge( this.constructor(), elems );

		// Add the old object onto the stack (as a reference)
		ret.prevObject = this;
		ret.context = this.context;

		// Return the newly-formed element set
		return ret;
	},

	// Execute a callback for every element in the matched set.
	each: function( callback ) {
		return jQuery.each( this, callback );
	},

	map: function( callback ) {
		return this.pushStack( jQuery.map( this, function( elem, i ) {
			return callback.call( elem, i, elem );
		} ) );
	},

	slice: function() {
		return this.pushStack( slice.apply( this, arguments ) );
	},

	first: function() {
		return this.eq( 0 );
	},

	last: function() {
		return this.eq( -1 );
	},

	eq: function( i ) {
		var len = this.length,
			j = +i + ( i < 0 ? len : 0 );
		return this.pushStack( j >= 0 && j < len ? [ this[ j ] ] : [] );
	},

	end: function() {
		return this.prevObject || this.constructor();
	},

	// For internal use only.
	// Behaves like an Array's method, not like a jQuery method.
	push: push,
	sort: deletedIds.sort,
	splice: deletedIds.splice
};

jQuery.extend = jQuery.fn.extend = function() {
	var src, copyIsArray, copy, name, options, clone,
		target = arguments[ 0 ] || {},
		i = 1,
		length = arguments.length,
		deep = false;

	// Handle a deep copy situation
	if ( typeof target === "boolean" ) {
		deep = target;

		// skip the boolean and the target
		target = arguments[ i ] || {};
		i++;
	}

	// Handle case when target is a string or something (possible in deep copy)
	if ( typeof target !== "object" && !jQuery.isFunction( target ) ) {
		target = {};
	}

	// extend jQuery itself if only one argument is passed
	if ( i === length ) {
		target = this;
		i--;
	}

	for ( ; i < length; i++ ) {

		// Only deal with non-null/undefined values
		if ( ( options = arguments[ i ] ) != null ) {

			// Extend the base object
			for ( name in options ) {
				src = target[ name ];
				copy = options[ name ];

				// Prevent never-ending loop
				if ( target === copy ) {
					continue;
				}

				// Recurse if we're merging plain objects or arrays
				if ( deep && copy && ( jQuery.isPlainObject( copy ) ||
					( copyIsArray = jQuery.isArray( copy ) ) ) ) {

					if ( copyIsArray ) {
						copyIsArray = false;
						clone = src && jQuery.isArray( src ) ? src : [];

					} else {
						clone = src && jQuery.isPlainObject( src ) ? src : {};
					}

					// Never move original objects, clone them
					target[ name ] = jQuery.extend( deep, clone, copy );

				// Don't bring in undefined values
				} else if ( copy !== undefined ) {
					target[ name ] = copy;
				}
			}
		}
	}

	// Return the modified object
	return target;
};

jQuery.extend( {

	// Unique for each copy of jQuery on the page
	expando: "jQuery" + ( version + Math.random() ).replace( /\D/g, "" ),

	// Assume jQuery is ready without the ready module
	isReady: true,

	error: function( msg ) {
		throw new Error( msg );
	},

	noop: function() {},

	// See test/unit/core.js for details concerning isFunction.
	// Since version 1.3, DOM methods and functions like alert
	// aren't supported. They return false on IE (#2968).
	isFunction: function( obj ) {
		return jQuery.type( obj ) === "function";
	},

	isArray: Array.isArray || function( obj ) {
		return jQuery.type( obj ) === "array";
	},

	isWindow: function( obj ) {
		/* jshint eqeqeq: false */
		return obj != null && obj == obj.window;
	},

	isNumeric: function( obj ) {

		// parseFloat NaNs numeric-cast false positives (null|true|false|"")
		// ...but misinterprets leading-number strings, particularly hex literals ("0x...")
		// subtraction forces infinities to NaN
		// adding 1 corrects loss of precision from parseFloat (#15100)
		var realStringObj = obj && obj.toString();
		return !jQuery.isArray( obj ) && ( realStringObj - parseFloat( realStringObj ) + 1 ) >= 0;
	},

	isEmptyObject: function( obj ) {
		var name;
		for ( name in obj ) {
			return false;
		}
		return true;
	},

	isPlainObject: function( obj ) {
		var key;

		// Must be an Object.
		// Because of IE, we also have to check the presence of the constructor property.
		// Make sure that DOM nodes and window objects don't pass through, as well
		if ( !obj || jQuery.type( obj ) !== "object" || obj.nodeType || jQuery.isWindow( obj ) ) {
			return false;
		}

		try {

			// Not own constructor property must be Object
			if ( obj.constructor &&
				!hasOwn.call( obj, "constructor" ) &&
				!hasOwn.call( obj.constructor.prototype, "isPrototypeOf" ) ) {
				return false;
			}
		} catch ( e ) {

			// IE8,9 Will throw exceptions on certain host objects #9897
			return false;
		}

		// Support: IE<9
		// Handle iteration over inherited properties before own properties.
		if ( !support.ownFirst ) {
			for ( key in obj ) {
				return hasOwn.call( obj, key );
			}
		}

		// Own properties are enumerated firstly, so to speed up,
		// if last one is own, then all properties are own.
		for ( key in obj ) {}

		return key === undefined || hasOwn.call( obj, key );
	},

	type: function( obj ) {
		if ( obj == null ) {
			return obj + "";
		}
		return typeof obj === "object" || typeof obj === "function" ?
			class2type[ toString.call( obj ) ] || "object" :
			typeof obj;
	},

	// Workarounds based on findings by Jim Driscoll
	// http://weblogs.java.net/blog/driscoll/archive/2009/09/08/eval-javascript-global-context
	globalEval: function( data ) {
		if ( data && jQuery.trim( data ) ) {

			// We use execScript on Internet Explorer
			// We use an anonymous function so that context is window
			// rather than jQuery in Firefox
			( window.execScript || function( data ) {
				window[ "eval" ].call( window, data ); // jscs:ignore requireDotNotation
			} )( data );
		}
	},

	// Convert dashed to camelCase; used by the css and data modules
	// Microsoft forgot to hump their vendor prefix (#9572)
	camelCase: function( string ) {
		return string.replace( rmsPrefix, "ms-" ).replace( rdashAlpha, fcamelCase );
	},

	nodeName: function( elem, name ) {
		return elem.nodeName && elem.nodeName.toLowerCase() === name.toLowerCase();
	},

	each: function( obj, callback ) {
		var length, i = 0;

		if ( isArrayLike( obj ) ) {
			length = obj.length;
			for ( ; i < length; i++ ) {
				if ( callback.call( obj[ i ], i, obj[ i ] ) === false ) {
					break;
				}
			}
		} else {
			for ( i in obj ) {
				if ( callback.call( obj[ i ], i, obj[ i ] ) === false ) {
					break;
				}
			}
		}

		return obj;
	},

	// Support: Android<4.1, IE<9
	trim: function( text ) {
		return text == null ?
			"" :
			( text + "" ).replace( rtrim, "" );
	},

	// results is for internal usage only
	makeArray: function( arr, results ) {
		var ret = results || [];

		if ( arr != null ) {
			if ( isArrayLike( Object( arr ) ) ) {
				jQuery.merge( ret,
					typeof arr === "string" ?
					[ arr ] : arr
				);
			} else {
				push.call( ret, arr );
			}
		}

		return ret;
	},

	inArray: function( elem, arr, i ) {
		var len;

		if ( arr ) {
			if ( indexOf ) {
				return indexOf.call( arr, elem, i );
			}

			len = arr.length;
			i = i ? i < 0 ? Math.max( 0, len + i ) : i : 0;

			for ( ; i < len; i++ ) {

				// Skip accessing in sparse arrays
				if ( i in arr && arr[ i ] === elem ) {
					return i;
				}
			}
		}

		return -1;
	},

	merge: function( first, second ) {
		var len = +second.length,
			j = 0,
			i = first.length;

		while ( j < len ) {
			first[ i++ ] = second[ j++ ];
		}

		// Support: IE<9
		// Workaround casting of .length to NaN on otherwise arraylike objects (e.g., NodeLists)
		if ( len !== len ) {
			while ( second[ j ] !== undefined ) {
				first[ i++ ] = second[ j++ ];
			}
		}

		first.length = i;

		return first;
	},

	grep: function( elems, callback, invert ) {
		var callbackInverse,
			matches = [],
			i = 0,
			length = elems.length,
			callbackExpect = !invert;

		// Go through the array, only saving the items
		// that pass the validator function
		for ( ; i < length; i++ ) {
			callbackInverse = !callback( elems[ i ], i );
			if ( callbackInverse !== callbackExpect ) {
				matches.push( elems[ i ] );
			}
		}

		return matches;
	},

	// arg is for internal usage only
	map: function( elems, callback, arg ) {
		var length, value,
			i = 0,
			ret = [];

		// Go through the array, translating each of the items to their new values
		if ( isArrayLike( elems ) ) {
			length = elems.length;
			for ( ; i < length; i++ ) {
				value = callback( elems[ i ], i, arg );

				if ( value != null ) {
					ret.push( value );
				}
			}

		// Go through every key on the object,
		} else {
			for ( i in elems ) {
				value = callback( elems[ i ], i, arg );

				if ( value != null ) {
					ret.push( value );
				}
			}
		}

		// Flatten any nested arrays
		return concat.apply( [], ret );
	},

	// A global GUID counter for objects
	guid: 1,

	// Bind a function to a context, optionally partially applying any
	// arguments.
	proxy: function( fn, context ) {
		var args, proxy, tmp;

		if ( typeof context === "string" ) {
			tmp = fn[ context ];
			context = fn;
			fn = tmp;
		}

		// Quick check to determine if target is callable, in the spec
		// this throws a TypeError, but we will just return undefined.
		if ( !jQuery.isFunction( fn ) ) {
			return undefined;
		}

		// Simulated bind
		args = slice.call( arguments, 2 );
		proxy = function() {
			return fn.apply( context || this, args.concat( slice.call( arguments ) ) );
		};

		// Set the guid of unique handler to the same of original handler, so it can be removed
		proxy.guid = fn.guid = fn.guid || jQuery.guid++;

		return proxy;
	},

	now: function() {
		return +( new Date() );
	},

	// jQuery.support is not used in Core but other projects attach their
	// properties to it so it needs to exist.
	support: support
} );

// JSHint would error on this code due to the Symbol not being defined in ES5.
// Defining this global in .jshintrc would create a danger of using the global
// unguarded in another place, it seems safer to just disable JSHint for these
// three lines.
/* jshint ignore: start */
if ( typeof Symbol === "function" ) {
	jQuery.fn[ Symbol.iterator ] = deletedIds[ Symbol.iterator ];
}
/* jshint ignore: end */

// Populate the class2type map
jQuery.each( "Boolean Number String Function Array Date RegExp Object Error Symbol".split( " " ),
function( i, name ) {
	class2type[ "[object " + name + "]" ] = name.toLowerCase();
} );

function isArrayLike( obj ) {

	// Support: iOS 8.2 (not reproducible in simulator)
	// `in` check used to prevent JIT error (gh-2145)
	// hasOwn isn't used here due to false negatives
	// regarding Nodelist length in IE
	var length = !!obj && "length" in obj && obj.length,
		type = jQuery.type( obj );

	if ( type === "function" || jQuery.isWindow( obj ) ) {
		return false;
	}

	return type === "array" || length === 0 ||
		typeof length === "number" && length > 0 && ( length - 1 ) in obj;
}
var Sizzle =
/*!
 * Sizzle CSS Selector Engine v2.2.1
 * http://sizzlejs.com/
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license
 * http://jquery.org/license
 *
 * Date: 2015-10-17
 */
(function( window ) {

var i,
	support,
	Expr,
	getText,
	isXML,
	tokenize,
	compile,
	select,
	outermostContext,
	sortInput,
	hasDuplicate,

	// Local document vars
	setDocument,
	document,
	docElem,
	documentIsHTML,
	rbuggyQSA,
	rbuggyMatches,
	matches,
	contains,

	// Instance-specific data
	expando = "sizzle" + 1 * new Date(),
	preferredDoc = window.document,
	dirruns = 0,
	done = 0,
	classCache = createCache(),
	tokenCache = createCache(),
	compilerCache = createCache(),
	sortOrder = function( a, b ) {
		if ( a === b ) {
			hasDuplicate = true;
		}
		return 0;
	},

	// General-purpose constants
	MAX_NEGATIVE = 1 << 31,

	// Instance methods
	hasOwn = ({}).hasOwnProperty,
	arr = [],
	pop = arr.pop,
	push_native = arr.push,
	push = arr.push,
	slice = arr.slice,
	// Use a stripped-down indexOf as it's faster than native
	// http://jsperf.com/thor-indexof-vs-for/5
	indexOf = function( list, elem ) {
		var i = 0,
			len = list.length;
		for ( ; i < len; i++ ) {
			if ( list[i] === elem ) {
				return i;
			}
		}
		return -1;
	},

	booleans = "checked|selected|async|autofocus|autoplay|controls|defer|disabled|hidden|ismap|loop|multiple|open|readonly|required|scoped",

	// Regular expressions

	// http://www.w3.org/TR/css3-selectors/#whitespace
	whitespace = "[\\x20\\t\\r\\n\\f]",

	// http://www.w3.org/TR/CSS21/syndata.html#value-def-identifier
	identifier = "(?:\\\\.|[\\w-]|[^\\x00-\\xa0])+",

	// Attribute selectors: http://www.w3.org/TR/selectors/#attribute-selectors
	attributes = "\\[" + whitespace + "*(" + identifier + ")(?:" + whitespace +
		// Operator (capture 2)
		"*([*^$|!~]?=)" + whitespace +
		// "Attribute values must be CSS identifiers [capture 5] or strings [capture 3 or capture 4]"
		"*(?:'((?:\\\\.|[^\\\\'])*)'|\"((?:\\\\.|[^\\\\\"])*)\"|(" + identifier + "))|)" + whitespace +
		"*\\]",

	pseudos = ":(" + identifier + ")(?:\\((" +
		// To reduce the number of selectors needing tokenize in the preFilter, prefer arguments:
		// 1. quoted (capture 3; capture 4 or capture 5)
		"('((?:\\\\.|[^\\\\'])*)'|\"((?:\\\\.|[^\\\\\"])*)\")|" +
		// 2. simple (capture 6)
		"((?:\\\\.|[^\\\\()[\\]]|" + attributes + ")*)|" +
		// 3. anything else (capture 2)
		".*" +
		")\\)|)",

	// Leading and non-escaped trailing whitespace, capturing some non-whitespace characters preceding the latter
	rwhitespace = new RegExp( whitespace + "+", "g" ),
	rtrim = new RegExp( "^" + whitespace + "+|((?:^|[^\\\\])(?:\\\\.)*)" + whitespace + "+$", "g" ),

	rcomma = new RegExp( "^" + whitespace + "*," + whitespace + "*" ),
	rcombinators = new RegExp( "^" + whitespace + "*([>+~]|" + whitespace + ")" + whitespace + "*" ),

	rattributeQuotes = new RegExp( "=" + whitespace + "*([^\\]'\"]*?)" + whitespace + "*\\]", "g" ),

	rpseudo = new RegExp( pseudos ),
	ridentifier = new RegExp( "^" + identifier + "$" ),

	matchExpr = {
		"ID": new RegExp( "^#(" + identifier + ")" ),
		"CLASS": new RegExp( "^\\.(" + identifier + ")" ),
		"TAG": new RegExp( "^(" + identifier + "|[*])" ),
		"ATTR": new RegExp( "^" + attributes ),
		"PSEUDO": new RegExp( "^" + pseudos ),
		"CHILD": new RegExp( "^:(only|first|last|nth|nth-last)-(child|of-type)(?:\\(" + whitespace +
			"*(even|odd|(([+-]|)(\\d*)n|)" + whitespace + "*(?:([+-]|)" + whitespace +
			"*(\\d+)|))" + whitespace + "*\\)|)", "i" ),
		"bool": new RegExp( "^(?:" + booleans + ")$", "i" ),
		// For use in libraries implementing .is()
		// We use this for POS matching in `select`
		"needsContext": new RegExp( "^" + whitespace + "*[>+~]|:(even|odd|eq|gt|lt|nth|first|last)(?:\\(" +
			whitespace + "*((?:-\\d)?\\d*)" + whitespace + "*\\)|)(?=[^-]|$)", "i" )
	},

	rinputs = /^(?:input|select|textarea|button)$/i,
	rheader = /^h\d$/i,

	rnative = /^[^{]+\{\s*\[native \w/,

	// Easily-parseable/retrievable ID or TAG or CLASS selectors
	rquickExpr = /^(?:#([\w-]+)|(\w+)|\.([\w-]+))$/,

	rsibling = /[+~]/,
	rescape = /'|\\/g,

	// CSS escapes http://www.w3.org/TR/CSS21/syndata.html#escaped-characters
	runescape = new RegExp( "\\\\([\\da-f]{1,6}" + whitespace + "?|(" + whitespace + ")|.)", "ig" ),
	funescape = function( _, escaped, escapedWhitespace ) {
		var high = "0x" + escaped - 0x10000;
		// NaN means non-codepoint
		// Support: Firefox<24
		// Workaround erroneous numeric interpretation of +"0x"
		return high !== high || escapedWhitespace ?
			escaped :
			high < 0 ?
				// BMP codepoint
				String.fromCharCode( high + 0x10000 ) :
				// Supplemental Plane codepoint (surrogate pair)
				String.fromCharCode( high >> 10 | 0xD800, high & 0x3FF | 0xDC00 );
	},

	// Used for iframes
	// See setDocument()
	// Removing the function wrapper causes a "Permission Denied"
	// error in IE
	unloadHandler = function() {
		setDocument();
	};

// Optimize for push.apply( _, NodeList )
try {
	push.apply(
		(arr = slice.call( preferredDoc.childNodes )),
		preferredDoc.childNodes
	);
	// Support: Android<4.0
	// Detect silently failing push.apply
	arr[ preferredDoc.childNodes.length ].nodeType;
} catch ( e ) {
	push = { apply: arr.length ?

		// Leverage slice if possible
		function( target, els ) {
			push_native.apply( target, slice.call(els) );
		} :

		// Support: IE<9
		// Otherwise append directly
		function( target, els ) {
			var j = target.length,
				i = 0;
			// Can't trust NodeList.length
			while ( (target[j++] = els[i++]) ) {}
			target.length = j - 1;
		}
	};
}

function Sizzle( selector, context, results, seed ) {
	var m, i, elem, nid, nidselect, match, groups, newSelector,
		newContext = context && context.ownerDocument,

		// nodeType defaults to 9, since context defaults to document
		nodeType = context ? context.nodeType : 9;

	results = results || [];

	// Return early from calls with invalid selector or context
	if ( typeof selector !== "string" || !selector ||
		nodeType !== 1 && nodeType !== 9 && nodeType !== 11 ) {

		return results;
	}

	// Try to shortcut find operations (as opposed to filters) in HTML documents
	if ( !seed ) {

		if ( ( context ? context.ownerDocument || context : preferredDoc ) !== document ) {
			setDocument( context );
		}
		context = context || document;

		if ( documentIsHTML ) {

			// If the selector is sufficiently simple, try using a "get*By*" DOM method
			// (excepting DocumentFragment context, where the methods don't exist)
			if ( nodeType !== 11 && (match = rquickExpr.exec( selector )) ) {

				// ID selector
				if ( (m = match[1]) ) {

					// Document context
					if ( nodeType === 9 ) {
						if ( (elem = context.getElementById( m )) ) {

							// Support: IE, Opera, Webkit
							// TODO: identify versions
							// getElementById can match elements by name instead of ID
							if ( elem.id === m ) {
								results.push( elem );
								return results;
							}
						} else {
							return results;
						}

					// Element context
					} else {

						// Support: IE, Opera, Webkit
						// TODO: identify versions
						// getElementById can match elements by name instead of ID
						if ( newContext && (elem = newContext.getElementById( m )) &&
							contains( context, elem ) &&
							elem.id === m ) {

							results.push( elem );
							return results;
						}
					}

				// Type selector
				} else if ( match[2] ) {
					push.apply( results, context.getElementsByTagName( selector ) );
					return results;

				// Class selector
				} else if ( (m = match[3]) && support.getElementsByClassName &&
					context.getElementsByClassName ) {

					push.apply( results, context.getElementsByClassName( m ) );
					return results;
				}
			}

			// Take advantage of querySelectorAll
			if ( support.qsa &&
				!compilerCache[ selector + " " ] &&
				(!rbuggyQSA || !rbuggyQSA.test( selector )) ) {

				if ( nodeType !== 1 ) {
					newContext = context;
					newSelector = selector;

				// qSA looks outside Element context, which is not what we want
				// Thanks to Andrew Dupont for this workaround technique
				// Support: IE <=8
				// Exclude object elements
				} else if ( context.nodeName.toLowerCase() !== "object" ) {

					// Capture the context ID, setting it first if necessary
					if ( (nid = context.getAttribute( "id" )) ) {
						nid = nid.replace( rescape, "\\$&" );
					} else {
						context.setAttribute( "id", (nid = expando) );
					}

					// Prefix every selector in the list
					groups = tokenize( selector );
					i = groups.length;
					nidselect = ridentifier.test( nid ) ? "#" + nid : "[id='" + nid + "']";
					while ( i-- ) {
						groups[i] = nidselect + " " + toSelector( groups[i] );
					}
					newSelector = groups.join( "," );

					// Expand context for sibling selectors
					newContext = rsibling.test( selector ) && testContext( context.parentNode ) ||
						context;
				}

				if ( newSelector ) {
					try {
						push.apply( results,
							newContext.querySelectorAll( newSelector )
						);
						return results;
					} catch ( qsaError ) {
					} finally {
						if ( nid === expando ) {
							context.removeAttribute( "id" );
						}
					}
				}
			}
		}
	}

	// All others
	return select( selector.replace( rtrim, "$1" ), context, results, seed );
}

/**
 * Create key-value caches of limited size
 * @returns {function(string, object)} Returns the Object data after storing it on itself with
 *	property name the (space-suffixed) string and (if the cache is larger than Expr.cacheLength)
 *	deleting the oldest entry
 */
function createCache() {
	var keys = [];

	function cache( key, value ) {
		// Use (key + " ") to avoid collision with native prototype properties (see Issue #157)
		if ( keys.push( key + " " ) > Expr.cacheLength ) {
			// Only keep the most recent entries
			delete cache[ keys.shift() ];
		}
		return (cache[ key + " " ] = value);
	}
	return cache;
}

/**
 * Mark a function for special use by Sizzle
 * @param {Function} fn The function to mark
 */
function markFunction( fn ) {
	fn[ expando ] = true;
	return fn;
}

/**
 * Support testing using an element
 * @param {Function} fn Passed the created div and expects a boolean result
 */
function assert( fn ) {
	var div = document.createElement("div");

	try {
		return !!fn( div );
	} catch (e) {
		return false;
	} finally {
		// Remove from its parent by default
		if ( div.parentNode ) {
			div.parentNode.removeChild( div );
		}
		// release memory in IE
		div = null;
	}
}

/**
 * Adds the same handler for all of the specified attrs
 * @param {String} attrs Pipe-separated list of attributes
 * @param {Function} handler The method that will be applied
 */
function addHandle( attrs, handler ) {
	var arr = attrs.split("|"),
		i = arr.length;

	while ( i-- ) {
		Expr.attrHandle[ arr[i] ] = handler;
	}
}

/**
 * Checks document order of two siblings
 * @param {Element} a
 * @param {Element} b
 * @returns {Number} Returns less than 0 if a precedes b, greater than 0 if a follows b
 */
function siblingCheck( a, b ) {
	var cur = b && a,
		diff = cur && a.nodeType === 1 && b.nodeType === 1 &&
			( ~b.sourceIndex || MAX_NEGATIVE ) -
			( ~a.sourceIndex || MAX_NEGATIVE );

	// Use IE sourceIndex if available on both nodes
	if ( diff ) {
		return diff;
	}

	// Check if b follows a
	if ( cur ) {
		while ( (cur = cur.nextSibling) ) {
			if ( cur === b ) {
				return -1;
			}
		}
	}

	return a ? 1 : -1;
}

/**
 * Returns a function to use in pseudos for input types
 * @param {String} type
 */
function createInputPseudo( type ) {
	return function( elem ) {
		var name = elem.nodeName.toLowerCase();
		return name === "input" && elem.type === type;
	};
}

/**
 * Returns a function to use in pseudos for buttons
 * @param {String} type
 */
function createButtonPseudo( type ) {
	return function( elem ) {
		var name = elem.nodeName.toLowerCase();
		return (name === "input" || name === "button") && elem.type === type;
	};
}

/**
 * Returns a function to use in pseudos for positionals
 * @param {Function} fn
 */
function createPositionalPseudo( fn ) {
	return markFunction(function( argument ) {
		argument = +argument;
		return markFunction(function( seed, matches ) {
			var j,
				matchIndexes = fn( [], seed.length, argument ),
				i = matchIndexes.length;

			// Match elements found at the specified indexes
			while ( i-- ) {
				if ( seed[ (j = matchIndexes[i]) ] ) {
					seed[j] = !(matches[j] = seed[j]);
				}
			}
		});
	});
}

/**
 * Checks a node for validity as a Sizzle context
 * @param {Element|Object=} context
 * @returns {Element|Object|Boolean} The input node if acceptable, otherwise a falsy value
 */
function testContext( context ) {
	return context && typeof context.getElementsByTagName !== "undefined" && context;
}

// Expose support vars for convenience
support = Sizzle.support = {};

/**
 * Detects XML nodes
 * @param {Element|Object} elem An element or a document
 * @returns {Boolean} True iff elem is a non-HTML XML node
 */
isXML = Sizzle.isXML = function( elem ) {
	// documentElement is verified for cases where it doesn't yet exist
	// (such as loading iframes in IE - #4833)
	var documentElement = elem && (elem.ownerDocument || elem).documentElement;
	return documentElement ? documentElement.nodeName !== "HTML" : false;
};

/**
 * Sets document-related variables once based on the current document
 * @param {Element|Object} [doc] An element or document object to use to set the document
 * @returns {Object} Returns the current document
 */
setDocument = Sizzle.setDocument = function( node ) {
	var hasCompare, parent,
		doc = node ? node.ownerDocument || node : preferredDoc;

	// Return early if doc is invalid or already selected
	if ( doc === document || doc.nodeType !== 9 || !doc.documentElement ) {
		return document;
	}

	// Update global variables
	document = doc;
	docElem = document.documentElement;
	documentIsHTML = !isXML( document );

	// Support: IE 9-11, Edge
	// Accessing iframe documents after unload throws "permission denied" errors (jQuery #13936)
	if ( (parent = document.defaultView) && parent.top !== parent ) {
		// Support: IE 11
		if ( parent.addEventListener ) {
			parent.addEventListener( "unload", unloadHandler, false );

		// Support: IE 9 - 10 only
		} else if ( parent.attachEvent ) {
			parent.attachEvent( "onunload", unloadHandler );
		}
	}

	/* Attributes
	---------------------------------------------------------------------- */

	// Support: IE<8
	// Verify that getAttribute really returns attributes and not properties
	// (excepting IE8 booleans)
	support.attributes = assert(function( div ) {
		div.className = "i";
		return !div.getAttribute("className");
	});

	/* getElement(s)By*
	---------------------------------------------------------------------- */

	// Check if getElementsByTagName("*") returns only elements
	support.getElementsByTagName = assert(function( div ) {
		div.appendChild( document.createComment("") );
		return !div.getElementsByTagName("*").length;
	});

	// Support: IE<9
	support.getElementsByClassName = rnative.test( document.getElementsByClassName );

	// Support: IE<10
	// Check if getElementById returns elements by name
	// The broken getElementById methods don't pick up programatically-set names,
	// so use a roundabout getElementsByName test
	support.getById = assert(function( div ) {
		docElem.appendChild( div ).id = expando;
		return !document.getElementsByName || !document.getElementsByName( expando ).length;
	});

	// ID find and filter
	if ( support.getById ) {
		Expr.find["ID"] = function( id, context ) {
			if ( typeof context.getElementById !== "undefined" && documentIsHTML ) {
				var m = context.getElementById( id );
				return m ? [ m ] : [];
			}
		};
		Expr.filter["ID"] = function( id ) {
			var attrId = id.replace( runescape, funescape );
			return function( elem ) {
				return elem.getAttribute("id") === attrId;
			};
		};
	} else {
		// Support: IE6/7
		// getElementById is not reliable as a find shortcut
		delete Expr.find["ID"];

		Expr.filter["ID"] =  function( id ) {
			var attrId = id.replace( runescape, funescape );
			return function( elem ) {
				var node = typeof elem.getAttributeNode !== "undefined" &&
					elem.getAttributeNode("id");
				return node && node.value === attrId;
			};
		};
	}

	// Tag
	Expr.find["TAG"] = support.getElementsByTagName ?
		function( tag, context ) {
			if ( typeof context.getElementsByTagName !== "undefined" ) {
				return context.getElementsByTagName( tag );

			// DocumentFragment nodes don't have gEBTN
			} else if ( support.qsa ) {
				return context.querySelectorAll( tag );
			}
		} :

		function( tag, context ) {
			var elem,
				tmp = [],
				i = 0,
				// By happy coincidence, a (broken) gEBTN appears on DocumentFragment nodes too
				results = context.getElementsByTagName( tag );

			// Filter out possible comments
			if ( tag === "*" ) {
				while ( (elem = results[i++]) ) {
					if ( elem.nodeType === 1 ) {
						tmp.push( elem );
					}
				}

				return tmp;
			}
			return results;
		};

	// Class
	Expr.find["CLASS"] = support.getElementsByClassName && function( className, context ) {
		if ( typeof context.getElementsByClassName !== "undefined" && documentIsHTML ) {
			return context.getElementsByClassName( className );
		}
	};

	/* QSA/matchesSelector
	---------------------------------------------------------------------- */

	// QSA and matchesSelector support

	// matchesSelector(:active) reports false when true (IE9/Opera 11.5)
	rbuggyMatches = [];

	// qSa(:focus) reports false when true (Chrome 21)
	// We allow this because of a bug in IE8/9 that throws an error
	// whenever `document.activeElement` is accessed on an iframe
	// So, we allow :focus to pass through QSA all the time to avoid the IE error
	// See http://bugs.jquery.com/ticket/13378
	rbuggyQSA = [];

	if ( (support.qsa = rnative.test( document.querySelectorAll )) ) {
		// Build QSA regex
		// Regex strategy adopted from Diego Perini
		assert(function( div ) {
			// Select is set to empty string on purpose
			// This is to test IE's treatment of not explicitly
			// setting a boolean content attribute,
			// since its presence should be enough
			// http://bugs.jquery.com/ticket/12359
			docElem.appendChild( div ).innerHTML = "<a id='" + expando + "'></a>" +
				"<select id='" + expando + "-\r\\' msallowcapture=''>" +
				"<option selected=''></option></select>";

			// Support: IE8, Opera 11-12.16
			// Nothing should be selected when empty strings follow ^= or $= or *=
			// The test attribute must be unknown in Opera but "safe" for WinRT
			// http://msdn.microsoft.com/en-us/library/ie/hh465388.aspx#attribute_section
			if ( div.querySelectorAll("[msallowcapture^='']").length ) {
				rbuggyQSA.push( "[*^$]=" + whitespace + "*(?:''|\"\")" );
			}

			// Support: IE8
			// Boolean attributes and "value" are not treated correctly
			if ( !div.querySelectorAll("[selected]").length ) {
				rbuggyQSA.push( "\\[" + whitespace + "*(?:value|" + booleans + ")" );
			}

			// Support: Chrome<29, Android<4.4, Safari<7.0+, iOS<7.0+, PhantomJS<1.9.8+
			if ( !div.querySelectorAll( "[id~=" + expando + "-]" ).length ) {
				rbuggyQSA.push("~=");
			}

			// Webkit/Opera - :checked should return selected option elements
			// http://www.w3.org/TR/2011/REC-css3-selectors-20110929/#checked
			// IE8 throws error here and will not see later tests
			if ( !div.querySelectorAll(":checked").length ) {
				rbuggyQSA.push(":checked");
			}

			// Support: Safari 8+, iOS 8+
			// https://bugs.webkit.org/show_bug.cgi?id=136851
			// In-page `selector#id sibing-combinator selector` fails
			if ( !div.querySelectorAll( "a#" + expando + "+*" ).length ) {
				rbuggyQSA.push(".#.+[+~]");
			}
		});

		assert(function( div ) {
			// Support: Windows 8 Native Apps
			// The type and name attributes are restricted during .innerHTML assignment
			var input = document.createElement("input");
			input.setAttribute( "type", "hidden" );
			div.appendChild( input ).setAttribute( "name", "D" );

			// Support: IE8
			// Enforce case-sensitivity of name attribute
			if ( div.querySelectorAll("[name=d]").length ) {
				rbuggyQSA.push( "name" + whitespace + "*[*^$|!~]?=" );
			}

			// FF 3.5 - :enabled/:disabled and hidden elements (hidden elements are still enabled)
			// IE8 throws error here and will not see later tests
			if ( !div.querySelectorAll(":enabled").length ) {
				rbuggyQSA.push( ":enabled", ":disabled" );
			}

			// Opera 10-11 does not throw on post-comma invalid pseudos
			div.querySelectorAll("*,:x");
			rbuggyQSA.push(",.*:");
		});
	}

	if ( (support.matchesSelector = rnative.test( (matches = docElem.matches ||
		docElem.webkitMatchesSelector ||
		docElem.mozMatchesSelector ||
		docElem.oMatchesSelector ||
		docElem.msMatchesSelector) )) ) {

		assert(function( div ) {
			// Check to see if it's possible to do matchesSelector
			// on a disconnected node (IE 9)
			support.disconnectedMatch = matches.call( div, "div" );

			// This should fail with an exception
			// Gecko does not error, returns false instead
			matches.call( div, "[s!='']:x" );
			rbuggyMatches.push( "!=", pseudos );
		});
	}

	rbuggyQSA = rbuggyQSA.length && new RegExp( rbuggyQSA.join("|") );
	rbuggyMatches = rbuggyMatches.length && new RegExp( rbuggyMatches.join("|") );

	/* Contains
	---------------------------------------------------------------------- */
	hasCompare = rnative.test( docElem.compareDocumentPosition );

	// Element contains another
	// Purposefully self-exclusive
	// As in, an element does not contain itself
	contains = hasCompare || rnative.test( docElem.contains ) ?
		function( a, b ) {
			var adown = a.nodeType === 9 ? a.documentElement : a,
				bup = b && b.parentNode;
			return a === bup || !!( bup && bup.nodeType === 1 && (
				adown.contains ?
					adown.contains( bup ) :
					a.compareDocumentPosition && a.compareDocumentPosition( bup ) & 16
			));
		} :
		function( a, b ) {
			if ( b ) {
				while ( (b = b.parentNode) ) {
					if ( b === a ) {
						return true;
					}
				}
			}
			return false;
		};

	/* Sorting
	---------------------------------------------------------------------- */

	// Document order sorting
	sortOrder = hasCompare ?
	function( a, b ) {

		// Flag for duplicate removal
		if ( a === b ) {
			hasDuplicate = true;
			return 0;
		}

		// Sort on method existence if only one input has compareDocumentPosition
		var compare = !a.compareDocumentPosition - !b.compareDocumentPosition;
		if ( compare ) {
			return compare;
		}

		// Calculate position if both inputs belong to the same document
		compare = ( a.ownerDocument || a ) === ( b.ownerDocument || b ) ?
			a.compareDocumentPosition( b ) :

			// Otherwise we know they are disconnected
			1;

		// Disconnected nodes
		if ( compare & 1 ||
			(!support.sortDetached && b.compareDocumentPosition( a ) === compare) ) {

			// Choose the first element that is related to our preferred document
			if ( a === document || a.ownerDocument === preferredDoc && contains(preferredDoc, a) ) {
				return -1;
			}
			if ( b === document || b.ownerDocument === preferredDoc && contains(preferredDoc, b) ) {
				return 1;
			}

			// Maintain original order
			return sortInput ?
				( indexOf( sortInput, a ) - indexOf( sortInput, b ) ) :
				0;
		}

		return compare & 4 ? -1 : 1;
	} :
	function( a, b ) {
		// Exit early if the nodes are identical
		if ( a === b ) {
			hasDuplicate = true;
			return 0;
		}

		var cur,
			i = 0,
			aup = a.parentNode,
			bup = b.parentNode,
			ap = [ a ],
			bp = [ b ];

		// Parentless nodes are either documents or disconnected
		if ( !aup || !bup ) {
			return a === document ? -1 :
				b === document ? 1 :
				aup ? -1 :
				bup ? 1 :
				sortInput ?
				( indexOf( sortInput, a ) - indexOf( sortInput, b ) ) :
				0;

		// If the nodes are siblings, we can do a quick check
		} else if ( aup === bup ) {
			return siblingCheck( a, b );
		}

		// Otherwise we need full lists of their ancestors for comparison
		cur = a;
		while ( (cur = cur.parentNode) ) {
			ap.unshift( cur );
		}
		cur = b;
		while ( (cur = cur.parentNode) ) {
			bp.unshift( cur );
		}

		// Walk down the tree looking for a discrepancy
		while ( ap[i] === bp[i] ) {
			i++;
		}

		return i ?
			// Do a sibling check if the nodes have a common ancestor
			siblingCheck( ap[i], bp[i] ) :

			// Otherwise nodes in our document sort first
			ap[i] === preferredDoc ? -1 :
			bp[i] === preferredDoc ? 1 :
			0;
	};

	return document;
};

Sizzle.matches = function( expr, elements ) {
	return Sizzle( expr, null, null, elements );
};

Sizzle.matchesSelector = function( elem, expr ) {
	// Set document vars if needed
	if ( ( elem.ownerDocument || elem ) !== document ) {
		setDocument( elem );
	}

	// Make sure that attribute selectors are quoted
	expr = expr.replace( rattributeQuotes, "='$1']" );

	if ( support.matchesSelector && documentIsHTML &&
		!compilerCache[ expr + " " ] &&
		( !rbuggyMatches || !rbuggyMatches.test( expr ) ) &&
		( !rbuggyQSA     || !rbuggyQSA.test( expr ) ) ) {

		try {
			var ret = matches.call( elem, expr );

			// IE 9's matchesSelector returns false on disconnected nodes
			if ( ret || support.disconnectedMatch ||
					// As well, disconnected nodes are said to be in a document
					// fragment in IE 9
					elem.document && elem.document.nodeType !== 11 ) {
				return ret;
			}
		} catch (e) {}
	}

	return Sizzle( expr, document, null, [ elem ] ).length > 0;
};

Sizzle.contains = function( context, elem ) {
	// Set document vars if needed
	if ( ( context.ownerDocument || context ) !== document ) {
		setDocument( context );
	}
	return contains( context, elem );
};

Sizzle.attr = function( elem, name ) {
	// Set document vars if needed
	if ( ( elem.ownerDocument || elem ) !== document ) {
		setDocument( elem );
	}

	var fn = Expr.attrHandle[ name.toLowerCase() ],
		// Don't get fooled by Object.prototype properties (jQuery #13807)
		val = fn && hasOwn.call( Expr.attrHandle, name.toLowerCase() ) ?
			fn( elem, name, !documentIsHTML ) :
			undefined;

	return val !== undefined ?
		val :
		support.attributes || !documentIsHTML ?
			elem.getAttribute( name ) :
			(val = elem.getAttributeNode(name)) && val.specified ?
				val.value :
				null;
};

Sizzle.error = function( msg ) {
	throw new Error( "Syntax error, unrecognized expression: " + msg );
};

/**
 * Document sorting and removing duplicates
 * @param {ArrayLike} results
 */
Sizzle.uniqueSort = function( results ) {
	var elem,
		duplicates = [],
		j = 0,
		i = 0;

	// Unless we *know* we can detect duplicates, assume their presence
	hasDuplicate = !support.detectDuplicates;
	sortInput = !support.sortStable && results.slice( 0 );
	results.sort( sortOrder );

	if ( hasDuplicate ) {
		while ( (elem = results[i++]) ) {
			if ( elem === results[ i ] ) {
				j = duplicates.push( i );
			}
		}
		while ( j-- ) {
			results.splice( duplicates[ j ], 1 );
		}
	}

	// Clear input after sorting to release objects
	// See https://github.com/jquery/sizzle/pull/225
	sortInput = null;

	return results;
};

/**
 * Utility function for retrieving the text value of an array of DOM nodes
 * @param {Array|Element} elem
 */
getText = Sizzle.getText = function( elem ) {
	var node,
		ret = "",
		i = 0,
		nodeType = elem.nodeType;

	if ( !nodeType ) {
		// If no nodeType, this is expected to be an array
		while ( (node = elem[i++]) ) {
			// Do not traverse comment nodes
			ret += getText( node );
		}
	} else if ( nodeType === 1 || nodeType === 9 || nodeType === 11 ) {
		// Use textContent for elements
		// innerText usage removed for consistency of new lines (jQuery #11153)
		if ( typeof elem.textContent === "string" ) {
			return elem.textContent;
		} else {
			// Traverse its children
			for ( elem = elem.firstChild; elem; elem = elem.nextSibling ) {
				ret += getText( elem );
			}
		}
	} else if ( nodeType === 3 || nodeType === 4 ) {
		return elem.nodeValue;
	}
	// Do not include comment or processing instruction nodes

	return ret;
};

Expr = Sizzle.selectors = {

	// Can be adjusted by the user
	cacheLength: 50,

	createPseudo: markFunction,

	match: matchExpr,

	attrHandle: {},

	find: {},

	relative: {
		">": { dir: "parentNode", first: true },
		" ": { dir: "parentNode" },
		"+": { dir: "previousSibling", first: true },
		"~": { dir: "previousSibling" }
	},

	preFilter: {
		"ATTR": function( match ) {
			match[1] = match[1].replace( runescape, funescape );

			// Move the given value to match[3] whether quoted or unquoted
			match[3] = ( match[3] || match[4] || match[5] || "" ).replace( runescape, funescape );

			if ( match[2] === "~=" ) {
				match[3] = " " + match[3] + " ";
			}

			return match.slice( 0, 4 );
		},

		"CHILD": function( match ) {
			/* matches from matchExpr["CHILD"]
				1 type (only|nth|...)
				2 what (child|of-type)
				3 argument (even|odd|\d*|\d*n([+-]\d+)?|...)
				4 xn-component of xn+y argument ([+-]?\d*n|)
				5 sign of xn-component
				6 x of xn-component
				7 sign of y-component
				8 y of y-component
			*/
			match[1] = match[1].toLowerCase();

			if ( match[1].slice( 0, 3 ) === "nth" ) {
				// nth-* requires argument
				if ( !match[3] ) {
					Sizzle.error( match[0] );
				}

				// numeric x and y parameters for Expr.filter.CHILD
				// remember that false/true cast respectively to 0/1
				match[4] = +( match[4] ? match[5] + (match[6] || 1) : 2 * ( match[3] === "even" || match[3] === "odd" ) );
				match[5] = +( ( match[7] + match[8] ) || match[3] === "odd" );

			// other types prohibit arguments
			} else if ( match[3] ) {
				Sizzle.error( match[0] );
			}

			return match;
		},

		"PSEUDO": function( match ) {
			var excess,
				unquoted = !match[6] && match[2];

			if ( matchExpr["CHILD"].test( match[0] ) ) {
				return null;
			}

			// Accept quoted arguments as-is
			if ( match[3] ) {
				match[2] = match[4] || match[5] || "";

			// Strip excess characters from unquoted arguments
			} else if ( unquoted && rpseudo.test( unquoted ) &&
				// Get excess from tokenize (recursively)
				(excess = tokenize( unquoted, true )) &&
				// advance to the next closing parenthesis
				(excess = unquoted.indexOf( ")", unquoted.length - excess ) - unquoted.length) ) {

				// excess is a negative index
				match[0] = match[0].slice( 0, excess );
				match[2] = unquoted.slice( 0, excess );
			}

			// Return only captures needed by the pseudo filter method (type and argument)
			return match.slice( 0, 3 );
		}
	},

	filter: {

		"TAG": function( nodeNameSelector ) {
			var nodeName = nodeNameSelector.replace( runescape, funescape ).toLowerCase();
			return nodeNameSelector === "*" ?
				function() { return true; } :
				function( elem ) {
					return elem.nodeName && elem.nodeName.toLowerCase() === nodeName;
				};
		},

		"CLASS": function( className ) {
			var pattern = classCache[ className + " " ];

			return pattern ||
				(pattern = new RegExp( "(^|" + whitespace + ")" + className + "(" + whitespace + "|$)" )) &&
				classCache( className, function( elem ) {
					return pattern.test( typeof elem.className === "string" && elem.className || typeof elem.getAttribute !== "undefined" && elem.getAttribute("class") || "" );
				});
		},

		"ATTR": function( name, operator, check ) {
			return function( elem ) {
				var result = Sizzle.attr( elem, name );

				if ( result == null ) {
					return operator === "!=";
				}
				if ( !operator ) {
					return true;
				}

				result += "";

				return operator === "=" ? result === check :
					operator === "!=" ? result !== check :
					operator === "^=" ? check && result.indexOf( check ) === 0 :
					operator === "*=" ? check && result.indexOf( check ) > -1 :
					operator === "$=" ? check && result.slice( -check.length ) === check :
					operator === "~=" ? ( " " + result.replace( rwhitespace, " " ) + " " ).indexOf( check ) > -1 :
					operator === "|=" ? result === check || result.slice( 0, check.length + 1 ) === check + "-" :
					false;
			};
		},

		"CHILD": function( type, what, argument, first, last ) {
			var simple = type.slice( 0, 3 ) !== "nth",
				forward = type.slice( -4 ) !== "last",
				ofType = what === "of-type";

			return first === 1 && last === 0 ?

				// Shortcut for :nth-*(n)
				function( elem ) {
					return !!elem.parentNode;
				} :

				function( elem, context, xml ) {
					var cache, uniqueCache, outerCache, node, nodeIndex, start,
						dir = simple !== forward ? "nextSibling" : "previousSibling",
						parent = elem.parentNode,
						name = ofType && elem.nodeName.toLowerCase(),
						useCache = !xml && !ofType,
						diff = false;

					if ( parent ) {

						// :(first|last|only)-(child|of-type)
						if ( simple ) {
							while ( dir ) {
								node = elem;
								while ( (node = node[ dir ]) ) {
									if ( ofType ?
										node.nodeName.toLowerCase() === name :
										node.nodeType === 1 ) {

										return false;
									}
								}
								// Reverse direction for :only-* (if we haven't yet done so)
								start = dir = type === "only" && !start && "nextSibling";
							}
							return true;
						}

						start = [ forward ? parent.firstChild : parent.lastChild ];

						// non-xml :nth-child(...) stores cache data on `parent`
						if ( forward && useCache ) {

							// Seek `elem` from a previously-cached index

							// ...in a gzip-friendly way
							node = parent;
							outerCache = node[ expando ] || (node[ expando ] = {});

							// Support: IE <9 only
							// Defend against cloned attroperties (jQuery gh-1709)
							uniqueCache = outerCache[ node.uniqueID ] ||
								(outerCache[ node.uniqueID ] = {});

							cache = uniqueCache[ type ] || [];
							nodeIndex = cache[ 0 ] === dirruns && cache[ 1 ];
							diff = nodeIndex && cache[ 2 ];
							node = nodeIndex && parent.childNodes[ nodeIndex ];

							while ( (node = ++nodeIndex && node && node[ dir ] ||

								// Fallback to seeking `elem` from the start
								(diff = nodeIndex = 0) || start.pop()) ) {

								// When found, cache indexes on `parent` and break
								if ( node.nodeType === 1 && ++diff && node === elem ) {
									uniqueCache[ type ] = [ dirruns, nodeIndex, diff ];
									break;
								}
							}

						} else {
							// Use previously-cached element index if available
							if ( useCache ) {
								// ...in a gzip-friendly way
								node = elem;
								outerCache = node[ expando ] || (node[ expando ] = {});

								// Support: IE <9 only
								// Defend against cloned attroperties (jQuery gh-1709)
								uniqueCache = outerCache[ node.uniqueID ] ||
									(outerCache[ node.uniqueID ] = {});

								cache = uniqueCache[ type ] || [];
								nodeIndex = cache[ 0 ] === dirruns && cache[ 1 ];
								diff = nodeIndex;
							}

							// xml :nth-child(...)
							// or :nth-last-child(...) or :nth(-last)?-of-type(...)
							if ( diff === false ) {
								// Use the same loop as above to seek `elem` from the start
								while ( (node = ++nodeIndex && node && node[ dir ] ||
									(diff = nodeIndex = 0) || start.pop()) ) {

									if ( ( ofType ?
										node.nodeName.toLowerCase() === name :
										node.nodeType === 1 ) &&
										++diff ) {

										// Cache the index of each encountered element
										if ( useCache ) {
											outerCache = node[ expando ] || (node[ expando ] = {});

											// Support: IE <9 only
											// Defend against cloned attroperties (jQuery gh-1709)
											uniqueCache = outerCache[ node.uniqueID ] ||
												(outerCache[ node.uniqueID ] = {});

											uniqueCache[ type ] = [ dirruns, diff ];
										}

										if ( node === elem ) {
											break;
										}
									}
								}
							}
						}

						// Incorporate the offset, then check against cycle size
						diff -= last;
						return diff === first || ( diff % first === 0 && diff / first >= 0 );
					}
				};
		},

		"PSEUDO": function( pseudo, argument ) {
			// pseudo-class names are case-insensitive
			// http://www.w3.org/TR/selectors/#pseudo-classes
			// Prioritize by case sensitivity in case custom pseudos are added with uppercase letters
			// Remember that setFilters inherits from pseudos
			var args,
				fn = Expr.pseudos[ pseudo ] || Expr.setFilters[ pseudo.toLowerCase() ] ||
					Sizzle.error( "unsupported pseudo: " + pseudo );

			// The user may use createPseudo to indicate that
			// arguments are needed to create the filter function
			// just as Sizzle does
			if ( fn[ expando ] ) {
				return fn( argument );
			}

			// But maintain support for old signatures
			if ( fn.length > 1 ) {
				args = [ pseudo, pseudo, "", argument ];
				return Expr.setFilters.hasOwnProperty( pseudo.toLowerCase() ) ?
					markFunction(function( seed, matches ) {
						var idx,
							matched = fn( seed, argument ),
							i = matched.length;
						while ( i-- ) {
							idx = indexOf( seed, matched[i] );
							seed[ idx ] = !( matches[ idx ] = matched[i] );
						}
					}) :
					function( elem ) {
						return fn( elem, 0, args );
					};
			}

			return fn;
		}
	},

	pseudos: {
		// Potentially complex pseudos
		"not": markFunction(function( selector ) {
			// Trim the selector passed to compile
			// to avoid treating leading and trailing
			// spaces as combinators
			var input = [],
				results = [],
				matcher = compile( selector.replace( rtrim, "$1" ) );

			return matcher[ expando ] ?
				markFunction(function( seed, matches, context, xml ) {
					var elem,
						unmatched = matcher( seed, null, xml, [] ),
						i = seed.length;

					// Match elements unmatched by `matcher`
					while ( i-- ) {
						if ( (elem = unmatched[i]) ) {
							seed[i] = !(matches[i] = elem);
						}
					}
				}) :
				function( elem, context, xml ) {
					input[0] = elem;
					matcher( input, null, xml, results );
					// Don't keep the element (issue #299)
					input[0] = null;
					return !results.pop();
				};
		}),

		"has": markFunction(function( selector ) {
			return function( elem ) {
				return Sizzle( selector, elem ).length > 0;
			};
		}),

		"contains": markFunction(function( text ) {
			text = text.replace( runescape, funescape );
			return function( elem ) {
				return ( elem.textContent || elem.innerText || getText( elem ) ).indexOf( text ) > -1;
			};
		}),

		// "Whether an element is represented by a :lang() selector
		// is based solely on the element's language value
		// being equal to the identifier C,
		// or beginning with the identifier C immediately followed by "-".
		// The matching of C against the element's language value is performed case-insensitively.
		// The identifier C does not have to be a valid language name."
		// http://www.w3.org/TR/selectors/#lang-pseudo
		"lang": markFunction( function( lang ) {
			// lang value must be a valid identifier
			if ( !ridentifier.test(lang || "") ) {
				Sizzle.error( "unsupported lang: " + lang );
			}
			lang = lang.replace( runescape, funescape ).toLowerCase();
			return function( elem ) {
				var elemLang;
				do {
					if ( (elemLang = documentIsHTML ?
						elem.lang :
						elem.getAttribute("xml:lang") || elem.getAttribute("lang")) ) {

						elemLang = elemLang.toLowerCase();
						return elemLang === lang || elemLang.indexOf( lang + "-" ) === 0;
					}
				} while ( (elem = elem.parentNode) && elem.nodeType === 1 );
				return false;
			};
		}),

		// Miscellaneous
		"target": function( elem ) {
			var hash = window.location && window.location.hash;
			return hash && hash.slice( 1 ) === elem.id;
		},

		"root": function( elem ) {
			return elem === docElem;
		},

		"focus": function( elem ) {
			return elem === document.activeElement && (!document.hasFocus || document.hasFocus()) && !!(elem.type || elem.href || ~elem.tabIndex);
		},

		// Boolean properties
		"enabled": function( elem ) {
			return elem.disabled === false;
		},

		"disabled": function( elem ) {
			return elem.disabled === true;
		},

		"checked": function( elem ) {
			// In CSS3, :checked should return both checked and selected elements
			// http://www.w3.org/TR/2011/REC-css3-selectors-20110929/#checked
			var nodeName = elem.nodeName.toLowerCase();
			return (nodeName === "input" && !!elem.checked) || (nodeName === "option" && !!elem.selected);
		},

		"selected": function( elem ) {
			// Accessing this property makes selected-by-default
			// options in Safari work properly
			if ( elem.parentNode ) {
				elem.parentNode.selectedIndex;
			}

			return elem.selected === true;
		},

		// Contents
		"empty": function( elem ) {
			// http://www.w3.org/TR/selectors/#empty-pseudo
			// :empty is negated by element (1) or content nodes (text: 3; cdata: 4; entity ref: 5),
			//   but not by others (comment: 8; processing instruction: 7; etc.)
			// nodeType < 6 works because attributes (2) do not appear as children
			for ( elem = elem.firstChild; elem; elem = elem.nextSibling ) {
				if ( elem.nodeType < 6 ) {
					return false;
				}
			}
			return true;
		},

		"parent": function( elem ) {
			return !Expr.pseudos["empty"]( elem );
		},

		// Element/input types
		"header": function( elem ) {
			return rheader.test( elem.nodeName );
		},

		"input": function( elem ) {
			return rinputs.test( elem.nodeName );
		},

		"button": function( elem ) {
			var name = elem.nodeName.toLowerCase();
			return name === "input" && elem.type === "button" || name === "button";
		},

		"text": function( elem ) {
			var attr;
			return elem.nodeName.toLowerCase() === "input" &&
				elem.type === "text" &&

				// Support: IE<8
				// New HTML5 attribute values (e.g., "search") appear with elem.type === "text"
				( (attr = elem.getAttribute("type")) == null || attr.toLowerCase() === "text" );
		},

		// Position-in-collection
		"first": createPositionalPseudo(function() {
			return [ 0 ];
		}),

		"last": createPositionalPseudo(function( matchIndexes, length ) {
			return [ length - 1 ];
		}),

		"eq": createPositionalPseudo(function( matchIndexes, length, argument ) {
			return [ argument < 0 ? argument + length : argument ];
		}),

		"even": createPositionalPseudo(function( matchIndexes, length ) {
			var i = 0;
			for ( ; i < length; i += 2 ) {
				matchIndexes.push( i );
			}
			return matchIndexes;
		}),

		"odd": createPositionalPseudo(function( matchIndexes, length ) {
			var i = 1;
			for ( ; i < length; i += 2 ) {
				matchIndexes.push( i );
			}
			return matchIndexes;
		}),

		"lt": createPositionalPseudo(function( matchIndexes, length, argument ) {
			var i = argument < 0 ? argument + length : argument;
			for ( ; --i >= 0; ) {
				matchIndexes.push( i );
			}
			return matchIndexes;
		}),

		"gt": createPositionalPseudo(function( matchIndexes, length, argument ) {
			var i = argument < 0 ? argument + length : argument;
			for ( ; ++i < length; ) {
				matchIndexes.push( i );
			}
			return matchIndexes;
		})
	}
};

Expr.pseudos["nth"] = Expr.pseudos["eq"];

// Add button/input type pseudos
for ( i in { radio: true, checkbox: true, file: true, password: true, image: true } ) {
	Expr.pseudos[ i ] = createInputPseudo( i );
}
for ( i in { submit: true, reset: true } ) {
	Expr.pseudos[ i ] = createButtonPseudo( i );
}

// Easy API for creating new setFilters
function setFilters() {}
setFilters.prototype = Expr.filters = Expr.pseudos;
Expr.setFilters = new setFilters();

tokenize = Sizzle.tokenize = function( selector, parseOnly ) {
	var matched, match, tokens, type,
		soFar, groups, preFilters,
		cached = tokenCache[ selector + " " ];

	if ( cached ) {
		return parseOnly ? 0 : cached.slice( 0 );
	}

	soFar = selector;
	groups = [];
	preFilters = Expr.preFilter;

	while ( soFar ) {

		// Comma and first run
		if ( !matched || (match = rcomma.exec( soFar )) ) {
			if ( match ) {
				// Don't consume trailing commas as valid
				soFar = soFar.slice( match[0].length ) || soFar;
			}
			groups.push( (tokens = []) );
		}

		matched = false;

		// Combinators
		if ( (match = rcombinators.exec( soFar )) ) {
			matched = match.shift();
			tokens.push({
				value: matched,
				// Cast descendant combinators to space
				type: match[0].replace( rtrim, " " )
			});
			soFar = soFar.slice( matched.length );
		}

		// Filters
		for ( type in Expr.filter ) {
			if ( (match = matchExpr[ type ].exec( soFar )) && (!preFilters[ type ] ||
				(match = preFilters[ type ]( match ))) ) {
				matched = match.shift();
				tokens.push({
					value: matched,
					type: type,
					matches: match
				});
				soFar = soFar.slice( matched.length );
			}
		}

		if ( !matched ) {
			break;
		}
	}

	// Return the length of the invalid excess
	// if we're just parsing
	// Otherwise, throw an error or return tokens
	return parseOnly ?
		soFar.length :
		soFar ?
			Sizzle.error( selector ) :
			// Cache the tokens
			tokenCache( selector, groups ).slice( 0 );
};

function toSelector( tokens ) {
	var i = 0,
		len = tokens.length,
		selector = "";
	for ( ; i < len; i++ ) {
		selector += tokens[i].value;
	}
	return selector;
}

function addCombinator( matcher, combinator, base ) {
	var dir = combinator.dir,
		checkNonElements = base && dir === "parentNode",
		doneName = done++;

	return combinator.first ?
		// Check against closest ancestor/preceding element
		function( elem, context, xml ) {
			while ( (elem = elem[ dir ]) ) {
				if ( elem.nodeType === 1 || checkNonElements ) {
					return matcher( elem, context, xml );
				}
			}
		} :

		// Check against all ancestor/preceding elements
		function( elem, context, xml ) {
			var oldCache, uniqueCache, outerCache,
				newCache = [ dirruns, doneName ];

			// We can't set arbitrary data on XML nodes, so they don't benefit from combinator caching
			if ( xml ) {
				while ( (elem = elem[ dir ]) ) {
					if ( elem.nodeType === 1 || checkNonElements ) {
						if ( matcher( elem, context, xml ) ) {
							return true;
						}
					}
				}
			} else {
				while ( (elem = elem[ dir ]) ) {
					if ( elem.nodeType === 1 || checkNonElements ) {
						outerCache = elem[ expando ] || (elem[ expando ] = {});

						// Support: IE <9 only
						// Defend against cloned attroperties (jQuery gh-1709)
						uniqueCache = outerCache[ elem.uniqueID ] || (outerCache[ elem.uniqueID ] = {});

						if ( (oldCache = uniqueCache[ dir ]) &&
							oldCache[ 0 ] === dirruns && oldCache[ 1 ] === doneName ) {

							// Assign to newCache so results back-propagate to previous elements
							return (newCache[ 2 ] = oldCache[ 2 ]);
						} else {
							// Reuse newcache so results back-propagate to previous elements
							uniqueCache[ dir ] = newCache;

							// A match means we're done; a fail means we have to keep checking
							if ( (newCache[ 2 ] = matcher( elem, context, xml )) ) {
								return true;
							}
						}
					}
				}
			}
		};
}

function elementMatcher( matchers ) {
	return matchers.length > 1 ?
		function( elem, context, xml ) {
			var i = matchers.length;
			while ( i-- ) {
				if ( !matchers[i]( elem, context, xml ) ) {
					return false;
				}
			}
			return true;
		} :
		matchers[0];
}

function multipleContexts( selector, contexts, results ) {
	var i = 0,
		len = contexts.length;
	for ( ; i < len; i++ ) {
		Sizzle( selector, contexts[i], results );
	}
	return results;
}

function condense( unmatched, map, filter, context, xml ) {
	var elem,
		newUnmatched = [],
		i = 0,
		len = unmatched.length,
		mapped = map != null;

	for ( ; i < len; i++ ) {
		if ( (elem = unmatched[i]) ) {
			if ( !filter || filter( elem, context, xml ) ) {
				newUnmatched.push( elem );
				if ( mapped ) {
					map.push( i );
				}
			}
		}
	}

	return newUnmatched;
}

function setMatcher( preFilter, selector, matcher, postFilter, postFinder, postSelector ) {
	if ( postFilter && !postFilter[ expando ] ) {
		postFilter = setMatcher( postFilter );
	}
	if ( postFinder && !postFinder[ expando ] ) {
		postFinder = setMatcher( postFinder, postSelector );
	}
	return markFunction(function( seed, results, context, xml ) {
		var temp, i, elem,
			preMap = [],
			postMap = [],
			preexisting = results.length,

			// Get initial elements from seed or context
			elems = seed || multipleContexts( selector || "*", context.nodeType ? [ context ] : context, [] ),

			// Prefilter to get matcher input, preserving a map for seed-results synchronization
			matcherIn = preFilter && ( seed || !selector ) ?
				condense( elems, preMap, preFilter, context, xml ) :
				elems,

			matcherOut = matcher ?
				// If we have a postFinder, or filtered seed, or non-seed postFilter or preexisting results,
				postFinder || ( seed ? preFilter : preexisting || postFilter ) ?

					// ...intermediate processing is necessary
					[] :

					// ...otherwise use results directly
					results :
				matcherIn;

		// Find primary matches
		if ( matcher ) {
			matcher( matcherIn, matcherOut, context, xml );
		}

		// Apply postFilter
		if ( postFilter ) {
			temp = condense( matcherOut, postMap );
			postFilter( temp, [], context, xml );

			// Un-match failing elements by moving them back to matcherIn
			i = temp.length;
			while ( i-- ) {
				if ( (elem = temp[i]) ) {
					matcherOut[ postMap[i] ] = !(matcherIn[ postMap[i] ] = elem);
				}
			}
		}

		if ( seed ) {
			if ( postFinder || preFilter ) {
				if ( postFinder ) {
					// Get the final matcherOut by condensing this intermediate into postFinder contexts
					temp = [];
					i = matcherOut.length;
					while ( i-- ) {
						if ( (elem = matcherOut[i]) ) {
							// Restore matcherIn since elem is not yet a final match
							temp.push( (matcherIn[i] = elem) );
						}
					}
					postFinder( null, (matcherOut = []), temp, xml );
				}

				// Move matched elements from seed to results to keep them synchronized
				i = matcherOut.length;
				while ( i-- ) {
					if ( (elem = matcherOut[i]) &&
						(temp = postFinder ? indexOf( seed, elem ) : preMap[i]) > -1 ) {

						seed[temp] = !(results[temp] = elem);
					}
				}
			}

		// Add elements to results, through postFinder if defined
		} else {
			matcherOut = condense(
				matcherOut === results ?
					matcherOut.splice( preexisting, matcherOut.length ) :
					matcherOut
			);
			if ( postFinder ) {
				postFinder( null, results, matcherOut, xml );
			} else {
				push.apply( results, matcherOut );
			}
		}
	});
}

function matcherFromTokens( tokens ) {
	var checkContext, matcher, j,
		len = tokens.length,
		leadingRelative = Expr.relative[ tokens[0].type ],
		implicitRelative = leadingRelative || Expr.relative[" "],
		i = leadingRelative ? 1 : 0,

		// The foundational matcher ensures that elements are reachable from top-level context(s)
		matchContext = addCombinator( function( elem ) {
			return elem === checkContext;
		}, implicitRelative, true ),
		matchAnyContext = addCombinator( function( elem ) {
			return indexOf( checkContext, elem ) > -1;
		}, implicitRelative, true ),
		matchers = [ function( elem, context, xml ) {
			var ret = ( !leadingRelative && ( xml || context !== outermostContext ) ) || (
				(checkContext = context).nodeType ?
					matchContext( elem, context, xml ) :
					matchAnyContext( elem, context, xml ) );
			// Avoid hanging onto element (issue #299)
			checkContext = null;
			return ret;
		} ];

	for ( ; i < len; i++ ) {
		if ( (matcher = Expr.relative[ tokens[i].type ]) ) {
			matchers = [ addCombinator(elementMatcher( matchers ), matcher) ];
		} else {
			matcher = Expr.filter[ tokens[i].type ].apply( null, tokens[i].matches );

			// Return special upon seeing a positional matcher
			if ( matcher[ expando ] ) {
				// Find the next relative operator (if any) for proper handling
				j = ++i;
				for ( ; j < len; j++ ) {
					if ( Expr.relative[ tokens[j].type ] ) {
						break;
					}
				}
				return setMatcher(
					i > 1 && elementMatcher( matchers ),
					i > 1 && toSelector(
						// If the preceding token was a descendant combinator, insert an implicit any-element `*`
						tokens.slice( 0, i - 1 ).concat({ value: tokens[ i - 2 ].type === " " ? "*" : "" })
					).replace( rtrim, "$1" ),
					matcher,
					i < j && matcherFromTokens( tokens.slice( i, j ) ),
					j < len && matcherFromTokens( (tokens = tokens.slice( j )) ),
					j < len && toSelector( tokens )
				);
			}
			matchers.push( matcher );
		}
	}

	return elementMatcher( matchers );
}

function matcherFromGroupMatchers( elementMatchers, setMatchers ) {
	var bySet = setMatchers.length > 0,
		byElement = elementMatchers.length > 0,
		superMatcher = function( seed, context, xml, results, outermost ) {
			var elem, j, matcher,
				matchedCount = 0,
				i = "0",
				unmatched = seed && [],
				setMatched = [],
				contextBackup = outermostContext,
				// We must always have either seed elements or outermost context
				elems = seed || byElement && Expr.find["TAG"]( "*", outermost ),
				// Use integer dirruns iff this is the outermost matcher
				dirrunsUnique = (dirruns += contextBackup == null ? 1 : Math.random() || 0.1),
				len = elems.length;

			if ( outermost ) {
				outermostContext = context === document || context || outermost;
			}

			// Add elements passing elementMatchers directly to results
			// Support: IE<9, Safari
			// Tolerate NodeList properties (IE: "length"; Safari: <number>) matching elements by id
			for ( ; i !== len && (elem = elems[i]) != null; i++ ) {
				if ( byElement && elem ) {
					j = 0;
					if ( !context && elem.ownerDocument !== document ) {
						setDocument( elem );
						xml = !documentIsHTML;
					}
					while ( (matcher = elementMatchers[j++]) ) {
						if ( matcher( elem, context || document, xml) ) {
							results.push( elem );
							break;
						}
					}
					if ( outermost ) {
						dirruns = dirrunsUnique;
					}
				}

				// Track unmatched elements for set filters
				if ( bySet ) {
					// They will have gone through all possible matchers
					if ( (elem = !matcher && elem) ) {
						matchedCount--;
					}

					// Lengthen the array for every element, matched or not
					if ( seed ) {
						unmatched.push( elem );
					}
				}
			}

			// `i` is now the count of elements visited above, and adding it to `matchedCount`
			// makes the latter nonnegative.
			matchedCount += i;

			// Apply set filters to unmatched elements
			// NOTE: This can be skipped if there are no unmatched elements (i.e., `matchedCount`
			// equals `i`), unless we didn't visit _any_ elements in the above loop because we have
			// no element matchers and no seed.
			// Incrementing an initially-string "0" `i` allows `i` to remain a string only in that
			// case, which will result in a "00" `matchedCount` that differs from `i` but is also
			// numerically zero.
			if ( bySet && i !== matchedCount ) {
				j = 0;
				while ( (matcher = setMatchers[j++]) ) {
					matcher( unmatched, setMatched, context, xml );
				}

				if ( seed ) {
					// Reintegrate element matches to eliminate the need for sorting
					if ( matchedCount > 0 ) {
						while ( i-- ) {
							if ( !(unmatched[i] || setMatched[i]) ) {
								setMatched[i] = pop.call( results );
							}
						}
					}

					// Discard index placeholder values to get only actual matches
					setMatched = condense( setMatched );
				}

				// Add matches to results
				push.apply( results, setMatched );

				// Seedless set matches succeeding multiple successful matchers stipulate sorting
				if ( outermost && !seed && setMatched.length > 0 &&
					( matchedCount + setMatchers.length ) > 1 ) {

					Sizzle.uniqueSort( results );
				}
			}

			// Override manipulation of globals by nested matchers
			if ( outermost ) {
				dirruns = dirrunsUnique;
				outermostContext = contextBackup;
			}

			return unmatched;
		};

	return bySet ?
		markFunction( superMatcher ) :
		superMatcher;
}

compile = Sizzle.compile = function( selector, match /* Internal Use Only */ ) {
	var i,
		setMatchers = [],
		elementMatchers = [],
		cached = compilerCache[ selector + " " ];

	if ( !cached ) {
		// Generate a function of recursive functions that can be used to check each element
		if ( !match ) {
			match = tokenize( selector );
		}
		i = match.length;
		while ( i-- ) {
			cached = matcherFromTokens( match[i] );
			if ( cached[ expando ] ) {
				setMatchers.push( cached );
			} else {
				elementMatchers.push( cached );
			}
		}

		// Cache the compiled function
		cached = compilerCache( selector, matcherFromGroupMatchers( elementMatchers, setMatchers ) );

		// Save selector and tokenization
		cached.selector = selector;
	}
	return cached;
};

/**
 * A low-level selection function that works with Sizzle's compiled
 *  selector functions
 * @param {String|Function} selector A selector or a pre-compiled
 *  selector function built with Sizzle.compile
 * @param {Element} context
 * @param {Array} [results]
 * @param {Array} [seed] A set of elements to match against
 */
select = Sizzle.select = function( selector, context, results, seed ) {
	var i, tokens, token, type, find,
		compiled = typeof selector === "function" && selector,
		match = !seed && tokenize( (selector = compiled.selector || selector) );

	results = results || [];

	// Try to minimize operations if there is only one selector in the list and no seed
	// (the latter of which guarantees us context)
	if ( match.length === 1 ) {

		// Reduce context if the leading compound selector is an ID
		tokens = match[0] = match[0].slice( 0 );
		if ( tokens.length > 2 && (token = tokens[0]).type === "ID" &&
				support.getById && context.nodeType === 9 && documentIsHTML &&
				Expr.relative[ tokens[1].type ] ) {

			context = ( Expr.find["ID"]( token.matches[0].replace(runescape, funescape), context ) || [] )[0];
			if ( !context ) {
				return results;

			// Precompiled matchers will still verify ancestry, so step up a level
			} else if ( compiled ) {
				context = context.parentNode;
			}

			selector = selector.slice( tokens.shift().value.length );
		}

		// Fetch a seed set for right-to-left matching
		i = matchExpr["needsContext"].test( selector ) ? 0 : tokens.length;
		while ( i-- ) {
			token = tokens[i];

			// Abort if we hit a combinator
			if ( Expr.relative[ (type = token.type) ] ) {
				break;
			}
			if ( (find = Expr.find[ type ]) ) {
				// Search, expanding context for leading sibling combinators
				if ( (seed = find(
					token.matches[0].replace( runescape, funescape ),
					rsibling.test( tokens[0].type ) && testContext( context.parentNode ) || context
				)) ) {

					// If seed is empty or no tokens remain, we can return early
					tokens.splice( i, 1 );
					selector = seed.length && toSelector( tokens );
					if ( !selector ) {
						push.apply( results, seed );
						return results;
					}

					break;
				}
			}
		}
	}

	// Compile and execute a filtering function if one is not provided
	// Provide `match` to avoid retokenization if we modified the selector above
	( compiled || compile( selector, match ) )(
		seed,
		context,
		!documentIsHTML,
		results,
		!context || rsibling.test( selector ) && testContext( context.parentNode ) || context
	);
	return results;
};

// One-time assignments

// Sort stability
support.sortStable = expando.split("").sort( sortOrder ).join("") === expando;

// Support: Chrome 14-35+
// Always assume duplicates if they aren't passed to the comparison function
support.detectDuplicates = !!hasDuplicate;

// Initialize against the default document
setDocument();

// Support: Webkit<537.32 - Safari 6.0.3/Chrome 25 (fixed in Chrome 27)
// Detached nodes confoundingly follow *each other*
support.sortDetached = assert(function( div1 ) {
	// Should return 1, but returns 4 (following)
	return div1.compareDocumentPosition( document.createElement("div") ) & 1;
});

// Support: IE<8
// Prevent attribute/property "interpolation"
// http://msdn.microsoft.com/en-us/library/ms536429%28VS.85%29.aspx
if ( !assert(function( div ) {
	div.innerHTML = "<a href='#'></a>";
	return div.firstChild.getAttribute("href") === "#" ;
}) ) {
	addHandle( "type|href|height|width", function( elem, name, isXML ) {
		if ( !isXML ) {
			return elem.getAttribute( name, name.toLowerCase() === "type" ? 1 : 2 );
		}
	});
}

// Support: IE<9
// Use defaultValue in place of getAttribute("value")
if ( !support.attributes || !assert(function( div ) {
	div.innerHTML = "<input/>";
	div.firstChild.setAttribute( "value", "" );
	return div.firstChild.getAttribute( "value" ) === "";
}) ) {
	addHandle( "value", function( elem, name, isXML ) {
		if ( !isXML && elem.nodeName.toLowerCase() === "input" ) {
			return elem.defaultValue;
		}
	});
}

// Support: IE<9
// Use getAttributeNode to fetch booleans when getAttribute lies
if ( !assert(function( div ) {
	return div.getAttribute("disabled") == null;
}) ) {
	addHandle( booleans, function( elem, name, isXML ) {
		var val;
		if ( !isXML ) {
			return elem[ name ] === true ? name.toLowerCase() :
					(val = elem.getAttributeNode( name )) && val.specified ?
					val.value :
				null;
		}
	});
}

return Sizzle;

})( window );



jQuery.find = Sizzle;
jQuery.expr = Sizzle.selectors;
jQuery.expr[ ":" ] = jQuery.expr.pseudos;
jQuery.uniqueSort = jQuery.unique = Sizzle.uniqueSort;
jQuery.text = Sizzle.getText;
jQuery.isXMLDoc = Sizzle.isXML;
jQuery.contains = Sizzle.contains;



var dir = function( elem, dir, until ) {
	var matched = [],
		truncate = until !== undefined;

	while ( ( elem = elem[ dir ] ) && elem.nodeType !== 9 ) {
		if ( elem.nodeType === 1 ) {
			if ( truncate && jQuery( elem ).is( until ) ) {
				break;
			}
			matched.push( elem );
		}
	}
	return matched;
};


var siblings = function( n, elem ) {
	var matched = [];

	for ( ; n; n = n.nextSibling ) {
		if ( n.nodeType === 1 && n !== elem ) {
			matched.push( n );
		}
	}

	return matched;
};


var rneedsContext = jQuery.expr.match.needsContext;

var rsingleTag = ( /^<([\w-]+)\s*\/?>(?:<\/\1>|)$/ );



var risSimple = /^.[^:#\[\.,]*$/;

// Implement the identical functionality for filter and not
function winnow( elements, qualifier, not ) {
	if ( jQuery.isFunction( qualifier ) ) {
		return jQuery.grep( elements, function( elem, i ) {
			/* jshint -W018 */
			return !!qualifier.call( elem, i, elem ) !== not;
		} );

	}

	if ( qualifier.nodeType ) {
		return jQuery.grep( elements, function( elem ) {
			return ( elem === qualifier ) !== not;
		} );

	}

	if ( typeof qualifier === "string" ) {
		if ( risSimple.test( qualifier ) ) {
			return jQuery.filter( qualifier, elements, not );
		}

		qualifier = jQuery.filter( qualifier, elements );
	}

	return jQuery.grep( elements, function( elem ) {
		return ( jQuery.inArray( elem, qualifier ) > -1 ) !== not;
	} );
}

jQuery.filter = function( expr, elems, not ) {
	var elem = elems[ 0 ];

	if ( not ) {
		expr = ":not(" + expr + ")";
	}

	return elems.length === 1 && elem.nodeType === 1 ?
		jQuery.find.matchesSelector( elem, expr ) ? [ elem ] : [] :
		jQuery.find.matches( expr, jQuery.grep( elems, function( elem ) {
			return elem.nodeType === 1;
		} ) );
};

jQuery.fn.extend( {
	find: function( selector ) {
		var i,
			ret = [],
			self = this,
			len = self.length;

		if ( typeof selector !== "string" ) {
			return this.pushStack( jQuery( selector ).filter( function() {
				for ( i = 0; i < len; i++ ) {
					if ( jQuery.contains( self[ i ], this ) ) {
						return true;
					}
				}
			} ) );
		}

		for ( i = 0; i < len; i++ ) {
			jQuery.find( selector, self[ i ], ret );
		}

		// Needed because $( selector, context ) becomes $( context ).find( selector )
		ret = this.pushStack( len > 1 ? jQuery.unique( ret ) : ret );
		ret.selector = this.selector ? this.selector + " " + selector : selector;
		return ret;
	},
	filter: function( selector ) {
		return this.pushStack( winnow( this, selector || [], false ) );
	},
	not: function( selector ) {
		return this.pushStack( winnow( this, selector || [], true ) );
	},
	is: function( selector ) {
		return !!winnow(
			this,

			// If this is a positional/relative selector, check membership in the returned set
			// so $("p:first").is("p:last") won't return true for a doc with two "p".
			typeof selector === "string" && rneedsContext.test( selector ) ?
				jQuery( selector ) :
				selector || [],
			false
		).length;
	}
} );


// Initialize a jQuery object


// A central reference to the root jQuery(document)
var rootjQuery,

	// A simple way to check for HTML strings
	// Prioritize #id over <tag> to avoid XSS via location.hash (#9521)
	// Strict HTML recognition (#11290: must start with <)
	rquickExpr = /^(?:\s*(<[\w\W]+>)[^>]*|#([\w-]*))$/,

	init = jQuery.fn.init = function( selector, context, root ) {
		var match, elem;

		// HANDLE: $(""), $(null), $(undefined), $(false)
		if ( !selector ) {
			return this;
		}

		// init accepts an alternate rootjQuery
		// so migrate can support jQuery.sub (gh-2101)
		root = root || rootjQuery;

		// Handle HTML strings
		if ( typeof selector === "string" ) {
			if ( selector.charAt( 0 ) === "<" &&
				selector.charAt( selector.length - 1 ) === ">" &&
				selector.length >= 3 ) {

				// Assume that strings that start and end with <> are HTML and skip the regex check
				match = [ null, selector, null ];

			} else {
				match = rquickExpr.exec( selector );
			}

			// Match html or make sure no context is specified for #id
			if ( match && ( match[ 1 ] || !context ) ) {

				// HANDLE: $(html) -> $(array)
				if ( match[ 1 ] ) {
					context = context instanceof jQuery ? context[ 0 ] : context;

					// scripts is true for back-compat
					// Intentionally let the error be thrown if parseHTML is not present
					jQuery.merge( this, jQuery.parseHTML(
						match[ 1 ],
						context && context.nodeType ? context.ownerDocument || context : document,
						true
					) );

					// HANDLE: $(html, props)
					if ( rsingleTag.test( match[ 1 ] ) && jQuery.isPlainObject( context ) ) {
						for ( match in context ) {

							// Properties of context are called as methods if possible
							if ( jQuery.isFunction( this[ match ] ) ) {
								this[ match ]( context[ match ] );

							// ...and otherwise set as attributes
							} else {
								this.attr( match, context[ match ] );
							}
						}
					}

					return this;

				// HANDLE: $(#id)
				} else {
					elem = document.getElementById( match[ 2 ] );

					// Check parentNode to catch when Blackberry 4.6 returns
					// nodes that are no longer in the document #6963
					if ( elem && elem.parentNode ) {

						// Handle the case where IE and Opera return items
						// by name instead of ID
						if ( elem.id !== match[ 2 ] ) {
							return rootjQuery.find( selector );
						}

						// Otherwise, we inject the element directly into the jQuery object
						this.length = 1;
						this[ 0 ] = elem;
					}

					this.context = document;
					this.selector = selector;
					return this;
				}

			// HANDLE: $(expr, $(...))
			} else if ( !context || context.jquery ) {
				return ( context || root ).find( selector );

			// HANDLE: $(expr, context)
			// (which is just equivalent to: $(context).find(expr)
			} else {
				return this.constructor( context ).find( selector );
			}

		// HANDLE: $(DOMElement)
		} else if ( selector.nodeType ) {
			this.context = this[ 0 ] = selector;
			this.length = 1;
			return this;

		// HANDLE: $(function)
		// Shortcut for document ready
		} else if ( jQuery.isFunction( selector ) ) {
			return typeof root.ready !== "undefined" ?
				root.ready( selector ) :

				// Execute immediately if ready is not present
				selector( jQuery );
		}

		if ( selector.selector !== undefined ) {
			this.selector = selector.selector;
			this.context = selector.context;
		}

		return jQuery.makeArray( selector, this );
	};

// Give the init function the jQuery prototype for later instantiation
init.prototype = jQuery.fn;

// Initialize central reference
rootjQuery = jQuery( document );


var rparentsprev = /^(?:parents|prev(?:Until|All))/,

	// methods guaranteed to produce a unique set when starting from a unique set
	guaranteedUnique = {
		children: true,
		contents: true,
		next: true,
		prev: true
	};

jQuery.fn.extend( {
	has: function( target ) {
		var i,
			targets = jQuery( target, this ),
			len = targets.length;

		return this.filter( function() {
			for ( i = 0; i < len; i++ ) {
				if ( jQuery.contains( this, targets[ i ] ) ) {
					return true;
				}
			}
		} );
	},

	closest: function( selectors, context ) {
		var cur,
			i = 0,
			l = this.length,
			matched = [],
			pos = rneedsContext.test( selectors ) || typeof selectors !== "string" ?
				jQuery( selectors, context || this.context ) :
				0;

		for ( ; i < l; i++ ) {
			for ( cur = this[ i ]; cur && cur !== context; cur = cur.parentNode ) {

				// Always skip document fragments
				if ( cur.nodeType < 11 && ( pos ?
					pos.index( cur ) > -1 :

					// Don't pass non-elements to Sizzle
					cur.nodeType === 1 &&
						jQuery.find.matchesSelector( cur, selectors ) ) ) {

					matched.push( cur );
					break;
				}
			}
		}

		return this.pushStack( matched.length > 1 ? jQuery.uniqueSort( matched ) : matched );
	},

	// Determine the position of an element within
	// the matched set of elements
	index: function( elem ) {

		// No argument, return index in parent
		if ( !elem ) {
			return ( this[ 0 ] && this[ 0 ].parentNode ) ? this.first().prevAll().length : -1;
		}

		// index in selector
		if ( typeof elem === "string" ) {
			return jQuery.inArray( this[ 0 ], jQuery( elem ) );
		}

		// Locate the position of the desired element
		return jQuery.inArray(

			// If it receives a jQuery object, the first element is used
			elem.jquery ? elem[ 0 ] : elem, this );
	},

	add: function( selector, context ) {
		return this.pushStack(
			jQuery.uniqueSort(
				jQuery.merge( this.get(), jQuery( selector, context ) )
			)
		);
	},

	addBack: function( selector ) {
		return this.add( selector == null ?
			this.prevObject : this.prevObject.filter( selector )
		);
	}
} );

function sibling( cur, dir ) {
	do {
		cur = cur[ dir ];
	} while ( cur && cur.nodeType !== 1 );

	return cur;
}

jQuery.each( {
	parent: function( elem ) {
		var parent = elem.parentNode;
		return parent && parent.nodeType !== 11 ? parent : null;
	},
	parents: function( elem ) {
		return dir( elem, "parentNode" );
	},
	parentsUntil: function( elem, i, until ) {
		return dir( elem, "parentNode", until );
	},
	next: function( elem ) {
		return sibling( elem, "nextSibling" );
	},
	prev: function( elem ) {
		return sibling( elem, "previousSibling" );
	},
	nextAll: function( elem ) {
		return dir( elem, "nextSibling" );
	},
	prevAll: function( elem ) {
		return dir( elem, "previousSibling" );
	},
	nextUntil: function( elem, i, until ) {
		return dir( elem, "nextSibling", until );
	},
	prevUntil: function( elem, i, until ) {
		return dir( elem, "previousSibling", until );
	},
	siblings: function( elem ) {
		return siblings( ( elem.parentNode || {} ).firstChild, elem );
	},
	children: function( elem ) {
		return siblings( elem.firstChild );
	},
	contents: function( elem ) {
		return jQuery.nodeName( elem, "iframe" ) ?
			elem.contentDocument || elem.contentWindow.document :
			jQuery.merge( [], elem.childNodes );
	}
}, function( name, fn ) {
	jQuery.fn[ name ] = function( until, selector ) {
		var ret = jQuery.map( this, fn, until );

		if ( name.slice( -5 ) !== "Until" ) {
			selector = until;
		}

		if ( selector && typeof selector === "string" ) {
			ret = jQuery.filter( selector, ret );
		}

		if ( this.length > 1 ) {

			// Remove duplicates
			if ( !guaranteedUnique[ name ] ) {
				ret = jQuery.uniqueSort( ret );
			}

			// Reverse order for parents* and prev-derivatives
			if ( rparentsprev.test( name ) ) {
				ret = ret.reverse();
			}
		}

		return this.pushStack( ret );
	};
} );
var rnotwhite = ( /\S+/g );



// Convert String-formatted options into Object-formatted ones
function createOptions( options ) {
	var object = {};
	jQuery.each( options.match( rnotwhite ) || [], function( _, flag ) {
		object[ flag ] = true;
	} );
	return object;
}

/*
 * Create a callback list using the following parameters:
 *
 *	options: an optional list of space-separated options that will change how
 *			the callback list behaves or a more traditional option object
 *
 * By default a callback list will act like an event callback list and can be
 * "fired" multiple times.
 *
 * Possible options:
 *
 *	once:			will ensure the callback list can only be fired once (like a Deferred)
 *
 *	memory:			will keep track of previous values and will call any callback added
 *					after the list has been fired right away with the latest "memorized"
 *					values (like a Deferred)
 *
 *	unique:			will ensure a callback can only be added once (no duplicate in the list)
 *
 *	stopOnFalse:	interrupt callings when a callback returns false
 *
 */
jQuery.Callbacks = function( options ) {

	// Convert options from String-formatted to Object-formatted if needed
	// (we check in cache first)
	options = typeof options === "string" ?
		createOptions( options ) :
		jQuery.extend( {}, options );

	var // Flag to know if list is currently firing
		firing,

		// Last fire value for non-forgettable lists
		memory,

		// Flag to know if list was already fired
		fired,

		// Flag to prevent firing
		locked,

		// Actual callback list
		list = [],

		// Queue of execution data for repeatable lists
		queue = [],

		// Index of currently firing callback (modified by add/remove as needed)
		firingIndex = -1,

		// Fire callbacks
		fire = function() {

			// Enforce single-firing
			locked = options.once;

			// Execute callbacks for all pending executions,
			// respecting firingIndex overrides and runtime changes
			fired = firing = true;
			for ( ; queue.length; firingIndex = -1 ) {
				memory = queue.shift();
				while ( ++firingIndex < list.length ) {

					// Run callback and check for early termination
					if ( list[ firingIndex ].apply( memory[ 0 ], memory[ 1 ] ) === false &&
						options.stopOnFalse ) {

						// Jump to end and forget the data so .add doesn't re-fire
						firingIndex = list.length;
						memory = false;
					}
				}
			}

			// Forget the data if we're done with it
			if ( !options.memory ) {
				memory = false;
			}

			firing = false;

			// Clean up if we're done firing for good
			if ( locked ) {

				// Keep an empty list if we have data for future add calls
				if ( memory ) {
					list = [];

				// Otherwise, this object is spent
				} else {
					list = "";
				}
			}
		},

		// Actual Callbacks object
		self = {

			// Add a callback or a collection of callbacks to the list
			add: function() {
				if ( list ) {

					// If we have memory from a past run, we should fire after adding
					if ( memory && !firing ) {
						firingIndex = list.length - 1;
						queue.push( memory );
					}

					( function add( args ) {
						jQuery.each( args, function( _, arg ) {
							if ( jQuery.isFunction( arg ) ) {
								if ( !options.unique || !self.has( arg ) ) {
									list.push( arg );
								}
							} else if ( arg && arg.length && jQuery.type( arg ) !== "string" ) {

								// Inspect recursively
								add( arg );
							}
						} );
					} )( arguments );

					if ( memory && !firing ) {
						fire();
					}
				}
				return this;
			},

			// Remove a callback from the list
			remove: function() {
				jQuery.each( arguments, function( _, arg ) {
					var index;
					while ( ( index = jQuery.inArray( arg, list, index ) ) > -1 ) {
						list.splice( index, 1 );

						// Handle firing indexes
						if ( index <= firingIndex ) {
							firingIndex--;
						}
					}
				} );
				return this;
			},

			// Check if a given callback is in the list.
			// If no argument is given, return whether or not list has callbacks attached.
			has: function( fn ) {
				return fn ?
					jQuery.inArray( fn, list ) > -1 :
					list.length > 0;
			},

			// Remove all callbacks from the list
			empty: function() {
				if ( list ) {
					list = [];
				}
				return this;
			},

			// Disable .fire and .add
			// Abort any current/pending executions
			// Clear all callbacks and values
			disable: function() {
				locked = queue = [];
				list = memory = "";
				return this;
			},
			disabled: function() {
				return !list;
			},

			// Disable .fire
			// Also disable .add unless we have memory (since it would have no effect)
			// Abort any pending executions
			lock: function() {
				locked = true;
				if ( !memory ) {
					self.disable();
				}
				return this;
			},
			locked: function() {
				return !!locked;
			},

			// Call all callbacks with the given context and arguments
			fireWith: function( context, args ) {
				if ( !locked ) {
					args = args || [];
					args = [ context, args.slice ? args.slice() : args ];
					queue.push( args );
					if ( !firing ) {
						fire();
					}
				}
				return this;
			},

			// Call all the callbacks with the given arguments
			fire: function() {
				self.fireWith( this, arguments );
				return this;
			},

			// To know if the callbacks have already been called at least once
			fired: function() {
				return !!fired;
			}
		};

	return self;
};


jQuery.extend( {

	Deferred: function( func ) {
		var tuples = [

				// action, add listener, listener list, final state
				[ "resolve", "done", jQuery.Callbacks( "once memory" ), "resolved" ],
				[ "reject", "fail", jQuery.Callbacks( "once memory" ), "rejected" ],
				[ "notify", "progress", jQuery.Callbacks( "memory" ) ]
			],
			state = "pending",
			promise = {
				state: function() {
					return state;
				},
				always: function() {
					deferred.done( arguments ).fail( arguments );
					return this;
				},
				then: function( /* fnDone, fnFail, fnProgress */ ) {
					var fns = arguments;
					return jQuery.Deferred( function( newDefer ) {
						jQuery.each( tuples, function( i, tuple ) {
							var fn = jQuery.isFunction( fns[ i ] ) && fns[ i ];

							// deferred[ done | fail | progress ] for forwarding actions to newDefer
							deferred[ tuple[ 1 ] ]( function() {
								var returned = fn && fn.apply( this, arguments );
								if ( returned && jQuery.isFunction( returned.promise ) ) {
									returned.promise()
										.progress( newDefer.notify )
										.done( newDefer.resolve )
										.fail( newDefer.reject );
								} else {
									newDefer[ tuple[ 0 ] + "With" ](
										this === promise ? newDefer.promise() : this,
										fn ? [ returned ] : arguments
									);
								}
							} );
						} );
						fns = null;
					} ).promise();
				},

				// Get a promise for this deferred
				// If obj is provided, the promise aspect is added to the object
				promise: function( obj ) {
					return obj != null ? jQuery.extend( obj, promise ) : promise;
				}
			},
			deferred = {};

		// Keep pipe for back-compat
		promise.pipe = promise.then;

		// Add list-specific methods
		jQuery.each( tuples, function( i, tuple ) {
			var list = tuple[ 2 ],
				stateString = tuple[ 3 ];

			// promise[ done | fail | progress ] = list.add
			promise[ tuple[ 1 ] ] = list.add;

			// Handle state
			if ( stateString ) {
				list.add( function() {

					// state = [ resolved | rejected ]
					state = stateString;

				// [ reject_list | resolve_list ].disable; progress_list.lock
				}, tuples[ i ^ 1 ][ 2 ].disable, tuples[ 2 ][ 2 ].lock );
			}

			// deferred[ resolve | reject | notify ]
			deferred[ tuple[ 0 ] ] = function() {
				deferred[ tuple[ 0 ] + "With" ]( this === deferred ? promise : this, arguments );
				return this;
			};
			deferred[ tuple[ 0 ] + "With" ] = list.fireWith;
		} );

		// Make the deferred a promise
		promise.promise( deferred );

		// Call given func if any
		if ( func ) {
			func.call( deferred, deferred );
		}

		// All done!
		return deferred;
	},

	// Deferred helper
	when: function( subordinate /* , ..., subordinateN */ ) {
		var i = 0,
			resolveValues = slice.call( arguments ),
			length = resolveValues.length,

			// the count of uncompleted subordinates
			remaining = length !== 1 ||
				( subordinate && jQuery.isFunction( subordinate.promise ) ) ? length : 0,

			// the master Deferred.
			// If resolveValues consist of only a single Deferred, just use that.
			deferred = remaining === 1 ? subordinate : jQuery.Deferred(),

			// Update function for both resolve and progress values
			updateFunc = function( i, contexts, values ) {
				return function( value ) {
					contexts[ i ] = this;
					values[ i ] = arguments.length > 1 ? slice.call( arguments ) : value;
					if ( values === progressValues ) {
						deferred.notifyWith( contexts, values );

					} else if ( !( --remaining ) ) {
						deferred.resolveWith( contexts, values );
					}
				};
			},

			progressValues, progressContexts, resolveContexts;

		// add listeners to Deferred subordinates; treat others as resolved
		if ( length > 1 ) {
			progressValues = new Array( length );
			progressContexts = new Array( length );
			resolveContexts = new Array( length );
			for ( ; i < length; i++ ) {
				if ( resolveValues[ i ] && jQuery.isFunction( resolveValues[ i ].promise ) ) {
					resolveValues[ i ].promise()
						.progress( updateFunc( i, progressContexts, progressValues ) )
						.done( updateFunc( i, resolveContexts, resolveValues ) )
						.fail( deferred.reject );
				} else {
					--remaining;
				}
			}
		}

		// if we're not waiting on anything, resolve the master
		if ( !remaining ) {
			deferred.resolveWith( resolveContexts, resolveValues );
		}

		return deferred.promise();
	}
} );


// The deferred used on DOM ready
var readyList;

jQuery.fn.ready = function( fn ) {

	// Add the callback
	jQuery.ready.promise().done( fn );

	return this;
};

jQuery.extend( {

	// Is the DOM ready to be used? Set to true once it occurs.
	isReady: false,

	// A counter to track how many items to wait for before
	// the ready event fires. See #6781
	readyWait: 1,

	// Hold (or release) the ready event
	holdReady: function( hold ) {
		if ( hold ) {
			jQuery.readyWait++;
		} else {
			jQuery.ready( true );
		}
	},

	// Handle when the DOM is ready
	ready: function( wait ) {

		// Abort if there are pending holds or we're already ready
		if ( wait === true ? --jQuery.readyWait : jQuery.isReady ) {
			return;
		}

		// Remember that the DOM is ready
		jQuery.isReady = true;

		// If a normal DOM Ready event fired, decrement, and wait if need be
		if ( wait !== true && --jQuery.readyWait > 0 ) {
			return;
		}

		// If there are functions bound, to execute
		readyList.resolveWith( document, [ jQuery ] );

		// Trigger any bound ready events
		if ( jQuery.fn.triggerHandler ) {
			jQuery( document ).triggerHandler( "ready" );
			jQuery( document ).off( "ready" );
		}
	}
} );

/**
 * Clean-up method for dom ready events
 */
function detach() {
	if ( document.addEventListener ) {
		document.removeEventListener( "DOMContentLoaded", completed );
		window.removeEventListener( "load", completed );

	} else {
		document.detachEvent( "onreadystatechange", completed );
		window.detachEvent( "onload", completed );
	}
}

/**
 * The ready event handler and self cleanup method
 */
function completed() {

	// readyState === "complete" is good enough for us to call the dom ready in oldIE
	if ( document.addEventListener ||
		window.event.type === "load" ||
		document.readyState === "complete" ) {

		detach();
		jQuery.ready();
	}
}

jQuery.ready.promise = function( obj ) {
	if ( !readyList ) {

		readyList = jQuery.Deferred();

		// Catch cases where $(document).ready() is called
		// after the browser event has already occurred.
		// Support: IE6-10
		// Older IE sometimes signals "interactive" too soon
		if ( document.readyState === "complete" ||
			( document.readyState !== "loading" && !document.documentElement.doScroll ) ) {

			// Handle it asynchronously to allow scripts the opportunity to delay ready
			window.setTimeout( jQuery.ready );

		// Standards-based browsers support DOMContentLoaded
		} else if ( document.addEventListener ) {

			// Use the handy event callback
			document.addEventListener( "DOMContentLoaded", completed );

			// A fallback to window.onload, that will always work
			window.addEventListener( "load", completed );

		// If IE event model is used
		} else {

			// Ensure firing before onload, maybe late but safe also for iframes
			document.attachEvent( "onreadystatechange", completed );

			// A fallback to window.onload, that will always work
			window.attachEvent( "onload", completed );

			// If IE and not a frame
			// continually check to see if the document is ready
			var top = false;

			try {
				top = window.frameElement == null && document.documentElement;
			} catch ( e ) {}

			if ( top && top.doScroll ) {
				( function doScrollCheck() {
					if ( !jQuery.isReady ) {

						try {

							// Use the trick by Diego Perini
							// http://javascript.nwbox.com/IEContentLoaded/
							top.doScroll( "left" );
						} catch ( e ) {
							return window.setTimeout( doScrollCheck, 50 );
						}

						// detach all dom ready events
						detach();

						// and execute any waiting functions
						jQuery.ready();
					}
				} )();
			}
		}
	}
	return readyList.promise( obj );
};

// Kick off the DOM ready check even if the user does not
jQuery.ready.promise();




// Support: IE<9
// Iteration over object's inherited properties before its own
var i;
for ( i in jQuery( support ) ) {
	break;
}
support.ownFirst = i === "0";

// Note: most support tests are defined in their respective modules.
// false until the test is run
support.inlineBlockNeedsLayout = false;

// Execute ASAP in case we need to set body.style.zoom
jQuery( function() {

	// Minified: var a,b,c,d
	var val, div, body, container;

	body = document.getElementsByTagName( "body" )[ 0 ];
	if ( !body || !body.style ) {

		// Return for frameset docs that don't have a body
		return;
	}

	// Setup
	div = document.createElement( "div" );
	container = document.createElement( "div" );
	container.style.cssText = "position:absolute;border:0;width:0;height:0;top:0;left:-9999px";
	body.appendChild( container ).appendChild( div );

	if ( typeof div.style.zoom !== "undefined" ) {

		// Support: IE<8
		// Check if natively block-level elements act like inline-block
		// elements when setting their display to 'inline' and giving
		// them layout
		div.style.cssText = "display:inline;margin:0;border:0;padding:1px;width:1px;zoom:1";

		support.inlineBlockNeedsLayout = val = div.offsetWidth === 3;
		if ( val ) {

			// Prevent IE 6 from affecting layout for positioned elements #11048
			// Prevent IE from shrinking the body in IE 7 mode #12869
			// Support: IE<8
			body.style.zoom = 1;
		}
	}

	body.removeChild( container );
} );


( function() {
	var div = document.createElement( "div" );

	// Support: IE<9
	support.deleteExpando = true;
	try {
		delete div.test;
	} catch ( e ) {
		support.deleteExpando = false;
	}

	// Null elements to avoid leaks in IE.
	div = null;
} )();
var acceptData = function( elem ) {
	var noData = jQuery.noData[ ( elem.nodeName + " " ).toLowerCase() ],
		nodeType = +elem.nodeType || 1;

	// Do not set data on non-element DOM nodes because it will not be cleared (#8335).
	return nodeType !== 1 && nodeType !== 9 ?
		false :

		// Nodes accept data unless otherwise specified; rejection can be conditional
		!noData || noData !== true && elem.getAttribute( "classid" ) === noData;
};




var rbrace = /^(?:\{[\w\W]*\}|\[[\w\W]*\])$/,
	rmultiDash = /([A-Z])/g;

function dataAttr( elem, key, data ) {

	// If nothing was found internally, try to fetch any
	// data from the HTML5 data-* attribute
	if ( data === undefined && elem.nodeType === 1 ) {

		var name = "data-" + key.replace( rmultiDash, "-$1" ).toLowerCase();

		data = elem.getAttribute( name );

		if ( typeof data === "string" ) {
			try {
				data = data === "true" ? true :
					data === "false" ? false :
					data === "null" ? null :

					// Only convert to a number if it doesn't change the string
					+data + "" === data ? +data :
					rbrace.test( data ) ? jQuery.parseJSON( data ) :
					data;
			} catch ( e ) {}

			// Make sure we set the data so it isn't changed later
			jQuery.data( elem, key, data );

		} else {
			data = undefined;
		}
	}

	return data;
}

// checks a cache object for emptiness
function isEmptyDataObject( obj ) {
	var name;
	for ( name in obj ) {

		// if the public data object is empty, the private is still empty
		if ( name === "data" && jQuery.isEmptyObject( obj[ name ] ) ) {
			continue;
		}
		if ( name !== "toJSON" ) {
			return false;
		}
	}

	return true;
}

function internalData( elem, name, data, pvt /* Internal Use Only */ ) {
	if ( !acceptData( elem ) ) {
		return;
	}

	var ret, thisCache,
		internalKey = jQuery.expando,

		// We have to handle DOM nodes and JS objects differently because IE6-7
		// can't GC object references properly across the DOM-JS boundary
		isNode = elem.nodeType,

		// Only DOM nodes need the global jQuery cache; JS object data is
		// attached directly to the object so GC can occur automatically
		cache = isNode ? jQuery.cache : elem,

		// Only defining an ID for JS objects if its cache already exists allows
		// the code to shortcut on the same path as a DOM node with no cache
		id = isNode ? elem[ internalKey ] : elem[ internalKey ] && internalKey;

	// Avoid doing any more work than we need to when trying to get data on an
	// object that has no data at all
	if ( ( !id || !cache[ id ] || ( !pvt && !cache[ id ].data ) ) &&
		data === undefined && typeof name === "string" ) {
		return;
	}

	if ( !id ) {

		// Only DOM nodes need a new unique ID for each element since their data
		// ends up in the global cache
		if ( isNode ) {
			id = elem[ internalKey ] = deletedIds.pop() || jQuery.guid++;
		} else {
			id = internalKey;
		}
	}

	if ( !cache[ id ] ) {

		// Avoid exposing jQuery metadata on plain JS objects when the object
		// is serialized using JSON.stringify
		cache[ id ] = isNode ? {} : { toJSON: jQuery.noop };
	}

	// An object can be passed to jQuery.data instead of a key/value pair; this gets
	// shallow copied over onto the existing cache
	if ( typeof name === "object" || typeof name === "function" ) {
		if ( pvt ) {
			cache[ id ] = jQuery.extend( cache[ id ], name );
		} else {
			cache[ id ].data = jQuery.extend( cache[ id ].data, name );
		}
	}

	thisCache = cache[ id ];

	// jQuery data() is stored in a separate object inside the object's internal data
	// cache in order to avoid key collisions between internal data and user-defined
	// data.
	if ( !pvt ) {
		if ( !thisCache.data ) {
			thisCache.data = {};
		}

		thisCache = thisCache.data;
	}

	if ( data !== undefined ) {
		thisCache[ jQuery.camelCase( name ) ] = data;
	}

	// Check for both converted-to-camel and non-converted data property names
	// If a data property was specified
	if ( typeof name === "string" ) {

		// First Try to find as-is property data
		ret = thisCache[ name ];

		// Test for null|undefined property data
		if ( ret == null ) {

			// Try to find the camelCased property
			ret = thisCache[ jQuery.camelCase( name ) ];
		}
	} else {
		ret = thisCache;
	}

	return ret;
}

function internalRemoveData( elem, name, pvt ) {
	if ( !acceptData( elem ) ) {
		return;
	}

	var thisCache, i,
		isNode = elem.nodeType,

		// See jQuery.data for more information
		cache = isNode ? jQuery.cache : elem,
		id = isNode ? elem[ jQuery.expando ] : jQuery.expando;

	// If there is already no cache entry for this object, there is no
	// purpose in continuing
	if ( !cache[ id ] ) {
		return;
	}

	if ( name ) {

		thisCache = pvt ? cache[ id ] : cache[ id ].data;

		if ( thisCache ) {

			// Support array or space separated string names for data keys
			if ( !jQuery.isArray( name ) ) {

				// try the string as a key before any manipulation
				if ( name in thisCache ) {
					name = [ name ];
				} else {

					// split the camel cased version by spaces unless a key with the spaces exists
					name = jQuery.camelCase( name );
					if ( name in thisCache ) {
						name = [ name ];
					} else {
						name = name.split( " " );
					}
				}
			} else {

				// If "name" is an array of keys...
				// When data is initially created, via ("key", "val") signature,
				// keys will be converted to camelCase.
				// Since there is no way to tell _how_ a key was added, remove
				// both plain key and camelCase key. #12786
				// This will only penalize the array argument path.
				name = name.concat( jQuery.map( name, jQuery.camelCase ) );
			}

			i = name.length;
			while ( i-- ) {
				delete thisCache[ name[ i ] ];
			}

			// If there is no data left in the cache, we want to continue
			// and let the cache object itself get destroyed
			if ( pvt ? !isEmptyDataObject( thisCache ) : !jQuery.isEmptyObject( thisCache ) ) {
				return;
			}
		}
	}

	// See jQuery.data for more information
	if ( !pvt ) {
		delete cache[ id ].data;

		// Don't destroy the parent cache unless the internal data object
		// had been the only thing left in it
		if ( !isEmptyDataObject( cache[ id ] ) ) {
			return;
		}
	}

	// Destroy the cache
	if ( isNode ) {
		jQuery.cleanData( [ elem ], true );

	// Use delete when supported for expandos or `cache` is not a window per isWindow (#10080)
	/* jshint eqeqeq: false */
	} else if ( support.deleteExpando || cache != cache.window ) {
		/* jshint eqeqeq: true */
		delete cache[ id ];

	// When all else fails, undefined
	} else {
		cache[ id ] = undefined;
	}
}

jQuery.extend( {
	cache: {},

	// The following elements (space-suffixed to avoid Object.prototype collisions)
	// throw uncatchable exceptions if you attempt to set expando properties
	noData: {
		"applet ": true,
		"embed ": true,

		// ...but Flash objects (which have this classid) *can* handle expandos
		"object ": "clsid:D27CDB6E-AE6D-11cf-96B8-444553540000"
	},

	hasData: function( elem ) {
		elem = elem.nodeType ? jQuery.cache[ elem[ jQuery.expando ] ] : elem[ jQuery.expando ];
		return !!elem && !isEmptyDataObject( elem );
	},

	data: function( elem, name, data ) {
		return internalData( elem, name, data );
	},

	removeData: function( elem, name ) {
		return internalRemoveData( elem, name );
	},

	// For internal use only.
	_data: function( elem, name, data ) {
		return internalData( elem, name, data, true );
	},

	_removeData: function( elem, name ) {
		return internalRemoveData( elem, name, true );
	}
} );

jQuery.fn.extend( {
	data: function( key, value ) {
		var i, name, data,
			elem = this[ 0 ],
			attrs = elem && elem.attributes;

		// Special expections of .data basically thwart jQuery.access,
		// so implement the relevant behavior ourselves

		// Gets all values
		if ( key === undefined ) {
			if ( this.length ) {
				data = jQuery.data( elem );

				if ( elem.nodeType === 1 && !jQuery._data( elem, "parsedAttrs" ) ) {
					i = attrs.length;
					while ( i-- ) {

						// Support: IE11+
						// The attrs elements can be null (#14894)
						if ( attrs[ i ] ) {
							name = attrs[ i ].name;
							if ( name.indexOf( "data-" ) === 0 ) {
								name = jQuery.camelCase( name.slice( 5 ) );
								dataAttr( elem, name, data[ name ] );
							}
						}
					}
					jQuery._data( elem, "parsedAttrs", true );
				}
			}

			return data;
		}

		// Sets multiple values
		if ( typeof key === "object" ) {
			return this.each( function() {
				jQuery.data( this, key );
			} );
		}

		return arguments.length > 1 ?

			// Sets one value
			this.each( function() {
				jQuery.data( this, key, value );
			} ) :

			// Gets one value
			// Try to fetch any internally stored data first
			elem ? dataAttr( elem, key, jQuery.data( elem, key ) ) : undefined;
	},

	removeData: function( key ) {
		return this.each( function() {
			jQuery.removeData( this, key );
		} );
	}
} );


jQuery.extend( {
	queue: function( elem, type, data ) {
		var queue;

		if ( elem ) {
			type = ( type || "fx" ) + "queue";
			queue = jQuery._data( elem, type );

			// Speed up dequeue by getting out quickly if this is just a lookup
			if ( data ) {
				if ( !queue || jQuery.isArray( data ) ) {
					queue = jQuery._data( elem, type, jQuery.makeArray( data ) );
				} else {
					queue.push( data );
				}
			}
			return queue || [];
		}
	},

	dequeue: function( elem, type ) {
		type = type || "fx";

		var queue = jQuery.queue( elem, type ),
			startLength = queue.length,
			fn = queue.shift(),
			hooks = jQuery._queueHooks( elem, type ),
			next = function() {
				jQuery.dequeue( elem, type );
			};

		// If the fx queue is dequeued, always remove the progress sentinel
		if ( fn === "inprogress" ) {
			fn = queue.shift();
			startLength--;
		}

		if ( fn ) {

			// Add a progress sentinel to prevent the fx queue from being
			// automatically dequeued
			if ( type === "fx" ) {
				queue.unshift( "inprogress" );
			}

			// clear up the last queue stop function
			delete hooks.stop;
			fn.call( elem, next, hooks );
		}

		if ( !startLength && hooks ) {
			hooks.empty.fire();
		}
	},

	// not intended for public consumption - generates a queueHooks object,
	// or returns the current one
	_queueHooks: function( elem, type ) {
		var key = type + "queueHooks";
		return jQuery._data( elem, key ) || jQuery._data( elem, key, {
			empty: jQuery.Callbacks( "once memory" ).add( function() {
				jQuery._removeData( elem, type + "queue" );
				jQuery._removeData( elem, key );
			} )
		} );
	}
} );

jQuery.fn.extend( {
	queue: function( type, data ) {
		var setter = 2;

		if ( typeof type !== "string" ) {
			data = type;
			type = "fx";
			setter--;
		}

		if ( arguments.length < setter ) {
			return jQuery.queue( this[ 0 ], type );
		}

		return data === undefined ?
			this :
			this.each( function() {
				var queue = jQuery.queue( this, type, data );

				// ensure a hooks for this queue
				jQuery._queueHooks( this, type );

				if ( type === "fx" && queue[ 0 ] !== "inprogress" ) {
					jQuery.dequeue( this, type );
				}
			} );
	},
	dequeue: function( type ) {
		return this.each( function() {
			jQuery.dequeue( this, type );
		} );
	},
	clearQueue: function( type ) {
		return this.queue( type || "fx", [] );
	},

	// Get a promise resolved when queues of a certain type
	// are emptied (fx is the type by default)
	promise: function( type, obj ) {
		var tmp,
			count = 1,
			defer = jQuery.Deferred(),
			elements = this,
			i = this.length,
			resolve = function() {
				if ( !( --count ) ) {
					defer.resolveWith( elements, [ elements ] );
				}
			};

		if ( typeof type !== "string" ) {
			obj = type;
			type = undefined;
		}
		type = type || "fx";

		while ( i-- ) {
			tmp = jQuery._data( elements[ i ], type + "queueHooks" );
			if ( tmp && tmp.empty ) {
				count++;
				tmp.empty.add( resolve );
			}
		}
		resolve();
		return defer.promise( obj );
	}
} );


( function() {
	var shrinkWrapBlocksVal;

	support.shrinkWrapBlocks = function() {
		if ( shrinkWrapBlocksVal != null ) {
			return shrinkWrapBlocksVal;
		}

		// Will be changed later if needed.
		shrinkWrapBlocksVal = false;

		// Minified: var b,c,d
		var div, body, container;

		body = document.getElementsByTagName( "body" )[ 0 ];
		if ( !body || !body.style ) {

			// Test fired too early or in an unsupported environment, exit.
			return;
		}

		// Setup
		div = document.createElement( "div" );
		container = document.createElement( "div" );
		container.style.cssText = "position:absolute;border:0;width:0;height:0;top:0;left:-9999px";
		body.appendChild( container ).appendChild( div );

		// Support: IE6
		// Check if elements with layout shrink-wrap their children
		if ( typeof div.style.zoom !== "undefined" ) {

			// Reset CSS: box-sizing; display; margin; border
			div.style.cssText =

				// Support: Firefox<29, Android 2.3
				// Vendor-prefix box-sizing
				"-webkit-box-sizing:content-box;-moz-box-sizing:content-box;" +
				"box-sizing:content-box;display:block;margin:0;border:0;" +
				"padding:1px;width:1px;zoom:1";
			div.appendChild( document.createElement( "div" ) ).style.width = "5px";
			shrinkWrapBlocksVal = div.offsetWidth !== 3;
		}

		body.removeChild( container );

		return shrinkWrapBlocksVal;
	};

} )();
var pnum = ( /[+-]?(?:\d*\.|)\d+(?:[eE][+-]?\d+|)/ ).source;

var rcssNum = new RegExp( "^(?:([+-])=|)(" + pnum + ")([a-z%]*)$", "i" );


var cssExpand = [ "Top", "Right", "Bottom", "Left" ];

var isHidden = function( elem, el ) {

		// isHidden might be called from jQuery#filter function;
		// in that case, element will be second argument
		elem = el || elem;
		return jQuery.css( elem, "display" ) === "none" ||
			!jQuery.contains( elem.ownerDocument, elem );
	};



function adjustCSS( elem, prop, valueParts, tween ) {
	var adjusted,
		scale = 1,
		maxIterations = 20,
		currentValue = tween ?
			function() { return tween.cur(); } :
			function() { return jQuery.css( elem, prop, "" ); },
		initial = currentValue(),
		unit = valueParts && valueParts[ 3 ] || ( jQuery.cssNumber[ prop ] ? "" : "px" ),

		// Starting value computation is required for potential unit mismatches
		initialInUnit = ( jQuery.cssNumber[ prop ] || unit !== "px" && +initial ) &&
			rcssNum.exec( jQuery.css( elem, prop ) );

	if ( initialInUnit && initialInUnit[ 3 ] !== unit ) {

		// Trust units reported by jQuery.css
		unit = unit || initialInUnit[ 3 ];

		// Make sure we update the tween properties later on
		valueParts = valueParts || [];

		// Iteratively approximate from a nonzero starting point
		initialInUnit = +initial || 1;

		do {

			// If previous iteration zeroed out, double until we get *something*.
			// Use string for doubling so we don't accidentally see scale as unchanged below
			scale = scale || ".5";

			// Adjust and apply
			initialInUnit = initialInUnit / scale;
			jQuery.style( elem, prop, initialInUnit + unit );

		// Update scale, tolerating zero or NaN from tween.cur()
		// Break the loop if scale is unchanged or perfect, or if we've just had enough.
		} while (
			scale !== ( scale = currentValue() / initial ) && scale !== 1 && --maxIterations
		);
	}

	if ( valueParts ) {
		initialInUnit = +initialInUnit || +initial || 0;

		// Apply relative offset (+=/-=) if specified
		adjusted = valueParts[ 1 ] ?
			initialInUnit + ( valueParts[ 1 ] + 1 ) * valueParts[ 2 ] :
			+valueParts[ 2 ];
		if ( tween ) {
			tween.unit = unit;
			tween.start = initialInUnit;
			tween.end = adjusted;
		}
	}
	return adjusted;
}


// Multifunctional method to get and set values of a collection
// The value/s can optionally be executed if it's a function
var access = function( elems, fn, key, value, chainable, emptyGet, raw ) {
	var i = 0,
		length = elems.length,
		bulk = key == null;

	// Sets many values
	if ( jQuery.type( key ) === "object" ) {
		chainable = true;
		for ( i in key ) {
			access( elems, fn, i, key[ i ], true, emptyGet, raw );
		}

	// Sets one value
	} else if ( value !== undefined ) {
		chainable = true;

		if ( !jQuery.isFunction( value ) ) {
			raw = true;
		}

		if ( bulk ) {

			// Bulk operations run against the entire set
			if ( raw ) {
				fn.call( elems, value );
				fn = null;

			// ...except when executing function values
			} else {
				bulk = fn;
				fn = function( elem, key, value ) {
					return bulk.call( jQuery( elem ), value );
				};
			}
		}

		if ( fn ) {
			for ( ; i < length; i++ ) {
				fn(
					elems[ i ],
					key,
					raw ? value : value.call( elems[ i ], i, fn( elems[ i ], key ) )
				);
			}
		}
	}

	return chainable ?
		elems :

		// Gets
		bulk ?
			fn.call( elems ) :
			length ? fn( elems[ 0 ], key ) : emptyGet;
};
var rcheckableType = ( /^(?:checkbox|radio)$/i );

var rtagName = ( /<([\w:-]+)/ );

var rscriptType = ( /^$|\/(?:java|ecma)script/i );

var rleadingWhitespace = ( /^\s+/ );

var nodeNames = "abbr|article|aside|audio|bdi|canvas|data|datalist|" +
		"details|dialog|figcaption|figure|footer|header|hgroup|main|" +
		"mark|meter|nav|output|picture|progress|section|summary|template|time|video";



function createSafeFragment( document ) {
	var list = nodeNames.split( "|" ),
		safeFrag = document.createDocumentFragment();

	if ( safeFrag.createElement ) {
		while ( list.length ) {
			safeFrag.createElement(
				list.pop()
			);
		}
	}
	return safeFrag;
}


( function() {
	var div = document.createElement( "div" ),
		fragment = document.createDocumentFragment(),
		input = document.createElement( "input" );

	// Setup
	div.innerHTML = "  <link/><table></table><a href='/a'>a</a><input type='checkbox'/>";

	// IE strips leading whitespace when .innerHTML is used
	support.leadingWhitespace = div.firstChild.nodeType === 3;

	// Make sure that tbody elements aren't automatically inserted
	// IE will insert them into empty tables
	support.tbody = !div.getElementsByTagName( "tbody" ).length;

	// Make sure that link elements get serialized correctly by innerHTML
	// This requires a wrapper element in IE
	support.htmlSerialize = !!div.getElementsByTagName( "link" ).length;

	// Makes sure cloning an html5 element does not cause problems
	// Where outerHTML is undefined, this still works
	support.html5Clone =
		document.createElement( "nav" ).cloneNode( true ).outerHTML !== "<:nav></:nav>";

	// Check if a disconnected checkbox will retain its checked
	// value of true after appended to the DOM (IE6/7)
	input.type = "checkbox";
	input.checked = true;
	fragment.appendChild( input );
	support.appendChecked = input.checked;

	// Make sure textarea (and checkbox) defaultValue is properly cloned
	// Support: IE6-IE11+
	div.innerHTML = "<textarea>x</textarea>";
	support.noCloneChecked = !!div.cloneNode( true ).lastChild.defaultValue;

	// #11217 - WebKit loses check when the name is after the checked attribute
	fragment.appendChild( div );

	// Support: Windows Web Apps (WWA)
	// `name` and `type` must use .setAttribute for WWA (#14901)
	input = document.createElement( "input" );
	input.setAttribute( "type", "radio" );
	input.setAttribute( "checked", "checked" );
	input.setAttribute( "name", "t" );

	div.appendChild( input );

	// Support: Safari 5.1, iOS 5.1, Android 4.x, Android 2.3
	// old WebKit doesn't clone checked state correctly in fragments
	support.checkClone = div.cloneNode( true ).cloneNode( true ).lastChild.checked;

	// Support: IE<9
	// Cloned elements keep attachEvent handlers, we use addEventListener on IE9+
	support.noCloneEvent = !!div.addEventListener;

	// Support: IE<9
	// Since attributes and properties are the same in IE,
	// cleanData must set properties to undefined rather than use removeAttribute
	div[ jQuery.expando ] = 1;
	support.attributes = !div.getAttribute( jQuery.expando );
} )();


// We have to close these tags to support XHTML (#13200)
var wrapMap = {
	option: [ 1, "<select multiple='multiple'>", "</select>" ],
	legend: [ 1, "<fieldset>", "</fieldset>" ],
	area: [ 1, "<map>", "</map>" ],

	// Support: IE8
	param: [ 1, "<object>", "</object>" ],
	thead: [ 1, "<table>", "</table>" ],
	tr: [ 2, "<table><tbody>", "</tbody></table>" ],
	col: [ 2, "<table><tbody></tbody><colgroup>", "</colgroup></table>" ],
	td: [ 3, "<table><tbody><tr>", "</tr></tbody></table>" ],

	// IE6-8 can't serialize link, script, style, or any html5 (NoScope) tags,
	// unless wrapped in a div with non-breaking characters in front of it.
	_default: support.htmlSerialize ? [ 0, "", "" ] : [ 1, "X<div>", "</div>" ]
};

// Support: IE8-IE9
wrapMap.optgroup = wrapMap.option;

wrapMap.tbody = wrapMap.tfoot = wrapMap.colgroup = wrapMap.caption = wrapMap.thead;
wrapMap.th = wrapMap.td;


function getAll( context, tag ) {
	var elems, elem,
		i = 0,
		found = typeof context.getElementsByTagName !== "undefined" ?
			context.getElementsByTagName( tag || "*" ) :
			typeof context.querySelectorAll !== "undefined" ?
				context.querySelectorAll( tag || "*" ) :
				undefined;

	if ( !found ) {
		for ( found = [], elems = context.childNodes || context;
			( elem = elems[ i ] ) != null;
			i++
		) {
			if ( !tag || jQuery.nodeName( elem, tag ) ) {
				found.push( elem );
			} else {
				jQuery.merge( found, getAll( elem, tag ) );
			}
		}
	}

	return tag === undefined || tag && jQuery.nodeName( context, tag ) ?
		jQuery.merge( [ context ], found ) :
		found;
}


// Mark scripts as having already been evaluated
function setGlobalEval( elems, refElements ) {
	var elem,
		i = 0;
	for ( ; ( elem = elems[ i ] ) != null; i++ ) {
		jQuery._data(
			elem,
			"globalEval",
			!refElements || jQuery._data( refElements[ i ], "globalEval" )
		);
	}
}


var rhtml = /<|&#?\w+;/,
	rtbody = /<tbody/i;

function fixDefaultChecked( elem ) {
	if ( rcheckableType.test( elem.type ) ) {
		elem.defaultChecked = elem.checked;
	}
}

function buildFragment( elems, context, scripts, selection, ignored ) {
	var j, elem, contains,
		tmp, tag, tbody, wrap,
		l = elems.length,

		// Ensure a safe fragment
		safe = createSafeFragment( context ),

		nodes = [],
		i = 0;

	for ( ; i < l; i++ ) {
		elem = elems[ i ];

		if ( elem || elem === 0 ) {

			// Add nodes directly
			if ( jQuery.type( elem ) === "object" ) {
				jQuery.merge( nodes, elem.nodeType ? [ elem ] : elem );

			// Convert non-html into a text node
			} else if ( !rhtml.test( elem ) ) {
				nodes.push( context.createTextNode( elem ) );

			// Convert html into DOM nodes
			} else {
				tmp = tmp || safe.appendChild( context.createElement( "div" ) );

				// Deserialize a standard representation
				tag = ( rtagName.exec( elem ) || [ "", "" ] )[ 1 ].toLowerCase();
				wrap = wrapMap[ tag ] || wrapMap._default;

				tmp.innerHTML = wrap[ 1 ] + jQuery.htmlPrefilter( elem ) + wrap[ 2 ];

				// Descend through wrappers to the right content
				j = wrap[ 0 ];
				while ( j-- ) {
					tmp = tmp.lastChild;
				}

				// Manually add leading whitespace removed by IE
				if ( !support.leadingWhitespace && rleadingWhitespace.test( elem ) ) {
					nodes.push( context.createTextNode( rleadingWhitespace.exec( elem )[ 0 ] ) );
				}

				// Remove IE's autoinserted <tbody> from table fragments
				if ( !support.tbody ) {

					// String was a <table>, *may* have spurious <tbody>
					elem = tag === "table" && !rtbody.test( elem ) ?
						tmp.firstChild :

						// String was a bare <thead> or <tfoot>
						wrap[ 1 ] === "<table>" && !rtbody.test( elem ) ?
							tmp :
							0;

					j = elem && elem.childNodes.length;
					while ( j-- ) {
						if ( jQuery.nodeName( ( tbody = elem.childNodes[ j ] ), "tbody" ) &&
							!tbody.childNodes.length ) {

							elem.removeChild( tbody );
						}
					}
				}

				jQuery.merge( nodes, tmp.childNodes );

				// Fix #12392 for WebKit and IE > 9
				tmp.textContent = "";

				// Fix #12392 for oldIE
				while ( tmp.firstChild ) {
					tmp.removeChild( tmp.firstChild );
				}

				// Remember the top-level container for proper cleanup
				tmp = safe.lastChild;
			}
		}
	}

	// Fix #11356: Clear elements from fragment
	if ( tmp ) {
		safe.removeChild( tmp );
	}

	// Reset defaultChecked for any radios and checkboxes
	// about to be appended to the DOM in IE 6/7 (#8060)
	if ( !support.appendChecked ) {
		jQuery.grep( getAll( nodes, "input" ), fixDefaultChecked );
	}

	i = 0;
	while ( ( elem = nodes[ i++ ] ) ) {

		// Skip elements already in the context collection (trac-4087)
		if ( selection && jQuery.inArray( elem, selection ) > -1 ) {
			if ( ignored ) {
				ignored.push( elem );
			}

			continue;
		}

		contains = jQuery.contains( elem.ownerDocument, elem );

		// Append to fragment
		tmp = getAll( safe.appendChild( elem ), "script" );

		// Preserve script evaluation history
		if ( contains ) {
			setGlobalEval( tmp );
		}

		// Capture executables
		if ( scripts ) {
			j = 0;
			while ( ( elem = tmp[ j++ ] ) ) {
				if ( rscriptType.test( elem.type || "" ) ) {
					scripts.push( elem );
				}
			}
		}
	}

	tmp = null;

	return safe;
}


( function() {
	var i, eventName,
		div = document.createElement( "div" );

	// Support: IE<9 (lack submit/change bubble), Firefox (lack focus(in | out) events)
	for ( i in { submit: true, change: true, focusin: true } ) {
		eventName = "on" + i;

		if ( !( support[ i ] = eventName in window ) ) {

			// Beware of CSP restrictions (https://developer.mozilla.org/en/Security/CSP)
			div.setAttribute( eventName, "t" );
			support[ i ] = div.attributes[ eventName ].expando === false;
		}
	}

	// Null elements to avoid leaks in IE.
	div = null;
} )();


var rformElems = /^(?:input|select|textarea)$/i,
	rkeyEvent = /^key/,
	rmouseEvent = /^(?:mouse|pointer|contextmenu|drag|drop)|click/,
	rfocusMorph = /^(?:focusinfocus|focusoutblur)$/,
	rtypenamespace = /^([^.]*)(?:\.(.+)|)/;

function returnTrue() {
	return true;
}

function returnFalse() {
	return false;
}

// Support: IE9
// See #13393 for more info
function safeActiveElement() {
	try {
		return document.activeElement;
	} catch ( err ) { }
}

function on( elem, types, selector, data, fn, one ) {
	var origFn, type;

	// Types can be a map of types/handlers
	if ( typeof types === "object" ) {

		// ( types-Object, selector, data )
		if ( typeof selector !== "string" ) {

			// ( types-Object, data )
			data = data || selector;
			selector = undefined;
		}
		for ( type in types ) {
			on( elem, type, selector, data, types[ type ], one );
		}
		return elem;
	}

	if ( data == null && fn == null ) {

		// ( types, fn )
		fn = selector;
		data = selector = undefined;
	} else if ( fn == null ) {
		if ( typeof selector === "string" ) {

			// ( types, selector, fn )
			fn = data;
			data = undefined;
		} else {

			// ( types, data, fn )
			fn = data;
			data = selector;
			selector = undefined;
		}
	}
	if ( fn === false ) {
		fn = returnFalse;
	} else if ( !fn ) {
		return elem;
	}

	if ( one === 1 ) {
		origFn = fn;
		fn = function( event ) {

			// Can use an empty set, since event contains the info
			jQuery().off( event );
			return origFn.apply( this, arguments );
		};

		// Use same guid so caller can remove using origFn
		fn.guid = origFn.guid || ( origFn.guid = jQuery.guid++ );
	}
	return elem.each( function() {
		jQuery.event.add( this, types, fn, data, selector );
	} );
}

/*
 * Helper functions for managing events -- not part of the public interface.
 * Props to Dean Edwards' addEvent library for many of the ideas.
 */
jQuery.event = {

	global: {},

	add: function( elem, types, handler, data, selector ) {
		var tmp, events, t, handleObjIn,
			special, eventHandle, handleObj,
			handlers, type, namespaces, origType,
			elemData = jQuery._data( elem );

		// Don't attach events to noData or text/comment nodes (but allow plain objects)
		if ( !elemData ) {
			return;
		}

		// Caller can pass in an object of custom data in lieu of the handler
		if ( handler.handler ) {
			handleObjIn = handler;
			handler = handleObjIn.handler;
			selector = handleObjIn.selector;
		}

		// Make sure that the handler has a unique ID, used to find/remove it later
		if ( !handler.guid ) {
			handler.guid = jQuery.guid++;
		}

		// Init the element's event structure and main handler, if this is the first
		if ( !( events = elemData.events ) ) {
			events = elemData.events = {};
		}
		if ( !( eventHandle = elemData.handle ) ) {
			eventHandle = elemData.handle = function( e ) {

				// Discard the second event of a jQuery.event.trigger() and
				// when an event is called after a page has unloaded
				return typeof jQuery !== "undefined" &&
					( !e || jQuery.event.triggered !== e.type ) ?
					jQuery.event.dispatch.apply( eventHandle.elem, arguments ) :
					undefined;
			};

			// Add elem as a property of the handle fn to prevent a memory leak
			// with IE non-native events
			eventHandle.elem = elem;
		}

		// Handle multiple events separated by a space
		types = ( types || "" ).match( rnotwhite ) || [ "" ];
		t = types.length;
		while ( t-- ) {
			tmp = rtypenamespace.exec( types[ t ] ) || [];
			type = origType = tmp[ 1 ];
			namespaces = ( tmp[ 2 ] || "" ).split( "." ).sort();

			// There *must* be a type, no attaching namespace-only handlers
			if ( !type ) {
				continue;
			}

			// If event changes its type, use the special event handlers for the changed type
			special = jQuery.event.special[ type ] || {};

			// If selector defined, determine special event api type, otherwise given type
			type = ( selector ? special.delegateType : special.bindType ) || type;

			// Update special based on newly reset type
			special = jQuery.event.special[ type ] || {};

			// handleObj is passed to all event handlers
			handleObj = jQuery.extend( {
				type: type,
				origType: origType,
				data: data,
				handler: handler,
				guid: handler.guid,
				selector: selector,
				needsContext: selector && jQuery.expr.match.needsContext.test( selector ),
				namespace: namespaces.join( "." )
			}, handleObjIn );

			// Init the event handler queue if we're the first
			if ( !( handlers = events[ type ] ) ) {
				handlers = events[ type ] = [];
				handlers.delegateCount = 0;

				// Only use addEventListener/attachEvent if the special events handler returns false
				if ( !special.setup ||
					special.setup.call( elem, data, namespaces, eventHandle ) === false ) {

					// Bind the global event handler to the element
					if ( elem.addEventListener ) {
						elem.addEventListener( type, eventHandle, false );

					} else if ( elem.attachEvent ) {
						elem.attachEvent( "on" + type, eventHandle );
					}
				}
			}

			if ( special.add ) {
				special.add.call( elem, handleObj );

				if ( !handleObj.handler.guid ) {
					handleObj.handler.guid = handler.guid;
				}
			}

			// Add to the element's handler list, delegates in front
			if ( selector ) {
				handlers.splice( handlers.delegateCount++, 0, handleObj );
			} else {
				handlers.push( handleObj );
			}

			// Keep track of which events have ever been used, for event optimization
			jQuery.event.global[ type ] = true;
		}

		// Nullify elem to prevent memory leaks in IE
		elem = null;
	},

	// Detach an event or set of events from an element
	remove: function( elem, types, handler, selector, mappedTypes ) {
		var j, handleObj, tmp,
			origCount, t, events,
			special, handlers, type,
			namespaces, origType,
			elemData = jQuery.hasData( elem ) && jQuery._data( elem );

		if ( !elemData || !( events = elemData.events ) ) {
			return;
		}

		// Once for each type.namespace in types; type may be omitted
		types = ( types || "" ).match( rnotwhite ) || [ "" ];
		t = types.length;
		while ( t-- ) {
			tmp = rtypenamespace.exec( types[ t ] ) || [];
			type = origType = tmp[ 1 ];
			namespaces = ( tmp[ 2 ] || "" ).split( "." ).sort();

			// Unbind all events (on this namespace, if provided) for the element
			if ( !type ) {
				for ( type in events ) {
					jQuery.event.remove( elem, type + types[ t ], handler, selector, true );
				}
				continue;
			}

			special = jQuery.event.special[ type ] || {};
			type = ( selector ? special.delegateType : special.bindType ) || type;
			handlers = events[ type ] || [];
			tmp = tmp[ 2 ] &&
				new RegExp( "(^|\\.)" + namespaces.join( "\\.(?:.*\\.|)" ) + "(\\.|$)" );

			// Remove matching events
			origCount = j = handlers.length;
			while ( j-- ) {
				handleObj = handlers[ j ];

				if ( ( mappedTypes || origType === handleObj.origType ) &&
					( !handler || handler.guid === handleObj.guid ) &&
					( !tmp || tmp.test( handleObj.namespace ) ) &&
					( !selector || selector === handleObj.selector ||
						selector === "**" && handleObj.selector ) ) {
					handlers.splice( j, 1 );

					if ( handleObj.selector ) {
						handlers.delegateCount--;
					}
					if ( special.remove ) {
						special.remove.call( elem, handleObj );
					}
				}
			}

			// Remove generic event handler if we removed something and no more handlers exist
			// (avoids potential for endless recursion during removal of special event handlers)
			if ( origCount && !handlers.length ) {
				if ( !special.teardown ||
					special.teardown.call( elem, namespaces, elemData.handle ) === false ) {

					jQuery.removeEvent( elem, type, elemData.handle );
				}

				delete events[ type ];
			}
		}

		// Remove the expando if it's no longer used
		if ( jQuery.isEmptyObject( events ) ) {
			delete elemData.handle;

			// removeData also checks for emptiness and clears the expando if empty
			// so use it instead of delete
			jQuery._removeData( elem, "events" );
		}
	},

	trigger: function( event, data, elem, onlyHandlers ) {
		var handle, ontype, cur,
			bubbleType, special, tmp, i,
			eventPath = [ elem || document ],
			type = hasOwn.call( event, "type" ) ? event.type : event,
			namespaces = hasOwn.call( event, "namespace" ) ? event.namespace.split( "." ) : [];

		cur = tmp = elem = elem || document;

		// Don't do events on text and comment nodes
		if ( elem.nodeType === 3 || elem.nodeType === 8 ) {
			return;
		}

		// focus/blur morphs to focusin/out; ensure we're not firing them right now
		if ( rfocusMorph.test( type + jQuery.event.triggered ) ) {
			return;
		}

		if ( type.indexOf( "." ) > -1 ) {

			// Namespaced trigger; create a regexp to match event type in handle()
			namespaces = type.split( "." );
			type = namespaces.shift();
			namespaces.sort();
		}
		ontype = type.indexOf( ":" ) < 0 && "on" + type;

		// Caller can pass in a jQuery.Event object, Object, or just an event type string
		event = event[ jQuery.expando ] ?
			event :
			new jQuery.Event( type, typeof event === "object" && event );

		// Trigger bitmask: & 1 for native handlers; & 2 for jQuery (always true)
		event.isTrigger = onlyHandlers ? 2 : 3;
		event.namespace = namespaces.join( "." );
		event.rnamespace = event.namespace ?
			new RegExp( "(^|\\.)" + namespaces.join( "\\.(?:.*\\.|)" ) + "(\\.|$)" ) :
			null;

		// Clean up the event in case it is being reused
		event.result = undefined;
		if ( !event.target ) {
			event.target = elem;
		}

		// Clone any incoming data and prepend the event, creating the handler arg list
		data = data == null ?
			[ event ] :
			jQuery.makeArray( data, [ event ] );

		// Allow special events to draw outside the lines
		special = jQuery.event.special[ type ] || {};
		if ( !onlyHandlers && special.trigger && special.trigger.apply( elem, data ) === false ) {
			return;
		}

		// Determine event propagation path in advance, per W3C events spec (#9951)
		// Bubble up to document, then to window; watch for a global ownerDocument var (#9724)
		if ( !onlyHandlers && !special.noBubble && !jQuery.isWindow( elem ) ) {

			bubbleType = special.delegateType || type;
			if ( !rfocusMorph.test( bubbleType + type ) ) {
				cur = cur.parentNode;
			}
			for ( ; cur; cur = cur.parentNode ) {
				eventPath.push( cur );
				tmp = cur;
			}

			// Only add window if we got to document (e.g., not plain obj or detached DOM)
			if ( tmp === ( elem.ownerDocument || document ) ) {
				eventPath.push( tmp.defaultView || tmp.parentWindow || window );
			}
		}

		// Fire handlers on the event path
		i = 0;
		while ( ( cur = eventPath[ i++ ] ) && !event.isPropagationStopped() ) {

			event.type = i > 1 ?
				bubbleType :
				special.bindType || type;

			// jQuery handler
			handle = ( jQuery._data( cur, "events" ) || {} )[ event.type ] &&
				jQuery._data( cur, "handle" );

			if ( handle ) {
				handle.apply( cur, data );
			}

			// Native handler
			handle = ontype && cur[ ontype ];
			if ( handle && handle.apply && acceptData( cur ) ) {
				event.result = handle.apply( cur, data );
				if ( event.result === false ) {
					event.preventDefault();
				}
			}
		}
		event.type = type;

		// If nobody prevented the default action, do it now
		if ( !onlyHandlers && !event.isDefaultPrevented() ) {

			if (
				( !special._default ||
				 special._default.apply( eventPath.pop(), data ) === false
				) && acceptData( elem )
			) {

				// Call a native DOM method on the target with the same name name as the event.
				// Can't use an .isFunction() check here because IE6/7 fails that test.
				// Don't do default actions on window, that's where global variables be (#6170)
				if ( ontype && elem[ type ] && !jQuery.isWindow( elem ) ) {

					// Don't re-trigger an onFOO event when we call its FOO() method
					tmp = elem[ ontype ];

					if ( tmp ) {
						elem[ ontype ] = null;
					}

					// Prevent re-triggering of the same event, since we already bubbled it above
					jQuery.event.triggered = type;
					try {
						elem[ type ]();
					} catch ( e ) {

						// IE<9 dies on focus/blur to hidden element (#1486,#12518)
						// only reproducible on winXP IE8 native, not IE9 in IE8 mode
					}
					jQuery.event.triggered = undefined;

					if ( tmp ) {
						elem[ ontype ] = tmp;
					}
				}
			}
		}

		return event.result;
	},

	dispatch: function( event ) {

		// Make a writable jQuery.Event from the native event object
		event = jQuery.event.fix( event );

		var i, j, ret, matched, handleObj,
			handlerQueue = [],
			args = slice.call( arguments ),
			handlers = ( jQuery._data( this, "events" ) || {} )[ event.type ] || [],
			special = jQuery.event.special[ event.type ] || {};

		// Use the fix-ed jQuery.Event rather than the (read-only) native event
		args[ 0 ] = event;
		event.delegateTarget = this;

		// Call the preDispatch hook for the mapped type, and let it bail if desired
		if ( special.preDispatch && special.preDispatch.call( this, event ) === false ) {
			return;
		}

		// Determine handlers
		handlerQueue = jQuery.event.handlers.call( this, event, handlers );

		// Run delegates first; they may want to stop propagation beneath us
		i = 0;
		while ( ( matched = handlerQueue[ i++ ] ) && !event.isPropagationStopped() ) {
			event.currentTarget = matched.elem;

			j = 0;
			while ( ( handleObj = matched.handlers[ j++ ] ) &&
				!event.isImmediatePropagationStopped() ) {

				// Triggered event must either 1) have no namespace, or 2) have namespace(s)
				// a subset or equal to those in the bound event (both can have no namespace).
				if ( !event.rnamespace || event.rnamespace.test( handleObj.namespace ) ) {

					event.handleObj = handleObj;
					event.data = handleObj.data;

					ret = ( ( jQuery.event.special[ handleObj.origType ] || {} ).handle ||
						handleObj.handler ).apply( matched.elem, args );

					if ( ret !== undefined ) {
						if ( ( event.result = ret ) === false ) {
							event.preventDefault();
							event.stopPropagation();
						}
					}
				}
			}
		}

		// Call the postDispatch hook for the mapped type
		if ( special.postDispatch ) {
			special.postDispatch.call( this, event );
		}

		return event.result;
	},

	handlers: function( event, handlers ) {
		var i, matches, sel, handleObj,
			handlerQueue = [],
			delegateCount = handlers.delegateCount,
			cur = event.target;

		// Support (at least): Chrome, IE9
		// Find delegate handlers
		// Black-hole SVG <use> instance trees (#13180)
		//
		// Support: Firefox<=42+
		// Avoid non-left-click in FF but don't block IE radio events (#3861, gh-2343)
		if ( delegateCount && cur.nodeType &&
			( event.type !== "click" || isNaN( event.button ) || event.button < 1 ) ) {

			/* jshint eqeqeq: false */
			for ( ; cur != this; cur = cur.parentNode || this ) {
				/* jshint eqeqeq: true */

				// Don't check non-elements (#13208)
				// Don't process clicks on disabled elements (#6911, #8165, #11382, #11764)
				if ( cur.nodeType === 1 && ( cur.disabled !== true || event.type !== "click" ) ) {
					matches = [];
					for ( i = 0; i < delegateCount; i++ ) {
						handleObj = handlers[ i ];

						// Don't conflict with Object.prototype properties (#13203)
						sel = handleObj.selector + " ";

						if ( matches[ sel ] === undefined ) {
							matches[ sel ] = handleObj.needsContext ?
								jQuery( sel, this ).index( cur ) > -1 :
								jQuery.find( sel, this, null, [ cur ] ).length;
						}
						if ( matches[ sel ] ) {
							matches.push( handleObj );
						}
					}
					if ( matches.length ) {
						handlerQueue.push( { elem: cur, handlers: matches } );
					}
				}
			}
		}

		// Add the remaining (directly-bound) handlers
		if ( delegateCount < handlers.length ) {
			handlerQueue.push( { elem: this, handlers: handlers.slice( delegateCount ) } );
		}

		return handlerQueue;
	},

	fix: function( event ) {
		if ( event[ jQuery.expando ] ) {
			return event;
		}

		// Create a writable copy of the event object and normalize some properties
		var i, prop, copy,
			type = event.type,
			originalEvent = event,
			fixHook = this.fixHooks[ type ];

		if ( !fixHook ) {
			this.fixHooks[ type ] = fixHook =
				rmouseEvent.test( type ) ? this.mouseHooks :
				rkeyEvent.test( type ) ? this.keyHooks :
				{};
		}
		copy = fixHook.props ? this.props.concat( fixHook.props ) : this.props;

		event = new jQuery.Event( originalEvent );

		i = copy.length;
		while ( i-- ) {
			prop = copy[ i ];
			event[ prop ] = originalEvent[ prop ];
		}

		// Support: IE<9
		// Fix target property (#1925)
		if ( !event.target ) {
			event.target = originalEvent.srcElement || document;
		}

		// Support: Safari 6-8+
		// Target should not be a text node (#504, #13143)
		if ( event.target.nodeType === 3 ) {
			event.target = event.target.parentNode;
		}

		// Support: IE<9
		// For mouse/key events, metaKey==false if it's undefined (#3368, #11328)
		event.metaKey = !!event.metaKey;

		return fixHook.filter ? fixHook.filter( event, originalEvent ) : event;
	},

	// Includes some event props shared by KeyEvent and MouseEvent
	props: ( "altKey bubbles cancelable ctrlKey currentTarget detail eventPhase " +
		"metaKey relatedTarget shiftKey target timeStamp view which" ).split( " " ),

	fixHooks: {},

	keyHooks: {
		props: "char charCode key keyCode".split( " " ),
		filter: function( event, original ) {

			// Add which for key events
			if ( event.which == null ) {
				event.which = original.charCode != null ? original.charCode : original.keyCode;
			}

			return event;
		}
	},

	mouseHooks: {
		props: ( "button buttons clientX clientY fromElement offsetX offsetY " +
			"pageX pageY screenX screenY toElement" ).split( " " ),
		filter: function( event, original ) {
			var body, eventDoc, doc,
				button = original.button,
				fromElement = original.fromElement;

			// Calculate pageX/Y if missing and clientX/Y available
			if ( event.pageX == null && original.clientX != null ) {
				eventDoc = event.target.ownerDocument || document;
				doc = eventDoc.documentElement;
				body = eventDoc.body;

				event.pageX = original.clientX +
					( doc && doc.scrollLeft || body && body.scrollLeft || 0 ) -
					( doc && doc.clientLeft || body && body.clientLeft || 0 );
				event.pageY = original.clientY +
					( doc && doc.scrollTop  || body && body.scrollTop  || 0 ) -
					( doc && doc.clientTop  || body && body.clientTop  || 0 );
			}

			// Add relatedTarget, if necessary
			if ( !event.relatedTarget && fromElement ) {
				event.relatedTarget = fromElement === event.target ?
					original.toElement :
					fromElement;
			}

			// Add which for click: 1 === left; 2 === middle; 3 === right
			// Note: button is not normalized, so don't use it
			if ( !event.which && button !== undefined ) {
				event.which = ( button & 1 ? 1 : ( button & 2 ? 3 : ( button & 4 ? 2 : 0 ) ) );
			}

			return event;
		}
	},

	special: {
		load: {

			// Prevent triggered image.load events from bubbling to window.load
			noBubble: true
		},
		focus: {

			// Fire native event if possible so blur/focus sequence is correct
			trigger: function() {
				if ( this !== safeActiveElement() && this.focus ) {
					try {
						this.focus();
						return false;
					} catch ( e ) {

						// Support: IE<9
						// If we error on focus to hidden element (#1486, #12518),
						// let .trigger() run the handlers
					}
				}
			},
			delegateType: "focusin"
		},
		blur: {
			trigger: function() {
				if ( this === safeActiveElement() && this.blur ) {
					this.blur();
					return false;
				}
			},
			delegateType: "focusout"
		},
		click: {

			// For checkbox, fire native event so checked state will be right
			trigger: function() {
				if ( jQuery.nodeName( this, "input" ) && this.type === "checkbox" && this.click ) {
					this.click();
					return false;
				}
			},

			// For cross-browser consistency, don't fire native .click() on links
			_default: function( event ) {
				return jQuery.nodeName( event.target, "a" );
			}
		},

		beforeunload: {
			postDispatch: function( event ) {

				// Support: Firefox 20+
				// Firefox doesn't alert if the returnValue field is not set.
				if ( event.result !== undefined && event.originalEvent ) {
					event.originalEvent.returnValue = event.result;
				}
			}
		}
	},

	// Piggyback on a donor event to simulate a different one
	simulate: function( type, elem, event ) {
		var e = jQuery.extend(
			new jQuery.Event(),
			event,
			{
				type: type,
				isSimulated: true

				// Previously, `originalEvent: {}` was set here, so stopPropagation call
				// would not be triggered on donor event, since in our own
				// jQuery.event.stopPropagation function we had a check for existence of
				// originalEvent.stopPropagation method, so, consequently it would be a noop.
				//
				// Guard for simulated events was moved to jQuery.event.stopPropagation function
				// since `originalEvent` should point to the original event for the
				// constancy with other events and for more focused logic
			}
		);

		jQuery.event.trigger( e, null, elem );

		if ( e.isDefaultPrevented() ) {
			event.preventDefault();
		}
	}
};

jQuery.removeEvent = document.removeEventListener ?
	function( elem, type, handle ) {

		// This "if" is needed for plain objects
		if ( elem.removeEventListener ) {
			elem.removeEventListener( type, handle );
		}
	} :
	function( elem, type, handle ) {
		var name = "on" + type;

		if ( elem.detachEvent ) {

			// #8545, #7054, preventing memory leaks for custom events in IE6-8
			// detachEvent needed property on element, by name of that event,
			// to properly expose it to GC
			if ( typeof elem[ name ] === "undefined" ) {
				elem[ name ] = null;
			}

			elem.detachEvent( name, handle );
		}
	};

jQuery.Event = function( src, props ) {

	// Allow instantiation without the 'new' keyword
	if ( !( this instanceof jQuery.Event ) ) {
		return new jQuery.Event( src, props );
	}

	// Event object
	if ( src && src.type ) {
		this.originalEvent = src;
		this.type = src.type;

		// Events bubbling up the document may have been marked as prevented
		// by a handler lower down the tree; reflect the correct value.
		this.isDefaultPrevented = src.defaultPrevented ||
				src.defaultPrevented === undefined &&

				// Support: IE < 9, Android < 4.0
				src.returnValue === false ?
			returnTrue :
			returnFalse;

	// Event type
	} else {
		this.type = src;
	}

	// Put explicitly provided properties onto the event object
	if ( props ) {
		jQuery.extend( this, props );
	}

	// Create a timestamp if incoming event doesn't have one
	this.timeStamp = src && src.timeStamp || jQuery.now();

	// Mark it as fixed
	this[ jQuery.expando ] = true;
};

// jQuery.Event is based on DOM3 Events as specified by the ECMAScript Language Binding
// http://www.w3.org/TR/2003/WD-DOM-Level-3-Events-20030331/ecma-script-binding.html
jQuery.Event.prototype = {
	constructor: jQuery.Event,
	isDefaultPrevented: returnFalse,
	isPropagationStopped: returnFalse,
	isImmediatePropagationStopped: returnFalse,

	preventDefault: function() {
		var e = this.originalEvent;

		this.isDefaultPrevented = returnTrue;
		if ( !e ) {
			return;
		}

		// If preventDefault exists, run it on the original event
		if ( e.preventDefault ) {
			e.preventDefault();

		// Support: IE
		// Otherwise set the returnValue property of the original event to false
		} else {
			e.returnValue = false;
		}
	},
	stopPropagation: function() {
		var e = this.originalEvent;

		this.isPropagationStopped = returnTrue;

		if ( !e || this.isSimulated ) {
			return;
		}

		// If stopPropagation exists, run it on the original event
		if ( e.stopPropagation ) {
			e.stopPropagation();
		}

		// Support: IE
		// Set the cancelBubble property of the original event to true
		e.cancelBubble = true;
	},
	stopImmediatePropagation: function() {
		var e = this.originalEvent;

		this.isImmediatePropagationStopped = returnTrue;

		if ( e && e.stopImmediatePropagation ) {
			e.stopImmediatePropagation();
		}

		this.stopPropagation();
	}
};

// Create mouseenter/leave events using mouseover/out and event-time checks
// so that event delegation works in jQuery.
// Do the same for pointerenter/pointerleave and pointerover/pointerout
//
// Support: Safari 7 only
// Safari sends mouseenter too often; see:
// https://code.google.com/p/chromium/issues/detail?id=470258
// for the description of the bug (it existed in older Chrome versions as well).
jQuery.each( {
	mouseenter: "mouseover",
	mouseleave: "mouseout",
	pointerenter: "pointerover",
	pointerleave: "pointerout"
}, function( orig, fix ) {
	jQuery.event.special[ orig ] = {
		delegateType: fix,
		bindType: fix,

		handle: function( event ) {
			var ret,
				target = this,
				related = event.relatedTarget,
				handleObj = event.handleObj;

			// For mouseenter/leave call the handler if related is outside the target.
			// NB: No relatedTarget if the mouse left/entered the browser window
			if ( !related || ( related !== target && !jQuery.contains( target, related ) ) ) {
				event.type = handleObj.origType;
				ret = handleObj.handler.apply( this, arguments );
				event.type = fix;
			}
			return ret;
		}
	};
} );

// IE submit delegation
if ( !support.submit ) {

	jQuery.event.special.submit = {
		setup: function() {

			// Only need this for delegated form submit events
			if ( jQuery.nodeName( this, "form" ) ) {
				return false;
			}

			// Lazy-add a submit handler when a descendant form may potentially be submitted
			jQuery.event.add( this, "click._submit keypress._submit", function( e ) {

				// Node name check avoids a VML-related crash in IE (#9807)
				var elem = e.target,
					form = jQuery.nodeName( elem, "input" ) || jQuery.nodeName( elem, "button" ) ?

						// Support: IE <=8
						// We use jQuery.prop instead of elem.form
						// to allow fixing the IE8 delegated submit issue (gh-2332)
						// by 3rd party polyfills/workarounds.
						jQuery.prop( elem, "form" ) :
						undefined;

				if ( form && !jQuery._data( form, "submit" ) ) {
					jQuery.event.add( form, "submit._submit", function( event ) {
						event._submitBubble = true;
					} );
					jQuery._data( form, "submit", true );
				}
			} );

			// return undefined since we don't need an event listener
		},

		postDispatch: function( event ) {

			// If form was submitted by the user, bubble the event up the tree
			if ( event._submitBubble ) {
				delete event._submitBubble;
				if ( this.parentNode && !event.isTrigger ) {
					jQuery.event.simulate( "submit", this.parentNode, event );
				}
			}
		},

		teardown: function() {

			// Only need this for delegated form submit events
			if ( jQuery.nodeName( this, "form" ) ) {
				return false;
			}

			// Remove delegated handlers; cleanData eventually reaps submit handlers attached above
			jQuery.event.remove( this, "._submit" );
		}
	};
}

// IE change delegation and checkbox/radio fix
if ( !support.change ) {

	jQuery.event.special.change = {

		setup: function() {

			if ( rformElems.test( this.nodeName ) ) {

				// IE doesn't fire change on a check/radio until blur; trigger it on click
				// after a propertychange. Eat the blur-change in special.change.handle.
				// This still fires onchange a second time for check/radio after blur.
				if ( this.type === "checkbox" || this.type === "radio" ) {
					jQuery.event.add( this, "propertychange._change", function( event ) {
						if ( event.originalEvent.propertyName === "checked" ) {
							this._justChanged = true;
						}
					} );
					jQuery.event.add( this, "click._change", function( event ) {
						if ( this._justChanged && !event.isTrigger ) {
							this._justChanged = false;
						}

						// Allow triggered, simulated change events (#11500)
						jQuery.event.simulate( "change", this, event );
					} );
				}
				return false;
			}

			// Delegated event; lazy-add a change handler on descendant inputs
			jQuery.event.add( this, "beforeactivate._change", function( e ) {
				var elem = e.target;

				if ( rformElems.test( elem.nodeName ) && !jQuery._data( elem, "change" ) ) {
					jQuery.event.add( elem, "change._change", function( event ) {
						if ( this.parentNode && !event.isSimulated && !event.isTrigger ) {
							jQuery.event.simulate( "change", this.parentNode, event );
						}
					} );
					jQuery._data( elem, "change", true );
				}
			} );
		},

		handle: function( event ) {
			var elem = event.target;

			// Swallow native change events from checkbox/radio, we already triggered them above
			if ( this !== elem || event.isSimulated || event.isTrigger ||
				( elem.type !== "radio" && elem.type !== "checkbox" ) ) {

				return event.handleObj.handler.apply( this, arguments );
			}
		},

		teardown: function() {
			jQuery.event.remove( this, "._change" );

			return !rformElems.test( this.nodeName );
		}
	};
}

// Support: Firefox
// Firefox doesn't have focus(in | out) events
// Related ticket - https://bugzilla.mozilla.org/show_bug.cgi?id=687787
//
// Support: Chrome, Safari
// focus(in | out) events fire after focus & blur events,
// which is spec violation - http://www.w3.org/TR/DOM-Level-3-Events/#events-focusevent-event-order
// Related ticket - https://code.google.com/p/chromium/issues/detail?id=449857
if ( !support.focusin ) {
	jQuery.each( { focus: "focusin", blur: "focusout" }, function( orig, fix ) {

		// Attach a single capturing handler on the document while someone wants focusin/focusout
		var handler = function( event ) {
			jQuery.event.simulate( fix, event.target, jQuery.event.fix( event ) );
		};

		jQuery.event.special[ fix ] = {
			setup: function() {
				var doc = this.ownerDocument || this,
					attaches = jQuery._data( doc, fix );

				if ( !attaches ) {
					doc.addEventListener( orig, handler, true );
				}
				jQuery._data( doc, fix, ( attaches || 0 ) + 1 );
			},
			teardown: function() {
				var doc = this.ownerDocument || this,
					attaches = jQuery._data( doc, fix ) - 1;

				if ( !attaches ) {
					doc.removeEventListener( orig, handler, true );
					jQuery._removeData( doc, fix );
				} else {
					jQuery._data( doc, fix, attaches );
				}
			}
		};
	} );
}

jQuery.fn.extend( {

	on: function( types, selector, data, fn ) {
		return on( this, types, selector, data, fn );
	},
	one: function( types, selector, data, fn ) {
		return on( this, types, selector, data, fn, 1 );
	},
	off: function( types, selector, fn ) {
		var handleObj, type;
		if ( types && types.preventDefault && types.handleObj ) {

			// ( event )  dispatched jQuery.Event
			handleObj = types.handleObj;
			jQuery( types.delegateTarget ).off(
				handleObj.namespace ?
					handleObj.origType + "." + handleObj.namespace :
					handleObj.origType,
				handleObj.selector,
				handleObj.handler
			);
			return this;
		}
		if ( typeof types === "object" ) {

			// ( types-object [, selector] )
			for ( type in types ) {
				this.off( type, selector, types[ type ] );
			}
			return this;
		}
		if ( selector === false || typeof selector === "function" ) {

			// ( types [, fn] )
			fn = selector;
			selector = undefined;
		}
		if ( fn === false ) {
			fn = returnFalse;
		}
		return this.each( function() {
			jQuery.event.remove( this, types, fn, selector );
		} );
	},

	trigger: function( type, data ) {
		return this.each( function() {
			jQuery.event.trigger( type, data, this );
		} );
	},
	triggerHandler: function( type, data ) {
		var elem = this[ 0 ];
		if ( elem ) {
			return jQuery.event.trigger( type, data, elem, true );
		}
	}
} );


var rinlinejQuery = / jQuery\d+="(?:null|\d+)"/g,
	rnoshimcache = new RegExp( "<(?:" + nodeNames + ")[\\s/>]", "i" ),
	rxhtmlTag = /<(?!area|br|col|embed|hr|img|input|link|meta|param)(([\w:-]+)[^>]*)\/>/gi,

	// Support: IE 10-11, Edge 10240+
	// In IE/Edge using regex groups here causes severe slowdowns.
	// See https://connect.microsoft.com/IE/feedback/details/1736512/
	rnoInnerhtml = /<script|<style|<link/i,

	// checked="checked" or checked
	rchecked = /checked\s*(?:[^=]|=\s*.checked.)/i,
	rscriptTypeMasked = /^true\/(.*)/,
	rcleanScript = /^\s*<!(?:\[CDATA\[|--)|(?:\]\]|--)>\s*$/g,
	safeFragment = createSafeFragment( document ),
	fragmentDiv = safeFragment.appendChild( document.createElement( "div" ) );

// Support: IE<8
// Manipulating tables requires a tbody
function manipulationTarget( elem, content ) {
	return jQuery.nodeName( elem, "table" ) &&
		jQuery.nodeName( content.nodeType !== 11 ? content : content.firstChild, "tr" ) ?

		elem.getElementsByTagName( "tbody" )[ 0 ] ||
			elem.appendChild( elem.ownerDocument.createElement( "tbody" ) ) :
		elem;
}

// Replace/restore the type attribute of script elements for safe DOM manipulation
function disableScript( elem ) {
	elem.type = ( jQuery.find.attr( elem, "type" ) !== null ) + "/" + elem.type;
	return elem;
}
function restoreScript( elem ) {
	var match = rscriptTypeMasked.exec( elem.type );
	if ( match ) {
		elem.type = match[ 1 ];
	} else {
		elem.removeAttribute( "type" );
	}
	return elem;
}

function cloneCopyEvent( src, dest ) {
	if ( dest.nodeType !== 1 || !jQuery.hasData( src ) ) {
		return;
	}

	var type, i, l,
		oldData = jQuery._data( src ),
		curData = jQuery._data( dest, oldData ),
		events = oldData.events;

	if ( events ) {
		delete curData.handle;
		curData.events = {};

		for ( type in events ) {
			for ( i = 0, l = events[ type ].length; i < l; i++ ) {
				jQuery.event.add( dest, type, events[ type ][ i ] );
			}
		}
	}

	// make the cloned public data object a copy from the original
	if ( curData.data ) {
		curData.data = jQuery.extend( {}, curData.data );
	}
}

function fixCloneNodeIssues( src, dest ) {
	var nodeName, e, data;

	// We do not need to do anything for non-Elements
	if ( dest.nodeType !== 1 ) {
		return;
	}

	nodeName = dest.nodeName.toLowerCase();

	// IE6-8 copies events bound via attachEvent when using cloneNode.
	if ( !support.noCloneEvent && dest[ jQuery.expando ] ) {
		data = jQuery._data( dest );

		for ( e in data.events ) {
			jQuery.removeEvent( dest, e, data.handle );
		}

		// Event data gets referenced instead of copied if the expando gets copied too
		dest.removeAttribute( jQuery.expando );
	}

	// IE blanks contents when cloning scripts, and tries to evaluate newly-set text
	if ( nodeName === "script" && dest.text !== src.text ) {
		disableScript( dest ).text = src.text;
		restoreScript( dest );

	// IE6-10 improperly clones children of object elements using classid.
	// IE10 throws NoModificationAllowedError if parent is null, #12132.
	} else if ( nodeName === "object" ) {
		if ( dest.parentNode ) {
			dest.outerHTML = src.outerHTML;
		}

		// This path appears unavoidable for IE9. When cloning an object
		// element in IE9, the outerHTML strategy above is not sufficient.
		// If the src has innerHTML and the destination does not,
		// copy the src.innerHTML into the dest.innerHTML. #10324
		if ( support.html5Clone && ( src.innerHTML && !jQuery.trim( dest.innerHTML ) ) ) {
			dest.innerHTML = src.innerHTML;
		}

	} else if ( nodeName === "input" && rcheckableType.test( src.type ) ) {

		// IE6-8 fails to persist the checked state of a cloned checkbox
		// or radio button. Worse, IE6-7 fail to give the cloned element
		// a checked appearance if the defaultChecked value isn't also set

		dest.defaultChecked = dest.checked = src.checked;

		// IE6-7 get confused and end up setting the value of a cloned
		// checkbox/radio button to an empty string instead of "on"
		if ( dest.value !== src.value ) {
			dest.value = src.value;
		}

	// IE6-8 fails to return the selected option to the default selected
	// state when cloning options
	} else if ( nodeName === "option" ) {
		dest.defaultSelected = dest.selected = src.defaultSelected;

	// IE6-8 fails to set the defaultValue to the correct value when
	// cloning other types of input fields
	} else if ( nodeName === "input" || nodeName === "textarea" ) {
		dest.defaultValue = src.defaultValue;
	}
}

function domManip( collection, args, callback, ignored ) {

	// Flatten any nested arrays
	args = concat.apply( [], args );

	var first, node, hasScripts,
		scripts, doc, fragment,
		i = 0,
		l = collection.length,
		iNoClone = l - 1,
		value = args[ 0 ],
		isFunction = jQuery.isFunction( value );

	// We can't cloneNode fragments that contain checked, in WebKit
	if ( isFunction ||
			( l > 1 && typeof value === "string" &&
				!support.checkClone && rchecked.test( value ) ) ) {
		return collection.each( function( index ) {
			var self = collection.eq( index );
			if ( isFunction ) {
				args[ 0 ] = value.call( this, index, self.html() );
			}
			domManip( self, args, callback, ignored );
		} );
	}

	if ( l ) {
		fragment = buildFragment( args, collection[ 0 ].ownerDocument, false, collection, ignored );
		first = fragment.firstChild;

		if ( fragment.childNodes.length === 1 ) {
			fragment = first;
		}

		// Require either new content or an interest in ignored elements to invoke the callback
		if ( first || ignored ) {
			scripts = jQuery.map( getAll( fragment, "script" ), disableScript );
			hasScripts = scripts.length;

			// Use the original fragment for the last item
			// instead of the first because it can end up
			// being emptied incorrectly in certain situations (#8070).
			for ( ; i < l; i++ ) {
				node = fragment;

				if ( i !== iNoClone ) {
					node = jQuery.clone( node, true, true );

					// Keep references to cloned scripts for later restoration
					if ( hasScripts ) {

						// Support: Android<4.1, PhantomJS<2
						// push.apply(_, arraylike) throws on ancient WebKit
						jQuery.merge( scripts, getAll( node, "script" ) );
					}
				}

				callback.call( collection[ i ], node, i );
			}

			if ( hasScripts ) {
				doc = scripts[ scripts.length - 1 ].ownerDocument;

				// Reenable scripts
				jQuery.map( scripts, restoreScript );

				// Evaluate executable scripts on first document insertion
				for ( i = 0; i < hasScripts; i++ ) {
					node = scripts[ i ];
					if ( rscriptType.test( node.type || "" ) &&
						!jQuery._data( node, "globalEval" ) &&
						jQuery.contains( doc, node ) ) {

						if ( node.src ) {

							// Optional AJAX dependency, but won't run scripts if not present
							if ( jQuery._evalUrl ) {
								jQuery._evalUrl( node.src );
							}
						} else {
							jQuery.globalEval(
								( node.text || node.textContent || node.innerHTML || "" )
									.replace( rcleanScript, "" )
							);
						}
					}
				}
			}

			// Fix #11809: Avoid leaking memory
			fragment = first = null;
		}
	}

	return collection;
}

function remove( elem, selector, keepData ) {
	var node,
		elems = selector ? jQuery.filter( selector, elem ) : elem,
		i = 0;

	for ( ; ( node = elems[ i ] ) != null; i++ ) {

		if ( !keepData && node.nodeType === 1 ) {
			jQuery.cleanData( getAll( node ) );
		}

		if ( node.parentNode ) {
			if ( keepData && jQuery.contains( node.ownerDocument, node ) ) {
				setGlobalEval( getAll( node, "script" ) );
			}
			node.parentNode.removeChild( node );
		}
	}

	return elem;
}

jQuery.extend( {
	htmlPrefilter: function( html ) {
		return html.replace( rxhtmlTag, "<$1></$2>" );
	},

	clone: function( elem, dataAndEvents, deepDataAndEvents ) {
		var destElements, node, clone, i, srcElements,
			inPage = jQuery.contains( elem.ownerDocument, elem );

		if ( support.html5Clone || jQuery.isXMLDoc( elem ) ||
			!rnoshimcache.test( "<" + elem.nodeName + ">" ) ) {

			clone = elem.cloneNode( true );

		// IE<=8 does not properly clone detached, unknown element nodes
		} else {
			fragmentDiv.innerHTML = elem.outerHTML;
			fragmentDiv.removeChild( clone = fragmentDiv.firstChild );
		}

		if ( ( !support.noCloneEvent || !support.noCloneChecked ) &&
				( elem.nodeType === 1 || elem.nodeType === 11 ) && !jQuery.isXMLDoc( elem ) ) {

			// We eschew Sizzle here for performance reasons: http://jsperf.com/getall-vs-sizzle/2
			destElements = getAll( clone );
			srcElements = getAll( elem );

			// Fix all IE cloning issues
			for ( i = 0; ( node = srcElements[ i ] ) != null; ++i ) {

				// Ensure that the destination node is not null; Fixes #9587
				if ( destElements[ i ] ) {
					fixCloneNodeIssues( node, destElements[ i ] );
				}
			}
		}

		// Copy the events from the original to the clone
		if ( dataAndEvents ) {
			if ( deepDataAndEvents ) {
				srcElements = srcElements || getAll( elem );
				destElements = destElements || getAll( clone );

				for ( i = 0; ( node = srcElements[ i ] ) != null; i++ ) {
					cloneCopyEvent( node, destElements[ i ] );
				}
			} else {
				cloneCopyEvent( elem, clone );
			}
		}

		// Preserve script evaluation history
		destElements = getAll( clone, "script" );
		if ( destElements.length > 0 ) {
			setGlobalEval( destElements, !inPage && getAll( elem, "script" ) );
		}

		destElements = srcElements = node = null;

		// Return the cloned set
		return clone;
	},

	cleanData: function( elems, /* internal */ forceAcceptData ) {
		var elem, type, id, data,
			i = 0,
			internalKey = jQuery.expando,
			cache = jQuery.cache,
			attributes = support.attributes,
			special = jQuery.event.special;

		for ( ; ( elem = elems[ i ] ) != null; i++ ) {
			if ( forceAcceptData || acceptData( elem ) ) {

				id = elem[ internalKey ];
				data = id && cache[ id ];

				if ( data ) {
					if ( data.events ) {
						for ( type in data.events ) {
							if ( special[ type ] ) {
								jQuery.event.remove( elem, type );

							// This is a shortcut to avoid jQuery.event.remove's overhead
							} else {
								jQuery.removeEvent( elem, type, data.handle );
							}
						}
					}

					// Remove cache only if it was not already removed by jQuery.event.remove
					if ( cache[ id ] ) {

						delete cache[ id ];

						// Support: IE<9
						// IE does not allow us to delete expando properties from nodes
						// IE creates expando attributes along with the property
						// IE does not have a removeAttribute function on Document nodes
						if ( !attributes && typeof elem.removeAttribute !== "undefined" ) {
							elem.removeAttribute( internalKey );

						// Webkit & Blink performance suffers when deleting properties
						// from DOM nodes, so set to undefined instead
						// https://code.google.com/p/chromium/issues/detail?id=378607
						} else {
							elem[ internalKey ] = undefined;
						}

						deletedIds.push( id );
					}
				}
			}
		}
	}
} );

jQuery.fn.extend( {

	// Keep domManip exposed until 3.0 (gh-2225)
	domManip: domManip,

	detach: function( selector ) {
		return remove( this, selector, true );
	},

	remove: function( selector ) {
		return remove( this, selector );
	},

	text: function( value ) {
		return access( this, function( value ) {
			return value === undefined ?
				jQuery.text( this ) :
				this.empty().append(
					( this[ 0 ] && this[ 0 ].ownerDocument || document ).createTextNode( value )
				);
		}, null, value, arguments.length );
	},

	append: function() {
		return domManip( this, arguments, function( elem ) {
			if ( this.nodeType === 1 || this.nodeType === 11 || this.nodeType === 9 ) {
				var target = manipulationTarget( this, elem );
				target.appendChild( elem );
			}
		} );
	},

	prepend: function() {
		return domManip( this, arguments, function( elem ) {
			if ( this.nodeType === 1 || this.nodeType === 11 || this.nodeType === 9 ) {
				var target = manipulationTarget( this, elem );
				target.insertBefore( elem, target.firstChild );
			}
		} );
	},

	before: function() {
		return domManip( this, arguments, function( elem ) {
			if ( this.parentNode ) {
				this.parentNode.insertBefore( elem, this );
			}
		} );
	},

	after: function() {
		return domManip( this, arguments, function( elem ) {
			if ( this.parentNode ) {
				this.parentNode.insertBefore( elem, this.nextSibling );
			}
		} );
	},

	empty: function() {
		var elem,
			i = 0;

		for ( ; ( elem = this[ i ] ) != null; i++ ) {

			// Remove element nodes and prevent memory leaks
			if ( elem.nodeType === 1 ) {
				jQuery.cleanData( getAll( elem, false ) );
			}

			// Remove any remaining nodes
			while ( elem.firstChild ) {
				elem.removeChild( elem.firstChild );
			}

			// If this is a select, ensure that it displays empty (#12336)
			// Support: IE<9
			if ( elem.options && jQuery.nodeName( elem, "select" ) ) {
				elem.options.length = 0;
			}
		}

		return this;
	},

	clone: function( dataAndEvents, deepDataAndEvents ) {
		dataAndEvents = dataAndEvents == null ? false : dataAndEvents;
		deepDataAndEvents = deepDataAndEvents == null ? dataAndEvents : deepDataAndEvents;

		return this.map( function() {
			return jQuery.clone( this, dataAndEvents, deepDataAndEvents );
		} );
	},

	html: function( value ) {
		return access( this, function( value ) {
			var elem = this[ 0 ] || {},
				i = 0,
				l = this.length;

			if ( value === undefined ) {
				return elem.nodeType === 1 ?
					elem.innerHTML.replace( rinlinejQuery, "" ) :
					undefined;
			}

			// See if we can take a shortcut and just use innerHTML
			if ( typeof value === "string" && !rnoInnerhtml.test( value ) &&
				( support.htmlSerialize || !rnoshimcache.test( value )  ) &&
				( support.leadingWhitespace || !rleadingWhitespace.test( value ) ) &&
				!wrapMap[ ( rtagName.exec( value ) || [ "", "" ] )[ 1 ].toLowerCase() ] ) {

				value = jQuery.htmlPrefilter( value );

				try {
					for ( ; i < l; i++ ) {

						// Remove element nodes and prevent memory leaks
						elem = this[ i ] || {};
						if ( elem.nodeType === 1 ) {
							jQuery.cleanData( getAll( elem, false ) );
							elem.innerHTML = value;
						}
					}

					elem = 0;

				// If using innerHTML throws an exception, use the fallback method
				} catch ( e ) {}
			}

			if ( elem ) {
				this.empty().append( value );
			}
		}, null, value, arguments.length );
	},

	replaceWith: function() {
		var ignored = [];

		// Make the changes, replacing each non-ignored context element with the new content
		return domManip( this, arguments, function( elem ) {
			var parent = this.parentNode;

			if ( jQuery.inArray( this, ignored ) < 0 ) {
				jQuery.cleanData( getAll( this ) );
				if ( parent ) {
					parent.replaceChild( elem, this );
				}
			}

		// Force callback invocation
		}, ignored );
	}
} );

jQuery.each( {
	appendTo: "append",
	prependTo: "prepend",
	insertBefore: "before",
	insertAfter: "after",
	replaceAll: "replaceWith"
}, function( name, original ) {
	jQuery.fn[ name ] = function( selector ) {
		var elems,
			i = 0,
			ret = [],
			insert = jQuery( selector ),
			last = insert.length - 1;

		for ( ; i <= last; i++ ) {
			elems = i === last ? this : this.clone( true );
			jQuery( insert[ i ] )[ original ]( elems );

			// Modern browsers can apply jQuery collections as arrays, but oldIE needs a .get()
			push.apply( ret, elems.get() );
		}

		return this.pushStack( ret );
	};
} );


var iframe,
	elemdisplay = {

		// Support: Firefox
		// We have to pre-define these values for FF (#10227)
		HTML: "block",
		BODY: "block"
	};

/**
 * Retrieve the actual display of a element
 * @param {String} name nodeName of the element
 * @param {Object} doc Document object
 */

// Called only from within defaultDisplay
function actualDisplay( name, doc ) {
	var elem = jQuery( doc.createElement( name ) ).appendTo( doc.body ),

		display = jQuery.css( elem[ 0 ], "display" );

	// We don't have any data stored on the element,
	// so use "detach" method as fast way to get rid of the element
	elem.detach();

	return display;
}

/**
 * Try to determine the default display value of an element
 * @param {String} nodeName
 */
function defaultDisplay( nodeName ) {
	var doc = document,
		display = elemdisplay[ nodeName ];

	if ( !display ) {
		display = actualDisplay( nodeName, doc );

		// If the simple way fails, read from inside an iframe
		if ( display === "none" || !display ) {

			// Use the already-created iframe if possible
			iframe = ( iframe || jQuery( "<iframe frameborder='0' width='0' height='0'/>" ) )
				.appendTo( doc.documentElement );

			// Always write a new HTML skeleton so Webkit and Firefox don't choke on reuse
			doc = ( iframe[ 0 ].contentWindow || iframe[ 0 ].contentDocument ).document;

			// Support: IE
			doc.write();
			doc.close();

			display = actualDisplay( nodeName, doc );
			iframe.detach();
		}

		// Store the correct default display
		elemdisplay[ nodeName ] = display;
	}

	return display;
}
var rmargin = ( /^margin/ );

var rnumnonpx = new RegExp( "^(" + pnum + ")(?!px)[a-z%]+$", "i" );

var swap = function( elem, options, callback, args ) {
	var ret, name,
		old = {};

	// Remember the old values, and insert the new ones
	for ( name in options ) {
		old[ name ] = elem.style[ name ];
		elem.style[ name ] = options[ name ];
	}

	ret = callback.apply( elem, args || [] );

	// Revert the old values
	for ( name in options ) {
		elem.style[ name ] = old[ name ];
	}

	return ret;
};


var documentElement = document.documentElement;



( function() {
	var pixelPositionVal, pixelMarginRightVal, boxSizingReliableVal,
		reliableHiddenOffsetsVal, reliableMarginRightVal, reliableMarginLeftVal,
		container = document.createElement( "div" ),
		div = document.createElement( "div" );

	// Finish early in limited (non-browser) environments
	if ( !div.style ) {
		return;
	}

	div.style.cssText = "float:left;opacity:.5";

	// Support: IE<9
	// Make sure that element opacity exists (as opposed to filter)
	support.opacity = div.style.opacity === "0.5";

	// Verify style float existence
	// (IE uses styleFloat instead of cssFloat)
	support.cssFloat = !!div.style.cssFloat;

	div.style.backgroundClip = "content-box";
	div.cloneNode( true ).style.backgroundClip = "";
	support.clearCloneStyle = div.style.backgroundClip === "content-box";

	container = document.createElement( "div" );
	container.style.cssText = "border:0;width:8px;height:0;top:0;left:-9999px;" +
		"padding:0;margin-top:1px;position:absolute";
	div.innerHTML = "";
	container.appendChild( div );

	// Support: Firefox<29, Android 2.3
	// Vendor-prefix box-sizing
	support.boxSizing = div.style.boxSizing === "" || div.style.MozBoxSizing === "" ||
		div.style.WebkitBoxSizing === "";

	jQuery.extend( support, {
		reliableHiddenOffsets: function() {
			if ( pixelPositionVal == null ) {
				computeStyleTests();
			}
			return reliableHiddenOffsetsVal;
		},

		boxSizingReliable: function() {

			// We're checking for pixelPositionVal here instead of boxSizingReliableVal
			// since that compresses better and they're computed together anyway.
			if ( pixelPositionVal == null ) {
				computeStyleTests();
			}
			return boxSizingReliableVal;
		},

		pixelMarginRight: function() {

			// Support: Android 4.0-4.3
			if ( pixelPositionVal == null ) {
				computeStyleTests();
			}
			return pixelMarginRightVal;
		},

		pixelPosition: function() {
			if ( pixelPositionVal == null ) {
				computeStyleTests();
			}
			return pixelPositionVal;
		},

		reliableMarginRight: function() {

			// Support: Android 2.3
			if ( pixelPositionVal == null ) {
				computeStyleTests();
			}
			return reliableMarginRightVal;
		},

		reliableMarginLeft: function() {

			// Support: IE <=8 only, Android 4.0 - 4.3 only, Firefox <=3 - 37
			if ( pixelPositionVal == null ) {
				computeStyleTests();
			}
			return reliableMarginLeftVal;
		}
	} );

	function computeStyleTests() {
		var contents, divStyle,
			documentElement = document.documentElement;

		// Setup
		documentElement.appendChild( container );

		div.style.cssText =

			// Support: Android 2.3
			// Vendor-prefix box-sizing
			"-webkit-box-sizing:border-box;box-sizing:border-box;" +
			"position:relative;display:block;" +
			"margin:auto;border:1px;padding:1px;" +
			"top:1%;width:50%";

		// Support: IE<9
		// Assume reasonable values in the absence of getComputedStyle
		pixelPositionVal = boxSizingReliableVal = reliableMarginLeftVal = false;
		pixelMarginRightVal = reliableMarginRightVal = true;

		// Check for getComputedStyle so that this code is not run in IE<9.
		if ( window.getComputedStyle ) {
			divStyle = window.getComputedStyle( div );
			pixelPositionVal = ( divStyle || {} ).top !== "1%";
			reliableMarginLeftVal = ( divStyle || {} ).marginLeft === "2px";
			boxSizingReliableVal = ( divStyle || { width: "4px" } ).width === "4px";

			// Support: Android 4.0 - 4.3 only
			// Some styles come back with percentage values, even though they shouldn't
			div.style.marginRight = "50%";
			pixelMarginRightVal = ( divStyle || { marginRight: "4px" } ).marginRight === "4px";

			// Support: Android 2.3 only
			// Div with explicit width and no margin-right incorrectly
			// gets computed margin-right based on width of container (#3333)
			// WebKit Bug 13343 - getComputedStyle returns wrong value for margin-right
			contents = div.appendChild( document.createElement( "div" ) );

			// Reset CSS: box-sizing; display; margin; border; padding
			contents.style.cssText = div.style.cssText =

				// Support: Android 2.3
				// Vendor-prefix box-sizing
				"-webkit-box-sizing:content-box;-moz-box-sizing:content-box;" +
				"box-sizing:content-box;display:block;margin:0;border:0;padding:0";
			contents.style.marginRight = contents.style.width = "0";
			div.style.width = "1px";

			reliableMarginRightVal =
				!parseFloat( ( window.getComputedStyle( contents ) || {} ).marginRight );

			div.removeChild( contents );
		}

		// Support: IE6-8
		// First check that getClientRects works as expected
		// Check if table cells still have offsetWidth/Height when they are set
		// to display:none and there are still other visible table cells in a
		// table row; if so, offsetWidth/Height are not reliable for use when
		// determining if an element has been hidden directly using
		// display:none (it is still safe to use offsets if a parent element is
		// hidden; don safety goggles and see bug #4512 for more information).
		div.style.display = "none";
		reliableHiddenOffsetsVal = div.getClientRects().length === 0;
		if ( reliableHiddenOffsetsVal ) {
			div.style.display = "";
			div.innerHTML = "<table><tr><td></td><td>t</td></tr></table>";
			div.childNodes[ 0 ].style.borderCollapse = "separate";
			contents = div.getElementsByTagName( "td" );
			contents[ 0 ].style.cssText = "margin:0;border:0;padding:0;display:none";
			reliableHiddenOffsetsVal = contents[ 0 ].offsetHeight === 0;
			if ( reliableHiddenOffsetsVal ) {
				contents[ 0 ].style.display = "";
				contents[ 1 ].style.display = "none";
				reliableHiddenOffsetsVal = contents[ 0 ].offsetHeight === 0;
			}
		}

		// Teardown
		documentElement.removeChild( container );
	}

} )();


var getStyles, curCSS,
	rposition = /^(top|right|bottom|left)$/;

if ( window.getComputedStyle ) {
	getStyles = function( elem ) {

		// Support: IE<=11+, Firefox<=30+ (#15098, #14150)
		// IE throws on elements created in popups
		// FF meanwhile throws on frame elements through "defaultView.getComputedStyle"
		var view = elem.ownerDocument.defaultView;

		if ( !view || !view.opener ) {
			view = window;
		}

		return view.getComputedStyle( elem );
	};

	curCSS = function( elem, name, computed ) {
		var width, minWidth, maxWidth, ret,
			style = elem.style;

		computed = computed || getStyles( elem );

		// getPropertyValue is only needed for .css('filter') in IE9, see #12537
		ret = computed ? computed.getPropertyValue( name ) || computed[ name ] : undefined;

		// Support: Opera 12.1x only
		// Fall back to style even without computed
		// computed is undefined for elems on document fragments
		if ( ( ret === "" || ret === undefined ) && !jQuery.contains( elem.ownerDocument, elem ) ) {
			ret = jQuery.style( elem, name );
		}

		if ( computed ) {

			// A tribute to the "awesome hack by Dean Edwards"
			// Chrome < 17 and Safari 5.0 uses "computed value"
			// instead of "used value" for margin-right
			// Safari 5.1.7 (at least) returns percentage for a larger set of values,
			// but width seems to be reliably pixels
			// this is against the CSSOM draft spec:
			// http://dev.w3.org/csswg/cssom/#resolved-values
			if ( !support.pixelMarginRight() && rnumnonpx.test( ret ) && rmargin.test( name ) ) {

				// Remember the original values
				width = style.width;
				minWidth = style.minWidth;
				maxWidth = style.maxWidth;

				// Put in the new values to get a computed value out
				style.minWidth = style.maxWidth = style.width = ret;
				ret = computed.width;

				// Revert the changed values
				style.width = width;
				style.minWidth = minWidth;
				style.maxWidth = maxWidth;
			}
		}

		// Support: IE
		// IE returns zIndex value as an integer.
		return ret === undefined ?
			ret :
			ret + "";
	};
} else if ( documentElement.currentStyle ) {
	getStyles = function( elem ) {
		return elem.currentStyle;
	};

	curCSS = function( elem, name, computed ) {
		var left, rs, rsLeft, ret,
			style = elem.style;

		computed = computed || getStyles( elem );
		ret = computed ? computed[ name ] : undefined;

		// Avoid setting ret to empty string here
		// so we don't default to auto
		if ( ret == null && style && style[ name ] ) {
			ret = style[ name ];
		}

		// From the awesome hack by Dean Edwards
		// http://erik.eae.net/archives/2007/07/27/18.54.15/#comment-102291

		// If we're not dealing with a regular pixel number
		// but a number that has a weird ending, we need to convert it to pixels
		// but not position css attributes, as those are
		// proportional to the parent element instead
		// and we can't measure the parent instead because it
		// might trigger a "stacking dolls" problem
		if ( rnumnonpx.test( ret ) && !rposition.test( name ) ) {

			// Remember the original values
			left = style.left;
			rs = elem.runtimeStyle;
			rsLeft = rs && rs.left;

			// Put in the new values to get a computed value out
			if ( rsLeft ) {
				rs.left = elem.currentStyle.left;
			}
			style.left = name === "fontSize" ? "1em" : ret;
			ret = style.pixelLeft + "px";

			// Revert the changed values
			style.left = left;
			if ( rsLeft ) {
				rs.left = rsLeft;
			}
		}

		// Support: IE
		// IE returns zIndex value as an integer.
		return ret === undefined ?
			ret :
			ret + "" || "auto";
	};
}




function addGetHookIf( conditionFn, hookFn ) {

	// Define the hook, we'll check on the first run if it's really needed.
	return {
		get: function() {
			if ( conditionFn() ) {

				// Hook not needed (or it's not possible to use it due
				// to missing dependency), remove it.
				delete this.get;
				return;
			}

			// Hook needed; redefine it so that the support test is not executed again.
			return ( this.get = hookFn ).apply( this, arguments );
		}
	};
}


var

		ralpha = /alpha\([^)]*\)/i,
	ropacity = /opacity\s*=\s*([^)]*)/i,

	// swappable if display is none or starts with table except
	// "table", "table-cell", or "table-caption"
	// see here for display values:
	// https://developer.mozilla.org/en-US/docs/CSS/display
	rdisplayswap = /^(none|table(?!-c[ea]).+)/,
	rnumsplit = new RegExp( "^(" + pnum + ")(.*)$", "i" ),

	cssShow = { position: "absolute", visibility: "hidden", display: "block" },
	cssNormalTransform = {
		letterSpacing: "0",
		fontWeight: "400"
	},

	cssPrefixes = [ "Webkit", "O", "Moz", "ms" ],
	emptyStyle = document.createElement( "div" ).style;


// return a css property mapped to a potentially vendor prefixed property
function vendorPropName( name ) {

	// shortcut for names that are not vendor prefixed
	if ( name in emptyStyle ) {
		return name;
	}

	// check for vendor prefixed names
	var capName = name.charAt( 0 ).toUpperCase() + name.slice( 1 ),
		i = cssPrefixes.length;

	while ( i-- ) {
		name = cssPrefixes[ i ] + capName;
		if ( name in emptyStyle ) {
			return name;
		}
	}
}

function showHide( elements, show ) {
	var display, elem, hidden,
		values = [],
		index = 0,
		length = elements.length;

	for ( ; index < length; index++ ) {
		elem = elements[ index ];
		if ( !elem.style ) {
			continue;
		}

		values[ index ] = jQuery._data( elem, "olddisplay" );
		display = elem.style.display;
		if ( show ) {

			// Reset the inline display of this element to learn if it is
			// being hidden by cascaded rules or not
			if ( !values[ index ] && display === "none" ) {
				elem.style.display = "";
			}

			// Set elements which have been overridden with display: none
			// in a stylesheet to whatever the default browser style is
			// for such an element
			if ( elem.style.display === "" && isHidden( elem ) ) {
				values[ index ] =
					jQuery._data( elem, "olddisplay", defaultDisplay( elem.nodeName ) );
			}
		} else {
			hidden = isHidden( elem );

			if ( display && display !== "none" || !hidden ) {
				jQuery._data(
					elem,
					"olddisplay",
					hidden ? display : jQuery.css( elem, "display" )
				);
			}
		}
	}

	// Set the display of most of the elements in a second loop
	// to avoid the constant reflow
	for ( index = 0; index < length; index++ ) {
		elem = elements[ index ];
		if ( !elem.style ) {
			continue;
		}
		if ( !show || elem.style.display === "none" || elem.style.display === "" ) {
			elem.style.display = show ? values[ index ] || "" : "none";
		}
	}

	return elements;
}

function setPositiveNumber( elem, value, subtract ) {
	var matches = rnumsplit.exec( value );
	return matches ?

		// Guard against undefined "subtract", e.g., when used as in cssHooks
		Math.max( 0, matches[ 1 ] - ( subtract || 0 ) ) + ( matches[ 2 ] || "px" ) :
		value;
}

function augmentWidthOrHeight( elem, name, extra, isBorderBox, styles ) {
	var i = extra === ( isBorderBox ? "border" : "content" ) ?

		// If we already have the right measurement, avoid augmentation
		4 :

		// Otherwise initialize for horizontal or vertical properties
		name === "width" ? 1 : 0,

		val = 0;

	for ( ; i < 4; i += 2 ) {

		// both box models exclude margin, so add it if we want it
		if ( extra === "margin" ) {
			val += jQuery.css( elem, extra + cssExpand[ i ], true, styles );
		}

		if ( isBorderBox ) {

			// border-box includes padding, so remove it if we want content
			if ( extra === "content" ) {
				val -= jQuery.css( elem, "padding" + cssExpand[ i ], true, styles );
			}

			// at this point, extra isn't border nor margin, so remove border
			if ( extra !== "margin" ) {
				val -= jQuery.css( elem, "border" + cssExpand[ i ] + "Width", true, styles );
			}
		} else {

			// at this point, extra isn't content, so add padding
			val += jQuery.css( elem, "padding" + cssExpand[ i ], true, styles );

			// at this point, extra isn't content nor padding, so add border
			if ( extra !== "padding" ) {
				val += jQuery.css( elem, "border" + cssExpand[ i ] + "Width", true, styles );
			}
		}
	}

	return val;
}

function getWidthOrHeight( elem, name, extra ) {

	// Start with offset property, which is equivalent to the border-box value
	var valueIsBorderBox = true,
		val = name === "width" ? elem.offsetWidth : elem.offsetHeight,
		styles = getStyles( elem ),
		isBorderBox = support.boxSizing &&
			jQuery.css( elem, "boxSizing", false, styles ) === "border-box";

	// some non-html elements return undefined for offsetWidth, so check for null/undefined
	// svg - https://bugzilla.mozilla.org/show_bug.cgi?id=649285
	// MathML - https://bugzilla.mozilla.org/show_bug.cgi?id=491668
	if ( val <= 0 || val == null ) {

		// Fall back to computed then uncomputed css if necessary
		val = curCSS( elem, name, styles );
		if ( val < 0 || val == null ) {
			val = elem.style[ name ];
		}

		// Computed unit is not pixels. Stop here and return.
		if ( rnumnonpx.test( val ) ) {
			return val;
		}

		// we need the check for style in case a browser which returns unreliable values
		// for getComputedStyle silently falls back to the reliable elem.style
		valueIsBorderBox = isBorderBox &&
			( support.boxSizingReliable() || val === elem.style[ name ] );

		// Normalize "", auto, and prepare for extra
		val = parseFloat( val ) || 0;
	}

	// use the active box-sizing model to add/subtract irrelevant styles
	return ( val +
		augmentWidthOrHeight(
			elem,
			name,
			extra || ( isBorderBox ? "border" : "content" ),
			valueIsBorderBox,
			styles
		)
	) + "px";
}

jQuery.extend( {

	// Add in style property hooks for overriding the default
	// behavior of getting and setting a style property
	cssHooks: {
		opacity: {
			get: function( elem, computed ) {
				if ( computed ) {

					// We should always get a number back from opacity
					var ret = curCSS( elem, "opacity" );
					return ret === "" ? "1" : ret;
				}
			}
		}
	},

	// Don't automatically add "px" to these possibly-unitless properties
	cssNumber: {
		"animationIterationCount": true,
		"columnCount": true,
		"fillOpacity": true,
		"flexGrow": true,
		"flexShrink": true,
		"fontWeight": true,
		"lineHeight": true,
		"opacity": true,
		"order": true,
		"orphans": true,
		"widows": true,
		"zIndex": true,
		"zoom": true
	},

	// Add in properties whose names you wish to fix before
	// setting or getting the value
	cssProps: {

		// normalize float css property
		"float": support.cssFloat ? "cssFloat" : "styleFloat"
	},

	// Get and set the style property on a DOM Node
	style: function( elem, name, value, extra ) {

		// Don't set styles on text and comment nodes
		if ( !elem || elem.nodeType === 3 || elem.nodeType === 8 || !elem.style ) {
			return;
		}

		// Make sure that we're working with the right name
		var ret, type, hooks,
			origName = jQuery.camelCase( name ),
			style = elem.style;

		name = jQuery.cssProps[ origName ] ||
			( jQuery.cssProps[ origName ] = vendorPropName( origName ) || origName );

		// gets hook for the prefixed version
		// followed by the unprefixed version
		hooks = jQuery.cssHooks[ name ] || jQuery.cssHooks[ origName ];

		// Check if we're setting a value
		if ( value !== undefined ) {
			type = typeof value;

			// Convert "+=" or "-=" to relative numbers (#7345)
			if ( type === "string" && ( ret = rcssNum.exec( value ) ) && ret[ 1 ] ) {
				value = adjustCSS( elem, name, ret );

				// Fixes bug #9237
				type = "number";
			}

			// Make sure that null and NaN values aren't set. See: #7116
			if ( value == null || value !== value ) {
				return;
			}

			// If a number was passed in, add the unit (except for certain CSS properties)
			if ( type === "number" ) {
				value += ret && ret[ 3 ] || ( jQuery.cssNumber[ origName ] ? "" : "px" );
			}

			// Fixes #8908, it can be done more correctly by specifing setters in cssHooks,
			// but it would mean to define eight
			// (for every problematic property) identical functions
			if ( !support.clearCloneStyle && value === "" && name.indexOf( "background" ) === 0 ) {
				style[ name ] = "inherit";
			}

			// If a hook was provided, use that value, otherwise just set the specified value
			if ( !hooks || !( "set" in hooks ) ||
				( value = hooks.set( elem, value, extra ) ) !== undefined ) {

				// Support: IE
				// Swallow errors from 'invalid' CSS values (#5509)
				try {
					style[ name ] = value;
				} catch ( e ) {}
			}

		} else {

			// If a hook was provided get the non-computed value from there
			if ( hooks && "get" in hooks &&
				( ret = hooks.get( elem, false, extra ) ) !== undefined ) {

				return ret;
			}

			// Otherwise just get the value from the style object
			return style[ name ];
		}
	},

	css: function( elem, name, extra, styles ) {
		var num, val, hooks,
			origName = jQuery.camelCase( name );

		// Make sure that we're working with the right name
		name = jQuery.cssProps[ origName ] ||
			( jQuery.cssProps[ origName ] = vendorPropName( origName ) || origName );

		// gets hook for the prefixed version
		// followed by the unprefixed version
		hooks = jQuery.cssHooks[ name ] || jQuery.cssHooks[ origName ];

		// If a hook was provided get the computed value from there
		if ( hooks && "get" in hooks ) {
			val = hooks.get( elem, true, extra );
		}

		// Otherwise, if a way to get the computed value exists, use that
		if ( val === undefined ) {
			val = curCSS( elem, name, styles );
		}

		//convert "normal" to computed value
		if ( val === "normal" && name in cssNormalTransform ) {
			val = cssNormalTransform[ name ];
		}

		// Return, converting to number if forced or a qualifier was provided and val looks numeric
		if ( extra === "" || extra ) {
			num = parseFloat( val );
			return extra === true || isFinite( num ) ? num || 0 : val;
		}
		return val;
	}
} );

jQuery.each( [ "height", "width" ], function( i, name ) {
	jQuery.cssHooks[ name ] = {
		get: function( elem, computed, extra ) {
			if ( computed ) {

				// certain elements can have dimension info if we invisibly show them
				// however, it must have a current display style that would benefit from this
				return rdisplayswap.test( jQuery.css( elem, "display" ) ) &&
					elem.offsetWidth === 0 ?
						swap( elem, cssShow, function() {
							return getWidthOrHeight( elem, name, extra );
						} ) :
						getWidthOrHeight( elem, name, extra );
			}
		},

		set: function( elem, value, extra ) {
			var styles = extra && getStyles( elem );
			return setPositiveNumber( elem, value, extra ?
				augmentWidthOrHeight(
					elem,
					name,
					extra,
					support.boxSizing &&
						jQuery.css( elem, "boxSizing", false, styles ) === "border-box",
					styles
				) : 0
			);
		}
	};
} );

if ( !support.opacity ) {
	jQuery.cssHooks.opacity = {
		get: function( elem, computed ) {

			// IE uses filters for opacity
			return ropacity.test( ( computed && elem.currentStyle ?
				elem.currentStyle.filter :
				elem.style.filter ) || "" ) ?
					( 0.01 * parseFloat( RegExp.$1 ) ) + "" :
					computed ? "1" : "";
		},

		set: function( elem, value ) {
			var style = elem.style,
				currentStyle = elem.currentStyle,
				opacity = jQuery.isNumeric( value ) ? "alpha(opacity=" + value * 100 + ")" : "",
				filter = currentStyle && currentStyle.filter || style.filter || "";

			// IE has trouble with opacity if it does not have layout
			// Force it by setting the zoom level
			style.zoom = 1;

			// if setting opacity to 1, and no other filters exist -
			// attempt to remove filter attribute #6652
			// if value === "", then remove inline opacity #12685
			if ( ( value >= 1 || value === "" ) &&
					jQuery.trim( filter.replace( ralpha, "" ) ) === "" &&
					style.removeAttribute ) {

				// Setting style.filter to null, "" & " " still leave "filter:" in the cssText
				// if "filter:" is present at all, clearType is disabled, we want to avoid this
				// style.removeAttribute is IE Only, but so apparently is this code path...
				style.removeAttribute( "filter" );

				// if there is no filter style applied in a css rule
				// or unset inline opacity, we are done
				if ( value === "" || currentStyle && !currentStyle.filter ) {
					return;
				}
			}

			// otherwise, set new filter values
			style.filter = ralpha.test( filter ) ?
				filter.replace( ralpha, opacity ) :
				filter + " " + opacity;
		}
	};
}

jQuery.cssHooks.marginRight = addGetHookIf( support.reliableMarginRight,
	function( elem, computed ) {
		if ( computed ) {
			return swap( elem, { "display": "inline-block" },
				curCSS, [ elem, "marginRight" ] );
		}
	}
);

jQuery.cssHooks.marginLeft = addGetHookIf( support.reliableMarginLeft,
	function( elem, computed ) {
		if ( computed ) {
			return (
				parseFloat( curCSS( elem, "marginLeft" ) ) ||

				// Support: IE<=11+
				// Running getBoundingClientRect on a disconnected node in IE throws an error
				// Support: IE8 only
				// getClientRects() errors on disconnected elems
				( jQuery.contains( elem.ownerDocument, elem ) ?
					elem.getBoundingClientRect().left -
						swap( elem, { marginLeft: 0 }, function() {
							return elem.getBoundingClientRect().left;
						} ) :
					0
				)
			) + "px";
		}
	}
);

// These hooks are used by animate to expand properties
jQuery.each( {
	margin: "",
	padding: "",
	border: "Width"
}, function( prefix, suffix ) {
	jQuery.cssHooks[ prefix + suffix ] = {
		expand: function( value ) {
			var i = 0,
				expanded = {},

				// assumes a single number if not a string
				parts = typeof value === "string" ? value.split( " " ) : [ value ];

			for ( ; i < 4; i++ ) {
				expanded[ prefix + cssExpand[ i ] + suffix ] =
					parts[ i ] || parts[ i - 2 ] || parts[ 0 ];
			}

			return expanded;
		}
	};

	if ( !rmargin.test( prefix ) ) {
		jQuery.cssHooks[ prefix + suffix ].set = setPositiveNumber;
	}
} );

jQuery.fn.extend( {
	css: function( name, value ) {
		return access( this, function( elem, name, value ) {
			var styles, len,
				map = {},
				i = 0;

			if ( jQuery.isArray( name ) ) {
				styles = getStyles( elem );
				len = name.length;

				for ( ; i < len; i++ ) {
					map[ name[ i ] ] = jQuery.css( elem, name[ i ], false, styles );
				}

				return map;
			}

			return value !== undefined ?
				jQuery.style( elem, name, value ) :
				jQuery.css( elem, name );
		}, name, value, arguments.length > 1 );
	},
	show: function() {
		return showHide( this, true );
	},
	hide: function() {
		return showHide( this );
	},
	toggle: function( state ) {
		if ( typeof state === "boolean" ) {
			return state ? this.show() : this.hide();
		}

		return this.each( function() {
			if ( isHidden( this ) ) {
				jQuery( this ).show();
			} else {
				jQuery( this ).hide();
			}
		} );
	}
} );


function Tween( elem, options, prop, end, easing ) {
	return new Tween.prototype.init( elem, options, prop, end, easing );
}
jQuery.Tween = Tween;

Tween.prototype = {
	constructor: Tween,
	init: function( elem, options, prop, end, easing, unit ) {
		this.elem = elem;
		this.prop = prop;
		this.easing = easing || jQuery.easing._default;
		this.options = options;
		this.start = this.now = this.cur();
		this.end = end;
		this.unit = unit || ( jQuery.cssNumber[ prop ] ? "" : "px" );
	},
	cur: function() {
		var hooks = Tween.propHooks[ this.prop ];

		return hooks && hooks.get ?
			hooks.get( this ) :
			Tween.propHooks._default.get( this );
	},
	run: function( percent ) {
		var eased,
			hooks = Tween.propHooks[ this.prop ];

		if ( this.options.duration ) {
			this.pos = eased = jQuery.easing[ this.easing ](
				percent, this.options.duration * percent, 0, 1, this.options.duration
			);
		} else {
			this.pos = eased = percent;
		}
		this.now = ( this.end - this.start ) * eased + this.start;

		if ( this.options.step ) {
			this.options.step.call( this.elem, this.now, this );
		}

		if ( hooks && hooks.set ) {
			hooks.set( this );
		} else {
			Tween.propHooks._default.set( this );
		}
		return this;
	}
};

Tween.prototype.init.prototype = Tween.prototype;

Tween.propHooks = {
	_default: {
		get: function( tween ) {
			var result;

			// Use a property on the element directly when it is not a DOM element,
			// or when there is no matching style property that exists.
			if ( tween.elem.nodeType !== 1 ||
				tween.elem[ tween.prop ] != null && tween.elem.style[ tween.prop ] == null ) {
				return tween.elem[ tween.prop ];
			}

			// passing an empty string as a 3rd parameter to .css will automatically
			// attempt a parseFloat and fallback to a string if the parse fails
			// so, simple values such as "10px" are parsed to Float.
			// complex values such as "rotate(1rad)" are returned as is.
			result = jQuery.css( tween.elem, tween.prop, "" );

			// Empty strings, null, undefined and "auto" are converted to 0.
			return !result || result === "auto" ? 0 : result;
		},
		set: function( tween ) {

			// use step hook for back compat - use cssHook if its there - use .style if its
			// available and use plain properties where available
			if ( jQuery.fx.step[ tween.prop ] ) {
				jQuery.fx.step[ tween.prop ]( tween );
			} else if ( tween.elem.nodeType === 1 &&
				( tween.elem.style[ jQuery.cssProps[ tween.prop ] ] != null ||
					jQuery.cssHooks[ tween.prop ] ) ) {
				jQuery.style( tween.elem, tween.prop, tween.now + tween.unit );
			} else {
				tween.elem[ tween.prop ] = tween.now;
			}
		}
	}
};

// Support: IE <=9
// Panic based approach to setting things on disconnected nodes

Tween.propHooks.scrollTop = Tween.propHooks.scrollLeft = {
	set: function( tween ) {
		if ( tween.elem.nodeType && tween.elem.parentNode ) {
			tween.elem[ tween.prop ] = tween.now;
		}
	}
};

jQuery.easing = {
	linear: function( p ) {
		return p;
	},
	swing: function( p ) {
		return 0.5 - Math.cos( p * Math.PI ) / 2;
	},
	_default: "swing"
};

jQuery.fx = Tween.prototype.init;

// Back Compat <1.8 extension point
jQuery.fx.step = {};




var
	fxNow, timerId,
	rfxtypes = /^(?:toggle|show|hide)$/,
	rrun = /queueHooks$/;

// Animations created synchronously will run synchronously
function createFxNow() {
	window.setTimeout( function() {
		fxNow = undefined;
	} );
	return ( fxNow = jQuery.now() );
}

// Generate parameters to create a standard animation
function genFx( type, includeWidth ) {
	var which,
		attrs = { height: type },
		i = 0;

	// if we include width, step value is 1 to do all cssExpand values,
	// if we don't include width, step value is 2 to skip over Left and Right
	includeWidth = includeWidth ? 1 : 0;
	for ( ; i < 4 ; i += 2 - includeWidth ) {
		which = cssExpand[ i ];
		attrs[ "margin" + which ] = attrs[ "padding" + which ] = type;
	}

	if ( includeWidth ) {
		attrs.opacity = attrs.width = type;
	}

	return attrs;
}

function createTween( value, prop, animation ) {
	var tween,
		collection = ( Animation.tweeners[ prop ] || [] ).concat( Animation.tweeners[ "*" ] ),
		index = 0,
		length = collection.length;
	for ( ; index < length; index++ ) {
		if ( ( tween = collection[ index ].call( animation, prop, value ) ) ) {

			// we're done with this property
			return tween;
		}
	}
}

function defaultPrefilter( elem, props, opts ) {
	/* jshint validthis: true */
	var prop, value, toggle, tween, hooks, oldfire, display, checkDisplay,
		anim = this,
		orig = {},
		style = elem.style,
		hidden = elem.nodeType && isHidden( elem ),
		dataShow = jQuery._data( elem, "fxshow" );

	// handle queue: false promises
	if ( !opts.queue ) {
		hooks = jQuery._queueHooks( elem, "fx" );
		if ( hooks.unqueued == null ) {
			hooks.unqueued = 0;
			oldfire = hooks.empty.fire;
			hooks.empty.fire = function() {
				if ( !hooks.unqueued ) {
					oldfire();
				}
			};
		}
		hooks.unqueued++;

		anim.always( function() {

			// doing this makes sure that the complete handler will be called
			// before this completes
			anim.always( function() {
				hooks.unqueued--;
				if ( !jQuery.queue( elem, "fx" ).length ) {
					hooks.empty.fire();
				}
			} );
		} );
	}

	// height/width overflow pass
	if ( elem.nodeType === 1 && ( "height" in props || "width" in props ) ) {

		// Make sure that nothing sneaks out
		// Record all 3 overflow attributes because IE does not
		// change the overflow attribute when overflowX and
		// overflowY are set to the same value
		opts.overflow = [ style.overflow, style.overflowX, style.overflowY ];

		// Set display property to inline-block for height/width
		// animations on inline elements that are having width/height animated
		display = jQuery.css( elem, "display" );

		// Test default display if display is currently "none"
		checkDisplay = display === "none" ?
			jQuery._data( elem, "olddisplay" ) || defaultDisplay( elem.nodeName ) : display;

		if ( checkDisplay === "inline" && jQuery.css( elem, "float" ) === "none" ) {

			// inline-level elements accept inline-block;
			// block-level elements need to be inline with layout
			if ( !support.inlineBlockNeedsLayout || defaultDisplay( elem.nodeName ) === "inline" ) {
				style.display = "inline-block";
			} else {
				style.zoom = 1;
			}
		}
	}

	if ( opts.overflow ) {
		style.overflow = "hidden";
		if ( !support.shrinkWrapBlocks() ) {
			anim.always( function() {
				style.overflow = opts.overflow[ 0 ];
				style.overflowX = opts.overflow[ 1 ];
				style.overflowY = opts.overflow[ 2 ];
			} );
		}
	}

	// show/hide pass
	for ( prop in props ) {
		value = props[ prop ];
		if ( rfxtypes.exec( value ) ) {
			delete props[ prop ];
			toggle = toggle || value === "toggle";
			if ( value === ( hidden ? "hide" : "show" ) ) {

				// If there is dataShow left over from a stopped hide or show
				// and we are going to proceed with show, we should pretend to be hidden
				if ( value === "show" && dataShow && dataShow[ prop ] !== undefined ) {
					hidden = true;
				} else {
					continue;
				}
			}
			orig[ prop ] = dataShow && dataShow[ prop ] || jQuery.style( elem, prop );

		// Any non-fx value stops us from restoring the original display value
		} else {
			display = undefined;
		}
	}

	if ( !jQuery.isEmptyObject( orig ) ) {
		if ( dataShow ) {
			if ( "hidden" in dataShow ) {
				hidden = dataShow.hidden;
			}
		} else {
			dataShow = jQuery._data( elem, "fxshow", {} );
		}

		// store state if its toggle - enables .stop().toggle() to "reverse"
		if ( toggle ) {
			dataShow.hidden = !hidden;
		}
		if ( hidden ) {
			jQuery( elem ).show();
		} else {
			anim.done( function() {
				jQuery( elem ).hide();
			} );
		}
		anim.done( function() {
			var prop;
			jQuery._removeData( elem, "fxshow" );
			for ( prop in orig ) {
				jQuery.style( elem, prop, orig[ prop ] );
			}
		} );
		for ( prop in orig ) {
			tween = createTween( hidden ? dataShow[ prop ] : 0, prop, anim );

			if ( !( prop in dataShow ) ) {
				dataShow[ prop ] = tween.start;
				if ( hidden ) {
					tween.end = tween.start;
					tween.start = prop === "width" || prop === "height" ? 1 : 0;
				}
			}
		}

	// If this is a noop like .hide().hide(), restore an overwritten display value
	} else if ( ( display === "none" ? defaultDisplay( elem.nodeName ) : display ) === "inline" ) {
		style.display = display;
	}
}

function propFilter( props, specialEasing ) {
	var index, name, easing, value, hooks;

	// camelCase, specialEasing and expand cssHook pass
	for ( index in props ) {
		name = jQuery.camelCase( index );
		easing = specialEasing[ name ];
		value = props[ index ];
		if ( jQuery.isArray( value ) ) {
			easing = value[ 1 ];
			value = props[ index ] = value[ 0 ];
		}

		if ( index !== name ) {
			props[ name ] = value;
			delete props[ index ];
		}

		hooks = jQuery.cssHooks[ name ];
		if ( hooks && "expand" in hooks ) {
			value = hooks.expand( value );
			delete props[ name ];

			// not quite $.extend, this wont overwrite keys already present.
			// also - reusing 'index' from above because we have the correct "name"
			for ( index in value ) {
				if ( !( index in props ) ) {
					props[ index ] = value[ index ];
					specialEasing[ index ] = easing;
				}
			}
		} else {
			specialEasing[ name ] = easing;
		}
	}
}

function Animation( elem, properties, options ) {
	var result,
		stopped,
		index = 0,
		length = Animation.prefilters.length,
		deferred = jQuery.Deferred().always( function() {

			// don't match elem in the :animated selector
			delete tick.elem;
		} ),
		tick = function() {
			if ( stopped ) {
				return false;
			}
			var currentTime = fxNow || createFxNow(),
				remaining = Math.max( 0, animation.startTime + animation.duration - currentTime ),

				// Support: Android 2.3
				// Archaic crash bug won't allow us to use `1 - ( 0.5 || 0 )` (#12497)
				temp = remaining / animation.duration || 0,
				percent = 1 - temp,
				index = 0,
				length = animation.tweens.length;

			for ( ; index < length ; index++ ) {
				animation.tweens[ index ].run( percent );
			}

			deferred.notifyWith( elem, [ animation, percent, remaining ] );

			if ( percent < 1 && length ) {
				return remaining;
			} else {
				deferred.resolveWith( elem, [ animation ] );
				return false;
			}
		},
		animation = deferred.promise( {
			elem: elem,
			props: jQuery.extend( {}, properties ),
			opts: jQuery.extend( true, {
				specialEasing: {},
				easing: jQuery.easing._default
			}, options ),
			originalProperties: properties,
			originalOptions: options,
			startTime: fxNow || createFxNow(),
			duration: options.duration,
			tweens: [],
			createTween: function( prop, end ) {
				var tween = jQuery.Tween( elem, animation.opts, prop, end,
						animation.opts.specialEasing[ prop ] || animation.opts.easing );
				animation.tweens.push( tween );
				return tween;
			},
			stop: function( gotoEnd ) {
				var index = 0,

					// if we are going to the end, we want to run all the tweens
					// otherwise we skip this part
					length = gotoEnd ? animation.tweens.length : 0;
				if ( stopped ) {
					return this;
				}
				stopped = true;
				for ( ; index < length ; index++ ) {
					animation.tweens[ index ].run( 1 );
				}

				// resolve when we played the last frame
				// otherwise, reject
				if ( gotoEnd ) {
					deferred.notifyWith( elem, [ animation, 1, 0 ] );
					deferred.resolveWith( elem, [ animation, gotoEnd ] );
				} else {
					deferred.rejectWith( elem, [ animation, gotoEnd ] );
				}
				return this;
			}
		} ),
		props = animation.props;

	propFilter( props, animation.opts.specialEasing );

	for ( ; index < length ; index++ ) {
		result = Animation.prefilters[ index ].call( animation, elem, props, animation.opts );
		if ( result ) {
			if ( jQuery.isFunction( result.stop ) ) {
				jQuery._queueHooks( animation.elem, animation.opts.queue ).stop =
					jQuery.proxy( result.stop, result );
			}
			return result;
		}
	}

	jQuery.map( props, createTween, animation );

	if ( jQuery.isFunction( animation.opts.start ) ) {
		animation.opts.start.call( elem, animation );
	}

	jQuery.fx.timer(
		jQuery.extend( tick, {
			elem: elem,
			anim: animation,
			queue: animation.opts.queue
		} )
	);

	// attach callbacks from options
	return animation.progress( animation.opts.progress )
		.done( animation.opts.done, animation.opts.complete )
		.fail( animation.opts.fail )
		.always( animation.opts.always );
}

jQuery.Animation = jQuery.extend( Animation, {

	tweeners: {
		"*": [ function( prop, value ) {
			var tween = this.createTween( prop, value );
			adjustCSS( tween.elem, prop, rcssNum.exec( value ), tween );
			return tween;
		} ]
	},

	tweener: function( props, callback ) {
		if ( jQuery.isFunction( props ) ) {
			callback = props;
			props = [ "*" ];
		} else {
			props = props.match( rnotwhite );
		}

		var prop,
			index = 0,
			length = props.length;

		for ( ; index < length ; index++ ) {
			prop = props[ index ];
			Animation.tweeners[ prop ] = Animation.tweeners[ prop ] || [];
			Animation.tweeners[ prop ].unshift( callback );
		}
	},

	prefilters: [ defaultPrefilter ],

	prefilter: function( callback, prepend ) {
		if ( prepend ) {
			Animation.prefilters.unshift( callback );
		} else {
			Animation.prefilters.push( callback );
		}
	}
} );

jQuery.speed = function( speed, easing, fn ) {
	var opt = speed && typeof speed === "object" ? jQuery.extend( {}, speed ) : {
		complete: fn || !fn && easing ||
			jQuery.isFunction( speed ) && speed,
		duration: speed,
		easing: fn && easing || easing && !jQuery.isFunction( easing ) && easing
	};

	opt.duration = jQuery.fx.off ? 0 : typeof opt.duration === "number" ? opt.duration :
		opt.duration in jQuery.fx.speeds ?
			jQuery.fx.speeds[ opt.duration ] : jQuery.fx.speeds._default;

	// normalize opt.queue - true/undefined/null -> "fx"
	if ( opt.queue == null || opt.queue === true ) {
		opt.queue = "fx";
	}

	// Queueing
	opt.old = opt.complete;

	opt.complete = function() {
		if ( jQuery.isFunction( opt.old ) ) {
			opt.old.call( this );
		}

		if ( opt.queue ) {
			jQuery.dequeue( this, opt.queue );
		}
	};

	return opt;
};

jQuery.fn.extend( {
	fadeTo: function( speed, to, easing, callback ) {

		// show any hidden elements after setting opacity to 0
		return this.filter( isHidden ).css( "opacity", 0 ).show()

			// animate to the value specified
			.end().animate( { opacity: to }, speed, easing, callback );
	},
	animate: function( prop, speed, easing, callback ) {
		var empty = jQuery.isEmptyObject( prop ),
			optall = jQuery.speed( speed, easing, callback ),
			doAnimation = function() {

				// Operate on a copy of prop so per-property easing won't be lost
				var anim = Animation( this, jQuery.extend( {}, prop ), optall );

				// Empty animations, or finishing resolves immediately
				if ( empty || jQuery._data( this, "finish" ) ) {
					anim.stop( true );
				}
			};
			doAnimation.finish = doAnimation;

		return empty || optall.queue === false ?
			this.each( doAnimation ) :
			this.queue( optall.queue, doAnimation );
	},
	stop: function( type, clearQueue, gotoEnd ) {
		var stopQueue = function( hooks ) {
			var stop = hooks.stop;
			delete hooks.stop;
			stop( gotoEnd );
		};

		if ( typeof type !== "string" ) {
			gotoEnd = clearQueue;
			clearQueue = type;
			type = undefined;
		}
		if ( clearQueue && type !== false ) {
			this.queue( type || "fx", [] );
		}

		return this.each( function() {
			var dequeue = true,
				index = type != null && type + "queueHooks",
				timers = jQuery.timers,
				data = jQuery._data( this );

			if ( index ) {
				if ( data[ index ] && data[ index ].stop ) {
					stopQueue( data[ index ] );
				}
			} else {
				for ( index in data ) {
					if ( data[ index ] && data[ index ].stop && rrun.test( index ) ) {
						stopQueue( data[ index ] );
					}
				}
			}

			for ( index = timers.length; index--; ) {
				if ( timers[ index ].elem === this &&
					( type == null || timers[ index ].queue === type ) ) {

					timers[ index ].anim.stop( gotoEnd );
					dequeue = false;
					timers.splice( index, 1 );
				}
			}

			// start the next in the queue if the last step wasn't forced
			// timers currently will call their complete callbacks, which will dequeue
			// but only if they were gotoEnd
			if ( dequeue || !gotoEnd ) {
				jQuery.dequeue( this, type );
			}
		} );
	},
	finish: function( type ) {
		if ( type !== false ) {
			type = type || "fx";
		}
		return this.each( function() {
			var index,
				data = jQuery._data( this ),
				queue = data[ type + "queue" ],
				hooks = data[ type + "queueHooks" ],
				timers = jQuery.timers,
				length = queue ? queue.length : 0;

			// enable finishing flag on private data
			data.finish = true;

			// empty the queue first
			jQuery.queue( this, type, [] );

			if ( hooks && hooks.stop ) {
				hooks.stop.call( this, true );
			}

			// look for any active animations, and finish them
			for ( index = timers.length; index--; ) {
				if ( timers[ index ].elem === this && timers[ index ].queue === type ) {
					timers[ index ].anim.stop( true );
					timers.splice( index, 1 );
				}
			}

			// look for any animations in the old queue and finish them
			for ( index = 0; index < length; index++ ) {
				if ( queue[ index ] && queue[ index ].finish ) {
					queue[ index ].finish.call( this );
				}
			}

			// turn off finishing flag
			delete data.finish;
		} );
	}
} );

jQuery.each( [ "toggle", "show", "hide" ], function( i, name ) {
	var cssFn = jQuery.fn[ name ];
	jQuery.fn[ name ] = function( speed, easing, callback ) {
		return speed == null || typeof speed === "boolean" ?
			cssFn.apply( this, arguments ) :
			this.animate( genFx( name, true ), speed, easing, callback );
	};
} );

// Generate shortcuts for custom animations
jQuery.each( {
	slideDown: genFx( "show" ),
	slideUp: genFx( "hide" ),
	slideToggle: genFx( "toggle" ),
	fadeIn: { opacity: "show" },
	fadeOut: { opacity: "hide" },
	fadeToggle: { opacity: "toggle" }
}, function( name, props ) {
	jQuery.fn[ name ] = function( speed, easing, callback ) {
		return this.animate( props, speed, easing, callback );
	};
} );

jQuery.timers = [];
jQuery.fx.tick = function() {
	var timer,
		timers = jQuery.timers,
		i = 0;

	fxNow = jQuery.now();

	for ( ; i < timers.length; i++ ) {
		timer = timers[ i ];

		// Checks the timer has not already been removed
		if ( !timer() && timers[ i ] === timer ) {
			timers.splice( i--, 1 );
		}
	}

	if ( !timers.length ) {
		jQuery.fx.stop();
	}
	fxNow = undefined;
};

jQuery.fx.timer = function( timer ) {
	jQuery.timers.push( timer );
	if ( timer() ) {
		jQuery.fx.start();
	} else {
		jQuery.timers.pop();
	}
};

jQuery.fx.interval = 13;

jQuery.fx.start = function() {
	if ( !timerId ) {
		timerId = window.setInterval( jQuery.fx.tick, jQuery.fx.interval );
	}
};

jQuery.fx.stop = function() {
	window.clearInterval( timerId );
	timerId = null;
};

jQuery.fx.speeds = {
	slow: 600,
	fast: 200,

	// Default speed
	_default: 400
};


// Based off of the plugin by Clint Helfers, with permission.
// http://web.archive.org/web/20100324014747/http://blindsignals.com/index.php/2009/07/jquery-delay/
jQuery.fn.delay = function( time, type ) {
	time = jQuery.fx ? jQuery.fx.speeds[ time ] || time : time;
	type = type || "fx";

	return this.queue( type, function( next, hooks ) {
		var timeout = window.setTimeout( next, time );
		hooks.stop = function() {
			window.clearTimeout( timeout );
		};
	} );
};


( function() {
	var a,
		input = document.createElement( "input" ),
		div = document.createElement( "div" ),
		select = document.createElement( "select" ),
		opt = select.appendChild( document.createElement( "option" ) );

	// Setup
	div = document.createElement( "div" );
	div.setAttribute( "className", "t" );
	div.innerHTML = "  <link/><table></table><a href='/a'>a</a><input type='checkbox'/>";
	a = div.getElementsByTagName( "a" )[ 0 ];

	// Support: Windows Web Apps (WWA)
	// `type` must use .setAttribute for WWA (#14901)
	input.setAttribute( "type", "checkbox" );
	div.appendChild( input );

	a = div.getElementsByTagName( "a" )[ 0 ];

	// First batch of tests.
	a.style.cssText = "top:1px";

	// Test setAttribute on camelCase class.
	// If it works, we need attrFixes when doing get/setAttribute (ie6/7)
	support.getSetAttribute = div.className !== "t";

	// Get the style information from getAttribute
	// (IE uses .cssText instead)
	support.style = /top/.test( a.getAttribute( "style" ) );

	// Make sure that URLs aren't manipulated
	// (IE normalizes it by default)
	support.hrefNormalized = a.getAttribute( "href" ) === "/a";

	// Check the default checkbox/radio value ("" on WebKit; "on" elsewhere)
	support.checkOn = !!input.value;

	// Make sure that a selected-by-default option has a working selected property.
	// (WebKit defaults to false instead of true, IE too, if it's in an optgroup)
	support.optSelected = opt.selected;

	// Tests for enctype support on a form (#6743)
	support.enctype = !!document.createElement( "form" ).enctype;

	// Make sure that the options inside disabled selects aren't marked as disabled
	// (WebKit marks them as disabled)
	select.disabled = true;
	support.optDisabled = !opt.disabled;

	// Support: IE8 only
	// Check if we can trust getAttribute("value")
	input = document.createElement( "input" );
	input.setAttribute( "value", "" );
	support.input = input.getAttribute( "value" ) === "";

	// Check if an input maintains its value after becoming a radio
	input.value = "t";
	input.setAttribute( "type", "radio" );
	support.radioValue = input.value === "t";
} )();


var rreturn = /\r/g,
	rspaces = /[\x20\t\r\n\f]+/g;

jQuery.fn.extend( {
	val: function( value ) {
		var hooks, ret, isFunction,
			elem = this[ 0 ];

		if ( !arguments.length ) {
			if ( elem ) {
				hooks = jQuery.valHooks[ elem.type ] ||
					jQuery.valHooks[ elem.nodeName.toLowerCase() ];

				if (
					hooks &&
					"get" in hooks &&
					( ret = hooks.get( elem, "value" ) ) !== undefined
				) {
					return ret;
				}

				ret = elem.value;

				return typeof ret === "string" ?

					// handle most common string cases
					ret.replace( rreturn, "" ) :

					// handle cases where value is null/undef or number
					ret == null ? "" : ret;
			}

			return;
		}

		isFunction = jQuery.isFunction( value );

		return this.each( function( i ) {
			var val;

			if ( this.nodeType !== 1 ) {
				return;
			}

			if ( isFunction ) {
				val = value.call( this, i, jQuery( this ).val() );
			} else {
				val = value;
			}

			// Treat null/undefined as ""; convert numbers to string
			if ( val == null ) {
				val = "";
			} else if ( typeof val === "number" ) {
				val += "";
			} else if ( jQuery.isArray( val ) ) {
				val = jQuery.map( val, function( value ) {
					return value == null ? "" : value + "";
				} );
			}

			hooks = jQuery.valHooks[ this.type ] || jQuery.valHooks[ this.nodeName.toLowerCase() ];

			// If set returns undefined, fall back to normal setting
			if ( !hooks || !( "set" in hooks ) || hooks.set( this, val, "value" ) === undefined ) {
				this.value = val;
			}
		} );
	}
} );

jQuery.extend( {
	valHooks: {
		option: {
			get: function( elem ) {
				var val = jQuery.find.attr( elem, "value" );
				return val != null ?
					val :

					// Support: IE10-11+
					// option.text throws exceptions (#14686, #14858)
					// Strip and collapse whitespace
					// https://html.spec.whatwg.org/#strip-and-collapse-whitespace
					jQuery.trim( jQuery.text( elem ) ).replace( rspaces, " " );
			}
		},
		select: {
			get: function( elem ) {
				var value, option,
					options = elem.options,
					index = elem.selectedIndex,
					one = elem.type === "select-one" || index < 0,
					values = one ? null : [],
					max = one ? index + 1 : options.length,
					i = index < 0 ?
						max :
						one ? index : 0;

				// Loop through all the selected options
				for ( ; i < max; i++ ) {
					option = options[ i ];

					// oldIE doesn't update selected after form reset (#2551)
					if ( ( option.selected || i === index ) &&

							// Don't return options that are disabled or in a disabled optgroup
							( support.optDisabled ?
								!option.disabled :
								option.getAttribute( "disabled" ) === null ) &&
							( !option.parentNode.disabled ||
								!jQuery.nodeName( option.parentNode, "optgroup" ) ) ) {

						// Get the specific value for the option
						value = jQuery( option ).val();

						// We don't need an array for one selects
						if ( one ) {
							return value;
						}

						// Multi-Selects return an array
						values.push( value );
					}
				}

				return values;
			},

			set: function( elem, value ) {
				var optionSet, option,
					options = elem.options,
					values = jQuery.makeArray( value ),
					i = options.length;

				while ( i-- ) {
					option = options[ i ];

					if ( jQuery.inArray( jQuery.valHooks.option.get( option ), values ) > -1 ) {

						// Support: IE6
						// When new option element is added to select box we need to
						// force reflow of newly added node in order to workaround delay
						// of initialization properties
						try {
							option.selected = optionSet = true;

						} catch ( _ ) {

							// Will be executed only in IE6
							option.scrollHeight;
						}

					} else {
						option.selected = false;
					}
				}

				// Force browsers to behave consistently when non-matching value is set
				if ( !optionSet ) {
					elem.selectedIndex = -1;
				}

				return options;
			}
		}
	}
} );

// Radios and checkboxes getter/setter
jQuery.each( [ "radio", "checkbox" ], function() {
	jQuery.valHooks[ this ] = {
		set: function( elem, value ) {
			if ( jQuery.isArray( value ) ) {
				return ( elem.checked = jQuery.inArray( jQuery( elem ).val(), value ) > -1 );
			}
		}
	};
	if ( !support.checkOn ) {
		jQuery.valHooks[ this ].get = function( elem ) {
			return elem.getAttribute( "value" ) === null ? "on" : elem.value;
		};
	}
} );




var nodeHook, boolHook,
	attrHandle = jQuery.expr.attrHandle,
	ruseDefault = /^(?:checked|selected)$/i,
	getSetAttribute = support.getSetAttribute,
	getSetInput = support.input;

jQuery.fn.extend( {
	attr: function( name, value ) {
		return access( this, jQuery.attr, name, value, arguments.length > 1 );
	},

	removeAttr: function( name ) {
		return this.each( function() {
			jQuery.removeAttr( this, name );
		} );
	}
} );

jQuery.extend( {
	attr: function( elem, name, value ) {
		var ret, hooks,
			nType = elem.nodeType;

		// Don't get/set attributes on text, comment and attribute nodes
		if ( nType === 3 || nType === 8 || nType === 2 ) {
			return;
		}

		// Fallback to prop when attributes are not supported
		if ( typeof elem.getAttribute === "undefined" ) {
			return jQuery.prop( elem, name, value );
		}

		// All attributes are lowercase
		// Grab necessary hook if one is defined
		if ( nType !== 1 || !jQuery.isXMLDoc( elem ) ) {
			name = name.toLowerCase();
			hooks = jQuery.attrHooks[ name ] ||
				( jQuery.expr.match.bool.test( name ) ? boolHook : nodeHook );
		}

		if ( value !== undefined ) {
			if ( value === null ) {
				jQuery.removeAttr( elem, name );
				return;
			}

			if ( hooks && "set" in hooks &&
				( ret = hooks.set( elem, value, name ) ) !== undefined ) {
				return ret;
			}

			elem.setAttribute( name, value + "" );
			return value;
		}

		if ( hooks && "get" in hooks && ( ret = hooks.get( elem, name ) ) !== null ) {
			return ret;
		}

		ret = jQuery.find.attr( elem, name );

		// Non-existent attributes return null, we normalize to undefined
		return ret == null ? undefined : ret;
	},

	attrHooks: {
		type: {
			set: function( elem, value ) {
				if ( !support.radioValue && value === "radio" &&
					jQuery.nodeName( elem, "input" ) ) {

					// Setting the type on a radio button after the value resets the value in IE8-9
					// Reset value to default in case type is set after value during creation
					var val = elem.value;
					elem.setAttribute( "type", value );
					if ( val ) {
						elem.value = val;
					}
					return value;
				}
			}
		}
	},

	removeAttr: function( elem, value ) {
		var name, propName,
			i = 0,
			attrNames = value && value.match( rnotwhite );

		if ( attrNames && elem.nodeType === 1 ) {
			while ( ( name = attrNames[ i++ ] ) ) {
				propName = jQuery.propFix[ name ] || name;

				// Boolean attributes get special treatment (#10870)
				if ( jQuery.expr.match.bool.test( name ) ) {

					// Set corresponding property to false
					if ( getSetInput && getSetAttribute || !ruseDefault.test( name ) ) {
						elem[ propName ] = false;

					// Support: IE<9
					// Also clear defaultChecked/defaultSelected (if appropriate)
					} else {
						elem[ jQuery.camelCase( "default-" + name ) ] =
							elem[ propName ] = false;
					}

				// See #9699 for explanation of this approach (setting first, then removal)
				} else {
					jQuery.attr( elem, name, "" );
				}

				elem.removeAttribute( getSetAttribute ? name : propName );
			}
		}
	}
} );

// Hooks for boolean attributes
boolHook = {
	set: function( elem, value, name ) {
		if ( value === false ) {

			// Remove boolean attributes when set to false
			jQuery.removeAttr( elem, name );
		} else if ( getSetInput && getSetAttribute || !ruseDefault.test( name ) ) {

			// IE<8 needs the *property* name
			elem.setAttribute( !getSetAttribute && jQuery.propFix[ name ] || name, name );

		} else {

			// Support: IE<9
			// Use defaultChecked and defaultSelected for oldIE
			elem[ jQuery.camelCase( "default-" + name ) ] = elem[ name ] = true;
		}
		return name;
	}
};

jQuery.each( jQuery.expr.match.bool.source.match( /\w+/g ), function( i, name ) {
	var getter = attrHandle[ name ] || jQuery.find.attr;

	if ( getSetInput && getSetAttribute || !ruseDefault.test( name ) ) {
		attrHandle[ name ] = function( elem, name, isXML ) {
			var ret, handle;
			if ( !isXML ) {

				// Avoid an infinite loop by temporarily removing this function from the getter
				handle = attrHandle[ name ];
				attrHandle[ name ] = ret;
				ret = getter( elem, name, isXML ) != null ?
					name.toLowerCase() :
					null;
				attrHandle[ name ] = handle;
			}
			return ret;
		};
	} else {
		attrHandle[ name ] = function( elem, name, isXML ) {
			if ( !isXML ) {
				return elem[ jQuery.camelCase( "default-" + name ) ] ?
					name.toLowerCase() :
					null;
			}
		};
	}
} );

// fix oldIE attroperties
if ( !getSetInput || !getSetAttribute ) {
	jQuery.attrHooks.value = {
		set: function( elem, value, name ) {
			if ( jQuery.nodeName( elem, "input" ) ) {

				// Does not return so that setAttribute is also used
				elem.defaultValue = value;
			} else {

				// Use nodeHook if defined (#1954); otherwise setAttribute is fine
				return nodeHook && nodeHook.set( elem, value, name );
			}
		}
	};
}

// IE6/7 do not support getting/setting some attributes with get/setAttribute
if ( !getSetAttribute ) {

	// Use this for any attribute in IE6/7
	// This fixes almost every IE6/7 issue
	nodeHook = {
		set: function( elem, value, name ) {

			// Set the existing or create a new attribute node
			var ret = elem.getAttributeNode( name );
			if ( !ret ) {
				elem.setAttributeNode(
					( ret = elem.ownerDocument.createAttribute( name ) )
				);
			}

			ret.value = value += "";

			// Break association with cloned elements by also using setAttribute (#9646)
			if ( name === "value" || value === elem.getAttribute( name ) ) {
				return value;
			}
		}
	};

	// Some attributes are constructed with empty-string values when not defined
	attrHandle.id = attrHandle.name = attrHandle.coords =
		function( elem, name, isXML ) {
			var ret;
			if ( !isXML ) {
				return ( ret = elem.getAttributeNode( name ) ) && ret.value !== "" ?
					ret.value :
					null;
			}
		};

	// Fixing value retrieval on a button requires this module
	jQuery.valHooks.button = {
		get: function( elem, name ) {
			var ret = elem.getAttributeNode( name );
			if ( ret && ret.specified ) {
				return ret.value;
			}
		},
		set: nodeHook.set
	};

	// Set contenteditable to false on removals(#10429)
	// Setting to empty string throws an error as an invalid value
	jQuery.attrHooks.contenteditable = {
		set: function( elem, value, name ) {
			nodeHook.set( elem, value === "" ? false : value, name );
		}
	};

	// Set width and height to auto instead of 0 on empty string( Bug #8150 )
	// This is for removals
	jQuery.each( [ "width", "height" ], function( i, name ) {
		jQuery.attrHooks[ name ] = {
			set: function( elem, value ) {
				if ( value === "" ) {
					elem.setAttribute( name, "auto" );
					return value;
				}
			}
		};
	} );
}

if ( !support.style ) {
	jQuery.attrHooks.style = {
		get: function( elem ) {

			// Return undefined in the case of empty string
			// Note: IE uppercases css property names, but if we were to .toLowerCase()
			// .cssText, that would destroy case sensitivity in URL's, like in "background"
			return elem.style.cssText || undefined;
		},
		set: function( elem, value ) {
			return ( elem.style.cssText = value + "" );
		}
	};
}




var rfocusable = /^(?:input|select|textarea|button|object)$/i,
	rclickable = /^(?:a|area)$/i;

jQuery.fn.extend( {
	prop: function( name, value ) {
		return access( this, jQuery.prop, name, value, arguments.length > 1 );
	},

	removeProp: function( name ) {
		name = jQuery.propFix[ name ] || name;
		return this.each( function() {

			// try/catch handles cases where IE balks (such as removing a property on window)
			try {
				this[ name ] = undefined;
				delete this[ name ];
			} catch ( e ) {}
		} );
	}
} );

jQuery.extend( {
	prop: function( elem, name, value ) {
		var ret, hooks,
			nType = elem.nodeType;

		// Don't get/set properties on text, comment and attribute nodes
		if ( nType === 3 || nType === 8 || nType === 2 ) {
			return;
		}

		if ( nType !== 1 || !jQuery.isXMLDoc( elem ) ) {

			// Fix name and attach hooks
			name = jQuery.propFix[ name ] || name;
			hooks = jQuery.propHooks[ name ];
		}

		if ( value !== undefined ) {
			if ( hooks && "set" in hooks &&
				( ret = hooks.set( elem, value, name ) ) !== undefined ) {
				return ret;
			}

			return ( elem[ name ] = value );
		}

		if ( hooks && "get" in hooks && ( ret = hooks.get( elem, name ) ) !== null ) {
			return ret;
		}

		return elem[ name ];
	},

	propHooks: {
		tabIndex: {
			get: function( elem ) {

				// elem.tabIndex doesn't always return the
				// correct value when it hasn't been explicitly set
				// http://fluidproject.org/blog/2008/01/09/getting-setting-and-removing-tabindex-values-with-javascript/
				// Use proper attribute retrieval(#12072)
				var tabindex = jQuery.find.attr( elem, "tabindex" );

				return tabindex ?
					parseInt( tabindex, 10 ) :
					rfocusable.test( elem.nodeName ) ||
						rclickable.test( elem.nodeName ) && elem.href ?
							0 :
							-1;
			}
		}
	},

	propFix: {
		"for": "htmlFor",
		"class": "className"
	}
} );

// Some attributes require a special call on IE
// http://msdn.microsoft.com/en-us/library/ms536429%28VS.85%29.aspx
if ( !support.hrefNormalized ) {

	// href/src property should get the full normalized URL (#10299/#12915)
	jQuery.each( [ "href", "src" ], function( i, name ) {
		jQuery.propHooks[ name ] = {
			get: function( elem ) {
				return elem.getAttribute( name, 4 );
			}
		};
	} );
}

// Support: Safari, IE9+
// Accessing the selectedIndex property
// forces the browser to respect setting selected
// on the option
// The getter ensures a default option is selected
// when in an optgroup
if ( !support.optSelected ) {
	jQuery.propHooks.selected = {
		get: function( elem ) {
			var parent = elem.parentNode;

			if ( parent ) {
				parent.selectedIndex;

				// Make sure that it also works with optgroups, see #5701
				if ( parent.parentNode ) {
					parent.parentNode.selectedIndex;
				}
			}
			return null;
		},
		set: function( elem ) {
			var parent = elem.parentNode;
			if ( parent ) {
				parent.selectedIndex;

				if ( parent.parentNode ) {
					parent.parentNode.selectedIndex;
				}
			}
		}
	};
}

jQuery.each( [
	"tabIndex",
	"readOnly",
	"maxLength",
	"cellSpacing",
	"cellPadding",
	"rowSpan",
	"colSpan",
	"useMap",
	"frameBorder",
	"contentEditable"
], function() {
	jQuery.propFix[ this.toLowerCase() ] = this;
} );

// IE6/7 call enctype encoding
if ( !support.enctype ) {
	jQuery.propFix.enctype = "encoding";
}




var rclass = /[\t\r\n\f]/g;

function getClass( elem ) {
	return jQuery.attr( elem, "class" ) || "";
}

jQuery.fn.extend( {
	addClass: function( value ) {
		var classes, elem, cur, curValue, clazz, j, finalValue,
			i = 0;

		if ( jQuery.isFunction( value ) ) {
			return this.each( function( j ) {
				jQuery( this ).addClass( value.call( this, j, getClass( this ) ) );
			} );
		}

		if ( typeof value === "string" && value ) {
			classes = value.match( rnotwhite ) || [];

			while ( ( elem = this[ i++ ] ) ) {
				curValue = getClass( elem );
				cur = elem.nodeType === 1 &&
					( " " + curValue + " " ).replace( rclass, " " );

				if ( cur ) {
					j = 0;
					while ( ( clazz = classes[ j++ ] ) ) {
						if ( cur.indexOf( " " + clazz + " " ) < 0 ) {
							cur += clazz + " ";
						}
					}

					// only assign if different to avoid unneeded rendering.
					finalValue = jQuery.trim( cur );
					if ( curValue !== finalValue ) {
						jQuery.attr( elem, "class", finalValue );
					}
				}
			}
		}

		return this;
	},

	removeClass: function( value ) {
		var classes, elem, cur, curValue, clazz, j, finalValue,
			i = 0;

		if ( jQuery.isFunction( value ) ) {
			return this.each( function( j ) {
				jQuery( this ).removeClass( value.call( this, j, getClass( this ) ) );
			} );
		}

		if ( !arguments.length ) {
			return this.attr( "class", "" );
		}

		if ( typeof value === "string" && value ) {
			classes = value.match( rnotwhite ) || [];

			while ( ( elem = this[ i++ ] ) ) {
				curValue = getClass( elem );

				// This expression is here for better compressibility (see addClass)
				cur = elem.nodeType === 1 &&
					( " " + curValue + " " ).replace( rclass, " " );

				if ( cur ) {
					j = 0;
					while ( ( clazz = classes[ j++ ] ) ) {

						// Remove *all* instances
						while ( cur.indexOf( " " + clazz + " " ) > -1 ) {
							cur = cur.replace( " " + clazz + " ", " " );
						}
					}

					// Only assign if different to avoid unneeded rendering.
					finalValue = jQuery.trim( cur );
					if ( curValue !== finalValue ) {
						jQuery.attr( elem, "class", finalValue );
					}
				}
			}
		}

		return this;
	},

	toggleClass: function( value, stateVal ) {
		var type = typeof value;

		if ( typeof stateVal === "boolean" && type === "string" ) {
			return stateVal ? this.addClass( value ) : this.removeClass( value );
		}

		if ( jQuery.isFunction( value ) ) {
			return this.each( function( i ) {
				jQuery( this ).toggleClass(
					value.call( this, i, getClass( this ), stateVal ),
					stateVal
				);
			} );
		}

		return this.each( function() {
			var className, i, self, classNames;

			if ( type === "string" ) {

				// Toggle individual class names
				i = 0;
				self = jQuery( this );
				classNames = value.match( rnotwhite ) || [];

				while ( ( className = classNames[ i++ ] ) ) {

					// Check each className given, space separated list
					if ( self.hasClass( className ) ) {
						self.removeClass( className );
					} else {
						self.addClass( className );
					}
				}

			// Toggle whole class name
			} else if ( value === undefined || type === "boolean" ) {
				className = getClass( this );
				if ( className ) {

					// store className if set
					jQuery._data( this, "__className__", className );
				}

				// If the element has a class name or if we're passed "false",
				// then remove the whole classname (if there was one, the above saved it).
				// Otherwise bring back whatever was previously saved (if anything),
				// falling back to the empty string if nothing was stored.
				jQuery.attr( this, "class",
					className || value === false ?
					"" :
					jQuery._data( this, "__className__" ) || ""
				);
			}
		} );
	},

	hasClass: function( selector ) {
		var className, elem,
			i = 0;

		className = " " + selector + " ";
		while ( ( elem = this[ i++ ] ) ) {
			if ( elem.nodeType === 1 &&
				( " " + getClass( elem ) + " " ).replace( rclass, " " )
					.indexOf( className ) > -1
			) {
				return true;
			}
		}

		return false;
	}
} );




// Return jQuery for attributes-only inclusion


jQuery.each( ( "blur focus focusin focusout load resize scroll unload click dblclick " +
	"mousedown mouseup mousemove mouseover mouseout mouseenter mouseleave " +
	"change select submit keydown keypress keyup error contextmenu" ).split( " " ),
	function( i, name ) {

	// Handle event binding
	jQuery.fn[ name ] = function( data, fn ) {
		return arguments.length > 0 ?
			this.on( name, null, data, fn ) :
			this.trigger( name );
	};
} );

jQuery.fn.extend( {
	hover: function( fnOver, fnOut ) {
		return this.mouseenter( fnOver ).mouseleave( fnOut || fnOver );
	}
} );


var location = window.location;

var nonce = jQuery.now();

var rquery = ( /\?/ );



var rvalidtokens = /(,)|(\[|{)|(}|])|"(?:[^"\\\r\n]|\\["\\\/bfnrt]|\\u[\da-fA-F]{4})*"\s*:?|true|false|null|-?(?!0\d)\d+(?:\.\d+|)(?:[eE][+-]?\d+|)/g;

jQuery.parseJSON = function( data ) {

	// Attempt to parse using the native JSON parser first
	if ( window.JSON && window.JSON.parse ) {

		// Support: Android 2.3
		// Workaround failure to string-cast null input
		return window.JSON.parse( data + "" );
	}

	var requireNonComma,
		depth = null,
		str = jQuery.trim( data + "" );

	// Guard against invalid (and possibly dangerous) input by ensuring that nothing remains
	// after removing valid tokens
	return str && !jQuery.trim( str.replace( rvalidtokens, function( token, comma, open, close ) {

		// Force termination if we see a misplaced comma
		if ( requireNonComma && comma ) {
			depth = 0;
		}

		// Perform no more replacements after returning to outermost depth
		if ( depth === 0 ) {
			return token;
		}

		// Commas must not follow "[", "{", or ","
		requireNonComma = open || comma;

		// Determine new depth
		// array/object open ("[" or "{"): depth += true - false (increment)
		// array/object close ("]" or "}"): depth += false - true (decrement)
		// other cases ("," or primitive): depth += true - true (numeric cast)
		depth += !close - !open;

		// Remove this token
		return "";
	} ) ) ?
		( Function( "return " + str ) )() :
		jQuery.error( "Invalid JSON: " + data );
};


// Cross-browser xml parsing
jQuery.parseXML = function( data ) {
	var xml, tmp;
	if ( !data || typeof data !== "string" ) {
		return null;
	}
	try {
		if ( window.DOMParser ) { // Standard
			tmp = new window.DOMParser();
			xml = tmp.parseFromString( data, "text/xml" );
		} else { // IE
			xml = new window.ActiveXObject( "Microsoft.XMLDOM" );
			xml.async = "false";
			xml.loadXML( data );
		}
	} catch ( e ) {
		xml = undefined;
	}
	if ( !xml || !xml.documentElement || xml.getElementsByTagName( "parsererror" ).length ) {
		jQuery.error( "Invalid XML: " + data );
	}
	return xml;
};


var
	rhash = /#.*$/,
	rts = /([?&])_=[^&]*/,

	// IE leaves an \r character at EOL
	rheaders = /^(.*?):[ \t]*([^\r\n]*)\r?$/mg,

	// #7653, #8125, #8152: local protocol detection
	rlocalProtocol = /^(?:about|app|app-storage|.+-extension|file|res|widget):$/,
	rnoContent = /^(?:GET|HEAD)$/,
	rprotocol = /^\/\//,
	rurl = /^([\w.+-]+:)(?:\/\/(?:[^\/?#]*@|)([^\/?#:]*)(?::(\d+)|)|)/,

	/* Prefilters
	 * 1) They are useful to introduce custom dataTypes (see ajax/jsonp.js for an example)
	 * 2) These are called:
	 *    - BEFORE asking for a transport
	 *    - AFTER param serialization (s.data is a string if s.processData is true)
	 * 3) key is the dataType
	 * 4) the catchall symbol "*" can be used
	 * 5) execution will start with transport dataType and THEN continue down to "*" if needed
	 */
	prefilters = {},

	/* Transports bindings
	 * 1) key is the dataType
	 * 2) the catchall symbol "*" can be used
	 * 3) selection will start with transport dataType and THEN go to "*" if needed
	 */
	transports = {},

	// Avoid comment-prolog char sequence (#10098); must appease lint and evade compression
	allTypes = "*/".concat( "*" ),

	// Document location
	ajaxLocation = location.href,

	// Segment location into parts
	ajaxLocParts = rurl.exec( ajaxLocation.toLowerCase() ) || [];

// Base "constructor" for jQuery.ajaxPrefilter and jQuery.ajaxTransport
function addToPrefiltersOrTransports( structure ) {

	// dataTypeExpression is optional and defaults to "*"
	return function( dataTypeExpression, func ) {

		if ( typeof dataTypeExpression !== "string" ) {
			func = dataTypeExpression;
			dataTypeExpression = "*";
		}

		var dataType,
			i = 0,
			dataTypes = dataTypeExpression.toLowerCase().match( rnotwhite ) || [];

		if ( jQuery.isFunction( func ) ) {

			// For each dataType in the dataTypeExpression
			while ( ( dataType = dataTypes[ i++ ] ) ) {

				// Prepend if requested
				if ( dataType.charAt( 0 ) === "+" ) {
					dataType = dataType.slice( 1 ) || "*";
					( structure[ dataType ] = structure[ dataType ] || [] ).unshift( func );

				// Otherwise append
				} else {
					( structure[ dataType ] = structure[ dataType ] || [] ).push( func );
				}
			}
		}
	};
}

// Base inspection function for prefilters and transports
function inspectPrefiltersOrTransports( structure, options, originalOptions, jqXHR ) {

	var inspected = {},
		seekingTransport = ( structure === transports );

	function inspect( dataType ) {
		var selected;
		inspected[ dataType ] = true;
		jQuery.each( structure[ dataType ] || [], function( _, prefilterOrFactory ) {
			var dataTypeOrTransport = prefilterOrFactory( options, originalOptions, jqXHR );
			if ( typeof dataTypeOrTransport === "string" &&
				!seekingTransport && !inspected[ dataTypeOrTransport ] ) {

				options.dataTypes.unshift( dataTypeOrTransport );
				inspect( dataTypeOrTransport );
				return false;
			} else if ( seekingTransport ) {
				return !( selected = dataTypeOrTransport );
			}
		} );
		return selected;
	}

	return inspect( options.dataTypes[ 0 ] ) || !inspected[ "*" ] && inspect( "*" );
}

// A special extend for ajax options
// that takes "flat" options (not to be deep extended)
// Fixes #9887
function ajaxExtend( target, src ) {
	var deep, key,
		flatOptions = jQuery.ajaxSettings.flatOptions || {};

	for ( key in src ) {
		if ( src[ key ] !== undefined ) {
			( flatOptions[ key ] ? target : ( deep || ( deep = {} ) ) )[ key ] = src[ key ];
		}
	}
	if ( deep ) {
		jQuery.extend( true, target, deep );
	}

	return target;
}

/* Handles responses to an ajax request:
 * - finds the right dataType (mediates between content-type and expected dataType)
 * - returns the corresponding response
 */
function ajaxHandleResponses( s, jqXHR, responses ) {
	var firstDataType, ct, finalDataType, type,
		contents = s.contents,
		dataTypes = s.dataTypes;

	// Remove auto dataType and get content-type in the process
	while ( dataTypes[ 0 ] === "*" ) {
		dataTypes.shift();
		if ( ct === undefined ) {
			ct = s.mimeType || jqXHR.getResponseHeader( "Content-Type" );
		}
	}

	// Check if we're dealing with a known content-type
	if ( ct ) {
		for ( type in contents ) {
			if ( contents[ type ] && contents[ type ].test( ct ) ) {
				dataTypes.unshift( type );
				break;
			}
		}
	}

	// Check to see if we have a response for the expected dataType
	if ( dataTypes[ 0 ] in responses ) {
		finalDataType = dataTypes[ 0 ];
	} else {

		// Try convertible dataTypes
		for ( type in responses ) {
			if ( !dataTypes[ 0 ] || s.converters[ type + " " + dataTypes[ 0 ] ] ) {
				finalDataType = type;
				break;
			}
			if ( !firstDataType ) {
				firstDataType = type;
			}
		}

		// Or just use first one
		finalDataType = finalDataType || firstDataType;
	}

	// If we found a dataType
	// We add the dataType to the list if needed
	// and return the corresponding response
	if ( finalDataType ) {
		if ( finalDataType !== dataTypes[ 0 ] ) {
			dataTypes.unshift( finalDataType );
		}
		return responses[ finalDataType ];
	}
}

/* Chain conversions given the request and the original response
 * Also sets the responseXXX fields on the jqXHR instance
 */
function ajaxConvert( s, response, jqXHR, isSuccess ) {
	var conv2, current, conv, tmp, prev,
		converters = {},

		// Work with a copy of dataTypes in case we need to modify it for conversion
		dataTypes = s.dataTypes.slice();

	// Create converters map with lowercased keys
	if ( dataTypes[ 1 ] ) {
		for ( conv in s.converters ) {
			converters[ conv.toLowerCase() ] = s.converters[ conv ];
		}
	}

	current = dataTypes.shift();

	// Convert to each sequential dataType
	while ( current ) {

		if ( s.responseFields[ current ] ) {
			jqXHR[ s.responseFields[ current ] ] = response;
		}

		// Apply the dataFilter if provided
		if ( !prev && isSuccess && s.dataFilter ) {
			response = s.dataFilter( response, s.dataType );
		}

		prev = current;
		current = dataTypes.shift();

		if ( current ) {

			// There's only work to do if current dataType is non-auto
			if ( current === "*" ) {

				current = prev;

			// Convert response if prev dataType is non-auto and differs from current
			} else if ( prev !== "*" && prev !== current ) {

				// Seek a direct converter
				conv = converters[ prev + " " + current ] || converters[ "* " + current ];

				// If none found, seek a pair
				if ( !conv ) {
					for ( conv2 in converters ) {

						// If conv2 outputs current
						tmp = conv2.split( " " );
						if ( tmp[ 1 ] === current ) {

							// If prev can be converted to accepted input
							conv = converters[ prev + " " + tmp[ 0 ] ] ||
								converters[ "* " + tmp[ 0 ] ];
							if ( conv ) {

								// Condense equivalence converters
								if ( conv === true ) {
									conv = converters[ conv2 ];

								// Otherwise, insert the intermediate dataType
								} else if ( converters[ conv2 ] !== true ) {
									current = tmp[ 0 ];
									dataTypes.unshift( tmp[ 1 ] );
								}
								break;
							}
						}
					}
				}

				// Apply converter (if not an equivalence)
				if ( conv !== true ) {

					// Unless errors are allowed to bubble, catch and return them
					if ( conv && s[ "throws" ] ) { // jscs:ignore requireDotNotation
						response = conv( response );
					} else {
						try {
							response = conv( response );
						} catch ( e ) {
							return {
								state: "parsererror",
								error: conv ? e : "No conversion from " + prev + " to " + current
							};
						}
					}
				}
			}
		}
	}

	return { state: "success", data: response };
}

jQuery.extend( {

	// Counter for holding the number of active queries
	active: 0,

	// Last-Modified header cache for next request
	lastModified: {},
	etag: {},

	ajaxSettings: {
		url: ajaxLocation,
		type: "GET",
		isLocal: rlocalProtocol.test( ajaxLocParts[ 1 ] ),
		global: true,
		processData: true,
		async: true,
		contentType: "application/x-www-form-urlencoded; charset=UTF-8",
		/*
		timeout: 0,
		data: null,
		dataType: null,
		username: null,
		password: null,
		cache: null,
		throws: false,
		traditional: false,
		headers: {},
		*/

		accepts: {
			"*": allTypes,
			text: "text/plain",
			html: "text/html",
			xml: "application/xml, text/xml",
			json: "application/json, text/javascript"
		},

		contents: {
			xml: /\bxml\b/,
			html: /\bhtml/,
			json: /\bjson\b/
		},

		responseFields: {
			xml: "responseXML",
			text: "responseText",
			json: "responseJSON"
		},

		// Data converters
		// Keys separate source (or catchall "*") and destination types with a single space
		converters: {

			// Convert anything to text
			"* text": String,

			// Text to html (true = no transformation)
			"text html": true,

			// Evaluate text as a json expression
			"text json": jQuery.parseJSON,

			// Parse text as xml
			"text xml": jQuery.parseXML
		},

		// For options that shouldn't be deep extended:
		// you can add your own custom options here if
		// and when you create one that shouldn't be
		// deep extended (see ajaxExtend)
		flatOptions: {
			url: true,
			context: true
		}
	},

	// Creates a full fledged settings object into target
	// with both ajaxSettings and settings fields.
	// If target is omitted, writes into ajaxSettings.
	ajaxSetup: function( target, settings ) {
		return settings ?

			// Building a settings object
			ajaxExtend( ajaxExtend( target, jQuery.ajaxSettings ), settings ) :

			// Extending ajaxSettings
			ajaxExtend( jQuery.ajaxSettings, target );
	},

	ajaxPrefilter: addToPrefiltersOrTransports( prefilters ),
	ajaxTransport: addToPrefiltersOrTransports( transports ),

	// Main method
	ajax: function( url, options ) {

		// If url is an object, simulate pre-1.5 signature
		if ( typeof url === "object" ) {
			options = url;
			url = undefined;
		}

		// Force options to be an object
		options = options || {};

		var

			// Cross-domain detection vars
			parts,

			// Loop variable
			i,

			// URL without anti-cache param
			cacheURL,

			// Response headers as string
			responseHeadersString,

			// timeout handle
			timeoutTimer,

			// To know if global events are to be dispatched
			fireGlobals,

			transport,

			// Response headers
			responseHeaders,

			// Create the final options object
			s = jQuery.ajaxSetup( {}, options ),

			// Callbacks context
			callbackContext = s.context || s,

			// Context for global events is callbackContext if it is a DOM node or jQuery collection
			globalEventContext = s.context &&
				( callbackContext.nodeType || callbackContext.jquery ) ?
					jQuery( callbackContext ) :
					jQuery.event,

			// Deferreds
			deferred = jQuery.Deferred(),
			completeDeferred = jQuery.Callbacks( "once memory" ),

			// Status-dependent callbacks
			statusCode = s.statusCode || {},

			// Headers (they are sent all at once)
			requestHeaders = {},
			requestHeadersNames = {},

			// The jqXHR state
			state = 0,

			// Default abort message
			strAbort = "canceled",

			// Fake xhr
			jqXHR = {
				readyState: 0,

				// Builds headers hashtable if needed
				getResponseHeader: function( key ) {
					var match;
					if ( state === 2 ) {
						if ( !responseHeaders ) {
							responseHeaders = {};
							while ( ( match = rheaders.exec( responseHeadersString ) ) ) {
								responseHeaders[ match[ 1 ].toLowerCase() ] = match[ 2 ];
							}
						}
						match = responseHeaders[ key.toLowerCase() ];
					}
					return match == null ? null : match;
				},

				// Raw string
				getAllResponseHeaders: function() {
					return state === 2 ? responseHeadersString : null;
				},

				// Caches the header
				setRequestHeader: function( name, value ) {
					var lname = name.toLowerCase();
					if ( !state ) {
						name = requestHeadersNames[ lname ] = requestHeadersNames[ lname ] || name;
						requestHeaders[ name ] = value;
					}
					return this;
				},

				// Overrides response content-type header
				overrideMimeType: function( type ) {
					if ( !state ) {
						s.mimeType = type;
					}
					return this;
				},

				// Status-dependent callbacks
				statusCode: function( map ) {
					var code;
					if ( map ) {
						if ( state < 2 ) {
							for ( code in map ) {

								// Lazy-add the new callback in a way that preserves old ones
								statusCode[ code ] = [ statusCode[ code ], map[ code ] ];
							}
						} else {

							// Execute the appropriate callbacks
							jqXHR.always( map[ jqXHR.status ] );
						}
					}
					return this;
				},

				// Cancel the request
				abort: function( statusText ) {
					var finalText = statusText || strAbort;
					if ( transport ) {
						transport.abort( finalText );
					}
					done( 0, finalText );
					return this;
				}
			};

		// Attach deferreds
		deferred.promise( jqXHR ).complete = completeDeferred.add;
		jqXHR.success = jqXHR.done;
		jqXHR.error = jqXHR.fail;

		// Remove hash character (#7531: and string promotion)
		// Add protocol if not provided (#5866: IE7 issue with protocol-less urls)
		// Handle falsy url in the settings object (#10093: consistency with old signature)
		// We also use the url parameter if available
		s.url = ( ( url || s.url || ajaxLocation ) + "" )
			.replace( rhash, "" )
			.replace( rprotocol, ajaxLocParts[ 1 ] + "//" );

		// Alias method option to type as per ticket #12004
		s.type = options.method || options.type || s.method || s.type;

		// Extract dataTypes list
		s.dataTypes = jQuery.trim( s.dataType || "*" ).toLowerCase().match( rnotwhite ) || [ "" ];

		// A cross-domain request is in order when we have a protocol:host:port mismatch
		if ( s.crossDomain == null ) {
			parts = rurl.exec( s.url.toLowerCase() );
			s.crossDomain = !!( parts &&
				( parts[ 1 ] !== ajaxLocParts[ 1 ] || parts[ 2 ] !== ajaxLocParts[ 2 ] ||
					( parts[ 3 ] || ( parts[ 1 ] === "http:" ? "80" : "443" ) ) !==
						( ajaxLocParts[ 3 ] || ( ajaxLocParts[ 1 ] === "http:" ? "80" : "443" ) ) )
			);
		}

		// Convert data if not already a string
		if ( s.data && s.processData && typeof s.data !== "string" ) {
			s.data = jQuery.param( s.data, s.traditional );
		}

		// Apply prefilters
		inspectPrefiltersOrTransports( prefilters, s, options, jqXHR );

		// If request was aborted inside a prefilter, stop there
		if ( state === 2 ) {
			return jqXHR;
		}

		// We can fire global events as of now if asked to
		// Don't fire events if jQuery.event is undefined in an AMD-usage scenario (#15118)
		fireGlobals = jQuery.event && s.global;

		// Watch for a new set of requests
		if ( fireGlobals && jQuery.active++ === 0 ) {
			jQuery.event.trigger( "ajaxStart" );
		}

		// Uppercase the type
		s.type = s.type.toUpperCase();

		// Determine if request has content
		s.hasContent = !rnoContent.test( s.type );

		// Save the URL in case we're toying with the If-Modified-Since
		// and/or If-None-Match header later on
		cacheURL = s.url;

		// More options handling for requests with no content
		if ( !s.hasContent ) {

			// If data is available, append data to url
			if ( s.data ) {
				cacheURL = ( s.url += ( rquery.test( cacheURL ) ? "&" : "?" ) + s.data );

				// #9682: remove data so that it's not used in an eventual retry
				delete s.data;
			}

			// Add anti-cache in url if needed
			if ( s.cache === false ) {
				s.url = rts.test( cacheURL ) ?

					// If there is already a '_' parameter, set its value
					cacheURL.replace( rts, "$1_=" + nonce++ ) :

					// Otherwise add one to the end
					cacheURL + ( rquery.test( cacheURL ) ? "&" : "?" ) + "_=" + nonce++;
			}
		}

		// Set the If-Modified-Since and/or If-None-Match header, if in ifModified mode.
		if ( s.ifModified ) {
			if ( jQuery.lastModified[ cacheURL ] ) {
				jqXHR.setRequestHeader( "If-Modified-Since", jQuery.lastModified[ cacheURL ] );
			}
			if ( jQuery.etag[ cacheURL ] ) {
				jqXHR.setRequestHeader( "If-None-Match", jQuery.etag[ cacheURL ] );
			}
		}

		// Set the correct header, if data is being sent
		if ( s.data && s.hasContent && s.contentType !== false || options.contentType ) {
			jqXHR.setRequestHeader( "Content-Type", s.contentType );
		}

		// Set the Accepts header for the server, depending on the dataType
		jqXHR.setRequestHeader(
			"Accept",
			s.dataTypes[ 0 ] && s.accepts[ s.dataTypes[ 0 ] ] ?
				s.accepts[ s.dataTypes[ 0 ] ] +
					( s.dataTypes[ 0 ] !== "*" ? ", " + allTypes + "; q=0.01" : "" ) :
				s.accepts[ "*" ]
		);

		// Check for headers option
		for ( i in s.headers ) {
			jqXHR.setRequestHeader( i, s.headers[ i ] );
		}

		// Allow custom headers/mimetypes and early abort
		if ( s.beforeSend &&
			( s.beforeSend.call( callbackContext, jqXHR, s ) === false || state === 2 ) ) {

			// Abort if not done already and return
			return jqXHR.abort();
		}

		// aborting is no longer a cancellation
		strAbort = "abort";

		// Install callbacks on deferreds
		for ( i in { success: 1, error: 1, complete: 1 } ) {
			jqXHR[ i ]( s[ i ] );
		}

		// Get transport
		transport = inspectPrefiltersOrTransports( transports, s, options, jqXHR );

		// If no transport, we auto-abort
		if ( !transport ) {
			done( -1, "No Transport" );
		} else {
			jqXHR.readyState = 1;

			// Send global event
			if ( fireGlobals ) {
				globalEventContext.trigger( "ajaxSend", [ jqXHR, s ] );
			}

			// If request was aborted inside ajaxSend, stop there
			if ( state === 2 ) {
				return jqXHR;
			}

			// Timeout
			if ( s.async && s.timeout > 0 ) {
				timeoutTimer = window.setTimeout( function() {
					jqXHR.abort( "timeout" );
				}, s.timeout );
			}

			try {
				state = 1;
				transport.send( requestHeaders, done );
			} catch ( e ) {

				// Propagate exception as error if not done
				if ( state < 2 ) {
					done( -1, e );

				// Simply rethrow otherwise
				} else {
					throw e;
				}
			}
		}

		// Callback for when everything is done
		function done( status, nativeStatusText, responses, headers ) {
			var isSuccess, success, error, response, modified,
				statusText = nativeStatusText;

			// Called once
			if ( state === 2 ) {
				return;
			}

			// State is "done" now
			state = 2;

			// Clear timeout if it exists
			if ( timeoutTimer ) {
				window.clearTimeout( timeoutTimer );
			}

			// Dereference transport for early garbage collection
			// (no matter how long the jqXHR object will be used)
			transport = undefined;

			// Cache response headers
			responseHeadersString = headers || "";

			// Set readyState
			jqXHR.readyState = status > 0 ? 4 : 0;

			// Determine if successful
			isSuccess = status >= 200 && status < 300 || status === 304;

			// Get response data
			if ( responses ) {
				response = ajaxHandleResponses( s, jqXHR, responses );
			}

			// Convert no matter what (that way responseXXX fields are always set)
			response = ajaxConvert( s, response, jqXHR, isSuccess );

			// If successful, handle type chaining
			if ( isSuccess ) {

				// Set the If-Modified-Since and/or If-None-Match header, if in ifModified mode.
				if ( s.ifModified ) {
					modified = jqXHR.getResponseHeader( "Last-Modified" );
					if ( modified ) {
						jQuery.lastModified[ cacheURL ] = modified;
					}
					modified = jqXHR.getResponseHeader( "etag" );
					if ( modified ) {
						jQuery.etag[ cacheURL ] = modified;
					}
				}

				// if no content
				if ( status === 204 || s.type === "HEAD" ) {
					statusText = "nocontent";

				// if not modified
				} else if ( status === 304 ) {
					statusText = "notmodified";

				// If we have data, let's convert it
				} else {
					statusText = response.state;
					success = response.data;
					error = response.error;
					isSuccess = !error;
				}
			} else {

				// We extract error from statusText
				// then normalize statusText and status for non-aborts
				error = statusText;
				if ( status || !statusText ) {
					statusText = "error";
					if ( status < 0 ) {
						status = 0;
					}
				}
			}

			// Set data for the fake xhr object
			jqXHR.status = status;
			jqXHR.statusText = ( nativeStatusText || statusText ) + "";

			// Success/Error
			if ( isSuccess ) {
				deferred.resolveWith( callbackContext, [ success, statusText, jqXHR ] );
			} else {
				deferred.rejectWith( callbackContext, [ jqXHR, statusText, error ] );
			}

			// Status-dependent callbacks
			jqXHR.statusCode( statusCode );
			statusCode = undefined;

			if ( fireGlobals ) {
				globalEventContext.trigger( isSuccess ? "ajaxSuccess" : "ajaxError",
					[ jqXHR, s, isSuccess ? success : error ] );
			}

			// Complete
			completeDeferred.fireWith( callbackContext, [ jqXHR, statusText ] );

			if ( fireGlobals ) {
				globalEventContext.trigger( "ajaxComplete", [ jqXHR, s ] );

				// Handle the global AJAX counter
				if ( !( --jQuery.active ) ) {
					jQuery.event.trigger( "ajaxStop" );
				}
			}
		}

		return jqXHR;
	},

	getJSON: function( url, data, callback ) {
		return jQuery.get( url, data, callback, "json" );
	},

	getScript: function( url, callback ) {
		return jQuery.get( url, undefined, callback, "script" );
	}
} );

jQuery.each( [ "get", "post" ], function( i, method ) {
	jQuery[ method ] = function( url, data, callback, type ) {

		// shift arguments if data argument was omitted
		if ( jQuery.isFunction( data ) ) {
			type = type || callback;
			callback = data;
			data = undefined;
		}

		// The url can be an options object (which then must have .url)
		return jQuery.ajax( jQuery.extend( {
			url: url,
			type: method,
			dataType: type,
			data: data,
			success: callback
		}, jQuery.isPlainObject( url ) && url ) );
	};
} );


jQuery._evalUrl = function( url ) {
	return jQuery.ajax( {
		url: url,

		// Make this explicit, since user can override this through ajaxSetup (#11264)
		type: "GET",
		dataType: "script",
		cache: true,
		async: false,
		global: false,
		"throws": true
	} );
};


jQuery.fn.extend( {
	wrapAll: function( html ) {
		if ( jQuery.isFunction( html ) ) {
			return this.each( function( i ) {
				jQuery( this ).wrapAll( html.call( this, i ) );
			} );
		}

		if ( this[ 0 ] ) {

			// The elements to wrap the target around
			var wrap = jQuery( html, this[ 0 ].ownerDocument ).eq( 0 ).clone( true );

			if ( this[ 0 ].parentNode ) {
				wrap.insertBefore( this[ 0 ] );
			}

			wrap.map( function() {
				var elem = this;

				while ( elem.firstChild && elem.firstChild.nodeType === 1 ) {
					elem = elem.firstChild;
				}

				return elem;
			} ).append( this );
		}

		return this;
	},

	wrapInner: function( html ) {
		if ( jQuery.isFunction( html ) ) {
			return this.each( function( i ) {
				jQuery( this ).wrapInner( html.call( this, i ) );
			} );
		}

		return this.each( function() {
			var self = jQuery( this ),
				contents = self.contents();

			if ( contents.length ) {
				contents.wrapAll( html );

			} else {
				self.append( html );
			}
		} );
	},

	wrap: function( html ) {
		var isFunction = jQuery.isFunction( html );

		return this.each( function( i ) {
			jQuery( this ).wrapAll( isFunction ? html.call( this, i ) : html );
		} );
	},

	unwrap: function() {
		return this.parent().each( function() {
			if ( !jQuery.nodeName( this, "body" ) ) {
				jQuery( this ).replaceWith( this.childNodes );
			}
		} ).end();
	}
} );


function getDisplay( elem ) {
	return elem.style && elem.style.display || jQuery.css( elem, "display" );
}

function filterHidden( elem ) {

	// Disconnected elements are considered hidden
	if ( !jQuery.contains( elem.ownerDocument || document, elem ) ) {
		return true;
	}
	while ( elem && elem.nodeType === 1 ) {
		if ( getDisplay( elem ) === "none" || elem.type === "hidden" ) {
			return true;
		}
		elem = elem.parentNode;
	}
	return false;
}

jQuery.expr.filters.hidden = function( elem ) {

	// Support: Opera <= 12.12
	// Opera reports offsetWidths and offsetHeights less than zero on some elements
	return support.reliableHiddenOffsets() ?
		( elem.offsetWidth <= 0 && elem.offsetHeight <= 0 &&
			!elem.getClientRects().length ) :
			filterHidden( elem );
};

jQuery.expr.filters.visible = function( elem ) {
	return !jQuery.expr.filters.hidden( elem );
};




var r20 = /%20/g,
	rbracket = /\[\]$/,
	rCRLF = /\r?\n/g,
	rsubmitterTypes = /^(?:submit|button|image|reset|file)$/i,
	rsubmittable = /^(?:input|select|textarea|keygen)/i;

function buildParams( prefix, obj, traditional, add ) {
	var name;

	if ( jQuery.isArray( obj ) ) {

		// Serialize array item.
		jQuery.each( obj, function( i, v ) {
			if ( traditional || rbracket.test( prefix ) ) {

				// Treat each array item as a scalar.
				add( prefix, v );

			} else {

				// Item is non-scalar (array or object), encode its numeric index.
				buildParams(
					prefix + "[" + ( typeof v === "object" && v != null ? i : "" ) + "]",
					v,
					traditional,
					add
				);
			}
		} );

	} else if ( !traditional && jQuery.type( obj ) === "object" ) {

		// Serialize object item.
		for ( name in obj ) {
			buildParams( prefix + "[" + name + "]", obj[ name ], traditional, add );
		}

	} else {

		// Serialize scalar item.
		add( prefix, obj );
	}
}

// Serialize an array of form elements or a set of
// key/values into a query string
jQuery.param = function( a, traditional ) {
	var prefix,
		s = [],
		add = function( key, value ) {

			// If value is a function, invoke it and return its value
			value = jQuery.isFunction( value ) ? value() : ( value == null ? "" : value );
			s[ s.length ] = encodeURIComponent( key ) + "=" + encodeURIComponent( value );
		};

	// Set traditional to true for jQuery <= 1.3.2 behavior.
	if ( traditional === undefined ) {
		traditional = jQuery.ajaxSettings && jQuery.ajaxSettings.traditional;
	}

	// If an array was passed in, assume that it is an array of form elements.
	if ( jQuery.isArray( a ) || ( a.jquery && !jQuery.isPlainObject( a ) ) ) {

		// Serialize the form elements
		jQuery.each( a, function() {
			add( this.name, this.value );
		} );

	} else {

		// If traditional, encode the "old" way (the way 1.3.2 or older
		// did it), otherwise encode params recursively.
		for ( prefix in a ) {
			buildParams( prefix, a[ prefix ], traditional, add );
		}
	}

	// Return the resulting serialization
	return s.join( "&" ).replace( r20, "+" );
};

jQuery.fn.extend( {
	serialize: function() {
		return jQuery.param( this.serializeArray() );
	},
	serializeArray: function() {
		return this.map( function() {

			// Can add propHook for "elements" to filter or add form elements
			var elements = jQuery.prop( this, "elements" );
			return elements ? jQuery.makeArray( elements ) : this;
		} )
		.filter( function() {
			var type = this.type;

			// Use .is(":disabled") so that fieldset[disabled] works
			return this.name && !jQuery( this ).is( ":disabled" ) &&
				rsubmittable.test( this.nodeName ) && !rsubmitterTypes.test( type ) &&
				( this.checked || !rcheckableType.test( type ) );
		} )
		.map( function( i, elem ) {
			var val = jQuery( this ).val();

			return val == null ?
				null :
				jQuery.isArray( val ) ?
					jQuery.map( val, function( val ) {
						return { name: elem.name, value: val.replace( rCRLF, "\r\n" ) };
					} ) :
					{ name: elem.name, value: val.replace( rCRLF, "\r\n" ) };
		} ).get();
	}
} );


// Create the request object
// (This is still attached to ajaxSettings for backward compatibility)
jQuery.ajaxSettings.xhr = window.ActiveXObject !== undefined ?

	// Support: IE6-IE8
	function() {

		// XHR cannot access local files, always use ActiveX for that case
		if ( this.isLocal ) {
			return createActiveXHR();
		}

		// Support: IE 9-11
		// IE seems to error on cross-domain PATCH requests when ActiveX XHR
		// is used. In IE 9+ always use the native XHR.
		// Note: this condition won't catch Edge as it doesn't define
		// document.documentMode but it also doesn't support ActiveX so it won't
		// reach this code.
		if ( document.documentMode > 8 ) {
			return createStandardXHR();
		}

		// Support: IE<9
		// oldIE XHR does not support non-RFC2616 methods (#13240)
		// See http://msdn.microsoft.com/en-us/library/ie/ms536648(v=vs.85).aspx
		// and http://www.w3.org/Protocols/rfc2616/rfc2616-sec9.html#sec9
		// Although this check for six methods instead of eight
		// since IE also does not support "trace" and "connect"
		return /^(get|post|head|put|delete|options)$/i.test( this.type ) &&
			createStandardXHR() || createActiveXHR();
	} :

	// For all other browsers, use the standard XMLHttpRequest object
	createStandardXHR;

var xhrId = 0,
	xhrCallbacks = {},
	xhrSupported = jQuery.ajaxSettings.xhr();

// Support: IE<10
// Open requests must be manually aborted on unload (#5280)
// See https://support.microsoft.com/kb/2856746 for more info
if ( window.attachEvent ) {
	window.attachEvent( "onunload", function() {
		for ( var key in xhrCallbacks ) {
			xhrCallbacks[ key ]( undefined, true );
		}
	} );
}

// Determine support properties
support.cors = !!xhrSupported && ( "withCredentials" in xhrSupported );
xhrSupported = support.ajax = !!xhrSupported;

// Create transport if the browser can provide an xhr
if ( xhrSupported ) {

	jQuery.ajaxTransport( function( options ) {

		// Cross domain only allowed if supported through XMLHttpRequest
		if ( !options.crossDomain || support.cors ) {

			var callback;

			return {
				send: function( headers, complete ) {
					var i,
						xhr = options.xhr(),
						id = ++xhrId;

					// Open the socket
					xhr.open(
						options.type,
						options.url,
						options.async,
						options.username,
						options.password
					);

					// Apply custom fields if provided
					if ( options.xhrFields ) {
						for ( i in options.xhrFields ) {
							xhr[ i ] = options.xhrFields[ i ];
						}
					}

					// Override mime type if needed
					if ( options.mimeType && xhr.overrideMimeType ) {
						xhr.overrideMimeType( options.mimeType );
					}

					// X-Requested-With header
					// For cross-domain requests, seeing as conditions for a preflight are
					// akin to a jigsaw puzzle, we simply never set it to be sure.
					// (it can always be set on a per-request basis or even using ajaxSetup)
					// For same-domain requests, won't change header if already provided.
					if ( !options.crossDomain && !headers[ "X-Requested-With" ] ) {
						headers[ "X-Requested-With" ] = "XMLHttpRequest";
					}

					// Set headers
					for ( i in headers ) {

						// Support: IE<9
						// IE's ActiveXObject throws a 'Type Mismatch' exception when setting
						// request header to a null-value.
						//
						// To keep consistent with other XHR implementations, cast the value
						// to string and ignore `undefined`.
						if ( headers[ i ] !== undefined ) {
							xhr.setRequestHeader( i, headers[ i ] + "" );
						}
					}

					// Do send the request
					// This may raise an exception which is actually
					// handled in jQuery.ajax (so no try/catch here)
					xhr.send( ( options.hasContent && options.data ) || null );

					// Listener
					callback = function( _, isAbort ) {
						var status, statusText, responses;

						// Was never called and is aborted or complete
						if ( callback && ( isAbort || xhr.readyState === 4 ) ) {

							// Clean up
							delete xhrCallbacks[ id ];
							callback = undefined;
							xhr.onreadystatechange = jQuery.noop;

							// Abort manually if needed
							if ( isAbort ) {
								if ( xhr.readyState !== 4 ) {
									xhr.abort();
								}
							} else {
								responses = {};
								status = xhr.status;

								// Support: IE<10
								// Accessing binary-data responseText throws an exception
								// (#11426)
								if ( typeof xhr.responseText === "string" ) {
									responses.text = xhr.responseText;
								}

								// Firefox throws an exception when accessing
								// statusText for faulty cross-domain requests
								try {
									statusText = xhr.statusText;
								} catch ( e ) {

									// We normalize with Webkit giving an empty statusText
									statusText = "";
								}

								// Filter status for non standard behaviors

								// If the request is local and we have data: assume a success
								// (success with no data won't get notified, that's the best we
								// can do given current implementations)
								if ( !status && options.isLocal && !options.crossDomain ) {
									status = responses.text ? 200 : 404;

								// IE - #1450: sometimes returns 1223 when it should be 204
								} else if ( status === 1223 ) {
									status = 204;
								}
							}
						}

						// Call complete if needed
						if ( responses ) {
							complete( status, statusText, responses, xhr.getAllResponseHeaders() );
						}
					};

					// Do send the request
					// `xhr.send` may raise an exception, but it will be
					// handled in jQuery.ajax (so no try/catch here)
					if ( !options.async ) {

						// If we're in sync mode we fire the callback
						callback();
					} else if ( xhr.readyState === 4 ) {

						// (IE6 & IE7) if it's in cache and has been
						// retrieved directly we need to fire the callback
						window.setTimeout( callback );
					} else {

						// Register the callback, but delay it in case `xhr.send` throws
						// Add to the list of active xhr callbacks
						xhr.onreadystatechange = xhrCallbacks[ id ] = callback;
					}
				},

				abort: function() {
					if ( callback ) {
						callback( undefined, true );
					}
				}
			};
		}
	} );
}

// Functions to create xhrs
function createStandardXHR() {
	try {
		return new window.XMLHttpRequest();
	} catch ( e ) {}
}

function createActiveXHR() {
	try {
		return new window.ActiveXObject( "Microsoft.XMLHTTP" );
	} catch ( e ) {}
}




// Install script dataType
jQuery.ajaxSetup( {
	accepts: {
		script: "text/javascript, application/javascript, " +
			"application/ecmascript, application/x-ecmascript"
	},
	contents: {
		script: /\b(?:java|ecma)script\b/
	},
	converters: {
		"text script": function( text ) {
			jQuery.globalEval( text );
			return text;
		}
	}
} );

// Handle cache's special case and global
jQuery.ajaxPrefilter( "script", function( s ) {
	if ( s.cache === undefined ) {
		s.cache = false;
	}
	if ( s.crossDomain ) {
		s.type = "GET";
		s.global = false;
	}
} );

// Bind script tag hack transport
jQuery.ajaxTransport( "script", function( s ) {

	// This transport only deals with cross domain requests
	if ( s.crossDomain ) {

		var script,
			head = document.head || jQuery( "head" )[ 0 ] || document.documentElement;

		return {

			send: function( _, callback ) {

				script = document.createElement( "script" );

				script.async = true;

				if ( s.scriptCharset ) {
					script.charset = s.scriptCharset;
				}

				script.src = s.url;

				// Attach handlers for all browsers
				script.onload = script.onreadystatechange = function( _, isAbort ) {

					if ( isAbort || !script.readyState || /loaded|complete/.test( script.readyState ) ) {

						// Handle memory leak in IE
						script.onload = script.onreadystatechange = null;

						// Remove the script
						if ( script.parentNode ) {
							script.parentNode.removeChild( script );
						}

						// Dereference the script
						script = null;

						// Callback if not abort
						if ( !isAbort ) {
							callback( 200, "success" );
						}
					}
				};

				// Circumvent IE6 bugs with base elements (#2709 and #4378) by prepending
				// Use native DOM manipulation to avoid our domManip AJAX trickery
				head.insertBefore( script, head.firstChild );
			},

			abort: function() {
				if ( script ) {
					script.onload( undefined, true );
				}
			}
		};
	}
} );




var oldCallbacks = [],
	rjsonp = /(=)\?(?=&|$)|\?\?/;

// Default jsonp settings
jQuery.ajaxSetup( {
	jsonp: "callback",
	jsonpCallback: function() {
		var callback = oldCallbacks.pop() || ( jQuery.expando + "_" + ( nonce++ ) );
		this[ callback ] = true;
		return callback;
	}
} );

// Detect, normalize options and install callbacks for jsonp requests
jQuery.ajaxPrefilter( "json jsonp", function( s, originalSettings, jqXHR ) {

	var callbackName, overwritten, responseContainer,
		jsonProp = s.jsonp !== false && ( rjsonp.test( s.url ) ?
			"url" :
			typeof s.data === "string" &&
				( s.contentType || "" )
					.indexOf( "application/x-www-form-urlencoded" ) === 0 &&
				rjsonp.test( s.data ) && "data"
		);

	// Handle iff the expected data type is "jsonp" or we have a parameter to set
	if ( jsonProp || s.dataTypes[ 0 ] === "jsonp" ) {

		// Get callback name, remembering preexisting value associated with it
		callbackName = s.jsonpCallback = jQuery.isFunction( s.jsonpCallback ) ?
			s.jsonpCallback() :
			s.jsonpCallback;

		// Insert callback into url or form data
		if ( jsonProp ) {
			s[ jsonProp ] = s[ jsonProp ].replace( rjsonp, "$1" + callbackName );
		} else if ( s.jsonp !== false ) {
			s.url += ( rquery.test( s.url ) ? "&" : "?" ) + s.jsonp + "=" + callbackName;
		}

		// Use data converter to retrieve json after script execution
		s.converters[ "script json" ] = function() {
			if ( !responseContainer ) {
				jQuery.error( callbackName + " was not called" );
			}
			return responseContainer[ 0 ];
		};

		// force json dataType
		s.dataTypes[ 0 ] = "json";

		// Install callback
		overwritten = window[ callbackName ];
		window[ callbackName ] = function() {
			responseContainer = arguments;
		};

		// Clean-up function (fires after converters)
		jqXHR.always( function() {

			// If previous value didn't exist - remove it
			if ( overwritten === undefined ) {
				jQuery( window ).removeProp( callbackName );

			// Otherwise restore preexisting value
			} else {
				window[ callbackName ] = overwritten;
			}

			// Save back as free
			if ( s[ callbackName ] ) {

				// make sure that re-using the options doesn't screw things around
				s.jsonpCallback = originalSettings.jsonpCallback;

				// save the callback name for future use
				oldCallbacks.push( callbackName );
			}

			// Call if it was a function and we have a response
			if ( responseContainer && jQuery.isFunction( overwritten ) ) {
				overwritten( responseContainer[ 0 ] );
			}

			responseContainer = overwritten = undefined;
		} );

		// Delegate to script
		return "script";
	}
} );




// data: string of html
// context (optional): If specified, the fragment will be created in this context,
// defaults to document
// keepScripts (optional): If true, will include scripts passed in the html string
jQuery.parseHTML = function( data, context, keepScripts ) {
	if ( !data || typeof data !== "string" ) {
		return null;
	}
	if ( typeof context === "boolean" ) {
		keepScripts = context;
		context = false;
	}
	context = context || document;

	var parsed = rsingleTag.exec( data ),
		scripts = !keepScripts && [];

	// Single tag
	if ( parsed ) {
		return [ context.createElement( parsed[ 1 ] ) ];
	}

	parsed = buildFragment( [ data ], context, scripts );

	if ( scripts && scripts.length ) {
		jQuery( scripts ).remove();
	}

	return jQuery.merge( [], parsed.childNodes );
};


// Keep a copy of the old load method
var _load = jQuery.fn.load;

/**
 * Load a url into a page
 */
jQuery.fn.load = function( url, params, callback ) {
	if ( typeof url !== "string" && _load ) {
		return _load.apply( this, arguments );
	}

	var selector, type, response,
		self = this,
		off = url.indexOf( " " );

	if ( off > -1 ) {
		selector = jQuery.trim( url.slice( off, url.length ) );
		url = url.slice( 0, off );
	}

	// If it's a function
	if ( jQuery.isFunction( params ) ) {

		// We assume that it's the callback
		callback = params;
		params = undefined;

	// Otherwise, build a param string
	} else if ( params && typeof params === "object" ) {
		type = "POST";
	}

	// If we have elements to modify, make the request
	if ( self.length > 0 ) {
		jQuery.ajax( {
			url: url,

			// If "type" variable is undefined, then "GET" method will be used.
			// Make value of this field explicit since
			// user can override it through ajaxSetup method
			type: type || "GET",
			dataType: "html",
			data: params
		} ).done( function( responseText ) {

			// Save response for use in complete callback
			response = arguments;

			self.html( selector ?

				// If a selector was specified, locate the right elements in a dummy div
				// Exclude scripts to avoid IE 'Permission Denied' errors
				jQuery( "<div>" ).append( jQuery.parseHTML( responseText ) ).find( selector ) :

				// Otherwise use the full result
				responseText );

		// If the request succeeds, this function gets "data", "status", "jqXHR"
		// but they are ignored because response was set above.
		// If it fails, this function gets "jqXHR", "status", "error"
		} ).always( callback && function( jqXHR, status ) {
			self.each( function() {
				callback.apply( this, response || [ jqXHR.responseText, status, jqXHR ] );
			} );
		} );
	}

	return this;
};




// Attach a bunch of functions for handling common AJAX events
jQuery.each( [
	"ajaxStart",
	"ajaxStop",
	"ajaxComplete",
	"ajaxError",
	"ajaxSuccess",
	"ajaxSend"
], function( i, type ) {
	jQuery.fn[ type ] = function( fn ) {
		return this.on( type, fn );
	};
} );




jQuery.expr.filters.animated = function( elem ) {
	return jQuery.grep( jQuery.timers, function( fn ) {
		return elem === fn.elem;
	} ).length;
};





/**
 * Gets a window from an element
 */
function getWindow( elem ) {
	return jQuery.isWindow( elem ) ?
		elem :
		elem.nodeType === 9 ?
			elem.defaultView || elem.parentWindow :
			false;
}

jQuery.offset = {
	setOffset: function( elem, options, i ) {
		var curPosition, curLeft, curCSSTop, curTop, curOffset, curCSSLeft, calculatePosition,
			position = jQuery.css( elem, "position" ),
			curElem = jQuery( elem ),
			props = {};

		// set position first, in-case top/left are set even on static elem
		if ( position === "static" ) {
			elem.style.position = "relative";
		}

		curOffset = curElem.offset();
		curCSSTop = jQuery.css( elem, "top" );
		curCSSLeft = jQuery.css( elem, "left" );
		calculatePosition = ( position === "absolute" || position === "fixed" ) &&
			jQuery.inArray( "auto", [ curCSSTop, curCSSLeft ] ) > -1;

		// need to be able to calculate position if either top or left
		// is auto and position is either absolute or fixed
		if ( calculatePosition ) {
			curPosition = curElem.position();
			curTop = curPosition.top;
			curLeft = curPosition.left;
		} else {
			curTop = parseFloat( curCSSTop ) || 0;
			curLeft = parseFloat( curCSSLeft ) || 0;
		}

		if ( jQuery.isFunction( options ) ) {

			// Use jQuery.extend here to allow modification of coordinates argument (gh-1848)
			options = options.call( elem, i, jQuery.extend( {}, curOffset ) );
		}

		if ( options.top != null ) {
			props.top = ( options.top - curOffset.top ) + curTop;
		}
		if ( options.left != null ) {
			props.left = ( options.left - curOffset.left ) + curLeft;
		}

		if ( "using" in options ) {
			options.using.call( elem, props );
		} else {
			curElem.css( props );
		}
	}
};

jQuery.fn.extend( {
	offset: function( options ) {
		if ( arguments.length ) {
			return options === undefined ?
				this :
				this.each( function( i ) {
					jQuery.offset.setOffset( this, options, i );
				} );
		}

		var docElem, win,
			box = { top: 0, left: 0 },
			elem = this[ 0 ],
			doc = elem && elem.ownerDocument;

		if ( !doc ) {
			return;
		}

		docElem = doc.documentElement;

		// Make sure it's not a disconnected DOM node
		if ( !jQuery.contains( docElem, elem ) ) {
			return box;
		}

		// If we don't have gBCR, just use 0,0 rather than error
		// BlackBerry 5, iOS 3 (original iPhone)
		if ( typeof elem.getBoundingClientRect !== "undefined" ) {
			box = elem.getBoundingClientRect();
		}
		win = getWindow( doc );
		return {
			top: box.top  + ( win.pageYOffset || docElem.scrollTop )  - ( docElem.clientTop  || 0 ),
			left: box.left + ( win.pageXOffset || docElem.scrollLeft ) - ( docElem.clientLeft || 0 )
		};
	},

	position: function() {
		if ( !this[ 0 ] ) {
			return;
		}

		var offsetParent, offset,
			parentOffset = { top: 0, left: 0 },
			elem = this[ 0 ];

		// Fixed elements are offset from window (parentOffset = {top:0, left: 0},
		// because it is its only offset parent
		if ( jQuery.css( elem, "position" ) === "fixed" ) {

			// we assume that getBoundingClientRect is available when computed position is fixed
			offset = elem.getBoundingClientRect();
		} else {

			// Get *real* offsetParent
			offsetParent = this.offsetParent();

			// Get correct offsets
			offset = this.offset();
			if ( !jQuery.nodeName( offsetParent[ 0 ], "html" ) ) {
				parentOffset = offsetParent.offset();
			}

			// Add offsetParent borders
			parentOffset.top  += jQuery.css( offsetParent[ 0 ], "borderTopWidth", true );
			parentOffset.left += jQuery.css( offsetParent[ 0 ], "borderLeftWidth", true );
		}

		// Subtract parent offsets and element margins
		// note: when an element has margin: auto the offsetLeft and marginLeft
		// are the same in Safari causing offset.left to incorrectly be 0
		return {
			top:  offset.top  - parentOffset.top - jQuery.css( elem, "marginTop", true ),
			left: offset.left - parentOffset.left - jQuery.css( elem, "marginLeft", true )
		};
	},

	offsetParent: function() {
		return this.map( function() {
			var offsetParent = this.offsetParent;

			while ( offsetParent && ( !jQuery.nodeName( offsetParent, "html" ) &&
				jQuery.css( offsetParent, "position" ) === "static" ) ) {
				offsetParent = offsetParent.offsetParent;
			}
			return offsetParent || documentElement;
		} );
	}
} );

// Create scrollLeft and scrollTop methods
jQuery.each( { scrollLeft: "pageXOffset", scrollTop: "pageYOffset" }, function( method, prop ) {
	var top = /Y/.test( prop );

	jQuery.fn[ method ] = function( val ) {
		return access( this, function( elem, method, val ) {
			var win = getWindow( elem );

			if ( val === undefined ) {
				return win ? ( prop in win ) ? win[ prop ] :
					win.document.documentElement[ method ] :
					elem[ method ];
			}

			if ( win ) {
				win.scrollTo(
					!top ? val : jQuery( win ).scrollLeft(),
					top ? val : jQuery( win ).scrollTop()
				);

			} else {
				elem[ method ] = val;
			}
		}, method, val, arguments.length, null );
	};
} );

// Support: Safari<7-8+, Chrome<37-44+
// Add the top/left cssHooks using jQuery.fn.position
// Webkit bug: https://bugs.webkit.org/show_bug.cgi?id=29084
// getComputedStyle returns percent when specified for top/left/bottom/right
// rather than make the css module depend on the offset module, we just check for it here
jQuery.each( [ "top", "left" ], function( i, prop ) {
	jQuery.cssHooks[ prop ] = addGetHookIf( support.pixelPosition,
		function( elem, computed ) {
			if ( computed ) {
				computed = curCSS( elem, prop );

				// if curCSS returns percentage, fallback to offset
				return rnumnonpx.test( computed ) ?
					jQuery( elem ).position()[ prop ] + "px" :
					computed;
			}
		}
	);
} );


// Create innerHeight, innerWidth, height, width, outerHeight and outerWidth methods
jQuery.each( { Height: "height", Width: "width" }, function( name, type ) {
	jQuery.each( { padding: "inner" + name, content: type, "": "outer" + name },
	function( defaultExtra, funcName ) {

		// margin is only for outerHeight, outerWidth
		jQuery.fn[ funcName ] = function( margin, value ) {
			var chainable = arguments.length && ( defaultExtra || typeof margin !== "boolean" ),
				extra = defaultExtra || ( margin === true || value === true ? "margin" : "border" );

			return access( this, function( elem, type, value ) {
				var doc;

				if ( jQuery.isWindow( elem ) ) {

					// As of 5/8/2012 this will yield incorrect results for Mobile Safari, but there
					// isn't a whole lot we can do. See pull request at this URL for discussion:
					// https://github.com/jquery/jquery/pull/764
					return elem.document.documentElement[ "client" + name ];
				}

				// Get document width or height
				if ( elem.nodeType === 9 ) {
					doc = elem.documentElement;

					// Either scroll[Width/Height] or offset[Width/Height] or client[Width/Height],
					// whichever is greatest
					// unfortunately, this causes bug #3838 in IE6/8 only,
					// but there is currently no good, small way to fix it.
					return Math.max(
						elem.body[ "scroll" + name ], doc[ "scroll" + name ],
						elem.body[ "offset" + name ], doc[ "offset" + name ],
						doc[ "client" + name ]
					);
				}

				return value === undefined ?

					// Get width or height on the element, requesting but not forcing parseFloat
					jQuery.css( elem, type, extra ) :

					// Set width or height on the element
					jQuery.style( elem, type, value, extra );
			}, type, chainable ? margin : undefined, chainable, null );
		};
	} );
} );


jQuery.fn.extend( {

	bind: function( types, data, fn ) {
		return this.on( types, null, data, fn );
	},
	unbind: function( types, fn ) {
		return this.off( types, null, fn );
	},

	delegate: function( selector, types, data, fn ) {
		return this.on( types, selector, data, fn );
	},
	undelegate: function( selector, types, fn ) {

		// ( namespace ) or ( selector, types [, fn] )
		return arguments.length === 1 ?
			this.off( selector, "**" ) :
			this.off( types, selector || "**", fn );
	}
} );

// The number of elements contained in the matched element set
jQuery.fn.size = function() {
	return this.length;
};

jQuery.fn.andSelf = jQuery.fn.addBack;




// Register as a named AMD module, since jQuery can be concatenated with other
// files that may use define, but not via a proper concatenation script that
// understands anonymous AMD modules. A named AMD is safest and most robust
// way to register. Lowercase jquery is used because AMD module names are
// derived from file names, and jQuery is normally delivered in a lowercase
// file name. Do this after creating the global so that if an AMD module wants
// to call noConflict to hide this version of jQuery, it will work.

// Note that for maximum portability, libraries that are not jQuery should
// declare themselves as anonymous modules, and avoid setting a global if an
// AMD loader is present. jQuery is a special case. For more information, see
// https://github.com/jrburke/requirejs/wiki/Updating-existing-libraries#wiki-anon

if ( true ) {
	!(__WEBPACK_AMD_DEFINE_ARRAY__ = [], __WEBPACK_AMD_DEFINE_RESULT__ = function() {
		return jQuery;
	}.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
}



var

	// Map over jQuery in case of overwrite
	_jQuery = window.jQuery,

	// Map over the $ in case of overwrite
	_$ = window.$;

jQuery.noConflict = function( deep ) {
	if ( window.$ === jQuery ) {
		window.$ = _$;
	}

	if ( deep && window.jQuery === jQuery ) {
		window.jQuery = _jQuery;
	}

	return jQuery;
};

// Expose jQuery and $ identifiers, even in
// AMD (#7102#comment:10, https://github.com/jquery/jquery/pull/557)
// and CommonJS for browser emulators (#13566)
if ( !noGlobal ) {
	window.jQuery = window.$ = jQuery;
}

return jQuery;
}));


/***/ }),
/* 1 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function(module) {var require;//! moment.js
//! version : 2.20.1
//! authors : Tim Wood, Iskren Chernev, Moment.js contributors
//! license : MIT
//! momentjs.com

;(function (global, factory) {
     true ? module.exports = factory() :
    typeof define === 'function' && define.amd ? define(factory) :
    global.moment = factory()
}(this, (function () { 'use strict';

var hookCallback;

function hooks () {
    return hookCallback.apply(null, arguments);
}

// This is done to register the method called with moment()
// without creating circular dependencies.
function setHookCallback (callback) {
    hookCallback = callback;
}

function isArray(input) {
    return input instanceof Array || Object.prototype.toString.call(input) === '[object Array]';
}

function isObject(input) {
    // IE8 will treat undefined and null as object if it wasn't for
    // input != null
    return input != null && Object.prototype.toString.call(input) === '[object Object]';
}

function isObjectEmpty(obj) {
    if (Object.getOwnPropertyNames) {
        return (Object.getOwnPropertyNames(obj).length === 0);
    } else {
        var k;
        for (k in obj) {
            if (obj.hasOwnProperty(k)) {
                return false;
            }
        }
        return true;
    }
}

function isUndefined(input) {
    return input === void 0;
}

function isNumber(input) {
    return typeof input === 'number' || Object.prototype.toString.call(input) === '[object Number]';
}

function isDate(input) {
    return input instanceof Date || Object.prototype.toString.call(input) === '[object Date]';
}

function map(arr, fn) {
    var res = [], i;
    for (i = 0; i < arr.length; ++i) {
        res.push(fn(arr[i], i));
    }
    return res;
}

function hasOwnProp(a, b) {
    return Object.prototype.hasOwnProperty.call(a, b);
}

function extend(a, b) {
    for (var i in b) {
        if (hasOwnProp(b, i)) {
            a[i] = b[i];
        }
    }

    if (hasOwnProp(b, 'toString')) {
        a.toString = b.toString;
    }

    if (hasOwnProp(b, 'valueOf')) {
        a.valueOf = b.valueOf;
    }

    return a;
}

function createUTC (input, format, locale, strict) {
    return createLocalOrUTC(input, format, locale, strict, true).utc();
}

function defaultParsingFlags() {
    // We need to deep clone this object.
    return {
        empty           : false,
        unusedTokens    : [],
        unusedInput     : [],
        overflow        : -2,
        charsLeftOver   : 0,
        nullInput       : false,
        invalidMonth    : null,
        invalidFormat   : false,
        userInvalidated : false,
        iso             : false,
        parsedDateParts : [],
        meridiem        : null,
        rfc2822         : false,
        weekdayMismatch : false
    };
}

function getParsingFlags(m) {
    if (m._pf == null) {
        m._pf = defaultParsingFlags();
    }
    return m._pf;
}

var some;
if (Array.prototype.some) {
    some = Array.prototype.some;
} else {
    some = function (fun) {
        var t = Object(this);
        var len = t.length >>> 0;

        for (var i = 0; i < len; i++) {
            if (i in t && fun.call(this, t[i], i, t)) {
                return true;
            }
        }

        return false;
    };
}

function isValid(m) {
    if (m._isValid == null) {
        var flags = getParsingFlags(m);
        var parsedParts = some.call(flags.parsedDateParts, function (i) {
            return i != null;
        });
        var isNowValid = !isNaN(m._d.getTime()) &&
            flags.overflow < 0 &&
            !flags.empty &&
            !flags.invalidMonth &&
            !flags.invalidWeekday &&
            !flags.weekdayMismatch &&
            !flags.nullInput &&
            !flags.invalidFormat &&
            !flags.userInvalidated &&
            (!flags.meridiem || (flags.meridiem && parsedParts));

        if (m._strict) {
            isNowValid = isNowValid &&
                flags.charsLeftOver === 0 &&
                flags.unusedTokens.length === 0 &&
                flags.bigHour === undefined;
        }

        if (Object.isFrozen == null || !Object.isFrozen(m)) {
            m._isValid = isNowValid;
        }
        else {
            return isNowValid;
        }
    }
    return m._isValid;
}

function createInvalid (flags) {
    var m = createUTC(NaN);
    if (flags != null) {
        extend(getParsingFlags(m), flags);
    }
    else {
        getParsingFlags(m).userInvalidated = true;
    }

    return m;
}

// Plugins that add properties should also add the key here (null value),
// so we can properly clone ourselves.
var momentProperties = hooks.momentProperties = [];

function copyConfig(to, from) {
    var i, prop, val;

    if (!isUndefined(from._isAMomentObject)) {
        to._isAMomentObject = from._isAMomentObject;
    }
    if (!isUndefined(from._i)) {
        to._i = from._i;
    }
    if (!isUndefined(from._f)) {
        to._f = from._f;
    }
    if (!isUndefined(from._l)) {
        to._l = from._l;
    }
    if (!isUndefined(from._strict)) {
        to._strict = from._strict;
    }
    if (!isUndefined(from._tzm)) {
        to._tzm = from._tzm;
    }
    if (!isUndefined(from._isUTC)) {
        to._isUTC = from._isUTC;
    }
    if (!isUndefined(from._offset)) {
        to._offset = from._offset;
    }
    if (!isUndefined(from._pf)) {
        to._pf = getParsingFlags(from);
    }
    if (!isUndefined(from._locale)) {
        to._locale = from._locale;
    }

    if (momentProperties.length > 0) {
        for (i = 0; i < momentProperties.length; i++) {
            prop = momentProperties[i];
            val = from[prop];
            if (!isUndefined(val)) {
                to[prop] = val;
            }
        }
    }

    return to;
}

var updateInProgress = false;

// Moment prototype object
function Moment(config) {
    copyConfig(this, config);
    this._d = new Date(config._d != null ? config._d.getTime() : NaN);
    if (!this.isValid()) {
        this._d = new Date(NaN);
    }
    // Prevent infinite loop in case updateOffset creates new moment
    // objects.
    if (updateInProgress === false) {
        updateInProgress = true;
        hooks.updateOffset(this);
        updateInProgress = false;
    }
}

function isMoment (obj) {
    return obj instanceof Moment || (obj != null && obj._isAMomentObject != null);
}

function absFloor (number) {
    if (number < 0) {
        // -0 -> 0
        return Math.ceil(number) || 0;
    } else {
        return Math.floor(number);
    }
}

function toInt(argumentForCoercion) {
    var coercedNumber = +argumentForCoercion,
        value = 0;

    if (coercedNumber !== 0 && isFinite(coercedNumber)) {
        value = absFloor(coercedNumber);
    }

    return value;
}

// compare two arrays, return the number of differences
function compareArrays(array1, array2, dontConvert) {
    var len = Math.min(array1.length, array2.length),
        lengthDiff = Math.abs(array1.length - array2.length),
        diffs = 0,
        i;
    for (i = 0; i < len; i++) {
        if ((dontConvert && array1[i] !== array2[i]) ||
            (!dontConvert && toInt(array1[i]) !== toInt(array2[i]))) {
            diffs++;
        }
    }
    return diffs + lengthDiff;
}

function warn(msg) {
    if (hooks.suppressDeprecationWarnings === false &&
            (typeof console !==  'undefined') && console.warn) {
        console.warn('Deprecation warning: ' + msg);
    }
}

function deprecate(msg, fn) {
    var firstTime = true;

    return extend(function () {
        if (hooks.deprecationHandler != null) {
            hooks.deprecationHandler(null, msg);
        }
        if (firstTime) {
            var args = [];
            var arg;
            for (var i = 0; i < arguments.length; i++) {
                arg = '';
                if (typeof arguments[i] === 'object') {
                    arg += '\n[' + i + '] ';
                    for (var key in arguments[0]) {
                        arg += key + ': ' + arguments[0][key] + ', ';
                    }
                    arg = arg.slice(0, -2); // Remove trailing comma and space
                } else {
                    arg = arguments[i];
                }
                args.push(arg);
            }
            warn(msg + '\nArguments: ' + Array.prototype.slice.call(args).join('') + '\n' + (new Error()).stack);
            firstTime = false;
        }
        return fn.apply(this, arguments);
    }, fn);
}

var deprecations = {};

function deprecateSimple(name, msg) {
    if (hooks.deprecationHandler != null) {
        hooks.deprecationHandler(name, msg);
    }
    if (!deprecations[name]) {
        warn(msg);
        deprecations[name] = true;
    }
}

hooks.suppressDeprecationWarnings = false;
hooks.deprecationHandler = null;

function isFunction(input) {
    return input instanceof Function || Object.prototype.toString.call(input) === '[object Function]';
}

function set (config) {
    var prop, i;
    for (i in config) {
        prop = config[i];
        if (isFunction(prop)) {
            this[i] = prop;
        } else {
            this['_' + i] = prop;
        }
    }
    this._config = config;
    // Lenient ordinal parsing accepts just a number in addition to
    // number + (possibly) stuff coming from _dayOfMonthOrdinalParse.
    // TODO: Remove "ordinalParse" fallback in next major release.
    this._dayOfMonthOrdinalParseLenient = new RegExp(
        (this._dayOfMonthOrdinalParse.source || this._ordinalParse.source) +
            '|' + (/\d{1,2}/).source);
}

function mergeConfigs(parentConfig, childConfig) {
    var res = extend({}, parentConfig), prop;
    for (prop in childConfig) {
        if (hasOwnProp(childConfig, prop)) {
            if (isObject(parentConfig[prop]) && isObject(childConfig[prop])) {
                res[prop] = {};
                extend(res[prop], parentConfig[prop]);
                extend(res[prop], childConfig[prop]);
            } else if (childConfig[prop] != null) {
                res[prop] = childConfig[prop];
            } else {
                delete res[prop];
            }
        }
    }
    for (prop in parentConfig) {
        if (hasOwnProp(parentConfig, prop) &&
                !hasOwnProp(childConfig, prop) &&
                isObject(parentConfig[prop])) {
            // make sure changes to properties don't modify parent config
            res[prop] = extend({}, res[prop]);
        }
    }
    return res;
}

function Locale(config) {
    if (config != null) {
        this.set(config);
    }
}

var keys;

if (Object.keys) {
    keys = Object.keys;
} else {
    keys = function (obj) {
        var i, res = [];
        for (i in obj) {
            if (hasOwnProp(obj, i)) {
                res.push(i);
            }
        }
        return res;
    };
}

var defaultCalendar = {
    sameDay : '[Today at] LT',
    nextDay : '[Tomorrow at] LT',
    nextWeek : 'dddd [at] LT',
    lastDay : '[Yesterday at] LT',
    lastWeek : '[Last] dddd [at] LT',
    sameElse : 'L'
};

function calendar (key, mom, now) {
    var output = this._calendar[key] || this._calendar['sameElse'];
    return isFunction(output) ? output.call(mom, now) : output;
}

var defaultLongDateFormat = {
    LTS  : 'h:mm:ss A',
    LT   : 'h:mm A',
    L    : 'MM/DD/YYYY',
    LL   : 'MMMM D, YYYY',
    LLL  : 'MMMM D, YYYY h:mm A',
    LLLL : 'dddd, MMMM D, YYYY h:mm A'
};

function longDateFormat (key) {
    var format = this._longDateFormat[key],
        formatUpper = this._longDateFormat[key.toUpperCase()];

    if (format || !formatUpper) {
        return format;
    }

    this._longDateFormat[key] = formatUpper.replace(/MMMM|MM|DD|dddd/g, function (val) {
        return val.slice(1);
    });

    return this._longDateFormat[key];
}

var defaultInvalidDate = 'Invalid date';

function invalidDate () {
    return this._invalidDate;
}

var defaultOrdinal = '%d';
var defaultDayOfMonthOrdinalParse = /\d{1,2}/;

function ordinal (number) {
    return this._ordinal.replace('%d', number);
}

var defaultRelativeTime = {
    future : 'in %s',
    past   : '%s ago',
    s  : 'a few seconds',
    ss : '%d seconds',
    m  : 'a minute',
    mm : '%d minutes',
    h  : 'an hour',
    hh : '%d hours',
    d  : 'a day',
    dd : '%d days',
    M  : 'a month',
    MM : '%d months',
    y  : 'a year',
    yy : '%d years'
};

function relativeTime (number, withoutSuffix, string, isFuture) {
    var output = this._relativeTime[string];
    return (isFunction(output)) ?
        output(number, withoutSuffix, string, isFuture) :
        output.replace(/%d/i, number);
}

function pastFuture (diff, output) {
    var format = this._relativeTime[diff > 0 ? 'future' : 'past'];
    return isFunction(format) ? format(output) : format.replace(/%s/i, output);
}

var aliases = {};

function addUnitAlias (unit, shorthand) {
    var lowerCase = unit.toLowerCase();
    aliases[lowerCase] = aliases[lowerCase + 's'] = aliases[shorthand] = unit;
}

function normalizeUnits(units) {
    return typeof units === 'string' ? aliases[units] || aliases[units.toLowerCase()] : undefined;
}

function normalizeObjectUnits(inputObject) {
    var normalizedInput = {},
        normalizedProp,
        prop;

    for (prop in inputObject) {
        if (hasOwnProp(inputObject, prop)) {
            normalizedProp = normalizeUnits(prop);
            if (normalizedProp) {
                normalizedInput[normalizedProp] = inputObject[prop];
            }
        }
    }

    return normalizedInput;
}

var priorities = {};

function addUnitPriority(unit, priority) {
    priorities[unit] = priority;
}

function getPrioritizedUnits(unitsObj) {
    var units = [];
    for (var u in unitsObj) {
        units.push({unit: u, priority: priorities[u]});
    }
    units.sort(function (a, b) {
        return a.priority - b.priority;
    });
    return units;
}

function zeroFill(number, targetLength, forceSign) {
    var absNumber = '' + Math.abs(number),
        zerosToFill = targetLength - absNumber.length,
        sign = number >= 0;
    return (sign ? (forceSign ? '+' : '') : '-') +
        Math.pow(10, Math.max(0, zerosToFill)).toString().substr(1) + absNumber;
}

var formattingTokens = /(\[[^\[]*\])|(\\)?([Hh]mm(ss)?|Mo|MM?M?M?|Do|DDDo|DD?D?D?|ddd?d?|do?|w[o|w]?|W[o|W]?|Qo?|YYYYYY|YYYYY|YYYY|YY|gg(ggg?)?|GG(GGG?)?|e|E|a|A|hh?|HH?|kk?|mm?|ss?|S{1,9}|x|X|zz?|ZZ?|.)/g;

var localFormattingTokens = /(\[[^\[]*\])|(\\)?(LTS|LT|LL?L?L?|l{1,4})/g;

var formatFunctions = {};

var formatTokenFunctions = {};

// token:    'M'
// padded:   ['MM', 2]
// ordinal:  'Mo'
// callback: function () { this.month() + 1 }
function addFormatToken (token, padded, ordinal, callback) {
    var func = callback;
    if (typeof callback === 'string') {
        func = function () {
            return this[callback]();
        };
    }
    if (token) {
        formatTokenFunctions[token] = func;
    }
    if (padded) {
        formatTokenFunctions[padded[0]] = function () {
            return zeroFill(func.apply(this, arguments), padded[1], padded[2]);
        };
    }
    if (ordinal) {
        formatTokenFunctions[ordinal] = function () {
            return this.localeData().ordinal(func.apply(this, arguments), token);
        };
    }
}

function removeFormattingTokens(input) {
    if (input.match(/\[[\s\S]/)) {
        return input.replace(/^\[|\]$/g, '');
    }
    return input.replace(/\\/g, '');
}

function makeFormatFunction(format) {
    var array = format.match(formattingTokens), i, length;

    for (i = 0, length = array.length; i < length; i++) {
        if (formatTokenFunctions[array[i]]) {
            array[i] = formatTokenFunctions[array[i]];
        } else {
            array[i] = removeFormattingTokens(array[i]);
        }
    }

    return function (mom) {
        var output = '', i;
        for (i = 0; i < length; i++) {
            output += isFunction(array[i]) ? array[i].call(mom, format) : array[i];
        }
        return output;
    };
}

// format date using native date object
function formatMoment(m, format) {
    if (!m.isValid()) {
        return m.localeData().invalidDate();
    }

    format = expandFormat(format, m.localeData());
    formatFunctions[format] = formatFunctions[format] || makeFormatFunction(format);

    return formatFunctions[format](m);
}

function expandFormat(format, locale) {
    var i = 5;

    function replaceLongDateFormatTokens(input) {
        return locale.longDateFormat(input) || input;
    }

    localFormattingTokens.lastIndex = 0;
    while (i >= 0 && localFormattingTokens.test(format)) {
        format = format.replace(localFormattingTokens, replaceLongDateFormatTokens);
        localFormattingTokens.lastIndex = 0;
        i -= 1;
    }

    return format;
}

var match1         = /\d/;            //       0 - 9
var match2         = /\d\d/;          //      00 - 99
var match3         = /\d{3}/;         //     000 - 999
var match4         = /\d{4}/;         //    0000 - 9999
var match6         = /[+-]?\d{6}/;    // -999999 - 999999
var match1to2      = /\d\d?/;         //       0 - 99
var match3to4      = /\d\d\d\d?/;     //     999 - 9999
var match5to6      = /\d\d\d\d\d\d?/; //   99999 - 999999
var match1to3      = /\d{1,3}/;       //       0 - 999
var match1to4      = /\d{1,4}/;       //       0 - 9999
var match1to6      = /[+-]?\d{1,6}/;  // -999999 - 999999

var matchUnsigned  = /\d+/;           //       0 - inf
var matchSigned    = /[+-]?\d+/;      //    -inf - inf

var matchOffset    = /Z|[+-]\d\d:?\d\d/gi; // +00:00 -00:00 +0000 -0000 or Z
var matchShortOffset = /Z|[+-]\d\d(?::?\d\d)?/gi; // +00 -00 +00:00 -00:00 +0000 -0000 or Z

var matchTimestamp = /[+-]?\d+(\.\d{1,3})?/; // 123456789 123456789.123

// any word (or two) characters or numbers including two/three word month in arabic.
// includes scottish gaelic two word and hyphenated months
var matchWord = /[0-9]{0,256}['a-z\u00A0-\u05FF\u0700-\uD7FF\uF900-\uFDCF\uFDF0-\uFF07\uFF10-\uFFEF]{1,256}|[\u0600-\u06FF\/]{1,256}(\s*?[\u0600-\u06FF]{1,256}){1,2}/i;


var regexes = {};

function addRegexToken (token, regex, strictRegex) {
    regexes[token] = isFunction(regex) ? regex : function (isStrict, localeData) {
        return (isStrict && strictRegex) ? strictRegex : regex;
    };
}

function getParseRegexForToken (token, config) {
    if (!hasOwnProp(regexes, token)) {
        return new RegExp(unescapeFormat(token));
    }

    return regexes[token](config._strict, config._locale);
}

// Code from http://stackoverflow.com/questions/3561493/is-there-a-regexp-escape-function-in-javascript
function unescapeFormat(s) {
    return regexEscape(s.replace('\\', '').replace(/\\(\[)|\\(\])|\[([^\]\[]*)\]|\\(.)/g, function (matched, p1, p2, p3, p4) {
        return p1 || p2 || p3 || p4;
    }));
}

function regexEscape(s) {
    return s.replace(/[-\/\\^$*+?.()|[\]{}]/g, '\\$&');
}

var tokens = {};

function addParseToken (token, callback) {
    var i, func = callback;
    if (typeof token === 'string') {
        token = [token];
    }
    if (isNumber(callback)) {
        func = function (input, array) {
            array[callback] = toInt(input);
        };
    }
    for (i = 0; i < token.length; i++) {
        tokens[token[i]] = func;
    }
}

function addWeekParseToken (token, callback) {
    addParseToken(token, function (input, array, config, token) {
        config._w = config._w || {};
        callback(input, config._w, config, token);
    });
}

function addTimeToArrayFromToken(token, input, config) {
    if (input != null && hasOwnProp(tokens, token)) {
        tokens[token](input, config._a, config, token);
    }
}

var YEAR = 0;
var MONTH = 1;
var DATE = 2;
var HOUR = 3;
var MINUTE = 4;
var SECOND = 5;
var MILLISECOND = 6;
var WEEK = 7;
var WEEKDAY = 8;

// FORMATTING

addFormatToken('Y', 0, 0, function () {
    var y = this.year();
    return y <= 9999 ? '' + y : '+' + y;
});

addFormatToken(0, ['YY', 2], 0, function () {
    return this.year() % 100;
});

addFormatToken(0, ['YYYY',   4],       0, 'year');
addFormatToken(0, ['YYYYY',  5],       0, 'year');
addFormatToken(0, ['YYYYYY', 6, true], 0, 'year');

// ALIASES

addUnitAlias('year', 'y');

// PRIORITIES

addUnitPriority('year', 1);

// PARSING

addRegexToken('Y',      matchSigned);
addRegexToken('YY',     match1to2, match2);
addRegexToken('YYYY',   match1to4, match4);
addRegexToken('YYYYY',  match1to6, match6);
addRegexToken('YYYYYY', match1to6, match6);

addParseToken(['YYYYY', 'YYYYYY'], YEAR);
addParseToken('YYYY', function (input, array) {
    array[YEAR] = input.length === 2 ? hooks.parseTwoDigitYear(input) : toInt(input);
});
addParseToken('YY', function (input, array) {
    array[YEAR] = hooks.parseTwoDigitYear(input);
});
addParseToken('Y', function (input, array) {
    array[YEAR] = parseInt(input, 10);
});

// HELPERS

function daysInYear(year) {
    return isLeapYear(year) ? 366 : 365;
}

function isLeapYear(year) {
    return (year % 4 === 0 && year % 100 !== 0) || year % 400 === 0;
}

// HOOKS

hooks.parseTwoDigitYear = function (input) {
    return toInt(input) + (toInt(input) > 68 ? 1900 : 2000);
};

// MOMENTS

var getSetYear = makeGetSet('FullYear', true);

function getIsLeapYear () {
    return isLeapYear(this.year());
}

function makeGetSet (unit, keepTime) {
    return function (value) {
        if (value != null) {
            set$1(this, unit, value);
            hooks.updateOffset(this, keepTime);
            return this;
        } else {
            return get(this, unit);
        }
    };
}

function get (mom, unit) {
    return mom.isValid() ?
        mom._d['get' + (mom._isUTC ? 'UTC' : '') + unit]() : NaN;
}

function set$1 (mom, unit, value) {
    if (mom.isValid() && !isNaN(value)) {
        if (unit === 'FullYear' && isLeapYear(mom.year()) && mom.month() === 1 && mom.date() === 29) {
            mom._d['set' + (mom._isUTC ? 'UTC' : '') + unit](value, mom.month(), daysInMonth(value, mom.month()));
        }
        else {
            mom._d['set' + (mom._isUTC ? 'UTC' : '') + unit](value);
        }
    }
}

// MOMENTS

function stringGet (units) {
    units = normalizeUnits(units);
    if (isFunction(this[units])) {
        return this[units]();
    }
    return this;
}


function stringSet (units, value) {
    if (typeof units === 'object') {
        units = normalizeObjectUnits(units);
        var prioritized = getPrioritizedUnits(units);
        for (var i = 0; i < prioritized.length; i++) {
            this[prioritized[i].unit](units[prioritized[i].unit]);
        }
    } else {
        units = normalizeUnits(units);
        if (isFunction(this[units])) {
            return this[units](value);
        }
    }
    return this;
}

function mod(n, x) {
    return ((n % x) + x) % x;
}

var indexOf;

if (Array.prototype.indexOf) {
    indexOf = Array.prototype.indexOf;
} else {
    indexOf = function (o) {
        // I know
        var i;
        for (i = 0; i < this.length; ++i) {
            if (this[i] === o) {
                return i;
            }
        }
        return -1;
    };
}

function daysInMonth(year, month) {
    if (isNaN(year) || isNaN(month)) {
        return NaN;
    }
    var modMonth = mod(month, 12);
    year += (month - modMonth) / 12;
    return modMonth === 1 ? (isLeapYear(year) ? 29 : 28) : (31 - modMonth % 7 % 2);
}

// FORMATTING

addFormatToken('M', ['MM', 2], 'Mo', function () {
    return this.month() + 1;
});

addFormatToken('MMM', 0, 0, function (format) {
    return this.localeData().monthsShort(this, format);
});

addFormatToken('MMMM', 0, 0, function (format) {
    return this.localeData().months(this, format);
});

// ALIASES

addUnitAlias('month', 'M');

// PRIORITY

addUnitPriority('month', 8);

// PARSING

addRegexToken('M',    match1to2);
addRegexToken('MM',   match1to2, match2);
addRegexToken('MMM',  function (isStrict, locale) {
    return locale.monthsShortRegex(isStrict);
});
addRegexToken('MMMM', function (isStrict, locale) {
    return locale.monthsRegex(isStrict);
});

addParseToken(['M', 'MM'], function (input, array) {
    array[MONTH] = toInt(input) - 1;
});

addParseToken(['MMM', 'MMMM'], function (input, array, config, token) {
    var month = config._locale.monthsParse(input, token, config._strict);
    // if we didn't find a month name, mark the date as invalid.
    if (month != null) {
        array[MONTH] = month;
    } else {
        getParsingFlags(config).invalidMonth = input;
    }
});

// LOCALES

var MONTHS_IN_FORMAT = /D[oD]?(\[[^\[\]]*\]|\s)+MMMM?/;
var defaultLocaleMonths = 'January_February_March_April_May_June_July_August_September_October_November_December'.split('_');
function localeMonths (m, format) {
    if (!m) {
        return isArray(this._months) ? this._months :
            this._months['standalone'];
    }
    return isArray(this._months) ? this._months[m.month()] :
        this._months[(this._months.isFormat || MONTHS_IN_FORMAT).test(format) ? 'format' : 'standalone'][m.month()];
}

var defaultLocaleMonthsShort = 'Jan_Feb_Mar_Apr_May_Jun_Jul_Aug_Sep_Oct_Nov_Dec'.split('_');
function localeMonthsShort (m, format) {
    if (!m) {
        return isArray(this._monthsShort) ? this._monthsShort :
            this._monthsShort['standalone'];
    }
    return isArray(this._monthsShort) ? this._monthsShort[m.month()] :
        this._monthsShort[MONTHS_IN_FORMAT.test(format) ? 'format' : 'standalone'][m.month()];
}

function handleStrictParse(monthName, format, strict) {
    var i, ii, mom, llc = monthName.toLocaleLowerCase();
    if (!this._monthsParse) {
        // this is not used
        this._monthsParse = [];
        this._longMonthsParse = [];
        this._shortMonthsParse = [];
        for (i = 0; i < 12; ++i) {
            mom = createUTC([2000, i]);
            this._shortMonthsParse[i] = this.monthsShort(mom, '').toLocaleLowerCase();
            this._longMonthsParse[i] = this.months(mom, '').toLocaleLowerCase();
        }
    }

    if (strict) {
        if (format === 'MMM') {
            ii = indexOf.call(this._shortMonthsParse, llc);
            return ii !== -1 ? ii : null;
        } else {
            ii = indexOf.call(this._longMonthsParse, llc);
            return ii !== -1 ? ii : null;
        }
    } else {
        if (format === 'MMM') {
            ii = indexOf.call(this._shortMonthsParse, llc);
            if (ii !== -1) {
                return ii;
            }
            ii = indexOf.call(this._longMonthsParse, llc);
            return ii !== -1 ? ii : null;
        } else {
            ii = indexOf.call(this._longMonthsParse, llc);
            if (ii !== -1) {
                return ii;
            }
            ii = indexOf.call(this._shortMonthsParse, llc);
            return ii !== -1 ? ii : null;
        }
    }
}

function localeMonthsParse (monthName, format, strict) {
    var i, mom, regex;

    if (this._monthsParseExact) {
        return handleStrictParse.call(this, monthName, format, strict);
    }

    if (!this._monthsParse) {
        this._monthsParse = [];
        this._longMonthsParse = [];
        this._shortMonthsParse = [];
    }

    // TODO: add sorting
    // Sorting makes sure if one month (or abbr) is a prefix of another
    // see sorting in computeMonthsParse
    for (i = 0; i < 12; i++) {
        // make the regex if we don't have it already
        mom = createUTC([2000, i]);
        if (strict && !this._longMonthsParse[i]) {
            this._longMonthsParse[i] = new RegExp('^' + this.months(mom, '').replace('.', '') + '$', 'i');
            this._shortMonthsParse[i] = new RegExp('^' + this.monthsShort(mom, '').replace('.', '') + '$', 'i');
        }
        if (!strict && !this._monthsParse[i]) {
            regex = '^' + this.months(mom, '') + '|^' + this.monthsShort(mom, '');
            this._monthsParse[i] = new RegExp(regex.replace('.', ''), 'i');
        }
        // test the regex
        if (strict && format === 'MMMM' && this._longMonthsParse[i].test(monthName)) {
            return i;
        } else if (strict && format === 'MMM' && this._shortMonthsParse[i].test(monthName)) {
            return i;
        } else if (!strict && this._monthsParse[i].test(monthName)) {
            return i;
        }
    }
}

// MOMENTS

function setMonth (mom, value) {
    var dayOfMonth;

    if (!mom.isValid()) {
        // No op
        return mom;
    }

    if (typeof value === 'string') {
        if (/^\d+$/.test(value)) {
            value = toInt(value);
        } else {
            value = mom.localeData().monthsParse(value);
            // TODO: Another silent failure?
            if (!isNumber(value)) {
                return mom;
            }
        }
    }

    dayOfMonth = Math.min(mom.date(), daysInMonth(mom.year(), value));
    mom._d['set' + (mom._isUTC ? 'UTC' : '') + 'Month'](value, dayOfMonth);
    return mom;
}

function getSetMonth (value) {
    if (value != null) {
        setMonth(this, value);
        hooks.updateOffset(this, true);
        return this;
    } else {
        return get(this, 'Month');
    }
}

function getDaysInMonth () {
    return daysInMonth(this.year(), this.month());
}

var defaultMonthsShortRegex = matchWord;
function monthsShortRegex (isStrict) {
    if (this._monthsParseExact) {
        if (!hasOwnProp(this, '_monthsRegex')) {
            computeMonthsParse.call(this);
        }
        if (isStrict) {
            return this._monthsShortStrictRegex;
        } else {
            return this._monthsShortRegex;
        }
    } else {
        if (!hasOwnProp(this, '_monthsShortRegex')) {
            this._monthsShortRegex = defaultMonthsShortRegex;
        }
        return this._monthsShortStrictRegex && isStrict ?
            this._monthsShortStrictRegex : this._monthsShortRegex;
    }
}

var defaultMonthsRegex = matchWord;
function monthsRegex (isStrict) {
    if (this._monthsParseExact) {
        if (!hasOwnProp(this, '_monthsRegex')) {
            computeMonthsParse.call(this);
        }
        if (isStrict) {
            return this._monthsStrictRegex;
        } else {
            return this._monthsRegex;
        }
    } else {
        if (!hasOwnProp(this, '_monthsRegex')) {
            this._monthsRegex = defaultMonthsRegex;
        }
        return this._monthsStrictRegex && isStrict ?
            this._monthsStrictRegex : this._monthsRegex;
    }
}

function computeMonthsParse () {
    function cmpLenRev(a, b) {
        return b.length - a.length;
    }

    var shortPieces = [], longPieces = [], mixedPieces = [],
        i, mom;
    for (i = 0; i < 12; i++) {
        // make the regex if we don't have it already
        mom = createUTC([2000, i]);
        shortPieces.push(this.monthsShort(mom, ''));
        longPieces.push(this.months(mom, ''));
        mixedPieces.push(this.months(mom, ''));
        mixedPieces.push(this.monthsShort(mom, ''));
    }
    // Sorting makes sure if one month (or abbr) is a prefix of another it
    // will match the longer piece.
    shortPieces.sort(cmpLenRev);
    longPieces.sort(cmpLenRev);
    mixedPieces.sort(cmpLenRev);
    for (i = 0; i < 12; i++) {
        shortPieces[i] = regexEscape(shortPieces[i]);
        longPieces[i] = regexEscape(longPieces[i]);
    }
    for (i = 0; i < 24; i++) {
        mixedPieces[i] = regexEscape(mixedPieces[i]);
    }

    this._monthsRegex = new RegExp('^(' + mixedPieces.join('|') + ')', 'i');
    this._monthsShortRegex = this._monthsRegex;
    this._monthsStrictRegex = new RegExp('^(' + longPieces.join('|') + ')', 'i');
    this._monthsShortStrictRegex = new RegExp('^(' + shortPieces.join('|') + ')', 'i');
}

function createDate (y, m, d, h, M, s, ms) {
    // can't just apply() to create a date:
    // https://stackoverflow.com/q/181348
    var date = new Date(y, m, d, h, M, s, ms);

    // the date constructor remaps years 0-99 to 1900-1999
    if (y < 100 && y >= 0 && isFinite(date.getFullYear())) {
        date.setFullYear(y);
    }
    return date;
}

function createUTCDate (y) {
    var date = new Date(Date.UTC.apply(null, arguments));

    // the Date.UTC function remaps years 0-99 to 1900-1999
    if (y < 100 && y >= 0 && isFinite(date.getUTCFullYear())) {
        date.setUTCFullYear(y);
    }
    return date;
}

// start-of-first-week - start-of-year
function firstWeekOffset(year, dow, doy) {
    var // first-week day -- which january is always in the first week (4 for iso, 1 for other)
        fwd = 7 + dow - doy,
        // first-week day local weekday -- which local weekday is fwd
        fwdlw = (7 + createUTCDate(year, 0, fwd).getUTCDay() - dow) % 7;

    return -fwdlw + fwd - 1;
}

// https://en.wikipedia.org/wiki/ISO_week_date#Calculating_a_date_given_the_year.2C_week_number_and_weekday
function dayOfYearFromWeeks(year, week, weekday, dow, doy) {
    var localWeekday = (7 + weekday - dow) % 7,
        weekOffset = firstWeekOffset(year, dow, doy),
        dayOfYear = 1 + 7 * (week - 1) + localWeekday + weekOffset,
        resYear, resDayOfYear;

    if (dayOfYear <= 0) {
        resYear = year - 1;
        resDayOfYear = daysInYear(resYear) + dayOfYear;
    } else if (dayOfYear > daysInYear(year)) {
        resYear = year + 1;
        resDayOfYear = dayOfYear - daysInYear(year);
    } else {
        resYear = year;
        resDayOfYear = dayOfYear;
    }

    return {
        year: resYear,
        dayOfYear: resDayOfYear
    };
}

function weekOfYear(mom, dow, doy) {
    var weekOffset = firstWeekOffset(mom.year(), dow, doy),
        week = Math.floor((mom.dayOfYear() - weekOffset - 1) / 7) + 1,
        resWeek, resYear;

    if (week < 1) {
        resYear = mom.year() - 1;
        resWeek = week + weeksInYear(resYear, dow, doy);
    } else if (week > weeksInYear(mom.year(), dow, doy)) {
        resWeek = week - weeksInYear(mom.year(), dow, doy);
        resYear = mom.year() + 1;
    } else {
        resYear = mom.year();
        resWeek = week;
    }

    return {
        week: resWeek,
        year: resYear
    };
}

function weeksInYear(year, dow, doy) {
    var weekOffset = firstWeekOffset(year, dow, doy),
        weekOffsetNext = firstWeekOffset(year + 1, dow, doy);
    return (daysInYear(year) - weekOffset + weekOffsetNext) / 7;
}

// FORMATTING

addFormatToken('w', ['ww', 2], 'wo', 'week');
addFormatToken('W', ['WW', 2], 'Wo', 'isoWeek');

// ALIASES

addUnitAlias('week', 'w');
addUnitAlias('isoWeek', 'W');

// PRIORITIES

addUnitPriority('week', 5);
addUnitPriority('isoWeek', 5);

// PARSING

addRegexToken('w',  match1to2);
addRegexToken('ww', match1to2, match2);
addRegexToken('W',  match1to2);
addRegexToken('WW', match1to2, match2);

addWeekParseToken(['w', 'ww', 'W', 'WW'], function (input, week, config, token) {
    week[token.substr(0, 1)] = toInt(input);
});

// HELPERS

// LOCALES

function localeWeek (mom) {
    return weekOfYear(mom, this._week.dow, this._week.doy).week;
}

var defaultLocaleWeek = {
    dow : 0, // Sunday is the first day of the week.
    doy : 6  // The week that contains Jan 1st is the first week of the year.
};

function localeFirstDayOfWeek () {
    return this._week.dow;
}

function localeFirstDayOfYear () {
    return this._week.doy;
}

// MOMENTS

function getSetWeek (input) {
    var week = this.localeData().week(this);
    return input == null ? week : this.add((input - week) * 7, 'd');
}

function getSetISOWeek (input) {
    var week = weekOfYear(this, 1, 4).week;
    return input == null ? week : this.add((input - week) * 7, 'd');
}

// FORMATTING

addFormatToken('d', 0, 'do', 'day');

addFormatToken('dd', 0, 0, function (format) {
    return this.localeData().weekdaysMin(this, format);
});

addFormatToken('ddd', 0, 0, function (format) {
    return this.localeData().weekdaysShort(this, format);
});

addFormatToken('dddd', 0, 0, function (format) {
    return this.localeData().weekdays(this, format);
});

addFormatToken('e', 0, 0, 'weekday');
addFormatToken('E', 0, 0, 'isoWeekday');

// ALIASES

addUnitAlias('day', 'd');
addUnitAlias('weekday', 'e');
addUnitAlias('isoWeekday', 'E');

// PRIORITY
addUnitPriority('day', 11);
addUnitPriority('weekday', 11);
addUnitPriority('isoWeekday', 11);

// PARSING

addRegexToken('d',    match1to2);
addRegexToken('e',    match1to2);
addRegexToken('E',    match1to2);
addRegexToken('dd',   function (isStrict, locale) {
    return locale.weekdaysMinRegex(isStrict);
});
addRegexToken('ddd',   function (isStrict, locale) {
    return locale.weekdaysShortRegex(isStrict);
});
addRegexToken('dddd',   function (isStrict, locale) {
    return locale.weekdaysRegex(isStrict);
});

addWeekParseToken(['dd', 'ddd', 'dddd'], function (input, week, config, token) {
    var weekday = config._locale.weekdaysParse(input, token, config._strict);
    // if we didn't get a weekday name, mark the date as invalid
    if (weekday != null) {
        week.d = weekday;
    } else {
        getParsingFlags(config).invalidWeekday = input;
    }
});

addWeekParseToken(['d', 'e', 'E'], function (input, week, config, token) {
    week[token] = toInt(input);
});

// HELPERS

function parseWeekday(input, locale) {
    if (typeof input !== 'string') {
        return input;
    }

    if (!isNaN(input)) {
        return parseInt(input, 10);
    }

    input = locale.weekdaysParse(input);
    if (typeof input === 'number') {
        return input;
    }

    return null;
}

function parseIsoWeekday(input, locale) {
    if (typeof input === 'string') {
        return locale.weekdaysParse(input) % 7 || 7;
    }
    return isNaN(input) ? null : input;
}

// LOCALES

var defaultLocaleWeekdays = 'Sunday_Monday_Tuesday_Wednesday_Thursday_Friday_Saturday'.split('_');
function localeWeekdays (m, format) {
    if (!m) {
        return isArray(this._weekdays) ? this._weekdays :
            this._weekdays['standalone'];
    }
    return isArray(this._weekdays) ? this._weekdays[m.day()] :
        this._weekdays[this._weekdays.isFormat.test(format) ? 'format' : 'standalone'][m.day()];
}

var defaultLocaleWeekdaysShort = 'Sun_Mon_Tue_Wed_Thu_Fri_Sat'.split('_');
function localeWeekdaysShort (m) {
    return (m) ? this._weekdaysShort[m.day()] : this._weekdaysShort;
}

var defaultLocaleWeekdaysMin = 'Su_Mo_Tu_We_Th_Fr_Sa'.split('_');
function localeWeekdaysMin (m) {
    return (m) ? this._weekdaysMin[m.day()] : this._weekdaysMin;
}

function handleStrictParse$1(weekdayName, format, strict) {
    var i, ii, mom, llc = weekdayName.toLocaleLowerCase();
    if (!this._weekdaysParse) {
        this._weekdaysParse = [];
        this._shortWeekdaysParse = [];
        this._minWeekdaysParse = [];

        for (i = 0; i < 7; ++i) {
            mom = createUTC([2000, 1]).day(i);
            this._minWeekdaysParse[i] = this.weekdaysMin(mom, '').toLocaleLowerCase();
            this._shortWeekdaysParse[i] = this.weekdaysShort(mom, '').toLocaleLowerCase();
            this._weekdaysParse[i] = this.weekdays(mom, '').toLocaleLowerCase();
        }
    }

    if (strict) {
        if (format === 'dddd') {
            ii = indexOf.call(this._weekdaysParse, llc);
            return ii !== -1 ? ii : null;
        } else if (format === 'ddd') {
            ii = indexOf.call(this._shortWeekdaysParse, llc);
            return ii !== -1 ? ii : null;
        } else {
            ii = indexOf.call(this._minWeekdaysParse, llc);
            return ii !== -1 ? ii : null;
        }
    } else {
        if (format === 'dddd') {
            ii = indexOf.call(this._weekdaysParse, llc);
            if (ii !== -1) {
                return ii;
            }
            ii = indexOf.call(this._shortWeekdaysParse, llc);
            if (ii !== -1) {
                return ii;
            }
            ii = indexOf.call(this._minWeekdaysParse, llc);
            return ii !== -1 ? ii : null;
        } else if (format === 'ddd') {
            ii = indexOf.call(this._shortWeekdaysParse, llc);
            if (ii !== -1) {
                return ii;
            }
            ii = indexOf.call(this._weekdaysParse, llc);
            if (ii !== -1) {
                return ii;
            }
            ii = indexOf.call(this._minWeekdaysParse, llc);
            return ii !== -1 ? ii : null;
        } else {
            ii = indexOf.call(this._minWeekdaysParse, llc);
            if (ii !== -1) {
                return ii;
            }
            ii = indexOf.call(this._weekdaysParse, llc);
            if (ii !== -1) {
                return ii;
            }
            ii = indexOf.call(this._shortWeekdaysParse, llc);
            return ii !== -1 ? ii : null;
        }
    }
}

function localeWeekdaysParse (weekdayName, format, strict) {
    var i, mom, regex;

    if (this._weekdaysParseExact) {
        return handleStrictParse$1.call(this, weekdayName, format, strict);
    }

    if (!this._weekdaysParse) {
        this._weekdaysParse = [];
        this._minWeekdaysParse = [];
        this._shortWeekdaysParse = [];
        this._fullWeekdaysParse = [];
    }

    for (i = 0; i < 7; i++) {
        // make the regex if we don't have it already

        mom = createUTC([2000, 1]).day(i);
        if (strict && !this._fullWeekdaysParse[i]) {
            this._fullWeekdaysParse[i] = new RegExp('^' + this.weekdays(mom, '').replace('.', '\.?') + '$', 'i');
            this._shortWeekdaysParse[i] = new RegExp('^' + this.weekdaysShort(mom, '').replace('.', '\.?') + '$', 'i');
            this._minWeekdaysParse[i] = new RegExp('^' + this.weekdaysMin(mom, '').replace('.', '\.?') + '$', 'i');
        }
        if (!this._weekdaysParse[i]) {
            regex = '^' + this.weekdays(mom, '') + '|^' + this.weekdaysShort(mom, '') + '|^' + this.weekdaysMin(mom, '');
            this._weekdaysParse[i] = new RegExp(regex.replace('.', ''), 'i');
        }
        // test the regex
        if (strict && format === 'dddd' && this._fullWeekdaysParse[i].test(weekdayName)) {
            return i;
        } else if (strict && format === 'ddd' && this._shortWeekdaysParse[i].test(weekdayName)) {
            return i;
        } else if (strict && format === 'dd' && this._minWeekdaysParse[i].test(weekdayName)) {
            return i;
        } else if (!strict && this._weekdaysParse[i].test(weekdayName)) {
            return i;
        }
    }
}

// MOMENTS

function getSetDayOfWeek (input) {
    if (!this.isValid()) {
        return input != null ? this : NaN;
    }
    var day = this._isUTC ? this._d.getUTCDay() : this._d.getDay();
    if (input != null) {
        input = parseWeekday(input, this.localeData());
        return this.add(input - day, 'd');
    } else {
        return day;
    }
}

function getSetLocaleDayOfWeek (input) {
    if (!this.isValid()) {
        return input != null ? this : NaN;
    }
    var weekday = (this.day() + 7 - this.localeData()._week.dow) % 7;
    return input == null ? weekday : this.add(input - weekday, 'd');
}

function getSetISODayOfWeek (input) {
    if (!this.isValid()) {
        return input != null ? this : NaN;
    }

    // behaves the same as moment#day except
    // as a getter, returns 7 instead of 0 (1-7 range instead of 0-6)
    // as a setter, sunday should belong to the previous week.

    if (input != null) {
        var weekday = parseIsoWeekday(input, this.localeData());
        return this.day(this.day() % 7 ? weekday : weekday - 7);
    } else {
        return this.day() || 7;
    }
}

var defaultWeekdaysRegex = matchWord;
function weekdaysRegex (isStrict) {
    if (this._weekdaysParseExact) {
        if (!hasOwnProp(this, '_weekdaysRegex')) {
            computeWeekdaysParse.call(this);
        }
        if (isStrict) {
            return this._weekdaysStrictRegex;
        } else {
            return this._weekdaysRegex;
        }
    } else {
        if (!hasOwnProp(this, '_weekdaysRegex')) {
            this._weekdaysRegex = defaultWeekdaysRegex;
        }
        return this._weekdaysStrictRegex && isStrict ?
            this._weekdaysStrictRegex : this._weekdaysRegex;
    }
}

var defaultWeekdaysShortRegex = matchWord;
function weekdaysShortRegex (isStrict) {
    if (this._weekdaysParseExact) {
        if (!hasOwnProp(this, '_weekdaysRegex')) {
            computeWeekdaysParse.call(this);
        }
        if (isStrict) {
            return this._weekdaysShortStrictRegex;
        } else {
            return this._weekdaysShortRegex;
        }
    } else {
        if (!hasOwnProp(this, '_weekdaysShortRegex')) {
            this._weekdaysShortRegex = defaultWeekdaysShortRegex;
        }
        return this._weekdaysShortStrictRegex && isStrict ?
            this._weekdaysShortStrictRegex : this._weekdaysShortRegex;
    }
}

var defaultWeekdaysMinRegex = matchWord;
function weekdaysMinRegex (isStrict) {
    if (this._weekdaysParseExact) {
        if (!hasOwnProp(this, '_weekdaysRegex')) {
            computeWeekdaysParse.call(this);
        }
        if (isStrict) {
            return this._weekdaysMinStrictRegex;
        } else {
            return this._weekdaysMinRegex;
        }
    } else {
        if (!hasOwnProp(this, '_weekdaysMinRegex')) {
            this._weekdaysMinRegex = defaultWeekdaysMinRegex;
        }
        return this._weekdaysMinStrictRegex && isStrict ?
            this._weekdaysMinStrictRegex : this._weekdaysMinRegex;
    }
}


function computeWeekdaysParse () {
    function cmpLenRev(a, b) {
        return b.length - a.length;
    }

    var minPieces = [], shortPieces = [], longPieces = [], mixedPieces = [],
        i, mom, minp, shortp, longp;
    for (i = 0; i < 7; i++) {
        // make the regex if we don't have it already
        mom = createUTC([2000, 1]).day(i);
        minp = this.weekdaysMin(mom, '');
        shortp = this.weekdaysShort(mom, '');
        longp = this.weekdays(mom, '');
        minPieces.push(minp);
        shortPieces.push(shortp);
        longPieces.push(longp);
        mixedPieces.push(minp);
        mixedPieces.push(shortp);
        mixedPieces.push(longp);
    }
    // Sorting makes sure if one weekday (or abbr) is a prefix of another it
    // will match the longer piece.
    minPieces.sort(cmpLenRev);
    shortPieces.sort(cmpLenRev);
    longPieces.sort(cmpLenRev);
    mixedPieces.sort(cmpLenRev);
    for (i = 0; i < 7; i++) {
        shortPieces[i] = regexEscape(shortPieces[i]);
        longPieces[i] = regexEscape(longPieces[i]);
        mixedPieces[i] = regexEscape(mixedPieces[i]);
    }

    this._weekdaysRegex = new RegExp('^(' + mixedPieces.join('|') + ')', 'i');
    this._weekdaysShortRegex = this._weekdaysRegex;
    this._weekdaysMinRegex = this._weekdaysRegex;

    this._weekdaysStrictRegex = new RegExp('^(' + longPieces.join('|') + ')', 'i');
    this._weekdaysShortStrictRegex = new RegExp('^(' + shortPieces.join('|') + ')', 'i');
    this._weekdaysMinStrictRegex = new RegExp('^(' + minPieces.join('|') + ')', 'i');
}

// FORMATTING

function hFormat() {
    return this.hours() % 12 || 12;
}

function kFormat() {
    return this.hours() || 24;
}

addFormatToken('H', ['HH', 2], 0, 'hour');
addFormatToken('h', ['hh', 2], 0, hFormat);
addFormatToken('k', ['kk', 2], 0, kFormat);

addFormatToken('hmm', 0, 0, function () {
    return '' + hFormat.apply(this) + zeroFill(this.minutes(), 2);
});

addFormatToken('hmmss', 0, 0, function () {
    return '' + hFormat.apply(this) + zeroFill(this.minutes(), 2) +
        zeroFill(this.seconds(), 2);
});

addFormatToken('Hmm', 0, 0, function () {
    return '' + this.hours() + zeroFill(this.minutes(), 2);
});

addFormatToken('Hmmss', 0, 0, function () {
    return '' + this.hours() + zeroFill(this.minutes(), 2) +
        zeroFill(this.seconds(), 2);
});

function meridiem (token, lowercase) {
    addFormatToken(token, 0, 0, function () {
        return this.localeData().meridiem(this.hours(), this.minutes(), lowercase);
    });
}

meridiem('a', true);
meridiem('A', false);

// ALIASES

addUnitAlias('hour', 'h');

// PRIORITY
addUnitPriority('hour', 13);

// PARSING

function matchMeridiem (isStrict, locale) {
    return locale._meridiemParse;
}

addRegexToken('a',  matchMeridiem);
addRegexToken('A',  matchMeridiem);
addRegexToken('H',  match1to2);
addRegexToken('h',  match1to2);
addRegexToken('k',  match1to2);
addRegexToken('HH', match1to2, match2);
addRegexToken('hh', match1to2, match2);
addRegexToken('kk', match1to2, match2);

addRegexToken('hmm', match3to4);
addRegexToken('hmmss', match5to6);
addRegexToken('Hmm', match3to4);
addRegexToken('Hmmss', match5to6);

addParseToken(['H', 'HH'], HOUR);
addParseToken(['k', 'kk'], function (input, array, config) {
    var kInput = toInt(input);
    array[HOUR] = kInput === 24 ? 0 : kInput;
});
addParseToken(['a', 'A'], function (input, array, config) {
    config._isPm = config._locale.isPM(input);
    config._meridiem = input;
});
addParseToken(['h', 'hh'], function (input, array, config) {
    array[HOUR] = toInt(input);
    getParsingFlags(config).bigHour = true;
});
addParseToken('hmm', function (input, array, config) {
    var pos = input.length - 2;
    array[HOUR] = toInt(input.substr(0, pos));
    array[MINUTE] = toInt(input.substr(pos));
    getParsingFlags(config).bigHour = true;
});
addParseToken('hmmss', function (input, array, config) {
    var pos1 = input.length - 4;
    var pos2 = input.length - 2;
    array[HOUR] = toInt(input.substr(0, pos1));
    array[MINUTE] = toInt(input.substr(pos1, 2));
    array[SECOND] = toInt(input.substr(pos2));
    getParsingFlags(config).bigHour = true;
});
addParseToken('Hmm', function (input, array, config) {
    var pos = input.length - 2;
    array[HOUR] = toInt(input.substr(0, pos));
    array[MINUTE] = toInt(input.substr(pos));
});
addParseToken('Hmmss', function (input, array, config) {
    var pos1 = input.length - 4;
    var pos2 = input.length - 2;
    array[HOUR] = toInt(input.substr(0, pos1));
    array[MINUTE] = toInt(input.substr(pos1, 2));
    array[SECOND] = toInt(input.substr(pos2));
});

// LOCALES

function localeIsPM (input) {
    // IE8 Quirks Mode & IE7 Standards Mode do not allow accessing strings like arrays
    // Using charAt should be more compatible.
    return ((input + '').toLowerCase().charAt(0) === 'p');
}

var defaultLocaleMeridiemParse = /[ap]\.?m?\.?/i;
function localeMeridiem (hours, minutes, isLower) {
    if (hours > 11) {
        return isLower ? 'pm' : 'PM';
    } else {
        return isLower ? 'am' : 'AM';
    }
}


// MOMENTS

// Setting the hour should keep the time, because the user explicitly
// specified which hour he wants. So trying to maintain the same hour (in
// a new timezone) makes sense. Adding/subtracting hours does not follow
// this rule.
var getSetHour = makeGetSet('Hours', true);

// months
// week
// weekdays
// meridiem
var baseConfig = {
    calendar: defaultCalendar,
    longDateFormat: defaultLongDateFormat,
    invalidDate: defaultInvalidDate,
    ordinal: defaultOrdinal,
    dayOfMonthOrdinalParse: defaultDayOfMonthOrdinalParse,
    relativeTime: defaultRelativeTime,

    months: defaultLocaleMonths,
    monthsShort: defaultLocaleMonthsShort,

    week: defaultLocaleWeek,

    weekdays: defaultLocaleWeekdays,
    weekdaysMin: defaultLocaleWeekdaysMin,
    weekdaysShort: defaultLocaleWeekdaysShort,

    meridiemParse: defaultLocaleMeridiemParse
};

// internal storage for locale config files
var locales = {};
var localeFamilies = {};
var globalLocale;

function normalizeLocale(key) {
    return key ? key.toLowerCase().replace('_', '-') : key;
}

// pick the locale from the array
// try ['en-au', 'en-gb'] as 'en-au', 'en-gb', 'en', as in move through the list trying each
// substring from most specific to least, but move to the next array item if it's a more specific variant than the current root
function chooseLocale(names) {
    var i = 0, j, next, locale, split;

    while (i < names.length) {
        split = normalizeLocale(names[i]).split('-');
        j = split.length;
        next = normalizeLocale(names[i + 1]);
        next = next ? next.split('-') : null;
        while (j > 0) {
            locale = loadLocale(split.slice(0, j).join('-'));
            if (locale) {
                return locale;
            }
            if (next && next.length >= j && compareArrays(split, next, true) >= j - 1) {
                //the next array item is better than a shallower substring of this one
                break;
            }
            j--;
        }
        i++;
    }
    return null;
}

function loadLocale(name) {
    var oldLocale = null;
    // TODO: Find a better way to register and load all the locales in Node
    if (!locales[name] && (typeof module !== 'undefined') &&
            module && module.exports) {
        try {
            oldLocale = globalLocale._abbr;
            var aliasedRequire = require;
            __webpack_require__(270)("./" + name);
            getSetGlobalLocale(oldLocale);
        } catch (e) {}
    }
    return locales[name];
}

// This function will load locale and then set the global locale.  If
// no arguments are passed in, it will simply return the current global
// locale key.
function getSetGlobalLocale (key, values) {
    var data;
    if (key) {
        if (isUndefined(values)) {
            data = getLocale(key);
        }
        else {
            data = defineLocale(key, values);
        }

        if (data) {
            // moment.duration._locale = moment._locale = data;
            globalLocale = data;
        }
    }

    return globalLocale._abbr;
}

function defineLocale (name, config) {
    if (config !== null) {
        var parentConfig = baseConfig;
        config.abbr = name;
        if (locales[name] != null) {
            deprecateSimple('defineLocaleOverride',
                    'use moment.updateLocale(localeName, config) to change ' +
                    'an existing locale. moment.defineLocale(localeName, ' +
                    'config) should only be used for creating a new locale ' +
                    'See http://momentjs.com/guides/#/warnings/define-locale/ for more info.');
            parentConfig = locales[name]._config;
        } else if (config.parentLocale != null) {
            if (locales[config.parentLocale] != null) {
                parentConfig = locales[config.parentLocale]._config;
            } else {
                if (!localeFamilies[config.parentLocale]) {
                    localeFamilies[config.parentLocale] = [];
                }
                localeFamilies[config.parentLocale].push({
                    name: name,
                    config: config
                });
                return null;
            }
        }
        locales[name] = new Locale(mergeConfigs(parentConfig, config));

        if (localeFamilies[name]) {
            localeFamilies[name].forEach(function (x) {
                defineLocale(x.name, x.config);
            });
        }

        // backwards compat for now: also set the locale
        // make sure we set the locale AFTER all child locales have been
        // created, so we won't end up with the child locale set.
        getSetGlobalLocale(name);


        return locales[name];
    } else {
        // useful for testing
        delete locales[name];
        return null;
    }
}

function updateLocale(name, config) {
    if (config != null) {
        var locale, tmpLocale, parentConfig = baseConfig;
        // MERGE
        tmpLocale = loadLocale(name);
        if (tmpLocale != null) {
            parentConfig = tmpLocale._config;
        }
        config = mergeConfigs(parentConfig, config);
        locale = new Locale(config);
        locale.parentLocale = locales[name];
        locales[name] = locale;

        // backwards compat for now: also set the locale
        getSetGlobalLocale(name);
    } else {
        // pass null for config to unupdate, useful for tests
        if (locales[name] != null) {
            if (locales[name].parentLocale != null) {
                locales[name] = locales[name].parentLocale;
            } else if (locales[name] != null) {
                delete locales[name];
            }
        }
    }
    return locales[name];
}

// returns locale data
function getLocale (key) {
    var locale;

    if (key && key._locale && key._locale._abbr) {
        key = key._locale._abbr;
    }

    if (!key) {
        return globalLocale;
    }

    if (!isArray(key)) {
        //short-circuit everything else
        locale = loadLocale(key);
        if (locale) {
            return locale;
        }
        key = [key];
    }

    return chooseLocale(key);
}

function listLocales() {
    return keys(locales);
}

function checkOverflow (m) {
    var overflow;
    var a = m._a;

    if (a && getParsingFlags(m).overflow === -2) {
        overflow =
            a[MONTH]       < 0 || a[MONTH]       > 11  ? MONTH :
            a[DATE]        < 1 || a[DATE]        > daysInMonth(a[YEAR], a[MONTH]) ? DATE :
            a[HOUR]        < 0 || a[HOUR]        > 24 || (a[HOUR] === 24 && (a[MINUTE] !== 0 || a[SECOND] !== 0 || a[MILLISECOND] !== 0)) ? HOUR :
            a[MINUTE]      < 0 || a[MINUTE]      > 59  ? MINUTE :
            a[SECOND]      < 0 || a[SECOND]      > 59  ? SECOND :
            a[MILLISECOND] < 0 || a[MILLISECOND] > 999 ? MILLISECOND :
            -1;

        if (getParsingFlags(m)._overflowDayOfYear && (overflow < YEAR || overflow > DATE)) {
            overflow = DATE;
        }
        if (getParsingFlags(m)._overflowWeeks && overflow === -1) {
            overflow = WEEK;
        }
        if (getParsingFlags(m)._overflowWeekday && overflow === -1) {
            overflow = WEEKDAY;
        }

        getParsingFlags(m).overflow = overflow;
    }

    return m;
}

// Pick the first defined of two or three arguments.
function defaults(a, b, c) {
    if (a != null) {
        return a;
    }
    if (b != null) {
        return b;
    }
    return c;
}

function currentDateArray(config) {
    // hooks is actually the exported moment object
    var nowValue = new Date(hooks.now());
    if (config._useUTC) {
        return [nowValue.getUTCFullYear(), nowValue.getUTCMonth(), nowValue.getUTCDate()];
    }
    return [nowValue.getFullYear(), nowValue.getMonth(), nowValue.getDate()];
}

// convert an array to a date.
// the array should mirror the parameters below
// note: all values past the year are optional and will default to the lowest possible value.
// [year, month, day , hour, minute, second, millisecond]
function configFromArray (config) {
    var i, date, input = [], currentDate, expectedWeekday, yearToUse;

    if (config._d) {
        return;
    }

    currentDate = currentDateArray(config);

    //compute day of the year from weeks and weekdays
    if (config._w && config._a[DATE] == null && config._a[MONTH] == null) {
        dayOfYearFromWeekInfo(config);
    }

    //if the day of the year is set, figure out what it is
    if (config._dayOfYear != null) {
        yearToUse = defaults(config._a[YEAR], currentDate[YEAR]);

        if (config._dayOfYear > daysInYear(yearToUse) || config._dayOfYear === 0) {
            getParsingFlags(config)._overflowDayOfYear = true;
        }

        date = createUTCDate(yearToUse, 0, config._dayOfYear);
        config._a[MONTH] = date.getUTCMonth();
        config._a[DATE] = date.getUTCDate();
    }

    // Default to current date.
    // * if no year, month, day of month are given, default to today
    // * if day of month is given, default month and year
    // * if month is given, default only year
    // * if year is given, don't default anything
    for (i = 0; i < 3 && config._a[i] == null; ++i) {
        config._a[i] = input[i] = currentDate[i];
    }

    // Zero out whatever was not defaulted, including time
    for (; i < 7; i++) {
        config._a[i] = input[i] = (config._a[i] == null) ? (i === 2 ? 1 : 0) : config._a[i];
    }

    // Check for 24:00:00.000
    if (config._a[HOUR] === 24 &&
            config._a[MINUTE] === 0 &&
            config._a[SECOND] === 0 &&
            config._a[MILLISECOND] === 0) {
        config._nextDay = true;
        config._a[HOUR] = 0;
    }

    config._d = (config._useUTC ? createUTCDate : createDate).apply(null, input);
    expectedWeekday = config._useUTC ? config._d.getUTCDay() : config._d.getDay();

    // Apply timezone offset from input. The actual utcOffset can be changed
    // with parseZone.
    if (config._tzm != null) {
        config._d.setUTCMinutes(config._d.getUTCMinutes() - config._tzm);
    }

    if (config._nextDay) {
        config._a[HOUR] = 24;
    }

    // check for mismatching day of week
    if (config._w && typeof config._w.d !== 'undefined' && config._w.d !== expectedWeekday) {
        getParsingFlags(config).weekdayMismatch = true;
    }
}

function dayOfYearFromWeekInfo(config) {
    var w, weekYear, week, weekday, dow, doy, temp, weekdayOverflow;

    w = config._w;
    if (w.GG != null || w.W != null || w.E != null) {
        dow = 1;
        doy = 4;

        // TODO: We need to take the current isoWeekYear, but that depends on
        // how we interpret now (local, utc, fixed offset). So create
        // a now version of current config (take local/utc/offset flags, and
        // create now).
        weekYear = defaults(w.GG, config._a[YEAR], weekOfYear(createLocal(), 1, 4).year);
        week = defaults(w.W, 1);
        weekday = defaults(w.E, 1);
        if (weekday < 1 || weekday > 7) {
            weekdayOverflow = true;
        }
    } else {
        dow = config._locale._week.dow;
        doy = config._locale._week.doy;

        var curWeek = weekOfYear(createLocal(), dow, doy);

        weekYear = defaults(w.gg, config._a[YEAR], curWeek.year);

        // Default to current week.
        week = defaults(w.w, curWeek.week);

        if (w.d != null) {
            // weekday -- low day numbers are considered next week
            weekday = w.d;
            if (weekday < 0 || weekday > 6) {
                weekdayOverflow = true;
            }
        } else if (w.e != null) {
            // local weekday -- counting starts from begining of week
            weekday = w.e + dow;
            if (w.e < 0 || w.e > 6) {
                weekdayOverflow = true;
            }
        } else {
            // default to begining of week
            weekday = dow;
        }
    }
    if (week < 1 || week > weeksInYear(weekYear, dow, doy)) {
        getParsingFlags(config)._overflowWeeks = true;
    } else if (weekdayOverflow != null) {
        getParsingFlags(config)._overflowWeekday = true;
    } else {
        temp = dayOfYearFromWeeks(weekYear, week, weekday, dow, doy);
        config._a[YEAR] = temp.year;
        config._dayOfYear = temp.dayOfYear;
    }
}

// iso 8601 regex
// 0000-00-00 0000-W00 or 0000-W00-0 + T + 00 or 00:00 or 00:00:00 or 00:00:00.000 + +00:00 or +0000 or +00)
var extendedIsoRegex = /^\s*((?:[+-]\d{6}|\d{4})-(?:\d\d-\d\d|W\d\d-\d|W\d\d|\d\d\d|\d\d))(?:(T| )(\d\d(?::\d\d(?::\d\d(?:[.,]\d+)?)?)?)([\+\-]\d\d(?::?\d\d)?|\s*Z)?)?$/;
var basicIsoRegex = /^\s*((?:[+-]\d{6}|\d{4})(?:\d\d\d\d|W\d\d\d|W\d\d|\d\d\d|\d\d))(?:(T| )(\d\d(?:\d\d(?:\d\d(?:[.,]\d+)?)?)?)([\+\-]\d\d(?::?\d\d)?|\s*Z)?)?$/;

var tzRegex = /Z|[+-]\d\d(?::?\d\d)?/;

var isoDates = [
    ['YYYYYY-MM-DD', /[+-]\d{6}-\d\d-\d\d/],
    ['YYYY-MM-DD', /\d{4}-\d\d-\d\d/],
    ['GGGG-[W]WW-E', /\d{4}-W\d\d-\d/],
    ['GGGG-[W]WW', /\d{4}-W\d\d/, false],
    ['YYYY-DDD', /\d{4}-\d{3}/],
    ['YYYY-MM', /\d{4}-\d\d/, false],
    ['YYYYYYMMDD', /[+-]\d{10}/],
    ['YYYYMMDD', /\d{8}/],
    // YYYYMM is NOT allowed by the standard
    ['GGGG[W]WWE', /\d{4}W\d{3}/],
    ['GGGG[W]WW', /\d{4}W\d{2}/, false],
    ['YYYYDDD', /\d{7}/]
];

// iso time formats and regexes
var isoTimes = [
    ['HH:mm:ss.SSSS', /\d\d:\d\d:\d\d\.\d+/],
    ['HH:mm:ss,SSSS', /\d\d:\d\d:\d\d,\d+/],
    ['HH:mm:ss', /\d\d:\d\d:\d\d/],
    ['HH:mm', /\d\d:\d\d/],
    ['HHmmss.SSSS', /\d\d\d\d\d\d\.\d+/],
    ['HHmmss,SSSS', /\d\d\d\d\d\d,\d+/],
    ['HHmmss', /\d\d\d\d\d\d/],
    ['HHmm', /\d\d\d\d/],
    ['HH', /\d\d/]
];

var aspNetJsonRegex = /^\/?Date\((\-?\d+)/i;

// date from iso format
function configFromISO(config) {
    var i, l,
        string = config._i,
        match = extendedIsoRegex.exec(string) || basicIsoRegex.exec(string),
        allowTime, dateFormat, timeFormat, tzFormat;

    if (match) {
        getParsingFlags(config).iso = true;

        for (i = 0, l = isoDates.length; i < l; i++) {
            if (isoDates[i][1].exec(match[1])) {
                dateFormat = isoDates[i][0];
                allowTime = isoDates[i][2] !== false;
                break;
            }
        }
        if (dateFormat == null) {
            config._isValid = false;
            return;
        }
        if (match[3]) {
            for (i = 0, l = isoTimes.length; i < l; i++) {
                if (isoTimes[i][1].exec(match[3])) {
                    // match[2] should be 'T' or space
                    timeFormat = (match[2] || ' ') + isoTimes[i][0];
                    break;
                }
            }
            if (timeFormat == null) {
                config._isValid = false;
                return;
            }
        }
        if (!allowTime && timeFormat != null) {
            config._isValid = false;
            return;
        }
        if (match[4]) {
            if (tzRegex.exec(match[4])) {
                tzFormat = 'Z';
            } else {
                config._isValid = false;
                return;
            }
        }
        config._f = dateFormat + (timeFormat || '') + (tzFormat || '');
        configFromStringAndFormat(config);
    } else {
        config._isValid = false;
    }
}

// RFC 2822 regex: For details see https://tools.ietf.org/html/rfc2822#section-3.3
var rfc2822 = /^(?:(Mon|Tue|Wed|Thu|Fri|Sat|Sun),?\s)?(\d{1,2})\s(Jan|Feb|Mar|Apr|May|Jun|Jul|Aug|Sep|Oct|Nov|Dec)\s(\d{2,4})\s(\d\d):(\d\d)(?::(\d\d))?\s(?:(UT|GMT|[ECMP][SD]T)|([Zz])|([+-]\d{4}))$/;

function extractFromRFC2822Strings(yearStr, monthStr, dayStr, hourStr, minuteStr, secondStr) {
    var result = [
        untruncateYear(yearStr),
        defaultLocaleMonthsShort.indexOf(monthStr),
        parseInt(dayStr, 10),
        parseInt(hourStr, 10),
        parseInt(minuteStr, 10)
    ];

    if (secondStr) {
        result.push(parseInt(secondStr, 10));
    }

    return result;
}

function untruncateYear(yearStr) {
    var year = parseInt(yearStr, 10);
    if (year <= 49) {
        return 2000 + year;
    } else if (year <= 999) {
        return 1900 + year;
    }
    return year;
}

function preprocessRFC2822(s) {
    // Remove comments and folding whitespace and replace multiple-spaces with a single space
    return s.replace(/\([^)]*\)|[\n\t]/g, ' ').replace(/(\s\s+)/g, ' ').trim();
}

function checkWeekday(weekdayStr, parsedInput, config) {
    if (weekdayStr) {
        // TODO: Replace the vanilla JS Date object with an indepentent day-of-week check.
        var weekdayProvided = defaultLocaleWeekdaysShort.indexOf(weekdayStr),
            weekdayActual = new Date(parsedInput[0], parsedInput[1], parsedInput[2]).getDay();
        if (weekdayProvided !== weekdayActual) {
            getParsingFlags(config).weekdayMismatch = true;
            config._isValid = false;
            return false;
        }
    }
    return true;
}

var obsOffsets = {
    UT: 0,
    GMT: 0,
    EDT: -4 * 60,
    EST: -5 * 60,
    CDT: -5 * 60,
    CST: -6 * 60,
    MDT: -6 * 60,
    MST: -7 * 60,
    PDT: -7 * 60,
    PST: -8 * 60
};

function calculateOffset(obsOffset, militaryOffset, numOffset) {
    if (obsOffset) {
        return obsOffsets[obsOffset];
    } else if (militaryOffset) {
        // the only allowed military tz is Z
        return 0;
    } else {
        var hm = parseInt(numOffset, 10);
        var m = hm % 100, h = (hm - m) / 100;
        return h * 60 + m;
    }
}

// date and time from ref 2822 format
function configFromRFC2822(config) {
    var match = rfc2822.exec(preprocessRFC2822(config._i));
    if (match) {
        var parsedArray = extractFromRFC2822Strings(match[4], match[3], match[2], match[5], match[6], match[7]);
        if (!checkWeekday(match[1], parsedArray, config)) {
            return;
        }

        config._a = parsedArray;
        config._tzm = calculateOffset(match[8], match[9], match[10]);

        config._d = createUTCDate.apply(null, config._a);
        config._d.setUTCMinutes(config._d.getUTCMinutes() - config._tzm);

        getParsingFlags(config).rfc2822 = true;
    } else {
        config._isValid = false;
    }
}

// date from iso format or fallback
function configFromString(config) {
    var matched = aspNetJsonRegex.exec(config._i);

    if (matched !== null) {
        config._d = new Date(+matched[1]);
        return;
    }

    configFromISO(config);
    if (config._isValid === false) {
        delete config._isValid;
    } else {
        return;
    }

    configFromRFC2822(config);
    if (config._isValid === false) {
        delete config._isValid;
    } else {
        return;
    }

    // Final attempt, use Input Fallback
    hooks.createFromInputFallback(config);
}

hooks.createFromInputFallback = deprecate(
    'value provided is not in a recognized RFC2822 or ISO format. moment construction falls back to js Date(), ' +
    'which is not reliable across all browsers and versions. Non RFC2822/ISO date formats are ' +
    'discouraged and will be removed in an upcoming major release. Please refer to ' +
    'http://momentjs.com/guides/#/warnings/js-date/ for more info.',
    function (config) {
        config._d = new Date(config._i + (config._useUTC ? ' UTC' : ''));
    }
);

// constant that refers to the ISO standard
hooks.ISO_8601 = function () {};

// constant that refers to the RFC 2822 form
hooks.RFC_2822 = function () {};

// date from string and format string
function configFromStringAndFormat(config) {
    // TODO: Move this to another part of the creation flow to prevent circular deps
    if (config._f === hooks.ISO_8601) {
        configFromISO(config);
        return;
    }
    if (config._f === hooks.RFC_2822) {
        configFromRFC2822(config);
        return;
    }
    config._a = [];
    getParsingFlags(config).empty = true;

    // This array is used to make a Date, either with `new Date` or `Date.UTC`
    var string = '' + config._i,
        i, parsedInput, tokens, token, skipped,
        stringLength = string.length,
        totalParsedInputLength = 0;

    tokens = expandFormat(config._f, config._locale).match(formattingTokens) || [];

    for (i = 0; i < tokens.length; i++) {
        token = tokens[i];
        parsedInput = (string.match(getParseRegexForToken(token, config)) || [])[0];
        // console.log('token', token, 'parsedInput', parsedInput,
        //         'regex', getParseRegexForToken(token, config));
        if (parsedInput) {
            skipped = string.substr(0, string.indexOf(parsedInput));
            if (skipped.length > 0) {
                getParsingFlags(config).unusedInput.push(skipped);
            }
            string = string.slice(string.indexOf(parsedInput) + parsedInput.length);
            totalParsedInputLength += parsedInput.length;
        }
        // don't parse if it's not a known token
        if (formatTokenFunctions[token]) {
            if (parsedInput) {
                getParsingFlags(config).empty = false;
            }
            else {
                getParsingFlags(config).unusedTokens.push(token);
            }
            addTimeToArrayFromToken(token, parsedInput, config);
        }
        else if (config._strict && !parsedInput) {
            getParsingFlags(config).unusedTokens.push(token);
        }
    }

    // add remaining unparsed input length to the string
    getParsingFlags(config).charsLeftOver = stringLength - totalParsedInputLength;
    if (string.length > 0) {
        getParsingFlags(config).unusedInput.push(string);
    }

    // clear _12h flag if hour is <= 12
    if (config._a[HOUR] <= 12 &&
        getParsingFlags(config).bigHour === true &&
        config._a[HOUR] > 0) {
        getParsingFlags(config).bigHour = undefined;
    }

    getParsingFlags(config).parsedDateParts = config._a.slice(0);
    getParsingFlags(config).meridiem = config._meridiem;
    // handle meridiem
    config._a[HOUR] = meridiemFixWrap(config._locale, config._a[HOUR], config._meridiem);

    configFromArray(config);
    checkOverflow(config);
}


function meridiemFixWrap (locale, hour, meridiem) {
    var isPm;

    if (meridiem == null) {
        // nothing to do
        return hour;
    }
    if (locale.meridiemHour != null) {
        return locale.meridiemHour(hour, meridiem);
    } else if (locale.isPM != null) {
        // Fallback
        isPm = locale.isPM(meridiem);
        if (isPm && hour < 12) {
            hour += 12;
        }
        if (!isPm && hour === 12) {
            hour = 0;
        }
        return hour;
    } else {
        // this is not supposed to happen
        return hour;
    }
}

// date from string and array of format strings
function configFromStringAndArray(config) {
    var tempConfig,
        bestMoment,

        scoreToBeat,
        i,
        currentScore;

    if (config._f.length === 0) {
        getParsingFlags(config).invalidFormat = true;
        config._d = new Date(NaN);
        return;
    }

    for (i = 0; i < config._f.length; i++) {
        currentScore = 0;
        tempConfig = copyConfig({}, config);
        if (config._useUTC != null) {
            tempConfig._useUTC = config._useUTC;
        }
        tempConfig._f = config._f[i];
        configFromStringAndFormat(tempConfig);

        if (!isValid(tempConfig)) {
            continue;
        }

        // if there is any input that was not parsed add a penalty for that format
        currentScore += getParsingFlags(tempConfig).charsLeftOver;

        //or tokens
        currentScore += getParsingFlags(tempConfig).unusedTokens.length * 10;

        getParsingFlags(tempConfig).score = currentScore;

        if (scoreToBeat == null || currentScore < scoreToBeat) {
            scoreToBeat = currentScore;
            bestMoment = tempConfig;
        }
    }

    extend(config, bestMoment || tempConfig);
}

function configFromObject(config) {
    if (config._d) {
        return;
    }

    var i = normalizeObjectUnits(config._i);
    config._a = map([i.year, i.month, i.day || i.date, i.hour, i.minute, i.second, i.millisecond], function (obj) {
        return obj && parseInt(obj, 10);
    });

    configFromArray(config);
}

function createFromConfig (config) {
    var res = new Moment(checkOverflow(prepareConfig(config)));
    if (res._nextDay) {
        // Adding is smart enough around DST
        res.add(1, 'd');
        res._nextDay = undefined;
    }

    return res;
}

function prepareConfig (config) {
    var input = config._i,
        format = config._f;

    config._locale = config._locale || getLocale(config._l);

    if (input === null || (format === undefined && input === '')) {
        return createInvalid({nullInput: true});
    }

    if (typeof input === 'string') {
        config._i = input = config._locale.preparse(input);
    }

    if (isMoment(input)) {
        return new Moment(checkOverflow(input));
    } else if (isDate(input)) {
        config._d = input;
    } else if (isArray(format)) {
        configFromStringAndArray(config);
    } else if (format) {
        configFromStringAndFormat(config);
    }  else {
        configFromInput(config);
    }

    if (!isValid(config)) {
        config._d = null;
    }

    return config;
}

function configFromInput(config) {
    var input = config._i;
    if (isUndefined(input)) {
        config._d = new Date(hooks.now());
    } else if (isDate(input)) {
        config._d = new Date(input.valueOf());
    } else if (typeof input === 'string') {
        configFromString(config);
    } else if (isArray(input)) {
        config._a = map(input.slice(0), function (obj) {
            return parseInt(obj, 10);
        });
        configFromArray(config);
    } else if (isObject(input)) {
        configFromObject(config);
    } else if (isNumber(input)) {
        // from milliseconds
        config._d = new Date(input);
    } else {
        hooks.createFromInputFallback(config);
    }
}

function createLocalOrUTC (input, format, locale, strict, isUTC) {
    var c = {};

    if (locale === true || locale === false) {
        strict = locale;
        locale = undefined;
    }

    if ((isObject(input) && isObjectEmpty(input)) ||
            (isArray(input) && input.length === 0)) {
        input = undefined;
    }
    // object construction must be done this way.
    // https://github.com/moment/moment/issues/1423
    c._isAMomentObject = true;
    c._useUTC = c._isUTC = isUTC;
    c._l = locale;
    c._i = input;
    c._f = format;
    c._strict = strict;

    return createFromConfig(c);
}

function createLocal (input, format, locale, strict) {
    return createLocalOrUTC(input, format, locale, strict, false);
}

var prototypeMin = deprecate(
    'moment().min is deprecated, use moment.max instead. http://momentjs.com/guides/#/warnings/min-max/',
    function () {
        var other = createLocal.apply(null, arguments);
        if (this.isValid() && other.isValid()) {
            return other < this ? this : other;
        } else {
            return createInvalid();
        }
    }
);

var prototypeMax = deprecate(
    'moment().max is deprecated, use moment.min instead. http://momentjs.com/guides/#/warnings/min-max/',
    function () {
        var other = createLocal.apply(null, arguments);
        if (this.isValid() && other.isValid()) {
            return other > this ? this : other;
        } else {
            return createInvalid();
        }
    }
);

// Pick a moment m from moments so that m[fn](other) is true for all
// other. This relies on the function fn to be transitive.
//
// moments should either be an array of moment objects or an array, whose
// first element is an array of moment objects.
function pickBy(fn, moments) {
    var res, i;
    if (moments.length === 1 && isArray(moments[0])) {
        moments = moments[0];
    }
    if (!moments.length) {
        return createLocal();
    }
    res = moments[0];
    for (i = 1; i < moments.length; ++i) {
        if (!moments[i].isValid() || moments[i][fn](res)) {
            res = moments[i];
        }
    }
    return res;
}

// TODO: Use [].sort instead?
function min () {
    var args = [].slice.call(arguments, 0);

    return pickBy('isBefore', args);
}

function max () {
    var args = [].slice.call(arguments, 0);

    return pickBy('isAfter', args);
}

var now = function () {
    return Date.now ? Date.now() : +(new Date());
};

var ordering = ['year', 'quarter', 'month', 'week', 'day', 'hour', 'minute', 'second', 'millisecond'];

function isDurationValid(m) {
    for (var key in m) {
        if (!(indexOf.call(ordering, key) !== -1 && (m[key] == null || !isNaN(m[key])))) {
            return false;
        }
    }

    var unitHasDecimal = false;
    for (var i = 0; i < ordering.length; ++i) {
        if (m[ordering[i]]) {
            if (unitHasDecimal) {
                return false; // only allow non-integers for smallest unit
            }
            if (parseFloat(m[ordering[i]]) !== toInt(m[ordering[i]])) {
                unitHasDecimal = true;
            }
        }
    }

    return true;
}

function isValid$1() {
    return this._isValid;
}

function createInvalid$1() {
    return createDuration(NaN);
}

function Duration (duration) {
    var normalizedInput = normalizeObjectUnits(duration),
        years = normalizedInput.year || 0,
        quarters = normalizedInput.quarter || 0,
        months = normalizedInput.month || 0,
        weeks = normalizedInput.week || 0,
        days = normalizedInput.day || 0,
        hours = normalizedInput.hour || 0,
        minutes = normalizedInput.minute || 0,
        seconds = normalizedInput.second || 0,
        milliseconds = normalizedInput.millisecond || 0;

    this._isValid = isDurationValid(normalizedInput);

    // representation for dateAddRemove
    this._milliseconds = +milliseconds +
        seconds * 1e3 + // 1000
        minutes * 6e4 + // 1000 * 60
        hours * 1000 * 60 * 60; //using 1000 * 60 * 60 instead of 36e5 to avoid floating point rounding errors https://github.com/moment/moment/issues/2978
    // Because of dateAddRemove treats 24 hours as different from a
    // day when working around DST, we need to store them separately
    this._days = +days +
        weeks * 7;
    // It is impossible to translate months into days without knowing
    // which months you are are talking about, so we have to store
    // it separately.
    this._months = +months +
        quarters * 3 +
        years * 12;

    this._data = {};

    this._locale = getLocale();

    this._bubble();
}

function isDuration (obj) {
    return obj instanceof Duration;
}

function absRound (number) {
    if (number < 0) {
        return Math.round(-1 * number) * -1;
    } else {
        return Math.round(number);
    }
}

// FORMATTING

function offset (token, separator) {
    addFormatToken(token, 0, 0, function () {
        var offset = this.utcOffset();
        var sign = '+';
        if (offset < 0) {
            offset = -offset;
            sign = '-';
        }
        return sign + zeroFill(~~(offset / 60), 2) + separator + zeroFill(~~(offset) % 60, 2);
    });
}

offset('Z', ':');
offset('ZZ', '');

// PARSING

addRegexToken('Z',  matchShortOffset);
addRegexToken('ZZ', matchShortOffset);
addParseToken(['Z', 'ZZ'], function (input, array, config) {
    config._useUTC = true;
    config._tzm = offsetFromString(matchShortOffset, input);
});

// HELPERS

// timezone chunker
// '+10:00' > ['10',  '00']
// '-1530'  > ['-15', '30']
var chunkOffset = /([\+\-]|\d\d)/gi;

function offsetFromString(matcher, string) {
    var matches = (string || '').match(matcher);

    if (matches === null) {
        return null;
    }

    var chunk   = matches[matches.length - 1] || [];
    var parts   = (chunk + '').match(chunkOffset) || ['-', 0, 0];
    var minutes = +(parts[1] * 60) + toInt(parts[2]);

    return minutes === 0 ?
      0 :
      parts[0] === '+' ? minutes : -minutes;
}

// Return a moment from input, that is local/utc/zone equivalent to model.
function cloneWithOffset(input, model) {
    var res, diff;
    if (model._isUTC) {
        res = model.clone();
        diff = (isMoment(input) || isDate(input) ? input.valueOf() : createLocal(input).valueOf()) - res.valueOf();
        // Use low-level api, because this fn is low-level api.
        res._d.setTime(res._d.valueOf() + diff);
        hooks.updateOffset(res, false);
        return res;
    } else {
        return createLocal(input).local();
    }
}

function getDateOffset (m) {
    // On Firefox.24 Date#getTimezoneOffset returns a floating point.
    // https://github.com/moment/moment/pull/1871
    return -Math.round(m._d.getTimezoneOffset() / 15) * 15;
}

// HOOKS

// This function will be called whenever a moment is mutated.
// It is intended to keep the offset in sync with the timezone.
hooks.updateOffset = function () {};

// MOMENTS

// keepLocalTime = true means only change the timezone, without
// affecting the local hour. So 5:31:26 +0300 --[utcOffset(2, true)]-->
// 5:31:26 +0200 It is possible that 5:31:26 doesn't exist with offset
// +0200, so we adjust the time as needed, to be valid.
//
// Keeping the time actually adds/subtracts (one hour)
// from the actual represented time. That is why we call updateOffset
// a second time. In case it wants us to change the offset again
// _changeInProgress == true case, then we have to adjust, because
// there is no such time in the given timezone.
function getSetOffset (input, keepLocalTime, keepMinutes) {
    var offset = this._offset || 0,
        localAdjust;
    if (!this.isValid()) {
        return input != null ? this : NaN;
    }
    if (input != null) {
        if (typeof input === 'string') {
            input = offsetFromString(matchShortOffset, input);
            if (input === null) {
                return this;
            }
        } else if (Math.abs(input) < 16 && !keepMinutes) {
            input = input * 60;
        }
        if (!this._isUTC && keepLocalTime) {
            localAdjust = getDateOffset(this);
        }
        this._offset = input;
        this._isUTC = true;
        if (localAdjust != null) {
            this.add(localAdjust, 'm');
        }
        if (offset !== input) {
            if (!keepLocalTime || this._changeInProgress) {
                addSubtract(this, createDuration(input - offset, 'm'), 1, false);
            } else if (!this._changeInProgress) {
                this._changeInProgress = true;
                hooks.updateOffset(this, true);
                this._changeInProgress = null;
            }
        }
        return this;
    } else {
        return this._isUTC ? offset : getDateOffset(this);
    }
}

function getSetZone (input, keepLocalTime) {
    if (input != null) {
        if (typeof input !== 'string') {
            input = -input;
        }

        this.utcOffset(input, keepLocalTime);

        return this;
    } else {
        return -this.utcOffset();
    }
}

function setOffsetToUTC (keepLocalTime) {
    return this.utcOffset(0, keepLocalTime);
}

function setOffsetToLocal (keepLocalTime) {
    if (this._isUTC) {
        this.utcOffset(0, keepLocalTime);
        this._isUTC = false;

        if (keepLocalTime) {
            this.subtract(getDateOffset(this), 'm');
        }
    }
    return this;
}

function setOffsetToParsedOffset () {
    if (this._tzm != null) {
        this.utcOffset(this._tzm, false, true);
    } else if (typeof this._i === 'string') {
        var tZone = offsetFromString(matchOffset, this._i);
        if (tZone != null) {
            this.utcOffset(tZone);
        }
        else {
            this.utcOffset(0, true);
        }
    }
    return this;
}

function hasAlignedHourOffset (input) {
    if (!this.isValid()) {
        return false;
    }
    input = input ? createLocal(input).utcOffset() : 0;

    return (this.utcOffset() - input) % 60 === 0;
}

function isDaylightSavingTime () {
    return (
        this.utcOffset() > this.clone().month(0).utcOffset() ||
        this.utcOffset() > this.clone().month(5).utcOffset()
    );
}

function isDaylightSavingTimeShifted () {
    if (!isUndefined(this._isDSTShifted)) {
        return this._isDSTShifted;
    }

    var c = {};

    copyConfig(c, this);
    c = prepareConfig(c);

    if (c._a) {
        var other = c._isUTC ? createUTC(c._a) : createLocal(c._a);
        this._isDSTShifted = this.isValid() &&
            compareArrays(c._a, other.toArray()) > 0;
    } else {
        this._isDSTShifted = false;
    }

    return this._isDSTShifted;
}

function isLocal () {
    return this.isValid() ? !this._isUTC : false;
}

function isUtcOffset () {
    return this.isValid() ? this._isUTC : false;
}

function isUtc () {
    return this.isValid() ? this._isUTC && this._offset === 0 : false;
}

// ASP.NET json date format regex
var aspNetRegex = /^(\-|\+)?(?:(\d*)[. ])?(\d+)\:(\d+)(?:\:(\d+)(\.\d*)?)?$/;

// from http://docs.closure-library.googlecode.com/git/closure_goog_date_date.js.source.html
// somewhat more in line with 4.4.3.2 2004 spec, but allows decimal anywhere
// and further modified to allow for strings containing both week and day
var isoRegex = /^(-|\+)?P(?:([-+]?[0-9,.]*)Y)?(?:([-+]?[0-9,.]*)M)?(?:([-+]?[0-9,.]*)W)?(?:([-+]?[0-9,.]*)D)?(?:T(?:([-+]?[0-9,.]*)H)?(?:([-+]?[0-9,.]*)M)?(?:([-+]?[0-9,.]*)S)?)?$/;

function createDuration (input, key) {
    var duration = input,
        // matching against regexp is expensive, do it on demand
        match = null,
        sign,
        ret,
        diffRes;

    if (isDuration(input)) {
        duration = {
            ms : input._milliseconds,
            d  : input._days,
            M  : input._months
        };
    } else if (isNumber(input)) {
        duration = {};
        if (key) {
            duration[key] = input;
        } else {
            duration.milliseconds = input;
        }
    } else if (!!(match = aspNetRegex.exec(input))) {
        sign = (match[1] === '-') ? -1 : 1;
        duration = {
            y  : 0,
            d  : toInt(match[DATE])                         * sign,
            h  : toInt(match[HOUR])                         * sign,
            m  : toInt(match[MINUTE])                       * sign,
            s  : toInt(match[SECOND])                       * sign,
            ms : toInt(absRound(match[MILLISECOND] * 1000)) * sign // the millisecond decimal point is included in the match
        };
    } else if (!!(match = isoRegex.exec(input))) {
        sign = (match[1] === '-') ? -1 : (match[1] === '+') ? 1 : 1;
        duration = {
            y : parseIso(match[2], sign),
            M : parseIso(match[3], sign),
            w : parseIso(match[4], sign),
            d : parseIso(match[5], sign),
            h : parseIso(match[6], sign),
            m : parseIso(match[7], sign),
            s : parseIso(match[8], sign)
        };
    } else if (duration == null) {// checks for null or undefined
        duration = {};
    } else if (typeof duration === 'object' && ('from' in duration || 'to' in duration)) {
        diffRes = momentsDifference(createLocal(duration.from), createLocal(duration.to));

        duration = {};
        duration.ms = diffRes.milliseconds;
        duration.M = diffRes.months;
    }

    ret = new Duration(duration);

    if (isDuration(input) && hasOwnProp(input, '_locale')) {
        ret._locale = input._locale;
    }

    return ret;
}

createDuration.fn = Duration.prototype;
createDuration.invalid = createInvalid$1;

function parseIso (inp, sign) {
    // We'd normally use ~~inp for this, but unfortunately it also
    // converts floats to ints.
    // inp may be undefined, so careful calling replace on it.
    var res = inp && parseFloat(inp.replace(',', '.'));
    // apply sign while we're at it
    return (isNaN(res) ? 0 : res) * sign;
}

function positiveMomentsDifference(base, other) {
    var res = {milliseconds: 0, months: 0};

    res.months = other.month() - base.month() +
        (other.year() - base.year()) * 12;
    if (base.clone().add(res.months, 'M').isAfter(other)) {
        --res.months;
    }

    res.milliseconds = +other - +(base.clone().add(res.months, 'M'));

    return res;
}

function momentsDifference(base, other) {
    var res;
    if (!(base.isValid() && other.isValid())) {
        return {milliseconds: 0, months: 0};
    }

    other = cloneWithOffset(other, base);
    if (base.isBefore(other)) {
        res = positiveMomentsDifference(base, other);
    } else {
        res = positiveMomentsDifference(other, base);
        res.milliseconds = -res.milliseconds;
        res.months = -res.months;
    }

    return res;
}

// TODO: remove 'name' arg after deprecation is removed
function createAdder(direction, name) {
    return function (val, period) {
        var dur, tmp;
        //invert the arguments, but complain about it
        if (period !== null && !isNaN(+period)) {
            deprecateSimple(name, 'moment().' + name  + '(period, number) is deprecated. Please use moment().' + name + '(number, period). ' +
            'See http://momentjs.com/guides/#/warnings/add-inverted-param/ for more info.');
            tmp = val; val = period; period = tmp;
        }

        val = typeof val === 'string' ? +val : val;
        dur = createDuration(val, period);
        addSubtract(this, dur, direction);
        return this;
    };
}

function addSubtract (mom, duration, isAdding, updateOffset) {
    var milliseconds = duration._milliseconds,
        days = absRound(duration._days),
        months = absRound(duration._months);

    if (!mom.isValid()) {
        // No op
        return;
    }

    updateOffset = updateOffset == null ? true : updateOffset;

    if (months) {
        setMonth(mom, get(mom, 'Month') + months * isAdding);
    }
    if (days) {
        set$1(mom, 'Date', get(mom, 'Date') + days * isAdding);
    }
    if (milliseconds) {
        mom._d.setTime(mom._d.valueOf() + milliseconds * isAdding);
    }
    if (updateOffset) {
        hooks.updateOffset(mom, days || months);
    }
}

var add      = createAdder(1, 'add');
var subtract = createAdder(-1, 'subtract');

function getCalendarFormat(myMoment, now) {
    var diff = myMoment.diff(now, 'days', true);
    return diff < -6 ? 'sameElse' :
            diff < -1 ? 'lastWeek' :
            diff < 0 ? 'lastDay' :
            diff < 1 ? 'sameDay' :
            diff < 2 ? 'nextDay' :
            diff < 7 ? 'nextWeek' : 'sameElse';
}

function calendar$1 (time, formats) {
    // We want to compare the start of today, vs this.
    // Getting start-of-today depends on whether we're local/utc/offset or not.
    var now = time || createLocal(),
        sod = cloneWithOffset(now, this).startOf('day'),
        format = hooks.calendarFormat(this, sod) || 'sameElse';

    var output = formats && (isFunction(formats[format]) ? formats[format].call(this, now) : formats[format]);

    return this.format(output || this.localeData().calendar(format, this, createLocal(now)));
}

function clone () {
    return new Moment(this);
}

function isAfter (input, units) {
    var localInput = isMoment(input) ? input : createLocal(input);
    if (!(this.isValid() && localInput.isValid())) {
        return false;
    }
    units = normalizeUnits(!isUndefined(units) ? units : 'millisecond');
    if (units === 'millisecond') {
        return this.valueOf() > localInput.valueOf();
    } else {
        return localInput.valueOf() < this.clone().startOf(units).valueOf();
    }
}

function isBefore (input, units) {
    var localInput = isMoment(input) ? input : createLocal(input);
    if (!(this.isValid() && localInput.isValid())) {
        return false;
    }
    units = normalizeUnits(!isUndefined(units) ? units : 'millisecond');
    if (units === 'millisecond') {
        return this.valueOf() < localInput.valueOf();
    } else {
        return this.clone().endOf(units).valueOf() < localInput.valueOf();
    }
}

function isBetween (from, to, units, inclusivity) {
    inclusivity = inclusivity || '()';
    return (inclusivity[0] === '(' ? this.isAfter(from, units) : !this.isBefore(from, units)) &&
        (inclusivity[1] === ')' ? this.isBefore(to, units) : !this.isAfter(to, units));
}

function isSame (input, units) {
    var localInput = isMoment(input) ? input : createLocal(input),
        inputMs;
    if (!(this.isValid() && localInput.isValid())) {
        return false;
    }
    units = normalizeUnits(units || 'millisecond');
    if (units === 'millisecond') {
        return this.valueOf() === localInput.valueOf();
    } else {
        inputMs = localInput.valueOf();
        return this.clone().startOf(units).valueOf() <= inputMs && inputMs <= this.clone().endOf(units).valueOf();
    }
}

function isSameOrAfter (input, units) {
    return this.isSame(input, units) || this.isAfter(input,units);
}

function isSameOrBefore (input, units) {
    return this.isSame(input, units) || this.isBefore(input,units);
}

function diff (input, units, asFloat) {
    var that,
        zoneDelta,
        delta, output;

    if (!this.isValid()) {
        return NaN;
    }

    that = cloneWithOffset(input, this);

    if (!that.isValid()) {
        return NaN;
    }

    zoneDelta = (that.utcOffset() - this.utcOffset()) * 6e4;

    units = normalizeUnits(units);

    switch (units) {
        case 'year': output = monthDiff(this, that) / 12; break;
        case 'month': output = monthDiff(this, that); break;
        case 'quarter': output = monthDiff(this, that) / 3; break;
        case 'second': output = (this - that) / 1e3; break; // 1000
        case 'minute': output = (this - that) / 6e4; break; // 1000 * 60
        case 'hour': output = (this - that) / 36e5; break; // 1000 * 60 * 60
        case 'day': output = (this - that - zoneDelta) / 864e5; break; // 1000 * 60 * 60 * 24, negate dst
        case 'week': output = (this - that - zoneDelta) / 6048e5; break; // 1000 * 60 * 60 * 24 * 7, negate dst
        default: output = this - that;
    }

    return asFloat ? output : absFloor(output);
}

function monthDiff (a, b) {
    // difference in months
    var wholeMonthDiff = ((b.year() - a.year()) * 12) + (b.month() - a.month()),
        // b is in (anchor - 1 month, anchor + 1 month)
        anchor = a.clone().add(wholeMonthDiff, 'months'),
        anchor2, adjust;

    if (b - anchor < 0) {
        anchor2 = a.clone().add(wholeMonthDiff - 1, 'months');
        // linear across the month
        adjust = (b - anchor) / (anchor - anchor2);
    } else {
        anchor2 = a.clone().add(wholeMonthDiff + 1, 'months');
        // linear across the month
        adjust = (b - anchor) / (anchor2 - anchor);
    }

    //check for negative zero, return zero if negative zero
    return -(wholeMonthDiff + adjust) || 0;
}

hooks.defaultFormat = 'YYYY-MM-DDTHH:mm:ssZ';
hooks.defaultFormatUtc = 'YYYY-MM-DDTHH:mm:ss[Z]';

function toString () {
    return this.clone().locale('en').format('ddd MMM DD YYYY HH:mm:ss [GMT]ZZ');
}

function toISOString(keepOffset) {
    if (!this.isValid()) {
        return null;
    }
    var utc = keepOffset !== true;
    var m = utc ? this.clone().utc() : this;
    if (m.year() < 0 || m.year() > 9999) {
        return formatMoment(m, utc ? 'YYYYYY-MM-DD[T]HH:mm:ss.SSS[Z]' : 'YYYYYY-MM-DD[T]HH:mm:ss.SSSZ');
    }
    if (isFunction(Date.prototype.toISOString)) {
        // native implementation is ~50x faster, use it when we can
        if (utc) {
            return this.toDate().toISOString();
        } else {
            return new Date(this._d.valueOf()).toISOString().replace('Z', formatMoment(m, 'Z'));
        }
    }
    return formatMoment(m, utc ? 'YYYY-MM-DD[T]HH:mm:ss.SSS[Z]' : 'YYYY-MM-DD[T]HH:mm:ss.SSSZ');
}

/**
 * Return a human readable representation of a moment that can
 * also be evaluated to get a new moment which is the same
 *
 * @link https://nodejs.org/dist/latest/docs/api/util.html#util_custom_inspect_function_on_objects
 */
function inspect () {
    if (!this.isValid()) {
        return 'moment.invalid(/* ' + this._i + ' */)';
    }
    var func = 'moment';
    var zone = '';
    if (!this.isLocal()) {
        func = this.utcOffset() === 0 ? 'moment.utc' : 'moment.parseZone';
        zone = 'Z';
    }
    var prefix = '[' + func + '("]';
    var year = (0 <= this.year() && this.year() <= 9999) ? 'YYYY' : 'YYYYYY';
    var datetime = '-MM-DD[T]HH:mm:ss.SSS';
    var suffix = zone + '[")]';

    return this.format(prefix + year + datetime + suffix);
}

function format (inputString) {
    if (!inputString) {
        inputString = this.isUtc() ? hooks.defaultFormatUtc : hooks.defaultFormat;
    }
    var output = formatMoment(this, inputString);
    return this.localeData().postformat(output);
}

function from (time, withoutSuffix) {
    if (this.isValid() &&
            ((isMoment(time) && time.isValid()) ||
             createLocal(time).isValid())) {
        return createDuration({to: this, from: time}).locale(this.locale()).humanize(!withoutSuffix);
    } else {
        return this.localeData().invalidDate();
    }
}

function fromNow (withoutSuffix) {
    return this.from(createLocal(), withoutSuffix);
}

function to (time, withoutSuffix) {
    if (this.isValid() &&
            ((isMoment(time) && time.isValid()) ||
             createLocal(time).isValid())) {
        return createDuration({from: this, to: time}).locale(this.locale()).humanize(!withoutSuffix);
    } else {
        return this.localeData().invalidDate();
    }
}

function toNow (withoutSuffix) {
    return this.to(createLocal(), withoutSuffix);
}

// If passed a locale key, it will set the locale for this
// instance.  Otherwise, it will return the locale configuration
// variables for this instance.
function locale (key) {
    var newLocaleData;

    if (key === undefined) {
        return this._locale._abbr;
    } else {
        newLocaleData = getLocale(key);
        if (newLocaleData != null) {
            this._locale = newLocaleData;
        }
        return this;
    }
}

var lang = deprecate(
    'moment().lang() is deprecated. Instead, use moment().localeData() to get the language configuration. Use moment().locale() to change languages.',
    function (key) {
        if (key === undefined) {
            return this.localeData();
        } else {
            return this.locale(key);
        }
    }
);

function localeData () {
    return this._locale;
}

function startOf (units) {
    units = normalizeUnits(units);
    // the following switch intentionally omits break keywords
    // to utilize falling through the cases.
    switch (units) {
        case 'year':
            this.month(0);
            /* falls through */
        case 'quarter':
        case 'month':
            this.date(1);
            /* falls through */
        case 'week':
        case 'isoWeek':
        case 'day':
        case 'date':
            this.hours(0);
            /* falls through */
        case 'hour':
            this.minutes(0);
            /* falls through */
        case 'minute':
            this.seconds(0);
            /* falls through */
        case 'second':
            this.milliseconds(0);
    }

    // weeks are a special case
    if (units === 'week') {
        this.weekday(0);
    }
    if (units === 'isoWeek') {
        this.isoWeekday(1);
    }

    // quarters are also special
    if (units === 'quarter') {
        this.month(Math.floor(this.month() / 3) * 3);
    }

    return this;
}

function endOf (units) {
    units = normalizeUnits(units);
    if (units === undefined || units === 'millisecond') {
        return this;
    }

    // 'date' is an alias for 'day', so it should be considered as such.
    if (units === 'date') {
        units = 'day';
    }

    return this.startOf(units).add(1, (units === 'isoWeek' ? 'week' : units)).subtract(1, 'ms');
}

function valueOf () {
    return this._d.valueOf() - ((this._offset || 0) * 60000);
}

function unix () {
    return Math.floor(this.valueOf() / 1000);
}

function toDate () {
    return new Date(this.valueOf());
}

function toArray () {
    var m = this;
    return [m.year(), m.month(), m.date(), m.hour(), m.minute(), m.second(), m.millisecond()];
}

function toObject () {
    var m = this;
    return {
        years: m.year(),
        months: m.month(),
        date: m.date(),
        hours: m.hours(),
        minutes: m.minutes(),
        seconds: m.seconds(),
        milliseconds: m.milliseconds()
    };
}

function toJSON () {
    // new Date(NaN).toJSON() === null
    return this.isValid() ? this.toISOString() : null;
}

function isValid$2 () {
    return isValid(this);
}

function parsingFlags () {
    return extend({}, getParsingFlags(this));
}

function invalidAt () {
    return getParsingFlags(this).overflow;
}

function creationData() {
    return {
        input: this._i,
        format: this._f,
        locale: this._locale,
        isUTC: this._isUTC,
        strict: this._strict
    };
}

// FORMATTING

addFormatToken(0, ['gg', 2], 0, function () {
    return this.weekYear() % 100;
});

addFormatToken(0, ['GG', 2], 0, function () {
    return this.isoWeekYear() % 100;
});

function addWeekYearFormatToken (token, getter) {
    addFormatToken(0, [token, token.length], 0, getter);
}

addWeekYearFormatToken('gggg',     'weekYear');
addWeekYearFormatToken('ggggg',    'weekYear');
addWeekYearFormatToken('GGGG',  'isoWeekYear');
addWeekYearFormatToken('GGGGG', 'isoWeekYear');

// ALIASES

addUnitAlias('weekYear', 'gg');
addUnitAlias('isoWeekYear', 'GG');

// PRIORITY

addUnitPriority('weekYear', 1);
addUnitPriority('isoWeekYear', 1);


// PARSING

addRegexToken('G',      matchSigned);
addRegexToken('g',      matchSigned);
addRegexToken('GG',     match1to2, match2);
addRegexToken('gg',     match1to2, match2);
addRegexToken('GGGG',   match1to4, match4);
addRegexToken('gggg',   match1to4, match4);
addRegexToken('GGGGG',  match1to6, match6);
addRegexToken('ggggg',  match1to6, match6);

addWeekParseToken(['gggg', 'ggggg', 'GGGG', 'GGGGG'], function (input, week, config, token) {
    week[token.substr(0, 2)] = toInt(input);
});

addWeekParseToken(['gg', 'GG'], function (input, week, config, token) {
    week[token] = hooks.parseTwoDigitYear(input);
});

// MOMENTS

function getSetWeekYear (input) {
    return getSetWeekYearHelper.call(this,
            input,
            this.week(),
            this.weekday(),
            this.localeData()._week.dow,
            this.localeData()._week.doy);
}

function getSetISOWeekYear (input) {
    return getSetWeekYearHelper.call(this,
            input, this.isoWeek(), this.isoWeekday(), 1, 4);
}

function getISOWeeksInYear () {
    return weeksInYear(this.year(), 1, 4);
}

function getWeeksInYear () {
    var weekInfo = this.localeData()._week;
    return weeksInYear(this.year(), weekInfo.dow, weekInfo.doy);
}

function getSetWeekYearHelper(input, week, weekday, dow, doy) {
    var weeksTarget;
    if (input == null) {
        return weekOfYear(this, dow, doy).year;
    } else {
        weeksTarget = weeksInYear(input, dow, doy);
        if (week > weeksTarget) {
            week = weeksTarget;
        }
        return setWeekAll.call(this, input, week, weekday, dow, doy);
    }
}

function setWeekAll(weekYear, week, weekday, dow, doy) {
    var dayOfYearData = dayOfYearFromWeeks(weekYear, week, weekday, dow, doy),
        date = createUTCDate(dayOfYearData.year, 0, dayOfYearData.dayOfYear);

    this.year(date.getUTCFullYear());
    this.month(date.getUTCMonth());
    this.date(date.getUTCDate());
    return this;
}

// FORMATTING

addFormatToken('Q', 0, 'Qo', 'quarter');

// ALIASES

addUnitAlias('quarter', 'Q');

// PRIORITY

addUnitPriority('quarter', 7);

// PARSING

addRegexToken('Q', match1);
addParseToken('Q', function (input, array) {
    array[MONTH] = (toInt(input) - 1) * 3;
});

// MOMENTS

function getSetQuarter (input) {
    return input == null ? Math.ceil((this.month() + 1) / 3) : this.month((input - 1) * 3 + this.month() % 3);
}

// FORMATTING

addFormatToken('D', ['DD', 2], 'Do', 'date');

// ALIASES

addUnitAlias('date', 'D');

// PRIOROITY
addUnitPriority('date', 9);

// PARSING

addRegexToken('D',  match1to2);
addRegexToken('DD', match1to2, match2);
addRegexToken('Do', function (isStrict, locale) {
    // TODO: Remove "ordinalParse" fallback in next major release.
    return isStrict ?
      (locale._dayOfMonthOrdinalParse || locale._ordinalParse) :
      locale._dayOfMonthOrdinalParseLenient;
});

addParseToken(['D', 'DD'], DATE);
addParseToken('Do', function (input, array) {
    array[DATE] = toInt(input.match(match1to2)[0]);
});

// MOMENTS

var getSetDayOfMonth = makeGetSet('Date', true);

// FORMATTING

addFormatToken('DDD', ['DDDD', 3], 'DDDo', 'dayOfYear');

// ALIASES

addUnitAlias('dayOfYear', 'DDD');

// PRIORITY
addUnitPriority('dayOfYear', 4);

// PARSING

addRegexToken('DDD',  match1to3);
addRegexToken('DDDD', match3);
addParseToken(['DDD', 'DDDD'], function (input, array, config) {
    config._dayOfYear = toInt(input);
});

// HELPERS

// MOMENTS

function getSetDayOfYear (input) {
    var dayOfYear = Math.round((this.clone().startOf('day') - this.clone().startOf('year')) / 864e5) + 1;
    return input == null ? dayOfYear : this.add((input - dayOfYear), 'd');
}

// FORMATTING

addFormatToken('m', ['mm', 2], 0, 'minute');

// ALIASES

addUnitAlias('minute', 'm');

// PRIORITY

addUnitPriority('minute', 14);

// PARSING

addRegexToken('m',  match1to2);
addRegexToken('mm', match1to2, match2);
addParseToken(['m', 'mm'], MINUTE);

// MOMENTS

var getSetMinute = makeGetSet('Minutes', false);

// FORMATTING

addFormatToken('s', ['ss', 2], 0, 'second');

// ALIASES

addUnitAlias('second', 's');

// PRIORITY

addUnitPriority('second', 15);

// PARSING

addRegexToken('s',  match1to2);
addRegexToken('ss', match1to2, match2);
addParseToken(['s', 'ss'], SECOND);

// MOMENTS

var getSetSecond = makeGetSet('Seconds', false);

// FORMATTING

addFormatToken('S', 0, 0, function () {
    return ~~(this.millisecond() / 100);
});

addFormatToken(0, ['SS', 2], 0, function () {
    return ~~(this.millisecond() / 10);
});

addFormatToken(0, ['SSS', 3], 0, 'millisecond');
addFormatToken(0, ['SSSS', 4], 0, function () {
    return this.millisecond() * 10;
});
addFormatToken(0, ['SSSSS', 5], 0, function () {
    return this.millisecond() * 100;
});
addFormatToken(0, ['SSSSSS', 6], 0, function () {
    return this.millisecond() * 1000;
});
addFormatToken(0, ['SSSSSSS', 7], 0, function () {
    return this.millisecond() * 10000;
});
addFormatToken(0, ['SSSSSSSS', 8], 0, function () {
    return this.millisecond() * 100000;
});
addFormatToken(0, ['SSSSSSSSS', 9], 0, function () {
    return this.millisecond() * 1000000;
});


// ALIASES

addUnitAlias('millisecond', 'ms');

// PRIORITY

addUnitPriority('millisecond', 16);

// PARSING

addRegexToken('S',    match1to3, match1);
addRegexToken('SS',   match1to3, match2);
addRegexToken('SSS',  match1to3, match3);

var token;
for (token = 'SSSS'; token.length <= 9; token += 'S') {
    addRegexToken(token, matchUnsigned);
}

function parseMs(input, array) {
    array[MILLISECOND] = toInt(('0.' + input) * 1000);
}

for (token = 'S'; token.length <= 9; token += 'S') {
    addParseToken(token, parseMs);
}
// MOMENTS

var getSetMillisecond = makeGetSet('Milliseconds', false);

// FORMATTING

addFormatToken('z',  0, 0, 'zoneAbbr');
addFormatToken('zz', 0, 0, 'zoneName');

// MOMENTS

function getZoneAbbr () {
    return this._isUTC ? 'UTC' : '';
}

function getZoneName () {
    return this._isUTC ? 'Coordinated Universal Time' : '';
}

var proto = Moment.prototype;

proto.add               = add;
proto.calendar          = calendar$1;
proto.clone             = clone;
proto.diff              = diff;
proto.endOf             = endOf;
proto.format            = format;
proto.from              = from;
proto.fromNow           = fromNow;
proto.to                = to;
proto.toNow             = toNow;
proto.get               = stringGet;
proto.invalidAt         = invalidAt;
proto.isAfter           = isAfter;
proto.isBefore          = isBefore;
proto.isBetween         = isBetween;
proto.isSame            = isSame;
proto.isSameOrAfter     = isSameOrAfter;
proto.isSameOrBefore    = isSameOrBefore;
proto.isValid           = isValid$2;
proto.lang              = lang;
proto.locale            = locale;
proto.localeData        = localeData;
proto.max               = prototypeMax;
proto.min               = prototypeMin;
proto.parsingFlags      = parsingFlags;
proto.set               = stringSet;
proto.startOf           = startOf;
proto.subtract          = subtract;
proto.toArray           = toArray;
proto.toObject          = toObject;
proto.toDate            = toDate;
proto.toISOString       = toISOString;
proto.inspect           = inspect;
proto.toJSON            = toJSON;
proto.toString          = toString;
proto.unix              = unix;
proto.valueOf           = valueOf;
proto.creationData      = creationData;

// Year
proto.year       = getSetYear;
proto.isLeapYear = getIsLeapYear;

// Week Year
proto.weekYear    = getSetWeekYear;
proto.isoWeekYear = getSetISOWeekYear;

// Quarter
proto.quarter = proto.quarters = getSetQuarter;

// Month
proto.month       = getSetMonth;
proto.daysInMonth = getDaysInMonth;

// Week
proto.week           = proto.weeks        = getSetWeek;
proto.isoWeek        = proto.isoWeeks     = getSetISOWeek;
proto.weeksInYear    = getWeeksInYear;
proto.isoWeeksInYear = getISOWeeksInYear;

// Day
proto.date       = getSetDayOfMonth;
proto.day        = proto.days             = getSetDayOfWeek;
proto.weekday    = getSetLocaleDayOfWeek;
proto.isoWeekday = getSetISODayOfWeek;
proto.dayOfYear  = getSetDayOfYear;

// Hour
proto.hour = proto.hours = getSetHour;

// Minute
proto.minute = proto.minutes = getSetMinute;

// Second
proto.second = proto.seconds = getSetSecond;

// Millisecond
proto.millisecond = proto.milliseconds = getSetMillisecond;

// Offset
proto.utcOffset            = getSetOffset;
proto.utc                  = setOffsetToUTC;
proto.local                = setOffsetToLocal;
proto.parseZone            = setOffsetToParsedOffset;
proto.hasAlignedHourOffset = hasAlignedHourOffset;
proto.isDST                = isDaylightSavingTime;
proto.isLocal              = isLocal;
proto.isUtcOffset          = isUtcOffset;
proto.isUtc                = isUtc;
proto.isUTC                = isUtc;

// Timezone
proto.zoneAbbr = getZoneAbbr;
proto.zoneName = getZoneName;

// Deprecations
proto.dates  = deprecate('dates accessor is deprecated. Use date instead.', getSetDayOfMonth);
proto.months = deprecate('months accessor is deprecated. Use month instead', getSetMonth);
proto.years  = deprecate('years accessor is deprecated. Use year instead', getSetYear);
proto.zone   = deprecate('moment().zone is deprecated, use moment().utcOffset instead. http://momentjs.com/guides/#/warnings/zone/', getSetZone);
proto.isDSTShifted = deprecate('isDSTShifted is deprecated. See http://momentjs.com/guides/#/warnings/dst-shifted/ for more information', isDaylightSavingTimeShifted);

function createUnix (input) {
    return createLocal(input * 1000);
}

function createInZone () {
    return createLocal.apply(null, arguments).parseZone();
}

function preParsePostFormat (string) {
    return string;
}

var proto$1 = Locale.prototype;

proto$1.calendar        = calendar;
proto$1.longDateFormat  = longDateFormat;
proto$1.invalidDate     = invalidDate;
proto$1.ordinal         = ordinal;
proto$1.preparse        = preParsePostFormat;
proto$1.postformat      = preParsePostFormat;
proto$1.relativeTime    = relativeTime;
proto$1.pastFuture      = pastFuture;
proto$1.set             = set;

// Month
proto$1.months            =        localeMonths;
proto$1.monthsShort       =        localeMonthsShort;
proto$1.monthsParse       =        localeMonthsParse;
proto$1.monthsRegex       = monthsRegex;
proto$1.monthsShortRegex  = monthsShortRegex;

// Week
proto$1.week = localeWeek;
proto$1.firstDayOfYear = localeFirstDayOfYear;
proto$1.firstDayOfWeek = localeFirstDayOfWeek;

// Day of Week
proto$1.weekdays       =        localeWeekdays;
proto$1.weekdaysMin    =        localeWeekdaysMin;
proto$1.weekdaysShort  =        localeWeekdaysShort;
proto$1.weekdaysParse  =        localeWeekdaysParse;

proto$1.weekdaysRegex       =        weekdaysRegex;
proto$1.weekdaysShortRegex  =        weekdaysShortRegex;
proto$1.weekdaysMinRegex    =        weekdaysMinRegex;

// Hours
proto$1.isPM = localeIsPM;
proto$1.meridiem = localeMeridiem;

function get$1 (format, index, field, setter) {
    var locale = getLocale();
    var utc = createUTC().set(setter, index);
    return locale[field](utc, format);
}

function listMonthsImpl (format, index, field) {
    if (isNumber(format)) {
        index = format;
        format = undefined;
    }

    format = format || '';

    if (index != null) {
        return get$1(format, index, field, 'month');
    }

    var i;
    var out = [];
    for (i = 0; i < 12; i++) {
        out[i] = get$1(format, i, field, 'month');
    }
    return out;
}

// ()
// (5)
// (fmt, 5)
// (fmt)
// (true)
// (true, 5)
// (true, fmt, 5)
// (true, fmt)
function listWeekdaysImpl (localeSorted, format, index, field) {
    if (typeof localeSorted === 'boolean') {
        if (isNumber(format)) {
            index = format;
            format = undefined;
        }

        format = format || '';
    } else {
        format = localeSorted;
        index = format;
        localeSorted = false;

        if (isNumber(format)) {
            index = format;
            format = undefined;
        }

        format = format || '';
    }

    var locale = getLocale(),
        shift = localeSorted ? locale._week.dow : 0;

    if (index != null) {
        return get$1(format, (index + shift) % 7, field, 'day');
    }

    var i;
    var out = [];
    for (i = 0; i < 7; i++) {
        out[i] = get$1(format, (i + shift) % 7, field, 'day');
    }
    return out;
}

function listMonths (format, index) {
    return listMonthsImpl(format, index, 'months');
}

function listMonthsShort (format, index) {
    return listMonthsImpl(format, index, 'monthsShort');
}

function listWeekdays (localeSorted, format, index) {
    return listWeekdaysImpl(localeSorted, format, index, 'weekdays');
}

function listWeekdaysShort (localeSorted, format, index) {
    return listWeekdaysImpl(localeSorted, format, index, 'weekdaysShort');
}

function listWeekdaysMin (localeSorted, format, index) {
    return listWeekdaysImpl(localeSorted, format, index, 'weekdaysMin');
}

getSetGlobalLocale('en', {
    dayOfMonthOrdinalParse: /\d{1,2}(th|st|nd|rd)/,
    ordinal : function (number) {
        var b = number % 10,
            output = (toInt(number % 100 / 10) === 1) ? 'th' :
            (b === 1) ? 'st' :
            (b === 2) ? 'nd' :
            (b === 3) ? 'rd' : 'th';
        return number + output;
    }
});

// Side effect imports
hooks.lang = deprecate('moment.lang is deprecated. Use moment.locale instead.', getSetGlobalLocale);
hooks.langData = deprecate('moment.langData is deprecated. Use moment.localeData instead.', getLocale);

var mathAbs = Math.abs;

function abs () {
    var data           = this._data;

    this._milliseconds = mathAbs(this._milliseconds);
    this._days         = mathAbs(this._days);
    this._months       = mathAbs(this._months);

    data.milliseconds  = mathAbs(data.milliseconds);
    data.seconds       = mathAbs(data.seconds);
    data.minutes       = mathAbs(data.minutes);
    data.hours         = mathAbs(data.hours);
    data.months        = mathAbs(data.months);
    data.years         = mathAbs(data.years);

    return this;
}

function addSubtract$1 (duration, input, value, direction) {
    var other = createDuration(input, value);

    duration._milliseconds += direction * other._milliseconds;
    duration._days         += direction * other._days;
    duration._months       += direction * other._months;

    return duration._bubble();
}

// supports only 2.0-style add(1, 's') or add(duration)
function add$1 (input, value) {
    return addSubtract$1(this, input, value, 1);
}

// supports only 2.0-style subtract(1, 's') or subtract(duration)
function subtract$1 (input, value) {
    return addSubtract$1(this, input, value, -1);
}

function absCeil (number) {
    if (number < 0) {
        return Math.floor(number);
    } else {
        return Math.ceil(number);
    }
}

function bubble () {
    var milliseconds = this._milliseconds;
    var days         = this._days;
    var months       = this._months;
    var data         = this._data;
    var seconds, minutes, hours, years, monthsFromDays;

    // if we have a mix of positive and negative values, bubble down first
    // check: https://github.com/moment/moment/issues/2166
    if (!((milliseconds >= 0 && days >= 0 && months >= 0) ||
            (milliseconds <= 0 && days <= 0 && months <= 0))) {
        milliseconds += absCeil(monthsToDays(months) + days) * 864e5;
        days = 0;
        months = 0;
    }

    // The following code bubbles up values, see the tests for
    // examples of what that means.
    data.milliseconds = milliseconds % 1000;

    seconds           = absFloor(milliseconds / 1000);
    data.seconds      = seconds % 60;

    minutes           = absFloor(seconds / 60);
    data.minutes      = minutes % 60;

    hours             = absFloor(minutes / 60);
    data.hours        = hours % 24;

    days += absFloor(hours / 24);

    // convert days to months
    monthsFromDays = absFloor(daysToMonths(days));
    months += monthsFromDays;
    days -= absCeil(monthsToDays(monthsFromDays));

    // 12 months -> 1 year
    years = absFloor(months / 12);
    months %= 12;

    data.days   = days;
    data.months = months;
    data.years  = years;

    return this;
}

function daysToMonths (days) {
    // 400 years have 146097 days (taking into account leap year rules)
    // 400 years have 12 months === 4800
    return days * 4800 / 146097;
}

function monthsToDays (months) {
    // the reverse of daysToMonths
    return months * 146097 / 4800;
}

function as (units) {
    if (!this.isValid()) {
        return NaN;
    }
    var days;
    var months;
    var milliseconds = this._milliseconds;

    units = normalizeUnits(units);

    if (units === 'month' || units === 'year') {
        days   = this._days   + milliseconds / 864e5;
        months = this._months + daysToMonths(days);
        return units === 'month' ? months : months / 12;
    } else {
        // handle milliseconds separately because of floating point math errors (issue #1867)
        days = this._days + Math.round(monthsToDays(this._months));
        switch (units) {
            case 'week'   : return days / 7     + milliseconds / 6048e5;
            case 'day'    : return days         + milliseconds / 864e5;
            case 'hour'   : return days * 24    + milliseconds / 36e5;
            case 'minute' : return days * 1440  + milliseconds / 6e4;
            case 'second' : return days * 86400 + milliseconds / 1000;
            // Math.floor prevents floating point math errors here
            case 'millisecond': return Math.floor(days * 864e5) + milliseconds;
            default: throw new Error('Unknown unit ' + units);
        }
    }
}

// TODO: Use this.as('ms')?
function valueOf$1 () {
    if (!this.isValid()) {
        return NaN;
    }
    return (
        this._milliseconds +
        this._days * 864e5 +
        (this._months % 12) * 2592e6 +
        toInt(this._months / 12) * 31536e6
    );
}

function makeAs (alias) {
    return function () {
        return this.as(alias);
    };
}

var asMilliseconds = makeAs('ms');
var asSeconds      = makeAs('s');
var asMinutes      = makeAs('m');
var asHours        = makeAs('h');
var asDays         = makeAs('d');
var asWeeks        = makeAs('w');
var asMonths       = makeAs('M');
var asYears        = makeAs('y');

function clone$1 () {
    return createDuration(this);
}

function get$2 (units) {
    units = normalizeUnits(units);
    return this.isValid() ? this[units + 's']() : NaN;
}

function makeGetter(name) {
    return function () {
        return this.isValid() ? this._data[name] : NaN;
    };
}

var milliseconds = makeGetter('milliseconds');
var seconds      = makeGetter('seconds');
var minutes      = makeGetter('minutes');
var hours        = makeGetter('hours');
var days         = makeGetter('days');
var months       = makeGetter('months');
var years        = makeGetter('years');

function weeks () {
    return absFloor(this.days() / 7);
}

var round = Math.round;
var thresholds = {
    ss: 44,         // a few seconds to seconds
    s : 45,         // seconds to minute
    m : 45,         // minutes to hour
    h : 22,         // hours to day
    d : 26,         // days to month
    M : 11          // months to year
};

// helper function for moment.fn.from, moment.fn.fromNow, and moment.duration.fn.humanize
function substituteTimeAgo(string, number, withoutSuffix, isFuture, locale) {
    return locale.relativeTime(number || 1, !!withoutSuffix, string, isFuture);
}

function relativeTime$1 (posNegDuration, withoutSuffix, locale) {
    var duration = createDuration(posNegDuration).abs();
    var seconds  = round(duration.as('s'));
    var minutes  = round(duration.as('m'));
    var hours    = round(duration.as('h'));
    var days     = round(duration.as('d'));
    var months   = round(duration.as('M'));
    var years    = round(duration.as('y'));

    var a = seconds <= thresholds.ss && ['s', seconds]  ||
            seconds < thresholds.s   && ['ss', seconds] ||
            minutes <= 1             && ['m']           ||
            minutes < thresholds.m   && ['mm', minutes] ||
            hours   <= 1             && ['h']           ||
            hours   < thresholds.h   && ['hh', hours]   ||
            days    <= 1             && ['d']           ||
            days    < thresholds.d   && ['dd', days]    ||
            months  <= 1             && ['M']           ||
            months  < thresholds.M   && ['MM', months]  ||
            years   <= 1             && ['y']           || ['yy', years];

    a[2] = withoutSuffix;
    a[3] = +posNegDuration > 0;
    a[4] = locale;
    return substituteTimeAgo.apply(null, a);
}

// This function allows you to set the rounding function for relative time strings
function getSetRelativeTimeRounding (roundingFunction) {
    if (roundingFunction === undefined) {
        return round;
    }
    if (typeof(roundingFunction) === 'function') {
        round = roundingFunction;
        return true;
    }
    return false;
}

// This function allows you to set a threshold for relative time strings
function getSetRelativeTimeThreshold (threshold, limit) {
    if (thresholds[threshold] === undefined) {
        return false;
    }
    if (limit === undefined) {
        return thresholds[threshold];
    }
    thresholds[threshold] = limit;
    if (threshold === 's') {
        thresholds.ss = limit - 1;
    }
    return true;
}

function humanize (withSuffix) {
    if (!this.isValid()) {
        return this.localeData().invalidDate();
    }

    var locale = this.localeData();
    var output = relativeTime$1(this, !withSuffix, locale);

    if (withSuffix) {
        output = locale.pastFuture(+this, output);
    }

    return locale.postformat(output);
}

var abs$1 = Math.abs;

function sign(x) {
    return ((x > 0) - (x < 0)) || +x;
}

function toISOString$1() {
    // for ISO strings we do not use the normal bubbling rules:
    //  * milliseconds bubble up until they become hours
    //  * days do not bubble at all
    //  * months bubble up until they become years
    // This is because there is no context-free conversion between hours and days
    // (think of clock changes)
    // and also not between days and months (28-31 days per month)
    if (!this.isValid()) {
        return this.localeData().invalidDate();
    }

    var seconds = abs$1(this._milliseconds) / 1000;
    var days         = abs$1(this._days);
    var months       = abs$1(this._months);
    var minutes, hours, years;

    // 3600 seconds -> 60 minutes -> 1 hour
    minutes           = absFloor(seconds / 60);
    hours             = absFloor(minutes / 60);
    seconds %= 60;
    minutes %= 60;

    // 12 months -> 1 year
    years  = absFloor(months / 12);
    months %= 12;


    // inspired by https://github.com/dordille/moment-isoduration/blob/master/moment.isoduration.js
    var Y = years;
    var M = months;
    var D = days;
    var h = hours;
    var m = minutes;
    var s = seconds ? seconds.toFixed(3).replace(/\.?0+$/, '') : '';
    var total = this.asSeconds();

    if (!total) {
        // this is the same as C#'s (Noda) and python (isodate)...
        // but not other JS (goog.date)
        return 'P0D';
    }

    var totalSign = total < 0 ? '-' : '';
    var ymSign = sign(this._months) !== sign(total) ? '-' : '';
    var daysSign = sign(this._days) !== sign(total) ? '-' : '';
    var hmsSign = sign(this._milliseconds) !== sign(total) ? '-' : '';

    return totalSign + 'P' +
        (Y ? ymSign + Y + 'Y' : '') +
        (M ? ymSign + M + 'M' : '') +
        (D ? daysSign + D + 'D' : '') +
        ((h || m || s) ? 'T' : '') +
        (h ? hmsSign + h + 'H' : '') +
        (m ? hmsSign + m + 'M' : '') +
        (s ? hmsSign + s + 'S' : '');
}

var proto$2 = Duration.prototype;

proto$2.isValid        = isValid$1;
proto$2.abs            = abs;
proto$2.add            = add$1;
proto$2.subtract       = subtract$1;
proto$2.as             = as;
proto$2.asMilliseconds = asMilliseconds;
proto$2.asSeconds      = asSeconds;
proto$2.asMinutes      = asMinutes;
proto$2.asHours        = asHours;
proto$2.asDays         = asDays;
proto$2.asWeeks        = asWeeks;
proto$2.asMonths       = asMonths;
proto$2.asYears        = asYears;
proto$2.valueOf        = valueOf$1;
proto$2._bubble        = bubble;
proto$2.clone          = clone$1;
proto$2.get            = get$2;
proto$2.milliseconds   = milliseconds;
proto$2.seconds        = seconds;
proto$2.minutes        = minutes;
proto$2.hours          = hours;
proto$2.days           = days;
proto$2.weeks          = weeks;
proto$2.months         = months;
proto$2.years          = years;
proto$2.humanize       = humanize;
proto$2.toISOString    = toISOString$1;
proto$2.toString       = toISOString$1;
proto$2.toJSON         = toISOString$1;
proto$2.locale         = locale;
proto$2.localeData     = localeData;

// Deprecations
proto$2.toIsoString = deprecate('toIsoString() is deprecated. Please use toISOString() instead (notice the capitals)', toISOString$1);
proto$2.lang = lang;

// Side effect imports

// FORMATTING

addFormatToken('X', 0, 0, 'unix');
addFormatToken('x', 0, 0, 'valueOf');

// PARSING

addRegexToken('x', matchSigned);
addRegexToken('X', matchTimestamp);
addParseToken('X', function (input, array, config) {
    config._d = new Date(parseFloat(input, 10) * 1000);
});
addParseToken('x', function (input, array, config) {
    config._d = new Date(toInt(input));
});

// Side effect imports


hooks.version = '2.20.1';

setHookCallback(createLocal);

hooks.fn                    = proto;
hooks.min                   = min;
hooks.max                   = max;
hooks.now                   = now;
hooks.utc                   = createUTC;
hooks.unix                  = createUnix;
hooks.months                = listMonths;
hooks.isDate                = isDate;
hooks.locale                = getSetGlobalLocale;
hooks.invalid               = createInvalid;
hooks.duration              = createDuration;
hooks.isMoment              = isMoment;
hooks.weekdays              = listWeekdays;
hooks.parseZone             = createInZone;
hooks.localeData            = getLocale;
hooks.isDuration            = isDuration;
hooks.monthsShort           = listMonthsShort;
hooks.weekdaysMin           = listWeekdaysMin;
hooks.defineLocale          = defineLocale;
hooks.updateLocale          = updateLocale;
hooks.locales               = listLocales;
hooks.weekdaysShort         = listWeekdaysShort;
hooks.normalizeUnits        = normalizeUnits;
hooks.relativeTimeRounding  = getSetRelativeTimeRounding;
hooks.relativeTimeThreshold = getSetRelativeTimeThreshold;
hooks.calendarFormat        = getCalendarFormat;
hooks.prototype             = proto;

// currently HTML5 input type only supports 24-hour formats
hooks.HTML5_FMT = {
    DATETIME_LOCAL: 'YYYY-MM-DDTHH:mm',             // <input type="datetime-local" />
    DATETIME_LOCAL_SECONDS: 'YYYY-MM-DDTHH:mm:ss',  // <input type="datetime-local" step="1" />
    DATETIME_LOCAL_MS: 'YYYY-MM-DDTHH:mm:ss.SSS',   // <input type="datetime-local" step="0.001" />
    DATE: 'YYYY-MM-DD',                             // <input type="date" />
    TIME: 'HH:mm',                                  // <input type="time" />
    TIME_SECONDS: 'HH:mm:ss',                       // <input type="time" step="1" />
    TIME_MS: 'HH:mm:ss.SSS',                        // <input type="time" step="0.001" />
    WEEK: 'YYYY-[W]WW',                             // <input type="week" />
    MONTH: 'YYYY-MM'                                // <input type="month" />
};

return hooks;

})));

/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(272)(module)))

/***/ }),
/* 2 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function(jQuery) {var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*!
 * Copyright 2013 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANT�?AS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 */

/*global define */
/*global jQuery */

(function (factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(17), __webpack_require__(191)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		factory(jQuery);
	}
})(function ($) {

	// NO MODIFICAR: (AUTOGENERADO)
	var rup_version = '3.6.0';

	jQuery.migrateMute = true;

	/**
   * jQuery definition to anchor JsDoc comments.
   *
   * @see http://jquery.com/
   * @name jQuery
   * @namespace jQuery
   */

	/**
   * jQuery object type
   * @namespace jQuery.rup
   * @memberOf jQuery
   */

	/**
   * The built in string object.
   * @external String
   * @see {@link https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/String|String}
   */

	/**
   * The File interface provides information about files and allows to access their content.
   * @typedef File
   * @see {@link https://developer.mozilla.org/en-US/docs/Web/API/File|File}
   */

	/**
   * A Blob object represents a file-like object of immutable, raw data. Blobs represent data that isn't necessarily in a JavaScript-native format.
   * @typedef Blob
   * @see {@link https://developer.mozilla.org/en-US/docs/Web/API/Blob|Blob}
   */

	/**
   * jQuery object type.
   * @typedef {object} jQuery
   */

	/**
   * Selector de jQuery para referenciar elementos del DOM.
   * @typedef {object} Selector
   * @see {@link http://api.jquery.com/Types/#Selector|Selector}
   */

	/**
   * jQuery Event type object.
   * @typedef {object} Event
   */

	/**
   * Elemento del Document Object Model (DOM).
   * @typedef {object} Element
   */

	/**
   * Tipo de dato entero.
   * @typedef {number} Integer
   */

	String.prototype.capitalize = function () {
		return this.charAt(0).toUpperCase() + this.slice(1);
	};

	$.extend({
		set_uda_ajax_mode_on: function set_uda_ajax_mode_on() {

			// En caso de que la función $.ajax no haya sido sustituida aún.
			if ($.ajax !== $.rup_ajax) {
				// Almacenamos la función original $.ajax en $.ajaxUDA para poder restablecerla posteriormente.
				$.ajaxUDA = $.ajax;
				// Sustituimos la función $.ajax por la función $.rup_ajax.
				$.ajax = $.rup_ajax;
			}
		},
		// Llamada ajax utilizada por los componentes RUP
		rup_ajax: function rup_ajax(options) {

			// Configuracion por defecto
			var defaults = {
				cache: false,
				error: null
			},
			    rup_ajax_settings = $.extend({}, defaults, options),
			    error_default,
			    error_user,
			    complete_user,
			    complete_default;

			// Callback de error especificado en la llamada a rup_ajax
			error_user = rup_ajax_settings.error;

			// Funcion error generica
			error_default = function error_default(xhr, textStatus, errorThrown) {

				var errorText = $.rup.rupAjaxDefaultError(xhr, textStatus, errorThrown);

				// Si se ha producido un error de los tratados lo mostramos
				if (error_user != null) {
					$(error_user(xhr, textStatus, errorThrown));
				} else {
					if (errorText) {
						$.rup.showErrorToUser(errorText);
					}
				}
			};

			// Callback de error especificado en la llamada a rup_ajax
			complete_user = rup_ajax_settings.complete;

			// Function complete generica
			complete_default = function complete_default(xhr, textStatus) {

				// Restablecemos la función $.ajax original.
				if ($.ajax === $.rup_ajax && $.ajaxUDA !== $.rup_ajax) {
					$.ajax = $.ajaxUDA;
				}
				// Se ejecuta el callback complete especificado por el usuario.
				if (complete_user != null) {
					complete_user(xhr, textStatus);
				}
			};

			// Asociamos las funciones a las propiedades que van a utilizarse en la peticion AJAX
			rup_ajax_settings.complete = complete_default;
			rup_ajax_settings.error = error_default;

			//Se valida la presencia de portal y, llegados al caso, se adecuan las llamadas ajax para trabajar con portales
			rup_ajax_settings.url = $.rup_utils.setNoPortalParam(rup_ajax_settings.url);

			// Se realiza la llamada ajax
			if (typeof $.ajaxUDA === 'function') {
				return $.ajaxUDA(rup_ajax_settings);
			} else {
				return $.ajax(rup_ajax_settings);
			}
		}
	});

	//Se crea el objeto base, que alberga toda la metódica y gestión de los componentes RUP, dentro de la jerarquía de JQuery
	$.rup = $.rup || {};

	$.extend($.rup, {
		_uaMatch: function _uaMatch(ua) {
			ua = ua.toLowerCase();

			var match = /(chrome)[ \/]([\w.]+)/.exec(ua) || /(webkit)[ \/]([\w.]+)/.exec(ua) || /(opera)(?:.*version|)[ \/]([\w.]+)/.exec(ua) || /(msie) ([\w.]+)/.exec(ua) || ua.indexOf('compatible') < 0 && /(mozilla)(?:.*? rv:([\w.]+)|)/.exec(ua) || [];

			return {
				browser: match[1] || '',
				version: match[2] || '0'
			};
		}
	});

	var matched = $.rup._uaMatch(navigator.userAgent);
	var browser = {};

	if (matched.browser) {
		browser[matched.browser] = true;
		browser.version = matched.version;
	}

	// Chrome is Webkit, but Webkit is also Safari.
	if (browser.chrome) {
		browser.webkit = true;
	} else if (browser.webkit) {
		browser.safari = true;
	}

	$.rup._browser = browser;

	$.extend($.rup, {
		i18n: {},
		appResources: {}, //fichero de recursos de la aplicacion
		lang: null,
		version: rup_version,
		//Funcion que rupera el idioma del navegador por defecto
		getBrowserLenguage: function getBrowserLenguage() {
			return (navigator.language || navigator.userLanguage).split('-')[0].toLowerCase();
		},
		browser: {
			version: $.rup._browser.version,
			versionNumber: $.isNumeric($.rup._browser.version) ? parseInt($.rup._browser.version) : undefined,
			isIE: /Trident\//.test(navigator.userAgent),
			isSafari: $.rup._browser.safari && $.rup._browser.webkit ? true : false,
			isChrome: $.rup._browser.safari && $.rup._browser.webkit ? true : false,
			isFF: $.rup._browser.mozilla ? true : false,
			isOpera: $.rup._browser.opera ? true : false,
			xhrFileUploadSupport: new XMLHttpRequest().upload !== undefined ? true : false
		},

		/**********/
		/** i18n **/
		/**********/
		//Funcion encargada de recargar, segun idioma definido en rup.lang, los literales a presentar en la pagina
		setLiterals: function setLiterals(lang) {
			if (lang !== undefined && lang !== null && lang !== '') {
				$.rup.lang = lang;
			}
			//Peticion ajax destinada a cargar el fichero  JSon de literales
			$.rup_ajax({
				url: $.rup.RUP + '/resources/rup.i18n_' + $.rup.lang + '.json',
				dataType: 'json',
				type: 'GET',
				async: false,
				contentType: 'application/x-www-form-urlencoded; charset=UTF-8',
				success: function success(data) {
					//Se cargan los literales generales de la aplicacion en RUP
					$.rup.i18n.base = data;
					//Se cargan los literales de la tabla por separado (consecuencia de la naturalza de JqGrid)
					$.jgrid = {};
					$.extend($.jgrid, data.rup_table);
					$.jgrid.formatter.date.S = new Function('j', data.rup_table.formatter.date.S);
				},
				error: function error(XMLHttpRequest, textStatus) {
					//tratamiento de error
					alert('Se ha producido un error en el parseo del fichero JSON de literales => ' + textStatus + '.\n\n' + 'Error devuelto:\n' + textStatus + ': ' + XMLHttpRequest.status + ' - ' + XMLHttpRequest.statusText);
				}
			});
		},
		//Funcion encargada de cargar el fichero i18n de la aplicación (síncrono)
		getFile_i18n: function getFile_i18n() {
			//Peticion ajax destinada a devolver el fichero JSON indicado
			$.rup_ajax({
				url: $.rup.APP_STATICS + '/resources/' + $.rup.WAR_NAME + '.i18n_' + $.rup.lang + '.json',
				dataType: 'json',
				type: 'GET',
				async: false,
				contentType: 'application/x-www-form-urlencoded; charset=UTF-8',
				success: function success(data) {
					//se carga la respuesta del servidor en la estructura I18n de RUP
					$.rup.i18n.app = data;
				},
				error: function error(XMLHttpRequest, textStatus) {
					alert('Se ha producido un error en el parseo del fichero JSON de literales de la aplicación => ' + textStatus + '.\n\n' + 'Error devuelto:\n' + textStatus + ': ' + XMLHttpRequest.status + ' - ' + XMLHttpRequest.statusText);
				}
			});
		},
		//Funcion encargada de cargar el fichero de la aplicación especificado (síncrono)
		getFile: function getFile(file) {
			if (file === undefined && file === null && file === '') {
				$.rup.errorGestor('No se ha definido el fichero a cargar');
			} else {
				if (!$.rup.i18n[file]) {

					//Peticion ajax destinada a devolver el fichero JSON indicado
					$.rup_ajax({
						url: $.rup.APP_STATICS + '/resources/' + file + '.json',
						dataType: 'json',
						type: 'GET',
						async: false,
						contentType: 'application/x-www-form-urlencoded; charset=UTF-8',
						success: function success(data) {
							//se carga la respuesta del servidor en la estructura I18n de RUP
							$.rup.i18n[file] = data;
						},
						error: function error(XMLHttpRequest, textStatus, errorThrown) {
							$.rup.errorGestor('Se ha producido un error en el parseo del fichero JSON de la aplicación => ' + textStatus + '.<br>' + 'Error devuelto:<br>' + errorThrown);
						}
					});
				}
			}
		},

		//Funcion encargada de devolver el literal obtenido de estructura JSON (en caso de error devuelve el literal con formato especial)
		i18nParse: function i18nParse(properties, i18nCaption, defaultValue) {
			if (i18nCaption !== undefined && i18nCaption !== null && i18nCaption !== '') {
				var i18nCaptionArr = i18nCaption.split('.'),
				    i18nValue = properties;
				for (var i = 0; i < i18nCaptionArr.length; i++) {
					//Navegar por las ramas JSON
					if (!$.isEmptyObject(i18nValue)) {
						i18nValue = i18nValue[i18nCaptionArr[i]]; //Existe objeto -> navegar
					} else {
						if (defaultValue === undefined || defaultValue === null || defaultValue === '') {
							i18nValue = i18nCaption; //No existe objeto -> devolver clave
						} else {
							i18nValue = defaultValue; //No existe objeto -> devolver valor recibido por parametro
						}
						break;
					}
				}
				return i18nValue == undefined ? i18nCaption : i18nValue;
			} else {
				return 'null_i18nCaption'; //retorno si no se recibe clave a buscar
			}
		},
		//Funcion encargada de devolver el literal obtenido de estructura JSON (en caso de error devuelve el literal con formato especial)
		i18nTemplate: function i18nTemplate(properties, i18nCaption) {
			var template = jQuery.rup.i18nParse(properties, i18nCaption),
			    args = $.makeArray(arguments).slice(2);

			if (template === undefined) {
				template = '';
			}
			return template.replace(/\{(\d+)\}/g, function (m, i) {
				return args[i];
			});
		},
		/**********/

		//Funcion encargada de presentar los errores
		errorGestor: function errorGestor(message) {
			$.rup_messages('msgError', {
				title: $.rup.i18nParse($.rup.i18n.base, 'rup_global.developerError'),
				message: '<p>' + message + '</p>'
			});

			throw message;
		},
		//Funcion encargada de hacer las inicializaciones basicas de RUP
		iniRup: function iniRup() {

			//Inicializar variables de ficheros de recuros (rup y app)
			$.rup.i18n.app = {};
			$.rup.i18n.base = {};

			//retrocompatibilidad
			if (!window.LOCALE_COOKIE_NAME) {
				LOCALE_COOKIE_NAME = 'language';
			}
			if (!window.LOCALE_PARAM_NAME) {
				LOCALE_PARAM_NAME = 'locale';
			}

			//Se cargan las variables generales del servidor (convertir variables js a variables internas de rup)
			$.rup.APP_RESOURCES = APP_RESOURCES;
			$.rup.APP_STATICS = STATICS + '/' + APP_RESOURCES;
			$.rup.CTX_PATH = CTX_PATH;
			$.rup.RUP = RUP;
			$.rup.STATICS = STATICS;
			$.rup.WAR_NAME = WAR_NAME;
			//model
			$.rup.AVAILABLE_LANGS = AVAILABLE_LANGS;
			$.rup.AVAILABLE_LANGS_ARRAY = $.map($.rup.AVAILABLE_LANGS.split(','), function (elem) {
				return elem.replace(/^\s*|\s*$/g, '');
			});
			$.rup.LAYOUT = LAYOUT;
			//mvc-config.xml
			$.rup.LOCALE_COOKIE_NAME = LOCALE_COOKIE_NAME;
			$.rup.LOCALE_PARAM_NAME = LOCALE_PARAM_NAME;
			//metodos http permitidos en la emulacion xhr para el uso con iframes
			$.rup.IFRAME_ONLY_SUPPORTED_METHODS = ['GET', 'POST'];

			//Borrar las variables javascript externas
			// delete APP_RESOURCES;
			// delete CTX_PATH;
			// delete RUP;
			// delete STATICS;
			// delete WAR_NAME;
			//model
			// delete AVAILABLE_LANGS;
			// delete LAYOUT;
			//mvc-config.xml
			// delete LOCALE_COOKIE_NAME;
			// delete LOCALE_PARAM_NAME;

			var cookie = $.rup_utils.get($.rup.LOCALE_COOKIE_NAME);
			if (cookie !== null && cookie !== '') {
				//si tenemos cookie con el lenguaje
				if ($.inArray(cookie, $.rup.AVAILABLE_LANGS_ARRAY) !== -1) {
					this.lang = cookie;
				} else {
					//retrocompatibilidad (MvcInterceptor genera correctamente la cookie, pero en versiones anteriores no)
					alert('La \'cookie\' de idioma (' + $.rup.LOCALE_COOKIE_NAME + ') no se corresponde con los idiomas soportados.\n\nLa página no se mostrará correctamente.');
					$.rup._avoidRUPFails();
					return false;
				}
			} else {
				alert('No se ha encontrado la \'cookie\' de idioma (' + $.rup.LOCALE_COOKIE_NAME + ') requerida por UDA.\nRevise la configuración del navegador.\n\nLa página no se mostrará correctamente.');
				$.rup._avoidRUPFails();
				return false;
			}

			//Se cargan los literales por defecto
			$.rup.setLiterals();
			//Carga de ficheros de literales de la apliaccion
			if ($.rup.WAR_NAME !== '') {
				$.rup.getFile_i18n();
			}
		},
		//Función encargada de cargar variables por defecto si no se han cargado los literales (ej. cookies deshabilitadas)
		//NOTA: El que se entre en la función indica mala configuración/error en la aplicación
		_avoidRUPFails: function _avoidRUPFails() {
			//Forzar carga formato fecha si no se ha cargado (evitar fallos)
			var dateFormat = $.rup.i18nParse($.rup.i18n.base, 'rup_date.dateFormat');
			if (dateFormat === 'rup_date.dateFormat') {
				$.rup.i18n.base['rup_date'] = {
					dateFormat: 'dd/mm/yy'
				};
			}
			$.jgrid = {
				formatter: {
					integer: {}
				}
			};
		},
		//Método gestor de invocación de un método expuesto por un componente o la creación del mismo (asociada a la metódica de invocación y gestión de los métodos públicos de un componente)
		getAccessor: function getAccessor(obj, objName, expr) {
			if (typeof expr === 'string') {
				fn = obj[expr];
				if (fn === undefined) {
					$.rup.errorGestor(objName + ' - No Existe el método "' + expr + '"  en el patrón.');
				} else {
					return fn;
				}
			} else {
				if (typeof expr === 'function') {
					$.rup.errorGestor(objName + ' - No es posible pasar funciones al patrón.');
				}
			}
			return undefined;
		},
		rupAjaxDefaultError: function rupAjaxDefaultError(xhr, textStatus, errorThrown) {

			// Evaluamos el error que se ha producido
			var errorText = null;

			if (xhr.status == 0) {
				errorText = $.rup.i18nParse($.rup.i18n.base, 'rup_ajax.httpStatus0');
			} else if (xhr.status == 401) {
				errorText = $.rup.i18nParse($.rup.i18n.base, 'rup_ajax.httpStatus401');
			} else if (xhr.status == 404) {
				errorText = $.rup.i18nParse($.rup.i18n.base, 'rup_ajax.httpStatus404');
			} else if (xhr.status == 500) {
				errorText = $.rup.i18nParse($.rup.i18n.base, 'rup_ajax.httpStatus500');
			} else if (xhr.status == 503) {
				errorText = $.rup.i18nParse($.rup.i18n.base, 'rup_ajax.httpStatus503');
			}
			//Excepción
			else if (xhr.status == 406) {
					//Código de error de UDA
					var obj = '';
					try {
						obj = JSON.parse(xhr.responseText);
					} catch (error) {
						errorText = xhr.responseText;
					}
				} else if (xhr.status == 413) {
					// Error de Too Large Entity
					var obj = '';
					try {
						obj = JSON.parse(xhr.responseText);
						errorText = obj.rupFeedback.message.label;
					} catch (error) {
						errorText = xhr.responseText;
					}
				}

			return errorText;
		},
		//Función encargada de crear los patrones de RUP que se alberguen en el componente de JQuery directamente
		//La estructura creada, proporciona proteccion a los metodos publicos y privados
		rupObjectConstructor: function rupObjectConstructor(name, object) {

			//Se crea el nuevo gestor del Pótron
			if ($[name] === undefined) {
				$[name] = function (options) {
					var options = options,
					    isMethodCall = typeof options === 'string',
					    args = $.makeArray(arguments).slice(1),
					    returnValue = this;

					// prevent calls to internal methods
					if (isMethodCall && options.charAt(0) === '_') {
						return returnValue;
					}

					if (isMethodCall) {
						if (options !== 'extend') {
							var instance = $.isEmptyObject($.data(object)) ? $.data(object, object) : $.data(object),
							    methodValue = instance && $.isFunction(instance[options]) ? instance[options].apply(instance, args) : 'no-function';

							if (methodValue === 'no-function') {
								return false;
							} else {
								returnValue = methodValue;
							}
						} else {
							object = $.extend.apply(null, [true, object].concat(args[0]));
						}
					} else {
						var instance = $.isEmptyObject($.data(object)) ? $.data(object, object) : $.data(object);
						if (instance && object['_init'] !== undefined && object['_init'] !== null) {
							instance._init($.makeArray(arguments));
						}
					}
					return returnValue;
				};
			}
		},
		//Funcion encargada de crear los patrones de RUP que usen el selector de JQuery.
		//La estructura creada, proporciona proteccion a los metodos publicos y privados
		rupSelectorObjectConstructor: function rupSelectorObjectConstructor(name, object) {

			//Se crea el nuevo gestor del Patrón
			if ($.fn[name] === undefined) {
				$.fn[name] = function (options) {
					var options = options,
					    isMethodCall = typeof options === 'string',
					    args = $.makeArray(arguments).slice(1),
					    returnValue = this;

					// prevent calls to internal methods
					if (isMethodCall && options.charAt(0) === '_') {
						return returnValue;
					}

					if (isMethodCall) {
						if (options !== 'extend') {
							var instance = $.extend(this, object),
							    methodValue = instance && $.isFunction(instance[options]) ? instance[options].apply(instance, args) : 'no-function';

							if (methodValue === 'no-function') {
								return false;
							} else {
								returnValue = methodValue;
							}
						} else {
							object = $.fn.extend.apply(null, [true, object].concat(args[0]));
						}
					} else {
						var instance = $.extend(this, object);
						if (instance && object['_init'] !== undefined && object['_init'] !== null) {
							instance._init($.makeArray(arguments));
						}
					}
					return returnValue;
				};
			}
		},
		//Funcion encargada de mostrar mediante el correspondiente canal el mensaje de error.
		//La estructura creada, proporciona proteccion a los metodos publicos y privados
		showErrorToUser: function showErrorToUser(errorText) {

			if (errorText != null && errorText !== '') {

				// Se comprueba si existe un dialog visible con una region de rup_feedbak
				var dialog_feedbacks = $('.ui-dialog:visible .rup-feedback'),
				    feedbacks = dialog_feedbacks.length !== 0 ? dialog_feedbacks : $('.rup-feedback');

				// Se comprueba si existe un rup_feedback en la pagina
				if (feedbacks.length != 0) {

					var feedback_props = {
						delay: null
					},

					//Si existen rup_feedbacks cogemos el primero
					feedback_principal = $('#' + feedbacks[0].id);

					// Mostramos el error en el feedback
					feedback_principal.rup_feedback('option', feedback_props);
					feedback_principal.rup_feedback('set', errorText, 'error');
					feedback_principal.rup_feedback('show');
				} else {
					// Si no hay feedback definido mostramos un mensaje
					$.rup_messages('msgError', {
						title: $.rup.i18nParse($.rup.i18n.base, 'rup_ajax.errorTitle'),
						message: errorText
					});
				}
			}
		}
	});

	//Almacenar y restaurar eventos
	$.fn.extend({
		storeEvents: function storeEvents() {
			this.each(function () {
				$(this).data('storedEvents', $.extend(true, {}, $._data($(this)[0], 'events')));
			});
			$(this).unbind();
			return this;
		},
		restoreEvents: function restoreEvents() {
			this.each(function () {
				var events = $.data(this, 'storedEvents');
				if (events) {
					$(this).unbind();
					for (var type in events) {
						for (var handler in events[type]) {
							$.event.add(this, type, events[type][handler], events[type][handler].data);
						}
					}
				}
			});
			return this;
		}
	});

	/*
   * EVENTOS PROPIOS
   * mousestop: Detecta cuando el ratón para su desplazamiento
   */
	$.fn.mousestop = {};
	$.fn.mousestop.defaults = {
		delay: 300
	};

	$.event.special.mousestop = {
		setup: function setup(data) {
			var self = this,
			    $self = $(this);

			$self.data('mousestop', $.extend(true, {}, $.fn.mousestop.defaults, data));

			$self.on({
				'mouseenter.rup_mousestop': mouseenterHandler,
				'mouseleave.rup_mousestop': mouseleaveHandler,
				'mousemove.rup_mousestop': mousemoveHandler
			});
		},
		teardown: function teardown() {
			$(this).removeData('mousestop').off('.rup_mousestop');
		}
	};

	function mouseenterHandler(event) {
		var self = this,
		    $self = $(this);
		clearTimeout(self.timeout);
	}

	function mouseleaveHandler(event) {
		var self = this,
		    $self = $(this);
		clearTimeout(self.timeout);
	}

	function mousemoveHandler(event) {
		var self = this,
		    $self = $(this);

		clearTimeout(self.timeout);
		self.timeout = setTimeout(function () {
			$self.trigger('mousestop', event);
		}, $self.data('mousestop').delay);
	}

	// Control de teclas especiales Ctrl y Shift

	jQuery('body').on({
		'keydown.rup': function keydownRup(event) {
			var $body = jQuery('body'),
			    ret;

			switch (event.which) {
				case 16:
					if ($body.data('tmp.multiselect.shiftPressed') !== true) {
						$body.data('tmp.multiselect.shiftPressed', true);
						ret = $body.triggerHandler('rup_shiftKeyDown');
						if (ret === false) {
							event.preventDefault();
							return false;
						}
					}
					break;
				case 17:
					if ($body.data('tmp.multiselect.ctrlPressed') !== true) {
						$body.data('tmp.multiselect.ctrlPressed', true);
						ret = $body.triggerHandler('rup_ctrlKeyDown');
						if (ret === false) {
							event.preventDefault();
							return false;
						}
					}
					break;
			}
		},
		'keyup.rup': function keyupRup(event) {
			var $body = jQuery('body'),
			    ret;

			switch (event.which) {
				case 16:
					if ($body.data('tmp.multiselect.shiftPressed') !== false) {
						$body.data('tmp.multiselect.shiftPressed', false);
						ret = $body.triggerHandler('rup_shiftKeyUp');
						if (ret === false) {
							return false;
						}
					}
					break;
				case 17:
					if ($body.data('tmp.multiselect.ctrlPressed') !== false) {
						$body.data('tmp.multiselect.ctrlPressed', false);
						ret = $body.triggerHandler('rup_ctrlKeyUp');
						if (ret === false) {
							return false;
						}
					}
					break;
			}
		}
	});

	jQuery.extend($.rup, {
		isCtrlPressed: function isCtrlPressed() {
			return jQuery('body').data('tmp.multiselect.ctrlPressed') === true;
		},
		isShiftPressed: function isShiftPressed() {
			return jQuery('body').data('tmp.multiselect.shiftPressed') === true;
		}
	});

	//Ejemplo de extension de la funcion de inicio
	//$.extend($.rup.iniRup, console.log("mundo")) ;

	//Inicializacion de las funciones de gestion de RUP en general
	$.rup.iniRup();
});
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))

/***/ }),
/* 3 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;var _typeof = typeof Symbol === "function" && typeof Symbol.iterator === "symbol" ? function (obj) { return typeof obj; } : function (obj) { return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj; };

(function (factory) {
    if (true) {

        // AMD. Register as an anonymous module.
        !(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(26)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
    } else {

        // Browser globals
        factory(Handlebars);
    }
})(function (Handlebars) {
    this["Rup"] = this["Rup"] || {};
    this["Rup"]["Templates"] = this["Rup"]["Templates"] || {};
    this["Rup"]["Templates"]["rup"] = this["Rup"]["Templates"]["rup"] || {};
    this["Rup"]["Templates"]["rup"]["button"] = this["Rup"]["Templates"]["rup"]["button"] || {};
    this["Rup"]["Templates"]["rup"]["button"]["dropdownButton"] = Handlebars.template({ "compiler": [7, ">= 4.0.0"], "main": function main(container, depth0, helpers, partials, data) {
            var helper;

            return "<button id=" + container.escapeExpression((helper = (helper = helpers.id || (depth0 != null ? depth0.id : depth0)) != null ? helper : helpers.helperMissing, typeof helper === "function" ? helper.call(depth0 != null ? depth0 : {}, { "name": "id", "hash": {}, "data": data }) : helper)) + " type=\"button\" class=\"rup-dropdown-button\">\r\n  <i class=\"fa fa-caret-down\" aria-hidden=\"true\"></i>\r\n  <span class=\"invisible\"></span>\r\n</button>\r\n";
        }, "useData": true });
    this["Rup"]["Templates"]["rup"]["button"]["mbutton-container"] = Handlebars.template({ "compiler": [7, ">= 4.0.0"], "main": function main(container, depth0, helpers, partials, data) {
            var helper,
                alias1 = depth0 != null ? depth0 : {},
                alias2 = helpers.helperMissing,
                alias3 = "function",
                alias4 = container.escapeExpression;

            return "<div id=\"" + alias4((helper = (helper = helpers.id || (depth0 != null ? depth0.id : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "id", "hash": {}, "data": data }) : helper)) + "\" class=\"" + alias4((helper = (helper = helpers.classes || (depth0 != null ? depth0.classes : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "classes", "hash": {}, "data": data }) : helper)) + "\">\r\n  <ul role=\"menu\" aria-activedescendant=\"active-menuitem\" aria-labelledby=\"active-menuitem\">\r\n    <li style=\"display: block;\">\r\n      <button type=\"button\" class=\"rup-toolbar_button ui-button ui-corner-all ui-widget rup-button rup-toolbar_menuButtonElement\" id=\"toolbar##mbuton1##nuevo\">\r\n        <span class=\"ui-button-icon ui-icon nuevo\"></span>\r\n        <span class=\"ui-button-icon-space\"></span>\r\n        <span class=\"rup-ui-button-text\">" + alias4((helpers.i18n || depth0 && depth0.i18n || alias2).call(alias1, "rup_button.new", { "name": "i18n", "hash": {}, "data": data })) + "</span>\r\n      </button>\r\n    </li>\r\n  </ul>\r\n</div>\r\n";
        }, "useData": true });
    this["Rup"]["Templates"]["rup"]["button"]["mbutton"] = Handlebars.template({ "compiler": [7, ">= 4.0.0"], "main": function main(container, depth0, helpers, partials, data) {
            var helper,
                alias1 = depth0 != null ? depth0 : {},
                alias2 = helpers.helperMissing,
                alias3 = "function",
                alias4 = container.escapeExpression;

            return "<a id=\"" + alias4((helper = (helper = helpers.id || (depth0 != null ? depth0.id : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "id", "hash": {}, "data": data }) : helper)) + "\"\r\n  class=\"rup-toolbar_menuButton ui-button ui-corner-all ui-widget rup-toolbar_menuButtonSlided\"\r\n  role=\"button\"\r\n  href=\"#\">\r\n  " + alias4((helper = (helper = helpers.label || (depth0 != null ? depth0.label : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "label", "hash": {}, "data": data }) : helper)) + "\r\n  <span class=\"ui-button-icon-space\"></span>\r\n  <span class=\"" + alias4((helper = (helper = helpers.iconClasses || (depth0 != null ? depth0.iconClasses : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "iconClasses", "hash": {}, "data": data }) : helper)) + "\" aria-hidden=\"true\"></span>\r\n</a>\r\n";
        }, "useData": true });
    this["Rup"]["Templates"]["rup"]["dashboard"] = this["Rup"]["Templates"]["rup"]["dashboard"] || {};
    this["Rup"]["Templates"]["rup"]["dashboard"]["item"] = Handlebars.template({ "1": function _(container, depth0, helpers, partials, data) {
            var helper;

            return " data-gs-min-width=\"" + container.escapeExpression((helper = (helper = helpers.minWidth || (depth0 != null ? depth0.minWidth : depth0)) != null ? helper : helpers.helperMissing, typeof helper === "function" ? helper.call(depth0 != null ? depth0 : {}, { "name": "minWidth", "hash": {}, "data": data }) : helper)) + "\" ";
        }, "3": function _(container, depth0, helpers, partials, data) {
            var helper;

            return " data-gs-max-width=\"" + container.escapeExpression((helper = (helper = helpers.maxWidth || (depth0 != null ? depth0.maxWidth : depth0)) != null ? helper : helpers.helperMissing, typeof helper === "function" ? helper.call(depth0 != null ? depth0 : {}, { "name": "maxWidth", "hash": {}, "data": data }) : helper)) + "\" ";
        }, "5": function _(container, depth0, helpers, partials, data) {
            var helper;

            return " data-gs-min-height=\"" + container.escapeExpression((helper = (helper = helpers.minHeight || (depth0 != null ? depth0.minHeight : depth0)) != null ? helper : helpers.helperMissing, typeof helper === "function" ? helper.call(depth0 != null ? depth0 : {}, { "name": "minHeight", "hash": {}, "data": data }) : helper)) + "\" ";
        }, "7": function _(container, depth0, helpers, partials, data) {
            var helper;

            return " data-gs-max-height=\"" + container.escapeExpression((helper = (helper = helpers.maxHeight || (depth0 != null ? depth0.maxHeight : depth0)) != null ? helper : helpers.helperMissing, typeof helper === "function" ? helper.call(depth0 != null ? depth0 : {}, { "name": "maxHeight", "hash": {}, "data": data }) : helper)) + "\" ";
        }, "compiler": [7, ">= 4.0.0"], "main": function main(container, depth0, helpers, partials, data) {
            var stack1,
                helper,
                alias1 = depth0 != null ? depth0 : {},
                alias2 = helpers.helperMissing,
                alias3 = "function",
                alias4 = container.escapeExpression;

            return "<div class=\"grid-stack-item\"  \r\n     " + ((stack1 = helpers["if"].call(alias1, depth0 != null ? depth0.minWidth : depth0, { "name": "if", "hash": {}, "fn": container.program(1, data, 0), "inverse": container.noop, "data": data })) != null ? stack1 : "") + "\r\n     " + ((stack1 = helpers["if"].call(alias1, depth0 != null ? depth0.maxWidth : depth0, { "name": "if", "hash": {}, "fn": container.program(3, data, 0), "inverse": container.noop, "data": data })) != null ? stack1 : "") + "\r\n     " + ((stack1 = helpers["if"].call(alias1, depth0 != null ? depth0.minHeight : depth0, { "name": "if", "hash": {}, "fn": container.program(5, data, 0), "inverse": container.noop, "data": data })) != null ? stack1 : "") + "\r\n     " + ((stack1 = helpers["if"].call(alias1, depth0 != null ? depth0.maxHeight : depth0, { "name": "if", "hash": {}, "fn": container.program(7, data, 0), "inverse": container.noop, "data": data })) != null ? stack1 : "") + "\r\n     data-rup-widget-type=\"" + alias4((helper = (helper = helpers.type || (depth0 != null ? depth0.type : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "type", "hash": {}, "data": data }) : helper)) + "\">\r\n\r\n    <div class=\"" + alias4((helper = (helper = helpers.itemClass || (depth0 != null ? depth0.itemClass : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "itemClass", "hash": {}, "data": data }) : helper)) + "\" >\r\n\r\n    </div>\r\n</div>\r\n";
        }, "useData": true });
    this["Rup"]["Templates"]["rup"]["table"] = this["Rup"]["Templates"]["rup"]["table"] || {};
    this["Rup"]["Templates"]["rup"]["table"]["detail"] = this["Rup"]["Templates"]["rup"]["table"]["detail"] || {};
    this["Rup"]["Templates"]["rup"]["table"]["detail"]["navigation"] = this["Rup"]["Templates"]["rup"]["table"]["detail"]["navigation"] || {};
    this["Rup"]["Templates"]["rup"]["table"]["detail"]["navigation"]["bootstrap"] = Handlebars.template({ "compiler": [7, ">= 4.0.0"], "main": function main(container, depth0, helpers, partials, data) {
            var helper,
                alias1 = depth0 != null ? depth0 : {},
                alias2 = helpers.helperMissing,
                alias3 = "function",
                alias4 = container.escapeExpression;

            return "<div id=\"pagination_" + alias4((helper = (helper = helpers.tableId || (depth0 != null ? depth0.tableId : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "tableId", "hash": {}, "data": data }) : helper)) + "\" class=\"rup-table-detail-info\">\r\n  <i class=\"fa fa-list-alt\" aria-hidden=\"true\" title=\"" + alias4((helper = (helper = helpers.resultNumText || (depth0 != null ? depth0.resultNumText : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "resultNumText", "hash": {}, "data": data }) : helper)) + "\"></i>\r\n  <span id=\"rup_table_selectedElements_" + alias4((helper = (helper = helpers.tableId || (depth0 != null ? depth0.tableId : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "tableId", "hash": {}, "data": data }) : helper)) + "\" class=\"rup-table-detail-currentElement\" >\r\n    " + alias4((helper = (helper = helpers.numResult || (depth0 != null ? depth0.numResult : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "numResult", "hash": {}, "data": data }) : helper)) + "\r\n  </span>\r\n</div>\r\n<div id=\"pag_" + alias4((helper = (helper = helpers.tableId || (depth0 != null ? depth0.tableId : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "tableId", "hash": {}, "data": data }) : helper)) + "\" class=\"rup-table-detail-navigation\">\r\n    <button type=\"button\" id=\"first_" + alias4((helper = (helper = helpers.tableId || (depth0 != null ? depth0.tableId : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "tableId", "hash": {}, "data": data }) : helper)) + "\" class=\"btn-sm btn-outline-dark\" alt=\"" + alias4((helper = (helper = helpers.labelFirst || (depth0 != null ? depth0.labelFirst : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "labelFirst", "hash": {}, "data": data }) : helper)) + "\">" + alias4((helper = (helper = helpers.labelFirst || (depth0 != null ? depth0.labelFirst : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "labelFirst", "hash": {}, "data": data }) : helper)) + "</button>\r\n    <button type=\"button\" id=\"back_" + alias4((helper = (helper = helpers.tableId || (depth0 != null ? depth0.tableId : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "tableId", "hash": {}, "data": data }) : helper)) + "\" class=\"btn-sm btn-outline-dark\" alt=\"" + alias4((helper = (helper = helpers.labelPrev || (depth0 != null ? depth0.labelPrev : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "labelPrev", "hash": {}, "data": data }) : helper)) + "\">" + alias4((helper = (helper = helpers.labelPrev || (depth0 != null ? depth0.labelPrev : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "labelPrev", "hash": {}, "data": data }) : helper)) + "</button>\r\n    <button type=\"button\" id=\"forward_" + alias4((helper = (helper = helpers.tableId || (depth0 != null ? depth0.tableId : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "tableId", "hash": {}, "data": data }) : helper)) + "\" class=\"btn-sm btn-outline-dark\" alt=\"" + alias4((helper = (helper = helpers.labelNext || (depth0 != null ? depth0.labelNext : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "labelNext", "hash": {}, "data": data }) : helper)) + "\">" + alias4((helper = (helper = helpers.labelNext || (depth0 != null ? depth0.labelNext : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "labelNext", "hash": {}, "data": data }) : helper)) + "</button>\r\n    <button type=\"button\" id=\"last_" + alias4((helper = (helper = helpers.tableId || (depth0 != null ? depth0.tableId : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "tableId", "hash": {}, "data": data }) : helper)) + "\" class=\"btn-sm btn-outline-dark\" alt=\"" + alias4((helper = (helper = helpers.labelLast || (depth0 != null ? depth0.labelLast : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "labelLast", "hash": {}, "data": data }) : helper)) + "\">" + alias4((helper = (helper = helpers.labelLast || (depth0 != null ? depth0.labelLast : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "labelLast", "hash": {}, "data": data }) : helper)) + "</button>\r\n  </div>\r\n  <div class=\"rup-table-detail-separator separador\"></div>\r\n";
        }, "useData": true });
    this["Rup"]["Templates"]["rup"]["table"]["pager"] = this["Rup"]["Templates"]["rup"]["table"]["pager"] || {};
    this["Rup"]["Templates"]["rup"]["table"]["pager"]["bootstrap"] = Handlebars.template({ "compiler": [7, ">= 4.0.0"], "main": function main(container, depth0, helpers, partials, data) {
            var helper,
                alias1 = depth0 != null ? depth0 : {},
                alias2 = helpers.helperMissing,
                alias3 = "function",
                alias4 = container.escapeExpression;

            return "\r\n  <div id=\"pg_" + alias4((helper = (helper = helpers.id || (depth0 != null ? depth0.id : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "id", "hash": {}, "data": data }) : helper)) + "_pager\" class=\"ui-pager-control rup_table_pager\" role=\"group\">\r\n    <div id=\"" + alias4((helper = (helper = helpers.idPager || (depth0 != null ? depth0.idPager : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "idPager", "hash": {}, "data": data }) : helper)) + "_left\" class=\"pager_left\"></div>\r\n    <div id=\"" + alias4((helper = (helper = helpers.idPager || (depth0 != null ? depth0.idPager : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "idPager", "hash": {}, "data": data }) : helper)) + "_center\" class=\"pager_center\">\r\n      <div id=\"first_" + alias4((helper = (helper = helpers.idPager || (depth0 != null ? depth0.idPager : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "idPager", "hash": {}, "data": data }) : helper)) + "\">\r\n        <a href=\"javascript:void(0)\" class=\"linkPaginacion\">" + alias4((helper = (helper = helpers.firstPageText || (depth0 != null ? depth0.firstPageText : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "firstPageText", "hash": {}, "data": data }) : helper)) + "</a>\r\n      </div>\r\n      <div id=\"prev_" + alias4((helper = (helper = helpers.idPager || (depth0 != null ? depth0.idPager : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "idPager", "hash": {}, "data": data }) : helper)) + "\">\r\n        <a href=\"javascript:void(0)\" class=\"linkPaginacion\">" + alias4((helper = (helper = helpers.prevPageText || (depth0 != null ? depth0.prevPageText : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "prevPageText", "hash": {}, "data": data }) : helper)) + "</a>\r\n      </div>\r\n      <div id=\"next_" + alias4((helper = (helper = helpers.idPager || (depth0 != null ? depth0.idPager : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "idPager", "hash": {}, "data": data }) : helper)) + "\">\r\n        <a href=\"javascript:void(0)\" class=\"linkPaginacion\">" + alias4((helper = (helper = helpers.nextPageText || (depth0 != null ? depth0.nextPageText : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "nextPageText", "hash": {}, "data": data }) : helper)) + "</a>\r\n      </div>\r\n      <div id=\"last_" + alias4((helper = (helper = helpers.idPager || (depth0 != null ? depth0.idPager : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "idPager", "hash": {}, "data": data }) : helper)) + "\">\r\n        <a href=\"javascript:void(0)\" class=\"linkPaginacion\">" + alias4((helper = (helper = helpers.lastPageText || (depth0 != null ? depth0.lastPageText : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "lastPageText", "hash": {}, "data": data }) : helper)) + "</a>\r\n      </div>\r\n\r\n    </div>\r\n    <div id=\"" + alias4((helper = (helper = helpers.table_pager || (depth0 != null ? depth0.table_pager : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "table_pager", "hash": {}, "data": data }) : helper)) + "_right\" class=\"pager_right\">\r\n      <div class=\"ui-paging-info\">" + alias4((helper = (helper = helpers.resultText || (depth0 != null ? depth0.resultText : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "resultText", "hash": {}, "data": data }) : helper)) + "</div>\r\n    </div>\r\n  </div>\r\n";
        }, "useData": true });
    this["Rup"]["Templates"]["rup"]["table"]["pager"]["jqueryui"] = Handlebars.template({ "compiler": [7, ">= 4.0.0"], "main": function main(container, depth0, helpers, partials, data) {
            return "<div id=\"table_pager\" class=\"ui-state-default ui-jqgrid-pager ui-corner-bottom\" dir=\"ltr\" style=\"width: 100%; height: auto;\">\r\n  <div id=\"pg_table_pager\" class=\"ui-pager-control\" role=\"group\">\r\n    <table cellspacing=\"0\" cellpadding=\"0\" border=\"0\" class=\"ui-pg-table\" style=\"width:100%;table-layout:fixed;height:100%;\" role=\"row\">\r\n      <tbody>\r\n        <tr>\r\n          <td id=\"table_pager_left\" align=\"left\" class=\"pager_left\"></td>\r\n          <td id=\"table_pager_center\" align=\"center\" style=\"white-space: pre; width: 305px;\" class=\"pager_center\">\r\n            <table cellspacing=\"0\" cellpadding=\"0\" border=\"0\" style=\"table-layout:auto;\" class=\"ui-pg-table\">\r\n              <tbody>\r\n                <tr>\r\n                  <td id=\"first_table_pager\" class=\"ui-corner-all pagControls ui-state-disabled\">\r\n                    <a href=\"javascript:void(0)\" class=\"linkPaginacion\">Primera Página</a>\r\n                  </td>\r\n                  <td id=\"prev_table_pager\" class=\"ui-corner-all pagControls ui-state-disabled\">\r\n                    <a href=\"javascript:void(0)\" class=\"linkPaginacion\">Anterior</a>\r\n                  </td>\r\n                  <td class=\"ui-pg-button ui-state-disabled pagControls\" style=\"width:4px;\">\r\n                    <span class=\"ui-separator\"></span>\r\n                  </td>\r\n                  <td dir=\"ltr\" class=\"pagControls\">\r\n                    Página\r\n                    <input class=\"ui-pg-input\" type=\"text\" size=\"2\" maxlength=\"7\" value=\"0\" role=\"textbox\" data-hasqtip=\"1\" oldtitle=\"Página actual\" title=\"\" aria-describedby=\"qtip-1\"> de <span id=\"sp_1_table_pager\">100</span>\r\n                  </td>\r\n                  <td class=\"ui-pg-button ui-state-disabled pagControls\" style=\"width:4px;\">\r\n                    <span class=\"ui-separator\"></span>\r\n                  </td>\r\n                  <td id=\"next_table_pager\" class=\"ui-corner-all pagControls\">\r\n                    <a href=\"javascript:void(0)\" class=\"linkPaginacion\">Siguiente</a>\r\n                  </td>\r\n                  <td id=\"last_table_pager\" class=\"ui-corner-all pagControls\">\r\n                    <a href=\"javascript:void(0)\" class=\"linkPaginacion\">Última Página</a>\r\n                  </td>\r\n                  <td dir=\"ltr\" class=\"pagControls\">\r\n                    <select class=\"ui-pg-selbox\" role=\"listbox\" data-hasqtip=\"0\" oldtitle=\"Número de elementos por página\" title=\"\" aria-describedby=\"qtip-0\">\r\n                      <option role=\"option\" value=\"10\" selected=\"selected\">10</option>\r\n                      <option role=\"option\" value=\"20\">20</option>\r\n                      <option role=\"option\" value=\"30\">30</option>\r\n                    </select>\r\n                  </td>\r\n                </tr>\r\n              </tbody>\r\n            </table>\r\n          </td>\r\n          <td id=\"table_pager_right\" align=\"right\" class=\"pager_right\">\r\n            <div dir=\"ltr\" style=\"text-align:right\" class=\"ui-paging-info\">Mostrando 1 - 10 de 1.000</div>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n</div>\r\n";
        }, "useData": true });
    this["Rup"]["Templates"]["rup"]["table"]["pager"]["link"] = this["Rup"]["Templates"]["rup"]["table"]["pager"]["link"] || {};
    this["Rup"]["Templates"]["rup"]["table"]["pager"]["link"]["bootstrap"] = Handlebars.template({ "compiler": [7, ">= 4.0.0"], "main": function main(container, depth0, helpers, partials, data) {
            var helper,
                alias1 = depth0 != null ? depth0 : {},
                alias2 = helpers.helperMissing,
                alias3 = "function",
                alias4 = container.escapeExpression;

            return "<a href=\"javascript:void(0)\" class=\"linkPaginacion\">" + alias4((helper = (helper = helpers.label || (depth0 != null ? depth0.label : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "label", "hash": {}, "data": data }) : helper)) + "</a>\r\n<i class=\"iconPaginacion " + alias4((helper = (helper = helpers.icon || (depth0 != null ? depth0.icon : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "icon", "hash": {}, "data": data }) : helper)) + "\"></i></td>\r\n";
        }, "useData": true });
    this["Rup"]["Templates"]["rup"]["tabs"] = this["Rup"]["Templates"]["rup"]["tabs"] || {};
    this["Rup"]["Templates"]["rup"]["tabs"]["container"] = Handlebars.template({ "compiler": [7, ">= 4.0.0"], "main": function main(container, depth0, helpers, partials, data) {
            return "<ul>\r\n\r\n</ul>\r\n";
        }, "useData": true });
    this["Rup"]["Templates"]["rup"]["tabs"]["subtab"] = Handlebars.template({ "compiler": [7, ">= 4.0.0"], "main": function main(container, depth0, helpers, partials, data) {
            var helper,
                alias1 = depth0 != null ? depth0 : {},
                alias2 = helpers.helperMissing,
                alias3 = "function",
                alias4 = container.escapeExpression;

            return "<div id=" + alias4((helper = (helper = helpers.rupRandomLayerId || (depth0 != null ? depth0.rupRandomLayerId : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "rupRandomLayerId", "hash": {}, "data": data }) : helper)) + " class=\"rupRandomLayerId ssss\">\r\n  <div id=" + alias4((helper = (helper = helpers.id || (depth0 != null ? depth0.id : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "id", "hash": {}, "data": data }) : helper)) + " actualTab=\"" + alias4((helper = (helper = helpers.actualTab || (depth0 != null ? depth0.actualTab : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "actualTab", "hash": {}, "data": data }) : helper)) + "\">\r\n\r\n  </div>\r\n</div>\r\n";
        }, "useData": true });
    this["Rup"]["Templates"]["rup"]["tabs"]["tab"] = Handlebars.template({ "1": function _(container, depth0, helpers, partials, data) {
            return "        <span class=\"ui-icon ui-icon-close\" role=\"presentation\">Remove Tab</span>\r\n";
        }, "compiler": [7, ">= 4.0.0"], "main": function main(container, depth0, helpers, partials, data) {
            var stack1,
                helper,
                alias1 = depth0 != null ? depth0 : {},
                alias2 = helpers.helperMissing,
                alias3 = "function",
                alias4 = container.escapeExpression;

            return "<li>\r\n  <a  id=\"" + alias4((helper = (helper = helpers.id || (depth0 != null ? depth0.id : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "id", "hash": {}, "data": data }) : helper)) + "\"\r\n      href=\"" + alias4((helper = (helper = helpers.href || (depth0 != null ? depth0.href : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "href", "hash": {}, "data": data }) : helper)) + "\"\r\n      rupLevel=\"" + alias4((helper = (helper = helpers.rupLevel || (depth0 != null ? depth0.rupLevel : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "rupLevel", "hash": {}, "data": data }) : helper)) + "\"\r\n      title=\"" + alias4((helper = (helper = helpers.title || (depth0 != null ? depth0.title : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "title", "hash": {}, "data": data }) : helper)) + "\"\r\n      alt=\"" + alias4((helper = (helper = helpers.alt || (depth0 != null ? depth0.alt : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "alt", "hash": {}, "data": data }) : helper)) + "\">\r\n\r\n      <div class=\"rup-tabs_title\">" + alias4((helper = (helper = helpers.label || (depth0 != null ? depth0.label : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "label", "hash": {}, "data": data }) : helper)) + "</div>\r\n      <span class=\"rup-tabs_loading\"> </span>\r\n" + ((stack1 = helpers["if"].call(alias1, depth0 != null ? depth0.btnClose : depth0, { "name": "if", "hash": {}, "fn": container.program(1, data, 0), "inverse": container.noop, "data": data })) != null ? stack1 : "") + "  </a>\r\n\r\n</li>\r\n";
        }, "useData": true });
    this["Rup"]["Templates"]["rup"]["toolbar"] = this["Rup"]["Templates"]["rup"]["toolbar"] || {};
    this["Rup"]["Templates"]["rup"]["toolbar"]["button"] = this["Rup"]["Templates"]["rup"]["toolbar"]["button"] || {};
    this["Rup"]["Templates"]["rup"]["toolbar"]["button"]["bootstrap"] = Handlebars.template({ "compiler": [7, ">= 4.0.0"], "main": function main(container, depth0, helpers, partials, data) {
            var helper,
                alias1 = depth0 != null ? depth0 : {},
                alias2 = helpers.helperMissing,
                alias3 = "function",
                alias4 = container.escapeExpression;

            return "\r\n<button type=\"button\" id=\"" + alias4((helper = (helper = helpers.id || (depth0 != null ? depth0.id : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "id", "hash": {}, "data": data }) : helper)) + "\" class=\"rup-button\">\r\n		<i class=\"" + alias4((helper = (helper = helpers.css || (depth0 != null ? depth0.css : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "css", "hash": {}, "data": data }) : helper)) + "\" aria-hidden=\"true\"></i>\r\n    <span class=\"rup-ui-button-text\">" + alias4((helper = (helper = helpers.label || (depth0 != null ? depth0.label : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "label", "hash": {}, "data": data }) : helper)) + "</span>\r\n</button>\r\n";
        }, "useData": true });
    this["Rup"]["Templates"]["rup"]["toolbar"]["button"]["jqueryui"] = Handlebars.template({ "compiler": [7, ">= 4.0.0"], "main": function main(container, depth0, helpers, partials, data) {
            var helper,
                alias1 = depth0 != null ? depth0 : {},
                alias2 = helpers.helperMissing,
                alias3 = "function",
                alias4 = container.escapeExpression;

            return "<button id=\"" + alias4((helper = (helper = helpers.id || (depth0 != null ? depth0.id : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "id", "hash": {}, "data": data }) : helper)) + "\" type=\"button\" class=\"rup-toolbar_button\">\r\n    <span class=\"ui-button-icon ui-icon " + alias4((helper = (helper = helpers.css || (depth0 != null ? depth0.css : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "css", "hash": {}, "data": data }) : helper)) + "\"></span>\r\n    <span class=\"ui-button-icon-space\"> </span>\r\n    <span class=\"rup-ui-button-text\">" + alias4((helper = (helper = helpers.label || (depth0 != null ? depth0.label : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "label", "hash": {}, "data": data }) : helper)) + "</span>\r\n</button>\r\n";
        }, "useData": true });
    this["Rup"]["Templates"]["rup"]["toolbar"]["mbutton"] = this["Rup"]["Templates"]["rup"]["toolbar"]["mbutton"] || {};
    this["Rup"]["Templates"]["rup"]["toolbar"]["mbutton"]["bootstrap"] = Handlebars.template({ "compiler": [7, ">= 4.0.0"], "main": function main(container, depth0, helpers, partials, data) {
            var helper,
                alias1 = depth0 != null ? depth0 : {},
                alias2 = helpers.helperMissing,
                alias3 = "function",
                alias4 = container.escapeExpression;

            return "<div id=\"" + alias4((helper = (helper = helpers.id || (depth0 != null ? depth0.id : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "id", "hash": {}, "data": data }) : helper)) + "-mbutton-group\" class=\"rup-mbutton " + alias4((helper = (helper = helpers.groupClasses || (depth0 != null ? depth0.groupClasses : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "groupClasses", "hash": {}, "data": data }) : helper)) + "\">\r\n		<button type=\"button\" data-mbutton=\"true\" id=\"" + alias4((helper = (helper = helpers.id || (depth0 != null ? depth0.id : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "id", "hash": {}, "data": data }) : helper)) + "\" data-mbutton=\"true\" class=\"ui-button ui-corner-all ui-widget rup-button\">\r\n			<i class=\"fa fa-cog\" aria-hidden=\"true\"></i>\r\n			<span class=\"rup-ui-button-text\">" + alias4((helper = (helper = helpers.label || (depth0 != null ? depth0.label : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "label", "hash": {}, "data": data }) : helper)) + "</span>\r\n		</button>\r\n		<ul id=\"" + alias4((helper = (helper = helpers.id || (depth0 != null ? depth0.id : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "id", "hash": {}, "data": data }) : helper)) + "-mbutton-container\" class=\"rup-mbutton-container\" aria-labelledby=\"" + alias4((helper = (helper = helpers.id || (depth0 != null ? depth0.id : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "id", "hash": {}, "data": data }) : helper)) + "\">\r\n\r\n		</ul>\r\n</div>\r\n";
        }, "useData": true });
    this["Rup"]["Templates"]["rup"]["upload"] = this["Rup"]["Templates"]["rup"]["upload"] || {};
    this["Rup"]["Templates"]["rup"]["upload"]["downloadTemplate"] = Handlebars.template({ "1": function _(container, depth0, helpers, partials, data) {
            var stack1,
                helper,
                alias1 = depth0 != null ? depth0 : {},
                alias2 = helpers.helperMissing,
                alias3 = "function",
                alias4 = container.escapeExpression;

            return "    <li class=\"list-group-item template-download " + ((stack1 = helpers["if"].call(alias1, depth0 != null ? depth0.error : depth0, { "name": "if", "hash": {}, "fn": container.program(2, data, 0), "inverse": container.noop, "data": data })) != null ? stack1 : "") + "\">\r\n      <div class=\"row\">\r\n\r\n\r\n          <div class=\"col-xs-6 col-md-3\">\r\n            <p class=\"name text-xs-left\"><b>" + ((stack1 = helpers["if"].call(alias1, depth0 != null ? depth0.error : depth0, { "name": "if", "hash": {}, "fn": container.program(4, data, 0), "inverse": container.program(6, data, 0), "data": data })) != null ? stack1 : "") + "</b></p>\r\n            <span class=\"name text-xs-left\"><span class=\"type\">" + alias4((helper = (helper = helpers.type || (depth0 != null ? depth0.type : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "type", "hash": {}, "data": data }) : helper)) + "</span></span>\r\n\r\n            <p class=\"name text-xs-left error-text error\">" + alias4((helper = (helper = helpers.error || (depth0 != null ? depth0.error : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "error", "hash": {}, "data": data }) : helper)) + "</p>\r\n\r\n          </div>\r\n\r\n" + ((stack1 = helpers["if"].call(alias1, depth0 != null ? depth0.error : depth0, { "name": "if", "hash": {}, "fn": container.program(8, data, 0), "inverse": container.program(10, data, 0), "data": data })) != null ? stack1 : "") + "      </div>\r\n    </li>\r\n";
        }, "2": function _(container, depth0, helpers, partials, data) {
            return "error";
        }, "4": function _(container, depth0, helpers, partials, data) {
            var helper;

            return container.escapeExpression((helper = (helper = helpers.name || (depth0 != null ? depth0.name : depth0)) != null ? helper : helpers.helperMissing, typeof helper === "function" ? helper.call(depth0 != null ? depth0 : {}, { "name": "name", "hash": {}, "data": data }) : helper));
        }, "6": function _(container, depth0, helpers, partials, data) {
            var helper,
                alias1 = depth0 != null ? depth0 : {},
                alias2 = helpers.helperMissing,
                alias3 = "function",
                alias4 = container.escapeExpression;

            return "<a href=\"" + alias4((helper = (helper = helpers.url || (depth0 != null ? depth0.url : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "url", "hash": {}, "data": data }) : helper)) + "\">" + alias4((helper = (helper = helpers.name || (depth0 != null ? depth0.name : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "name", "hash": {}, "data": data }) : helper)) + "</a>";
        }, "8": function _(container, depth0, helpers, partials, data) {
            return "\r\n";
        }, "10": function _(container, depth0, helpers, partials, data) {
            var helper,
                alias1 = depth0 != null ? depth0 : {},
                alias2 = helpers.helperMissing,
                alias3 = "function",
                alias4 = container.escapeExpression;

            return "            <div class=\"col-xs-6 col-md-4 fileupload-buttonbar\">\r\n                  <a href=\"" + alias4((helper = (helper = helpers.url || (depth0 != null ? depth0.url : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "url", "hash": {}, "data": data }) : helper)) + "\">\r\n                    <span  class=\"btn btn-primary download\">\r\n                        <i class=\"fa fa-download\" aria-hidden=\"true\"></i>\r\n                        <span>" + alias4((helpers.i18n || depth0 && depth0.i18n || alias2).call(alias1, "rup_upload.openUploaded", { "name": "i18n", "hash": {}, "data": data })) + "</span>\r\n                    </span>\r\n                  </a>\r\n\r\n                    <span  class=\"btn btn-secondary delete\" data-type=\"" + alias4((helper = (helper = helpers.delete_type || (depth0 != null ? depth0.delete_type : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "delete_type", "hash": {}, "data": data }) : helper)) + "\" data-url=\"" + alias4((helper = (helper = helpers.delete_url || (depth0 != null ? depth0.delete_url : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "delete_url", "hash": {}, "data": data }) : helper)) + "\">\r\n                        <i class=\"fa fa-trash\" aria-hidden=\"true\"></i>\r\n                        <span>" + alias4((helpers.i18n || depth0 && depth0.i18n || alias2).call(alias1, "rup_upload.deleteUploaded", { "name": "i18n", "hash": {}, "data": data })) + "</span>\r\n                    </span>\r\n            </div>\r\n";
        }, "compiler": [7, ">= 4.0.0"], "main": function main(container, depth0, helpers, partials, data) {
            var stack1;

            return "\r\n\r\n" + ((stack1 = helpers.each.call(depth0 != null ? depth0 : {}, depth0 != null ? depth0.files : depth0, { "name": "each", "hash": {}, "fn": container.program(1, data, 0), "inverse": container.noop, "data": data })) != null ? stack1 : "");
        }, "useData": true });
    this["Rup"]["Templates"]["rup"]["upload"]["uploadTemplate"] = Handlebars.template({ "1": function _(container, depth0, helpers, partials, data, blockParams, depths) {
            var stack1,
                helper,
                alias1 = depth0 != null ? depth0 : {},
                alias2 = helpers.helperMissing,
                alias3 = "function",
                alias4 = container.escapeExpression;

            return "    <li class=\"list-group-item template-upload\">\r\n      <div class=\"row\">\r\n        <div class=\"col-xs-6 col-md-3\">\r\n          <p class=\"name text-xs-left\"><b>" + alias4((helper = (helper = helpers.name || (depth0 != null ? depth0.name : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "name", "hash": {}, "data": data }) : helper)) + "</b></p>\r\n          <span class=\"name text-xs-left\"><span class=\"type-text type\">" + alias4((helper = (helper = helpers.type || (depth0 != null ? depth0.type : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "type", "hash": {}, "data": data }) : helper)) + "</span><span class=\"name text-xs-left size-text size\">" + alias4((helper = (helper = helpers.size || (depth0 != null ? depth0.size : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "size", "hash": {}, "data": data }) : helper)) + "</span></span>\r\n          <p class=\"name text-xs-left error-text error\"></p>\r\n\r\n\r\n        </div>\r\n\r\n        <div class=\"col-xs-6 col-md-4 fileupload-buttonbar\">\r\n" + ((stack1 = helpers["if"].call(alias1, depths[1] != null ? depths[1].notSubmitInForm : depths[1], { "name": "if", "hash": {}, "fn": container.program(2, data, 0, blockParams, depths), "inverse": container.noop, "data": data })) != null ? stack1 : "") + "\r\n                <span class=\"btn btn-secondary cancel\">\r\n                    <i class=\"fa fa-times-circle\" aria-hidden=\"true\"></i>\r\n                    <span>" + alias4((helpers.i18n || depth0 && depth0.i18n || alias2).call(alias1, "rup_upload.cancelUpload", { "name": "i18n", "hash": {}, "data": data })) + "</span>\r\n                </span>\r\n        </div>\r\n\r\n      </div>\r\n\r\n    </li>\r\n";
        }, "2": function _(container, depth0, helpers, partials, data) {
            return "                <button class=\"btn btn-primary start\" disabled=\"true\">\r\n                    <i class=\"fa fa-upload\" aria-hidden=\"true\"></i>\r\n                    <span>" + container.escapeExpression((helpers.i18n || depth0 && depth0.i18n || helpers.helperMissing).call(depth0 != null ? depth0 : {}, "rup_upload.startUpload", { "name": "i18n", "hash": {}, "data": data })) + "</span>\r\n                </button>\r\n\r\n";
        }, "compiler": [7, ">= 4.0.0"], "main": function main(container, depth0, helpers, partials, data, blockParams, depths) {
            var stack1;

            return "\r\n\r\n" + ((stack1 = helpers.each.call(depth0 != null ? depth0 : {}, depth0 != null ? depth0.files : depth0, { "name": "each", "hash": {}, "fn": container.program(1, data, 0, blockParams, depths), "inverse": container.noop, "data": data })) != null ? stack1 : "");
        }, "useData": true, "useDepths": true });
    this["Rup"]["Templates"]["rup"]["widget"] = this["Rup"]["Templates"]["rup"]["widget"] || {};
    this["Rup"]["Templates"]["rup"]["widget"]["base"] = Handlebars.template({ "1": function _(container, depth0, helpers, partials, data) {
            var helper,
                alias1 = depth0 != null ? depth0 : {},
                alias2 = helpers.helperMissing,
                alias3 = container.escapeExpression;

            return "          <span id=\"widgetClose-" + alias3((helper = (helper = helpers.uuid || (depth0 != null ? depth0.uuid : depth0)) != null ? helper : alias2, typeof helper === "function" ? helper.call(alias1, { "name": "uuid", "hash": {}, "data": data }) : helper)) + "\" class=\"widget-icon widget-icon-right glyphicon glyphicon-trash\" data-toggle=\"tooltip\" data-placement=\"top\" title=\"" + alias3((helpers.i18n || depth0 && depth0.i18n || alias2).call(alias1, "title.eliminar", { "name": "i18n", "hash": {}, "data": data })) + "\"></span>\r\n";
        }, "3": function _(container, depth0, helpers, partials, data) {
            var helper,
                alias1 = depth0 != null ? depth0 : {},
                alias2 = helpers.helperMissing,
                alias3 = container.escapeExpression;

            return "          <span id=\"widgetReload-" + alias3((helper = (helper = helpers.uuid || (depth0 != null ? depth0.uuid : depth0)) != null ? helper : alias2, typeof helper === "function" ? helper.call(alias1, { "name": "uuid", "hash": {}, "data": data }) : helper)) + "\" class=\"widget-icon widget-icon-right glyphicon glyphicon-refresh\" data-toggle=\"tooltip\" data-placement=\"top\" title=\"" + alias3((helpers.i18n || depth0 && depth0.i18n || alias2).call(alias1, "title.refrescar", { "name": "i18n", "hash": {}, "data": data })) + "\"></span>\r\n";
        }, "5": function _(container, depth0, helpers, partials, data) {
            var helper,
                alias1 = depth0 != null ? depth0 : {},
                alias2 = helpers.helperMissing,
                alias3 = container.escapeExpression;

            return "          <span id=\"widgetResizeFull-" + alias3((helper = (helper = helpers.uuid || (depth0 != null ? depth0.uuid : depth0)) != null ? helper : alias2, typeof helper === "function" ? helper.call(alias1, { "name": "uuid", "hash": {}, "data": data }) : helper)) + "\" class=\"widget-icon widget-icon-right glyphicon glyphicon-resize-full\" data-toggle=\"tooltip\" data-placement=\"top\" title=\"" + alias3((helpers.i18n || depth0 && depth0.i18n || alias2).call(alias1, "title.maximizar", { "name": "i18n", "hash": {}, "data": data })) + "\"></span>\r\n";
        }, "7": function _(container, depth0, helpers, partials, data) {
            var helper,
                alias1 = depth0 != null ? depth0 : {},
                alias2 = helpers.helperMissing,
                alias3 = container.escapeExpression;

            return "          <span id=\"widgetConfig-" + alias3((helper = (helper = helpers.uuid || (depth0 != null ? depth0.uuid : depth0)) != null ? helper : alias2, typeof helper === "function" ? helper.call(alias1, { "name": "uuid", "hash": {}, "data": data }) : helper)) + "\" class=\"widget-icon widget-icon-right glyphicon glyphicon-cog\" data-toggle=\"tooltip\" data-placement=\"top\" title=\"" + alias3((helpers.i18n || depth0 && depth0.i18n || alias2).call(alias1, "title.configuracion", { "name": "i18n", "hash": {}, "data": data })) + "\" ></span>\r\n";
        }, "9": function _(container, depth0, helpers, partials, data) {
            var helper,
                alias1 = depth0 != null ? depth0 : {},
                alias2 = helpers.helperMissing,
                alias3 = "function",
                alias4 = container.escapeExpression;

            return "          <span id=\"widgetInfo-" + alias4((helper = (helper = helpers.uuid || (depth0 != null ? depth0.uuid : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "uuid", "hash": {}, "data": data }) : helper)) + "\" class=\"widget-icon widget-icon-right glyphicon glyphicon-question-sign\" data-toggle=\"tooltip\" data-placement=\"bottom\" title=\"" + alias4((helper = (helper = helpers.infoTextNew || (depth0 != null ? depth0.infoTextNew : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "infoTextNew", "hash": {}, "data": data }) : helper)) + "\" tttt=\"" + alias4((helper = (helper = helpers.infoText || (depth0 != null ? depth0.infoText : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "infoText", "hash": {}, "data": data }) : helper)) + "\"></span>\r\n";
        }, "11": function _(container, depth0, helpers, partials, data) {
            var helper,
                alias1 = depth0 != null ? depth0 : {},
                alias2 = helpers.helperMissing,
                alias3 = container.escapeExpression;

            return "          <span id=\"widgetShow-" + alias3((helper = (helper = helpers.uuid || (depth0 != null ? depth0.uuid : depth0)) != null ? helper : alias2, typeof helper === "function" ? helper.call(alias1, { "name": "uuid", "hash": {}, "data": data }) : helper)) + "\" class=\"widget-icon widget-icon-right glyphicon glyphicon-eye-close\" data-toggle=\"tooltip\" data-placement=\"top\" title=\"" + alias3((helpers.i18n || depth0 && depth0.i18n || alias2).call(alias1, "title.mostrarOcultar", { "name": "i18n", "hash": {}, "data": data })) + "\"></span>\r\n";
        }, "compiler": [7, ">= 4.0.0"], "main": function main(container, depth0, helpers, partials, data) {
            var stack1,
                helper,
                alias1 = depth0 != null ? depth0 : {},
                alias2 = helpers.helperMissing,
                alias3 = "function",
                alias4 = container.escapeExpression;

            return "<div class=\"widget rssBottom\" id=\"" + alias4((helper = (helper = helpers.uuid || (depth0 != null ? depth0.uuid : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "uuid", "hash": {}, "data": data }) : helper)) + "\">\r\n    <div class=\"widget-header\">\r\n        <div>\r\n          <span class=\"widget-header-title\">" + alias4((helper = (helper = helpers.title || (depth0 != null ? depth0.title : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "title", "hash": {}, "data": data }) : helper)) + "</span>\r\n        </div>\r\n        <div class=\"widget-header-controls\">\r\n" + ((stack1 = helpers["if"].call(alias1, (stack1 = depth0 != null ? depth0.buttons : depth0) != null ? stack1.btnClose : stack1, { "name": "if", "hash": {}, "fn": container.program(1, data, 0), "inverse": container.noop, "data": data })) != null ? stack1 : "") + ((stack1 = helpers["if"].call(alias1, (stack1 = depth0 != null ? depth0.buttons : depth0) != null ? stack1.btnReload : stack1, { "name": "if", "hash": {}, "fn": container.program(3, data, 0), "inverse": container.noop, "data": data })) != null ? stack1 : "") + ((stack1 = helpers["if"].call(alias1, (stack1 = depth0 != null ? depth0.buttons : depth0) != null ? stack1.btnResizeFull : stack1, { "name": "if", "hash": {}, "fn": container.program(5, data, 0), "inverse": container.noop, "data": data })) != null ? stack1 : "") + "          <span id=\"widgetResizeSmall-" + alias4((helper = (helper = helpers.uuid || (depth0 != null ? depth0.uuid : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "uuid", "hash": {}, "data": data }) : helper)) + "\" class=\"widget-icon widget-icon-right glyphicon glyphicon-resize-small\" data-toggle=\"tooltip\" data-placement=\"top\" title=\"" + alias4((helpers.i18n || depth0 && depth0.i18n || alias2).call(alias1, "title.minimizar", { "name": "i18n", "hash": {}, "data": data })) + "\"></span>\r\n" + ((stack1 = helpers["if"].call(alias1, (stack1 = depth0 != null ? depth0.buttons : depth0) != null ? stack1.btnConfig : stack1, { "name": "if", "hash": {}, "fn": container.program(7, data, 0), "inverse": container.noop, "data": data })) != null ? stack1 : "") + ((stack1 = helpers["if"].call(alias1, depth0 != null ? depth0.infoText : depth0, { "name": "if", "hash": {}, "fn": container.program(9, data, 0), "inverse": container.noop, "data": data })) != null ? stack1 : "") + ((stack1 = helpers["if"].call(alias1, (stack1 = depth0 != null ? depth0.buttons : depth0) != null ? stack1.btnShow : stack1, { "name": "if", "hash": {}, "fn": container.program(11, data, 0), "inverse": container.noop, "data": data })) != null ? stack1 : "") + "        </div>\r\n    </div>\r\n    <div class=\"widget-feedback\">\r\n    </div>\r\n    <div class=\"widget-body\">\r\n\r\n    </div>\r\n</div>\r\n";
        }, "useData": true });
    this["Rup"]["Templates"]["rup"]["widget"]["close"] = Handlebars.template({ "compiler": [7, ">= 4.0.0"], "main": function main(container, depth0, helpers, partials, data) {
            return "";
        }, "useData": true });
    this["Rup"]["Templates"]["rup"]["widget"]["configRequired"] = Handlebars.template({ "1": function _(container, depth0, helpers, partials, data) {
            var stack1, helper;

            return "<br/>" + ((stack1 = (helper = (helper = helpers.urlConsulta || (depth0 != null ? depth0.urlConsulta : depth0)) != null ? helper : helpers.helperMissing, typeof helper === "function" ? helper.call(depth0 != null ? depth0 : {}, { "name": "urlConsulta", "hash": {}, "data": data }) : helper)) != null ? stack1 : "");
        }, "compiler": [7, ">= 4.0.0"], "main": function main(container, depth0, helpers, partials, data) {
            var stack1,
                helper,
                alias1 = depth0 != null ? depth0 : {},
                alias2 = helpers.helperMissing,
                alias3 = "function",
                alias4 = container.escapeExpression;

            return "<div id=\"" + alias4((helper = (helper = helpers.idModal || (depth0 != null ? depth0.idModal : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "idModal", "hash": {}, "data": data }) : helper)) + "\" class=\"config-required-modal\">\r\n    <div>\r\n        <div>\r\n            <span>" + alias4((helper = (helper = helpers.titulo || (depth0 != null ? depth0.titulo : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "titulo", "hash": {}, "data": data }) : helper)) + ((stack1 = helpers["if"].call(alias1, depth0 != null ? depth0.urlConsulta : depth0, { "name": "if", "hash": {}, "fn": container.program(1, data, 0), "inverse": container.noop, "data": data })) != null ? stack1 : "") + "</span><br>\r\n            <button id=\"btnConfigRequired\" type=\"button\" class=\"btn btn-primary\">\r\n                <span class=\"glyphicon glyphicon-cog\" aria-hidden=\"true\"></span>" + alias4((helpers.i18n || depth0 && depth0.i18n || alias2).call(alias1, "title.configuracion", { "name": "i18n", "hash": {}, "data": data })) + "</button>\r\n            <button id=\"btnDelete\" type=\"button\" class=\"btn btn-danger\">\r\n                <span class=\"glyphicon glyphicon-trash\" aria-hidden=\"true\"></span>" + alias4((helpers.i18n || depth0 && depth0.i18n || alias2).call(alias1, "title.eliminar", { "name": "i18n", "hash": {}, "data": data })) + "</button>\r\n            \r\n        </div>\r\n    </div>\r\n</div>";
        }, "useData": true });
    this["Rup"]["Templates"]["rup"]["widget"]["help"] = Handlebars.template({ "compiler": [7, ">= 4.0.0"], "main": function main(container, depth0, helpers, partials, data) {
            var alias1 = depth0 != null ? depth0 : {},
                alias2 = helpers.helperMissing,
                alias3 = container.escapeExpression;

            return "\r\n<p class=\"help_widget_intro\">" + alias3((helpers.i18n || depth0 && depth0.i18n || alias2).call(alias1, "help.parrafo1", { "name": "i18n", "hash": {}, "data": data })) + "</p>\r\n\r\n<div class=\"help_block add_widget_action\">\r\n<p>" + alias3((helpers.i18n || depth0 && depth0.i18n || alias2).call(alias1, "help.addWidget", { "name": "i18n", "hash": {}, "data": data })) + "</p>\r\n<p>" + alias3((helpers.i18n || depth0 && depth0.i18n || alias2).call(alias1, "help.addWidgetText", { "name": "i18n", "hash": {}, "data": data })) + "</p>\r\n</div>\r\n\r\n<div class=\"help_block config_widget_action\">\r\n<p>" + alias3((helpers.i18n || depth0 && depth0.i18n || alias2).call(alias1, "help.configura", { "name": "i18n", "hash": {}, "data": data })) + "</p>\r\n<p>" + alias3((helpers.i18n || depth0 && depth0.i18n || alias2).call(alias1, "help.configuraText", { "name": "i18n", "hash": {}, "data": data })) + "</p>\r\n</div>\r\n\r\n<div class=\"help_block help_widget_action\">\r\n<p>" + alias3((helpers.i18n || depth0 && depth0.i18n || alias2).call(alias1, "help.ayuda", { "name": "i18n", "hash": {}, "data": data })) + "</p>\r\n<p>" + alias3((helpers.i18n || depth0 && depth0.i18n || alias2).call(alias1, "help.ayudaText", { "name": "i18n", "hash": {}, "data": data })) + "</p>\r\n</div>\r\n";
        }, "useData": true });
    this["Rup"]["Templates"]["rup"]["widget"]["rss"] = Handlebars.template({ "1": function _(container, depth0, helpers, partials, data) {
            var stack1;

            return "    <div class=\"list-group\">\r\n" + ((stack1 = helpers.each.call(depth0 != null ? depth0 : {}, depth0 != null ? depth0.items : depth0, { "name": "each", "hash": {}, "fn": container.program(2, data, 0), "inverse": container.noop, "data": data })) != null ? stack1 : "") + "    </div>\r\n";
        }, "2": function _(container, depth0, helpers, partials, data) {
            var helper,
                alias1 = depth0 != null ? depth0 : {},
                alias2 = helpers.helperMissing,
                alias3 = "function",
                alias4 = container.escapeExpression;

            return "          <a href=\"" + alias4((helper = (helper = helpers.link || (depth0 != null ? depth0.link : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "link", "hash": {}, "data": data }) : helper)) + "\" class=\"list-group-item\" data-source=\"" + alias4((helper = (helper = helpers.source || (depth0 != null ? depth0.source : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "source", "hash": {}, "data": data }) : helper)) + "\" data-url=\"" + alias4((helper = (helper = helpers.link || (depth0 != null ? depth0.link : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "link", "hash": {}, "data": data }) : helper)) + "\" data-comments=\"" + alias4((helper = (helper = helpers.comments || (depth0 != null ? depth0.comments : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "comments", "hash": {}, "data": data }) : helper)) + "\" target=\"_blank\">\r\n            <h5 class=\"list-group-item-heading\">" + alias4((helper = (helper = helpers.title || (depth0 != null ? depth0.title : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "title", "hash": {}, "data": data }) : helper)) + "</h5>\r\n            <p class=\"list-group-item-text\">" + alias4((helper = (helper = helpers.content || (depth0 != null ? depth0.content : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "content", "hash": {}, "data": data }) : helper)) + "</p>\r\n            <p class=\"list-group-item-text\">" + alias4((helper = (helper = helpers.pubDate || (depth0 != null ? depth0.pubDate : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "pubDate", "hash": {}, "data": data }) : helper)) + "</p>\r\n          </a>\r\n";
        }, "compiler": [7, ">= 4.0.0"], "main": function main(container, depth0, helpers, partials, data) {
            var stack1;

            return ((stack1 = helpers.each.call(depth0 != null ? depth0 : {}, depth0 != null ? depth0.channel : depth0, { "name": "each", "hash": {}, "fn": container.program(1, data, 0), "inverse": container.noop, "data": data })) != null ? stack1 : "") + "\r\n";
        }, "useData": true });
    this["Rup"]["Templates"]["rup"]["widget"]["search"] = Handlebars.template({ "compiler": [7, ">= 4.0.0"], "main": function main(container, depth0, helpers, partials, data) {
            var helper,
                alias1 = depth0 != null ? depth0 : {},
                alias2 = helpers.helperMissing,
                alias3 = "function",
                alias4 = container.escapeExpression;

            return "<form>\r\n    <div class=\"form-group\">\r\n        <label for=\"" + alias4((helper = (helper = helpers.fieldId || (depth0 != null ? depth0.fieldId : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "fieldId", "hash": {}, "data": data }) : helper)) + "\" class=\"control-label\">" + alias4((helper = (helper = helpers.fieldLabel || (depth0 != null ? depth0.fieldLabel : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "fieldLabel", "hash": {}, "data": data }) : helper)) + "</label>\r\n        <input type=\"text\" class=\"form-control\" id=\"" + alias4((helper = (helper = helpers.fieldId || (depth0 != null ? depth0.fieldId : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "fieldId", "hash": {}, "data": data }) : helper)) + "\" placeholder=\"" + alias4((helper = (helper = helpers.fieldPlaceholder || (depth0 != null ? depth0.fieldPlaceholder : depth0)) != null ? helper : alias2, (typeof helper === "undefined" ? "undefined" : _typeof(helper)) === alias3 ? helper.call(alias1, { "name": "fieldPlaceholder", "hash": {}, "data": data }) : helper)) + "\">\r\n    </div>\r\n    <div class=\"form-group\">\r\n        <button type=\"button\" class=\"btn btn-default\">\r\n            <span class=\"glyphicon glyphicon-search\"></span>\r\n            Consultar</button>\r\n        <button type=\"button\" class=\"btn btn-primary\">\r\n            <span class=\"glyphicon glyphicon-cog\"></span>\r\n            Tramitar</button>\r\n    </div>\r\n</form> \r\n";
        }, "useData": true });
    this["Rup"]["Templates"]["rup"]["widget"]["welcome"] = Handlebars.template({ "compiler": [7, ">= 4.0.0"], "main": function main(container, depth0, helpers, partials, data) {
            var alias1 = depth0 != null ? depth0 : {},
                alias2 = helpers.helperMissing,
                alias3 = container.escapeExpression;

            return "<p>" + alias3((helpers.i18n || depth0 && depth0.i18n || alias2).call(alias1, "welcome.parrafo1", { "name": "i18n", "hash": {}, "data": data })) + "</p>\r\n<p>" + alias3((helpers.i18n || depth0 && depth0.i18n || alias2).call(alias1, "welcome.parrafo2", { "name": "i18n", "hash": {}, "data": data })) + "</p>\r\n\r\n\r\n<div class=\"help_herramienta bienvenida_1 noborder_widget\">\r\n<h2>" + alias3((helpers.i18n || depth0 && depth0.i18n || alias2).call(alias1, "welcome.seleccionActivo", { "name": "i18n", "hash": {}, "data": data })) + "</h2>\r\n<p>" + alias3((helpers.i18n || depth0 && depth0.i18n || alias2).call(alias1, "welcome.seleccionActivoText", { "name": "i18n", "hash": {}, "data": data })) + "</p>\r\n</div>\r\n\r\n<div class=\"help_herramienta bienvenida_2\">\r\n<h2>" + alias3((helpers.i18n || depth0 && depth0.i18n || alias2).call(alias1, "welcome.opcionConfiguracion", { "name": "i18n", "hash": {}, "data": data })) + "</h2>\r\n<p>" + alias3((helpers.i18n || depth0 && depth0.i18n || alias2).call(alias1, "welcome.opcionConfiguracionText", { "name": "i18n", "hash": {}, "data": data })) + "</p>\r\n</div>\r\n\r\n<div class=\"help_herramienta bienvenida_3\">\r\n<h2>" + alias3((helpers.i18n || depth0 && depth0.i18n || alias2).call(alias1, "welcome.addWidget", { "name": "i18n", "hash": {}, "data": data })) + "</h2>\r\n<p>" + alias3((helpers.i18n || depth0 && depth0.i18n || alias2).call(alias1, "welcome.addWidgetText", { "name": "i18n", "hash": {}, "data": data })) + "</p>\r\n</div>\r\n\r\n<div class=\"help_herramienta bienvenida_4\">\r\n<h2>" + alias3((helpers.i18n || depth0 && depth0.i18n || alias2).call(alias1, "welcome.accesoFamilias", { "name": "i18n", "hash": {}, "data": data })) + "</h2>\r\n<p>" + alias3((helpers.i18n || depth0 && depth0.i18n || alias2).call(alias1, "welcome.accesoFamiliasText", { "name": "i18n", "hash": {}, "data": data })) + "</p>\r\n</div>\r\n\r\n<div class=\"help_herramienta bienvenida_5\">\r\n<h2>" + alias3((helpers.i18n || depth0 && depth0.i18n || alias2).call(alias1, "welcome.herramientas", { "name": "i18n", "hash": {}, "data": data })) + "</h2>\r\n<p>" + alias3((helpers.i18n || depth0 && depth0.i18n || alias2).call(alias1, "welcome.herramientasText", { "name": "i18n", "hash": {}, "data": data })) + "</p>\r\n</div>\r\n\r\n";
        }, "useData": true });
    return this['Rup'];
});

/***/ }),
/* 4 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*! DataTables 1.10.16
 * ©2008-2017 SpryMedia Ltd - datatables.net/license
 */

/**
 * @summary     DataTables
 * @description Paginate, search and order HTML tables
 * @version     1.10.16
 * @file        jquery.dataTables.js
 *  
 * @contact     www.datatables.net
 * @copyright   Copyright 2008-2017 SpryMedia Ltd.
 *
 * This source file is free software, available under the following license:
 *   MIT license - http://datatables.net/license
 *
 * This source file is distributed in the hope that it will be useful, but
 * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
 * or FITNESS FOR A PARTICULAR PURPOSE. See the license files for details.
 *
 * For details please refer to: http://www.datatables.net
 */

/*jslint evil: true, undef: true, browser: true */
/*globals $,require,jQuery,define,_selector_run,_selector_opts,_selector_first,_selector_row_indexes,_ext,_Api,_api_register,_api_registerPlural,_re_new_lines,_re_html,_re_formatted_numeric,_re_escape_regex,_empty,_intVal,_numToDecimal,_isNumber,_isHtml,_htmlNumeric,_pluck,_pluck_order,_range,_stripHtml,_unique,_fnBuildAjax,_fnAjaxUpdate,_fnAjaxParameters,_fnAjaxUpdateDraw,_fnAjaxDataSrc,_fnAddColumn,_fnColumnOptions,_fnAdjustColumnSizing,_fnVisibleToColumnIndex,_fnColumnIndexToVisible,_fnVisbleColumns,_fnGetColumns,_fnColumnTypes,_fnApplyColumnDefs,_fnHungarianMap,_fnCamelToHungarian,_fnLanguageCompat,_fnBrowserDetect,_fnAddData,_fnAddTr,_fnNodeToDataIndex,_fnNodeToColumnIndex,_fnGetCellData,_fnSetCellData,_fnSplitObjNotation,_fnGetObjectDataFn,_fnSetObjectDataFn,_fnGetDataMaster,_fnClearTable,_fnDeleteIndex,_fnInvalidate,_fnGetRowElements,_fnCreateTr,_fnBuildHead,_fnDrawHead,_fnDraw,_fnReDraw,_fnAddOptionsHtml,_fnDetectHeader,_fnGetUniqueThs,_fnFeatureHtmlFilter,_fnFilterComplete,_fnFilterCustom,_fnFilterColumn,_fnFilter,_fnFilterCreateSearch,_fnEscapeRegex,_fnFilterData,_fnFeatureHtmlInfo,_fnUpdateInfo,_fnInfoMacros,_fnInitialise,_fnInitComplete,_fnLengthChange,_fnFeatureHtmlLength,_fnFeatureHtmlPaginate,_fnPageChange,_fnFeatureHtmlProcessing,_fnProcessingDisplay,_fnFeatureHtmlTable,_fnScrollDraw,_fnApplyToChildren,_fnCalculateColumnWidths,_fnThrottle,_fnConvertToWidth,_fnGetWidestNode,_fnGetMaxLenString,_fnStringToCss,_fnSortFlatten,_fnSort,_fnSortAria,_fnSortListener,_fnSortAttachListener,_fnSortingClasses,_fnSortData,_fnSaveState,_fnLoadState,_fnSettingsFromNode,_fnLog,_fnMap,_fnBindAction,_fnCallbackReg,_fnCallbackFire,_fnLengthOverflow,_fnRenderer,_fnDataSource,_fnRowAttributes*/

(function( factory ) {
	"use strict";

	if ( true ) {
		// AMD
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0)], __WEBPACK_AMD_DEFINE_RESULT__ = function ( $ ) {
			return factory( $, window, document );
		}.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	}
	else if ( typeof exports === 'object' ) {
		// CommonJS
		module.exports = function (root, $) {
			if ( ! root ) {
				// CommonJS environments without a window global must pass a
				// root. This will give an error otherwise
				root = window;
			}

			if ( ! $ ) {
				$ = typeof window !== 'undefined' ? // jQuery's factory checks for a global window
					require('jquery') :
					require('jquery')( root );
			}

			return factory( $, root, root.document );
		};
	}
	else {
		// Browser
		factory( jQuery, window, document );
	}
}
(function( $, window, document, undefined ) {
	"use strict";

	/**
	 * DataTables is a plug-in for the jQuery Javascript library. It is a highly
	 * flexible tool, based upon the foundations of progressive enhancement,
	 * which will add advanced interaction controls to any HTML table. For a
	 * full list of features please refer to
	 * [DataTables.net](href="http://datatables.net).
	 *
	 * Note that the `DataTable` object is not a global variable but is aliased
	 * to `jQuery.fn.DataTable` and `jQuery.fn.dataTable` through which it may
	 * be  accessed.
	 *
	 *  @class
	 *  @param {object} [init={}] Configuration object for DataTables. Options
	 *    are defined by {@link DataTable.defaults}
	 *  @requires jQuery 1.7+
	 *
	 *  @example
	 *    // Basic initialisation
	 *    $(document).ready( function {
	 *      $('#example').dataTable();
	 *    } );
	 *
	 *  @example
	 *    // Initialisation with configuration options - in this case, disable
	 *    // pagination and sorting.
	 *    $(document).ready( function {
	 *      $('#example').dataTable( {
	 *        "paginate": false,
	 *        "sort": false
	 *      } );
	 *    } );
	 */
	var DataTable = function ( options )
	{
		/**
		 * Perform a jQuery selector action on the table's TR elements (from the tbody) and
		 * return the resulting jQuery object.
		 *  @param {string|node|jQuery} sSelector jQuery selector or node collection to act on
		 *  @param {object} [oOpts] Optional parameters for modifying the rows to be included
		 *  @param {string} [oOpts.filter=none] Select TR elements that meet the current filter
		 *    criterion ("applied") or all TR elements (i.e. no filter).
		 *  @param {string} [oOpts.order=current] Order of the TR elements in the processed array.
		 *    Can be either 'current', whereby the current sorting of the table is used, or
		 *    'original' whereby the original order the data was read into the table is used.
		 *  @param {string} [oOpts.page=all] Limit the selection to the currently displayed page
		 *    ("current") or not ("all"). If 'current' is given, then order is assumed to be
		 *    'current' and filter is 'applied', regardless of what they might be given as.
		 *  @returns {object} jQuery object, filtered by the given selector.
		 *  @dtopt API
		 *  @deprecated Since v1.10
		 *
		 *  @example
		 *    $(document).ready(function() {
		 *      var oTable = $('#example').dataTable();
		 *
		 *      // Highlight every second row
		 *      oTable.$('tr:odd').css('backgroundColor', 'blue');
		 *    } );
		 *
		 *  @example
		 *    $(document).ready(function() {
		 *      var oTable = $('#example').dataTable();
		 *
		 *      // Filter to rows with 'Webkit' in them, add a background colour and then
		 *      // remove the filter, thus highlighting the 'Webkit' rows only.
		 *      oTable.fnFilter('Webkit');
		 *      oTable.$('tr', {"search": "applied"}).css('backgroundColor', 'blue');
		 *      oTable.fnFilter('');
		 *    } );
		 */
		this.$ = function ( sSelector, oOpts )
		{
			return this.api(true).$( sSelector, oOpts );
		};
		
		
		/**
		 * Almost identical to $ in operation, but in this case returns the data for the matched
		 * rows - as such, the jQuery selector used should match TR row nodes or TD/TH cell nodes
		 * rather than any descendants, so the data can be obtained for the row/cell. If matching
		 * rows are found, the data returned is the original data array/object that was used to
		 * create the row (or a generated array if from a DOM source).
		 *
		 * This method is often useful in-combination with $ where both functions are given the
		 * same parameters and the array indexes will match identically.
		 *  @param {string|node|jQuery} sSelector jQuery selector or node collection to act on
		 *  @param {object} [oOpts] Optional parameters for modifying the rows to be included
		 *  @param {string} [oOpts.filter=none] Select elements that meet the current filter
		 *    criterion ("applied") or all elements (i.e. no filter).
		 *  @param {string} [oOpts.order=current] Order of the data in the processed array.
		 *    Can be either 'current', whereby the current sorting of the table is used, or
		 *    'original' whereby the original order the data was read into the table is used.
		 *  @param {string} [oOpts.page=all] Limit the selection to the currently displayed page
		 *    ("current") or not ("all"). If 'current' is given, then order is assumed to be
		 *    'current' and filter is 'applied', regardless of what they might be given as.
		 *  @returns {array} Data for the matched elements. If any elements, as a result of the
		 *    selector, were not TR, TD or TH elements in the DataTable, they will have a null
		 *    entry in the array.
		 *  @dtopt API
		 *  @deprecated Since v1.10
		 *
		 *  @example
		 *    $(document).ready(function() {
		 *      var oTable = $('#example').dataTable();
		 *
		 *      // Get the data from the first row in the table
		 *      var data = oTable._('tr:first');
		 *
		 *      // Do something useful with the data
		 *      alert( "First cell is: "+data[0] );
		 *    } );
		 *
		 *  @example
		 *    $(document).ready(function() {
		 *      var oTable = $('#example').dataTable();
		 *
		 *      // Filter to 'Webkit' and get all data for
		 *      oTable.fnFilter('Webkit');
		 *      var data = oTable._('tr', {"search": "applied"});
		 *
		 *      // Do something with the data
		 *      alert( data.length+" rows matched the search" );
		 *    } );
		 */
		this._ = function ( sSelector, oOpts )
		{
			return this.api(true).rows( sSelector, oOpts ).data();
		};
		
		
		/**
		 * Create a DataTables Api instance, with the currently selected tables for
		 * the Api's context.
		 * @param {boolean} [traditional=false] Set the API instance's context to be
		 *   only the table referred to by the `DataTable.ext.iApiIndex` option, as was
		 *   used in the API presented by DataTables 1.9- (i.e. the traditional mode),
		 *   or if all tables captured in the jQuery object should be used.
		 * @return {DataTables.Api}
		 */
		this.api = function ( traditional )
		{
			return traditional ?
				new _Api(
					_fnSettingsFromNode( this[ _ext.iApiIndex ] )
				) :
				new _Api( this );
		};
		
		
		/**
		 * Add a single new row or multiple rows of data to the table. Please note
		 * that this is suitable for client-side processing only - if you are using
		 * server-side processing (i.e. "bServerSide": true), then to add data, you
		 * must add it to the data source, i.e. the server-side, through an Ajax call.
		 *  @param {array|object} data The data to be added to the table. This can be:
		 *    <ul>
		 *      <li>1D array of data - add a single row with the data provided</li>
		 *      <li>2D array of arrays - add multiple rows in a single call</li>
		 *      <li>object - data object when using <i>mData</i></li>
		 *      <li>array of objects - multiple data objects when using <i>mData</i></li>
		 *    </ul>
		 *  @param {bool} [redraw=true] redraw the table or not
		 *  @returns {array} An array of integers, representing the list of indexes in
		 *    <i>aoData</i> ({@link DataTable.models.oSettings}) that have been added to
		 *    the table.
		 *  @dtopt API
		 *  @deprecated Since v1.10
		 *
		 *  @example
		 *    // Global var for counter
		 *    var giCount = 2;
		 *
		 *    $(document).ready(function() {
		 *      $('#example').dataTable();
		 *    } );
		 *
		 *    function fnClickAddRow() {
		 *      $('#example').dataTable().fnAddData( [
		 *        giCount+".1",
		 *        giCount+".2",
		 *        giCount+".3",
		 *        giCount+".4" ]
		 *      );
		 *
		 *      giCount++;
		 *    }
		 */
		this.fnAddData = function( data, redraw )
		{
			var api = this.api( true );
		
			/* Check if we want to add multiple rows or not */
			var rows = $.isArray(data) && ( $.isArray(data[0]) || $.isPlainObject(data[0]) ) ?
				api.rows.add( data ) :
				api.row.add( data );
		
			if ( redraw === undefined || redraw ) {
				api.draw();
			}
		
			return rows.flatten().toArray();
		};
		
		
		/**
		 * This function will make DataTables recalculate the column sizes, based on the data
		 * contained in the table and the sizes applied to the columns (in the DOM, CSS or
		 * through the sWidth parameter). This can be useful when the width of the table's
		 * parent element changes (for example a window resize).
		 *  @param {boolean} [bRedraw=true] Redraw the table or not, you will typically want to
		 *  @dtopt API
		 *  @deprecated Since v1.10
		 *
		 *  @example
		 *    $(document).ready(function() {
		 *      var oTable = $('#example').dataTable( {
		 *        "sScrollY": "200px",
		 *        "bPaginate": false
		 *      } );
		 *
		 *      $(window).on('resize', function () {
		 *        oTable.fnAdjustColumnSizing();
		 *      } );
		 *    } );
		 */
		this.fnAdjustColumnSizing = function ( bRedraw )
		{
			var api = this.api( true ).columns.adjust();
			var settings = api.settings()[0];
			var scroll = settings.oScroll;
		
			if ( bRedraw === undefined || bRedraw ) {
				api.draw( false );
			}
			else if ( scroll.sX !== "" || scroll.sY !== "" ) {
				/* If not redrawing, but scrolling, we want to apply the new column sizes anyway */
				_fnScrollDraw( settings );
			}
		};
		
		
		/**
		 * Quickly and simply clear a table
		 *  @param {bool} [bRedraw=true] redraw the table or not
		 *  @dtopt API
		 *  @deprecated Since v1.10
		 *
		 *  @example
		 *    $(document).ready(function() {
		 *      var oTable = $('#example').dataTable();
		 *
		 *      // Immediately 'nuke' the current rows (perhaps waiting for an Ajax callback...)
		 *      oTable.fnClearTable();
		 *    } );
		 */
		this.fnClearTable = function( bRedraw )
		{
			var api = this.api( true ).clear();
		
			if ( bRedraw === undefined || bRedraw ) {
				api.draw();
			}
		};
		
		
		/**
		 * The exact opposite of 'opening' a row, this function will close any rows which
		 * are currently 'open'.
		 *  @param {node} nTr the table row to 'close'
		 *  @returns {int} 0 on success, or 1 if failed (can't find the row)
		 *  @dtopt API
		 *  @deprecated Since v1.10
		 *
		 *  @example
		 *    $(document).ready(function() {
		 *      var oTable;
		 *
		 *      // 'open' an information row when a row is clicked on
		 *      $('#example tbody tr').click( function () {
		 *        if ( oTable.fnIsOpen(this) ) {
		 *          oTable.fnClose( this );
		 *        } else {
		 *          oTable.fnOpen( this, "Temporary row opened", "info_row" );
		 *        }
		 *      } );
		 *
		 *      oTable = $('#example').dataTable();
		 *    } );
		 */
		this.fnClose = function( nTr )
		{
			this.api( true ).row( nTr ).child.hide();
		};
		
		
		/**
		 * Remove a row for the table
		 *  @param {mixed} target The index of the row from aoData to be deleted, or
		 *    the TR element you want to delete
		 *  @param {function|null} [callBack] Callback function
		 *  @param {bool} [redraw=true] Redraw the table or not
		 *  @returns {array} The row that was deleted
		 *  @dtopt API
		 *  @deprecated Since v1.10
		 *
		 *  @example
		 *    $(document).ready(function() {
		 *      var oTable = $('#example').dataTable();
		 *
		 *      // Immediately remove the first row
		 *      oTable.fnDeleteRow( 0 );
		 *    } );
		 */
		this.fnDeleteRow = function( target, callback, redraw )
		{
			var api = this.api( true );
			var rows = api.rows( target );
			var settings = rows.settings()[0];
			var data = settings.aoData[ rows[0][0] ];
		
			rows.remove();
		
			if ( callback ) {
				callback.call( this, settings, data );
			}
		
			if ( redraw === undefined || redraw ) {
				api.draw();
			}
		
			return data;
		};
		
		
		/**
		 * Restore the table to it's original state in the DOM by removing all of DataTables
		 * enhancements, alterations to the DOM structure of the table and event listeners.
		 *  @param {boolean} [remove=false] Completely remove the table from the DOM
		 *  @dtopt API
		 *  @deprecated Since v1.10
		 *
		 *  @example
		 *    $(document).ready(function() {
		 *      // This example is fairly pointless in reality, but shows how fnDestroy can be used
		 *      var oTable = $('#example').dataTable();
		 *      oTable.fnDestroy();
		 *    } );
		 */
		this.fnDestroy = function ( remove )
		{
			this.api( true ).destroy( remove );
		};
		
		
		/**
		 * Redraw the table
		 *  @param {bool} [complete=true] Re-filter and resort (if enabled) the table before the draw.
		 *  @dtopt API
		 *  @deprecated Since v1.10
		 *
		 *  @example
		 *    $(document).ready(function() {
		 *      var oTable = $('#example').dataTable();
		 *
		 *      // Re-draw the table - you wouldn't want to do it here, but it's an example :-)
		 *      oTable.fnDraw();
		 *    } );
		 */
		this.fnDraw = function( complete )
		{
			// Note that this isn't an exact match to the old call to _fnDraw - it takes
			// into account the new data, but can hold position.
			this.api( true ).draw( complete );
		};
		
		
		/**
		 * Filter the input based on data
		 *  @param {string} sInput String to filter the table on
		 *  @param {int|null} [iColumn] Column to limit filtering to
		 *  @param {bool} [bRegex=false] Treat as regular expression or not
		 *  @param {bool} [bSmart=true] Perform smart filtering or not
		 *  @param {bool} [bShowGlobal=true] Show the input global filter in it's input box(es)
		 *  @param {bool} [bCaseInsensitive=true] Do case-insensitive matching (true) or not (false)
		 *  @dtopt API
		 *  @deprecated Since v1.10
		 *
		 *  @example
		 *    $(document).ready(function() {
		 *      var oTable = $('#example').dataTable();
		 *
		 *      // Sometime later - filter...
		 *      oTable.fnFilter( 'test string' );
		 *    } );
		 */
		this.fnFilter = function( sInput, iColumn, bRegex, bSmart, bShowGlobal, bCaseInsensitive )
		{
			var api = this.api( true );
		
			if ( iColumn === null || iColumn === undefined ) {
				api.search( sInput, bRegex, bSmart, bCaseInsensitive );
			}
			else {
				api.column( iColumn ).search( sInput, bRegex, bSmart, bCaseInsensitive );
			}
		
			api.draw();
		};
		
		
		/**
		 * Get the data for the whole table, an individual row or an individual cell based on the
		 * provided parameters.
		 *  @param {int|node} [src] A TR row node, TD/TH cell node or an integer. If given as
		 *    a TR node then the data source for the whole row will be returned. If given as a
		 *    TD/TH cell node then iCol will be automatically calculated and the data for the
		 *    cell returned. If given as an integer, then this is treated as the aoData internal
		 *    data index for the row (see fnGetPosition) and the data for that row used.
		 *  @param {int} [col] Optional column index that you want the data of.
		 *  @returns {array|object|string} If mRow is undefined, then the data for all rows is
		 *    returned. If mRow is defined, just data for that row, and is iCol is
		 *    defined, only data for the designated cell is returned.
		 *  @dtopt API
		 *  @deprecated Since v1.10
		 *
		 *  @example
		 *    // Row data
		 *    $(document).ready(function() {
		 *      oTable = $('#example').dataTable();
		 *
		 *      oTable.$('tr').click( function () {
		 *        var data = oTable.fnGetData( this );
		 *        // ... do something with the array / object of data for the row
		 *      } );
		 *    } );
		 *
		 *  @example
		 *    // Individual cell data
		 *    $(document).ready(function() {
		 *      oTable = $('#example').dataTable();
		 *
		 *      oTable.$('td').click( function () {
		 *        var sData = oTable.fnGetData( this );
		 *        alert( 'The cell clicked on had the value of '+sData );
		 *      } );
		 *    } );
		 */
		this.fnGetData = function( src, col )
		{
			var api = this.api( true );
		
			if ( src !== undefined ) {
				var type = src.nodeName ? src.nodeName.toLowerCase() : '';
		
				return col !== undefined || type == 'td' || type == 'th' ?
					api.cell( src, col ).data() :
					api.row( src ).data() || null;
			}
		
			return api.data().toArray();
		};
		
		
		/**
		 * Get an array of the TR nodes that are used in the table's body. Note that you will
		 * typically want to use the '$' API method in preference to this as it is more
		 * flexible.
		 *  @param {int} [iRow] Optional row index for the TR element you want
		 *  @returns {array|node} If iRow is undefined, returns an array of all TR elements
		 *    in the table's body, or iRow is defined, just the TR element requested.
		 *  @dtopt API
		 *  @deprecated Since v1.10
		 *
		 *  @example
		 *    $(document).ready(function() {
		 *      var oTable = $('#example').dataTable();
		 *
		 *      // Get the nodes from the table
		 *      var nNodes = oTable.fnGetNodes( );
		 *    } );
		 */
		this.fnGetNodes = function( iRow )
		{
			var api = this.api( true );
		
			return iRow !== undefined ?
				api.row( iRow ).node() :
				api.rows().nodes().flatten().toArray();
		};
		
		
		/**
		 * Get the array indexes of a particular cell from it's DOM element
		 * and column index including hidden columns
		 *  @param {node} node this can either be a TR, TD or TH in the table's body
		 *  @returns {int} If nNode is given as a TR, then a single index is returned, or
		 *    if given as a cell, an array of [row index, column index (visible),
		 *    column index (all)] is given.
		 *  @dtopt API
		 *  @deprecated Since v1.10
		 *
		 *  @example
		 *    $(document).ready(function() {
		 *      $('#example tbody td').click( function () {
		 *        // Get the position of the current data from the node
		 *        var aPos = oTable.fnGetPosition( this );
		 *
		 *        // Get the data array for this row
		 *        var aData = oTable.fnGetData( aPos[0] );
		 *
		 *        // Update the data array and return the value
		 *        aData[ aPos[1] ] = 'clicked';
		 *        this.innerHTML = 'clicked';
		 *      } );
		 *
		 *      // Init DataTables
		 *      oTable = $('#example').dataTable();
		 *    } );
		 */
		this.fnGetPosition = function( node )
		{
			var api = this.api( true );
			var nodeName = node.nodeName.toUpperCase();
		
			if ( nodeName == 'TR' ) {
				return api.row( node ).index();
			}
			else if ( nodeName == 'TD' || nodeName == 'TH' ) {
				var cell = api.cell( node ).index();
		
				return [
					cell.row,
					cell.columnVisible,
					cell.column
				];
			}
			return null;
		};
		
		
		/**
		 * Check to see if a row is 'open' or not.
		 *  @param {node} nTr the table row to check
		 *  @returns {boolean} true if the row is currently open, false otherwise
		 *  @dtopt API
		 *  @deprecated Since v1.10
		 *
		 *  @example
		 *    $(document).ready(function() {
		 *      var oTable;
		 *
		 *      // 'open' an information row when a row is clicked on
		 *      $('#example tbody tr').click( function () {
		 *        if ( oTable.fnIsOpen(this) ) {
		 *          oTable.fnClose( this );
		 *        } else {
		 *          oTable.fnOpen( this, "Temporary row opened", "info_row" );
		 *        }
		 *      } );
		 *
		 *      oTable = $('#example').dataTable();
		 *    } );
		 */
		this.fnIsOpen = function( nTr )
		{
			return this.api( true ).row( nTr ).child.isShown();
		};
		
		
		/**
		 * This function will place a new row directly after a row which is currently
		 * on display on the page, with the HTML contents that is passed into the
		 * function. This can be used, for example, to ask for confirmation that a
		 * particular record should be deleted.
		 *  @param {node} nTr The table row to 'open'
		 *  @param {string|node|jQuery} mHtml The HTML to put into the row
		 *  @param {string} sClass Class to give the new TD cell
		 *  @returns {node} The row opened. Note that if the table row passed in as the
		 *    first parameter, is not found in the table, this method will silently
		 *    return.
		 *  @dtopt API
		 *  @deprecated Since v1.10
		 *
		 *  @example
		 *    $(document).ready(function() {
		 *      var oTable;
		 *
		 *      // 'open' an information row when a row is clicked on
		 *      $('#example tbody tr').click( function () {
		 *        if ( oTable.fnIsOpen(this) ) {
		 *          oTable.fnClose( this );
		 *        } else {
		 *          oTable.fnOpen( this, "Temporary row opened", "info_row" );
		 *        }
		 *      } );
		 *
		 *      oTable = $('#example').dataTable();
		 *    } );
		 */
		this.fnOpen = function( nTr, mHtml, sClass )
		{
			return this.api( true )
				.row( nTr )
				.child( mHtml, sClass )
				.show()
				.child()[0];
		};
		
		
		/**
		 * Change the pagination - provides the internal logic for pagination in a simple API
		 * function. With this function you can have a DataTables table go to the next,
		 * previous, first or last pages.
		 *  @param {string|int} mAction Paging action to take: "first", "previous", "next" or "last"
		 *    or page number to jump to (integer), note that page 0 is the first page.
		 *  @param {bool} [bRedraw=true] Redraw the table or not
		 *  @dtopt API
		 *  @deprecated Since v1.10
		 *
		 *  @example
		 *    $(document).ready(function() {
		 *      var oTable = $('#example').dataTable();
		 *      oTable.fnPageChange( 'next' );
		 *    } );
		 */
		this.fnPageChange = function ( mAction, bRedraw )
		{
			var api = this.api( true ).page( mAction );
		
			if ( bRedraw === undefined || bRedraw ) {
				api.draw(false);
			}
		};
		
		
		/**
		 * Show a particular column
		 *  @param {int} iCol The column whose display should be changed
		 *  @param {bool} bShow Show (true) or hide (false) the column
		 *  @param {bool} [bRedraw=true] Redraw the table or not
		 *  @dtopt API
		 *  @deprecated Since v1.10
		 *
		 *  @example
		 *    $(document).ready(function() {
		 *      var oTable = $('#example').dataTable();
		 *
		 *      // Hide the second column after initialisation
		 *      oTable.fnSetColumnVis( 1, false );
		 *    } );
		 */
		this.fnSetColumnVis = function ( iCol, bShow, bRedraw )
		{
			var api = this.api( true ).column( iCol ).visible( bShow );
		
			if ( bRedraw === undefined || bRedraw ) {
				api.columns.adjust().draw();
			}
		};
		
		
		/**
		 * Get the settings for a particular table for external manipulation
		 *  @returns {object} DataTables settings object. See
		 *    {@link DataTable.models.oSettings}
		 *  @dtopt API
		 *  @deprecated Since v1.10
		 *
		 *  @example
		 *    $(document).ready(function() {
		 *      var oTable = $('#example').dataTable();
		 *      var oSettings = oTable.fnSettings();
		 *
		 *      // Show an example parameter from the settings
		 *      alert( oSettings._iDisplayStart );
		 *    } );
		 */
		this.fnSettings = function()
		{
			return _fnSettingsFromNode( this[_ext.iApiIndex] );
		};
		
		
		/**
		 * Sort the table by a particular column
		 *  @param {int} iCol the data index to sort on. Note that this will not match the
		 *    'display index' if you have hidden data entries
		 *  @dtopt API
		 *  @deprecated Since v1.10
		 *
		 *  @example
		 *    $(document).ready(function() {
		 *      var oTable = $('#example').dataTable();
		 *
		 *      // Sort immediately with columns 0 and 1
		 *      oTable.fnSort( [ [0,'asc'], [1,'asc'] ] );
		 *    } );
		 */
		this.fnSort = function( aaSort )
		{
			this.api( true ).order( aaSort ).draw();
		};
		
		
		/**
		 * Attach a sort listener to an element for a given column
		 *  @param {node} nNode the element to attach the sort listener to
		 *  @param {int} iColumn the column that a click on this node will sort on
		 *  @param {function} [fnCallback] callback function when sort is run
		 *  @dtopt API
		 *  @deprecated Since v1.10
		 *
		 *  @example
		 *    $(document).ready(function() {
		 *      var oTable = $('#example').dataTable();
		 *
		 *      // Sort on column 1, when 'sorter' is clicked on
		 *      oTable.fnSortListener( document.getElementById('sorter'), 1 );
		 *    } );
		 */
		this.fnSortListener = function( nNode, iColumn, fnCallback )
		{
			this.api( true ).order.listener( nNode, iColumn, fnCallback );
		};
		
		
		/**
		 * Update a table cell or row - this method will accept either a single value to
		 * update the cell with, an array of values with one element for each column or
		 * an object in the same format as the original data source. The function is
		 * self-referencing in order to make the multi column updates easier.
		 *  @param {object|array|string} mData Data to update the cell/row with
		 *  @param {node|int} mRow TR element you want to update or the aoData index
		 *  @param {int} [iColumn] The column to update, give as null or undefined to
		 *    update a whole row.
		 *  @param {bool} [bRedraw=true] Redraw the table or not
		 *  @param {bool} [bAction=true] Perform pre-draw actions or not
		 *  @returns {int} 0 on success, 1 on error
		 *  @dtopt API
		 *  @deprecated Since v1.10
		 *
		 *  @example
		 *    $(document).ready(function() {
		 *      var oTable = $('#example').dataTable();
		 *      oTable.fnUpdate( 'Example update', 0, 0 ); // Single cell
		 *      oTable.fnUpdate( ['a', 'b', 'c', 'd', 'e'], $('tbody tr')[0] ); // Row
		 *    } );
		 */
		this.fnUpdate = function( mData, mRow, iColumn, bRedraw, bAction )
		{
			var api = this.api( true );
		
			if ( iColumn === undefined || iColumn === null ) {
				api.row( mRow ).data( mData );
			}
			else {
				api.cell( mRow, iColumn ).data( mData );
			}
		
			if ( bAction === undefined || bAction ) {
				api.columns.adjust();
			}
		
			if ( bRedraw === undefined || bRedraw ) {
				api.draw();
			}
			return 0;
		};
		
		
		/**
		 * Provide a common method for plug-ins to check the version of DataTables being used, in order
		 * to ensure compatibility.
		 *  @param {string} sVersion Version string to check for, in the format "X.Y.Z". Note that the
		 *    formats "X" and "X.Y" are also acceptable.
		 *  @returns {boolean} true if this version of DataTables is greater or equal to the required
		 *    version, or false if this version of DataTales is not suitable
		 *  @method
		 *  @dtopt API
		 *  @deprecated Since v1.10
		 *
		 *  @example
		 *    $(document).ready(function() {
		 *      var oTable = $('#example').dataTable();
		 *      alert( oTable.fnVersionCheck( '1.9.0' ) );
		 *    } );
		 */
		this.fnVersionCheck = _ext.fnVersionCheck;
		

		var _that = this;
		var emptyInit = options === undefined;
		var len = this.length;

		if ( emptyInit ) {
			options = {};
		}

		this.oApi = this.internal = _ext.internal;

		// Extend with old style plug-in API methods
		for ( var fn in DataTable.ext.internal ) {
			if ( fn ) {
				this[fn] = _fnExternApiFunc(fn);
			}
		}

		this.each(function() {
			// For each initialisation we want to give it a clean initialisation
			// object that can be bashed around
			var o = {};
			var oInit = len > 1 ? // optimisation for single table case
				_fnExtend( o, options, true ) :
				options;

			/*global oInit,_that,emptyInit*/
			var i=0, iLen, j, jLen, k, kLen;
			var sId = this.getAttribute( 'id' );
			var bInitHandedOff = false;
			var defaults = DataTable.defaults;
			var $this = $(this);
			
			
			/* Sanity check */
			if ( this.nodeName.toLowerCase() != 'table' )
			{
				_fnLog( null, 0, 'Non-table node initialisation ('+this.nodeName+')', 2 );
				return;
			}
			
			/* Backwards compatibility for the defaults */
			_fnCompatOpts( defaults );
			_fnCompatCols( defaults.column );
			
			/* Convert the camel-case defaults to Hungarian */
			_fnCamelToHungarian( defaults, defaults, true );
			_fnCamelToHungarian( defaults.column, defaults.column, true );
			
			/* Setting up the initialisation object */
			_fnCamelToHungarian( defaults, $.extend( oInit, $this.data() ) );
			
			
			
			/* Check to see if we are re-initialising a table */
			var allSettings = DataTable.settings;
			for ( i=0, iLen=allSettings.length ; i<iLen ; i++ )
			{
				var s = allSettings[i];
			
				/* Base check on table node */
				if ( s.nTable == this || s.nTHead.parentNode == this || (s.nTFoot && s.nTFoot.parentNode == this) )
				{
					var bRetrieve = oInit.bRetrieve !== undefined ? oInit.bRetrieve : defaults.bRetrieve;
					var bDestroy = oInit.bDestroy !== undefined ? oInit.bDestroy : defaults.bDestroy;
			
					if ( emptyInit || bRetrieve )
					{
						return s.oInstance;
					}
					else if ( bDestroy )
					{
						s.oInstance.fnDestroy();
						break;
					}
					else
					{
						_fnLog( s, 0, 'Cannot reinitialise DataTable', 3 );
						return;
					}
				}
			
				/* If the element we are initialising has the same ID as a table which was previously
				 * initialised, but the table nodes don't match (from before) then we destroy the old
				 * instance by simply deleting it. This is under the assumption that the table has been
				 * destroyed by other methods. Anyone using non-id selectors will need to do this manually
				 */
				if ( s.sTableId == this.id )
				{
					allSettings.splice( i, 1 );
					break;
				}
			}
			
			/* Ensure the table has an ID - required for accessibility */
			if ( sId === null || sId === "" )
			{
				sId = "DataTables_Table_"+(DataTable.ext._unique++);
				this.id = sId;
			}
			
			/* Create the settings object for this table and set some of the default parameters */
			var oSettings = $.extend( true, {}, DataTable.models.oSettings, {
				"sDestroyWidth": $this[0].style.width,
				"sInstance":     sId,
				"sTableId":      sId
			} );
			oSettings.nTable = this;
			oSettings.oApi   = _that.internal;
			oSettings.oInit  = oInit;
			
			allSettings.push( oSettings );
			
			// Need to add the instance after the instance after the settings object has been added
			// to the settings array, so we can self reference the table instance if more than one
			oSettings.oInstance = (_that.length===1) ? _that : $this.dataTable();
			
			// Backwards compatibility, before we apply all the defaults
			_fnCompatOpts( oInit );
			
			if ( oInit.oLanguage )
			{
				_fnLanguageCompat( oInit.oLanguage );
			}
			
			// If the length menu is given, but the init display length is not, use the length menu
			if ( oInit.aLengthMenu && ! oInit.iDisplayLength )
			{
				oInit.iDisplayLength = $.isArray( oInit.aLengthMenu[0] ) ?
					oInit.aLengthMenu[0][0] : oInit.aLengthMenu[0];
			}
			
			// Apply the defaults and init options to make a single init object will all
			// options defined from defaults and instance options.
			oInit = _fnExtend( $.extend( true, {}, defaults ), oInit );
			
			
			// Map the initialisation options onto the settings object
			_fnMap( oSettings.oFeatures, oInit, [
				"bPaginate",
				"bLengthChange",
				"bFilter",
				"bSort",
				"bSortMulti",
				"bInfo",
				"bProcessing",
				"bAutoWidth",
				"bSortClasses",
				"bServerSide",
				"bDeferRender"
			] );
			_fnMap( oSettings, oInit, [
				"asStripeClasses",
				"ajax",
				"fnServerData",
				"fnFormatNumber",
				"sServerMethod",
				"aaSorting",
				"aaSortingFixed",
				"aLengthMenu",
				"sPaginationType",
				"sAjaxSource",
				"sAjaxDataProp",
				"iStateDuration",
				"sDom",
				"bSortCellsTop",
				"iTabIndex",
				"fnStateLoadCallback",
				"fnStateSaveCallback",
				"renderer",
				"searchDelay",
				"rowId",
				[ "iCookieDuration", "iStateDuration" ], // backwards compat
				[ "oSearch", "oPreviousSearch" ],
				[ "aoSearchCols", "aoPreSearchCols" ],
				[ "iDisplayLength", "_iDisplayLength" ]
			] );
			_fnMap( oSettings.oScroll, oInit, [
				[ "sScrollX", "sX" ],
				[ "sScrollXInner", "sXInner" ],
				[ "sScrollY", "sY" ],
				[ "bScrollCollapse", "bCollapse" ]
			] );
			_fnMap( oSettings.oLanguage, oInit, "fnInfoCallback" );
			
			/* Callback functions which are array driven */
			_fnCallbackReg( oSettings, 'aoDrawCallback',       oInit.fnDrawCallback,      'user' );
			_fnCallbackReg( oSettings, 'aoServerParams',       oInit.fnServerParams,      'user' );
			_fnCallbackReg( oSettings, 'aoStateSaveParams',    oInit.fnStateSaveParams,   'user' );
			_fnCallbackReg( oSettings, 'aoStateLoadParams',    oInit.fnStateLoadParams,   'user' );
			_fnCallbackReg( oSettings, 'aoStateLoaded',        oInit.fnStateLoaded,       'user' );
			_fnCallbackReg( oSettings, 'aoRowCallback',        oInit.fnRowCallback,       'user' );
			_fnCallbackReg( oSettings, 'aoRowCreatedCallback', oInit.fnCreatedRow,        'user' );
			_fnCallbackReg( oSettings, 'aoHeaderCallback',     oInit.fnHeaderCallback,    'user' );
			_fnCallbackReg( oSettings, 'aoFooterCallback',     oInit.fnFooterCallback,    'user' );
			_fnCallbackReg( oSettings, 'aoInitComplete',       oInit.fnInitComplete,      'user' );
			_fnCallbackReg( oSettings, 'aoPreDrawCallback',    oInit.fnPreDrawCallback,   'user' );
			
			oSettings.rowIdFn = _fnGetObjectDataFn( oInit.rowId );
			
			/* Browser support detection */
			_fnBrowserDetect( oSettings );
			
			var oClasses = oSettings.oClasses;
			
			$.extend( oClasses, DataTable.ext.classes, oInit.oClasses );
			$this.addClass( oClasses.sTable );
			
			
			if ( oSettings.iInitDisplayStart === undefined )
			{
				/* Display start point, taking into account the save saving */
				oSettings.iInitDisplayStart = oInit.iDisplayStart;
				oSettings._iDisplayStart = oInit.iDisplayStart;
			}
			
			if ( oInit.iDeferLoading !== null )
			{
				oSettings.bDeferLoading = true;
				var tmp = $.isArray( oInit.iDeferLoading );
				oSettings._iRecordsDisplay = tmp ? oInit.iDeferLoading[0] : oInit.iDeferLoading;
				oSettings._iRecordsTotal = tmp ? oInit.iDeferLoading[1] : oInit.iDeferLoading;
			}
			
			/* Language definitions */
			var oLanguage = oSettings.oLanguage;
			$.extend( true, oLanguage, oInit.oLanguage );
			
			if ( oLanguage.sUrl )
			{
				/* Get the language definitions from a file - because this Ajax call makes the language
				 * get async to the remainder of this function we use bInitHandedOff to indicate that
				 * _fnInitialise will be fired by the returned Ajax handler, rather than the constructor
				 */
				$.ajax( {
					dataType: 'json',
					url: oLanguage.sUrl,
					success: function ( json ) {
						_fnLanguageCompat( json );
						_fnCamelToHungarian( defaults.oLanguage, json );
						$.extend( true, oLanguage, json );
						_fnInitialise( oSettings );
					},
					error: function () {
						// Error occurred loading language file, continue on as best we can
						_fnInitialise( oSettings );
					}
				} );
				bInitHandedOff = true;
			}
			
			/*
			 * Stripes
			 */
			if ( oInit.asStripeClasses === null )
			{
				oSettings.asStripeClasses =[
					oClasses.sStripeOdd,
					oClasses.sStripeEven
				];
			}
			
			/* Remove row stripe classes if they are already on the table row */
			var stripeClasses = oSettings.asStripeClasses;
			var rowOne = $this.children('tbody').find('tr').eq(0);
			if ( $.inArray( true, $.map( stripeClasses, function(el, i) {
				return rowOne.hasClass(el);
			} ) ) !== -1 ) {
				$('tbody tr', this).removeClass( stripeClasses.join(' ') );
				oSettings.asDestroyStripes = stripeClasses.slice();
			}
			
			/*
			 * Columns
			 * See if we should load columns automatically or use defined ones
			 */
			var anThs = [];
			var aoColumnsInit;
			var nThead = this.getElementsByTagName('thead');
			if ( nThead.length !== 0 )
			{
				_fnDetectHeader( oSettings.aoHeader, nThead[0] );
				anThs = _fnGetUniqueThs( oSettings );
			}
			
			/* If not given a column array, generate one with nulls */
			if ( oInit.aoColumns === null )
			{
				aoColumnsInit = [];
				for ( i=0, iLen=anThs.length ; i<iLen ; i++ )
				{
					aoColumnsInit.push( null );
				}
			}
			else
			{
				aoColumnsInit = oInit.aoColumns;
			}
			
			/* Add the columns */
			for ( i=0, iLen=aoColumnsInit.length ; i<iLen ; i++ )
			{
				_fnAddColumn( oSettings, anThs ? anThs[i] : null );
			}
			
			/* Apply the column definitions */
			_fnApplyColumnDefs( oSettings, oInit.aoColumnDefs, aoColumnsInit, function (iCol, oDef) {
				_fnColumnOptions( oSettings, iCol, oDef );
			} );
			
			/* HTML5 attribute detection - build an mData object automatically if the
			 * attributes are found
			 */
			if ( rowOne.length ) {
				var a = function ( cell, name ) {
					return cell.getAttribute( 'data-'+name ) !== null ? name : null;
				};
			
				$( rowOne[0] ).children('th, td').each( function (i, cell) {
					var col = oSettings.aoColumns[i];
			
					if ( col.mData === i ) {
						var sort = a( cell, 'sort' ) || a( cell, 'order' );
						var filter = a( cell, 'filter' ) || a( cell, 'search' );
			
						if ( sort !== null || filter !== null ) {
							col.mData = {
								_:      i+'.display',
								sort:   sort !== null   ? i+'.@data-'+sort   : undefined,
								type:   sort !== null   ? i+'.@data-'+sort   : undefined,
								filter: filter !== null ? i+'.@data-'+filter : undefined
							};
			
							_fnColumnOptions( oSettings, i );
						}
					}
				} );
			}
			
			var features = oSettings.oFeatures;
			var loadedInit = function () {
				/*
				 * Sorting
				 * @todo For modularisation (1.11) this needs to do into a sort start up handler
				 */
			
				// If aaSorting is not defined, then we use the first indicator in asSorting
				// in case that has been altered, so the default sort reflects that option
				if ( oInit.aaSorting === undefined ) {
					var sorting = oSettings.aaSorting;
					for ( i=0, iLen=sorting.length ; i<iLen ; i++ ) {
						sorting[i][1] = oSettings.aoColumns[ i ].asSorting[0];
					}
				}
			
				/* Do a first pass on the sorting classes (allows any size changes to be taken into
				 * account, and also will apply sorting disabled classes if disabled
				 */
				_fnSortingClasses( oSettings );
			
				if ( features.bSort ) {
					_fnCallbackReg( oSettings, 'aoDrawCallback', function () {
						if ( oSettings.bSorted ) {
							var aSort = _fnSortFlatten( oSettings );
							var sortedColumns = {};
			
							$.each( aSort, function (i, val) {
								sortedColumns[ val.src ] = val.dir;
							} );
			
							_fnCallbackFire( oSettings, null, 'order', [oSettings, aSort, sortedColumns] );
							_fnSortAria( oSettings );
						}
					} );
				}
			
				_fnCallbackReg( oSettings, 'aoDrawCallback', function () {
					if ( oSettings.bSorted || _fnDataSource( oSettings ) === 'ssp' || features.bDeferRender ) {
						_fnSortingClasses( oSettings );
					}
				}, 'sc' );
			
			
				/*
				 * Final init
				 * Cache the header, body and footer as required, creating them if needed
				 */
			
				// Work around for Webkit bug 83867 - store the caption-side before removing from doc
				var captions = $this.children('caption').each( function () {
					this._captionSide = $(this).css('caption-side');
				} );
			
				var thead = $this.children('thead');
				if ( thead.length === 0 ) {
					thead = $('<thead/>').appendTo($this);
				}
				oSettings.nTHead = thead[0];
			
				var tbody = $this.children('tbody');
				if ( tbody.length === 0 ) {
					tbody = $('<tbody/>').appendTo($this);
				}
				oSettings.nTBody = tbody[0];
			
				var tfoot = $this.children('tfoot');
				if ( tfoot.length === 0 && captions.length > 0 && (oSettings.oScroll.sX !== "" || oSettings.oScroll.sY !== "") ) {
					// If we are a scrolling table, and no footer has been given, then we need to create
					// a tfoot element for the caption element to be appended to
					tfoot = $('<tfoot/>').appendTo($this);
				}
			
				if ( tfoot.length === 0 || tfoot.children().length === 0 ) {
					$this.addClass( oClasses.sNoFooter );
				}
				else if ( tfoot.length > 0 ) {
					oSettings.nTFoot = tfoot[0];
					_fnDetectHeader( oSettings.aoFooter, oSettings.nTFoot );
				}
			
				/* Check if there is data passing into the constructor */
				if ( oInit.aaData ) {
					for ( i=0 ; i<oInit.aaData.length ; i++ ) {
						_fnAddData( oSettings, oInit.aaData[ i ] );
					}
				}
				else if ( oSettings.bDeferLoading || _fnDataSource( oSettings ) == 'dom' ) {
					/* Grab the data from the page - only do this when deferred loading or no Ajax
					 * source since there is no point in reading the DOM data if we are then going
					 * to replace it with Ajax data
					 */
					_fnAddTr( oSettings, $(oSettings.nTBody).children('tr') );
				}
			
				/* Copy the data index array */
				oSettings.aiDisplay = oSettings.aiDisplayMaster.slice();
			
				/* Initialisation complete - table can be drawn */
				oSettings.bInitialised = true;
			
				/* Check if we need to initialise the table (it might not have been handed off to the
				 * language processor)
				 */
				if ( bInitHandedOff === false ) {
					_fnInitialise( oSettings );
				}
			};
			
			/* Must be done after everything which can be overridden by the state saving! */
			if ( oInit.bStateSave )
			{
				features.bStateSave = true;
				_fnCallbackReg( oSettings, 'aoDrawCallback', _fnSaveState, 'state_save' );
				_fnLoadState( oSettings, oInit, loadedInit );
			}
			else {
				loadedInit();
			}
			
		} );
		_that = null;
		return this;
	};

	
	/*
	 * It is useful to have variables which are scoped locally so only the
	 * DataTables functions can access them and they don't leak into global space.
	 * At the same time these functions are often useful over multiple files in the
	 * core and API, so we list, or at least document, all variables which are used
	 * by DataTables as private variables here. This also ensures that there is no
	 * clashing of variable names and that they can easily referenced for reuse.
	 */
	
	
	// Defined else where
	//  _selector_run
	//  _selector_opts
	//  _selector_first
	//  _selector_row_indexes
	
	var _ext; // DataTable.ext
	var _Api; // DataTable.Api
	var _api_register; // DataTable.Api.register
	var _api_registerPlural; // DataTable.Api.registerPlural
	
	var _re_dic = {};
	var _re_new_lines = /[\r\n]/g;
	var _re_html = /<.*?>/g;
	
	// This is not strict ISO8601 - Date.parse() is quite lax, although
	// implementations differ between browsers.
	var _re_date = /^\d{2,4}[\.\/\-]\d{1,2}[\.\/\-]\d{1,2}([T ]{1}\d{1,2}[:\.]\d{2}([\.:]\d{2})?)?$/;
	
	// Escape regular expression special characters
	var _re_escape_regex = new RegExp( '(\\' + [ '/', '.', '*', '+', '?', '|', '(', ')', '[', ']', '{', '}', '\\', '$', '^', '-' ].join('|\\') + ')', 'g' );
	
	// http://en.wikipedia.org/wiki/Foreign_exchange_market
	// - \u20BD - Russian ruble.
	// - \u20a9 - South Korean Won
	// - \u20BA - Turkish Lira
	// - \u20B9 - Indian Rupee
	// - R - Brazil (R$) and South Africa
	// - fr - Swiss Franc
	// - kr - Swedish krona, Norwegian krone and Danish krone
	// - \u2009 is thin space and \u202F is narrow no-break space, both used in many
	//   standards as thousands separators.
	var _re_formatted_numeric = /[',$£€¥%\u2009\u202F\u20BD\u20a9\u20BArfk]/gi;
	
	
	var _empty = function ( d ) {
		return !d || d === true || d === '-' ? true : false;
	};
	
	
	var _intVal = function ( s ) {
		var integer = parseInt( s, 10 );
		return !isNaN(integer) && isFinite(s) ? integer : null;
	};
	
	// Convert from a formatted number with characters other than `.` as the
	// decimal place, to a Javascript number
	var _numToDecimal = function ( num, decimalPoint ) {
		// Cache created regular expressions for speed as this function is called often
		if ( ! _re_dic[ decimalPoint ] ) {
			_re_dic[ decimalPoint ] = new RegExp( _fnEscapeRegex( decimalPoint ), 'g' );
		}
		return typeof num === 'string' && decimalPoint !== '.' ?
			num.replace( /\./g, '' ).replace( _re_dic[ decimalPoint ], '.' ) :
			num;
	};
	
	
	var _isNumber = function ( d, decimalPoint, formatted ) {
		var strType = typeof d === 'string';
	
		// If empty return immediately so there must be a number if it is a
		// formatted string (this stops the string "k", or "kr", etc being detected
		// as a formatted number for currency
		if ( _empty( d ) ) {
			return true;
		}
	
		if ( decimalPoint && strType ) {
			d = _numToDecimal( d, decimalPoint );
		}
	
		if ( formatted && strType ) {
			d = d.replace( _re_formatted_numeric, '' );
		}
	
		return !isNaN( parseFloat(d) ) && isFinite( d );
	};
	
	
	// A string without HTML in it can be considered to be HTML still
	var _isHtml = function ( d ) {
		return _empty( d ) || typeof d === 'string';
	};
	
	
	var _htmlNumeric = function ( d, decimalPoint, formatted ) {
		if ( _empty( d ) ) {
			return true;
		}
	
		var html = _isHtml( d );
		return ! html ?
			null :
			_isNumber( _stripHtml( d ), decimalPoint, formatted ) ?
				true :
				null;
	};
	
	
	var _pluck = function ( a, prop, prop2 ) {
		var out = [];
		var i=0, ien=a.length;
	
		// Could have the test in the loop for slightly smaller code, but speed
		// is essential here
		if ( prop2 !== undefined ) {
			for ( ; i<ien ; i++ ) {
				if ( a[i] && a[i][ prop ] ) {
					out.push( a[i][ prop ][ prop2 ] );
				}
			}
		}
		else {
			for ( ; i<ien ; i++ ) {
				if ( a[i] ) {
					out.push( a[i][ prop ] );
				}
			}
		}
	
		return out;
	};
	
	
	// Basically the same as _pluck, but rather than looping over `a` we use `order`
	// as the indexes to pick from `a`
	var _pluck_order = function ( a, order, prop, prop2 )
	{
		var out = [];
		var i=0, ien=order.length;
	
		// Could have the test in the loop for slightly smaller code, but speed
		// is essential here
		if ( prop2 !== undefined ) {
			for ( ; i<ien ; i++ ) {
				if ( a[ order[i] ][ prop ] ) {
					out.push( a[ order[i] ][ prop ][ prop2 ] );
				}
			}
		}
		else {
			for ( ; i<ien ; i++ ) {
				out.push( a[ order[i] ][ prop ] );
			}
		}
	
		return out;
	};
	
	
	var _range = function ( len, start )
	{
		var out = [];
		var end;
	
		if ( start === undefined ) {
			start = 0;
			end = len;
		}
		else {
			end = start;
			start = len;
		}
	
		for ( var i=start ; i<end ; i++ ) {
			out.push( i );
		}
	
		return out;
	};
	
	
	var _removeEmpty = function ( a )
	{
		var out = [];
	
		for ( var i=0, ien=a.length ; i<ien ; i++ ) {
			if ( a[i] ) { // careful - will remove all falsy values!
				out.push( a[i] );
			}
		}
	
		return out;
	};
	
	
	var _stripHtml = function ( d ) {
		return d.replace( _re_html, '' );
	};
	
	
	/**
	 * Determine if all values in the array are unique. This means we can short
	 * cut the _unique method at the cost of a single loop. A sorted array is used
	 * to easily check the values.
	 *
	 * @param  {array} src Source array
	 * @return {boolean} true if all unique, false otherwise
	 * @ignore
	 */
	var _areAllUnique = function ( src ) {
		if ( src.length < 2 ) {
			return true;
		}
	
		var sorted = src.slice().sort();
		var last = sorted[0];
	
		for ( var i=1, ien=sorted.length ; i<ien ; i++ ) {
			if ( sorted[i] === last ) {
				return false;
			}
	
			last = sorted[i];
		}
	
		return true;
	};
	
	
	/**
	 * Find the unique elements in a source array.
	 *
	 * @param  {array} src Source array
	 * @return {array} Array of unique items
	 * @ignore
	 */
	var _unique = function ( src )
	{
		if ( _areAllUnique( src ) ) {
			return src.slice();
		}
	
		// A faster unique method is to use object keys to identify used values,
		// but this doesn't work with arrays or objects, which we must also
		// consider. See jsperf.com/compare-array-unique-versions/4 for more
		// information.
		var
			out = [],
			val,
			i, ien=src.length,
			j, k=0;
	
		again: for ( i=0 ; i<ien ; i++ ) {
			val = src[i];
	
			for ( j=0 ; j<k ; j++ ) {
				if ( out[j] === val ) {
					continue again;
				}
			}
	
			out.push( val );
			k++;
		}
	
		return out;
	};
	
	
	/**
	 * DataTables utility methods
	 * 
	 * This namespace provides helper methods that DataTables uses internally to
	 * create a DataTable, but which are not exclusively used only for DataTables.
	 * These methods can be used by extension authors to save the duplication of
	 * code.
	 *
	 *  @namespace
	 */
	DataTable.util = {
		/**
		 * Throttle the calls to a function. Arguments and context are maintained
		 * for the throttled function.
		 *
		 * @param {function} fn Function to be called
		 * @param {integer} freq Call frequency in mS
		 * @return {function} Wrapped function
		 */
		throttle: function ( fn, freq ) {
			var
				frequency = freq !== undefined ? freq : 200,
				last,
				timer;
	
			return function () {
				var
					that = this,
					now  = +new Date(),
					args = arguments;
	
				if ( last && now < last + frequency ) {
					clearTimeout( timer );
	
					timer = setTimeout( function () {
						last = undefined;
						fn.apply( that, args );
					}, frequency );
				}
				else {
					last = now;
					fn.apply( that, args );
				}
			};
		},
	
	
		/**
		 * Escape a string such that it can be used in a regular expression
		 *
		 *  @param {string} val string to escape
		 *  @returns {string} escaped string
		 */
		escapeRegex: function ( val ) {
			return val.replace( _re_escape_regex, '\\$1' );
		}
	};
	
	
	
	/**
	 * Create a mapping object that allows camel case parameters to be looked up
	 * for their Hungarian counterparts. The mapping is stored in a private
	 * parameter called `_hungarianMap` which can be accessed on the source object.
	 *  @param {object} o
	 *  @memberof DataTable#oApi
	 */
	function _fnHungarianMap ( o )
	{
		var
			hungarian = 'a aa ai ao as b fn i m o s ',
			match,
			newKey,
			map = {};
	
		$.each( o, function (key, val) {
			match = key.match(/^([^A-Z]+?)([A-Z])/);
	
			if ( match && hungarian.indexOf(match[1]+' ') !== -1 )
			{
				newKey = key.replace( match[0], match[2].toLowerCase() );
				map[ newKey ] = key;
	
				if ( match[1] === 'o' )
				{
					_fnHungarianMap( o[key] );
				}
			}
		} );
	
		o._hungarianMap = map;
	}
	
	
	/**
	 * Convert from camel case parameters to Hungarian, based on a Hungarian map
	 * created by _fnHungarianMap.
	 *  @param {object} src The model object which holds all parameters that can be
	 *    mapped.
	 *  @param {object} user The object to convert from camel case to Hungarian.
	 *  @param {boolean} force When set to `true`, properties which already have a
	 *    Hungarian value in the `user` object will be overwritten. Otherwise they
	 *    won't be.
	 *  @memberof DataTable#oApi
	 */
	function _fnCamelToHungarian ( src, user, force )
	{
		if ( ! src._hungarianMap ) {
			_fnHungarianMap( src );
		}
	
		var hungarianKey;
	
		$.each( user, function (key, val) {
			hungarianKey = src._hungarianMap[ key ];
	
			if ( hungarianKey !== undefined && (force || user[hungarianKey] === undefined) )
			{
				// For objects, we need to buzz down into the object to copy parameters
				if ( hungarianKey.charAt(0) === 'o' )
				{
					// Copy the camelCase options over to the hungarian
					if ( ! user[ hungarianKey ] ) {
						user[ hungarianKey ] = {};
					}
					$.extend( true, user[hungarianKey], user[key] );
	
					_fnCamelToHungarian( src[hungarianKey], user[hungarianKey], force );
				}
				else {
					user[hungarianKey] = user[ key ];
				}
			}
		} );
	}
	
	
	/**
	 * Language compatibility - when certain options are given, and others aren't, we
	 * need to duplicate the values over, in order to provide backwards compatibility
	 * with older language files.
	 *  @param {object} oSettings dataTables settings object
	 *  @memberof DataTable#oApi
	 */
	function _fnLanguageCompat( lang )
	{
		var defaults = DataTable.defaults.oLanguage;
		var zeroRecords = lang.sZeroRecords;
	
		/* Backwards compatibility - if there is no sEmptyTable given, then use the same as
		 * sZeroRecords - assuming that is given.
		 */
		if ( ! lang.sEmptyTable && zeroRecords &&
			defaults.sEmptyTable === "No data available in table" )
		{
			_fnMap( lang, lang, 'sZeroRecords', 'sEmptyTable' );
		}
	
		/* Likewise with loading records */
		if ( ! lang.sLoadingRecords && zeroRecords &&
			defaults.sLoadingRecords === "Loading..." )
		{
			_fnMap( lang, lang, 'sZeroRecords', 'sLoadingRecords' );
		}
	
		// Old parameter name of the thousands separator mapped onto the new
		if ( lang.sInfoThousands ) {
			lang.sThousands = lang.sInfoThousands;
		}
	
		var decimal = lang.sDecimal;
		if ( decimal ) {
			_addNumericSort( decimal );
		}
	}
	
	
	/**
	 * Map one parameter onto another
	 *  @param {object} o Object to map
	 *  @param {*} knew The new parameter name
	 *  @param {*} old The old parameter name
	 */
	var _fnCompatMap = function ( o, knew, old ) {
		if ( o[ knew ] !== undefined ) {
			o[ old ] = o[ knew ];
		}
	};
	
	
	/**
	 * Provide backwards compatibility for the main DT options. Note that the new
	 * options are mapped onto the old parameters, so this is an external interface
	 * change only.
	 *  @param {object} init Object to map
	 */
	function _fnCompatOpts ( init )
	{
		_fnCompatMap( init, 'ordering',      'bSort' );
		_fnCompatMap( init, 'orderMulti',    'bSortMulti' );
		_fnCompatMap( init, 'orderClasses',  'bSortClasses' );
		_fnCompatMap( init, 'orderCellsTop', 'bSortCellsTop' );
		_fnCompatMap( init, 'order',         'aaSorting' );
		_fnCompatMap( init, 'orderFixed',    'aaSortingFixed' );
		_fnCompatMap( init, 'paging',        'bPaginate' );
		_fnCompatMap( init, 'pagingType',    'sPaginationType' );
		_fnCompatMap( init, 'pageLength',    'iDisplayLength' );
		_fnCompatMap( init, 'searching',     'bFilter' );
	
		// Boolean initialisation of x-scrolling
		if ( typeof init.sScrollX === 'boolean' ) {
			init.sScrollX = init.sScrollX ? '100%' : '';
		}
		if ( typeof init.scrollX === 'boolean' ) {
			init.scrollX = init.scrollX ? '100%' : '';
		}
	
		// Column search objects are in an array, so it needs to be converted
		// element by element
		var searchCols = init.aoSearchCols;
	
		if ( searchCols ) {
			for ( var i=0, ien=searchCols.length ; i<ien ; i++ ) {
				if ( searchCols[i] ) {
					_fnCamelToHungarian( DataTable.models.oSearch, searchCols[i] );
				}
			}
		}
	}
	
	
	/**
	 * Provide backwards compatibility for column options. Note that the new options
	 * are mapped onto the old parameters, so this is an external interface change
	 * only.
	 *  @param {object} init Object to map
	 */
	function _fnCompatCols ( init )
	{
		_fnCompatMap( init, 'orderable',     'bSortable' );
		_fnCompatMap( init, 'orderData',     'aDataSort' );
		_fnCompatMap( init, 'orderSequence', 'asSorting' );
		_fnCompatMap( init, 'orderDataType', 'sortDataType' );
	
		// orderData can be given as an integer
		var dataSort = init.aDataSort;
		if ( typeof dataSort === 'number' && ! $.isArray( dataSort ) ) {
			init.aDataSort = [ dataSort ];
		}
	}
	
	
	/**
	 * Browser feature detection for capabilities, quirks
	 *  @param {object} settings dataTables settings object
	 *  @memberof DataTable#oApi
	 */
	function _fnBrowserDetect( settings )
	{
		// We don't need to do this every time DataTables is constructed, the values
		// calculated are specific to the browser and OS configuration which we
		// don't expect to change between initialisations
		if ( ! DataTable.__browser ) {
			var browser = {};
			DataTable.__browser = browser;
	
			// Scrolling feature / quirks detection
			var n = $('<div/>')
				.css( {
					position: 'fixed',
					top: 0,
					left: $(window).scrollLeft()*-1, // allow for scrolling
					height: 1,
					width: 1,
					overflow: 'hidden'
				} )
				.append(
					$('<div/>')
						.css( {
							position: 'absolute',
							top: 1,
							left: 1,
							width: 100,
							overflow: 'scroll'
						} )
						.append(
							$('<div/>')
								.css( {
									width: '100%',
									height: 10
								} )
						)
				)
				.appendTo( 'body' );
	
			var outer = n.children();
			var inner = outer.children();
	
			// Numbers below, in order, are:
			// inner.offsetWidth, inner.clientWidth, outer.offsetWidth, outer.clientWidth
			//
			// IE6 XP:                           100 100 100  83
			// IE7 Vista:                        100 100 100  83
			// IE 8+ Windows:                     83  83 100  83
			// Evergreen Windows:                 83  83 100  83
			// Evergreen Mac with scrollbars:     85  85 100  85
			// Evergreen Mac without scrollbars: 100 100 100 100
	
			// Get scrollbar width
			browser.barWidth = outer[0].offsetWidth - outer[0].clientWidth;
	
			// IE6/7 will oversize a width 100% element inside a scrolling element, to
			// include the width of the scrollbar, while other browsers ensure the inner
			// element is contained without forcing scrolling
			browser.bScrollOversize = inner[0].offsetWidth === 100 && outer[0].clientWidth !== 100;
	
			// In rtl text layout, some browsers (most, but not all) will place the
			// scrollbar on the left, rather than the right.
			browser.bScrollbarLeft = Math.round( inner.offset().left ) !== 1;
	
			// IE8- don't provide height and width for getBoundingClientRect
			browser.bBounding = n[0].getBoundingClientRect().width ? true : false;
	
			n.remove();
		}
	
		$.extend( settings.oBrowser, DataTable.__browser );
		settings.oScroll.iBarWidth = DataTable.__browser.barWidth;
	}
	
	
	/**
	 * Array.prototype reduce[Right] method, used for browsers which don't support
	 * JS 1.6. Done this way to reduce code size, since we iterate either way
	 *  @param {object} settings dataTables settings object
	 *  @memberof DataTable#oApi
	 */
	function _fnReduce ( that, fn, init, start, end, inc )
	{
		var
			i = start,
			value,
			isSet = false;
	
		if ( init !== undefined ) {
			value = init;
			isSet = true;
		}
	
		while ( i !== end ) {
			if ( ! that.hasOwnProperty(i) ) {
				continue;
			}
	
			value = isSet ?
				fn( value, that[i], i, that ) :
				that[i];
	
			isSet = true;
			i += inc;
		}
	
		return value;
	}
	
	/**
	 * Add a column to the list used for the table with default values
	 *  @param {object} oSettings dataTables settings object
	 *  @param {node} nTh The th element for this column
	 *  @memberof DataTable#oApi
	 */
	function _fnAddColumn( oSettings, nTh )
	{
		// Add column to aoColumns array
		var oDefaults = DataTable.defaults.column;
		var iCol = oSettings.aoColumns.length;
		var oCol = $.extend( {}, DataTable.models.oColumn, oDefaults, {
			"nTh": nTh ? nTh : document.createElement('th'),
			"sTitle":    oDefaults.sTitle    ? oDefaults.sTitle    : nTh ? nTh.innerHTML : '',
			"aDataSort": oDefaults.aDataSort ? oDefaults.aDataSort : [iCol],
			"mData": oDefaults.mData ? oDefaults.mData : iCol,
			idx: iCol
		} );
		oSettings.aoColumns.push( oCol );
	
		// Add search object for column specific search. Note that the `searchCols[ iCol ]`
		// passed into extend can be undefined. This allows the user to give a default
		// with only some of the parameters defined, and also not give a default
		var searchCols = oSettings.aoPreSearchCols;
		searchCols[ iCol ] = $.extend( {}, DataTable.models.oSearch, searchCols[ iCol ] );
	
		// Use the default column options function to initialise classes etc
		_fnColumnOptions( oSettings, iCol, $(nTh).data() );
	}
	
	
	/**
	 * Apply options for a column
	 *  @param {object} oSettings dataTables settings object
	 *  @param {int} iCol column index to consider
	 *  @param {object} oOptions object with sType, bVisible and bSearchable etc
	 *  @memberof DataTable#oApi
	 */
	function _fnColumnOptions( oSettings, iCol, oOptions )
	{
		var oCol = oSettings.aoColumns[ iCol ];
		var oClasses = oSettings.oClasses;
		var th = $(oCol.nTh);
	
		// Try to get width information from the DOM. We can't get it from CSS
		// as we'd need to parse the CSS stylesheet. `width` option can override
		if ( ! oCol.sWidthOrig ) {
			// Width attribute
			oCol.sWidthOrig = th.attr('width') || null;
	
			// Style attribute
			var t = (th.attr('style') || '').match(/width:\s*(\d+[pxem%]+)/);
			if ( t ) {
				oCol.sWidthOrig = t[1];
			}
		}
	
		/* User specified column options */
		if ( oOptions !== undefined && oOptions !== null )
		{
			// Backwards compatibility
			_fnCompatCols( oOptions );
	
			// Map camel case parameters to their Hungarian counterparts
			_fnCamelToHungarian( DataTable.defaults.column, oOptions );
	
			/* Backwards compatibility for mDataProp */
			if ( oOptions.mDataProp !== undefined && !oOptions.mData )
			{
				oOptions.mData = oOptions.mDataProp;
			}
	
			if ( oOptions.sType )
			{
				oCol._sManualType = oOptions.sType;
			}
	
			// `class` is a reserved word in Javascript, so we need to provide
			// the ability to use a valid name for the camel case input
			if ( oOptions.className && ! oOptions.sClass )
			{
				oOptions.sClass = oOptions.className;
			}
			if ( oOptions.sClass ) {
				th.addClass( oOptions.sClass );
			}
	
			$.extend( oCol, oOptions );
			_fnMap( oCol, oOptions, "sWidth", "sWidthOrig" );
	
			/* iDataSort to be applied (backwards compatibility), but aDataSort will take
			 * priority if defined
			 */
			if ( oOptions.iDataSort !== undefined )
			{
				oCol.aDataSort = [ oOptions.iDataSort ];
			}
			_fnMap( oCol, oOptions, "aDataSort" );
		}
	
		/* Cache the data get and set functions for speed */
		var mDataSrc = oCol.mData;
		var mData = _fnGetObjectDataFn( mDataSrc );
		var mRender = oCol.mRender ? _fnGetObjectDataFn( oCol.mRender ) : null;
	
		var attrTest = function( src ) {
			return typeof src === 'string' && src.indexOf('@') !== -1;
		};
		oCol._bAttrSrc = $.isPlainObject( mDataSrc ) && (
			attrTest(mDataSrc.sort) || attrTest(mDataSrc.type) || attrTest(mDataSrc.filter)
		);
		oCol._setter = null;
	
		oCol.fnGetData = function (rowData, type, meta) {
			var innerData = mData( rowData, type, undefined, meta );
	
			return mRender && type ?
				mRender( innerData, type, rowData, meta ) :
				innerData;
		};
		oCol.fnSetData = function ( rowData, val, meta ) {
			return _fnSetObjectDataFn( mDataSrc )( rowData, val, meta );
		};
	
		// Indicate if DataTables should read DOM data as an object or array
		// Used in _fnGetRowElements
		if ( typeof mDataSrc !== 'number' ) {
			oSettings._rowReadObject = true;
		}
	
		/* Feature sorting overrides column specific when off */
		if ( !oSettings.oFeatures.bSort )
		{
			oCol.bSortable = false;
			th.addClass( oClasses.sSortableNone ); // Have to add class here as order event isn't called
		}
	
		/* Check that the class assignment is correct for sorting */
		var bAsc = $.inArray('asc', oCol.asSorting) !== -1;
		var bDesc = $.inArray('desc', oCol.asSorting) !== -1;
		if ( !oCol.bSortable || (!bAsc && !bDesc) )
		{
			oCol.sSortingClass = oClasses.sSortableNone;
			oCol.sSortingClassJUI = "";
		}
		else if ( bAsc && !bDesc )
		{
			oCol.sSortingClass = oClasses.sSortableAsc;
			oCol.sSortingClassJUI = oClasses.sSortJUIAscAllowed;
		}
		else if ( !bAsc && bDesc )
		{
			oCol.sSortingClass = oClasses.sSortableDesc;
			oCol.sSortingClassJUI = oClasses.sSortJUIDescAllowed;
		}
		else
		{
			oCol.sSortingClass = oClasses.sSortable;
			oCol.sSortingClassJUI = oClasses.sSortJUI;
		}
	}
	
	
	/**
	 * Adjust the table column widths for new data. Note: you would probably want to
	 * do a redraw after calling this function!
	 *  @param {object} settings dataTables settings object
	 *  @memberof DataTable#oApi
	 */
	function _fnAdjustColumnSizing ( settings )
	{
		/* Not interested in doing column width calculation if auto-width is disabled */
		if ( settings.oFeatures.bAutoWidth !== false )
		{
			var columns = settings.aoColumns;
	
			_fnCalculateColumnWidths( settings );
			for ( var i=0 , iLen=columns.length ; i<iLen ; i++ )
			{
				columns[i].nTh.style.width = columns[i].sWidth;
			}
		}
	
		var scroll = settings.oScroll;
		if ( scroll.sY !== '' || scroll.sX !== '')
		{
			_fnScrollDraw( settings );
		}
	
		_fnCallbackFire( settings, null, 'column-sizing', [settings] );
	}
	
	
	/**
	 * Covert the index of a visible column to the index in the data array (take account
	 * of hidden columns)
	 *  @param {object} oSettings dataTables settings object
	 *  @param {int} iMatch Visible column index to lookup
	 *  @returns {int} i the data index
	 *  @memberof DataTable#oApi
	 */
	function _fnVisibleToColumnIndex( oSettings, iMatch )
	{
		var aiVis = _fnGetColumns( oSettings, 'bVisible' );
	
		return typeof aiVis[iMatch] === 'number' ?
			aiVis[iMatch] :
			null;
	}
	
	
	/**
	 * Covert the index of an index in the data array and convert it to the visible
	 *   column index (take account of hidden columns)
	 *  @param {int} iMatch Column index to lookup
	 *  @param {object} oSettings dataTables settings object
	 *  @returns {int} i the data index
	 *  @memberof DataTable#oApi
	 */
	function _fnColumnIndexToVisible( oSettings, iMatch )
	{
		var aiVis = _fnGetColumns( oSettings, 'bVisible' );
		var iPos = $.inArray( iMatch, aiVis );
	
		return iPos !== -1 ? iPos : null;
	}
	
	
	/**
	 * Get the number of visible columns
	 *  @param {object} oSettings dataTables settings object
	 *  @returns {int} i the number of visible columns
	 *  @memberof DataTable#oApi
	 */
	function _fnVisbleColumns( oSettings )
	{
		var vis = 0;
	
		// No reduce in IE8, use a loop for now
		$.each( oSettings.aoColumns, function ( i, col ) {
			if ( col.bVisible && $(col.nTh).css('display') !== 'none' ) {
				vis++;
			}
		} );
	
		return vis;
	}
	
	
	/**
	 * Get an array of column indexes that match a given property
	 *  @param {object} oSettings dataTables settings object
	 *  @param {string} sParam Parameter in aoColumns to look for - typically
	 *    bVisible or bSearchable
	 *  @returns {array} Array of indexes with matched properties
	 *  @memberof DataTable#oApi
	 */
	function _fnGetColumns( oSettings, sParam )
	{
		var a = [];
	
		$.map( oSettings.aoColumns, function(val, i) {
			if ( val[sParam] ) {
				a.push( i );
			}
		} );
	
		return a;
	}
	
	
	/**
	 * Calculate the 'type' of a column
	 *  @param {object} settings dataTables settings object
	 *  @memberof DataTable#oApi
	 */
	function _fnColumnTypes ( settings )
	{
		var columns = settings.aoColumns;
		var data = settings.aoData;
		var types = DataTable.ext.type.detect;
		var i, ien, j, jen, k, ken;
		var col, cell, detectedType, cache;
	
		// For each column, spin over the 
		for ( i=0, ien=columns.length ; i<ien ; i++ ) {
			col = columns[i];
			cache = [];
	
			if ( ! col.sType && col._sManualType ) {
				col.sType = col._sManualType;
			}
			else if ( ! col.sType ) {
				for ( j=0, jen=types.length ; j<jen ; j++ ) {
					for ( k=0, ken=data.length ; k<ken ; k++ ) {
						// Use a cache array so we only need to get the type data
						// from the formatter once (when using multiple detectors)
						if ( cache[k] === undefined ) {
							cache[k] = _fnGetCellData( settings, k, i, 'type' );
						}
	
						detectedType = types[j]( cache[k], settings );
	
						// If null, then this type can't apply to this column, so
						// rather than testing all cells, break out. There is an
						// exception for the last type which is `html`. We need to
						// scan all rows since it is possible to mix string and HTML
						// types
						if ( ! detectedType && j !== types.length-1 ) {
							break;
						}
	
						// Only a single match is needed for html type since it is
						// bottom of the pile and very similar to string
						if ( detectedType === 'html' ) {
							break;
						}
					}
	
					// Type is valid for all data points in the column - use this
					// type
					if ( detectedType ) {
						col.sType = detectedType;
						break;
					}
				}
	
				// Fall back - if no type was detected, always use string
				if ( ! col.sType ) {
					col.sType = 'string';
				}
			}
		}
	}
	
	
	/**
	 * Take the column definitions and static columns arrays and calculate how
	 * they relate to column indexes. The callback function will then apply the
	 * definition found for a column to a suitable configuration object.
	 *  @param {object} oSettings dataTables settings object
	 *  @param {array} aoColDefs The aoColumnDefs array that is to be applied
	 *  @param {array} aoCols The aoColumns array that defines columns individually
	 *  @param {function} fn Callback function - takes two parameters, the calculated
	 *    column index and the definition for that column.
	 *  @memberof DataTable#oApi
	 */
	function _fnApplyColumnDefs( oSettings, aoColDefs, aoCols, fn )
	{
		var i, iLen, j, jLen, k, kLen, def;
		var columns = oSettings.aoColumns;
	
		// Column definitions with aTargets
		if ( aoColDefs )
		{
			/* Loop over the definitions array - loop in reverse so first instance has priority */
			for ( i=aoColDefs.length-1 ; i>=0 ; i-- )
			{
				def = aoColDefs[i];
	
				/* Each definition can target multiple columns, as it is an array */
				var aTargets = def.targets !== undefined ?
					def.targets :
					def.aTargets;
	
				if ( ! $.isArray( aTargets ) )
				{
					aTargets = [ aTargets ];
				}
	
				for ( j=0, jLen=aTargets.length ; j<jLen ; j++ )
				{
					if ( typeof aTargets[j] === 'number' && aTargets[j] >= 0 )
					{
						/* Add columns that we don't yet know about */
						while( columns.length <= aTargets[j] )
						{
							_fnAddColumn( oSettings );
						}
	
						/* Integer, basic index */
						fn( aTargets[j], def );
					}
					else if ( typeof aTargets[j] === 'number' && aTargets[j] < 0 )
					{
						/* Negative integer, right to left column counting */
						fn( columns.length+aTargets[j], def );
					}
					else if ( typeof aTargets[j] === 'string' )
					{
						/* Class name matching on TH element */
						for ( k=0, kLen=columns.length ; k<kLen ; k++ )
						{
							if ( aTargets[j] == "_all" ||
							     $(columns[k].nTh).hasClass( aTargets[j] ) )
							{
								fn( k, def );
							}
						}
					}
				}
			}
		}
	
		// Statically defined columns array
		if ( aoCols )
		{
			for ( i=0, iLen=aoCols.length ; i<iLen ; i++ )
			{
				fn( i, aoCols[i] );
			}
		}
	}
	
	/**
	 * Add a data array to the table, creating DOM node etc. This is the parallel to
	 * _fnGatherData, but for adding rows from a Javascript source, rather than a
	 * DOM source.
	 *  @param {object} oSettings dataTables settings object
	 *  @param {array} aData data array to be added
	 *  @param {node} [nTr] TR element to add to the table - optional. If not given,
	 *    DataTables will create a row automatically
	 *  @param {array} [anTds] Array of TD|TH elements for the row - must be given
	 *    if nTr is.
	 *  @returns {int} >=0 if successful (index of new aoData entry), -1 if failed
	 *  @memberof DataTable#oApi
	 */
	function _fnAddData ( oSettings, aDataIn, nTr, anTds )
	{
		/* Create the object for storing information about this new row */
		var iRow = oSettings.aoData.length;
		var oData = $.extend( true, {}, DataTable.models.oRow, {
			src: nTr ? 'dom' : 'data',
			idx: iRow
		} );
	
		oData._aData = aDataIn;
		oSettings.aoData.push( oData );
	
		/* Create the cells */
		var nTd, sThisType;
		var columns = oSettings.aoColumns;
	
		// Invalidate the column types as the new data needs to be revalidated
		for ( var i=0, iLen=columns.length ; i<iLen ; i++ )
		{
			columns[i].sType = null;
		}
	
		/* Add to the display array */
		oSettings.aiDisplayMaster.push( iRow );
	
		var id = oSettings.rowIdFn( aDataIn );
		if ( id !== undefined ) {
			oSettings.aIds[ id ] = oData;
		}
	
		/* Create the DOM information, or register it if already present */
		if ( nTr || ! oSettings.oFeatures.bDeferRender )
		{
			_fnCreateTr( oSettings, iRow, nTr, anTds );
		}
	
		return iRow;
	}
	
	
	/**
	 * Add one or more TR elements to the table. Generally we'd expect to
	 * use this for reading data from a DOM sourced table, but it could be
	 * used for an TR element. Note that if a TR is given, it is used (i.e.
	 * it is not cloned).
	 *  @param {object} settings dataTables settings object
	 *  @param {array|node|jQuery} trs The TR element(s) to add to the table
	 *  @returns {array} Array of indexes for the added rows
	 *  @memberof DataTable#oApi
	 */
	function _fnAddTr( settings, trs )
	{
		var row;
	
		// Allow an individual node to be passed in
		if ( ! (trs instanceof $) ) {
			trs = $(trs);
		}
	
		return trs.map( function (i, el) {
			row = _fnGetRowElements( settings, el );
			return _fnAddData( settings, row.data, el, row.cells );
		} );
	}
	
	
	/**
	 * Take a TR element and convert it to an index in aoData
	 *  @param {object} oSettings dataTables settings object
	 *  @param {node} n the TR element to find
	 *  @returns {int} index if the node is found, null if not
	 *  @memberof DataTable#oApi
	 */
	function _fnNodeToDataIndex( oSettings, n )
	{
		return (n._DT_RowIndex!==undefined) ? n._DT_RowIndex : null;
	}
	
	
	/**
	 * Take a TD element and convert it into a column data index (not the visible index)
	 *  @param {object} oSettings dataTables settings object
	 *  @param {int} iRow The row number the TD/TH can be found in
	 *  @param {node} n The TD/TH element to find
	 *  @returns {int} index if the node is found, -1 if not
	 *  @memberof DataTable#oApi
	 */
	function _fnNodeToColumnIndex( oSettings, iRow, n )
	{
		return $.inArray( n, oSettings.aoData[ iRow ].anCells );
	}
	
	
	/**
	 * Get the data for a given cell from the internal cache, taking into account data mapping
	 *  @param {object} settings dataTables settings object
	 *  @param {int} rowIdx aoData row id
	 *  @param {int} colIdx Column index
	 *  @param {string} type data get type ('display', 'type' 'filter' 'sort')
	 *  @returns {*} Cell data
	 *  @memberof DataTable#oApi
	 */
	function _fnGetCellData( settings, rowIdx, colIdx, type )
	{
		var draw           = settings.iDraw;
		var col            = settings.aoColumns[colIdx];
		var rowData        = settings.aoData[rowIdx]._aData;
		var defaultContent = col.sDefaultContent;
		var cellData       = col.fnGetData( rowData, type, {
			settings: settings,
			row:      rowIdx,
			col:      colIdx
		} );
	
		if ( cellData === undefined ) {
			if ( settings.iDrawError != draw && defaultContent === null) {
				_fnLog( settings, 0, "Requested unknown parameter "+
					(typeof col.mData=='function' ? '{function}' : "'"+col.mData+"'")+
					" for row "+rowIdx+", column "+colIdx, 4 );
				settings.iDrawError = draw;
			}
			return defaultContent;
		}
	
		// When the data source is null and a specific data type is requested (i.e.
		// not the original data), we can use default column data
		if ( (cellData === rowData || cellData === null) && defaultContent !== null && type !== undefined ) {
			cellData = defaultContent;
		}
		else if ( typeof cellData === 'function' ) {
			// If the data source is a function, then we run it and use the return,
			// executing in the scope of the data object (for instances)
			return cellData.call( rowData );
		}
	
		if ( cellData === null && type == 'display' ) {
			return '';
		}
		return cellData;
	}
	
	
	/**
	 * Set the value for a specific cell, into the internal data cache
	 *  @param {object} settings dataTables settings object
	 *  @param {int} rowIdx aoData row id
	 *  @param {int} colIdx Column index
	 *  @param {*} val Value to set
	 *  @memberof DataTable#oApi
	 */
	function _fnSetCellData( settings, rowIdx, colIdx, val )
	{
		var col     = settings.aoColumns[colIdx];
		var rowData = settings.aoData[rowIdx]._aData;
	
		col.fnSetData( rowData, val, {
			settings: settings,
			row:      rowIdx,
			col:      colIdx
		}  );
	}
	
	
	// Private variable that is used to match action syntax in the data property object
	var __reArray = /\[.*?\]$/;
	var __reFn = /\(\)$/;
	
	/**
	 * Split string on periods, taking into account escaped periods
	 * @param  {string} str String to split
	 * @return {array} Split string
	 */
	function _fnSplitObjNotation( str )
	{
		return $.map( str.match(/(\\.|[^\.])+/g) || [''], function ( s ) {
			return s.replace(/\\\./g, '.');
		} );
	}
	
	
	/**
	 * Return a function that can be used to get data from a source object, taking
	 * into account the ability to use nested objects as a source
	 *  @param {string|int|function} mSource The data source for the object
	 *  @returns {function} Data get function
	 *  @memberof DataTable#oApi
	 */
	function _fnGetObjectDataFn( mSource )
	{
		if ( $.isPlainObject( mSource ) )
		{
			/* Build an object of get functions, and wrap them in a single call */
			var o = {};
			$.each( mSource, function (key, val) {
				if ( val ) {
					o[key] = _fnGetObjectDataFn( val );
				}
			} );
	
			return function (data, type, row, meta) {
				var t = o[type] || o._;
				return t !== undefined ?
					t(data, type, row, meta) :
					data;
			};
		}
		else if ( mSource === null )
		{
			/* Give an empty string for rendering / sorting etc */
			return function (data) { // type, row and meta also passed, but not used
				return data;
			};
		}
		else if ( typeof mSource === 'function' )
		{
			return function (data, type, row, meta) {
				return mSource( data, type, row, meta );
			};
		}
		else if ( typeof mSource === 'string' && (mSource.indexOf('.') !== -1 ||
			      mSource.indexOf('[') !== -1 || mSource.indexOf('(') !== -1) )
		{
			/* If there is a . in the source string then the data source is in a
			 * nested object so we loop over the data for each level to get the next
			 * level down. On each loop we test for undefined, and if found immediately
			 * return. This allows entire objects to be missing and sDefaultContent to
			 * be used if defined, rather than throwing an error
			 */
			var fetchData = function (data, type, src) {
				var arrayNotation, funcNotation, out, innerSrc;
	
				if ( src !== "" )
				{
					var a = _fnSplitObjNotation( src );
	
					for ( var i=0, iLen=a.length ; i<iLen ; i++ )
					{
						// Check if we are dealing with special notation
						arrayNotation = a[i].match(__reArray);
						funcNotation = a[i].match(__reFn);
	
						if ( arrayNotation )
						{
							// Array notation
							a[i] = a[i].replace(__reArray, '');
	
							// Condition allows simply [] to be passed in
							if ( a[i] !== "" ) {
								data = data[ a[i] ];
							}
							out = [];
	
							// Get the remainder of the nested object to get
							a.splice( 0, i+1 );
							innerSrc = a.join('.');
	
							// Traverse each entry in the array getting the properties requested
							if ( $.isArray( data ) ) {
								for ( var j=0, jLen=data.length ; j<jLen ; j++ ) {
									out.push( fetchData( data[j], type, innerSrc ) );
								}
							}
	
							// If a string is given in between the array notation indicators, that
							// is used to join the strings together, otherwise an array is returned
							var join = arrayNotation[0].substring(1, arrayNotation[0].length-1);
							data = (join==="") ? out : out.join(join);
	
							// The inner call to fetchData has already traversed through the remainder
							// of the source requested, so we exit from the loop
							break;
						}
						else if ( funcNotation )
						{
							// Function call
							a[i] = a[i].replace(__reFn, '');
							data = data[ a[i] ]();
							continue;
						}
	
						if ( data === null || data[ a[i] ] === undefined )
						{
							return undefined;
						}
						data = data[ a[i] ];
					}
				}
	
				return data;
			};
	
			return function (data, type) { // row and meta also passed, but not used
				return fetchData( data, type, mSource );
			};
		}
		else
		{
			/* Array or flat object mapping */
			return function (data, type) { // row and meta also passed, but not used
				return data[mSource];
			};
		}
	}
	
	
	/**
	 * Return a function that can be used to set data from a source object, taking
	 * into account the ability to use nested objects as a source
	 *  @param {string|int|function} mSource The data source for the object
	 *  @returns {function} Data set function
	 *  @memberof DataTable#oApi
	 */
	function _fnSetObjectDataFn( mSource )
	{
		if ( $.isPlainObject( mSource ) )
		{
			/* Unlike get, only the underscore (global) option is used for for
			 * setting data since we don't know the type here. This is why an object
			 * option is not documented for `mData` (which is read/write), but it is
			 * for `mRender` which is read only.
			 */
			return _fnSetObjectDataFn( mSource._ );
		}
		else if ( mSource === null )
		{
			/* Nothing to do when the data source is null */
			return function () {};
		}
		else if ( typeof mSource === 'function' )
		{
			return function (data, val, meta) {
				mSource( data, 'set', val, meta );
			};
		}
		else if ( typeof mSource === 'string' && (mSource.indexOf('.') !== -1 ||
			      mSource.indexOf('[') !== -1 || mSource.indexOf('(') !== -1) )
		{
			/* Like the get, we need to get data from a nested object */
			var setData = function (data, val, src) {
				var a = _fnSplitObjNotation( src ), b;
				var aLast = a[a.length-1];
				var arrayNotation, funcNotation, o, innerSrc;
	
				for ( var i=0, iLen=a.length-1 ; i<iLen ; i++ )
				{
					// Check if we are dealing with an array notation request
					arrayNotation = a[i].match(__reArray);
					funcNotation = a[i].match(__reFn);
	
					if ( arrayNotation )
					{
						a[i] = a[i].replace(__reArray, '');
						data[ a[i] ] = [];
	
						// Get the remainder of the nested object to set so we can recurse
						b = a.slice();
						b.splice( 0, i+1 );
						innerSrc = b.join('.');
	
						// Traverse each entry in the array setting the properties requested
						if ( $.isArray( val ) )
						{
							for ( var j=0, jLen=val.length ; j<jLen ; j++ )
							{
								o = {};
								setData( o, val[j], innerSrc );
								data[ a[i] ].push( o );
							}
						}
						else
						{
							// We've been asked to save data to an array, but it
							// isn't array data to be saved. Best that can be done
							// is to just save the value.
							data[ a[i] ] = val;
						}
	
						// The inner call to setData has already traversed through the remainder
						// of the source and has set the data, thus we can exit here
						return;
					}
					else if ( funcNotation )
					{
						// Function call
						a[i] = a[i].replace(__reFn, '');
						data = data[ a[i] ]( val );
					}
	
					// If the nested object doesn't currently exist - since we are
					// trying to set the value - create it
					if ( data[ a[i] ] === null || data[ a[i] ] === undefined )
					{
						data[ a[i] ] = {};
					}
					data = data[ a[i] ];
				}
	
				// Last item in the input - i.e, the actual set
				if ( aLast.match(__reFn ) )
				{
					// Function call
					data = data[ aLast.replace(__reFn, '') ]( val );
				}
				else
				{
					// If array notation is used, we just want to strip it and use the property name
					// and assign the value. If it isn't used, then we get the result we want anyway
					data[ aLast.replace(__reArray, '') ] = val;
				}
			};
	
			return function (data, val) { // meta is also passed in, but not used
				return setData( data, val, mSource );
			};
		}
		else
		{
			/* Array or flat object mapping */
			return function (data, val) { // meta is also passed in, but not used
				data[mSource] = val;
			};
		}
	}
	
	
	/**
	 * Return an array with the full table data
	 *  @param {object} oSettings dataTables settings object
	 *  @returns array {array} aData Master data array
	 *  @memberof DataTable#oApi
	 */
	function _fnGetDataMaster ( settings )
	{
		return _pluck( settings.aoData, '_aData' );
	}
	
	
	/**
	 * Nuke the table
	 *  @param {object} oSettings dataTables settings object
	 *  @memberof DataTable#oApi
	 */
	function _fnClearTable( settings )
	{
		settings.aoData.length = 0;
		settings.aiDisplayMaster.length = 0;
		settings.aiDisplay.length = 0;
		settings.aIds = {};
	}
	
	
	 /**
	 * Take an array of integers (index array) and remove a target integer (value - not
	 * the key!)
	 *  @param {array} a Index array to target
	 *  @param {int} iTarget value to find
	 *  @memberof DataTable#oApi
	 */
	function _fnDeleteIndex( a, iTarget, splice )
	{
		var iTargetIndex = -1;
	
		for ( var i=0, iLen=a.length ; i<iLen ; i++ )
		{
			if ( a[i] == iTarget )
			{
				iTargetIndex = i;
			}
			else if ( a[i] > iTarget )
			{
				a[i]--;
			}
		}
	
		if ( iTargetIndex != -1 && splice === undefined )
		{
			a.splice( iTargetIndex, 1 );
		}
	}
	
	
	/**
	 * Mark cached data as invalid such that a re-read of the data will occur when
	 * the cached data is next requested. Also update from the data source object.
	 *
	 * @param {object} settings DataTables settings object
	 * @param {int}    rowIdx   Row index to invalidate
	 * @param {string} [src]    Source to invalidate from: undefined, 'auto', 'dom'
	 *     or 'data'
	 * @param {int}    [colIdx] Column index to invalidate. If undefined the whole
	 *     row will be invalidated
	 * @memberof DataTable#oApi
	 *
	 * @todo For the modularisation of v1.11 this will need to become a callback, so
	 *   the sort and filter methods can subscribe to it. That will required
	 *   initialisation options for sorting, which is why it is not already baked in
	 */
	function _fnInvalidate( settings, rowIdx, src, colIdx )
	{
		var row = settings.aoData[ rowIdx ];
		var i, ien;
		var cellWrite = function ( cell, col ) {
			// This is very frustrating, but in IE if you just write directly
			// to innerHTML, and elements that are overwritten are GC'ed,
			// even if there is a reference to them elsewhere
			while ( cell.childNodes.length ) {
				cell.removeChild( cell.firstChild );
			}
	
			cell.innerHTML = _fnGetCellData( settings, rowIdx, col, 'display' );
		};
	
		// Are we reading last data from DOM or the data object?
		if ( src === 'dom' || ((! src || src === 'auto') && row.src === 'dom') ) {
			// Read the data from the DOM
			row._aData = _fnGetRowElements(
					settings, row, colIdx, colIdx === undefined ? undefined : row._aData
				)
				.data;
		}
		else {
			// Reading from data object, update the DOM
			var cells = row.anCells;
	
			if ( cells ) {
				if ( colIdx !== undefined ) {
					cellWrite( cells[colIdx], colIdx );
				}
				else {
					for ( i=0, ien=cells.length ; i<ien ; i++ ) {
						cellWrite( cells[i], i );
					}
				}
			}
		}
	
		// For both row and cell invalidation, the cached data for sorting and
		// filtering is nulled out
		row._aSortData = null;
		row._aFilterData = null;
	
		// Invalidate the type for a specific column (if given) or all columns since
		// the data might have changed
		var cols = settings.aoColumns;
		if ( colIdx !== undefined ) {
			cols[ colIdx ].sType = null;
		}
		else {
			for ( i=0, ien=cols.length ; i<ien ; i++ ) {
				cols[i].sType = null;
			}
	
			// Update DataTables special `DT_*` attributes for the row
			_fnRowAttributes( settings, row );
		}
	}
	
	
	/**
	 * Build a data source object from an HTML row, reading the contents of the
	 * cells that are in the row.
	 *
	 * @param {object} settings DataTables settings object
	 * @param {node|object} TR element from which to read data or existing row
	 *   object from which to re-read the data from the cells
	 * @param {int} [colIdx] Optional column index
	 * @param {array|object} [d] Data source object. If `colIdx` is given then this
	 *   parameter should also be given and will be used to write the data into.
	 *   Only the column in question will be written
	 * @returns {object} Object with two parameters: `data` the data read, in
	 *   document order, and `cells` and array of nodes (they can be useful to the
	 *   caller, so rather than needing a second traversal to get them, just return
	 *   them from here).
	 * @memberof DataTable#oApi
	 */
	function _fnGetRowElements( settings, row, colIdx, d )
	{
		var
			tds = [],
			td = row.firstChild,
			name, col, o, i=0, contents,
			columns = settings.aoColumns,
			objectRead = settings._rowReadObject;
	
		// Allow the data object to be passed in, or construct
		d = d !== undefined ?
			d :
			objectRead ?
				{} :
				[];
	
		var attr = function ( str, td  ) {
			if ( typeof str === 'string' ) {
				var idx = str.indexOf('@');
	
				if ( idx !== -1 ) {
					var attr = str.substring( idx+1 );
					var setter = _fnSetObjectDataFn( str );
					setter( d, td.getAttribute( attr ) );
				}
			}
		};
	
		// Read data from a cell and store into the data object
		var cellProcess = function ( cell ) {
			if ( colIdx === undefined || colIdx === i ) {
				col = columns[i];
				contents = $.trim(cell.innerHTML);
	
				if ( col && col._bAttrSrc ) {
					var setter = _fnSetObjectDataFn( col.mData._ );
					setter( d, contents );
	
					attr( col.mData.sort, cell );
					attr( col.mData.type, cell );
					attr( col.mData.filter, cell );
				}
				else {
					// Depending on the `data` option for the columns the data can
					// be read to either an object or an array.
					if ( objectRead ) {
						if ( ! col._setter ) {
							// Cache the setter function
							col._setter = _fnSetObjectDataFn( col.mData );
						}
						col._setter( d, contents );
					}
					else {
						d[i] = contents;
					}
				}
			}
	
			i++;
		};
	
		if ( td ) {
			// `tr` element was passed in
			while ( td ) {
				name = td.nodeName.toUpperCase();
	
				if ( name == "TD" || name == "TH" ) {
					cellProcess( td );
					tds.push( td );
				}
	
				td = td.nextSibling;
			}
		}
		else {
			// Existing row object passed in
			tds = row.anCells;
	
			for ( var j=0, jen=tds.length ; j<jen ; j++ ) {
				cellProcess( tds[j] );
			}
		}
	
		// Read the ID from the DOM if present
		var rowNode = row.firstChild ? row : row.nTr;
	
		if ( rowNode ) {
			var id = rowNode.getAttribute( 'id' );
	
			if ( id ) {
				_fnSetObjectDataFn( settings.rowId )( d, id );
			}
		}
	
		return {
			data: d,
			cells: tds
		};
	}
	/**
	 * Create a new TR element (and it's TD children) for a row
	 *  @param {object} oSettings dataTables settings object
	 *  @param {int} iRow Row to consider
	 *  @param {node} [nTrIn] TR element to add to the table - optional. If not given,
	 *    DataTables will create a row automatically
	 *  @param {array} [anTds] Array of TD|TH elements for the row - must be given
	 *    if nTr is.
	 *  @memberof DataTable#oApi
	 */
	function _fnCreateTr ( oSettings, iRow, nTrIn, anTds )
	{
		var
			row = oSettings.aoData[iRow],
			rowData = row._aData,
			cells = [],
			nTr, nTd, oCol,
			i, iLen;
	
		if ( row.nTr === null )
		{
			nTr = nTrIn || document.createElement('tr');
	
			row.nTr = nTr;
			row.anCells = cells;
	
			/* Use a private property on the node to allow reserve mapping from the node
			 * to the aoData array for fast look up
			 */
			nTr._DT_RowIndex = iRow;
	
			/* Special parameters can be given by the data source to be used on the row */
			_fnRowAttributes( oSettings, row );
	
			/* Process each column */
			for ( i=0, iLen=oSettings.aoColumns.length ; i<iLen ; i++ )
			{
				oCol = oSettings.aoColumns[i];
	
				nTd = nTrIn ? anTds[i] : document.createElement( oCol.sCellType );
				nTd._DT_CellIndex = {
					row: iRow,
					column: i
				};
				
				cells.push( nTd );
	
				// Need to create the HTML if new, or if a rendering function is defined
				if ( (!nTrIn || oCol.mRender || oCol.mData !== i) &&
					 (!$.isPlainObject(oCol.mData) || oCol.mData._ !== i+'.display')
				) {
					nTd.innerHTML = _fnGetCellData( oSettings, iRow, i, 'display' );
				}
	
				/* Add user defined class */
				if ( oCol.sClass )
				{
					nTd.className += ' '+oCol.sClass;
				}
	
				// Visibility - add or remove as required
				if ( oCol.bVisible && ! nTrIn )
				{
					nTr.appendChild( nTd );
				}
				else if ( ! oCol.bVisible && nTrIn )
				{
					nTd.parentNode.removeChild( nTd );
				}
	
				if ( oCol.fnCreatedCell )
				{
					oCol.fnCreatedCell.call( oSettings.oInstance,
						nTd, _fnGetCellData( oSettings, iRow, i ), rowData, iRow, i
					);
				}
			}
	
			_fnCallbackFire( oSettings, 'aoRowCreatedCallback', null, [nTr, rowData, iRow] );
		}
	
		// Remove once webkit bug 131819 and Chromium bug 365619 have been resolved
		// and deployed
		row.nTr.setAttribute( 'role', 'row' );
	}
	
	
	/**
	 * Add attributes to a row based on the special `DT_*` parameters in a data
	 * source object.
	 *  @param {object} settings DataTables settings object
	 *  @param {object} DataTables row object for the row to be modified
	 *  @memberof DataTable#oApi
	 */
	function _fnRowAttributes( settings, row )
	{
		var tr = row.nTr;
		var data = row._aData;
	
		if ( tr ) {
			var id = settings.rowIdFn( data );
	
			if ( id ) {
				tr.id = id;
			}
	
			if ( data.DT_RowClass ) {
				// Remove any classes added by DT_RowClass before
				var a = data.DT_RowClass.split(' ');
				row.__rowc = row.__rowc ?
					_unique( row.__rowc.concat( a ) ) :
					a;
	
				$(tr)
					.removeClass( row.__rowc.join(' ') )
					.addClass( data.DT_RowClass );
			}
	
			if ( data.DT_RowAttr ) {
				$(tr).attr( data.DT_RowAttr );
			}
	
			if ( data.DT_RowData ) {
				$(tr).data( data.DT_RowData );
			}
		}
	}
	
	
	/**
	 * Create the HTML header for the table
	 *  @param {object} oSettings dataTables settings object
	 *  @memberof DataTable#oApi
	 */
	function _fnBuildHead( oSettings )
	{
		var i, ien, cell, row, column;
		var thead = oSettings.nTHead;
		var tfoot = oSettings.nTFoot;
		var createHeader = $('th, td', thead).length === 0;
		var classes = oSettings.oClasses;
		var columns = oSettings.aoColumns;
	
		if ( createHeader ) {
			row = $('<tr/>').appendTo( thead );
		}
	
		for ( i=0, ien=columns.length ; i<ien ; i++ ) {
			column = columns[i];
			cell = $( column.nTh ).addClass( column.sClass );
	
			if ( createHeader ) {
				cell.appendTo( row );
			}
	
			// 1.11 move into sorting
			if ( oSettings.oFeatures.bSort ) {
				cell.addClass( column.sSortingClass );
	
				if ( column.bSortable !== false ) {
					cell
						.attr( 'tabindex', oSettings.iTabIndex )
						.attr( 'aria-controls', oSettings.sTableId );
	
					_fnSortAttachListener( oSettings, column.nTh, i );
				}
			}
	
			if ( column.sTitle != cell[0].innerHTML ) {
				cell.html( column.sTitle );
			}
	
			_fnRenderer( oSettings, 'header' )(
				oSettings, cell, column, classes
			);
		}
	
		if ( createHeader ) {
			_fnDetectHeader( oSettings.aoHeader, thead );
		}
		
		/* ARIA role for the rows */
	 	$(thead).find('>tr').attr('role', 'row');
	
		/* Deal with the footer - add classes if required */
		$(thead).find('>tr>th, >tr>td').addClass( classes.sHeaderTH );
		$(tfoot).find('>tr>th, >tr>td').addClass( classes.sFooterTH );
	
		// Cache the footer cells. Note that we only take the cells from the first
		// row in the footer. If there is more than one row the user wants to
		// interact with, they need to use the table().foot() method. Note also this
		// allows cells to be used for multiple columns using colspan
		if ( tfoot !== null ) {
			var cells = oSettings.aoFooter[0];
	
			for ( i=0, ien=cells.length ; i<ien ; i++ ) {
				column = columns[i];
				column.nTf = cells[i].cell;
	
				if ( column.sClass ) {
					$(column.nTf).addClass( column.sClass );
				}
			}
		}
	}
	
	
	/**
	 * Draw the header (or footer) element based on the column visibility states. The
	 * methodology here is to use the layout array from _fnDetectHeader, modified for
	 * the instantaneous column visibility, to construct the new layout. The grid is
	 * traversed over cell at a time in a rows x columns grid fashion, although each
	 * cell insert can cover multiple elements in the grid - which is tracks using the
	 * aApplied array. Cell inserts in the grid will only occur where there isn't
	 * already a cell in that position.
	 *  @param {object} oSettings dataTables settings object
	 *  @param array {objects} aoSource Layout array from _fnDetectHeader
	 *  @param {boolean} [bIncludeHidden=false] If true then include the hidden columns in the calc,
	 *  @memberof DataTable#oApi
	 */
	function _fnDrawHead( oSettings, aoSource, bIncludeHidden )
	{
		var i, iLen, j, jLen, k, kLen, n, nLocalTr;
		var aoLocal = [];
		var aApplied = [];
		var iColumns = oSettings.aoColumns.length;
		var iRowspan, iColspan;
	
		if ( ! aoSource )
		{
			return;
		}
	
		if (  bIncludeHidden === undefined )
		{
			bIncludeHidden = false;
		}
	
		/* Make a copy of the master layout array, but without the visible columns in it */
		for ( i=0, iLen=aoSource.length ; i<iLen ; i++ )
		{
			aoLocal[i] = aoSource[i].slice();
			aoLocal[i].nTr = aoSource[i].nTr;
	
			/* Remove any columns which are currently hidden */
			for ( j=iColumns-1 ; j>=0 ; j-- )
			{
				if ( !oSettings.aoColumns[j].bVisible && !bIncludeHidden )
				{
					aoLocal[i].splice( j, 1 );
				}
			}
	
			/* Prep the applied array - it needs an element for each row */
			aApplied.push( [] );
		}
	
		for ( i=0, iLen=aoLocal.length ; i<iLen ; i++ )
		{
			nLocalTr = aoLocal[i].nTr;
	
			/* All cells are going to be replaced, so empty out the row */
			if ( nLocalTr )
			{
				while( (n = nLocalTr.firstChild) )
				{
					nLocalTr.removeChild( n );
				}
			}
	
			for ( j=0, jLen=aoLocal[i].length ; j<jLen ; j++ )
			{
				iRowspan = 1;
				iColspan = 1;
	
				/* Check to see if there is already a cell (row/colspan) covering our target
				 * insert point. If there is, then there is nothing to do.
				 */
				if ( aApplied[i][j] === undefined )
				{
					nLocalTr.appendChild( aoLocal[i][j].cell );
					aApplied[i][j] = 1;
	
					/* Expand the cell to cover as many rows as needed */
					while ( aoLocal[i+iRowspan] !== undefined &&
					        aoLocal[i][j].cell == aoLocal[i+iRowspan][j].cell )
					{
						aApplied[i+iRowspan][j] = 1;
						iRowspan++;
					}
	
					/* Expand the cell to cover as many columns as needed */
					while ( aoLocal[i][j+iColspan] !== undefined &&
					        aoLocal[i][j].cell == aoLocal[i][j+iColspan].cell )
					{
						/* Must update the applied array over the rows for the columns */
						for ( k=0 ; k<iRowspan ; k++ )
						{
							aApplied[i+k][j+iColspan] = 1;
						}
						iColspan++;
					}
	
					/* Do the actual expansion in the DOM */
					$(aoLocal[i][j].cell)
						.attr('rowspan', iRowspan)
						.attr('colspan', iColspan);
				}
			}
		}
	}
	
	
	/**
	 * Insert the required TR nodes into the table for display
	 *  @param {object} oSettings dataTables settings object
	 *  @memberof DataTable#oApi
	 */
	function _fnDraw( oSettings )
	{
		/* Provide a pre-callback function which can be used to cancel the draw is false is returned */
		var aPreDraw = _fnCallbackFire( oSettings, 'aoPreDrawCallback', 'preDraw', [oSettings] );
		if ( $.inArray( false, aPreDraw ) !== -1 )
		{
			_fnProcessingDisplay( oSettings, false );
			return;
		}
	
		var i, iLen, n;
		var anRows = [];
		var iRowCount = 0;
		var asStripeClasses = oSettings.asStripeClasses;
		var iStripes = asStripeClasses.length;
		var iOpenRows = oSettings.aoOpenRows.length;
		var oLang = oSettings.oLanguage;
		var iInitDisplayStart = oSettings.iInitDisplayStart;
		var bServerSide = _fnDataSource( oSettings ) == 'ssp';
		var aiDisplay = oSettings.aiDisplay;
	
		oSettings.bDrawing = true;
	
		/* Check and see if we have an initial draw position from state saving */
		if ( iInitDisplayStart !== undefined && iInitDisplayStart !== -1 )
		{
			oSettings._iDisplayStart = bServerSide ?
				iInitDisplayStart :
				iInitDisplayStart >= oSettings.fnRecordsDisplay() ?
					0 :
					iInitDisplayStart;
	
			oSettings.iInitDisplayStart = -1;
		}
	
		var iDisplayStart = oSettings._iDisplayStart;
		var iDisplayEnd = oSettings.fnDisplayEnd();
	
		/* Server-side processing draw intercept */
		if ( oSettings.bDeferLoading )
		{
			oSettings.bDeferLoading = false;
			oSettings.iDraw++;
			_fnProcessingDisplay( oSettings, false );
		}
		else if ( !bServerSide )
		{
			oSettings.iDraw++;
		}
		else if ( !oSettings.bDestroying && !_fnAjaxUpdate( oSettings ) )
		{
			return;
		}
	
		if ( aiDisplay.length !== 0 )
		{
			var iStart = bServerSide ? 0 : iDisplayStart;
			var iEnd = bServerSide ? oSettings.aoData.length : iDisplayEnd;
	
			for ( var j=iStart ; j<iEnd ; j++ )
			{
				var iDataIndex = aiDisplay[j];
				var aoData = oSettings.aoData[ iDataIndex ];
				if ( aoData.nTr === null )
				{
					_fnCreateTr( oSettings, iDataIndex );
				}
	
				var nRow = aoData.nTr;
	
				/* Remove the old striping classes and then add the new one */
				if ( iStripes !== 0 )
				{
					var sStripe = asStripeClasses[ iRowCount % iStripes ];
					if ( aoData._sRowStripe != sStripe )
					{
						$(nRow).removeClass( aoData._sRowStripe ).addClass( sStripe );
						aoData._sRowStripe = sStripe;
					}
				}
	
				// Row callback functions - might want to manipulate the row
				// iRowCount and j are not currently documented. Are they at all
				// useful?
				_fnCallbackFire( oSettings, 'aoRowCallback', null,
					[nRow, aoData._aData, iRowCount, j] );
	
				anRows.push( nRow );
				iRowCount++;
			}
		}
		else
		{
			/* Table is empty - create a row with an empty message in it */
			var sZero = oLang.sZeroRecords;
			if ( oSettings.iDraw == 1 &&  _fnDataSource( oSettings ) == 'ajax' )
			{
				sZero = oLang.sLoadingRecords;
			}
			else if ( oLang.sEmptyTable && oSettings.fnRecordsTotal() === 0 )
			{
				sZero = oLang.sEmptyTable;
			}
	
			anRows[ 0 ] = $( '<tr/>', { 'class': iStripes ? asStripeClasses[0] : '' } )
				.append( $('<td />', {
					'valign':  'top',
					'colSpan': _fnVisbleColumns( oSettings ),
					'class':   oSettings.oClasses.sRowEmpty
				} ).html( sZero ) )[0];
		}
	
		/* Header and footer callbacks */
		_fnCallbackFire( oSettings, 'aoHeaderCallback', 'header', [ $(oSettings.nTHead).children('tr')[0],
			_fnGetDataMaster( oSettings ), iDisplayStart, iDisplayEnd, aiDisplay ] );
	
		_fnCallbackFire( oSettings, 'aoFooterCallback', 'footer', [ $(oSettings.nTFoot).children('tr')[0],
			_fnGetDataMaster( oSettings ), iDisplayStart, iDisplayEnd, aiDisplay ] );
	
		var body = $(oSettings.nTBody);
	
		body.children().detach();
		body.append( $(anRows) );
	
		/* Call all required callback functions for the end of a draw */
		_fnCallbackFire( oSettings, 'aoDrawCallback', 'draw', [oSettings] );
	
		/* Draw is complete, sorting and filtering must be as well */
		oSettings.bSorted = false;
		oSettings.bFiltered = false;
		oSettings.bDrawing = false;
	}
	
	
	/**
	 * Redraw the table - taking account of the various features which are enabled
	 *  @param {object} oSettings dataTables settings object
	 *  @param {boolean} [holdPosition] Keep the current paging position. By default
	 *    the paging is reset to the first page
	 *  @memberof DataTable#oApi
	 */
	function _fnReDraw( settings, holdPosition )
	{
		var
			features = settings.oFeatures,
			sort     = features.bSort,
			filter   = features.bFilter;
	
		if ( sort ) {
			_fnSort( settings );
		}
	
		if ( filter ) {
			_fnFilterComplete( settings, settings.oPreviousSearch );
		}
		else {
			// No filtering, so we want to just use the display master
			settings.aiDisplay = settings.aiDisplayMaster.slice();
		}
	
		if ( holdPosition !== true ) {
			settings._iDisplayStart = 0;
		}
	
		// Let any modules know about the draw hold position state (used by
		// scrolling internally)
		settings._drawHold = holdPosition;
	
		_fnDraw( settings );
	
		settings._drawHold = false;
	}
	
	
	/**
	 * Add the options to the page HTML for the table
	 *  @param {object} oSettings dataTables settings object
	 *  @memberof DataTable#oApi
	 */
	function _fnAddOptionsHtml ( oSettings )
	{
		var classes = oSettings.oClasses;
		var table = $(oSettings.nTable);
		var holding = $('<div/>').insertBefore( table ); // Holding element for speed
		var features = oSettings.oFeatures;
	
		// All DataTables are wrapped in a div
		var insert = $('<div/>', {
			id:      oSettings.sTableId+'_wrapper',
			'class': classes.sWrapper + (oSettings.nTFoot ? '' : ' '+classes.sNoFooter)
		} );
	
		oSettings.nHolding = holding[0];
		oSettings.nTableWrapper = insert[0];
		oSettings.nTableReinsertBefore = oSettings.nTable.nextSibling;
	
		/* Loop over the user set positioning and place the elements as needed */
		var aDom = oSettings.sDom.split('');
		var featureNode, cOption, nNewNode, cNext, sAttr, j;
		for ( var i=0 ; i<aDom.length ; i++ )
		{
			featureNode = null;
			cOption = aDom[i];
	
			if ( cOption == '<' )
			{
				/* New container div */
				nNewNode = $('<div/>')[0];
	
				/* Check to see if we should append an id and/or a class name to the container */
				cNext = aDom[i+1];
				if ( cNext == "'" || cNext == '"' )
				{
					sAttr = "";
					j = 2;
					while ( aDom[i+j] != cNext )
					{
						sAttr += aDom[i+j];
						j++;
					}
	
					/* Replace jQuery UI constants @todo depreciated */
					if ( sAttr == "H" )
					{
						sAttr = classes.sJUIHeader;
					}
					else if ( sAttr == "F" )
					{
						sAttr = classes.sJUIFooter;
					}
	
					/* The attribute can be in the format of "#id.class", "#id" or "class" This logic
					 * breaks the string into parts and applies them as needed
					 */
					if ( sAttr.indexOf('.') != -1 )
					{
						var aSplit = sAttr.split('.');
						nNewNode.id = aSplit[0].substr(1, aSplit[0].length-1);
						nNewNode.className = aSplit[1];
					}
					else if ( sAttr.charAt(0) == "#" )
					{
						nNewNode.id = sAttr.substr(1, sAttr.length-1);
					}
					else
					{
						nNewNode.className = sAttr;
					}
	
					i += j; /* Move along the position array */
				}
	
				insert.append( nNewNode );
				insert = $(nNewNode);
			}
			else if ( cOption == '>' )
			{
				/* End container div */
				insert = insert.parent();
			}
			// @todo Move options into their own plugins?
			else if ( cOption == 'l' && features.bPaginate && features.bLengthChange )
			{
				/* Length */
				featureNode = _fnFeatureHtmlLength( oSettings );
			}
			else if ( cOption == 'f' && features.bFilter )
			{
				/* Filter */
				featureNode = _fnFeatureHtmlFilter( oSettings );
			}
			else if ( cOption == 'r' && features.bProcessing )
			{
				/* pRocessing */
				featureNode = _fnFeatureHtmlProcessing( oSettings );
			}
			else if ( cOption == 't' )
			{
				/* Table */
				featureNode = _fnFeatureHtmlTable( oSettings );
			}
			else if ( cOption ==  'i' && features.bInfo )
			{
				/* Info */
				featureNode = _fnFeatureHtmlInfo( oSettings );
			}
			else if ( cOption == 'p' && features.bPaginate )
			{
				/* Pagination */
				featureNode = _fnFeatureHtmlPaginate( oSettings );
			}
			else if ( DataTable.ext.feature.length !== 0 )
			{
				/* Plug-in features */
				var aoFeatures = DataTable.ext.feature;
				for ( var k=0, kLen=aoFeatures.length ; k<kLen ; k++ )
				{
					if ( cOption == aoFeatures[k].cFeature )
					{
						featureNode = aoFeatures[k].fnInit( oSettings );
						break;
					}
				}
			}
	
			/* Add to the 2D features array */
			if ( featureNode )
			{
				var aanFeatures = oSettings.aanFeatures;
	
				if ( ! aanFeatures[cOption] )
				{
					aanFeatures[cOption] = [];
				}
	
				aanFeatures[cOption].push( featureNode );
				insert.append( featureNode );
			}
		}
	
		/* Built our DOM structure - replace the holding div with what we want */
		holding.replaceWith( insert );
		oSettings.nHolding = null;
	}
	
	
	/**
	 * Use the DOM source to create up an array of header cells. The idea here is to
	 * create a layout grid (array) of rows x columns, which contains a reference
	 * to the cell that that point in the grid (regardless of col/rowspan), such that
	 * any column / row could be removed and the new grid constructed
	 *  @param array {object} aLayout Array to store the calculated layout in
	 *  @param {node} nThead The header/footer element for the table
	 *  @memberof DataTable#oApi
	 */
	function _fnDetectHeader ( aLayout, nThead )
	{
		var nTrs = $(nThead).children('tr');
		var nTr, nCell;
		var i, k, l, iLen, jLen, iColShifted, iColumn, iColspan, iRowspan;
		var bUnique;
		var fnShiftCol = function ( a, i, j ) {
			var k = a[i];
	                while ( k[j] ) {
				j++;
			}
			return j;
		};
	
		aLayout.splice( 0, aLayout.length );
	
		/* We know how many rows there are in the layout - so prep it */
		for ( i=0, iLen=nTrs.length ; i<iLen ; i++ )
		{
			aLayout.push( [] );
		}
	
		/* Calculate a layout array */
		for ( i=0, iLen=nTrs.length ; i<iLen ; i++ )
		{
			nTr = nTrs[i];
			iColumn = 0;
	
			/* For every cell in the row... */
			nCell = nTr.firstChild;
			while ( nCell ) {
				if ( nCell.nodeName.toUpperCase() == "TD" ||
				     nCell.nodeName.toUpperCase() == "TH" )
				{
					/* Get the col and rowspan attributes from the DOM and sanitise them */
					iColspan = nCell.getAttribute('colspan') * 1;
					iRowspan = nCell.getAttribute('rowspan') * 1;
					iColspan = (!iColspan || iColspan===0 || iColspan===1) ? 1 : iColspan;
					iRowspan = (!iRowspan || iRowspan===0 || iRowspan===1) ? 1 : iRowspan;
	
					/* There might be colspan cells already in this row, so shift our target
					 * accordingly
					 */
					iColShifted = fnShiftCol( aLayout, i, iColumn );
	
					/* Cache calculation for unique columns */
					bUnique = iColspan === 1 ? true : false;
	
					/* If there is col / rowspan, copy the information into the layout grid */
					for ( l=0 ; l<iColspan ; l++ )
					{
						for ( k=0 ; k<iRowspan ; k++ )
						{
							aLayout[i+k][iColShifted+l] = {
								"cell": nCell,
								"unique": bUnique
							};
							aLayout[i+k].nTr = nTr;
						}
					}
				}
				nCell = nCell.nextSibling;
			}
		}
	}
	
	
	/**
	 * Get an array of unique th elements, one for each column
	 *  @param {object} oSettings dataTables settings object
	 *  @param {node} nHeader automatically detect the layout from this node - optional
	 *  @param {array} aLayout thead/tfoot layout from _fnDetectHeader - optional
	 *  @returns array {node} aReturn list of unique th's
	 *  @memberof DataTable#oApi
	 */
	function _fnGetUniqueThs ( oSettings, nHeader, aLayout )
	{
		var aReturn = [];
		if ( !aLayout )
		{
			aLayout = oSettings.aoHeader;
			if ( nHeader )
			{
				aLayout = [];
				_fnDetectHeader( aLayout, nHeader );
			}
		}
	
		for ( var i=0, iLen=aLayout.length ; i<iLen ; i++ )
		{
			for ( var j=0, jLen=aLayout[i].length ; j<jLen ; j++ )
			{
				if ( aLayout[i][j].unique &&
					 (!aReturn[j] || !oSettings.bSortCellsTop) )
				{
					aReturn[j] = aLayout[i][j].cell;
				}
			}
		}
	
		return aReturn;
	}
	
	/**
	 * Create an Ajax call based on the table's settings, taking into account that
	 * parameters can have multiple forms, and backwards compatibility.
	 *
	 * @param {object} oSettings dataTables settings object
	 * @param {array} data Data to send to the server, required by
	 *     DataTables - may be augmented by developer callbacks
	 * @param {function} fn Callback function to run when data is obtained
	 */
	function _fnBuildAjax( oSettings, data, fn )
	{
		// Compatibility with 1.9-, allow fnServerData and event to manipulate
		_fnCallbackFire( oSettings, 'aoServerParams', 'serverParams', [data] );
	
		// Convert to object based for 1.10+ if using the old array scheme which can
		// come from server-side processing or serverParams
		if ( data && $.isArray(data) ) {
			var tmp = {};
			var rbracket = /(.*?)\[\]$/;
	
			$.each( data, function (key, val) {
				var match = val.name.match(rbracket);
	
				if ( match ) {
					// Support for arrays
					var name = match[0];
	
					if ( ! tmp[ name ] ) {
						tmp[ name ] = [];
					}
					tmp[ name ].push( val.value );
				}
				else {
					tmp[val.name] = val.value;
				}
			} );
			data = tmp;
		}
	
		var ajaxData;
		var ajax = oSettings.ajax;
		var instance = oSettings.oInstance;
		var callback = function ( json ) {
			_fnCallbackFire( oSettings, null, 'xhr', [oSettings, json, oSettings.jqXHR] );
			fn( json );
		};
	
		if ( $.isPlainObject( ajax ) && ajax.data )
		{
			ajaxData = ajax.data;
	
			var newData = $.isFunction( ajaxData ) ?
				ajaxData( data, oSettings ) :  // fn can manipulate data or return
				ajaxData;                      // an object object or array to merge
	
			// If the function returned something, use that alone
			data = $.isFunction( ajaxData ) && newData ?
				newData :
				$.extend( true, data, newData );
	
			// Remove the data property as we've resolved it already and don't want
			// jQuery to do it again (it is restored at the end of the function)
			delete ajax.data;
		}
	
		var baseAjax = {
			"data": data,
			"success": function (json) {
				var error = json.error || json.sError;
				if ( error ) {
					_fnLog( oSettings, 0, error );
				}
	
				oSettings.json = json;
				callback( json );
			},
			"dataType": "json",
			"cache": false,
			"type": oSettings.sServerMethod,
			"error": function (xhr, error, thrown) {
				var ret = _fnCallbackFire( oSettings, null, 'xhr', [oSettings, null, oSettings.jqXHR] );
	
				if ( $.inArray( true, ret ) === -1 ) {
					if ( error == "parsererror" ) {
						_fnLog( oSettings, 0, 'Invalid JSON response', 1 );
					}
					else if ( xhr.readyState === 4 ) {
						_fnLog( oSettings, 0, 'Ajax error', 7 );
					}
				}
	
				_fnProcessingDisplay( oSettings, false );
			}
		};
	
		// Store the data submitted for the API
		oSettings.oAjaxData = data;
	
		// Allow plug-ins and external processes to modify the data
		_fnCallbackFire( oSettings, null, 'preXhr', [oSettings, data] );
	
		if ( oSettings.fnServerData )
		{
			// DataTables 1.9- compatibility
			oSettings.fnServerData.call( instance,
				oSettings.sAjaxSource,
				$.map( data, function (val, key) { // Need to convert back to 1.9 trad format
					return { name: key, value: val };
				} ),
				callback,
				oSettings
			);
		}
		else if ( oSettings.sAjaxSource || typeof ajax === 'string' )
		{
			// DataTables 1.9- compatibility
			oSettings.jqXHR = $.ajax( $.extend( baseAjax, {
				url: ajax || oSettings.sAjaxSource
			} ) );
		}
		else if ( $.isFunction( ajax ) )
		{
			// Is a function - let the caller define what needs to be done
			oSettings.jqXHR = ajax.call( instance, data, callback, oSettings );
		}
		else
		{
			// Object to extend the base settings
			oSettings.jqXHR = $.ajax( $.extend( baseAjax, ajax ) );
	
			// Restore for next time around
			ajax.data = ajaxData;
		}
	}
	
	
	/**
	 * Update the table using an Ajax call
	 *  @param {object} settings dataTables settings object
	 *  @returns {boolean} Block the table drawing or not
	 *  @memberof DataTable#oApi
	 */
	function _fnAjaxUpdate( settings )
	{
		if ( settings.bAjaxDataGet ) {
			settings.iDraw++;
			_fnProcessingDisplay( settings, true );
	
			_fnBuildAjax(
				settings,
				_fnAjaxParameters( settings ),
				function(json) {
					_fnAjaxUpdateDraw( settings, json );
				}
			);
	
			return false;
		}
		return true;
	}
	
	
	/**
	 * Build up the parameters in an object needed for a server-side processing
	 * request. Note that this is basically done twice, is different ways - a modern
	 * method which is used by default in DataTables 1.10 which uses objects and
	 * arrays, or the 1.9- method with is name / value pairs. 1.9 method is used if
	 * the sAjaxSource option is used in the initialisation, or the legacyAjax
	 * option is set.
	 *  @param {object} oSettings dataTables settings object
	 *  @returns {bool} block the table drawing or not
	 *  @memberof DataTable#oApi
	 */
	function _fnAjaxParameters( settings )
	{
		var
			columns = settings.aoColumns,
			columnCount = columns.length,
			features = settings.oFeatures,
			preSearch = settings.oPreviousSearch,
			preColSearch = settings.aoPreSearchCols,
			i, data = [], dataProp, column, columnSearch,
			sort = _fnSortFlatten( settings ),
			displayStart = settings._iDisplayStart,
			displayLength = features.bPaginate !== false ?
				settings._iDisplayLength :
				-1;
	
		var param = function ( name, value ) {
			data.push( { 'name': name, 'value': value } );
		};
	
		// DataTables 1.9- compatible method
		param( 'sEcho',          settings.iDraw );
		param( 'iColumns',       columnCount );
		param( 'sColumns',       _pluck( columns, 'sName' ).join(',') );
		param( 'iDisplayStart',  displayStart );
		param( 'iDisplayLength', displayLength );
	
		// DataTables 1.10+ method
		var d = {
			draw:    settings.iDraw,
			columns: [],
			order:   [],
			start:   displayStart,
			length:  displayLength,
			search:  {
				value: preSearch.sSearch,
				regex: preSearch.bRegex
			}
		};
	
		for ( i=0 ; i<columnCount ; i++ ) {
			column = columns[i];
			columnSearch = preColSearch[i];
			dataProp = typeof column.mData=="function" ? 'function' : column.mData ;
	
			d.columns.push( {
				data:       dataProp,
				name:       column.sName,
				searchable: column.bSearchable,
				orderable:  column.bSortable,
				search:     {
					value: columnSearch.sSearch,
					regex: columnSearch.bRegex
				}
			} );
	
			param( "mDataProp_"+i, dataProp );
	
			if ( features.bFilter ) {
				param( 'sSearch_'+i,     columnSearch.sSearch );
				param( 'bRegex_'+i,      columnSearch.bRegex );
				param( 'bSearchable_'+i, column.bSearchable );
			}
	
			if ( features.bSort ) {
				param( 'bSortable_'+i, column.bSortable );
			}
		}
	
		if ( features.bFilter ) {
			param( 'sSearch', preSearch.sSearch );
			param( 'bRegex', preSearch.bRegex );
		}
	
		if ( features.bSort ) {
			$.each( sort, function ( i, val ) {
				d.order.push( { column: val.col, dir: val.dir } );
	
				param( 'iSortCol_'+i, val.col );
				param( 'sSortDir_'+i, val.dir );
			} );
	
			param( 'iSortingCols', sort.length );
		}
	
		// If the legacy.ajax parameter is null, then we automatically decide which
		// form to use, based on sAjaxSource
		var legacy = DataTable.ext.legacy.ajax;
		if ( legacy === null ) {
			return settings.sAjaxSource ? data : d;
		}
	
		// Otherwise, if legacy has been specified then we use that to decide on the
		// form
		return legacy ? data : d;
	}
	
	
	/**
	 * Data the data from the server (nuking the old) and redraw the table
	 *  @param {object} oSettings dataTables settings object
	 *  @param {object} json json data return from the server.
	 *  @param {string} json.sEcho Tracking flag for DataTables to match requests
	 *  @param {int} json.iTotalRecords Number of records in the data set, not accounting for filtering
	 *  @param {int} json.iTotalDisplayRecords Number of records in the data set, accounting for filtering
	 *  @param {array} json.aaData The data to display on this page
	 *  @param {string} [json.sColumns] Column ordering (sName, comma separated)
	 *  @memberof DataTable#oApi
	 */
	function _fnAjaxUpdateDraw ( settings, json )
	{
		// v1.10 uses camelCase variables, while 1.9 uses Hungarian notation.
		// Support both
		var compat = function ( old, modern ) {
			return json[old] !== undefined ? json[old] : json[modern];
		};
	
		var data = _fnAjaxDataSrc( settings, json );
		var draw            = compat( 'sEcho',                'draw' );
		var recordsTotal    = compat( 'iTotalRecords',        'recordsTotal' );
		var recordsFiltered = compat( 'iTotalDisplayRecords', 'recordsFiltered' );
	
		if ( draw ) {
			// Protect against out of sequence returns
			if ( draw*1 < settings.iDraw ) {
				return;
			}
			settings.iDraw = draw * 1;
		}
	
		_fnClearTable( settings );
		settings._iRecordsTotal   = parseInt(recordsTotal, 10);
		settings._iRecordsDisplay = parseInt(recordsFiltered, 10);
	
		for ( var i=0, ien=data.length ; i<ien ; i++ ) {
			_fnAddData( settings, data[i] );
		}
		settings.aiDisplay = settings.aiDisplayMaster.slice();
	
		settings.bAjaxDataGet = false;
		_fnDraw( settings );
	
		if ( ! settings._bInitComplete ) {
			_fnInitComplete( settings, json );
		}
	
		settings.bAjaxDataGet = true;
		_fnProcessingDisplay( settings, false );
	}
	
	
	/**
	 * Get the data from the JSON data source to use for drawing a table. Using
	 * `_fnGetObjectDataFn` allows the data to be sourced from a property of the
	 * source object, or from a processing function.
	 *  @param {object} oSettings dataTables settings object
	 *  @param  {object} json Data source object / array from the server
	 *  @return {array} Array of data to use
	 */
	function _fnAjaxDataSrc ( oSettings, json )
	{
		var dataSrc = $.isPlainObject( oSettings.ajax ) && oSettings.ajax.dataSrc !== undefined ?
			oSettings.ajax.dataSrc :
			oSettings.sAjaxDataProp; // Compatibility with 1.9-.
	
		// Compatibility with 1.9-. In order to read from aaData, check if the
		// default has been changed, if not, check for aaData
		if ( dataSrc === 'data' ) {
			return json.aaData || json[dataSrc];
		}
	
		return dataSrc !== "" ?
			_fnGetObjectDataFn( dataSrc )( json ) :
			json;
	}
	
	/**
	 * Generate the node required for filtering text
	 *  @returns {node} Filter control element
	 *  @param {object} oSettings dataTables settings object
	 *  @memberof DataTable#oApi
	 */
	function _fnFeatureHtmlFilter ( settings )
	{
		var classes = settings.oClasses;
		var tableId = settings.sTableId;
		var language = settings.oLanguage;
		var previousSearch = settings.oPreviousSearch;
		var features = settings.aanFeatures;
		var input = '<input type="search" class="'+classes.sFilterInput+'"/>';
	
		var str = language.sSearch;
		str = str.match(/_INPUT_/) ?
			str.replace('_INPUT_', input) :
			str+input;
	
		var filter = $('<div/>', {
				'id': ! features.f ? tableId+'_filter' : null,
				'class': classes.sFilter
			} )
			.append( $('<label/>' ).append( str ) );
	
		var searchFn = function() {
			/* Update all other filter input elements for the new display */
			var n = features.f;
			var val = !this.value ? "" : this.value; // mental IE8 fix :-(
	
			/* Now do the filter */
			if ( val != previousSearch.sSearch ) {
				_fnFilterComplete( settings, {
					"sSearch": val,
					"bRegex": previousSearch.bRegex,
					"bSmart": previousSearch.bSmart ,
					"bCaseInsensitive": previousSearch.bCaseInsensitive
				} );
	
				// Need to redraw, without resorting
				settings._iDisplayStart = 0;
				_fnDraw( settings );
			}
		};
	
		var searchDelay = settings.searchDelay !== null ?
			settings.searchDelay :
			_fnDataSource( settings ) === 'ssp' ?
				400 :
				0;
	
		var jqFilter = $('input', filter)
			.val( previousSearch.sSearch )
			.attr( 'placeholder', language.sSearchPlaceholder )
			.on(
				'keyup.DT search.DT input.DT paste.DT cut.DT',
				searchDelay ?
					_fnThrottle( searchFn, searchDelay ) :
					searchFn
			)
			.on( 'keypress.DT', function(e) {
				/* Prevent form submission */
				if ( e.keyCode == 13 ) {
					return false;
				}
			} )
			.attr('aria-controls', tableId);
	
		// Update the input elements whenever the table is filtered
		$(settings.nTable).on( 'search.dt.DT', function ( ev, s ) {
			if ( settings === s ) {
				// IE9 throws an 'unknown error' if document.activeElement is used
				// inside an iframe or frame...
				try {
					if ( jqFilter[0] !== document.activeElement ) {
						jqFilter.val( previousSearch.sSearch );
					}
				}
				catch ( e ) {}
			}
		} );
	
		return filter[0];
	}
	
	
	/**
	 * Filter the table using both the global filter and column based filtering
	 *  @param {object} oSettings dataTables settings object
	 *  @param {object} oSearch search information
	 *  @param {int} [iForce] force a research of the master array (1) or not (undefined or 0)
	 *  @memberof DataTable#oApi
	 */
	function _fnFilterComplete ( oSettings, oInput, iForce )
	{
		var oPrevSearch = oSettings.oPreviousSearch;
		var aoPrevSearch = oSettings.aoPreSearchCols;
		var fnSaveFilter = function ( oFilter ) {
			/* Save the filtering values */
			oPrevSearch.sSearch = oFilter.sSearch;
			oPrevSearch.bRegex = oFilter.bRegex;
			oPrevSearch.bSmart = oFilter.bSmart;
			oPrevSearch.bCaseInsensitive = oFilter.bCaseInsensitive;
		};
		var fnRegex = function ( o ) {
			// Backwards compatibility with the bEscapeRegex option
			return o.bEscapeRegex !== undefined ? !o.bEscapeRegex : o.bRegex;
		};
	
		// Resolve any column types that are unknown due to addition or invalidation
		// @todo As per sort - can this be moved into an event handler?
		_fnColumnTypes( oSettings );
	
		/* In server-side processing all filtering is done by the server, so no point hanging around here */
		if ( _fnDataSource( oSettings ) != 'ssp' )
		{
			/* Global filter */
			_fnFilter( oSettings, oInput.sSearch, iForce, fnRegex(oInput), oInput.bSmart, oInput.bCaseInsensitive );
			fnSaveFilter( oInput );
	
			/* Now do the individual column filter */
			for ( var i=0 ; i<aoPrevSearch.length ; i++ )
			{
				_fnFilterColumn( oSettings, aoPrevSearch[i].sSearch, i, fnRegex(aoPrevSearch[i]),
					aoPrevSearch[i].bSmart, aoPrevSearch[i].bCaseInsensitive );
			}
	
			/* Custom filtering */
			_fnFilterCustom( oSettings );
		}
		else
		{
			fnSaveFilter( oInput );
		}
	
		/* Tell the draw function we have been filtering */
		oSettings.bFiltered = true;
		_fnCallbackFire( oSettings, null, 'search', [oSettings] );
	}
	
	
	/**
	 * Apply custom filtering functions
	 *  @param {object} oSettings dataTables settings object
	 *  @memberof DataTable#oApi
	 */
	function _fnFilterCustom( settings )
	{
		var filters = DataTable.ext.search;
		var displayRows = settings.aiDisplay;
		var row, rowIdx;
	
		for ( var i=0, ien=filters.length ; i<ien ; i++ ) {
			var rows = [];
	
			// Loop over each row and see if it should be included
			for ( var j=0, jen=displayRows.length ; j<jen ; j++ ) {
				rowIdx = displayRows[ j ];
				row = settings.aoData[ rowIdx ];
	
				if ( filters[i]( settings, row._aFilterData, rowIdx, row._aData, j ) ) {
					rows.push( rowIdx );
				}
			}
	
			// So the array reference doesn't break set the results into the
			// existing array
			displayRows.length = 0;
			$.merge( displayRows, rows );
		}
	}
	
	
	/**
	 * Filter the table on a per-column basis
	 *  @param {object} oSettings dataTables settings object
	 *  @param {string} sInput string to filter on
	 *  @param {int} iColumn column to filter
	 *  @param {bool} bRegex treat search string as a regular expression or not
	 *  @param {bool} bSmart use smart filtering or not
	 *  @param {bool} bCaseInsensitive Do case insenstive matching or not
	 *  @memberof DataTable#oApi
	 */
	function _fnFilterColumn ( settings, searchStr, colIdx, regex, smart, caseInsensitive )
	{
		if ( searchStr === '' ) {
			return;
		}
	
		var data;
		var out = [];
		var display = settings.aiDisplay;
		var rpSearch = _fnFilterCreateSearch( searchStr, regex, smart, caseInsensitive );
	
		for ( var i=0 ; i<display.length ; i++ ) {
			data = settings.aoData[ display[i] ]._aFilterData[ colIdx ];
	
			if ( rpSearch.test( data ) ) {
				out.push( display[i] );
			}
		}
	
		settings.aiDisplay = out;
	}
	
	
	/**
	 * Filter the data table based on user input and draw the table
	 *  @param {object} settings dataTables settings object
	 *  @param {string} input string to filter on
	 *  @param {int} force optional - force a research of the master array (1) or not (undefined or 0)
	 *  @param {bool} regex treat as a regular expression or not
	 *  @param {bool} smart perform smart filtering or not
	 *  @param {bool} caseInsensitive Do case insenstive matching or not
	 *  @memberof DataTable#oApi
	 */
	function _fnFilter( settings, input, force, regex, smart, caseInsensitive )
	{
		var rpSearch = _fnFilterCreateSearch( input, regex, smart, caseInsensitive );
		var prevSearch = settings.oPreviousSearch.sSearch;
		var displayMaster = settings.aiDisplayMaster;
		var display, invalidated, i;
		var filtered = [];
	
		// Need to take account of custom filtering functions - always filter
		if ( DataTable.ext.search.length !== 0 ) {
			force = true;
		}
	
		// Check if any of the rows were invalidated
		invalidated = _fnFilterData( settings );
	
		// If the input is blank - we just want the full data set
		if ( input.length <= 0 ) {
			settings.aiDisplay = displayMaster.slice();
		}
		else {
			// New search - start from the master array
			if ( invalidated ||
				 force ||
				 prevSearch.length > input.length ||
				 input.indexOf(prevSearch) !== 0 ||
				 settings.bSorted // On resort, the display master needs to be
				                  // re-filtered since indexes will have changed
			) {
				settings.aiDisplay = displayMaster.slice();
			}
	
			// Search the display array
			display = settings.aiDisplay;
	
			for ( i=0 ; i<display.length ; i++ ) {
				if ( rpSearch.test( settings.aoData[ display[i] ]._sFilterRow ) ) {
					filtered.push( display[i] );
				}
			}
	
			settings.aiDisplay = filtered;
		}
	}
	
	
	/**
	 * Build a regular expression object suitable for searching a table
	 *  @param {string} sSearch string to search for
	 *  @param {bool} bRegex treat as a regular expression or not
	 *  @param {bool} bSmart perform smart filtering or not
	 *  @param {bool} bCaseInsensitive Do case insensitive matching or not
	 *  @returns {RegExp} constructed object
	 *  @memberof DataTable#oApi
	 */
	function _fnFilterCreateSearch( search, regex, smart, caseInsensitive )
	{
		search = regex ?
			search :
			_fnEscapeRegex( search );
		
		if ( smart ) {
			/* For smart filtering we want to allow the search to work regardless of
			 * word order. We also want double quoted text to be preserved, so word
			 * order is important - a la google. So this is what we want to
			 * generate:
			 * 
			 * ^(?=.*?\bone\b)(?=.*?\btwo three\b)(?=.*?\bfour\b).*$
			 */
			var a = $.map( search.match( /"[^"]+"|[^ ]+/g ) || [''], function ( word ) {
				if ( word.charAt(0) === '"' ) {
					var m = word.match( /^"(.*)"$/ );
					word = m ? m[1] : word;
				}
	
				return word.replace('"', '');
			} );
	
			search = '^(?=.*?'+a.join( ')(?=.*?' )+').*$';
		}
	
		return new RegExp( search, caseInsensitive ? 'i' : '' );
	}
	
	
	/**
	 * Escape a string such that it can be used in a regular expression
	 *  @param {string} sVal string to escape
	 *  @returns {string} escaped string
	 *  @memberof DataTable#oApi
	 */
	var _fnEscapeRegex = DataTable.util.escapeRegex;
	
	var __filter_div = $('<div>')[0];
	var __filter_div_textContent = __filter_div.textContent !== undefined;
	
	// Update the filtering data for each row if needed (by invalidation or first run)
	function _fnFilterData ( settings )
	{
		var columns = settings.aoColumns;
		var column;
		var i, j, ien, jen, filterData, cellData, row;
		var fomatters = DataTable.ext.type.search;
		var wasInvalidated = false;
	
		for ( i=0, ien=settings.aoData.length ; i<ien ; i++ ) {
			row = settings.aoData[i];
	
			if ( ! row._aFilterData ) {
				filterData = [];
	
				for ( j=0, jen=columns.length ; j<jen ; j++ ) {
					column = columns[j];
	
					if ( column.bSearchable ) {
						cellData = _fnGetCellData( settings, i, j, 'filter' );
	
						if ( fomatters[ column.sType ] ) {
							cellData = fomatters[ column.sType ]( cellData );
						}
	
						// Search in DataTables 1.10 is string based. In 1.11 this
						// should be altered to also allow strict type checking.
						if ( cellData === null ) {
							cellData = '';
						}
	
						if ( typeof cellData !== 'string' && cellData.toString ) {
							cellData = cellData.toString();
						}
					}
					else {
						cellData = '';
					}
	
					// If it looks like there is an HTML entity in the string,
					// attempt to decode it so sorting works as expected. Note that
					// we could use a single line of jQuery to do this, but the DOM
					// method used here is much faster http://jsperf.com/html-decode
					if ( cellData.indexOf && cellData.indexOf('&') !== -1 ) {
						__filter_div.innerHTML = cellData;
						cellData = __filter_div_textContent ?
							__filter_div.textContent :
							__filter_div.innerText;
					}
	
					if ( cellData.replace ) {
						cellData = cellData.replace(/[\r\n]/g, '');
					}
	
					filterData.push( cellData );
				}
	
				row._aFilterData = filterData;
				row._sFilterRow = filterData.join('  ');
				wasInvalidated = true;
			}
		}
	
		return wasInvalidated;
	}
	
	
	/**
	 * Convert from the internal Hungarian notation to camelCase for external
	 * interaction
	 *  @param {object} obj Object to convert
	 *  @returns {object} Inverted object
	 *  @memberof DataTable#oApi
	 */
	function _fnSearchToCamel ( obj )
	{
		return {
			search:          obj.sSearch,
			smart:           obj.bSmart,
			regex:           obj.bRegex,
			caseInsensitive: obj.bCaseInsensitive
		};
	}
	
	
	
	/**
	 * Convert from camelCase notation to the internal Hungarian. We could use the
	 * Hungarian convert function here, but this is cleaner
	 *  @param {object} obj Object to convert
	 *  @returns {object} Inverted object
	 *  @memberof DataTable#oApi
	 */
	function _fnSearchToHung ( obj )
	{
		return {
			sSearch:          obj.search,
			bSmart:           obj.smart,
			bRegex:           obj.regex,
			bCaseInsensitive: obj.caseInsensitive
		};
	}
	
	/**
	 * Generate the node required for the info display
	 *  @param {object} oSettings dataTables settings object
	 *  @returns {node} Information element
	 *  @memberof DataTable#oApi
	 */
	function _fnFeatureHtmlInfo ( settings )
	{
		var
			tid = settings.sTableId,
			nodes = settings.aanFeatures.i,
			n = $('<div/>', {
				'class': settings.oClasses.sInfo,
				'id': ! nodes ? tid+'_info' : null
			} );
	
		if ( ! nodes ) {
			// Update display on each draw
			settings.aoDrawCallback.push( {
				"fn": _fnUpdateInfo,
				"sName": "information"
			} );
	
			n
				.attr( 'role', 'status' )
				.attr( 'aria-live', 'polite' );
	
			// Table is described by our info div
			$(settings.nTable).attr( 'aria-describedby', tid+'_info' );
		}
	
		return n[0];
	}
	
	
	/**
	 * Update the information elements in the display
	 *  @param {object} settings dataTables settings object
	 *  @memberof DataTable#oApi
	 */
	function _fnUpdateInfo ( settings )
	{
		/* Show information about the table */
		var nodes = settings.aanFeatures.i;
		if ( nodes.length === 0 ) {
			return;
		}
	
		var
			lang  = settings.oLanguage,
			start = settings._iDisplayStart+1,
			end   = settings.fnDisplayEnd(),
			max   = settings.fnRecordsTotal(),
			total = settings.fnRecordsDisplay(),
			out   = total ?
				lang.sInfo :
				lang.sInfoEmpty;
	
		if ( total !== max ) {
			/* Record set after filtering */
			out += ' ' + lang.sInfoFiltered;
		}
	
		// Convert the macros
		out += lang.sInfoPostFix;
		out = _fnInfoMacros( settings, out );
	
		var callback = lang.fnInfoCallback;
		if ( callback !== null ) {
			out = callback.call( settings.oInstance,
				settings, start, end, max, total, out
			);
		}
	
		$(nodes).html( out );
	}
	
	
	function _fnInfoMacros ( settings, str )
	{
		// When infinite scrolling, we are always starting at 1. _iDisplayStart is used only
		// internally
		var
			formatter  = settings.fnFormatNumber,
			start      = settings._iDisplayStart+1,
			len        = settings._iDisplayLength,
			vis        = settings.fnRecordsDisplay(),
			all        = len === -1;
	
		return str.
			replace(/_START_/g, formatter.call( settings, start ) ).
			replace(/_END_/g,   formatter.call( settings, settings.fnDisplayEnd() ) ).
			replace(/_MAX_/g,   formatter.call( settings, settings.fnRecordsTotal() ) ).
			replace(/_TOTAL_/g, formatter.call( settings, vis ) ).
			replace(/_PAGE_/g,  formatter.call( settings, all ? 1 : Math.ceil( start / len ) ) ).
			replace(/_PAGES_/g, formatter.call( settings, all ? 1 : Math.ceil( vis / len ) ) );
	}
	
	
	
	/**
	 * Draw the table for the first time, adding all required features
	 *  @param {object} settings dataTables settings object
	 *  @memberof DataTable#oApi
	 */
	function _fnInitialise ( settings )
	{
		var i, iLen, iAjaxStart=settings.iInitDisplayStart;
		var columns = settings.aoColumns, column;
		var features = settings.oFeatures;
		var deferLoading = settings.bDeferLoading; // value modified by the draw
	
		/* Ensure that the table data is fully initialised */
		if ( ! settings.bInitialised ) {
			setTimeout( function(){ _fnInitialise( settings ); }, 200 );
			return;
		}
	
		/* Show the display HTML options */
		_fnAddOptionsHtml( settings );
	
		/* Build and draw the header / footer for the table */
		_fnBuildHead( settings );
		_fnDrawHead( settings, settings.aoHeader );
		_fnDrawHead( settings, settings.aoFooter );
	
		/* Okay to show that something is going on now */
		_fnProcessingDisplay( settings, true );
	
		/* Calculate sizes for columns */
		if ( features.bAutoWidth ) {
			_fnCalculateColumnWidths( settings );
		}
	
		for ( i=0, iLen=columns.length ; i<iLen ; i++ ) {
			column = columns[i];
	
			if ( column.sWidth ) {
				column.nTh.style.width = _fnStringToCss( column.sWidth );
			}
		}
	
		_fnCallbackFire( settings, null, 'preInit', [settings] );
	
		// If there is default sorting required - let's do it. The sort function
		// will do the drawing for us. Otherwise we draw the table regardless of the
		// Ajax source - this allows the table to look initialised for Ajax sourcing
		// data (show 'loading' message possibly)
		_fnReDraw( settings );
	
		// Server-side processing init complete is done by _fnAjaxUpdateDraw
		var dataSrc = _fnDataSource( settings );
		if ( dataSrc != 'ssp' || deferLoading ) {
			// if there is an ajax source load the data
			if ( dataSrc == 'ajax' ) {
				_fnBuildAjax( settings, [], function(json) {
					var aData = _fnAjaxDataSrc( settings, json );
	
					// Got the data - add it to the table
					for ( i=0 ; i<aData.length ; i++ ) {
						_fnAddData( settings, aData[i] );
					}
	
					// Reset the init display for cookie saving. We've already done
					// a filter, and therefore cleared it before. So we need to make
					// it appear 'fresh'
					settings.iInitDisplayStart = iAjaxStart;
	
					_fnReDraw( settings );
	
					_fnProcessingDisplay( settings, false );
					_fnInitComplete( settings, json );
				}, settings );
			}
			else {
				_fnProcessingDisplay( settings, false );
				_fnInitComplete( settings );
			}
		}
	}
	
	
	/**
	 * Draw the table for the first time, adding all required features
	 *  @param {object} oSettings dataTables settings object
	 *  @param {object} [json] JSON from the server that completed the table, if using Ajax source
	 *    with client-side processing (optional)
	 *  @memberof DataTable#oApi
	 */
	function _fnInitComplete ( settings, json )
	{
		settings._bInitComplete = true;
	
		// When data was added after the initialisation (data or Ajax) we need to
		// calculate the column sizing
		if ( json || settings.oInit.aaData ) {
			_fnAdjustColumnSizing( settings );
		}
	
		_fnCallbackFire( settings, null, 'plugin-init', [settings, json] );
		_fnCallbackFire( settings, 'aoInitComplete', 'init', [settings, json] );
	}
	
	
	function _fnLengthChange ( settings, val )
	{
		var len = parseInt( val, 10 );
		settings._iDisplayLength = len;
	
		_fnLengthOverflow( settings );
	
		// Fire length change event
		_fnCallbackFire( settings, null, 'length', [settings, len] );
	}
	
	
	/**
	 * Generate the node required for user display length changing
	 *  @param {object} settings dataTables settings object
	 *  @returns {node} Display length feature node
	 *  @memberof DataTable#oApi
	 */
	function _fnFeatureHtmlLength ( settings )
	{
		var
			classes  = settings.oClasses,
			tableId  = settings.sTableId,
			menu     = settings.aLengthMenu,
			d2       = $.isArray( menu[0] ),
			lengths  = d2 ? menu[0] : menu,
			language = d2 ? menu[1] : menu;
	
		var select = $('<select/>', {
			'name':          tableId+'_length',
			'aria-controls': tableId,
			'class':         classes.sLengthSelect
		} );
	
		for ( var i=0, ien=lengths.length ; i<ien ; i++ ) {
			select[0][ i ] = new Option(
				typeof language[i] === 'number' ?
					settings.fnFormatNumber( language[i] ) :
					language[i],
				lengths[i]
			);
		}
	
		var div = $('<div><label/></div>').addClass( classes.sLength );
		if ( ! settings.aanFeatures.l ) {
			div[0].id = tableId+'_length';
		}
	
		div.children().append(
			settings.oLanguage.sLengthMenu.replace( '_MENU_', select[0].outerHTML )
		);
	
		// Can't use `select` variable as user might provide their own and the
		// reference is broken by the use of outerHTML
		$('select', div)
			.val( settings._iDisplayLength )
			.on( 'change.DT', function(e) {
				_fnLengthChange( settings, $(this).val() );
				_fnDraw( settings );
			} );
	
		// Update node value whenever anything changes the table's length
		$(settings.nTable).on( 'length.dt.DT', function (e, s, len) {
			if ( settings === s ) {
				$('select', div).val( len );
			}
		} );
	
		return div[0];
	}
	
	
	
	/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
	 * Note that most of the paging logic is done in
	 * DataTable.ext.pager
	 */
	
	/**
	 * Generate the node required for default pagination
	 *  @param {object} oSettings dataTables settings object
	 *  @returns {node} Pagination feature node
	 *  @memberof DataTable#oApi
	 */
	function _fnFeatureHtmlPaginate ( settings )
	{
		var
			type   = settings.sPaginationType,
			plugin = DataTable.ext.pager[ type ],
			modern = typeof plugin === 'function',
			redraw = function( settings ) {
				_fnDraw( settings );
			},
			node = $('<div/>').addClass( settings.oClasses.sPaging + type )[0],
			features = settings.aanFeatures;
	
		if ( ! modern ) {
			plugin.fnInit( settings, node, redraw );
		}
	
		/* Add a draw callback for the pagination on first instance, to update the paging display */
		if ( ! features.p )
		{
			node.id = settings.sTableId+'_paginate';
	
			settings.aoDrawCallback.push( {
				"fn": function( settings ) {
					if ( modern ) {
						var
							start      = settings._iDisplayStart,
							len        = settings._iDisplayLength,
							visRecords = settings.fnRecordsDisplay(),
							all        = len === -1,
							page = all ? 0 : Math.ceil( start / len ),
							pages = all ? 1 : Math.ceil( visRecords / len ),
							buttons = plugin(page, pages),
							i, ien;
	
						for ( i=0, ien=features.p.length ; i<ien ; i++ ) {
							_fnRenderer( settings, 'pageButton' )(
								settings, features.p[i], i, buttons, page, pages
							);
						}
					}
					else {
						plugin.fnUpdate( settings, redraw );
					}
				},
				"sName": "pagination"
			} );
		}
	
		return node;
	}
	
	
	/**
	 * Alter the display settings to change the page
	 *  @param {object} settings DataTables settings object
	 *  @param {string|int} action Paging action to take: "first", "previous",
	 *    "next" or "last" or page number to jump to (integer)
	 *  @param [bool] redraw Automatically draw the update or not
	 *  @returns {bool} true page has changed, false - no change
	 *  @memberof DataTable#oApi
	 */
	function _fnPageChange ( settings, action, redraw )
	{
		var
			start     = settings._iDisplayStart,
			len       = settings._iDisplayLength,
			records   = settings.fnRecordsDisplay();
	
		if ( records === 0 || len === -1 )
		{
			start = 0;
		}
		else if ( typeof action === "number" )
		{
			start = action * len;
	
			if ( start > records )
			{
				start = 0;
			}
		}
		else if ( action == "first" )
		{
			start = 0;
		}
		else if ( action == "previous" )
		{
			start = len >= 0 ?
				start - len :
				0;
	
			if ( start < 0 )
			{
			  start = 0;
			}
		}
		else if ( action == "next" )
		{
			if ( start + len < records )
			{
				start += len;
			}
		}
		else if ( action == "last" )
		{
			start = Math.floor( (records-1) / len) * len;
		}
		else
		{
			_fnLog( settings, 0, "Unknown paging action: "+action, 5 );
		}
	
		var changed = settings._iDisplayStart !== start;
		settings._iDisplayStart = start;
	
		if ( changed ) {
			_fnCallbackFire( settings, null, 'page', [settings] );
	
			if ( redraw ) {
				_fnDraw( settings );
			}
		}
	
		return changed;
	}
	
	
	
	/**
	 * Generate the node required for the processing node
	 *  @param {object} settings dataTables settings object
	 *  @returns {node} Processing element
	 *  @memberof DataTable#oApi
	 */
	function _fnFeatureHtmlProcessing ( settings )
	{
		return $('<div/>', {
				'id': ! settings.aanFeatures.r ? settings.sTableId+'_processing' : null,
				'class': settings.oClasses.sProcessing
			} )
			.html( settings.oLanguage.sProcessing )
			.insertBefore( settings.nTable )[0];
	}
	
	
	/**
	 * Display or hide the processing indicator
	 *  @param {object} settings dataTables settings object
	 *  @param {bool} show Show the processing indicator (true) or not (false)
	 *  @memberof DataTable#oApi
	 */
	function _fnProcessingDisplay ( settings, show )
	{
		if ( settings.oFeatures.bProcessing ) {
			$(settings.aanFeatures.r).css( 'display', show ? 'block' : 'none' );
		}
	
		_fnCallbackFire( settings, null, 'processing', [settings, show] );
	}
	
	/**
	 * Add any control elements for the table - specifically scrolling
	 *  @param {object} settings dataTables settings object
	 *  @returns {node} Node to add to the DOM
	 *  @memberof DataTable#oApi
	 */
	function _fnFeatureHtmlTable ( settings )
	{
		var table = $(settings.nTable);
	
		// Add the ARIA grid role to the table
		table.attr( 'role', 'grid' );
	
		// Scrolling from here on in
		var scroll = settings.oScroll;
	
		if ( scroll.sX === '' && scroll.sY === '' ) {
			return settings.nTable;
		}
	
		var scrollX = scroll.sX;
		var scrollY = scroll.sY;
		var classes = settings.oClasses;
		var caption = table.children('caption');
		var captionSide = caption.length ? caption[0]._captionSide : null;
		var headerClone = $( table[0].cloneNode(false) );
		var footerClone = $( table[0].cloneNode(false) );
		var footer = table.children('tfoot');
		var _div = '<div/>';
		var size = function ( s ) {
			return !s ? null : _fnStringToCss( s );
		};
	
		if ( ! footer.length ) {
			footer = null;
		}
	
		/*
		 * The HTML structure that we want to generate in this function is:
		 *  div - scroller
		 *    div - scroll head
		 *      div - scroll head inner
		 *        table - scroll head table
		 *          thead - thead
		 *    div - scroll body
		 *      table - table (master table)
		 *        thead - thead clone for sizing
		 *        tbody - tbody
		 *    div - scroll foot
		 *      div - scroll foot inner
		 *        table - scroll foot table
		 *          tfoot - tfoot
		 */
		var scroller = $( _div, { 'class': classes.sScrollWrapper } )
			.append(
				$(_div, { 'class': classes.sScrollHead } )
					.css( {
						overflow: 'hidden',
						position: 'relative',
						border: 0,
						width: scrollX ? size(scrollX) : '100%'
					} )
					.append(
						$(_div, { 'class': classes.sScrollHeadInner } )
							.css( {
								'box-sizing': 'content-box',
								width: scroll.sXInner || '100%'
							} )
							.append(
								headerClone
									.removeAttr('id')
									.css( 'margin-left', 0 )
									.append( captionSide === 'top' ? caption : null )
									.append(
										table.children('thead')
									)
							)
					)
			)
			.append(
				$(_div, { 'class': classes.sScrollBody } )
					.css( {
						position: 'relative',
						overflow: 'auto',
						width: size( scrollX )
					} )
					.append( table )
			);
	
		if ( footer ) {
			scroller.append(
				$(_div, { 'class': classes.sScrollFoot } )
					.css( {
						overflow: 'hidden',
						border: 0,
						width: scrollX ? size(scrollX) : '100%'
					} )
					.append(
						$(_div, { 'class': classes.sScrollFootInner } )
							.append(
								footerClone
									.removeAttr('id')
									.css( 'margin-left', 0 )
									.append( captionSide === 'bottom' ? caption : null )
									.append(
										table.children('tfoot')
									)
							)
					)
			);
		}
	
		var children = scroller.children();
		var scrollHead = children[0];
		var scrollBody = children[1];
		var scrollFoot = footer ? children[2] : null;
	
		// When the body is scrolled, then we also want to scroll the headers
		if ( scrollX ) {
			$(scrollBody).on( 'scroll.DT', function (e) {
				var scrollLeft = this.scrollLeft;
	
				scrollHead.scrollLeft = scrollLeft;
	
				if ( footer ) {
					scrollFoot.scrollLeft = scrollLeft;
				}
			} );
		}
	
		$(scrollBody).css(
			scrollY && scroll.bCollapse ? 'max-height' : 'height', 
			scrollY
		);
	
		settings.nScrollHead = scrollHead;
		settings.nScrollBody = scrollBody;
		settings.nScrollFoot = scrollFoot;
	
		// On redraw - align columns
		settings.aoDrawCallback.push( {
			"fn": _fnScrollDraw,
			"sName": "scrolling"
		} );
	
		return scroller[0];
	}
	
	
	
	/**
	 * Update the header, footer and body tables for resizing - i.e. column
	 * alignment.
	 *
	 * Welcome to the most horrible function DataTables. The process that this
	 * function follows is basically:
	 *   1. Re-create the table inside the scrolling div
	 *   2. Take live measurements from the DOM
	 *   3. Apply the measurements to align the columns
	 *   4. Clean up
	 *
	 *  @param {object} settings dataTables settings object
	 *  @memberof DataTable#oApi
	 */
	function _fnScrollDraw ( settings )
	{
		// Given that this is such a monster function, a lot of variables are use
		// to try and keep the minimised size as small as possible
		var
			scroll         = settings.oScroll,
			scrollX        = scroll.sX,
			scrollXInner   = scroll.sXInner,
			scrollY        = scroll.sY,
			barWidth       = scroll.iBarWidth,
			divHeader      = $(settings.nScrollHead),
			divHeaderStyle = divHeader[0].style,
			divHeaderInner = divHeader.children('div'),
			divHeaderInnerStyle = divHeaderInner[0].style,
			divHeaderTable = divHeaderInner.children('table'),
			divBodyEl      = settings.nScrollBody,
			divBody        = $(divBodyEl),
			divBodyStyle   = divBodyEl.style,
			divFooter      = $(settings.nScrollFoot),
			divFooterInner = divFooter.children('div'),
			divFooterTable = divFooterInner.children('table'),
			header         = $(settings.nTHead),
			table          = $(settings.nTable),
			tableEl        = table[0],
			tableStyle     = tableEl.style,
			footer         = settings.nTFoot ? $(settings.nTFoot) : null,
			browser        = settings.oBrowser,
			ie67           = browser.bScrollOversize,
			dtHeaderCells  = _pluck( settings.aoColumns, 'nTh' ),
			headerTrgEls, footerTrgEls,
			headerSrcEls, footerSrcEls,
			headerCopy, footerCopy,
			headerWidths=[], footerWidths=[],
			headerContent=[], footerContent=[],
			idx, correction, sanityWidth,
			zeroOut = function(nSizer) {
				var style = nSizer.style;
				style.paddingTop = "0";
				style.paddingBottom = "0";
				style.borderTopWidth = "0";
				style.borderBottomWidth = "0";
				style.height = 0;
			};
	
		// If the scrollbar visibility has changed from the last draw, we need to
		// adjust the column sizes as the table width will have changed to account
		// for the scrollbar
		var scrollBarVis = divBodyEl.scrollHeight > divBodyEl.clientHeight;
		
		if ( settings.scrollBarVis !== scrollBarVis && settings.scrollBarVis !== undefined ) {
			settings.scrollBarVis = scrollBarVis;
			_fnAdjustColumnSizing( settings );
			return; // adjust column sizing will call this function again
		}
		else {
			settings.scrollBarVis = scrollBarVis;
		}
	
		/*
		 * 1. Re-create the table inside the scrolling div
		 */
	
		// Remove the old minimised thead and tfoot elements in the inner table
		table.children('thead, tfoot').remove();
	
		if ( footer ) {
			footerCopy = footer.clone().prependTo( table );
			footerTrgEls = footer.find('tr'); // the original tfoot is in its own table and must be sized
			footerSrcEls = footerCopy.find('tr');
		}
	
		// Clone the current header and footer elements and then place it into the inner table
		headerCopy = header.clone().prependTo( table );
		headerTrgEls = header.find('tr'); // original header is in its own table
		headerSrcEls = headerCopy.find('tr');
		headerCopy.find('th, td').removeAttr('tabindex');
	
	
		/*
		 * 2. Take live measurements from the DOM - do not alter the DOM itself!
		 */
	
		// Remove old sizing and apply the calculated column widths
		// Get the unique column headers in the newly created (cloned) header. We want to apply the
		// calculated sizes to this header
		if ( ! scrollX )
		{
			divBodyStyle.width = '100%';
			divHeader[0].style.width = '100%';
		}
	
		$.each( _fnGetUniqueThs( settings, headerCopy ), function ( i, el ) {
			idx = _fnVisibleToColumnIndex( settings, i );
			el.style.width = settings.aoColumns[idx].sWidth;
		} );
	
		if ( footer ) {
			_fnApplyToChildren( function(n) {
				n.style.width = "";
			}, footerSrcEls );
		}
	
		// Size the table as a whole
		sanityWidth = table.outerWidth();
		if ( scrollX === "" ) {
			// No x scrolling
			tableStyle.width = "100%";
	
			// IE7 will make the width of the table when 100% include the scrollbar
			// - which is shouldn't. When there is a scrollbar we need to take this
			// into account.
			if ( ie67 && (table.find('tbody').height() > divBodyEl.offsetHeight ||
				divBody.css('overflow-y') == "scroll")
			) {
				tableStyle.width = _fnStringToCss( table.outerWidth() - barWidth);
			}
	
			// Recalculate the sanity width
			sanityWidth = table.outerWidth();
		}
		else if ( scrollXInner !== "" ) {
			// legacy x scroll inner has been given - use it
			tableStyle.width = _fnStringToCss(scrollXInner);
	
			// Recalculate the sanity width
			sanityWidth = table.outerWidth();
		}
	
		// Hidden header should have zero height, so remove padding and borders. Then
		// set the width based on the real headers
	
		// Apply all styles in one pass
		_fnApplyToChildren( zeroOut, headerSrcEls );
	
		// Read all widths in next pass
		_fnApplyToChildren( function(nSizer) {
			headerContent.push( nSizer.innerHTML );
			headerWidths.push( _fnStringToCss( $(nSizer).css('width') ) );
		}, headerSrcEls );
	
		// Apply all widths in final pass
		_fnApplyToChildren( function(nToSize, i) {
			// Only apply widths to the DataTables detected header cells - this
			// prevents complex headers from having contradictory sizes applied
			if ( $.inArray( nToSize, dtHeaderCells ) !== -1 ) {
				nToSize.style.width = headerWidths[i];
			}
		}, headerTrgEls );
	
		$(headerSrcEls).height(0);
	
		/* Same again with the footer if we have one */
		if ( footer )
		{
			_fnApplyToChildren( zeroOut, footerSrcEls );
	
			_fnApplyToChildren( function(nSizer) {
				footerContent.push( nSizer.innerHTML );
				footerWidths.push( _fnStringToCss( $(nSizer).css('width') ) );
			}, footerSrcEls );
	
			_fnApplyToChildren( function(nToSize, i) {
				nToSize.style.width = footerWidths[i];
			}, footerTrgEls );
	
			$(footerSrcEls).height(0);
		}
	
	
		/*
		 * 3. Apply the measurements
		 */
	
		// "Hide" the header and footer that we used for the sizing. We need to keep
		// the content of the cell so that the width applied to the header and body
		// both match, but we want to hide it completely. We want to also fix their
		// width to what they currently are
		_fnApplyToChildren( function(nSizer, i) {
			nSizer.innerHTML = '<div class="dataTables_sizing" style="height:0;overflow:hidden;">'+headerContent[i]+'</div>';
			nSizer.style.width = headerWidths[i];
		}, headerSrcEls );
	
		if ( footer )
		{
			_fnApplyToChildren( function(nSizer, i) {
				nSizer.innerHTML = '<div class="dataTables_sizing" style="height:0;overflow:hidden;">'+footerContent[i]+'</div>';
				nSizer.style.width = footerWidths[i];
			}, footerSrcEls );
		}
	
		// Sanity check that the table is of a sensible width. If not then we are going to get
		// misalignment - try to prevent this by not allowing the table to shrink below its min width
		if ( table.outerWidth() < sanityWidth )
		{
			// The min width depends upon if we have a vertical scrollbar visible or not */
			correction = ((divBodyEl.scrollHeight > divBodyEl.offsetHeight ||
				divBody.css('overflow-y') == "scroll")) ?
					sanityWidth+barWidth :
					sanityWidth;
	
			// IE6/7 are a law unto themselves...
			if ( ie67 && (divBodyEl.scrollHeight >
				divBodyEl.offsetHeight || divBody.css('overflow-y') == "scroll")
			) {
				tableStyle.width = _fnStringToCss( correction-barWidth );
			}
	
			// And give the user a warning that we've stopped the table getting too small
			if ( scrollX === "" || scrollXInner !== "" ) {
				_fnLog( settings, 1, 'Possible column misalignment', 6 );
			}
		}
		else
		{
			correction = '100%';
		}
	
		// Apply to the container elements
		divBodyStyle.width = _fnStringToCss( correction );
		divHeaderStyle.width = _fnStringToCss( correction );
	
		if ( footer ) {
			settings.nScrollFoot.style.width = _fnStringToCss( correction );
		}
	
	
		/*
		 * 4. Clean up
		 */
		if ( ! scrollY ) {
			/* IE7< puts a vertical scrollbar in place (when it shouldn't be) due to subtracting
			 * the scrollbar height from the visible display, rather than adding it on. We need to
			 * set the height in order to sort this. Don't want to do it in any other browsers.
			 */
			if ( ie67 ) {
				divBodyStyle.height = _fnStringToCss( tableEl.offsetHeight+barWidth );
			}
		}
	
		/* Finally set the width's of the header and footer tables */
		var iOuterWidth = table.outerWidth();
		divHeaderTable[0].style.width = _fnStringToCss( iOuterWidth );
		divHeaderInnerStyle.width = _fnStringToCss( iOuterWidth );
	
		// Figure out if there are scrollbar present - if so then we need a the header and footer to
		// provide a bit more space to allow "overflow" scrolling (i.e. past the scrollbar)
		var bScrolling = table.height() > divBodyEl.clientHeight || divBody.css('overflow-y') == "scroll";
		var padding = 'padding' + (browser.bScrollbarLeft ? 'Left' : 'Right' );
		divHeaderInnerStyle[ padding ] = bScrolling ? barWidth+"px" : "0px";
	
		if ( footer ) {
			divFooterTable[0].style.width = _fnStringToCss( iOuterWidth );
			divFooterInner[0].style.width = _fnStringToCss( iOuterWidth );
			divFooterInner[0].style[padding] = bScrolling ? barWidth+"px" : "0px";
		}
	
		// Correct DOM ordering for colgroup - comes before the thead
		table.children('colgroup').insertBefore( table.children('thead') );
	
		/* Adjust the position of the header in case we loose the y-scrollbar */
		divBody.scroll();
	
		// If sorting or filtering has occurred, jump the scrolling back to the top
		// only if we aren't holding the position
		if ( (settings.bSorted || settings.bFiltered) && ! settings._drawHold ) {
			divBodyEl.scrollTop = 0;
		}
	}
	
	
	
	/**
	 * Apply a given function to the display child nodes of an element array (typically
	 * TD children of TR rows
	 *  @param {function} fn Method to apply to the objects
	 *  @param array {nodes} an1 List of elements to look through for display children
	 *  @param array {nodes} an2 Another list (identical structure to the first) - optional
	 *  @memberof DataTable#oApi
	 */
	function _fnApplyToChildren( fn, an1, an2 )
	{
		var index=0, i=0, iLen=an1.length;
		var nNode1, nNode2;
	
		while ( i < iLen ) {
			nNode1 = an1[i].firstChild;
			nNode2 = an2 ? an2[i].firstChild : null;
	
			while ( nNode1 ) {
				if ( nNode1.nodeType === 1 ) {
					if ( an2 ) {
						fn( nNode1, nNode2, index );
					}
					else {
						fn( nNode1, index );
					}
	
					index++;
				}
	
				nNode1 = nNode1.nextSibling;
				nNode2 = an2 ? nNode2.nextSibling : null;
			}
	
			i++;
		}
	}
	
	
	
	var __re_html_remove = /<.*?>/g;
	
	
	/**
	 * Calculate the width of columns for the table
	 *  @param {object} oSettings dataTables settings object
	 *  @memberof DataTable#oApi
	 */
	function _fnCalculateColumnWidths ( oSettings )
	{
		var
			table = oSettings.nTable,
			columns = oSettings.aoColumns,
			scroll = oSettings.oScroll,
			scrollY = scroll.sY,
			scrollX = scroll.sX,
			scrollXInner = scroll.sXInner,
			columnCount = columns.length,
			visibleColumns = _fnGetColumns( oSettings, 'bVisible' ),
			headerCells = $('th', oSettings.nTHead),
			tableWidthAttr = table.getAttribute('width'), // from DOM element
			tableContainer = table.parentNode,
			userInputs = false,
			i, column, columnIdx, width, outerWidth,
			browser = oSettings.oBrowser,
			ie67 = browser.bScrollOversize;
	
		var styleWidth = table.style.width;
		if ( styleWidth && styleWidth.indexOf('%') !== -1 ) {
			tableWidthAttr = styleWidth;
		}
	
		/* Convert any user input sizes into pixel sizes */
		for ( i=0 ; i<visibleColumns.length ; i++ ) {
			column = columns[ visibleColumns[i] ];
	
			if ( column.sWidth !== null ) {
				column.sWidth = _fnConvertToWidth( column.sWidthOrig, tableContainer );
	
				userInputs = true;
			}
		}
	
		/* If the number of columns in the DOM equals the number that we have to
		 * process in DataTables, then we can use the offsets that are created by
		 * the web- browser. No custom sizes can be set in order for this to happen,
		 * nor scrolling used
		 */
		if ( ie67 || ! userInputs && ! scrollX && ! scrollY &&
		     columnCount == _fnVisbleColumns( oSettings ) &&
		     columnCount == headerCells.length
		) {
			for ( i=0 ; i<columnCount ; i++ ) {
				var colIdx = _fnVisibleToColumnIndex( oSettings, i );
	
				if ( colIdx !== null ) {
					columns[ colIdx ].sWidth = _fnStringToCss( headerCells.eq(i).width() );
				}
			}
		}
		else
		{
			// Otherwise construct a single row, worst case, table with the widest
			// node in the data, assign any user defined widths, then insert it into
			// the DOM and allow the browser to do all the hard work of calculating
			// table widths
			var tmpTable = $(table).clone() // don't use cloneNode - IE8 will remove events on the main table
				.css( 'visibility', 'hidden' )
				.removeAttr( 'id' );
	
			// Clean up the table body
			tmpTable.find('tbody tr').remove();
			var tr = $('<tr/>').appendTo( tmpTable.find('tbody') );
	
			// Clone the table header and footer - we can't use the header / footer
			// from the cloned table, since if scrolling is active, the table's
			// real header and footer are contained in different table tags
			tmpTable.find('thead, tfoot').remove();
			tmpTable
				.append( $(oSettings.nTHead).clone() )
				.append( $(oSettings.nTFoot).clone() );
	
			// Remove any assigned widths from the footer (from scrolling)
			tmpTable.find('tfoot th, tfoot td').css('width', '');
	
			// Apply custom sizing to the cloned header
			headerCells = _fnGetUniqueThs( oSettings, tmpTable.find('thead')[0] );
	
			for ( i=0 ; i<visibleColumns.length ; i++ ) {
				column = columns[ visibleColumns[i] ];
	
				headerCells[i].style.width = column.sWidthOrig !== null && column.sWidthOrig !== '' ?
					_fnStringToCss( column.sWidthOrig ) :
					'';
	
				// For scrollX we need to force the column width otherwise the
				// browser will collapse it. If this width is smaller than the
				// width the column requires, then it will have no effect
				if ( column.sWidthOrig && scrollX ) {
					$( headerCells[i] ).append( $('<div/>').css( {
						width: column.sWidthOrig,
						margin: 0,
						padding: 0,
						border: 0,
						height: 1
					} ) );
				}
			}
	
			// Find the widest cell for each column and put it into the table
			if ( oSettings.aoData.length ) {
				for ( i=0 ; i<visibleColumns.length ; i++ ) {
					columnIdx = visibleColumns[i];
					column = columns[ columnIdx ];
	
					$( _fnGetWidestNode( oSettings, columnIdx ) )
						.clone( false )
						.append( column.sContentPadding )
						.appendTo( tr );
				}
			}
	
			// Tidy the temporary table - remove name attributes so there aren't
			// duplicated in the dom (radio elements for example)
			$('[name]', tmpTable).removeAttr('name');
	
			// Table has been built, attach to the document so we can work with it.
			// A holding element is used, positioned at the top of the container
			// with minimal height, so it has no effect on if the container scrolls
			// or not. Otherwise it might trigger scrolling when it actually isn't
			// needed
			var holder = $('<div/>').css( scrollX || scrollY ?
					{
						position: 'absolute',
						top: 0,
						left: 0,
						height: 1,
						right: 0,
						overflow: 'hidden'
					} :
					{}
				)
				.append( tmpTable )
				.appendTo( tableContainer );
	
			// When scrolling (X or Y) we want to set the width of the table as 
			// appropriate. However, when not scrolling leave the table width as it
			// is. This results in slightly different, but I think correct behaviour
			if ( scrollX && scrollXInner ) {
				tmpTable.width( scrollXInner );
			}
			else if ( scrollX ) {
				tmpTable.css( 'width', 'auto' );
				tmpTable.removeAttr('width');
	
				// If there is no width attribute or style, then allow the table to
				// collapse
				if ( tmpTable.width() < tableContainer.clientWidth && tableWidthAttr ) {
					tmpTable.width( tableContainer.clientWidth );
				}
			}
			else if ( scrollY ) {
				tmpTable.width( tableContainer.clientWidth );
			}
			else if ( tableWidthAttr ) {
				tmpTable.width( tableWidthAttr );
			}
	
			// Get the width of each column in the constructed table - we need to
			// know the inner width (so it can be assigned to the other table's
			// cells) and the outer width so we can calculate the full width of the
			// table. This is safe since DataTables requires a unique cell for each
			// column, but if ever a header can span multiple columns, this will
			// need to be modified.
			var total = 0;
			for ( i=0 ; i<visibleColumns.length ; i++ ) {
				var cell = $(headerCells[i]);
				var border = cell.outerWidth() - cell.width();
	
				// Use getBounding... where possible (not IE8-) because it can give
				// sub-pixel accuracy, which we then want to round up!
				var bounding = browser.bBounding ?
					Math.ceil( headerCells[i].getBoundingClientRect().width ) :
					cell.outerWidth();
	
				// Total is tracked to remove any sub-pixel errors as the outerWidth
				// of the table might not equal the total given here (IE!).
				total += bounding;
	
				// Width for each column to use
				columns[ visibleColumns[i] ].sWidth = _fnStringToCss( bounding - border );
			}
	
			table.style.width = _fnStringToCss( total );
	
			// Finished with the table - ditch it
			holder.remove();
		}
	
		// If there is a width attr, we want to attach an event listener which
		// allows the table sizing to automatically adjust when the window is
		// resized. Use the width attr rather than CSS, since we can't know if the
		// CSS is a relative value or absolute - DOM read is always px.
		if ( tableWidthAttr ) {
			table.style.width = _fnStringToCss( tableWidthAttr );
		}
	
		if ( (tableWidthAttr || scrollX) && ! oSettings._reszEvt ) {
			var bindResize = function () {
				$(window).on('resize.DT-'+oSettings.sInstance, _fnThrottle( function () {
					_fnAdjustColumnSizing( oSettings );
				} ) );
			};
	
			// IE6/7 will crash if we bind a resize event handler on page load.
			// To be removed in 1.11 which drops IE6/7 support
			if ( ie67 ) {
				setTimeout( bindResize, 1000 );
			}
			else {
				bindResize();
			}
	
			oSettings._reszEvt = true;
		}
	}
	
	
	/**
	 * Throttle the calls to a function. Arguments and context are maintained for
	 * the throttled function
	 *  @param {function} fn Function to be called
	 *  @param {int} [freq=200] call frequency in mS
	 *  @returns {function} wrapped function
	 *  @memberof DataTable#oApi
	 */
	var _fnThrottle = DataTable.util.throttle;
	
	
	/**
	 * Convert a CSS unit width to pixels (e.g. 2em)
	 *  @param {string} width width to be converted
	 *  @param {node} parent parent to get the with for (required for relative widths) - optional
	 *  @returns {int} width in pixels
	 *  @memberof DataTable#oApi
	 */
	function _fnConvertToWidth ( width, parent )
	{
		if ( ! width ) {
			return 0;
		}
	
		var n = $('<div/>')
			.css( 'width', _fnStringToCss( width ) )
			.appendTo( parent || document.body );
	
		var val = n[0].offsetWidth;
		n.remove();
	
		return val;
	}
	
	
	/**
	 * Get the widest node
	 *  @param {object} settings dataTables settings object
	 *  @param {int} colIdx column of interest
	 *  @returns {node} widest table node
	 *  @memberof DataTable#oApi
	 */
	function _fnGetWidestNode( settings, colIdx )
	{
		var idx = _fnGetMaxLenString( settings, colIdx );
		if ( idx < 0 ) {
			return null;
		}
	
		var data = settings.aoData[ idx ];
		return ! data.nTr ? // Might not have been created when deferred rendering
			$('<td/>').html( _fnGetCellData( settings, idx, colIdx, 'display' ) )[0] :
			data.anCells[ colIdx ];
	}
	
	
	/**
	 * Get the maximum strlen for each data column
	 *  @param {object} settings dataTables settings object
	 *  @param {int} colIdx column of interest
	 *  @returns {string} max string length for each column
	 *  @memberof DataTable#oApi
	 */
	function _fnGetMaxLenString( settings, colIdx )
	{
		var s, max=-1, maxIdx = -1;
	
		for ( var i=0, ien=settings.aoData.length ; i<ien ; i++ ) {
			s = _fnGetCellData( settings, i, colIdx, 'display' )+'';
			s = s.replace( __re_html_remove, '' );
			s = s.replace( /&nbsp;/g, ' ' );
	
			if ( s.length > max ) {
				max = s.length;
				maxIdx = i;
			}
		}
	
		return maxIdx;
	}
	
	
	/**
	 * Append a CSS unit (only if required) to a string
	 *  @param {string} value to css-ify
	 *  @returns {string} value with css unit
	 *  @memberof DataTable#oApi
	 */
	function _fnStringToCss( s )
	{
		if ( s === null ) {
			return '0px';
		}
	
		if ( typeof s == 'number' ) {
			return s < 0 ?
				'0px' :
				s+'px';
		}
	
		// Check it has a unit character already
		return s.match(/\d$/) ?
			s+'px' :
			s;
	}
	
	
	
	function _fnSortFlatten ( settings )
	{
		var
			i, iLen, k, kLen,
			aSort = [],
			aiOrig = [],
			aoColumns = settings.aoColumns,
			aDataSort, iCol, sType, srcCol,
			fixed = settings.aaSortingFixed,
			fixedObj = $.isPlainObject( fixed ),
			nestedSort = [],
			add = function ( a ) {
				if ( a.length && ! $.isArray( a[0] ) ) {
					// 1D array
					nestedSort.push( a );
				}
				else {
					// 2D array
					$.merge( nestedSort, a );
				}
			};
	
		// Build the sort array, with pre-fix and post-fix options if they have been
		// specified
		if ( $.isArray( fixed ) ) {
			add( fixed );
		}
	
		if ( fixedObj && fixed.pre ) {
			add( fixed.pre );
		}
	
		add( settings.aaSorting );
	
		if (fixedObj && fixed.post ) {
			add( fixed.post );
		}
	
		for ( i=0 ; i<nestedSort.length ; i++ )
		{
			srcCol = nestedSort[i][0];
			aDataSort = aoColumns[ srcCol ].aDataSort;
	
			for ( k=0, kLen=aDataSort.length ; k<kLen ; k++ )
			{
				iCol = aDataSort[k];
				sType = aoColumns[ iCol ].sType || 'string';
	
				if ( nestedSort[i]._idx === undefined ) {
					nestedSort[i]._idx = $.inArray( nestedSort[i][1], aoColumns[iCol].asSorting );
				}
	
				aSort.push( {
					src:       srcCol,
					col:       iCol,
					dir:       nestedSort[i][1],
					index:     nestedSort[i]._idx,
					type:      sType,
					formatter: DataTable.ext.type.order[ sType+"-pre" ]
				} );
			}
		}
	
		return aSort;
	}
	
	/**
	 * Change the order of the table
	 *  @param {object} oSettings dataTables settings object
	 *  @memberof DataTable#oApi
	 *  @todo This really needs split up!
	 */
	function _fnSort ( oSettings )
	{
		var
			i, ien, iLen, j, jLen, k, kLen,
			sDataType, nTh,
			aiOrig = [],
			oExtSort = DataTable.ext.type.order,
			aoData = oSettings.aoData,
			aoColumns = oSettings.aoColumns,
			aDataSort, data, iCol, sType, oSort,
			formatters = 0,
			sortCol,
			displayMaster = oSettings.aiDisplayMaster,
			aSort;
	
		// Resolve any column types that are unknown due to addition or invalidation
		// @todo Can this be moved into a 'data-ready' handler which is called when
		//   data is going to be used in the table?
		_fnColumnTypes( oSettings );
	
		aSort = _fnSortFlatten( oSettings );
	
		for ( i=0, ien=aSort.length ; i<ien ; i++ ) {
			sortCol = aSort[i];
	
			// Track if we can use the fast sort algorithm
			if ( sortCol.formatter ) {
				formatters++;
			}
	
			// Load the data needed for the sort, for each cell
			_fnSortData( oSettings, sortCol.col );
		}
	
		/* No sorting required if server-side or no sorting array */
		if ( _fnDataSource( oSettings ) != 'ssp' && aSort.length !== 0 )
		{
			// Create a value - key array of the current row positions such that we can use their
			// current position during the sort, if values match, in order to perform stable sorting
			for ( i=0, iLen=displayMaster.length ; i<iLen ; i++ ) {
				aiOrig[ displayMaster[i] ] = i;
			}
	
			/* Do the sort - here we want multi-column sorting based on a given data source (column)
			 * and sorting function (from oSort) in a certain direction. It's reasonably complex to
			 * follow on it's own, but this is what we want (example two column sorting):
			 *  fnLocalSorting = function(a,b){
			 *    var iTest;
			 *    iTest = oSort['string-asc']('data11', 'data12');
			 *      if (iTest !== 0)
			 *        return iTest;
			 *    iTest = oSort['numeric-desc']('data21', 'data22');
			 *    if (iTest !== 0)
			 *      return iTest;
			 *    return oSort['numeric-asc']( aiOrig[a], aiOrig[b] );
			 *  }
			 * Basically we have a test for each sorting column, if the data in that column is equal,
			 * test the next column. If all columns match, then we use a numeric sort on the row
			 * positions in the original data array to provide a stable sort.
			 *
			 * Note - I know it seems excessive to have two sorting methods, but the first is around
			 * 15% faster, so the second is only maintained for backwards compatibility with sorting
			 * methods which do not have a pre-sort formatting function.
			 */
			if ( formatters === aSort.length ) {
				// All sort types have formatting functions
				displayMaster.sort( function ( a, b ) {
					var
						x, y, k, test, sort,
						len=aSort.length,
						dataA = aoData[a]._aSortData,
						dataB = aoData[b]._aSortData;
	
					for ( k=0 ; k<len ; k++ ) {
						sort = aSort[k];
	
						x = dataA[ sort.col ];
						y = dataB[ sort.col ];
	
						test = x<y ? -1 : x>y ? 1 : 0;
						if ( test !== 0 ) {
							return sort.dir === 'asc' ? test : -test;
						}
					}
	
					x = aiOrig[a];
					y = aiOrig[b];
					return x<y ? -1 : x>y ? 1 : 0;
				} );
			}
			else {
				// Depreciated - remove in 1.11 (providing a plug-in option)
				// Not all sort types have formatting methods, so we have to call their sorting
				// methods.
				displayMaster.sort( function ( a, b ) {
					var
						x, y, k, l, test, sort, fn,
						len=aSort.length,
						dataA = aoData[a]._aSortData,
						dataB = aoData[b]._aSortData;
	
					for ( k=0 ; k<len ; k++ ) {
						sort = aSort[k];
	
						x = dataA[ sort.col ];
						y = dataB[ sort.col ];
	
						fn = oExtSort[ sort.type+"-"+sort.dir ] || oExtSort[ "string-"+sort.dir ];
						test = fn( x, y );
						if ( test !== 0 ) {
							return test;
						}
					}
	
					x = aiOrig[a];
					y = aiOrig[b];
					return x<y ? -1 : x>y ? 1 : 0;
				} );
			}
		}
	
		/* Tell the draw function that we have sorted the data */
		oSettings.bSorted = true;
	}
	
	
	function _fnSortAria ( settings )
	{
		var label;
		var nextSort;
		var columns = settings.aoColumns;
		var aSort = _fnSortFlatten( settings );
		var oAria = settings.oLanguage.oAria;
	
		// ARIA attributes - need to loop all columns, to update all (removing old
		// attributes as needed)
		for ( var i=0, iLen=columns.length ; i<iLen ; i++ )
		{
			var col = columns[i];
			var asSorting = col.asSorting;
			var sTitle = col.sTitle.replace( /<.*?>/g, "" );
			var th = col.nTh;
	
			// IE7 is throwing an error when setting these properties with jQuery's
			// attr() and removeAttr() methods...
			th.removeAttribute('aria-sort');
	
			/* In ARIA only the first sorting column can be marked as sorting - no multi-sort option */
			if ( col.bSortable ) {
				if ( aSort.length > 0 && aSort[0].col == i ) {
					th.setAttribute('aria-sort', aSort[0].dir=="asc" ? "ascending" : "descending" );
					nextSort = asSorting[ aSort[0].index+1 ] || asSorting[0];
				}
				else {
					nextSort = asSorting[0];
				}
	
				label = sTitle + ( nextSort === "asc" ?
					oAria.sSortAscending :
					oAria.sSortDescending
				);
			}
			else {
				label = sTitle;
			}
	
			th.setAttribute('aria-label', label);
		}
	}
	
	
	/**
	 * Function to run on user sort request
	 *  @param {object} settings dataTables settings object
	 *  @param {node} attachTo node to attach the handler to
	 *  @param {int} colIdx column sorting index
	 *  @param {boolean} [append=false] Append the requested sort to the existing
	 *    sort if true (i.e. multi-column sort)
	 *  @param {function} [callback] callback function
	 *  @memberof DataTable#oApi
	 */
	function _fnSortListener ( settings, colIdx, append, callback )
	{
		var col = settings.aoColumns[ colIdx ];
		var sorting = settings.aaSorting;
		var asSorting = col.asSorting;
		var nextSortIdx;
		var next = function ( a, overflow ) {
			var idx = a._idx;
			if ( idx === undefined ) {
				idx = $.inArray( a[1], asSorting );
			}
	
			return idx+1 < asSorting.length ?
				idx+1 :
				overflow ?
					null :
					0;
		};
	
		// Convert to 2D array if needed
		if ( typeof sorting[0] === 'number' ) {
			sorting = settings.aaSorting = [ sorting ];
		}
	
		// If appending the sort then we are multi-column sorting
		if ( append && settings.oFeatures.bSortMulti ) {
			// Are we already doing some kind of sort on this column?
			var sortIdx = $.inArray( colIdx, _pluck(sorting, '0') );
	
			if ( sortIdx !== -1 ) {
				// Yes, modify the sort
				nextSortIdx = next( sorting[sortIdx], true );
	
				if ( nextSortIdx === null && sorting.length === 1 ) {
					nextSortIdx = 0; // can't remove sorting completely
				}
	
				if ( nextSortIdx === null ) {
					sorting.splice( sortIdx, 1 );
				}
				else {
					sorting[sortIdx][1] = asSorting[ nextSortIdx ];
					sorting[sortIdx]._idx = nextSortIdx;
				}
			}
			else {
				// No sort on this column yet
				sorting.push( [ colIdx, asSorting[0], 0 ] );
				sorting[sorting.length-1]._idx = 0;
			}
		}
		else if ( sorting.length && sorting[0][0] == colIdx ) {
			// Single column - already sorting on this column, modify the sort
			nextSortIdx = next( sorting[0] );
	
			sorting.length = 1;
			sorting[0][1] = asSorting[ nextSortIdx ];
			sorting[0]._idx = nextSortIdx;
		}
		else {
			// Single column - sort only on this column
			sorting.length = 0;
			sorting.push( [ colIdx, asSorting[0] ] );
			sorting[0]._idx = 0;
		}
	
		// Run the sort by calling a full redraw
		_fnReDraw( settings );
	
		// callback used for async user interaction
		if ( typeof callback == 'function' ) {
			callback( settings );
		}
	}
	
	
	/**
	 * Attach a sort handler (click) to a node
	 *  @param {object} settings dataTables settings object
	 *  @param {node} attachTo node to attach the handler to
	 *  @param {int} colIdx column sorting index
	 *  @param {function} [callback] callback function
	 *  @memberof DataTable#oApi
	 */
	function _fnSortAttachListener ( settings, attachTo, colIdx, callback )
	{
		var col = settings.aoColumns[ colIdx ];
	
		_fnBindAction( attachTo, {}, function (e) {
			/* If the column is not sortable - don't to anything */
			if ( col.bSortable === false ) {
				return;
			}
	
			// If processing is enabled use a timeout to allow the processing
			// display to be shown - otherwise to it synchronously
			if ( settings.oFeatures.bProcessing ) {
				_fnProcessingDisplay( settings, true );
	
				setTimeout( function() {
					_fnSortListener( settings, colIdx, e.shiftKey, callback );
	
					// In server-side processing, the draw callback will remove the
					// processing display
					if ( _fnDataSource( settings ) !== 'ssp' ) {
						_fnProcessingDisplay( settings, false );
					}
				}, 0 );
			}
			else {
				_fnSortListener( settings, colIdx, e.shiftKey, callback );
			}
		} );
	}
	
	
	/**
	 * Set the sorting classes on table's body, Note: it is safe to call this function
	 * when bSort and bSortClasses are false
	 *  @param {object} oSettings dataTables settings object
	 *  @memberof DataTable#oApi
	 */
	function _fnSortingClasses( settings )
	{
		var oldSort = settings.aLastSort;
		var sortClass = settings.oClasses.sSortColumn;
		var sort = _fnSortFlatten( settings );
		var features = settings.oFeatures;
		var i, ien, colIdx;
	
		if ( features.bSort && features.bSortClasses ) {
			// Remove old sorting classes
			for ( i=0, ien=oldSort.length ; i<ien ; i++ ) {
				colIdx = oldSort[i].src;
	
				// Remove column sorting
				$( _pluck( settings.aoData, 'anCells', colIdx ) )
					.removeClass( sortClass + (i<2 ? i+1 : 3) );
			}
	
			// Add new column sorting
			for ( i=0, ien=sort.length ; i<ien ; i++ ) {
				colIdx = sort[i].src;
	
				$( _pluck( settings.aoData, 'anCells', colIdx ) )
					.addClass( sortClass + (i<2 ? i+1 : 3) );
			}
		}
	
		settings.aLastSort = sort;
	}
	
	
	// Get the data to sort a column, be it from cache, fresh (populating the
	// cache), or from a sort formatter
	function _fnSortData( settings, idx )
	{
		// Custom sorting function - provided by the sort data type
		var column = settings.aoColumns[ idx ];
		var customSort = DataTable.ext.order[ column.sSortDataType ];
		var customData;
	
		if ( customSort ) {
			customData = customSort.call( settings.oInstance, settings, idx,
				_fnColumnIndexToVisible( settings, idx )
			);
		}
	
		// Use / populate cache
		var row, cellData;
		var formatter = DataTable.ext.type.order[ column.sType+"-pre" ];
	
		for ( var i=0, ien=settings.aoData.length ; i<ien ; i++ ) {
			row = settings.aoData[i];
	
			if ( ! row._aSortData ) {
				row._aSortData = [];
			}
	
			if ( ! row._aSortData[idx] || customSort ) {
				cellData = customSort ?
					customData[i] : // If there was a custom sort function, use data from there
					_fnGetCellData( settings, i, idx, 'sort' );
	
				row._aSortData[ idx ] = formatter ?
					formatter( cellData ) :
					cellData;
			}
		}
	}
	
	
	
	/**
	 * Save the state of a table
	 *  @param {object} oSettings dataTables settings object
	 *  @memberof DataTable#oApi
	 */
	function _fnSaveState ( settings )
	{
		if ( !settings.oFeatures.bStateSave || settings.bDestroying )
		{
			return;
		}
	
		/* Store the interesting variables */
		var state = {
			time:    +new Date(),
			start:   settings._iDisplayStart,
			length:  settings._iDisplayLength,
			order:   $.extend( true, [], settings.aaSorting ),
			search:  _fnSearchToCamel( settings.oPreviousSearch ),
			columns: $.map( settings.aoColumns, function ( col, i ) {
				return {
					visible: col.bVisible,
					search: _fnSearchToCamel( settings.aoPreSearchCols[i] )
				};
			} )
		};
	
		_fnCallbackFire( settings, "aoStateSaveParams", 'stateSaveParams', [settings, state] );
	
		settings.oSavedState = state;
		settings.fnStateSaveCallback.call( settings.oInstance, settings, state );
	}
	
	
	/**
	 * Attempt to load a saved table state
	 *  @param {object} oSettings dataTables settings object
	 *  @param {object} oInit DataTables init object so we can override settings
	 *  @param {function} callback Callback to execute when the state has been loaded
	 *  @memberof DataTable#oApi
	 */
	function _fnLoadState ( settings, oInit, callback )
	{
		var i, ien;
		var columns = settings.aoColumns;
		var loaded = function ( s ) {
			if ( ! s || ! s.time ) {
				callback();
				return;
			}
	
			// Allow custom and plug-in manipulation functions to alter the saved data set and
			// cancelling of loading by returning false
			var abStateLoad = _fnCallbackFire( settings, 'aoStateLoadParams', 'stateLoadParams', [settings, s] );
			if ( $.inArray( false, abStateLoad ) !== -1 ) {
				callback();
				return;
			}
	
			// Reject old data
			var duration = settings.iStateDuration;
			if ( duration > 0 && s.time < +new Date() - (duration*1000) ) {
				callback();
				return;
			}
	
			// Number of columns have changed - all bets are off, no restore of settings
			if ( s.columns && columns.length !== s.columns.length ) {
				callback();
				return;
			}
	
			// Store the saved state so it might be accessed at any time
			settings.oLoadedState = $.extend( true, {}, s );
	
			// Restore key features - todo - for 1.11 this needs to be done by
			// subscribed events
			if ( s.start !== undefined ) {
				settings._iDisplayStart    = s.start;
				settings.iInitDisplayStart = s.start;
			}
			if ( s.length !== undefined ) {
				settings._iDisplayLength   = s.length;
			}
	
			// Order
			if ( s.order !== undefined ) {
				settings.aaSorting = [];
				$.each( s.order, function ( i, col ) {
					settings.aaSorting.push( col[0] >= columns.length ?
						[ 0, col[1] ] :
						col
					);
				} );
			}
	
			// Search
			if ( s.search !== undefined ) {
				$.extend( settings.oPreviousSearch, _fnSearchToHung( s.search ) );
			}
	
			// Columns
			//
			if ( s.columns ) {
				for ( i=0, ien=s.columns.length ; i<ien ; i++ ) {
					var col = s.columns[i];
	
					// Visibility
					if ( col.visible !== undefined ) {
						columns[i].bVisible = col.visible;
					}
	
					// Search
					if ( col.search !== undefined ) {
						$.extend( settings.aoPreSearchCols[i], _fnSearchToHung( col.search ) );
					}
				}
			}
	
			_fnCallbackFire( settings, 'aoStateLoaded', 'stateLoaded', [settings, s] );
			callback();
		}
	
		if ( ! settings.oFeatures.bStateSave ) {
			callback();
			return;
		}
	
		var state = settings.fnStateLoadCallback.call( settings.oInstance, settings, loaded );
	
		if ( state !== undefined ) {
			loaded( state );
		}
		// otherwise, wait for the loaded callback to be executed
	}
	
	
	/**
	 * Return the settings object for a particular table
	 *  @param {node} table table we are using as a dataTable
	 *  @returns {object} Settings object - or null if not found
	 *  @memberof DataTable#oApi
	 */
	function _fnSettingsFromNode ( table )
	{
		var settings = DataTable.settings;
		var idx = $.inArray( table, _pluck( settings, 'nTable' ) );
	
		return idx !== -1 ?
			settings[ idx ] :
			null;
	}
	
	
	/**
	 * Log an error message
	 *  @param {object} settings dataTables settings object
	 *  @param {int} level log error messages, or display them to the user
	 *  @param {string} msg error message
	 *  @param {int} tn Technical note id to get more information about the error.
	 *  @memberof DataTable#oApi
	 */
	function _fnLog( settings, level, msg, tn )
	{
		msg = 'DataTables warning: '+
			(settings ? 'table id='+settings.sTableId+' - ' : '')+msg;
	
		if ( tn ) {
			msg += '. For more information about this error, please see '+
			'http://datatables.net/tn/'+tn;
		}
		
		//Para los tipo 4, cuando es por row indefinidas se muestra solo el log.
		if(tn === 4){
			level = true;
		}
	
		if ( ! level  ) {
			// Backwards compatibility pre 1.10
			var ext = DataTable.ext;
			var type = ext.sErrMode || ext.errMode;
	
			if ( settings ) {
				_fnCallbackFire( settings, null, 'error', [ settings, tn, msg ] );
			}
	
			if ( type == 'alert' ) {
				alert( msg );
			}
			else if ( type == 'throw' ) {
				throw new Error(msg);
			}
			else if ( typeof type == 'function' ) {
				type( settings, tn, msg );
			}
		}
		else if ( window.console && console.log ) {
			console.log( msg );
		}
	}
	
	
	/**
	 * See if a property is defined on one object, if so assign it to the other object
	 *  @param {object} ret target object
	 *  @param {object} src source object
	 *  @param {string} name property
	 *  @param {string} [mappedName] name to map too - optional, name used if not given
	 *  @memberof DataTable#oApi
	 */
	function _fnMap( ret, src, name, mappedName )
	{
		if ( $.isArray( name ) ) {
			$.each( name, function (i, val) {
				if ( $.isArray( val ) ) {
					_fnMap( ret, src, val[0], val[1] );
				}
				else {
					_fnMap( ret, src, val );
				}
			} );
	
			return;
		}
	
		if ( mappedName === undefined ) {
			mappedName = name;
		}
	
		if ( src[name] !== undefined ) {
			ret[mappedName] = src[name];
		}
	}
	
	
	/**
	 * Extend objects - very similar to jQuery.extend, but deep copy objects, and
	 * shallow copy arrays. The reason we need to do this, is that we don't want to
	 * deep copy array init values (such as aaSorting) since the dev wouldn't be
	 * able to override them, but we do want to deep copy arrays.
	 *  @param {object} out Object to extend
	 *  @param {object} extender Object from which the properties will be applied to
	 *      out
	 *  @param {boolean} breakRefs If true, then arrays will be sliced to take an
	 *      independent copy with the exception of the `data` or `aaData` parameters
	 *      if they are present. This is so you can pass in a collection to
	 *      DataTables and have that used as your data source without breaking the
	 *      references
	 *  @returns {object} out Reference, just for convenience - out === the return.
	 *  @memberof DataTable#oApi
	 *  @todo This doesn't take account of arrays inside the deep copied objects.
	 */
	function _fnExtend( out, extender, breakRefs )
	{
		var val;
	
		for ( var prop in extender ) {
			if ( extender.hasOwnProperty(prop) ) {
				val = extender[prop];
	
				if ( $.isPlainObject( val ) ) {
					if ( ! $.isPlainObject( out[prop] ) ) {
						out[prop] = {};
					}
					$.extend( true, out[prop], val );
				}
				else if ( breakRefs && prop !== 'data' && prop !== 'aaData' && $.isArray(val) ) {
					out[prop] = val.slice();
				}
				else {
					out[prop] = val;
				}
			}
		}
	
		return out;
	}
	
	
	/**
	 * Bind an event handers to allow a click or return key to activate the callback.
	 * This is good for accessibility since a return on the keyboard will have the
	 * same effect as a click, if the element has focus.
	 *  @param {element} n Element to bind the action to
	 *  @param {object} oData Data object to pass to the triggered function
	 *  @param {function} fn Callback function for when the event is triggered
	 *  @memberof DataTable#oApi
	 */
	function _fnBindAction( n, oData, fn )
	{
		$(n)
			.on( 'click.DT', oData, function (e) {
					n.blur(); // Remove focus outline for mouse users
					fn(e);
				} )
			.on( 'keypress.DT', oData, function (e){
					if ( e.which === 13 ) {
						e.preventDefault();
						fn(e);
					}
				} )
			.on( 'selectstart.DT', function () {
					/* Take the brutal approach to cancelling text selection */
					return false;
				} );
	}
	
	
	/**
	 * Register a callback function. Easily allows a callback function to be added to
	 * an array store of callback functions that can then all be called together.
	 *  @param {object} oSettings dataTables settings object
	 *  @param {string} sStore Name of the array storage for the callbacks in oSettings
	 *  @param {function} fn Function to be called back
	 *  @param {string} sName Identifying name for the callback (i.e. a label)
	 *  @memberof DataTable#oApi
	 */
	function _fnCallbackReg( oSettings, sStore, fn, sName )
	{
		if ( fn )
		{
			oSettings[sStore].push( {
				"fn": fn,
				"sName": sName
			} );
		}
	}
	
	
	/**
	 * Fire callback functions and trigger events. Note that the loop over the
	 * callback array store is done backwards! Further note that you do not want to
	 * fire off triggers in time sensitive applications (for example cell creation)
	 * as its slow.
	 *  @param {object} settings dataTables settings object
	 *  @param {string} callbackArr Name of the array storage for the callbacks in
	 *      oSettings
	 *  @param {string} eventName Name of the jQuery custom event to trigger. If
	 *      null no trigger is fired
	 *  @param {array} args Array of arguments to pass to the callback function /
	 *      trigger
	 *  @memberof DataTable#oApi
	 */
	function _fnCallbackFire( settings, callbackArr, eventName, args )
	{
		var ret = [];
	
		if ( callbackArr ) {
			ret = $.map( settings[callbackArr].slice().reverse(), function (val, i) {
				return val.fn.apply( settings.oInstance, args );
			} );
		}
	
		if ( eventName !== null ) {
			var e = $.Event( eventName+'.dt' );
	
			$(settings.nTable).trigger( e, args );
	
			ret.push( e.result );
		}
	
		return ret;
	}
	
	
	function _fnLengthOverflow ( settings )
	{
		var
			start = settings._iDisplayStart,
			end = settings.fnDisplayEnd(),
			len = settings._iDisplayLength;
	
		/* If we have space to show extra rows (backing up from the end point - then do so */
		if ( start >= end )
		{
			start = end - len;
		}
	
		// Keep the start record on the current page
		start -= (start % len);
	
		if ( len === -1 || start < 0 )
		{
			start = 0;
		}
	
		settings._iDisplayStart = start;
	}
	
	
	function _fnRenderer( settings, type )
	{
		var renderer = settings.renderer;
		var host = DataTable.ext.renderer[type];
	
		if ( $.isPlainObject( renderer ) && renderer[type] ) {
			// Specific renderer for this type. If available use it, otherwise use
			// the default.
			return host[renderer[type]] || host._;
		}
		else if ( typeof renderer === 'string' ) {
			// Common renderer - if there is one available for this type use it,
			// otherwise use the default
			return host[renderer] || host._;
		}
	
		// Use the default
		return host._;
	}
	
	
	/**
	 * Detect the data source being used for the table. Used to simplify the code
	 * a little (ajax) and to make it compress a little smaller.
	 *
	 *  @param {object} settings dataTables settings object
	 *  @returns {string} Data source
	 *  @memberof DataTable#oApi
	 */
	function _fnDataSource ( settings )
	{
		if ( settings.oFeatures.bServerSide ) {
			return 'ssp';
		}
		else if ( settings.ajax || settings.sAjaxSource ) {
			return 'ajax';
		}
		return 'dom';
	}
	

	
	
	/**
	 * Computed structure of the DataTables API, defined by the options passed to
	 * `DataTable.Api.register()` when building the API.
	 *
	 * The structure is built in order to speed creation and extension of the Api
	 * objects since the extensions are effectively pre-parsed.
	 *
	 * The array is an array of objects with the following structure, where this
	 * base array represents the Api prototype base:
	 *
	 *     [
	 *       {
	 *         name:      'data'                -- string   - Property name
	 *         val:       function () {},       -- function - Api method (or undefined if just an object
	 *         methodExt: [ ... ],              -- array    - Array of Api object definitions to extend the method result
	 *         propExt:   [ ... ]               -- array    - Array of Api object definitions to extend the property
	 *       },
	 *       {
	 *         name:     'row'
	 *         val:       {},
	 *         methodExt: [ ... ],
	 *         propExt:   [
	 *           {
	 *             name:      'data'
	 *             val:       function () {},
	 *             methodExt: [ ... ],
	 *             propExt:   [ ... ]
	 *           },
	 *           ...
	 *         ]
	 *       }
	 *     ]
	 *
	 * @type {Array}
	 * @ignore
	 */
	var __apiStruct = [];
	
	
	/**
	 * `Array.prototype` reference.
	 *
	 * @type object
	 * @ignore
	 */
	var __arrayProto = Array.prototype;
	
	
	/**
	 * Abstraction for `context` parameter of the `Api` constructor to allow it to
	 * take several different forms for ease of use.
	 *
	 * Each of the input parameter types will be converted to a DataTables settings
	 * object where possible.
	 *
	 * @param  {string|node|jQuery|object} mixed DataTable identifier. Can be one
	 *   of:
	 *
	 *   * `string` - jQuery selector. Any DataTables' matching the given selector
	 *     with be found and used.
	 *   * `node` - `TABLE` node which has already been formed into a DataTable.
	 *   * `jQuery` - A jQuery object of `TABLE` nodes.
	 *   * `object` - DataTables settings object
	 *   * `DataTables.Api` - API instance
	 * @return {array|null} Matching DataTables settings objects. `null` or
	 *   `undefined` is returned if no matching DataTable is found.
	 * @ignore
	 */
	var _toSettings = function ( mixed )
	{
		var idx, jq;
		var settings = DataTable.settings;
		var tables = $.map( settings, function (el, i) {
			return el.nTable;
		} );
	
		if ( ! mixed ) {
			return [];
		}
		else if ( mixed.nTable && mixed.oApi ) {
			// DataTables settings object
			return [ mixed ];
		}
		else if ( mixed.nodeName && mixed.nodeName.toLowerCase() === 'table' ) {
			// Table node
			idx = $.inArray( mixed, tables );
			return idx !== -1 ? [ settings[idx] ] : null;
		}
		else if ( mixed && typeof mixed.settings === 'function' ) {
			return mixed.settings().toArray();
		}
		else if ( typeof mixed === 'string' ) {
			// jQuery selector
			jq = $(mixed);
		}
		else if ( mixed instanceof $ ) {
			// jQuery object (also DataTables instance)
			jq = mixed;
		}
	
		if ( jq ) {
			return jq.map( function(i) {
				idx = $.inArray( this, tables );
				return idx !== -1 ? settings[idx] : null;
			} ).toArray();
		}
	};
	
	
	/**
	 * DataTables API class - used to control and interface with  one or more
	 * DataTables enhanced tables.
	 *
	 * The API class is heavily based on jQuery, presenting a chainable interface
	 * that you can use to interact with tables. Each instance of the API class has
	 * a "context" - i.e. the tables that it will operate on. This could be a single
	 * table, all tables on a page or a sub-set thereof.
	 *
	 * Additionally the API is designed to allow you to easily work with the data in
	 * the tables, retrieving and manipulating it as required. This is done by
	 * presenting the API class as an array like interface. The contents of the
	 * array depend upon the actions requested by each method (for example
	 * `rows().nodes()` will return an array of nodes, while `rows().data()` will
	 * return an array of objects or arrays depending upon your table's
	 * configuration). The API object has a number of array like methods (`push`,
	 * `pop`, `reverse` etc) as well as additional helper methods (`each`, `pluck`,
	 * `unique` etc) to assist your working with the data held in a table.
	 *
	 * Most methods (those which return an Api instance) are chainable, which means
	 * the return from a method call also has all of the methods available that the
	 * top level object had. For example, these two calls are equivalent:
	 *
	 *     // Not chained
	 *     api.row.add( {...} );
	 *     api.draw();
	 *
	 *     // Chained
	 *     api.row.add( {...} ).draw();
	 *
	 * @class DataTable.Api
	 * @param {array|object|string|jQuery} context DataTable identifier. This is
	 *   used to define which DataTables enhanced tables this API will operate on.
	 *   Can be one of:
	 *
	 *   * `string` - jQuery selector. Any DataTables' matching the given selector
	 *     with be found and used.
	 *   * `node` - `TABLE` node which has already been formed into a DataTable.
	 *   * `jQuery` - A jQuery object of `TABLE` nodes.
	 *   * `object` - DataTables settings object
	 * @param {array} [data] Data to initialise the Api instance with.
	 *
	 * @example
	 *   // Direct initialisation during DataTables construction
	 *   var api = $('#example').DataTable();
	 *
	 * @example
	 *   // Initialisation using a DataTables jQuery object
	 *   var api = $('#example').dataTable().api();
	 *
	 * @example
	 *   // Initialisation as a constructor
	 *   var api = new $.fn.DataTable.Api( 'table.dataTable' );
	 */
	_Api = function ( context, data )
	{
		if ( ! (this instanceof _Api) ) {
			return new _Api( context, data );
		}
	
		var settings = [];
		var ctxSettings = function ( o ) {
			var a = _toSettings( o );
			if ( a ) {
				settings = settings.concat( a );
			}
		};
	
		if ( $.isArray( context ) ) {
			for ( var i=0, ien=context.length ; i<ien ; i++ ) {
				ctxSettings( context[i] );
			}
		}
		else {
			ctxSettings( context );
		}
	
		// Remove duplicates
		this.context = _unique( settings );
	
		// Initial data
		if ( data ) {
			$.merge( this, data );
		}
	
		// selector
		this.selector = {
			rows: null,
			cols: null,
			opts: null
		};
	
		_Api.extend( this, this, __apiStruct );
	};
	
	DataTable.Api = _Api;
	
	// Don't destroy the existing prototype, just extend it. Required for jQuery 2's
	// isPlainObject.
	$.extend( _Api.prototype, {
		any: function ()
		{
			return this.count() !== 0;
		},
	
	
		concat:  __arrayProto.concat,
	
	
		context: [], // array of table settings objects
	
	
		count: function ()
		{
			return this.flatten().length;
		},
	
	
		each: function ( fn )
		{
			for ( var i=0, ien=this.length ; i<ien; i++ ) {
				fn.call( this, this[i], i, this );
			}
	
			return this;
		},
	
	
		eq: function ( idx )
		{
			var ctx = this.context;
	
			return ctx.length > idx ?
				new _Api( ctx[idx], this[idx] ) :
				null;
		},
	
	
		filter: function ( fn )
		{
			var a = [];
	
			if ( __arrayProto.filter ) {
				a = __arrayProto.filter.call( this, fn, this );
			}
			else {
				// Compatibility for browsers without EMCA-252-5 (JS 1.6)
				for ( var i=0, ien=this.length ; i<ien ; i++ ) {
					if ( fn.call( this, this[i], i, this ) ) {
						a.push( this[i] );
					}
				}
			}
	
			return new _Api( this.context, a );
		},
	
	
		flatten: function ()
		{
			var a = [];
			return new _Api( this.context, a.concat.apply( a, this.toArray() ) );
		},
	
	
		join:    __arrayProto.join,
	
	
		indexOf: __arrayProto.indexOf || function (obj, start)
		{
			for ( var i=(start || 0), ien=this.length ; i<ien ; i++ ) {
				if ( this[i] === obj ) {
					return i;
				}
			}
			return -1;
		},
	
		iterator: function ( flatten, type, fn, alwaysNew ) {
			var
				a = [], ret,
				i, ien, j, jen,
				context = this.context,
				rows, items, item,
				selector = this.selector;
	
			// Argument shifting
			if ( typeof flatten === 'string' ) {
				alwaysNew = fn;
				fn = type;
				type = flatten;
				flatten = false;
			}
	
			for ( i=0, ien=context.length ; i<ien ; i++ ) {
				var apiInst = new _Api( context[i] );
	
				if ( type === 'table' ) {
					ret = fn.call( apiInst, context[i], i );
	
					if ( ret !== undefined ) {
						a.push( ret );
					}
				}
				else if ( type === 'columns' || type === 'rows' ) {
					// this has same length as context - one entry for each table
					ret = fn.call( apiInst, context[i], this[i], i );
	
					if ( ret !== undefined ) {
						a.push( ret );
					}
				}
				else if ( type === 'column' || type === 'column-rows' || type === 'row' || type === 'cell' ) {
					// columns and rows share the same structure.
					// 'this' is an array of column indexes for each context
					items = this[i];
	
					if ( type === 'column-rows' ) {
						rows = _selector_row_indexes( context[i], selector.opts );
					}
	
					for ( j=0, jen=items.length ; j<jen ; j++ ) {
						item = items[j];
	
						if ( type === 'cell' ) {
							ret = fn.call( apiInst, context[i], item.row, item.column, i, j );
						}
						else {
							ret = fn.call( apiInst, context[i], item, i, j, rows );
						}
	
						if ( ret !== undefined ) {
							a.push( ret );
						}
					}
				}
			}
	
			if ( a.length || alwaysNew ) {
				var api = new _Api( context, flatten ? a.concat.apply( [], a ) : a );
				var apiSelector = api.selector;
				apiSelector.rows = selector.rows;
				apiSelector.cols = selector.cols;
				apiSelector.opts = selector.opts;
				return api;
			}
			return this;
		},
	
	
		lastIndexOf: __arrayProto.lastIndexOf || function (obj, start)
		{
			// Bit cheeky...
			return this.indexOf.apply( this.toArray.reverse(), arguments );
		},
	
	
		length:  0,
	
	
		map: function ( fn )
		{
			var a = [];
	
			if ( __arrayProto.map ) {
				a = __arrayProto.map.call( this, fn, this );
			}
			else {
				// Compatibility for browsers without EMCA-252-5 (JS 1.6)
				for ( var i=0, ien=this.length ; i<ien ; i++ ) {
					a.push( fn.call( this, this[i], i ) );
				}
			}
	
			return new _Api( this.context, a );
		},
	
	
		pluck: function ( prop )
		{
			return this.map( function ( el ) {
				return el[ prop ];
			} );
		},
	
		pop:     __arrayProto.pop,
	
	
		push:    __arrayProto.push,
	
	
		// Does not return an API instance
		reduce: __arrayProto.reduce || function ( fn, init )
		{
			return _fnReduce( this, fn, init, 0, this.length, 1 );
		},
	
	
		reduceRight: __arrayProto.reduceRight || function ( fn, init )
		{
			return _fnReduce( this, fn, init, this.length-1, -1, -1 );
		},
	
	
		reverse: __arrayProto.reverse,
	
	
		// Object with rows, columns and opts
		selector: null,
	
	
		shift:   __arrayProto.shift,
	
	
		slice: function () {
			return new _Api( this.context, this );
		},
	
	
		sort:    __arrayProto.sort, // ? name - order?
	
	
		splice:  __arrayProto.splice,
	
	
		toArray: function ()
		{
			return __arrayProto.slice.call( this );
		},
	
	
		to$: function ()
		{
			return $( this );
		},
	
	
		toJQuery: function ()
		{
			return $( this );
		},
	
	
		unique: function ()
		{
			return new _Api( this.context, _unique(this) );
		},
	
	
		unshift: __arrayProto.unshift
	} );
	
	
	_Api.extend = function ( scope, obj, ext )
	{
		// Only extend API instances and static properties of the API
		if ( ! ext.length || ! obj || ( ! (obj instanceof _Api) && ! obj.__dt_wrapper ) ) {
			return;
		}
	
		var
			i, ien,
			j, jen,
			struct, inner,
			methodScoping = function ( scope, fn, struc ) {
				return function () {
					var ret = fn.apply( scope, arguments );
	
					// Method extension
					_Api.extend( ret, ret, struc.methodExt );
					return ret;
				};
			};
	
		for ( i=0, ien=ext.length ; i<ien ; i++ ) {
			struct = ext[i];
	
			// Value
			obj[ struct.name ] = typeof struct.val === 'function' ?
				methodScoping( scope, struct.val, struct ) :
				$.isPlainObject( struct.val ) ?
					{} :
					struct.val;
	
			obj[ struct.name ].__dt_wrapper = true;
	
			// Property extension
			_Api.extend( scope, obj[ struct.name ], struct.propExt );
		}
	};
	
	
	// @todo - Is there need for an augment function?
	// _Api.augment = function ( inst, name )
	// {
	// 	// Find src object in the structure from the name
	// 	var parts = name.split('.');
	
	// 	_Api.extend( inst, obj );
	// };
	
	
	//     [
	//       {
	//         name:      'data'                -- string   - Property name
	//         val:       function () {},       -- function - Api method (or undefined if just an object
	//         methodExt: [ ... ],              -- array    - Array of Api object definitions to extend the method result
	//         propExt:   [ ... ]               -- array    - Array of Api object definitions to extend the property
	//       },
	//       {
	//         name:     'row'
	//         val:       {},
	//         methodExt: [ ... ],
	//         propExt:   [
	//           {
	//             name:      'data'
	//             val:       function () {},
	//             methodExt: [ ... ],
	//             propExt:   [ ... ]
	//           },
	//           ...
	//         ]
	//       }
	//     ]
	
	_Api.register = _api_register = function ( name, val )
	{
		if ( $.isArray( name ) ) {
			for ( var j=0, jen=name.length ; j<jen ; j++ ) {
				_Api.register( name[j], val );
			}
			return;
		}
	
		var
			i, ien,
			heir = name.split('.'),
			struct = __apiStruct,
			key, method;
	
		var find = function ( src, name ) {
			for ( var i=0, ien=src.length ; i<ien ; i++ ) {
				if ( src[i].name === name ) {
					return src[i];
				}
			}
			return null;
		};
	
		for ( i=0, ien=heir.length ; i<ien ; i++ ) {
			method = heir[i].indexOf('()') !== -1;
			key = method ?
				heir[i].replace('()', '') :
				heir[i];
	
			var src = find( struct, key );
			if ( ! src ) {
				src = {
					name:      key,
					val:       {},
					methodExt: [],
					propExt:   []
				};
				struct.push( src );
			}
	
			if ( i === ien-1 ) {
				src.val = val;
			}
			else {
				struct = method ?
					src.methodExt :
					src.propExt;
			}
		}
	};
	
	
	_Api.registerPlural = _api_registerPlural = function ( pluralName, singularName, val ) {
		_Api.register( pluralName, val );
	
		_Api.register( singularName, function () {
			var ret = val.apply( this, arguments );
	
			if ( ret === this ) {
				// Returned item is the API instance that was passed in, return it
				return this;
			}
			else if ( ret instanceof _Api ) {
				// New API instance returned, want the value from the first item
				// in the returned array for the singular result.
				return ret.length ?
					$.isArray( ret[0] ) ?
						new _Api( ret.context, ret[0] ) : // Array results are 'enhanced'
						ret[0] :
					undefined;
			}
	
			// Non-API return - just fire it back
			return ret;
		} );
	};
	
	
	/**
	 * Selector for HTML tables. Apply the given selector to the give array of
	 * DataTables settings objects.
	 *
	 * @param {string|integer} [selector] jQuery selector string or integer
	 * @param  {array} Array of DataTables settings objects to be filtered
	 * @return {array}
	 * @ignore
	 */
	var __table_selector = function ( selector, a )
	{
		// Integer is used to pick out a table by index
		if ( typeof selector === 'number' ) {
			return [ a[ selector ] ];
		}
	
		// Perform a jQuery selector on the table nodes
		var nodes = $.map( a, function (el, i) {
			return el.nTable;
		} );
	
		return $(nodes)
			.filter( selector )
			.map( function (i) {
				// Need to translate back from the table node to the settings
				var idx = $.inArray( this, nodes );
				return a[ idx ];
			} )
			.toArray();
	};
	
	
	
	/**
	 * Context selector for the API's context (i.e. the tables the API instance
	 * refers to.
	 *
	 * @name    DataTable.Api#tables
	 * @param {string|integer} [selector] Selector to pick which tables the iterator
	 *   should operate on. If not given, all tables in the current context are
	 *   used. This can be given as a jQuery selector (for example `':gt(0)'`) to
	 *   select multiple tables or as an integer to select a single table.
	 * @returns {DataTable.Api} Returns a new API instance if a selector is given.
	 */
	_api_register( 'tables()', function ( selector ) {
		// A new instance is created if there was a selector specified
		return selector ?
			new _Api( __table_selector( selector, this.context ) ) :
			this;
	} );
	
	
	_api_register( 'table()', function ( selector ) {
		var tables = this.tables( selector );
		var ctx = tables.context;
	
		// Truncate to the first matched table
		return ctx.length ?
			new _Api( ctx[0] ) :
			tables;
	} );
	
	
	_api_registerPlural( 'tables().nodes()', 'table().node()' , function () {
		return this.iterator( 'table', function ( ctx ) {
			return ctx.nTable;
		}, 1 );
	} );
	
	
	_api_registerPlural( 'tables().body()', 'table().body()' , function () {
		return this.iterator( 'table', function ( ctx ) {
			return ctx.nTBody;
		}, 1 );
	} );
	
	
	_api_registerPlural( 'tables().header()', 'table().header()' , function () {
		return this.iterator( 'table', function ( ctx ) {
			return ctx.nTHead;
		}, 1 );
	} );
	
	
	_api_registerPlural( 'tables().footer()', 'table().footer()' , function () {
		return this.iterator( 'table', function ( ctx ) {
			return ctx.nTFoot;
		}, 1 );
	} );
	
	
	_api_registerPlural( 'tables().containers()', 'table().container()' , function () {
		return this.iterator( 'table', function ( ctx ) {
			return ctx.nTableWrapper;
		}, 1 );
	} );
	
	
	
	/**
	 * Redraw the tables in the current context.
	 */
	_api_register( 'draw()', function ( paging ) {
		return this.iterator( 'table', function ( settings ) {
			if ( paging === 'page' ) {
				_fnDraw( settings );
			}
			else {
				if ( typeof paging === 'string' ) {
					paging = paging === 'full-hold' ?
						false :
						true;
				}
	
				_fnReDraw( settings, paging===false );
			}
		} );
	} );
	
	
	
	/**
	 * Get the current page index.
	 *
	 * @return {integer} Current page index (zero based)
	 *//**
	 * Set the current page.
	 *
	 * Note that if you attempt to show a page which does not exist, DataTables will
	 * not throw an error, but rather reset the paging.
	 *
	 * @param {integer|string} action The paging action to take. This can be one of:
	 *  * `integer` - The page index to jump to
	 *  * `string` - An action to take:
	 *    * `first` - Jump to first page.
	 *    * `next` - Jump to the next page
	 *    * `previous` - Jump to previous page
	 *    * `last` - Jump to the last page.
	 * @returns {DataTables.Api} this
	 */
	_api_register( 'page()', function ( action ) {
		if ( action === undefined ) {
			return this.page.info().page; // not an expensive call
		}
	
		// else, have an action to take on all tables
		return this.iterator( 'table', function ( settings ) {
			_fnPageChange( settings, action );
		} );
	} );
	
	
	/**
	 * Paging information for the first table in the current context.
	 *
	 * If you require paging information for another table, use the `table()` method
	 * with a suitable selector.
	 *
	 * @return {object} Object with the following properties set:
	 *  * `page` - Current page index (zero based - i.e. the first page is `0`)
	 *  * `pages` - Total number of pages
	 *  * `start` - Display index for the first record shown on the current page
	 *  * `end` - Display index for the last record shown on the current page
	 *  * `length` - Display length (number of records). Note that generally `start
	 *    + length = end`, but this is not always true, for example if there are
	 *    only 2 records to show on the final page, with a length of 10.
	 *  * `recordsTotal` - Full data set length
	 *  * `recordsDisplay` - Data set length once the current filtering criterion
	 *    are applied.
	 */
	_api_register( 'page.info()', function ( action ) {
		if ( this.context.length === 0 ) {
			return undefined;
		}
	
		var
			settings   = this.context[0],
			start      = settings._iDisplayStart,
			len        = settings.oFeatures.bPaginate ? settings._iDisplayLength : -1,
			visRecords = settings.fnRecordsDisplay(),
			all        = len === -1;
	
		return {
			"page":           all ? 0 : Math.floor( start / len ),
			"pages":          all ? 1 : Math.ceil( visRecords / len ),
			"start":          start,
			"end":            settings.fnDisplayEnd(),
			"length":         len,
			"recordsTotal":   settings.fnRecordsTotal(),
			"recordsDisplay": visRecords,
			"serverSide":     _fnDataSource( settings ) === 'ssp'
		};
	} );
	
	
	/**
	 * Get the current page length.
	 *
	 * @return {integer} Current page length. Note `-1` indicates that all records
	 *   are to be shown.
	 *//**
	 * Set the current page length.
	 *
	 * @param {integer} Page length to set. Use `-1` to show all records.
	 * @returns {DataTables.Api} this
	 */
	_api_register( 'page.len()', function ( len ) {
		// Note that we can't call this function 'length()' because `length`
		// is a Javascript property of functions which defines how many arguments
		// the function expects.
		if ( len === undefined ) {
			return this.context.length !== 0 ?
				this.context[0]._iDisplayLength :
				undefined;
		}
	
		// else, set the page length
		return this.iterator( 'table', function ( settings ) {
			_fnLengthChange( settings, len );
		} );
	} );
	
	
	
	var __reload = function ( settings, holdPosition, callback ) {
		// Use the draw event to trigger a callback
		if ( callback ) {
			var api = new _Api( settings );
	
			api.one( 'draw', function () {
				callback( api.ajax.json() );
			} );
		}
	
		if ( _fnDataSource( settings ) == 'ssp' ) {
			_fnReDraw( settings, holdPosition );
		}
		else {
			_fnProcessingDisplay( settings, true );
	
			// Cancel an existing request
			var xhr = settings.jqXHR;
			if ( xhr && xhr.readyState !== 4 ) {
				xhr.abort();
			}
	
			// Trigger xhr
			_fnBuildAjax( settings, [], function( json ) {
				_fnClearTable( settings );
	
				var data = _fnAjaxDataSrc( settings, json );
				for ( var i=0, ien=data.length ; i<ien ; i++ ) {
					_fnAddData( settings, data[i] );
				}
	
				_fnReDraw( settings, holdPosition );
				_fnProcessingDisplay( settings, false );
			} );
		}
	};
	
	
	/**
	 * Get the JSON response from the last Ajax request that DataTables made to the
	 * server. Note that this returns the JSON from the first table in the current
	 * context.
	 *
	 * @return {object} JSON received from the server.
	 */
	_api_register( 'ajax.json()', function () {
		var ctx = this.context;
	
		if ( ctx.length > 0 ) {
			return ctx[0].json;
		}
	
		// else return undefined;
	} );
	
	
	/**
	 * Get the data submitted in the last Ajax request
	 */
	_api_register( 'ajax.params()', function () {
		var ctx = this.context;
	
		if ( ctx.length > 0 ) {
			return ctx[0].oAjaxData;
		}
	
		// else return undefined;
	} );
	
	
	/**
	 * Reload tables from the Ajax data source. Note that this function will
	 * automatically re-draw the table when the remote data has been loaded.
	 *
	 * @param {boolean} [reset=true] Reset (default) or hold the current paging
	 *   position. A full re-sort and re-filter is performed when this method is
	 *   called, which is why the pagination reset is the default action.
	 * @returns {DataTables.Api} this
	 */
	_api_register( 'ajax.reload()', function ( callback, resetPaging ) {
		return this.iterator( 'table', function (settings) {
			__reload( settings, resetPaging===false, callback );
		} );
	} );
	
	
	/**
	 * Get the current Ajax URL. Note that this returns the URL from the first
	 * table in the current context.
	 *
	 * @return {string} Current Ajax source URL
	 *//**
	 * Set the Ajax URL. Note that this will set the URL for all tables in the
	 * current context.
	 *
	 * @param {string} url URL to set.
	 * @returns {DataTables.Api} this
	 */
	_api_register( 'ajax.url()', function ( url ) {
		var ctx = this.context;
	
		if ( url === undefined ) {
			// get
			if ( ctx.length === 0 ) {
				return undefined;
			}
			ctx = ctx[0];
	
			return ctx.ajax ?
				$.isPlainObject( ctx.ajax ) ?
					ctx.ajax.url :
					ctx.ajax :
				ctx.sAjaxSource;
		}
	
		// set
		return this.iterator( 'table', function ( settings ) {
			if ( $.isPlainObject( settings.ajax ) ) {
				settings.ajax.url = url;
			}
			else {
				settings.ajax = url;
			}
			// No need to consider sAjaxSource here since DataTables gives priority
			// to `ajax` over `sAjaxSource`. So setting `ajax` here, renders any
			// value of `sAjaxSource` redundant.
		} );
	} );
	
	
	/**
	 * Load data from the newly set Ajax URL. Note that this method is only
	 * available when `ajax.url()` is used to set a URL. Additionally, this method
	 * has the same effect as calling `ajax.reload()` but is provided for
	 * convenience when setting a new URL. Like `ajax.reload()` it will
	 * automatically redraw the table once the remote data has been loaded.
	 *
	 * @returns {DataTables.Api} this
	 */
	_api_register( 'ajax.url().load()', function ( callback, resetPaging ) {
		// Same as a reload, but makes sense to present it for easy access after a
		// url change
		return this.iterator( 'table', function ( ctx ) {
			__reload( ctx, resetPaging===false, callback );
		} );
	} );
	
	
	
	
	var _selector_run = function ( type, selector, selectFn, settings, opts )
	{
		var
			out = [], res,
			a, i, ien, j, jen,
			selectorType = typeof selector;
	
		// Can't just check for isArray here, as an API or jQuery instance might be
		// given with their array like look
		if ( ! selector || selectorType === 'string' || selectorType === 'function' || selector.length === undefined ) {
			selector = [ selector ];
		}
	
		for ( i=0, ien=selector.length ; i<ien ; i++ ) {
			// Only split on simple strings - complex expressions will be jQuery selectors
			a = selector[i] && selector[i].split && ! selector[i].match(/[\[\(:]/) ?
				selector[i].split(',') :
				[ selector[i] ];
	
			for ( j=0, jen=a.length ; j<jen ; j++ ) {
				res = selectFn( typeof a[j] === 'string' ? $.trim(a[j]) : a[j] );
	
				if ( res && res.length ) {
					out = out.concat( res );
				}
			}
		}
	
		// selector extensions
		var ext = _ext.selector[ type ];
		if ( ext.length ) {
			for ( i=0, ien=ext.length ; i<ien ; i++ ) {
				out = ext[i]( settings, opts, out );
			}
		}
	
		return _unique( out );
	};
	
	
	var _selector_opts = function ( opts )
	{
		if ( ! opts ) {
			opts = {};
		}
	
		// Backwards compatibility for 1.9- which used the terminology filter rather
		// than search
		if ( opts.filter && opts.search === undefined ) {
			opts.search = opts.filter;
		}
	
		return $.extend( {
			search: 'none',
			order: 'current',
			page: 'all'
		}, opts );
	};
	
	
	var _selector_first = function ( inst )
	{
		// Reduce the API instance to the first item found
		for ( var i=0, ien=inst.length ; i<ien ; i++ ) {
			if ( inst[i].length > 0 ) {
				// Assign the first element to the first item in the instance
				// and truncate the instance and context
				inst[0] = inst[i];
				inst[0].length = 1;
				inst.length = 1;
				inst.context = [ inst.context[i] ];
	
				return inst;
			}
		}
	
		// Not found - return an empty instance
		inst.length = 0;
		return inst;
	};
	
	
	var _selector_row_indexes = function ( settings, opts )
	{
		var
			i, ien, tmp, a=[],
			displayFiltered = settings.aiDisplay,
			displayMaster = settings.aiDisplayMaster;
	
		var
			search = opts.search,  // none, applied, removed
			order  = opts.order,   // applied, current, index (original - compatibility with 1.9)
			page   = opts.page;    // all, current
	
		if ( _fnDataSource( settings ) == 'ssp' ) {
			// In server-side processing mode, most options are irrelevant since
			// rows not shown don't exist and the index order is the applied order
			// Removed is a special case - for consistency just return an empty
			// array
			return search === 'removed' ?
				[] :
				_range( 0, displayMaster.length );
		}
		else if ( page == 'current' ) {
			// Current page implies that order=current and fitler=applied, since it is
			// fairly senseless otherwise, regardless of what order and search actually
			// are
			for ( i=settings._iDisplayStart, ien=settings.fnDisplayEnd() ; i<ien ; i++ ) {
				a.push( displayFiltered[i] );
			}
		}
		else if ( order == 'current' || order == 'applied' ) {
			a = search == 'none' ?
				displayMaster.slice() :                      // no search
				search == 'applied' ?
					displayFiltered.slice() :                // applied search
					$.map( displayMaster, function (el, i) { // removed search
						return $.inArray( el, displayFiltered ) === -1 ? el : null;
					} );
		}
		else if ( order == 'index' || order == 'original' ) {
			for ( i=0, ien=settings.aoData.length ; i<ien ; i++ ) {
				if ( search == 'none' ) {
					a.push( i );
				}
				else { // applied | removed
					tmp = $.inArray( i, displayFiltered );
	
					if ((tmp === -1 && search == 'removed') ||
						(tmp >= 0   && search == 'applied') )
					{
						a.push( i );
					}
				}
			}
		}
	
		return a;
	};
	
	
	/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
	 * Rows
	 *
	 * {}          - no selector - use all available rows
	 * {integer}   - row aoData index
	 * {node}      - TR node
	 * {string}    - jQuery selector to apply to the TR elements
	 * {array}     - jQuery array of nodes, or simply an array of TR nodes
	 *
	 */
	
	
	var __row_selector = function ( settings, selector, opts )
	{
		var rows;
		var run = function ( sel ) {
			var selInt = _intVal( sel );
			var i, ien;
	
			// Short cut - selector is a number and no options provided (default is
			// all records, so no need to check if the index is in there, since it
			// must be - dev error if the index doesn't exist).
			if ( selInt !== null && ! opts ) {
				return [ selInt ];
			}
	
			if ( ! rows ) {
				rows = _selector_row_indexes( settings, opts );
			}
	
			if ( selInt !== null && $.inArray( selInt, rows ) !== -1 ) {
				// Selector - integer
				return [ selInt ];
			}
			else if ( sel === null || sel === undefined || sel === '' ) {
				// Selector - none
				return rows;
			}
	
			// Selector - function
			if ( typeof sel === 'function' ) {
				return $.map( rows, function (idx) {
					var row = settings.aoData[ idx ];
					return sel( idx, row._aData, row.nTr ) ? idx : null;
				} );
			}
	
			// Get nodes in the order from the `rows` array with null values removed
			var nodes = _removeEmpty(
				_pluck_order( settings.aoData, rows, 'nTr' )
			);
	
			// Selector - node
			if ( sel.nodeName ) {
				if ( sel._DT_RowIndex !== undefined ) {
					return [ sel._DT_RowIndex ]; // Property added by DT for fast lookup
				}
				else if ( sel._DT_CellIndex ) {
					return [ sel._DT_CellIndex.row ];
				}
				else {
					var host = $(sel).closest('*[data-dt-row]');
					return host.length ?
						[ host.data('dt-row') ] :
						[];
				}
			}
	
			// ID selector. Want to always be able to select rows by id, regardless
			// of if the tr element has been created or not, so can't rely upon
			// jQuery here - hence a custom implementation. This does not match
			// Sizzle's fast selector or HTML4 - in HTML5 the ID can be anything,
			// but to select it using a CSS selector engine (like Sizzle or
			// querySelect) it would need to need to be escaped for some characters.
			// DataTables simplifies this for row selectors since you can select
			// only a row. A # indicates an id any anything that follows is the id -
			// unescaped.
			if ( typeof sel === 'string' && sel.charAt(0) === '#' ) {
				// get row index from id
				var rowObj = settings.aIds[ sel.replace( /^#/, '' ) ];
				if ( rowObj !== undefined ) {
					return [ rowObj.idx ];
				}
	
				// need to fall through to jQuery in case there is DOM id that
				// matches
			}
	
			// Selector - jQuery selector string, array of nodes or jQuery object/
			// As jQuery's .filter() allows jQuery objects to be passed in filter,
			// it also allows arrays, so this will cope with all three options
			return $(nodes)
				.filter( sel )
				.map( function () {
					return this._DT_RowIndex;
				} )
				.toArray();
		};
	
		return _selector_run( 'row', selector, run, settings, opts );
	};
	
	
	_api_register( 'rows()', function ( selector, opts ) {
		// argument shifting
		if ( selector === undefined ) {
			selector = '';
		}
		else if ( $.isPlainObject( selector ) ) {
			opts = selector;
			selector = '';
		}
	
		opts = _selector_opts( opts );
	
		var inst = this.iterator( 'table', function ( settings ) {
			return __row_selector( settings, selector, opts );
		}, 1 );
	
		// Want argument shifting here and in __row_selector?
		inst.selector.rows = selector;
		inst.selector.opts = opts;
	
		return inst;
	} );
	
	_api_register( 'rows().nodes()', function () {
		return this.iterator( 'row', function ( settings, row ) {
			return settings.aoData[ row ].nTr || undefined;
		}, 1 );
	} );
	
	_api_register( 'rows().data()', function () {
		return this.iterator( true, 'rows', function ( settings, rows ) {
			return _pluck_order( settings.aoData, rows, '_aData' );
		}, 1 );
	} );
	
	_api_registerPlural( 'rows().cache()', 'row().cache()', function ( type ) {
		return this.iterator( 'row', function ( settings, row ) {
			var r = settings.aoData[ row ];
			return type === 'search' ? r._aFilterData : r._aSortData;
		}, 1 );
	} );
	
	_api_registerPlural( 'rows().invalidate()', 'row().invalidate()', function ( src ) {
		return this.iterator( 'row', function ( settings, row ) {
			_fnInvalidate( settings, row, src );
		} );
	} );
	
	_api_registerPlural( 'rows().indexes()', 'row().index()', function () {
		return this.iterator( 'row', function ( settings, row ) {
			return row;
		}, 1 );
	} );
	
	_api_registerPlural( 'rows().ids()', 'row().id()', function ( hash ) {
		var a = [];
		var context = this.context;
	
		// `iterator` will drop undefined values, but in this case we want them
		for ( var i=0, ien=context.length ; i<ien ; i++ ) {
			for ( var j=0, jen=this[i].length ; j<jen ; j++ ) {
				var id = context[i].rowIdFn( context[i].aoData[ this[i][j] ]._aData );
				a.push( (hash === true ? '#' : '' )+ id );
			}
		}
	
		return new _Api( context, a );
	} );
	
	_api_registerPlural( 'rows().remove()', 'row().remove()', function () {
		var that = this;
	
		this.iterator( 'row', function ( settings, row, thatIdx ) {
			var data = settings.aoData;
			var rowData = data[ row ];
			var i, ien, j, jen;
			var loopRow, loopCells;
	
			data.splice( row, 1 );
	
			// Update the cached indexes
			for ( i=0, ien=data.length ; i<ien ; i++ ) {
				loopRow = data[i];
				loopCells = loopRow.anCells;
	
				// Rows
				if ( loopRow.nTr !== null ) {
					loopRow.nTr._DT_RowIndex = i;
				}
	
				// Cells
				if ( loopCells !== null ) {
					for ( j=0, jen=loopCells.length ; j<jen ; j++ ) {
						loopCells[j]._DT_CellIndex.row = i;
					}
				}
			}
	
			// Delete from the display arrays
			_fnDeleteIndex( settings.aiDisplayMaster, row );
			_fnDeleteIndex( settings.aiDisplay, row );
			_fnDeleteIndex( that[ thatIdx ], row, false ); // maintain local indexes
	
			// For server-side processing tables - subtract the deleted row from the count
			if ( settings._iRecordsDisplay > 0 ) {
				settings._iRecordsDisplay--;
			}
	
			// Check for an 'overflow' they case for displaying the table
			_fnLengthOverflow( settings );
	
			// Remove the row's ID reference if there is one
			var id = settings.rowIdFn( rowData._aData );
			if ( id !== undefined ) {
				delete settings.aIds[ id ];
			}
		} );
	
		this.iterator( 'table', function ( settings ) {
			for ( var i=0, ien=settings.aoData.length ; i<ien ; i++ ) {
				settings.aoData[i].idx = i;
			}
		} );
	
		return this;
	} );
	
	
	_api_register( 'rows.add()', function ( rows ) {
		var newRows = this.iterator( 'table', function ( settings ) {
				var row, i, ien;
				var out = [];
	
				for ( i=0, ien=rows.length ; i<ien ; i++ ) {
					row = rows[i];
	
					if ( row.nodeName && row.nodeName.toUpperCase() === 'TR' ) {
						out.push( _fnAddTr( settings, row )[0] );
					}
					else {
						out.push( _fnAddData( settings, row ) );
					}
				}
	
				return out;
			}, 1 );
	
		// Return an Api.rows() extended instance, so rows().nodes() etc can be used
		var modRows = this.rows( -1 );
		modRows.pop();
		$.merge( modRows, newRows );
	
		return modRows;
	} );
	
	
	
	
	
	/**
	 *
	 */
	_api_register( 'row()', function ( selector, opts ) {
		return _selector_first( this.rows( selector, opts ) );
	} );
	
	
	_api_register( 'row().data()', function ( data ) {
		var ctx = this.context;
	
		if ( data === undefined ) {
			// Get
			return ctx.length && this.length ?
				ctx[0].aoData[ this[0] ]._aData :
				undefined;
		}
	
		// Set
		ctx[0].aoData[ this[0] ]._aData = data;
	
		// Automatically invalidate
		_fnInvalidate( ctx[0], this[0], 'data' );
	
		return this;
	} );
	
	
	_api_register( 'row().node()', function () {
		var ctx = this.context;
	
		return ctx.length && this.length ?
			ctx[0].aoData[ this[0] ].nTr || null :
			null;
	} );
	
	
	_api_register( 'row.add()', function ( row ) {
		// Allow a jQuery object to be passed in - only a single row is added from
		// it though - the first element in the set
		if ( row instanceof $ && row.length ) {
			row = row[0];
		}
	
		var rows = this.iterator( 'table', function ( settings ) {
			if ( row.nodeName && row.nodeName.toUpperCase() === 'TR' ) {
				return _fnAddTr( settings, row )[0];
			}
			return _fnAddData( settings, row );
		} );
	
		// Return an Api.rows() extended instance, with the newly added row selected
		return this.row( rows[0] );
	} );
	
	
	
	var __details_add = function ( ctx, row, data, klass )
	{
		// Convert to array of TR elements
		var rows = [];
		var addRow = function ( r, k ) {
			// Recursion to allow for arrays of jQuery objects
			if ( $.isArray( r ) || r instanceof $ ) {
				for ( var i=0, ien=r.length ; i<ien ; i++ ) {
					addRow( r[i], k );
				}
				return;
			}
	
			// If we get a TR element, then just add it directly - up to the dev
			// to add the correct number of columns etc
			if ( r.nodeName && r.nodeName.toLowerCase() === 'tr' ) {
				rows.push( r );
			}
			else {
				// Otherwise create a row with a wrapper
				var created = $('<tr><td/></tr>').addClass( k );
				$('td', created)
					.addClass( k )
					.html( r )
					[0].colSpan = _fnVisbleColumns( ctx );
	
				rows.push( created[0] );
			}
		};
	
		addRow( data, klass );
	
		if ( row._details ) {
			row._details.detach();
		}
	
		row._details = $(rows);
	
		// If the children were already shown, that state should be retained
		if ( row._detailsShow ) {
			row._details.insertAfter( row.nTr );
		}
	};
	
	
	var __details_remove = function ( api, idx )
	{
		var ctx = api.context;
	
		if ( ctx.length ) {
			var row = ctx[0].aoData[ idx !== undefined ? idx : api[0] ];
	
			if ( row && row._details ) {
				row._details.remove();
	
				row._detailsShow = undefined;
				row._details = undefined;
			}
		}
	};
	
	
	var __details_display = function ( api, show ) {
		var ctx = api.context;
	
		if ( ctx.length && api.length ) {
			var row = ctx[0].aoData[ api[0] ];
	
			if ( row._details ) {
				row._detailsShow = show;
	
				if ( show ) {
					row._details.insertAfter( row.nTr );
				}
				else {
					row._details.detach();
				}
	
				__details_events( ctx[0] );
			}
		}
	};
	
	
	var __details_events = function ( settings )
	{
		var api = new _Api( settings );
		var namespace = '.dt.DT_details';
		var drawEvent = 'draw'+namespace;
		var colvisEvent = 'column-visibility'+namespace;
		var destroyEvent = 'destroy'+namespace;
		var data = settings.aoData;
	
		api.off( drawEvent +' '+ colvisEvent +' '+ destroyEvent );
	
		if ( _pluck( data, '_details' ).length > 0 ) {
			// On each draw, insert the required elements into the document
			api.on( drawEvent, function ( e, ctx ) {
				if ( settings !== ctx ) {
					return;
				}
	
				api.rows( {page:'current'} ).eq(0).each( function (idx) {
					// Internal data grab
					var row = data[ idx ];
	
					if ( row._detailsShow ) {
						row._details.insertAfter( row.nTr );
					}
				} );
			} );
	
			// Column visibility change - update the colspan
			api.on( colvisEvent, function ( e, ctx, idx, vis ) {
				if ( settings !== ctx ) {
					return;
				}
	
				// Update the colspan for the details rows (note, only if it already has
				// a colspan)
				var row, visible = _fnVisbleColumns( ctx );
	
				for ( var i=0, ien=data.length ; i<ien ; i++ ) {
					row = data[i];
	
					if ( row._details ) {
						row._details.children('td[colspan]').attr('colspan', visible );
					}
				}
			} );
	
			// Table destroyed - nuke any child rows
			api.on( destroyEvent, function ( e, ctx ) {
				if ( settings !== ctx ) {
					return;
				}
	
				for ( var i=0, ien=data.length ; i<ien ; i++ ) {
					if ( data[i]._details ) {
						__details_remove( api, i );
					}
				}
			} );
		}
	};
	
	// Strings for the method names to help minification
	var _emp = '';
	var _child_obj = _emp+'row().child';
	var _child_mth = _child_obj+'()';
	
	// data can be:
	//  tr
	//  string
	//  jQuery or array of any of the above
	_api_register( _child_mth, function ( data, klass ) {
		var ctx = this.context;
	
		if ( data === undefined ) {
			// get
			return ctx.length && this.length ?
				ctx[0].aoData[ this[0] ]._details :
				undefined;
		}
		else if ( data === true ) {
			// show
			this.child.show();
		}
		else if ( data === false ) {
			// remove
			__details_remove( this );
		}
		else if ( ctx.length && this.length ) {
			// set
			__details_add( ctx[0], ctx[0].aoData[ this[0] ], data, klass );
		}
	
		return this;
	} );
	
	
	_api_register( [
		_child_obj+'.show()',
		_child_mth+'.show()' // only when `child()` was called with parameters (without
	], function ( show ) {   // it returns an object and this method is not executed)
		__details_display( this, true );
		return this;
	} );
	
	
	_api_register( [
		_child_obj+'.hide()',
		_child_mth+'.hide()' // only when `child()` was called with parameters (without
	], function () {         // it returns an object and this method is not executed)
		__details_display( this, false );
		return this;
	} );
	
	
	_api_register( [
		_child_obj+'.remove()',
		_child_mth+'.remove()' // only when `child()` was called with parameters (without
	], function () {           // it returns an object and this method is not executed)
		__details_remove( this );
		return this;
	} );
	
	
	_api_register( _child_obj+'.isShown()', function () {
		var ctx = this.context;
	
		if ( ctx.length && this.length ) {
			// _detailsShown as false or undefined will fall through to return false
			return ctx[0].aoData[ this[0] ]._detailsShow || false;
		}
		return false;
	} );
	
	
	
	/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
	 * Columns
	 *
	 * {integer}           - column index (>=0 count from left, <0 count from right)
	 * "{integer}:visIdx"  - visible column index (i.e. translate to column index)  (>=0 count from left, <0 count from right)
	 * "{integer}:visible" - alias for {integer}:visIdx  (>=0 count from left, <0 count from right)
	 * "{string}:name"     - column name
	 * "{string}"          - jQuery selector on column header nodes
	 *
	 */
	
	// can be an array of these items, comma separated list, or an array of comma
	// separated lists
	
	var __re_column_selector = /^([^:]+):(name|visIdx|visible)$/;
	
	
	// r1 and r2 are redundant - but it means that the parameters match for the
	// iterator callback in columns().data()
	var __columnData = function ( settings, column, r1, r2, rows ) {
		var a = [];
		for ( var row=0, ien=rows.length ; row<ien ; row++ ) {
			a.push( _fnGetCellData( settings, rows[row], column ) );
		}
		return a;
	};
	
	
	var __column_selector = function ( settings, selector, opts )
	{
		var
			columns = settings.aoColumns,
			names = _pluck( columns, 'sName' ),
			nodes = _pluck( columns, 'nTh' );
	
		var run = function ( s ) {
			var selInt = _intVal( s );
	
			// Selector - all
			if ( s === '' ) {
				return _range( columns.length );
			}
	
			// Selector - index
			if ( selInt !== null ) {
				return [ selInt >= 0 ?
					selInt : // Count from left
					columns.length + selInt // Count from right (+ because its a negative value)
				];
			}
	
			// Selector = function
			if ( typeof s === 'function' ) {
				var rows = _selector_row_indexes( settings, opts );
	
				return $.map( columns, function (col, idx) {
					return s(
							idx,
							__columnData( settings, idx, 0, 0, rows ),
							nodes[ idx ]
						) ? idx : null;
				} );
			}
	
			// jQuery or string selector
			var match = typeof s === 'string' ?
				s.match( __re_column_selector ) :
				'';
	
			if ( match ) {
				switch( match[2] ) {
					case 'visIdx':
					case 'visible':
						var idx = parseInt( match[1], 10 );
						// Visible index given, convert to column index
						if ( idx < 0 ) {
							// Counting from the right
							var visColumns = $.map( columns, function (col,i) {
								return col.bVisible ? i : null;
							} );
							return [ visColumns[ visColumns.length + idx ] ];
						}
						// Counting from the left
						return [ _fnVisibleToColumnIndex( settings, idx ) ];
	
					case 'name':
						// match by name. `names` is column index complete and in order
						return $.map( names, function (name, i) {
							return name === match[1] ? i : null;
						} );
	
					default:
						return [];
				}
			}
	
			// Cell in the table body
			if ( s.nodeName && s._DT_CellIndex ) {
				return [ s._DT_CellIndex.column ];
			}
	
			// jQuery selector on the TH elements for the columns
			var jqResult = $( nodes )
				.filter( s )
				.map( function () {
					return $.inArray( this, nodes ); // `nodes` is column index complete and in order
				} )
				.toArray();
	
			if ( jqResult.length || ! s.nodeName ) {
				return jqResult;
			}
	
			// Otherwise a node which might have a `dt-column` data attribute, or be
			// a child or such an element
			var host = $(s).closest('*[data-dt-column]');
			return host.length ?
				[ host.data('dt-column') ] :
				[];
		};
	
		return _selector_run( 'column', selector, run, settings, opts );
	};
	
	
	var __setColumnVis = function ( settings, column, vis ) {
		var
			cols = settings.aoColumns,
			col  = cols[ column ],
			data = settings.aoData,
			row, cells, i, ien, tr;
	
		// Get
		if ( vis === undefined ) {
			return col.bVisible;
		}
	
		// Set
		// No change
		if ( col.bVisible === vis ) {
			return;
		}
	
		if ( vis ) {
			// Insert column
			// Need to decide if we should use appendChild or insertBefore
			var insertBefore = $.inArray( true, _pluck(cols, 'bVisible'), column+1 );
	
			for ( i=0, ien=data.length ; i<ien ; i++ ) {
				tr = data[i].nTr;
				cells = data[i].anCells;
	
				if ( tr ) {
					// insertBefore can act like appendChild if 2nd arg is null
					tr.insertBefore( cells[ column ], cells[ insertBefore ] || null );
				}
			}
		}
		else {
			// Remove column
			$( _pluck( settings.aoData, 'anCells', column ) ).detach();
		}
	
		// Common actions
		col.bVisible = vis;
		_fnDrawHead( settings, settings.aoHeader );
		_fnDrawHead( settings, settings.aoFooter );
	
		_fnSaveState( settings );
	};
	
	
	_api_register( 'columns()', function ( selector, opts ) {
		// argument shifting
		if ( selector === undefined ) {
			selector = '';
		}
		else if ( $.isPlainObject( selector ) ) {
			opts = selector;
			selector = '';
		}
	
		opts = _selector_opts( opts );
	
		var inst = this.iterator( 'table', function ( settings ) {
			return __column_selector( settings, selector, opts );
		}, 1 );
	
		// Want argument shifting here and in _row_selector?
		inst.selector.cols = selector;
		inst.selector.opts = opts;
	
		return inst;
	} );
	
	_api_registerPlural( 'columns().header()', 'column().header()', function ( selector, opts ) {
		return this.iterator( 'column', function ( settings, column ) {
			return settings.aoColumns[column].nTh;
		}, 1 );
	} );
	
	_api_registerPlural( 'columns().footer()', 'column().footer()', function ( selector, opts ) {
		return this.iterator( 'column', function ( settings, column ) {
			return settings.aoColumns[column].nTf;
		}, 1 );
	} );
	
	_api_registerPlural( 'columns().data()', 'column().data()', function () {
		return this.iterator( 'column-rows', __columnData, 1 );
	} );
	
	_api_registerPlural( 'columns().dataSrc()', 'column().dataSrc()', function () {
		return this.iterator( 'column', function ( settings, column ) {
			return settings.aoColumns[column].mData;
		}, 1 );
	} );
	
	_api_registerPlural( 'columns().cache()', 'column().cache()', function ( type ) {
		return this.iterator( 'column-rows', function ( settings, column, i, j, rows ) {
			return _pluck_order( settings.aoData, rows,
				type === 'search' ? '_aFilterData' : '_aSortData', column
			);
		}, 1 );
	} );
	
	_api_registerPlural( 'columns().nodes()', 'column().nodes()', function () {
		return this.iterator( 'column-rows', function ( settings, column, i, j, rows ) {
			return _pluck_order( settings.aoData, rows, 'anCells', column ) ;
		}, 1 );
	} );
	
	_api_registerPlural( 'columns().visible()', 'column().visible()', function ( vis, calc ) {
		var ret = this.iterator( 'column', function ( settings, column ) {
			if ( vis === undefined ) {
				return settings.aoColumns[ column ].bVisible;
			} // else
			__setColumnVis( settings, column, vis );
		} );
	
		// Group the column visibility changes
		if ( vis !== undefined ) {
			// Second loop once the first is done for events
			this.iterator( 'column', function ( settings, column ) {
				_fnCallbackFire( settings, null, 'column-visibility', [settings, column, vis, calc] );
			} );
	
			if ( calc === undefined || calc ) {
				this.columns.adjust();
			}
		}
	
		return ret;
	} );
	
	_api_registerPlural( 'columns().indexes()', 'column().index()', function ( type ) {
		return this.iterator( 'column', function ( settings, column ) {
			return type === 'visible' ?
				_fnColumnIndexToVisible( settings, column ) :
				column;
		}, 1 );
	} );
	
	_api_register( 'columns.adjust()', function () {
		return this.iterator( 'table', function ( settings ) {
			_fnAdjustColumnSizing( settings );
		}, 1 );
	} );
	
	_api_register( 'column.index()', function ( type, idx ) {
		if ( this.context.length !== 0 ) {
			var ctx = this.context[0];
	
			if ( type === 'fromVisible' || type === 'toData' ) {
				return _fnVisibleToColumnIndex( ctx, idx );
			}
			else if ( type === 'fromData' || type === 'toVisible' ) {
				return _fnColumnIndexToVisible( ctx, idx );
			}
		}
	} );
	
	_api_register( 'column()', function ( selector, opts ) {
		return _selector_first( this.columns( selector, opts ) );
	} );
	
	
	
	var __cell_selector = function ( settings, selector, opts )
	{
		var data = settings.aoData;
		var rows = _selector_row_indexes( settings, opts );
		var cells = _removeEmpty( _pluck_order( data, rows, 'anCells' ) );
		var allCells = $( [].concat.apply([], cells) );
		var row;
		var columns = settings.aoColumns.length;
		var a, i, ien, j, o, host;
	
		var run = function ( s ) {
			var fnSelector = typeof s === 'function';
	
			if ( s === null || s === undefined || fnSelector ) {
				// All cells and function selectors
				a = [];
	
				for ( i=0, ien=rows.length ; i<ien ; i++ ) {
					row = rows[i];
	
					for ( j=0 ; j<columns ; j++ ) {
						o = {
							row: row,
							column: j
						};
	
						if ( fnSelector ) {
							// Selector - function
							host = data[ row ];
	
							if ( s( o, _fnGetCellData(settings, row, j), host.anCells ? host.anCells[j] : null ) ) {
								a.push( o );
							}
						}
						else {
							// Selector - all
							a.push( o );
						}
					}
				}
	
				return a;
			}
			
			// Selector - index
			if ( $.isPlainObject( s ) ) {
				return [s];
			}
	
			// Selector - jQuery filtered cells
			var jqResult = allCells
				.filter( s )
				.map( function (i, el) {
					return { // use a new object, in case someone changes the values
						row:    el._DT_CellIndex.row,
						column: el._DT_CellIndex.column
	 				};
				} )
				.toArray();
	
			if ( jqResult.length || ! s.nodeName ) {
				return jqResult;
			}
	
			// Otherwise the selector is a node, and there is one last option - the
			// element might be a child of an element which has dt-row and dt-column
			// data attributes
			host = $(s).closest('*[data-dt-row]');
			return host.length ?
				[ {
					row: host.data('dt-row'),
					column: host.data('dt-column')
				} ] :
				[];
		};
	
		return _selector_run( 'cell', selector, run, settings, opts );
	};
	
	
	
	
	_api_register( 'cells()', function ( rowSelector, columnSelector, opts ) {
		// Argument shifting
		if ( $.isPlainObject( rowSelector ) ) {
			// Indexes
			if ( rowSelector.row === undefined ) {
				// Selector options in first parameter
				opts = rowSelector;
				rowSelector = null;
			}
			else {
				// Cell index objects in first parameter
				opts = columnSelector;
				columnSelector = null;
			}
		}
		if ( $.isPlainObject( columnSelector ) ) {
			opts = columnSelector;
			columnSelector = null;
		}
	
		// Cell selector
		if ( columnSelector === null || columnSelector === undefined ) {
			return this.iterator( 'table', function ( settings ) {
				return __cell_selector( settings, rowSelector, _selector_opts( opts ) );
			} );
		}
	
		// Row + column selector
		var columns = this.columns( columnSelector, opts );
		var rows = this.rows( rowSelector, opts );
		var a, i, ien, j, jen;
	
		var cells = this.iterator( 'table', function ( settings, idx ) {
			a = [];
	
			for ( i=0, ien=rows[idx].length ; i<ien ; i++ ) {
				for ( j=0, jen=columns[idx].length ; j<jen ; j++ ) {
					a.push( {
						row:    rows[idx][i],
						column: columns[idx][j]
					} );
				}
			}
	
			return a;
		}, 1 );
	
		$.extend( cells.selector, {
			cols: columnSelector,
			rows: rowSelector,
			opts: opts
		} );
	
		return cells;
	} );
	
	
	_api_registerPlural( 'cells().nodes()', 'cell().node()', function () {
		return this.iterator( 'cell', function ( settings, row, column ) {
			var data = settings.aoData[ row ];
	
			return data && data.anCells ?
				data.anCells[ column ] :
				undefined;
		}, 1 );
	} );
	
	
	_api_register( 'cells().data()', function () {
		return this.iterator( 'cell', function ( settings, row, column ) {
			return _fnGetCellData( settings, row, column );
		}, 1 );
	} );
	
	
	_api_registerPlural( 'cells().cache()', 'cell().cache()', function ( type ) {
		type = type === 'search' ? '_aFilterData' : '_aSortData';
	
		return this.iterator( 'cell', function ( settings, row, column ) {
			return settings.aoData[ row ][ type ][ column ];
		}, 1 );
	} );
	
	
	_api_registerPlural( 'cells().render()', 'cell().render()', function ( type ) {
		return this.iterator( 'cell', function ( settings, row, column ) {
			return _fnGetCellData( settings, row, column, type );
		}, 1 );
	} );
	
	
	_api_registerPlural( 'cells().indexes()', 'cell().index()', function () {
		return this.iterator( 'cell', function ( settings, row, column ) {
			return {
				row: row,
				column: column,
				columnVisible: _fnColumnIndexToVisible( settings, column )
			};
		}, 1 );
	} );
	
	
	_api_registerPlural( 'cells().invalidate()', 'cell().invalidate()', function ( src ) {
		return this.iterator( 'cell', function ( settings, row, column ) {
			_fnInvalidate( settings, row, src, column );
		} );
	} );
	
	
	
	_api_register( 'cell()', function ( rowSelector, columnSelector, opts ) {
		return _selector_first( this.cells( rowSelector, columnSelector, opts ) );
	} );
	
	
	_api_register( 'cell().data()', function ( data ) {
		var ctx = this.context;
		var cell = this[0];
	
		if ( data === undefined ) {
			// Get
			return ctx.length && cell.length ?
				_fnGetCellData( ctx[0], cell[0].row, cell[0].column ) :
				undefined;
		}
	
		// Set
		_fnSetCellData( ctx[0], cell[0].row, cell[0].column, data );
		_fnInvalidate( ctx[0], cell[0].row, 'data', cell[0].column );
	
		return this;
	} );
	
	
	
	/**
	 * Get current ordering (sorting) that has been applied to the table.
	 *
	 * @returns {array} 2D array containing the sorting information for the first
	 *   table in the current context. Each element in the parent array represents
	 *   a column being sorted upon (i.e. multi-sorting with two columns would have
	 *   2 inner arrays). The inner arrays may have 2 or 3 elements. The first is
	 *   the column index that the sorting condition applies to, the second is the
	 *   direction of the sort (`desc` or `asc`) and, optionally, the third is the
	 *   index of the sorting order from the `column.sorting` initialisation array.
	 *//**
	 * Set the ordering for the table.
	 *
	 * @param {integer} order Column index to sort upon.
	 * @param {string} direction Direction of the sort to be applied (`asc` or `desc`)
	 * @returns {DataTables.Api} this
	 *//**
	 * Set the ordering for the table.
	 *
	 * @param {array} order 1D array of sorting information to be applied.
	 * @param {array} [...] Optional additional sorting conditions
	 * @returns {DataTables.Api} this
	 *//**
	 * Set the ordering for the table.
	 *
	 * @param {array} order 2D array of sorting information to be applied.
	 * @returns {DataTables.Api} this
	 */
	_api_register( 'order()', function ( order, dir ) {
		var ctx = this.context;
	
		if ( order === undefined ) {
			// get
			return ctx.length !== 0 ?
				ctx[0].aaSorting :
				undefined;
		}
	
		// set
		if ( typeof order === 'number' ) {
			// Simple column / direction passed in
			order = [ [ order, dir ] ];
		}
		else if ( order.length && ! $.isArray( order[0] ) ) {
			// Arguments passed in (list of 1D arrays)
			order = Array.prototype.slice.call( arguments );
		}
		// otherwise a 2D array was passed in
	
		return this.iterator( 'table', function ( settings ) {
			settings.aaSorting = order.slice();
		} );
	} );
	
	
	/**
	 * Attach a sort listener to an element for a given column
	 *
	 * @param {node|jQuery|string} node Identifier for the element(s) to attach the
	 *   listener to. This can take the form of a single DOM node, a jQuery
	 *   collection of nodes or a jQuery selector which will identify the node(s).
	 * @param {integer} column the column that a click on this node will sort on
	 * @param {function} [callback] callback function when sort is run
	 * @returns {DataTables.Api} this
	 */
	_api_register( 'order.listener()', function ( node, column, callback ) {
		return this.iterator( 'table', function ( settings ) {
			_fnSortAttachListener( settings, node, column, callback );
		} );
	} );
	
	
	_api_register( 'order.fixed()', function ( set ) {
		if ( ! set ) {
			var ctx = this.context;
			var fixed = ctx.length ?
				ctx[0].aaSortingFixed :
				undefined;
	
			return $.isArray( fixed ) ?
				{ pre: fixed } :
				fixed;
		}
	
		return this.iterator( 'table', function ( settings ) {
			settings.aaSortingFixed = $.extend( true, {}, set );
		} );
	} );
	
	
	// Order by the selected column(s)
	_api_register( [
		'columns().order()',
		'column().order()'
	], function ( dir ) {
		var that = this;
	
		return this.iterator( 'table', function ( settings, i ) {
			var sort = [];
	
			$.each( that[i], function (j, col) {
				sort.push( [ col, dir ] );
			} );
	
			settings.aaSorting = sort;
		} );
	} );
	
	
	
	_api_register( 'search()', function ( input, regex, smart, caseInsen ) {
		var ctx = this.context;
	
		if ( input === undefined ) {
			// get
			return ctx.length !== 0 ?
				ctx[0].oPreviousSearch.sSearch :
				undefined;
		}
	
		// set
		return this.iterator( 'table', function ( settings ) {
			if ( ! settings.oFeatures.bFilter ) {
				return;
			}
	
			_fnFilterComplete( settings, $.extend( {}, settings.oPreviousSearch, {
				"sSearch": input+"",
				"bRegex":  regex === null ? false : regex,
				"bSmart":  smart === null ? true  : smart,
				"bCaseInsensitive": caseInsen === null ? true : caseInsen
			} ), 1 );
		} );
	} );
	
	
	_api_registerPlural(
		'columns().search()',
		'column().search()',
		function ( input, regex, smart, caseInsen ) {
			return this.iterator( 'column', function ( settings, column ) {
				var preSearch = settings.aoPreSearchCols;
	
				if ( input === undefined ) {
					// get
					return preSearch[ column ].sSearch;
				}
	
				// set
				if ( ! settings.oFeatures.bFilter ) {
					return;
				}
	
				$.extend( preSearch[ column ], {
					"sSearch": input+"",
					"bRegex":  regex === null ? false : regex,
					"bSmart":  smart === null ? true  : smart,
					"bCaseInsensitive": caseInsen === null ? true : caseInsen
				} );
	
				_fnFilterComplete( settings, settings.oPreviousSearch, 1 );
			} );
		}
	);
	
	/*
	 * State API methods
	 */
	
	_api_register( 'state()', function () {
		return this.context.length ?
			this.context[0].oSavedState :
			null;
	} );
	
	
	_api_register( 'state.clear()', function () {
		return this.iterator( 'table', function ( settings ) {
			// Save an empty object
			settings.fnStateSaveCallback.call( settings.oInstance, settings, {} );
		} );
	} );
	
	
	_api_register( 'state.loaded()', function () {
		return this.context.length ?
			this.context[0].oLoadedState :
			null;
	} );
	
	
	_api_register( 'state.save()', function () {
		return this.iterator( 'table', function ( settings ) {
			_fnSaveState( settings );
		} );
	} );
	
	
	
	/**
	 * Provide a common method for plug-ins to check the version of DataTables being
	 * used, in order to ensure compatibility.
	 *
	 *  @param {string} version Version string to check for, in the format "X.Y.Z".
	 *    Note that the formats "X" and "X.Y" are also acceptable.
	 *  @returns {boolean} true if this version of DataTables is greater or equal to
	 *    the required version, or false if this version of DataTales is not
	 *    suitable
	 *  @static
	 *  @dtopt API-Static
	 *
	 *  @example
	 *    alert( $.fn.dataTable.versionCheck( '1.9.0' ) );
	 */
	DataTable.versionCheck = DataTable.fnVersionCheck = function( version )
	{
		var aThis = DataTable.version.split('.');
		var aThat = version.split('.');
		var iThis, iThat;
	
		for ( var i=0, iLen=aThat.length ; i<iLen ; i++ ) {
			iThis = parseInt( aThis[i], 10 ) || 0;
			iThat = parseInt( aThat[i], 10 ) || 0;
	
			// Parts are the same, keep comparing
			if (iThis === iThat) {
				continue;
			}
	
			// Parts are different, return immediately
			return iThis > iThat;
		}
	
		return true;
	};
	
	
	/**
	 * Check if a `<table>` node is a DataTable table already or not.
	 *
	 *  @param {node|jquery|string} table Table node, jQuery object or jQuery
	 *      selector for the table to test. Note that if more than more than one
	 *      table is passed on, only the first will be checked
	 *  @returns {boolean} true the table given is a DataTable, or false otherwise
	 *  @static
	 *  @dtopt API-Static
	 *
	 *  @example
	 *    if ( ! $.fn.DataTable.isDataTable( '#example' ) ) {
	 *      $('#example').dataTable();
	 *    }
	 */
	DataTable.isDataTable = DataTable.fnIsDataTable = function ( table )
	{
		var t = $(table).get(0);
		var is = false;
	
		if ( table instanceof DataTable.Api ) {
			return true;
		}
	
		$.each( DataTable.settings, function (i, o) {
			var head = o.nScrollHead ? $('table', o.nScrollHead)[0] : null;
			var foot = o.nScrollFoot ? $('table', o.nScrollFoot)[0] : null;
	
			if ( o.nTable === t || head === t || foot === t ) {
				is = true;
			}
		} );
	
		return is;
	};
	
	
	/**
	 * Get all DataTable tables that have been initialised - optionally you can
	 * select to get only currently visible tables.
	 *
	 *  @param {boolean} [visible=false] Flag to indicate if you want all (default)
	 *    or visible tables only.
	 *  @returns {array} Array of `table` nodes (not DataTable instances) which are
	 *    DataTables
	 *  @static
	 *  @dtopt API-Static
	 *
	 *  @example
	 *    $.each( $.fn.dataTable.tables(true), function () {
	 *      $(table).DataTable().columns.adjust();
	 *    } );
	 */
	DataTable.tables = DataTable.fnTables = function ( visible )
	{
		var api = false;
	
		if ( $.isPlainObject( visible ) ) {
			api = visible.api;
			visible = visible.visible;
		}
	
		var a = $.map( DataTable.settings, function (o) {
			if ( !visible || (visible && $(o.nTable).is(':visible')) ) {
				return o.nTable;
			}
		} );
	
		return api ?
			new _Api( a ) :
			a;
	};
	
	
	/**
	 * Convert from camel case parameters to Hungarian notation. This is made public
	 * for the extensions to provide the same ability as DataTables core to accept
	 * either the 1.9 style Hungarian notation, or the 1.10+ style camelCase
	 * parameters.
	 *
	 *  @param {object} src The model object which holds all parameters that can be
	 *    mapped.
	 *  @param {object} user The object to convert from camel case to Hungarian.
	 *  @param {boolean} force When set to `true`, properties which already have a
	 *    Hungarian value in the `user` object will be overwritten. Otherwise they
	 *    won't be.
	 */
	DataTable.camelToHungarian = _fnCamelToHungarian;
	
	
	
	/**
	 *
	 */
	_api_register( '$()', function ( selector, opts ) {
		var
			rows   = this.rows( opts ).nodes(), // Get all rows
			jqRows = $(rows);
	
		return $( [].concat(
			jqRows.filter( selector ).toArray(),
			jqRows.find( selector ).toArray()
		) );
	} );
	
	
	// jQuery functions to operate on the tables
	$.each( [ 'on', 'one', 'off' ], function (i, key) {
		_api_register( key+'()', function ( /* event, handler */ ) {
			var args = Array.prototype.slice.call(arguments);
	
			// Add the `dt` namespace automatically if it isn't already present
			args[0] = $.map( args[0].split( /\s/ ), function ( e ) {
				return ! e.match(/\.dt\b/) ?
					e+'.dt' :
					e;
				} ).join( ' ' );
	
			var inst = $( this.tables().nodes() );
			inst[key].apply( inst, args );
			return this;
		} );
	} );
	
	
	_api_register( 'clear()', function () {
		return this.iterator( 'table', function ( settings ) {
			_fnClearTable( settings );
		} );
	} );
	
	
	_api_register( 'settings()', function () {
		return new _Api( this.context, this.context );
	} );
	
	
	_api_register( 'init()', function () {
		var ctx = this.context;
		return ctx.length ? ctx[0].oInit : null;
	} );
	
	
	_api_register( 'data()', function () {
		return this.iterator( 'table', function ( settings ) {
			return _pluck( settings.aoData, '_aData' );
		} ).flatten();
	} );
	
	
	_api_register( 'destroy()', function ( remove ) {
		remove = remove || false;
	
		return this.iterator( 'table', function ( settings ) {
			var orig      = settings.nTableWrapper.parentNode;
			var classes   = settings.oClasses;
			var table     = settings.nTable;
			var tbody     = settings.nTBody;
			var thead     = settings.nTHead;
			var tfoot     = settings.nTFoot;
			var jqTable   = $(table);
			var jqTbody   = $(tbody);
			var jqWrapper = $(settings.nTableWrapper);
			var rows      = $.map( settings.aoData, function (r) { return r.nTr; } );
			var i, ien;
	
			// Flag to note that the table is currently being destroyed - no action
			// should be taken
			settings.bDestroying = true;
	
			// Fire off the destroy callbacks for plug-ins etc
			_fnCallbackFire( settings, "aoDestroyCallback", "destroy", [settings] );
	
			// If not being removed from the document, make all columns visible
			if ( ! remove ) {
				new _Api( settings ).columns().visible( true );
			}
	
			// Blitz all `DT` namespaced events (these are internal events, the
			// lowercase, `dt` events are user subscribed and they are responsible
			// for removing them
			jqWrapper.off('.DT').find(':not(tbody *)').off('.DT');
			$(window).off('.DT-'+settings.sInstance);
	
			// When scrolling we had to break the table up - restore it
			if ( table != thead.parentNode ) {
				jqTable.children('thead').detach();
				jqTable.append( thead );
			}
	
			if ( tfoot && table != tfoot.parentNode ) {
				jqTable.children('tfoot').detach();
				jqTable.append( tfoot );
			}
	
			settings.aaSorting = [];
			settings.aaSortingFixed = [];
			_fnSortingClasses( settings );
	
			$( rows ).removeClass( settings.asStripeClasses.join(' ') );
	
			$('th, td', thead).removeClass( classes.sSortable+' '+
				classes.sSortableAsc+' '+classes.sSortableDesc+' '+classes.sSortableNone
			);
	
			// Add the TR elements back into the table in their original order
			jqTbody.children().detach();
			jqTbody.append( rows );
	
			// Remove the DataTables generated nodes, events and classes
			var removedMethod = remove ? 'remove' : 'detach';
			jqTable[ removedMethod ]();
			jqWrapper[ removedMethod ]();
	
			// If we need to reattach the table to the document
			if ( ! remove && orig ) {
				// insertBefore acts like appendChild if !arg[1]
				orig.insertBefore( table, settings.nTableReinsertBefore );
	
				// Restore the width of the original table - was read from the style property,
				// so we can restore directly to that
				jqTable
					.css( 'width', settings.sDestroyWidth )
					.removeClass( classes.sTable );
	
				// If the were originally stripe classes - then we add them back here.
				// Note this is not fool proof (for example if not all rows had stripe
				// classes - but it's a good effort without getting carried away
				ien = settings.asDestroyStripes.length;
	
				if ( ien ) {
					jqTbody.children().each( function (i) {
						$(this).addClass( settings.asDestroyStripes[i % ien] );
					} );
				}
			}
	
			/* Remove the settings object from the settings array */
			var idx = $.inArray( settings, DataTable.settings );
			if ( idx !== -1 ) {
				DataTable.settings.splice( idx, 1 );
			}
		} );
	} );
	
	
	// Add the `every()` method for rows, columns and cells in a compact form
	$.each( [ 'column', 'row', 'cell' ], function ( i, type ) {
		_api_register( type+'s().every()', function ( fn ) {
			var opts = this.selector.opts;
			var api = this;
	
			return this.iterator( type, function ( settings, arg1, arg2, arg3, arg4 ) {
				// Rows and columns:
				//  arg1 - index
				//  arg2 - table counter
				//  arg3 - loop counter
				//  arg4 - undefined
				// Cells:
				//  arg1 - row index
				//  arg2 - column index
				//  arg3 - table counter
				//  arg4 - loop counter
				fn.call(
					api[ type ](
						arg1,
						type==='cell' ? arg2 : opts,
						type==='cell' ? opts : undefined
					),
					arg1, arg2, arg3, arg4
				);
			} );
		} );
	} );
	
	
	// i18n method for extensions to be able to use the language object from the
	// DataTable
	_api_register( 'i18n()', function ( token, def, plural ) {
		var ctx = this.context[0];
		var resolved = _fnGetObjectDataFn( token )( ctx.oLanguage );
	
		if ( resolved === undefined ) {
			resolved = def;
		}
	
		if ( plural !== undefined && $.isPlainObject( resolved ) ) {
			resolved = resolved[ plural ] !== undefined ?
				resolved[ plural ] :
				resolved._;
		}
	
		return resolved.replace( '%d', plural ); // nb: plural might be undefined,
	} );
	/**
	 * Version string for plug-ins to check compatibility. Allowed format is
	 * `a.b.c-d` where: a:int, b:int, c:int, d:string(dev|beta|alpha). `d` is used
	 * only for non-release builds. See http://semver.org/ for more information.
	 *  @member
	 *  @type string
	 *  @default Version number
	 */
	DataTable.version = "1.10.16";

	/**
	 * Private data store, containing all of the settings objects that are
	 * created for the tables on a given page.
	 *
	 * Note that the `DataTable.settings` object is aliased to
	 * `jQuery.fn.dataTableExt` through which it may be accessed and
	 * manipulated, or `jQuery.fn.dataTable.settings`.
	 *  @member
	 *  @type array
	 *  @default []
	 *  @private
	 */
	DataTable.settings = [];

	/**
	 * Object models container, for the various models that DataTables has
	 * available to it. These models define the objects that are used to hold
	 * the active state and configuration of the table.
	 *  @namespace
	 */
	DataTable.models = {};
	
	
	
	/**
	 * Template object for the way in which DataTables holds information about
	 * search information for the global filter and individual column filters.
	 *  @namespace
	 */
	DataTable.models.oSearch = {
		/**
		 * Flag to indicate if the filtering should be case insensitive or not
		 *  @type boolean
		 *  @default true
		 */
		"bCaseInsensitive": true,
	
		/**
		 * Applied search term
		 *  @type string
		 *  @default <i>Empty string</i>
		 */
		"sSearch": "",
	
		/**
		 * Flag to indicate if the search term should be interpreted as a
		 * regular expression (true) or not (false) and therefore and special
		 * regex characters escaped.
		 *  @type boolean
		 *  @default false
		 */
		"bRegex": false,
	
		/**
		 * Flag to indicate if DataTables is to use its smart filtering or not.
		 *  @type boolean
		 *  @default true
		 */
		"bSmart": true
	};
	
	
	
	
	/**
	 * Template object for the way in which DataTables holds information about
	 * each individual row. This is the object format used for the settings
	 * aoData array.
	 *  @namespace
	 */
	DataTable.models.oRow = {
		/**
		 * TR element for the row
		 *  @type node
		 *  @default null
		 */
		"nTr": null,
	
		/**
		 * Array of TD elements for each row. This is null until the row has been
		 * created.
		 *  @type array nodes
		 *  @default []
		 */
		"anCells": null,
	
		/**
		 * Data object from the original data source for the row. This is either
		 * an array if using the traditional form of DataTables, or an object if
		 * using mData options. The exact type will depend on the passed in
		 * data from the data source, or will be an array if using DOM a data
		 * source.
		 *  @type array|object
		 *  @default []
		 */
		"_aData": [],
	
		/**
		 * Sorting data cache - this array is ostensibly the same length as the
		 * number of columns (although each index is generated only as it is
		 * needed), and holds the data that is used for sorting each column in the
		 * row. We do this cache generation at the start of the sort in order that
		 * the formatting of the sort data need be done only once for each cell
		 * per sort. This array should not be read from or written to by anything
		 * other than the master sorting methods.
		 *  @type array
		 *  @default null
		 *  @private
		 */
		"_aSortData": null,
	
		/**
		 * Per cell filtering data cache. As per the sort data cache, used to
		 * increase the performance of the filtering in DataTables
		 *  @type array
		 *  @default null
		 *  @private
		 */
		"_aFilterData": null,
	
		/**
		 * Filtering data cache. This is the same as the cell filtering cache, but
		 * in this case a string rather than an array. This is easily computed with
		 * a join on `_aFilterData`, but is provided as a cache so the join isn't
		 * needed on every search (memory traded for performance)
		 *  @type array
		 *  @default null
		 *  @private
		 */
		"_sFilterRow": null,
	
		/**
		 * Cache of the class name that DataTables has applied to the row, so we
		 * can quickly look at this variable rather than needing to do a DOM check
		 * on className for the nTr property.
		 *  @type string
		 *  @default <i>Empty string</i>
		 *  @private
		 */
		"_sRowStripe": "",
	
		/**
		 * Denote if the original data source was from the DOM, or the data source
		 * object. This is used for invalidating data, so DataTables can
		 * automatically read data from the original source, unless uninstructed
		 * otherwise.
		 *  @type string
		 *  @default null
		 *  @private
		 */
		"src": null,
	
		/**
		 * Index in the aoData array. This saves an indexOf lookup when we have the
		 * object, but want to know the index
		 *  @type integer
		 *  @default -1
		 *  @private
		 */
		"idx": -1
	};
	
	
	/**
	 * Template object for the column information object in DataTables. This object
	 * is held in the settings aoColumns array and contains all the information that
	 * DataTables needs about each individual column.
	 *
	 * Note that this object is related to {@link DataTable.defaults.column}
	 * but this one is the internal data store for DataTables's cache of columns.
	 * It should NOT be manipulated outside of DataTables. Any configuration should
	 * be done through the initialisation options.
	 *  @namespace
	 */
	DataTable.models.oColumn = {
		/**
		 * Column index. This could be worked out on-the-fly with $.inArray, but it
		 * is faster to just hold it as a variable
		 *  @type integer
		 *  @default null
		 */
		"idx": null,
	
		/**
		 * A list of the columns that sorting should occur on when this column
		 * is sorted. That this property is an array allows multi-column sorting
		 * to be defined for a column (for example first name / last name columns
		 * would benefit from this). The values are integers pointing to the
		 * columns to be sorted on (typically it will be a single integer pointing
		 * at itself, but that doesn't need to be the case).
		 *  @type array
		 */
		"aDataSort": null,
	
		/**
		 * Define the sorting directions that are applied to the column, in sequence
		 * as the column is repeatedly sorted upon - i.e. the first value is used
		 * as the sorting direction when the column if first sorted (clicked on).
		 * Sort it again (click again) and it will move on to the next index.
		 * Repeat until loop.
		 *  @type array
		 */
		"asSorting": null,
	
		/**
		 * Flag to indicate if the column is searchable, and thus should be included
		 * in the filtering or not.
		 *  @type boolean
		 */
		"bSearchable": null,
	
		/**
		 * Flag to indicate if the column is sortable or not.
		 *  @type boolean
		 */
		"bSortable": null,
	
		/**
		 * Flag to indicate if the column is currently visible in the table or not
		 *  @type boolean
		 */
		"bVisible": null,
	
		/**
		 * Store for manual type assignment using the `column.type` option. This
		 * is held in store so we can manipulate the column's `sType` property.
		 *  @type string
		 *  @default null
		 *  @private
		 */
		"_sManualType": null,
	
		/**
		 * Flag to indicate if HTML5 data attributes should be used as the data
		 * source for filtering or sorting. True is either are.
		 *  @type boolean
		 *  @default false
		 *  @private
		 */
		"_bAttrSrc": false,
	
		/**
		 * Developer definable function that is called whenever a cell is created (Ajax source,
		 * etc) or processed for input (DOM source). This can be used as a compliment to mRender
		 * allowing you to modify the DOM element (add background colour for example) when the
		 * element is available.
		 *  @type function
		 *  @param {element} nTd The TD node that has been created
		 *  @param {*} sData The Data for the cell
		 *  @param {array|object} oData The data for the whole row
		 *  @param {int} iRow The row index for the aoData data store
		 *  @default null
		 */
		"fnCreatedCell": null,
	
		/**
		 * Function to get data from a cell in a column. You should <b>never</b>
		 * access data directly through _aData internally in DataTables - always use
		 * the method attached to this property. It allows mData to function as
		 * required. This function is automatically assigned by the column
		 * initialisation method
		 *  @type function
		 *  @param {array|object} oData The data array/object for the array
		 *    (i.e. aoData[]._aData)
		 *  @param {string} sSpecific The specific data type you want to get -
		 *    'display', 'type' 'filter' 'sort'
		 *  @returns {*} The data for the cell from the given row's data
		 *  @default null
		 */
		"fnGetData": null,
	
		/**
		 * Function to set data for a cell in the column. You should <b>never</b>
		 * set the data directly to _aData internally in DataTables - always use
		 * this method. It allows mData to function as required. This function
		 * is automatically assigned by the column initialisation method
		 *  @type function
		 *  @param {array|object} oData The data array/object for the array
		 *    (i.e. aoData[]._aData)
		 *  @param {*} sValue Value to set
		 *  @default null
		 */
		"fnSetData": null,
	
		/**
		 * Property to read the value for the cells in the column from the data
		 * source array / object. If null, then the default content is used, if a
		 * function is given then the return from the function is used.
		 *  @type function|int|string|null
		 *  @default null
		 */
		"mData": null,
	
		/**
		 * Partner property to mData which is used (only when defined) to get
		 * the data - i.e. it is basically the same as mData, but without the
		 * 'set' option, and also the data fed to it is the result from mData.
		 * This is the rendering method to match the data method of mData.
		 *  @type function|int|string|null
		 *  @default null
		 */
		"mRender": null,
	
		/**
		 * Unique header TH/TD element for this column - this is what the sorting
		 * listener is attached to (if sorting is enabled.)
		 *  @type node
		 *  @default null
		 */
		"nTh": null,
	
		/**
		 * Unique footer TH/TD element for this column (if there is one). Not used
		 * in DataTables as such, but can be used for plug-ins to reference the
		 * footer for each column.
		 *  @type node
		 *  @default null
		 */
		"nTf": null,
	
		/**
		 * The class to apply to all TD elements in the table's TBODY for the column
		 *  @type string
		 *  @default null
		 */
		"sClass": null,
	
		/**
		 * When DataTables calculates the column widths to assign to each column,
		 * it finds the longest string in each column and then constructs a
		 * temporary table and reads the widths from that. The problem with this
		 * is that "mmm" is much wider then "iiii", but the latter is a longer
		 * string - thus the calculation can go wrong (doing it properly and putting
		 * it into an DOM object and measuring that is horribly(!) slow). Thus as
		 * a "work around" we provide this option. It will append its value to the
		 * text that is found to be the longest string for the column - i.e. padding.
		 *  @type string
		 */
		"sContentPadding": null,
	
		/**
		 * Allows a default value to be given for a column's data, and will be used
		 * whenever a null data source is encountered (this can be because mData
		 * is set to null, or because the data source itself is null).
		 *  @type string
		 *  @default null
		 */
		"sDefaultContent": null,
	
		/**
		 * Name for the column, allowing reference to the column by name as well as
		 * by index (needs a lookup to work by name).
		 *  @type string
		 */
		"sName": null,
	
		/**
		 * Custom sorting data type - defines which of the available plug-ins in
		 * afnSortData the custom sorting will use - if any is defined.
		 *  @type string
		 *  @default std
		 */
		"sSortDataType": 'std',
	
		/**
		 * Class to be applied to the header element when sorting on this column
		 *  @type string
		 *  @default null
		 */
		"sSortingClass": null,
	
		/**
		 * Class to be applied to the header element when sorting on this column -
		 * when jQuery UI theming is used.
		 *  @type string
		 *  @default null
		 */
		"sSortingClassJUI": null,
	
		/**
		 * Title of the column - what is seen in the TH element (nTh).
		 *  @type string
		 */
		"sTitle": null,
	
		/**
		 * Column sorting and filtering type
		 *  @type string
		 *  @default null
		 */
		"sType": null,
	
		/**
		 * Width of the column
		 *  @type string
		 *  @default null
		 */
		"sWidth": null,
	
		/**
		 * Width of the column when it was first "encountered"
		 *  @type string
		 *  @default null
		 */
		"sWidthOrig": null
	};
	
	
	/*
	 * Developer note: The properties of the object below are given in Hungarian
	 * notation, that was used as the interface for DataTables prior to v1.10, however
	 * from v1.10 onwards the primary interface is camel case. In order to avoid
	 * breaking backwards compatibility utterly with this change, the Hungarian
	 * version is still, internally the primary interface, but is is not documented
	 * - hence the @name tags in each doc comment. This allows a Javascript function
	 * to create a map from Hungarian notation to camel case (going the other direction
	 * would require each property to be listed, which would at around 3K to the size
	 * of DataTables, while this method is about a 0.5K hit.
	 *
	 * Ultimately this does pave the way for Hungarian notation to be dropped
	 * completely, but that is a massive amount of work and will break current
	 * installs (therefore is on-hold until v2).
	 */
	
	/**
	 * Initialisation options that can be given to DataTables at initialisation
	 * time.
	 *  @namespace
	 */
	DataTable.defaults = {
		/**
		 * An array of data to use for the table, passed in at initialisation which
		 * will be used in preference to any data which is already in the DOM. This is
		 * particularly useful for constructing tables purely in Javascript, for
		 * example with a custom Ajax call.
		 *  @type array
		 *  @default null
		 *
		 *  @dtopt Option
		 *  @name DataTable.defaults.data
		 *
		 *  @example
		 *    // Using a 2D array data source
		 *    $(document).ready( function () {
		 *      $('#example').dataTable( {
		 *        "data": [
		 *          ['Trident', 'Internet Explorer 4.0', 'Win 95+', 4, 'X'],
		 *          ['Trident', 'Internet Explorer 5.0', 'Win 95+', 5, 'C'],
		 *        ],
		 *        "columns": [
		 *          { "title": "Engine" },
		 *          { "title": "Browser" },
		 *          { "title": "Platform" },
		 *          { "title": "Version" },
		 *          { "title": "Grade" }
		 *        ]
		 *      } );
		 *    } );
		 *
		 *  @example
		 *    // Using an array of objects as a data source (`data`)
		 *    $(document).ready( function () {
		 *      $('#example').dataTable( {
		 *        "data": [
		 *          {
		 *            "engine":   "Trident",
		 *            "browser":  "Internet Explorer 4.0",
		 *            "platform": "Win 95+",
		 *            "version":  4,
		 *            "grade":    "X"
		 *          },
		 *          {
		 *            "engine":   "Trident",
		 *            "browser":  "Internet Explorer 5.0",
		 *            "platform": "Win 95+",
		 *            "version":  5,
		 *            "grade":    "C"
		 *          }
		 *        ],
		 *        "columns": [
		 *          { "title": "Engine",   "data": "engine" },
		 *          { "title": "Browser",  "data": "browser" },
		 *          { "title": "Platform", "data": "platform" },
		 *          { "title": "Version",  "data": "version" },
		 *          { "title": "Grade",    "data": "grade" }
		 *        ]
		 *      } );
		 *    } );
		 */
		"aaData": null,
	
	
		/**
		 * If ordering is enabled, then DataTables will perform a first pass sort on
		 * initialisation. You can define which column(s) the sort is performed
		 * upon, and the sorting direction, with this variable. The `sorting` array
		 * should contain an array for each column to be sorted initially containing
		 * the column's index and a direction string ('asc' or 'desc').
		 *  @type array
		 *  @default [[0,'asc']]
		 *
		 *  @dtopt Option
		 *  @name DataTable.defaults.order
		 *
		 *  @example
		 *    // Sort by 3rd column first, and then 4th column
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "order": [[2,'asc'], [3,'desc']]
		 *      } );
		 *    } );
		 *
		 *    // No initial sorting
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "order": []
		 *      } );
		 *    } );
		 */
		"aaSorting": [[0,'asc']],
	
	
		/**
		 * This parameter is basically identical to the `sorting` parameter, but
		 * cannot be overridden by user interaction with the table. What this means
		 * is that you could have a column (visible or hidden) which the sorting
		 * will always be forced on first - any sorting after that (from the user)
		 * will then be performed as required. This can be useful for grouping rows
		 * together.
		 *  @type array
		 *  @default null
		 *
		 *  @dtopt Option
		 *  @name DataTable.defaults.orderFixed
		 *
		 *  @example
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "orderFixed": [[0,'asc']]
		 *      } );
		 *    } )
		 */
		"aaSortingFixed": [],
	
	
		/**
		 * DataTables can be instructed to load data to display in the table from a
		 * Ajax source. This option defines how that Ajax call is made and where to.
		 *
		 * The `ajax` property has three different modes of operation, depending on
		 * how it is defined. These are:
		 *
		 * * `string` - Set the URL from where the data should be loaded from.
		 * * `object` - Define properties for `jQuery.ajax`.
		 * * `function` - Custom data get function
		 *
		 * `string`
		 * --------
		 *
		 * As a string, the `ajax` property simply defines the URL from which
		 * DataTables will load data.
		 *
		 * `object`
		 * --------
		 *
		 * As an object, the parameters in the object are passed to
		 * [jQuery.ajax](http://api.jquery.com/jQuery.ajax/) allowing fine control
		 * of the Ajax request. DataTables has a number of default parameters which
		 * you can override using this option. Please refer to the jQuery
		 * documentation for a full description of the options available, although
		 * the following parameters provide additional options in DataTables or
		 * require special consideration:
		 *
		 * * `data` - As with jQuery, `data` can be provided as an object, but it
		 *   can also be used as a function to manipulate the data DataTables sends
		 *   to the server. The function takes a single parameter, an object of
		 *   parameters with the values that DataTables has readied for sending. An
		 *   object may be returned which will be merged into the DataTables
		 *   defaults, or you can add the items to the object that was passed in and
		 *   not return anything from the function. This supersedes `fnServerParams`
		 *   from DataTables 1.9-.
		 *
		 * * `dataSrc` - By default DataTables will look for the property `data` (or
		 *   `aaData` for compatibility with DataTables 1.9-) when obtaining data
		 *   from an Ajax source or for server-side processing - this parameter
		 *   allows that property to be changed. You can use Javascript dotted
		 *   object notation to get a data source for multiple levels of nesting, or
		 *   it my be used as a function. As a function it takes a single parameter,
		 *   the JSON returned from the server, which can be manipulated as
		 *   required, with the returned value being that used by DataTables as the
		 *   data source for the table. This supersedes `sAjaxDataProp` from
		 *   DataTables 1.9-.
		 *
		 * * `success` - Should not be overridden it is used internally in
		 *   DataTables. To manipulate / transform the data returned by the server
		 *   use `ajax.dataSrc`, or use `ajax` as a function (see below).
		 *
		 * `function`
		 * ----------
		 *
		 * As a function, making the Ajax call is left up to yourself allowing
		 * complete control of the Ajax request. Indeed, if desired, a method other
		 * than Ajax could be used to obtain the required data, such as Web storage
		 * or an AIR database.
		 *
		 * The function is given four parameters and no return is required. The
		 * parameters are:
		 *
		 * 1. _object_ - Data to send to the server
		 * 2. _function_ - Callback function that must be executed when the required
		 *    data has been obtained. That data should be passed into the callback
		 *    as the only parameter
		 * 3. _object_ - DataTables settings object for the table
		 *
		 * Note that this supersedes `fnServerData` from DataTables 1.9-.
		 *
		 *  @type string|object|function
		 *  @default null
		 *
		 *  @dtopt Option
		 *  @name DataTable.defaults.ajax
		 *  @since 1.10.0
		 *
		 * @example
		 *   // Get JSON data from a file via Ajax.
		 *   // Note DataTables expects data in the form `{ data: [ ...data... ] }` by default).
		 *   $('#example').dataTable( {
		 *     "ajax": "data.json"
		 *   } );
		 *
		 * @example
		 *   // Get JSON data from a file via Ajax, using `dataSrc` to change
		 *   // `data` to `tableData` (i.e. `{ tableData: [ ...data... ] }`)
		 *   $('#example').dataTable( {
		 *     "ajax": {
		 *       "url": "data.json",
		 *       "dataSrc": "tableData"
		 *     }
		 *   } );
		 *
		 * @example
		 *   // Get JSON data from a file via Ajax, using `dataSrc` to read data
		 *   // from a plain array rather than an array in an object
		 *   $('#example').dataTable( {
		 *     "ajax": {
		 *       "url": "data.json",
		 *       "dataSrc": ""
		 *     }
		 *   } );
		 *
		 * @example
		 *   // Manipulate the data returned from the server - add a link to data
		 *   // (note this can, should, be done using `render` for the column - this
		 *   // is just a simple example of how the data can be manipulated).
		 *   $('#example').dataTable( {
		 *     "ajax": {
		 *       "url": "data.json",
		 *       "dataSrc": function ( json ) {
		 *         for ( var i=0, ien=json.length ; i<ien ; i++ ) {
		 *           json[i][0] = '<a href="/message/'+json[i][0]+'>View message</a>';
		 *         }
		 *         return json;
		 *       }
		 *     }
		 *   } );
		 *
		 * @example
		 *   // Add data to the request
		 *   $('#example').dataTable( {
		 *     "ajax": {
		 *       "url": "data.json",
		 *       "data": function ( d ) {
		 *         return {
		 *           "extra_search": $('#extra').val()
		 *         };
		 *       }
		 *     }
		 *   } );
		 *
		 * @example
		 *   // Send request as POST
		 *   $('#example').dataTable( {
		 *     "ajax": {
		 *       "url": "data.json",
		 *       "type": "POST"
		 *     }
		 *   } );
		 *
		 * @example
		 *   // Get the data from localStorage (could interface with a form for
		 *   // adding, editing and removing rows).
		 *   $('#example').dataTable( {
		 *     "ajax": function (data, callback, settings) {
		 *       callback(
		 *         JSON.parse( localStorage.getItem('dataTablesData') )
		 *       );
		 *     }
		 *   } );
		 */
		"ajax": null,
	
	
		/**
		 * This parameter allows you to readily specify the entries in the length drop
		 * down menu that DataTables shows when pagination is enabled. It can be
		 * either a 1D array of options which will be used for both the displayed
		 * option and the value, or a 2D array which will use the array in the first
		 * position as the value, and the array in the second position as the
		 * displayed options (useful for language strings such as 'All').
		 *
		 * Note that the `pageLength` property will be automatically set to the
		 * first value given in this array, unless `pageLength` is also provided.
		 *  @type array
		 *  @default [ 10, 25, 50, 100 ]
		 *
		 *  @dtopt Option
		 *  @name DataTable.defaults.lengthMenu
		 *
		 *  @example
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "lengthMenu": [[10, 25, 50, -1], [10, 25, 50, "All"]]
		 *      } );
		 *    } );
		 */
		"aLengthMenu": [ 10, 25, 50, 100 ],
	
	
		/**
		 * The `columns` option in the initialisation parameter allows you to define
		 * details about the way individual columns behave. For a full list of
		 * column options that can be set, please see
		 * {@link DataTable.defaults.column}. Note that if you use `columns` to
		 * define your columns, you must have an entry in the array for every single
		 * column that you have in your table (these can be null if you don't which
		 * to specify any options).
		 *  @member
		 *
		 *  @name DataTable.defaults.column
		 */
		"aoColumns": null,
	
		/**
		 * Very similar to `columns`, `columnDefs` allows you to target a specific
		 * column, multiple columns, or all columns, using the `targets` property of
		 * each object in the array. This allows great flexibility when creating
		 * tables, as the `columnDefs` arrays can be of any length, targeting the
		 * columns you specifically want. `columnDefs` may use any of the column
		 * options available: {@link DataTable.defaults.column}, but it _must_
		 * have `targets` defined in each object in the array. Values in the `targets`
		 * array may be:
		 *   <ul>
		 *     <li>a string - class name will be matched on the TH for the column</li>
		 *     <li>0 or a positive integer - column index counting from the left</li>
		 *     <li>a negative integer - column index counting from the right</li>
		 *     <li>the string "_all" - all columns (i.e. assign a default)</li>
		 *   </ul>
		 *  @member
		 *
		 *  @name DataTable.defaults.columnDefs
		 */
		"aoColumnDefs": null,
	
	
		/**
		 * Basically the same as `search`, this parameter defines the individual column
		 * filtering state at initialisation time. The array must be of the same size
		 * as the number of columns, and each element be an object with the parameters
		 * `search` and `escapeRegex` (the latter is optional). 'null' is also
		 * accepted and the default will be used.
		 *  @type array
		 *  @default []
		 *
		 *  @dtopt Option
		 *  @name DataTable.defaults.searchCols
		 *
		 *  @example
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "searchCols": [
		 *          null,
		 *          { "search": "My filter" },
		 *          null,
		 *          { "search": "^[0-9]", "escapeRegex": false }
		 *        ]
		 *      } );
		 *    } )
		 */
		"aoSearchCols": [],
	
	
		/**
		 * An array of CSS classes that should be applied to displayed rows. This
		 * array may be of any length, and DataTables will apply each class
		 * sequentially, looping when required.
		 *  @type array
		 *  @default null <i>Will take the values determined by the `oClasses.stripe*`
		 *    options</i>
		 *
		 *  @dtopt Option
		 *  @name DataTable.defaults.stripeClasses
		 *
		 *  @example
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "stripeClasses": [ 'strip1', 'strip2', 'strip3' ]
		 *      } );
		 *    } )
		 */
		"asStripeClasses": null,
	
	
		/**
		 * Enable or disable automatic column width calculation. This can be disabled
		 * as an optimisation (it takes some time to calculate the widths) if the
		 * tables widths are passed in using `columns`.
		 *  @type boolean
		 *  @default true
		 *
		 *  @dtopt Features
		 *  @name DataTable.defaults.autoWidth
		 *
		 *  @example
		 *    $(document).ready( function () {
		 *      $('#example').dataTable( {
		 *        "autoWidth": false
		 *      } );
		 *    } );
		 */
		"bAutoWidth": true,
	
	
		/**
		 * Deferred rendering can provide DataTables with a huge speed boost when you
		 * are using an Ajax or JS data source for the table. This option, when set to
		 * true, will cause DataTables to defer the creation of the table elements for
		 * each row until they are needed for a draw - saving a significant amount of
		 * time.
		 *  @type boolean
		 *  @default false
		 *
		 *  @dtopt Features
		 *  @name DataTable.defaults.deferRender
		 *
		 *  @example
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "ajax": "sources/arrays.txt",
		 *        "deferRender": true
		 *      } );
		 *    } );
		 */
		"bDeferRender": false,
	
	
		/**
		 * Replace a DataTable which matches the given selector and replace it with
		 * one which has the properties of the new initialisation object passed. If no
		 * table matches the selector, then the new DataTable will be constructed as
		 * per normal.
		 *  @type boolean
		 *  @default false
		 *
		 *  @dtopt Options
		 *  @name DataTable.defaults.destroy
		 *
		 *  @example
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "srollY": "200px",
		 *        "paginate": false
		 *      } );
		 *
		 *      // Some time later....
		 *      $('#example').dataTable( {
		 *        "filter": false,
		 *        "destroy": true
		 *      } );
		 *    } );
		 */
		"bDestroy": false,
	
	
		/**
		 * Enable or disable filtering of data. Filtering in DataTables is "smart" in
		 * that it allows the end user to input multiple words (space separated) and
		 * will match a row containing those words, even if not in the order that was
		 * specified (this allow matching across multiple columns). Note that if you
		 * wish to use filtering in DataTables this must remain 'true' - to remove the
		 * default filtering input box and retain filtering abilities, please use
		 * {@link DataTable.defaults.dom}.
		 *  @type boolean
		 *  @default true
		 *
		 *  @dtopt Features
		 *  @name DataTable.defaults.searching
		 *
		 *  @example
		 *    $(document).ready( function () {
		 *      $('#example').dataTable( {
		 *        "searching": false
		 *      } );
		 *    } );
		 */
		"bFilter": true,
	
	
		/**
		 * Enable or disable the table information display. This shows information
		 * about the data that is currently visible on the page, including information
		 * about filtered data if that action is being performed.
		 *  @type boolean
		 *  @default true
		 *
		 *  @dtopt Features
		 *  @name DataTable.defaults.info
		 *
		 *  @example
		 *    $(document).ready( function () {
		 *      $('#example').dataTable( {
		 *        "info": false
		 *      } );
		 *    } );
		 */
		"bInfo": true,
	
	
		/**
		 * Allows the end user to select the size of a formatted page from a select
		 * menu (sizes are 10, 25, 50 and 100). Requires pagination (`paginate`).
		 *  @type boolean
		 *  @default true
		 *
		 *  @dtopt Features
		 *  @name DataTable.defaults.lengthChange
		 *
		 *  @example
		 *    $(document).ready( function () {
		 *      $('#example').dataTable( {
		 *        "lengthChange": false
		 *      } );
		 *    } );
		 */
		"bLengthChange": true,
	
	
		/**
		 * Enable or disable pagination.
		 *  @type boolean
		 *  @default true
		 *
		 *  @dtopt Features
		 *  @name DataTable.defaults.paging
		 *
		 *  @example
		 *    $(document).ready( function () {
		 *      $('#example').dataTable( {
		 *        "paging": false
		 *      } );
		 *    } );
		 */
		"bPaginate": true,
	
	
		/**
		 * Enable or disable the display of a 'processing' indicator when the table is
		 * being processed (e.g. a sort). This is particularly useful for tables with
		 * large amounts of data where it can take a noticeable amount of time to sort
		 * the entries.
		 *  @type boolean
		 *  @default false
		 *
		 *  @dtopt Features
		 *  @name DataTable.defaults.processing
		 *
		 *  @example
		 *    $(document).ready( function () {
		 *      $('#example').dataTable( {
		 *        "processing": true
		 *      } );
		 *    } );
		 */
		"bProcessing": false,
	
	
		/**
		 * Retrieve the DataTables object for the given selector. Note that if the
		 * table has already been initialised, this parameter will cause DataTables
		 * to simply return the object that has already been set up - it will not take
		 * account of any changes you might have made to the initialisation object
		 * passed to DataTables (setting this parameter to true is an acknowledgement
		 * that you understand this). `destroy` can be used to reinitialise a table if
		 * you need.
		 *  @type boolean
		 *  @default false
		 *
		 *  @dtopt Options
		 *  @name DataTable.defaults.retrieve
		 *
		 *  @example
		 *    $(document).ready( function() {
		 *      initTable();
		 *      tableActions();
		 *    } );
		 *
		 *    function initTable ()
		 *    {
		 *      return $('#example').dataTable( {
		 *        "scrollY": "200px",
		 *        "paginate": false,
		 *        "retrieve": true
		 *      } );
		 *    }
		 *
		 *    function tableActions ()
		 *    {
		 *      var table = initTable();
		 *      // perform API operations with oTable
		 *    }
		 */
		"bRetrieve": false,
	
	
		/**
		 * When vertical (y) scrolling is enabled, DataTables will force the height of
		 * the table's viewport to the given height at all times (useful for layout).
		 * However, this can look odd when filtering data down to a small data set,
		 * and the footer is left "floating" further down. This parameter (when
		 * enabled) will cause DataTables to collapse the table's viewport down when
		 * the result set will fit within the given Y height.
		 *  @type boolean
		 *  @default false
		 *
		 *  @dtopt Options
		 *  @name DataTable.defaults.scrollCollapse
		 *
		 *  @example
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "scrollY": "200",
		 *        "scrollCollapse": true
		 *      } );
		 *    } );
		 */
		"bScrollCollapse": false,
	
	
		/**
		 * Configure DataTables to use server-side processing. Note that the
		 * `ajax` parameter must also be given in order to give DataTables a
		 * source to obtain the required data for each draw.
		 *  @type boolean
		 *  @default false
		 *
		 *  @dtopt Features
		 *  @dtopt Server-side
		 *  @name DataTable.defaults.serverSide
		 *
		 *  @example
		 *    $(document).ready( function () {
		 *      $('#example').dataTable( {
		 *        "serverSide": true,
		 *        "ajax": "xhr.php"
		 *      } );
		 *    } );
		 */
		"bServerSide": false,
	
	
		/**
		 * Enable or disable sorting of columns. Sorting of individual columns can be
		 * disabled by the `sortable` option for each column.
		 *  @type boolean
		 *  @default true
		 *
		 *  @dtopt Features
		 *  @name DataTable.defaults.ordering
		 *
		 *  @example
		 *    $(document).ready( function () {
		 *      $('#example').dataTable( {
		 *        "ordering": false
		 *      } );
		 *    } );
		 */
		"bSort": true,
	
	
		/**
		 * Enable or display DataTables' ability to sort multiple columns at the
		 * same time (activated by shift-click by the user).
		 *  @type boolean
		 *  @default true
		 *
		 *  @dtopt Options
		 *  @name DataTable.defaults.orderMulti
		 *
		 *  @example
		 *    // Disable multiple column sorting ability
		 *    $(document).ready( function () {
		 *      $('#example').dataTable( {
		 *        "orderMulti": false
		 *      } );
		 *    } );
		 */
		"bSortMulti": true,
	
	
		/**
		 * Allows control over whether DataTables should use the top (true) unique
		 * cell that is found for a single column, or the bottom (false - default).
		 * This is useful when using complex headers.
		 *  @type boolean
		 *  @default false
		 *
		 *  @dtopt Options
		 *  @name DataTable.defaults.orderCellsTop
		 *
		 *  @example
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "orderCellsTop": true
		 *      } );
		 *    } );
		 */
		"bSortCellsTop": false,
	
	
		/**
		 * Enable or disable the addition of the classes `sorting\_1`, `sorting\_2` and
		 * `sorting\_3` to the columns which are currently being sorted on. This is
		 * presented as a feature switch as it can increase processing time (while
		 * classes are removed and added) so for large data sets you might want to
		 * turn this off.
		 *  @type boolean
		 *  @default true
		 *
		 *  @dtopt Features
		 *  @name DataTable.defaults.orderClasses
		 *
		 *  @example
		 *    $(document).ready( function () {
		 *      $('#example').dataTable( {
		 *        "orderClasses": false
		 *      } );
		 *    } );
		 */
		"bSortClasses": true,
	
	
		/**
		 * Enable or disable state saving. When enabled HTML5 `localStorage` will be
		 * used to save table display information such as pagination information,
		 * display length, filtering and sorting. As such when the end user reloads
		 * the page the display display will match what thy had previously set up.
		 *
		 * Due to the use of `localStorage` the default state saving is not supported
		 * in IE6 or 7. If state saving is required in those browsers, use
		 * `stateSaveCallback` to provide a storage solution such as cookies.
		 *  @type boolean
		 *  @default false
		 *
		 *  @dtopt Features
		 *  @name DataTable.defaults.stateSave
		 *
		 *  @example
		 *    $(document).ready( function () {
		 *      $('#example').dataTable( {
		 *        "stateSave": true
		 *      } );
		 *    } );
		 */
		"bStateSave": false,
	
	
		/**
		 * This function is called when a TR element is created (and all TD child
		 * elements have been inserted), or registered if using a DOM source, allowing
		 * manipulation of the TR element (adding classes etc).
		 *  @type function
		 *  @param {node} row "TR" element for the current row
		 *  @param {array} data Raw data array for this row
		 *  @param {int} dataIndex The index of this row in the internal aoData array
		 *
		 *  @dtopt Callbacks
		 *  @name DataTable.defaults.createdRow
		 *
		 *  @example
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "createdRow": function( row, data, dataIndex ) {
		 *          // Bold the grade for all 'A' grade browsers
		 *          if ( data[4] == "A" )
		 *          {
		 *            $('td:eq(4)', row).html( '<b>A</b>' );
		 *          }
		 *        }
		 *      } );
		 *    } );
		 */
		"fnCreatedRow": null,
	
	
		/**
		 * This function is called on every 'draw' event, and allows you to
		 * dynamically modify any aspect you want about the created DOM.
		 *  @type function
		 *  @param {object} settings DataTables settings object
		 *
		 *  @dtopt Callbacks
		 *  @name DataTable.defaults.drawCallback
		 *
		 *  @example
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "drawCallback": function( settings ) {
		 *          alert( 'DataTables has redrawn the table' );
		 *        }
		 *      } );
		 *    } );
		 */
		"fnDrawCallback": null,
	
	
		/**
		 * Identical to fnHeaderCallback() but for the table footer this function
		 * allows you to modify the table footer on every 'draw' event.
		 *  @type function
		 *  @param {node} foot "TR" element for the footer
		 *  @param {array} data Full table data (as derived from the original HTML)
		 *  @param {int} start Index for the current display starting point in the
		 *    display array
		 *  @param {int} end Index for the current display ending point in the
		 *    display array
		 *  @param {array int} display Index array to translate the visual position
		 *    to the full data array
		 *
		 *  @dtopt Callbacks
		 *  @name DataTable.defaults.footerCallback
		 *
		 *  @example
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "footerCallback": function( tfoot, data, start, end, display ) {
		 *          tfoot.getElementsByTagName('th')[0].innerHTML = "Starting index is "+start;
		 *        }
		 *      } );
		 *    } )
		 */
		"fnFooterCallback": null,
	
	
		/**
		 * When rendering large numbers in the information element for the table
		 * (i.e. "Showing 1 to 10 of 57 entries") DataTables will render large numbers
		 * to have a comma separator for the 'thousands' units (e.g. 1 million is
		 * rendered as "1,000,000") to help readability for the end user. This
		 * function will override the default method DataTables uses.
		 *  @type function
		 *  @member
		 *  @param {int} toFormat number to be formatted
		 *  @returns {string} formatted string for DataTables to show the number
		 *
		 *  @dtopt Callbacks
		 *  @name DataTable.defaults.formatNumber
		 *
		 *  @example
		 *    // Format a number using a single quote for the separator (note that
		 *    // this can also be done with the language.thousands option)
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "formatNumber": function ( toFormat ) {
		 *          return toFormat.toString().replace(
		 *            /\B(?=(\d{3})+(?!\d))/g, "'"
		 *          );
		 *        };
		 *      } );
		 *    } );
		 */
		"fnFormatNumber": function ( toFormat ) {
			return toFormat.toString().replace(
				/\B(?=(\d{3})+(?!\d))/g,
				this.oLanguage.sThousands
			);
		},
	
	
		/**
		 * This function is called on every 'draw' event, and allows you to
		 * dynamically modify the header row. This can be used to calculate and
		 * display useful information about the table.
		 *  @type function
		 *  @param {node} head "TR" element for the header
		 *  @param {array} data Full table data (as derived from the original HTML)
		 *  @param {int} start Index for the current display starting point in the
		 *    display array
		 *  @param {int} end Index for the current display ending point in the
		 *    display array
		 *  @param {array int} display Index array to translate the visual position
		 *    to the full data array
		 *
		 *  @dtopt Callbacks
		 *  @name DataTable.defaults.headerCallback
		 *
		 *  @example
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "fheaderCallback": function( head, data, start, end, display ) {
		 *          head.getElementsByTagName('th')[0].innerHTML = "Displaying "+(end-start)+" records";
		 *        }
		 *      } );
		 *    } )
		 */
		"fnHeaderCallback": null,
	
	
		/**
		 * The information element can be used to convey information about the current
		 * state of the table. Although the internationalisation options presented by
		 * DataTables are quite capable of dealing with most customisations, there may
		 * be times where you wish to customise the string further. This callback
		 * allows you to do exactly that.
		 *  @type function
		 *  @param {object} oSettings DataTables settings object
		 *  @param {int} start Starting position in data for the draw
		 *  @param {int} end End position in data for the draw
		 *  @param {int} max Total number of rows in the table (regardless of
		 *    filtering)
		 *  @param {int} total Total number of rows in the data set, after filtering
		 *  @param {string} pre The string that DataTables has formatted using it's
		 *    own rules
		 *  @returns {string} The string to be displayed in the information element.
		 *
		 *  @dtopt Callbacks
		 *  @name DataTable.defaults.infoCallback
		 *
		 *  @example
		 *    $('#example').dataTable( {
		 *      "infoCallback": function( settings, start, end, max, total, pre ) {
		 *        return start +" to "+ end;
		 *      }
		 *    } );
		 */
		"fnInfoCallback": null,
	
	
		/**
		 * Called when the table has been initialised. Normally DataTables will
		 * initialise sequentially and there will be no need for this function,
		 * however, this does not hold true when using external language information
		 * since that is obtained using an async XHR call.
		 *  @type function
		 *  @param {object} settings DataTables settings object
		 *  @param {object} json The JSON object request from the server - only
		 *    present if client-side Ajax sourced data is used
		 *
		 *  @dtopt Callbacks
		 *  @name DataTable.defaults.initComplete
		 *
		 *  @example
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "initComplete": function(settings, json) {
		 *          alert( 'DataTables has finished its initialisation.' );
		 *        }
		 *      } );
		 *    } )
		 */
		"fnInitComplete": null,
	
	
		/**
		 * Called at the very start of each table draw and can be used to cancel the
		 * draw by returning false, any other return (including undefined) results in
		 * the full draw occurring).
		 *  @type function
		 *  @param {object} settings DataTables settings object
		 *  @returns {boolean} False will cancel the draw, anything else (including no
		 *    return) will allow it to complete.
		 *
		 *  @dtopt Callbacks
		 *  @name DataTable.defaults.preDrawCallback
		 *
		 *  @example
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "preDrawCallback": function( settings ) {
		 *          if ( $('#test').val() == 1 ) {
		 *            return false;
		 *          }
		 *        }
		 *      } );
		 *    } );
		 */
		"fnPreDrawCallback": null,
	
	
		/**
		 * This function allows you to 'post process' each row after it have been
		 * generated for each table draw, but before it is rendered on screen. This
		 * function might be used for setting the row class name etc.
		 *  @type function
		 *  @param {node} row "TR" element for the current row
		 *  @param {array} data Raw data array for this row
		 *  @param {int} displayIndex The display index for the current table draw
		 *  @param {int} displayIndexFull The index of the data in the full list of
		 *    rows (after filtering)
		 *
		 *  @dtopt Callbacks
		 *  @name DataTable.defaults.rowCallback
		 *
		 *  @example
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "rowCallback": function( row, data, displayIndex, displayIndexFull ) {
		 *          // Bold the grade for all 'A' grade browsers
		 *          if ( data[4] == "A" ) {
		 *            $('td:eq(4)', row).html( '<b>A</b>' );
		 *          }
		 *        }
		 *      } );
		 *    } );
		 */
		"fnRowCallback": null,
	
	
		/**
		 * __Deprecated__ The functionality provided by this parameter has now been
		 * superseded by that provided through `ajax`, which should be used instead.
		 *
		 * This parameter allows you to override the default function which obtains
		 * the data from the server so something more suitable for your application.
		 * For example you could use POST data, or pull information from a Gears or
		 * AIR database.
		 *  @type function
		 *  @member
		 *  @param {string} source HTTP source to obtain the data from (`ajax`)
		 *  @param {array} data A key/value pair object containing the data to send
		 *    to the server
		 *  @param {function} callback to be called on completion of the data get
		 *    process that will draw the data on the page.
		 *  @param {object} settings DataTables settings object
		 *
		 *  @dtopt Callbacks
		 *  @dtopt Server-side
		 *  @name DataTable.defaults.serverData
		 *
		 *  @deprecated 1.10. Please use `ajax` for this functionality now.
		 */
		"fnServerData": null,
	
	
		/**
		 * __Deprecated__ The functionality provided by this parameter has now been
		 * superseded by that provided through `ajax`, which should be used instead.
		 *
		 *  It is often useful to send extra data to the server when making an Ajax
		 * request - for example custom filtering information, and this callback
		 * function makes it trivial to send extra information to the server. The
		 * passed in parameter is the data set that has been constructed by
		 * DataTables, and you can add to this or modify it as you require.
		 *  @type function
		 *  @param {array} data Data array (array of objects which are name/value
		 *    pairs) that has been constructed by DataTables and will be sent to the
		 *    server. In the case of Ajax sourced data with server-side processing
		 *    this will be an empty array, for server-side processing there will be a
		 *    significant number of parameters!
		 *  @returns {undefined} Ensure that you modify the data array passed in,
		 *    as this is passed by reference.
		 *
		 *  @dtopt Callbacks
		 *  @dtopt Server-side
		 *  @name DataTable.defaults.serverParams
		 *
		 *  @deprecated 1.10. Please use `ajax` for this functionality now.
		 */
		"fnServerParams": null,
	
	
		/**
		 * Load the table state. With this function you can define from where, and how, the
		 * state of a table is loaded. By default DataTables will load from `localStorage`
		 * but you might wish to use a server-side database or cookies.
		 *  @type function
		 *  @member
		 *  @param {object} settings DataTables settings object
		 *  @param {object} callback Callback that can be executed when done. It
		 *    should be passed the loaded state object.
		 *  @return {object} The DataTables state object to be loaded
		 *
		 *  @dtopt Callbacks
		 *  @name DataTable.defaults.stateLoadCallback
		 *
		 *  @example
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "stateSave": true,
		 *        "stateLoadCallback": function (settings, callback) {
		 *          $.ajax( {
		 *            "url": "/state_load",
		 *            "dataType": "json",
		 *            "success": function (json) {
		 *              callback( json );
		 *            }
		 *          } );
		 *        }
		 *      } );
		 *    } );
		 */
		"fnStateLoadCallback": function ( settings ) {
			try {
				return JSON.parse(
					(settings.iStateDuration === -1 ? sessionStorage : localStorage).getItem(
						'DataTables_'+settings.sInstance+'_'+location.pathname
					)
				);
			} catch (e) {}
		},
	
	
		/**
		 * Callback which allows modification of the saved state prior to loading that state.
		 * This callback is called when the table is loading state from the stored data, but
		 * prior to the settings object being modified by the saved state. Note that for
		 * plug-in authors, you should use the `stateLoadParams` event to load parameters for
		 * a plug-in.
		 *  @type function
		 *  @param {object} settings DataTables settings object
		 *  @param {object} data The state object that is to be loaded
		 *
		 *  @dtopt Callbacks
		 *  @name DataTable.defaults.stateLoadParams
		 *
		 *  @example
		 *    // Remove a saved filter, so filtering is never loaded
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "stateSave": true,
		 *        "stateLoadParams": function (settings, data) {
		 *          data.oSearch.sSearch = "";
		 *        }
		 *      } );
		 *    } );
		 *
		 *  @example
		 *    // Disallow state loading by returning false
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "stateSave": true,
		 *        "stateLoadParams": function (settings, data) {
		 *          return false;
		 *        }
		 *      } );
		 *    } );
		 */
		"fnStateLoadParams": null,
	
	
		/**
		 * Callback that is called when the state has been loaded from the state saving method
		 * and the DataTables settings object has been modified as a result of the loaded state.
		 *  @type function
		 *  @param {object} settings DataTables settings object
		 *  @param {object} data The state object that was loaded
		 *
		 *  @dtopt Callbacks
		 *  @name DataTable.defaults.stateLoaded
		 *
		 *  @example
		 *    // Show an alert with the filtering value that was saved
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "stateSave": true,
		 *        "stateLoaded": function (settings, data) {
		 *          alert( 'Saved filter was: '+data.oSearch.sSearch );
		 *        }
		 *      } );
		 *    } );
		 */
		"fnStateLoaded": null,
	
	
		/**
		 * Save the table state. This function allows you to define where and how the state
		 * information for the table is stored By default DataTables will use `localStorage`
		 * but you might wish to use a server-side database or cookies.
		 *  @type function
		 *  @member
		 *  @param {object} settings DataTables settings object
		 *  @param {object} data The state object to be saved
		 *
		 *  @dtopt Callbacks
		 *  @name DataTable.defaults.stateSaveCallback
		 *
		 *  @example
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "stateSave": true,
		 *        "stateSaveCallback": function (settings, data) {
		 *          // Send an Ajax request to the server with the state object
		 *          $.ajax( {
		 *            "url": "/state_save",
		 *            "data": data,
		 *            "dataType": "json",
		 *            "method": "POST"
		 *            "success": function () {}
		 *          } );
		 *        }
		 *      } );
		 *    } );
		 */
		"fnStateSaveCallback": function ( settings, data ) {
			try {
				(settings.iStateDuration === -1 ? sessionStorage : localStorage).setItem(
					'DataTables_'+settings.sInstance+'_'+location.pathname,
					JSON.stringify( data )
				);
			} catch (e) {}
		},
	
	
		/**
		 * Callback which allows modification of the state to be saved. Called when the table
		 * has changed state a new state save is required. This method allows modification of
		 * the state saving object prior to actually doing the save, including addition or
		 * other state properties or modification. Note that for plug-in authors, you should
		 * use the `stateSaveParams` event to save parameters for a plug-in.
		 *  @type function
		 *  @param {object} settings DataTables settings object
		 *  @param {object} data The state object to be saved
		 *
		 *  @dtopt Callbacks
		 *  @name DataTable.defaults.stateSaveParams
		 *
		 *  @example
		 *    // Remove a saved filter, so filtering is never saved
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "stateSave": true,
		 *        "stateSaveParams": function (settings, data) {
		 *          data.oSearch.sSearch = "";
		 *        }
		 *      } );
		 *    } );
		 */
		"fnStateSaveParams": null,
	
	
		/**
		 * Duration for which the saved state information is considered valid. After this period
		 * has elapsed the state will be returned to the default.
		 * Value is given in seconds.
		 *  @type int
		 *  @default 7200 <i>(2 hours)</i>
		 *
		 *  @dtopt Options
		 *  @name DataTable.defaults.stateDuration
		 *
		 *  @example
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "stateDuration": 60*60*24; // 1 day
		 *      } );
		 *    } )
		 */
		"iStateDuration": 7200,
	
	
		/**
		 * When enabled DataTables will not make a request to the server for the first
		 * page draw - rather it will use the data already on the page (no sorting etc
		 * will be applied to it), thus saving on an XHR at load time. `deferLoading`
		 * is used to indicate that deferred loading is required, but it is also used
		 * to tell DataTables how many records there are in the full table (allowing
		 * the information element and pagination to be displayed correctly). In the case
		 * where a filtering is applied to the table on initial load, this can be
		 * indicated by giving the parameter as an array, where the first element is
		 * the number of records available after filtering and the second element is the
		 * number of records without filtering (allowing the table information element
		 * to be shown correctly).
		 *  @type int | array
		 *  @default null
		 *
		 *  @dtopt Options
		 *  @name DataTable.defaults.deferLoading
		 *
		 *  @example
		 *    // 57 records available in the table, no filtering applied
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "serverSide": true,
		 *        "ajax": "scripts/server_processing.php",
		 *        "deferLoading": 57
		 *      } );
		 *    } );
		 *
		 *  @example
		 *    // 57 records after filtering, 100 without filtering (an initial filter applied)
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "serverSide": true,
		 *        "ajax": "scripts/server_processing.php",
		 *        "deferLoading": [ 57, 100 ],
		 *        "search": {
		 *          "search": "my_filter"
		 *        }
		 *      } );
		 *    } );
		 */
		"iDeferLoading": null,
	
	
		/**
		 * Number of rows to display on a single page when using pagination. If
		 * feature enabled (`lengthChange`) then the end user will be able to override
		 * this to a custom setting using a pop-up menu.
		 *  @type int
		 *  @default 10
		 *
		 *  @dtopt Options
		 *  @name DataTable.defaults.pageLength
		 *
		 *  @example
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "pageLength": 50
		 *      } );
		 *    } )
		 */
		"iDisplayLength": 10,
	
	
		/**
		 * Define the starting point for data display when using DataTables with
		 * pagination. Note that this parameter is the number of records, rather than
		 * the page number, so if you have 10 records per page and want to start on
		 * the third page, it should be "20".
		 *  @type int
		 *  @default 0
		 *
		 *  @dtopt Options
		 *  @name DataTable.defaults.displayStart
		 *
		 *  @example
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "displayStart": 20
		 *      } );
		 *    } )
		 */
		"iDisplayStart": 0,
	
	
		/**
		 * By default DataTables allows keyboard navigation of the table (sorting, paging,
		 * and filtering) by adding a `tabindex` attribute to the required elements. This
		 * allows you to tab through the controls and press the enter key to activate them.
		 * The tabindex is default 0, meaning that the tab follows the flow of the document.
		 * You can overrule this using this parameter if you wish. Use a value of -1 to
		 * disable built-in keyboard navigation.
		 *  @type int
		 *  @default 0
		 *
		 *  @dtopt Options
		 *  @name DataTable.defaults.tabIndex
		 *
		 *  @example
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "tabIndex": 1
		 *      } );
		 *    } );
		 */
		"iTabIndex": 0,
	
	
		/**
		 * Classes that DataTables assigns to the various components and features
		 * that it adds to the HTML table. This allows classes to be configured
		 * during initialisation in addition to through the static
		 * {@link DataTable.ext.oStdClasses} object).
		 *  @namespace
		 *  @name DataTable.defaults.classes
		 */
		"oClasses": {},
	
	
		/**
		 * All strings that DataTables uses in the user interface that it creates
		 * are defined in this object, allowing you to modified them individually or
		 * completely replace them all as required.
		 *  @namespace
		 *  @name DataTable.defaults.language
		 */
		"oLanguage": {
			/**
			 * Strings that are used for WAI-ARIA labels and controls only (these are not
			 * actually visible on the page, but will be read by screenreaders, and thus
			 * must be internationalised as well).
			 *  @namespace
			 *  @name DataTable.defaults.language.aria
			 */
			"oAria": {
				/**
				 * ARIA label that is added to the table headers when the column may be
				 * sorted ascending by activing the column (click or return when focused).
				 * Note that the column header is prefixed to this string.
				 *  @type string
				 *  @default : activate to sort column ascending
				 *
				 *  @dtopt Language
				 *  @name DataTable.defaults.language.aria.sortAscending
				 *
				 *  @example
				 *    $(document).ready( function() {
				 *      $('#example').dataTable( {
				 *        "language": {
				 *          "aria": {
				 *            "sortAscending": " - click/return to sort ascending"
				 *          }
				 *        }
				 *      } );
				 *    } );
				 */
				"sSortAscending": ": activate to sort column ascending",
	
				/**
				 * ARIA label that is added to the table headers when the column may be
				 * sorted descending by activing the column (click or return when focused).
				 * Note that the column header is prefixed to this string.
				 *  @type string
				 *  @default : activate to sort column ascending
				 *
				 *  @dtopt Language
				 *  @name DataTable.defaults.language.aria.sortDescending
				 *
				 *  @example
				 *    $(document).ready( function() {
				 *      $('#example').dataTable( {
				 *        "language": {
				 *          "aria": {
				 *            "sortDescending": " - click/return to sort descending"
				 *          }
				 *        }
				 *      } );
				 *    } );
				 */
				"sSortDescending": ": activate to sort column descending"
			},
	
			/**
			 * Pagination string used by DataTables for the built-in pagination
			 * control types.
			 *  @namespace
			 *  @name DataTable.defaults.language.paginate
			 */
			"oPaginate": {
				/**
				 * Text to use when using the 'full_numbers' type of pagination for the
				 * button to take the user to the first page.
				 *  @type string
				 *  @default First
				 *
				 *  @dtopt Language
				 *  @name DataTable.defaults.language.paginate.first
				 *
				 *  @example
				 *    $(document).ready( function() {
				 *      $('#example').dataTable( {
				 *        "language": {
				 *          "paginate": {
				 *            "first": "First page"
				 *          }
				 *        }
				 *      } );
				 *    } );
				 */
				"sFirst": "First",
	
	
				/**
				 * Text to use when using the 'full_numbers' type of pagination for the
				 * button to take the user to the last page.
				 *  @type string
				 *  @default Last
				 *
				 *  @dtopt Language
				 *  @name DataTable.defaults.language.paginate.last
				 *
				 *  @example
				 *    $(document).ready( function() {
				 *      $('#example').dataTable( {
				 *        "language": {
				 *          "paginate": {
				 *            "last": "Last page"
				 *          }
				 *        }
				 *      } );
				 *    } );
				 */
				"sLast": "Last",
	
	
				/**
				 * Text to use for the 'next' pagination button (to take the user to the
				 * next page).
				 *  @type string
				 *  @default Next
				 *
				 *  @dtopt Language
				 *  @name DataTable.defaults.language.paginate.next
				 *
				 *  @example
				 *    $(document).ready( function() {
				 *      $('#example').dataTable( {
				 *        "language": {
				 *          "paginate": {
				 *            "next": "Next page"
				 *          }
				 *        }
				 *      } );
				 *    } );
				 */
				"sNext": "Next",
	
	
				/**
				 * Text to use for the 'previous' pagination button (to take the user to
				 * the previous page).
				 *  @type string
				 *  @default Previous
				 *
				 *  @dtopt Language
				 *  @name DataTable.defaults.language.paginate.previous
				 *
				 *  @example
				 *    $(document).ready( function() {
				 *      $('#example').dataTable( {
				 *        "language": {
				 *          "paginate": {
				 *            "previous": "Previous page"
				 *          }
				 *        }
				 *      } );
				 *    } );
				 */
				"sPrevious": "Previous"
			},
	
			/**
			 * This string is shown in preference to `zeroRecords` when the table is
			 * empty of data (regardless of filtering). Note that this is an optional
			 * parameter - if it is not given, the value of `zeroRecords` will be used
			 * instead (either the default or given value).
			 *  @type string
			 *  @default No data available in table
			 *
			 *  @dtopt Language
			 *  @name DataTable.defaults.language.emptyTable
			 *
			 *  @example
			 *    $(document).ready( function() {
			 *      $('#example').dataTable( {
			 *        "language": {
			 *          "emptyTable": "No data available in table"
			 *        }
			 *      } );
			 *    } );
			 */
			"sEmptyTable": "No data available in table",
	
	
			/**
			 * This string gives information to the end user about the information
			 * that is current on display on the page. The following tokens can be
			 * used in the string and will be dynamically replaced as the table
			 * display updates. This tokens can be placed anywhere in the string, or
			 * removed as needed by the language requires:
			 *
			 * * `\_START\_` - Display index of the first record on the current page
			 * * `\_END\_` - Display index of the last record on the current page
			 * * `\_TOTAL\_` - Number of records in the table after filtering
			 * * `\_MAX\_` - Number of records in the table without filtering
			 * * `\_PAGE\_` - Current page number
			 * * `\_PAGES\_` - Total number of pages of data in the table
			 *
			 *  @type string
			 *  @default Showing _START_ to _END_ of _TOTAL_ entries
			 *
			 *  @dtopt Language
			 *  @name DataTable.defaults.language.info
			 *
			 *  @example
			 *    $(document).ready( function() {
			 *      $('#example').dataTable( {
			 *        "language": {
			 *          "info": "Showing page _PAGE_ of _PAGES_"
			 *        }
			 *      } );
			 *    } );
			 */
			"sInfo": "Showing _START_ to _END_ of _TOTAL_ entries",
	
	
			/**
			 * Display information string for when the table is empty. Typically the
			 * format of this string should match `info`.
			 *  @type string
			 *  @default Showing 0 to 0 of 0 entries
			 *
			 *  @dtopt Language
			 *  @name DataTable.defaults.language.infoEmpty
			 *
			 *  @example
			 *    $(document).ready( function() {
			 *      $('#example').dataTable( {
			 *        "language": {
			 *          "infoEmpty": "No entries to show"
			 *        }
			 *      } );
			 *    } );
			 */
			"sInfoEmpty": "Showing 0 to 0 of 0 entries",
	
	
			/**
			 * When a user filters the information in a table, this string is appended
			 * to the information (`info`) to give an idea of how strong the filtering
			 * is. The variable _MAX_ is dynamically updated.
			 *  @type string
			 *  @default (filtered from _MAX_ total entries)
			 *
			 *  @dtopt Language
			 *  @name DataTable.defaults.language.infoFiltered
			 *
			 *  @example
			 *    $(document).ready( function() {
			 *      $('#example').dataTable( {
			 *        "language": {
			 *          "infoFiltered": " - filtering from _MAX_ records"
			 *        }
			 *      } );
			 *    } );
			 */
			"sInfoFiltered": "(filtered from _MAX_ total entries)",
	
	
			/**
			 * If can be useful to append extra information to the info string at times,
			 * and this variable does exactly that. This information will be appended to
			 * the `info` (`infoEmpty` and `infoFiltered` in whatever combination they are
			 * being used) at all times.
			 *  @type string
			 *  @default <i>Empty string</i>
			 *
			 *  @dtopt Language
			 *  @name DataTable.defaults.language.infoPostFix
			 *
			 *  @example
			 *    $(document).ready( function() {
			 *      $('#example').dataTable( {
			 *        "language": {
			 *          "infoPostFix": "All records shown are derived from real information."
			 *        }
			 *      } );
			 *    } );
			 */
			"sInfoPostFix": "",
	
	
			/**
			 * This decimal place operator is a little different from the other
			 * language options since DataTables doesn't output floating point
			 * numbers, so it won't ever use this for display of a number. Rather,
			 * what this parameter does is modify the sort methods of the table so
			 * that numbers which are in a format which has a character other than
			 * a period (`.`) as a decimal place will be sorted numerically.
			 *
			 * Note that numbers with different decimal places cannot be shown in
			 * the same table and still be sortable, the table must be consistent.
			 * However, multiple different tables on the page can use different
			 * decimal place characters.
			 *  @type string
			 *  @default 
			 *
			 *  @dtopt Language
			 *  @name DataTable.defaults.language.decimal
			 *
			 *  @example
			 *    $(document).ready( function() {
			 *      $('#example').dataTable( {
			 *        "language": {
			 *          "decimal": ","
			 *          "thousands": "."
			 *        }
			 *      } );
			 *    } );
			 */
			"sDecimal": "",
	
	
			/**
			 * DataTables has a build in number formatter (`formatNumber`) which is
			 * used to format large numbers that are used in the table information.
			 * By default a comma is used, but this can be trivially changed to any
			 * character you wish with this parameter.
			 *  @type string
			 *  @default ,
			 *
			 *  @dtopt Language
			 *  @name DataTable.defaults.language.thousands
			 *
			 *  @example
			 *    $(document).ready( function() {
			 *      $('#example').dataTable( {
			 *        "language": {
			 *          "thousands": "'"
			 *        }
			 *      } );
			 *    } );
			 */
			"sThousands": ",",
	
	
			/**
			 * Detail the action that will be taken when the drop down menu for the
			 * pagination length option is changed. The '_MENU_' variable is replaced
			 * with a default select list of 10, 25, 50 and 100, and can be replaced
			 * with a custom select box if required.
			 *  @type string
			 *  @default Show _MENU_ entries
			 *
			 *  @dtopt Language
			 *  @name DataTable.defaults.language.lengthMenu
			 *
			 *  @example
			 *    // Language change only
			 *    $(document).ready( function() {
			 *      $('#example').dataTable( {
			 *        "language": {
			 *          "lengthMenu": "Display _MENU_ records"
			 *        }
			 *      } );
			 *    } );
			 *
			 *  @example
			 *    // Language and options change
			 *    $(document).ready( function() {
			 *      $('#example').dataTable( {
			 *        "language": {
			 *          "lengthMenu": 'Display <select>'+
			 *            '<option value="10">10</option>'+
			 *            '<option value="20">20</option>'+
			 *            '<option value="30">30</option>'+
			 *            '<option value="40">40</option>'+
			 *            '<option value="50">50</option>'+
			 *            '<option value="-1">All</option>'+
			 *            '</select> records'
			 *        }
			 *      } );
			 *    } );
			 */
			"sLengthMenu": "Show _MENU_ entries",
	
	
			/**
			 * When using Ajax sourced data and during the first draw when DataTables is
			 * gathering the data, this message is shown in an empty row in the table to
			 * indicate to the end user the the data is being loaded. Note that this
			 * parameter is not used when loading data by server-side processing, just
			 * Ajax sourced data with client-side processing.
			 *  @type string
			 *  @default Loading...
			 *
			 *  @dtopt Language
			 *  @name DataTable.defaults.language.loadingRecords
			 *
			 *  @example
			 *    $(document).ready( function() {
			 *      $('#example').dataTable( {
			 *        "language": {
			 *          "loadingRecords": "Please wait - loading..."
			 *        }
			 *      } );
			 *    } );
			 */
			"sLoadingRecords": "Loading...",
	
	
			/**
			 * Text which is displayed when the table is processing a user action
			 * (usually a sort command or similar).
			 *  @type string
			 *  @default Processing...
			 *
			 *  @dtopt Language
			 *  @name DataTable.defaults.language.processing
			 *
			 *  @example
			 *    $(document).ready( function() {
			 *      $('#example').dataTable( {
			 *        "language": {
			 *          "processing": "DataTables is currently busy"
			 *        }
			 *      } );
			 *    } );
			 */
			"sProcessing": "Processing...",
	
	
			/**
			 * Details the actions that will be taken when the user types into the
			 * filtering input text box. The variable "_INPUT_", if used in the string,
			 * is replaced with the HTML text box for the filtering input allowing
			 * control over where it appears in the string. If "_INPUT_" is not given
			 * then the input box is appended to the string automatically.
			 *  @type string
			 *  @default Search:
			 *
			 *  @dtopt Language
			 *  @name DataTable.defaults.language.search
			 *
			 *  @example
			 *    // Input text box will be appended at the end automatically
			 *    $(document).ready( function() {
			 *      $('#example').dataTable( {
			 *        "language": {
			 *          "search": "Filter records:"
			 *        }
			 *      } );
			 *    } );
			 *
			 *  @example
			 *    // Specify where the filter should appear
			 *    $(document).ready( function() {
			 *      $('#example').dataTable( {
			 *        "language": {
			 *          "search": "Apply filter _INPUT_ to table"
			 *        }
			 *      } );
			 *    } );
			 */
			"sSearch": "Search:",
	
	
			/**
			 * Assign a `placeholder` attribute to the search `input` element
			 *  @type string
			 *  @default 
			 *
			 *  @dtopt Language
			 *  @name DataTable.defaults.language.searchPlaceholder
			 */
			"sSearchPlaceholder": "",
	
	
			/**
			 * All of the language information can be stored in a file on the
			 * server-side, which DataTables will look up if this parameter is passed.
			 * It must store the URL of the language file, which is in a JSON format,
			 * and the object has the same properties as the oLanguage object in the
			 * initialiser object (i.e. the above parameters). Please refer to one of
			 * the example language files to see how this works in action.
			 *  @type string
			 *  @default <i>Empty string - i.e. disabled</i>
			 *
			 *  @dtopt Language
			 *  @name DataTable.defaults.language.url
			 *
			 *  @example
			 *    $(document).ready( function() {
			 *      $('#example').dataTable( {
			 *        "language": {
			 *          "url": "http://www.sprymedia.co.uk/dataTables/lang.txt"
			 *        }
			 *      } );
			 *    } );
			 */
			"sUrl": "",
	
	
			/**
			 * Text shown inside the table records when the is no information to be
			 * displayed after filtering. `emptyTable` is shown when there is simply no
			 * information in the table at all (regardless of filtering).
			 *  @type string
			 *  @default No matching records found
			 *
			 *  @dtopt Language
			 *  @name DataTable.defaults.language.zeroRecords
			 *
			 *  @example
			 *    $(document).ready( function() {
			 *      $('#example').dataTable( {
			 *        "language": {
			 *          "zeroRecords": "No records to display"
			 *        }
			 *      } );
			 *    } );
			 */
			"sZeroRecords": "No matching records found"
		},
	
	
		/**
		 * This parameter allows you to have define the global filtering state at
		 * initialisation time. As an object the `search` parameter must be
		 * defined, but all other parameters are optional. When `regex` is true,
		 * the search string will be treated as a regular expression, when false
		 * (default) it will be treated as a straight string. When `smart`
		 * DataTables will use it's smart filtering methods (to word match at
		 * any point in the data), when false this will not be done.
		 *  @namespace
		 *  @extends DataTable.models.oSearch
		 *
		 *  @dtopt Options
		 *  @name DataTable.defaults.search
		 *
		 *  @example
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "search": {"search": "Initial search"}
		 *      } );
		 *    } )
		 */
		"oSearch": $.extend( {}, DataTable.models.oSearch ),
	
	
		/**
		 * __Deprecated__ The functionality provided by this parameter has now been
		 * superseded by that provided through `ajax`, which should be used instead.
		 *
		 * By default DataTables will look for the property `data` (or `aaData` for
		 * compatibility with DataTables 1.9-) when obtaining data from an Ajax
		 * source or for server-side processing - this parameter allows that
		 * property to be changed. You can use Javascript dotted object notation to
		 * get a data source for multiple levels of nesting.
		 *  @type string
		 *  @default data
		 *
		 *  @dtopt Options
		 *  @dtopt Server-side
		 *  @name DataTable.defaults.ajaxDataProp
		 *
		 *  @deprecated 1.10. Please use `ajax` for this functionality now.
		 */
		"sAjaxDataProp": "data",
	
	
		/**
		 * __Deprecated__ The functionality provided by this parameter has now been
		 * superseded by that provided through `ajax`, which should be used instead.
		 *
		 * You can instruct DataTables to load data from an external
		 * source using this parameter (use aData if you want to pass data in you
		 * already have). Simply provide a url a JSON object can be obtained from.
		 *  @type string
		 *  @default null
		 *
		 *  @dtopt Options
		 *  @dtopt Server-side
		 *  @name DataTable.defaults.ajaxSource
		 *
		 *  @deprecated 1.10. Please use `ajax` for this functionality now.
		 */
		"sAjaxSource": null,
	
	
		/**
		 * This initialisation variable allows you to specify exactly where in the
		 * DOM you want DataTables to inject the various controls it adds to the page
		 * (for example you might want the pagination controls at the top of the
		 * table). DIV elements (with or without a custom class) can also be added to
		 * aid styling. The follow syntax is used:
		 *   <ul>
		 *     <li>The following options are allowed:
		 *       <ul>
		 *         <li>'l' - Length changing</li>
		 *         <li>'f' - Filtering input</li>
		 *         <li>'t' - The table!</li>
		 *         <li>'i' - Information</li>
		 *         <li>'p' - Pagination</li>
		 *         <li>'r' - pRocessing</li>
		 *       </ul>
		 *     </li>
		 *     <li>The following constants are allowed:
		 *       <ul>
		 *         <li>'H' - jQueryUI theme "header" classes ('fg-toolbar ui-widget-header ui-corner-tl ui-corner-tr ui-helper-clearfix')</li>
		 *         <li>'F' - jQueryUI theme "footer" classes ('fg-toolbar ui-widget-header ui-corner-bl ui-corner-br ui-helper-clearfix')</li>
		 *       </ul>
		 *     </li>
		 *     <li>The following syntax is expected:
		 *       <ul>
		 *         <li>'&lt;' and '&gt;' - div elements</li>
		 *         <li>'&lt;"class" and '&gt;' - div with a class</li>
		 *         <li>'&lt;"#id" and '&gt;' - div with an ID</li>
		 *       </ul>
		 *     </li>
		 *     <li>Examples:
		 *       <ul>
		 *         <li>'&lt;"wrapper"flipt&gt;'</li>
		 *         <li>'&lt;lf&lt;t&gt;ip&gt;'</li>
		 *       </ul>
		 *     </li>
		 *   </ul>
		 *  @type string
		 *  @default lfrtip <i>(when `jQueryUI` is false)</i> <b>or</b>
		 *    <"H"lfr>t<"F"ip> <i>(when `jQueryUI` is true)</i>
		 *
		 *  @dtopt Options
		 *  @name DataTable.defaults.dom
		 *
		 *  @example
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "dom": '&lt;"top"i&gt;rt&lt;"bottom"flp&gt;&lt;"clear"&gt;'
		 *      } );
		 *    } );
		 */
		"sDom": "lfrtip",
	
	
		/**
		 * Search delay option. This will throttle full table searches that use the
		 * DataTables provided search input element (it does not effect calls to
		 * `dt-api search()`, providing a delay before the search is made.
		 *  @type integer
		 *  @default 0
		 *
		 *  @dtopt Options
		 *  @name DataTable.defaults.searchDelay
		 *
		 *  @example
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "searchDelay": 200
		 *      } );
		 *    } )
		 */
		"searchDelay": null,
	
	
		/**
		 * DataTables features six different built-in options for the buttons to
		 * display for pagination control:
		 *
		 * * `numbers` - Page number buttons only
		 * * `simple` - 'Previous' and 'Next' buttons only
		 * * 'simple_numbers` - 'Previous' and 'Next' buttons, plus page numbers
		 * * `full` - 'First', 'Previous', 'Next' and 'Last' buttons
		 * * `full_numbers` - 'First', 'Previous', 'Next' and 'Last' buttons, plus page numbers
		 * * `first_last_numbers` - 'First' and 'Last' buttons, plus page numbers
		 *  
		 * Further methods can be added using {@link DataTable.ext.oPagination}.
		 *  @type string
		 *  @default simple_numbers
		 *
		 *  @dtopt Options
		 *  @name DataTable.defaults.pagingType
		 *
		 *  @example
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "pagingType": "full_numbers"
		 *      } );
		 *    } )
		 */
		"sPaginationType": "simple_numbers",
	
	
		/**
		 * Enable horizontal scrolling. When a table is too wide to fit into a
		 * certain layout, or you have a large number of columns in the table, you
		 * can enable x-scrolling to show the table in a viewport, which can be
		 * scrolled. This property can be `true` which will allow the table to
		 * scroll horizontally when needed, or any CSS unit, or a number (in which
		 * case it will be treated as a pixel measurement). Setting as simply `true`
		 * is recommended.
		 *  @type boolean|string
		 *  @default <i>blank string - i.e. disabled</i>
		 *
		 *  @dtopt Features
		 *  @name DataTable.defaults.scrollX
		 *
		 *  @example
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "scrollX": true,
		 *        "scrollCollapse": true
		 *      } );
		 *    } );
		 */
		"sScrollX": "",
	
	
		/**
		 * This property can be used to force a DataTable to use more width than it
		 * might otherwise do when x-scrolling is enabled. For example if you have a
		 * table which requires to be well spaced, this parameter is useful for
		 * "over-sizing" the table, and thus forcing scrolling. This property can by
		 * any CSS unit, or a number (in which case it will be treated as a pixel
		 * measurement).
		 *  @type string
		 *  @default <i>blank string - i.e. disabled</i>
		 *
		 *  @dtopt Options
		 *  @name DataTable.defaults.scrollXInner
		 *
		 *  @example
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "scrollX": "100%",
		 *        "scrollXInner": "110%"
		 *      } );
		 *    } );
		 */
		"sScrollXInner": "",
	
	
		/**
		 * Enable vertical scrolling. Vertical scrolling will constrain the DataTable
		 * to the given height, and enable scrolling for any data which overflows the
		 * current viewport. This can be used as an alternative to paging to display
		 * a lot of data in a small area (although paging and scrolling can both be
		 * enabled at the same time). This property can be any CSS unit, or a number
		 * (in which case it will be treated as a pixel measurement).
		 *  @type string
		 *  @default <i>blank string - i.e. disabled</i>
		 *
		 *  @dtopt Features
		 *  @name DataTable.defaults.scrollY
		 *
		 *  @example
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "scrollY": "200px",
		 *        "paginate": false
		 *      } );
		 *    } );
		 */
		"sScrollY": "",
	
	
		/**
		 * __Deprecated__ The functionality provided by this parameter has now been
		 * superseded by that provided through `ajax`, which should be used instead.
		 *
		 * Set the HTTP method that is used to make the Ajax call for server-side
		 * processing or Ajax sourced data.
		 *  @type string
		 *  @default GET
		 *
		 *  @dtopt Options
		 *  @dtopt Server-side
		 *  @name DataTable.defaults.serverMethod
		 *
		 *  @deprecated 1.10. Please use `ajax` for this functionality now.
		 */
		"sServerMethod": "GET",
	
	
		/**
		 * DataTables makes use of renderers when displaying HTML elements for
		 * a table. These renderers can be added or modified by plug-ins to
		 * generate suitable mark-up for a site. For example the Bootstrap
		 * integration plug-in for DataTables uses a paging button renderer to
		 * display pagination buttons in the mark-up required by Bootstrap.
		 *
		 * For further information about the renderers available see
		 * DataTable.ext.renderer
		 *  @type string|object
		 *  @default null
		 *
		 *  @name DataTable.defaults.renderer
		 *
		 */
		"renderer": null,
	
	
		/**
		 * Set the data property name that DataTables should use to get a row's id
		 * to set as the `id` property in the node.
		 *  @type string
		 *  @default DT_RowId
		 *
		 *  @name DataTable.defaults.rowId
		 */
		"rowId": "DT_RowId"
	};
	
	_fnHungarianMap( DataTable.defaults );
	
	
	
	/*
	 * Developer note - See note in model.defaults.js about the use of Hungarian
	 * notation and camel case.
	 */
	
	/**
	 * Column options that can be given to DataTables at initialisation time.
	 *  @namespace
	 */
	DataTable.defaults.column = {
		/**
		 * Define which column(s) an order will occur on for this column. This
		 * allows a column's ordering to take multiple columns into account when
		 * doing a sort or use the data from a different column. For example first
		 * name / last name columns make sense to do a multi-column sort over the
		 * two columns.
		 *  @type array|int
		 *  @default null <i>Takes the value of the column index automatically</i>
		 *
		 *  @name DataTable.defaults.column.orderData
		 *  @dtopt Columns
		 *
		 *  @example
		 *    // Using `columnDefs`
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "columnDefs": [
		 *          { "orderData": [ 0, 1 ], "targets": [ 0 ] },
		 *          { "orderData": [ 1, 0 ], "targets": [ 1 ] },
		 *          { "orderData": 2, "targets": [ 2 ] }
		 *        ]
		 *      } );
		 *    } );
		 *
		 *  @example
		 *    // Using `columns`
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "columns": [
		 *          { "orderData": [ 0, 1 ] },
		 *          { "orderData": [ 1, 0 ] },
		 *          { "orderData": 2 },
		 *          null,
		 *          null
		 *        ]
		 *      } );
		 *    } );
		 */
		"aDataSort": null,
		"iDataSort": -1,
	
	
		/**
		 * You can control the default ordering direction, and even alter the
		 * behaviour of the sort handler (i.e. only allow ascending ordering etc)
		 * using this parameter.
		 *  @type array
		 *  @default [ 'asc', 'desc' ]
		 *
		 *  @name DataTable.defaults.column.orderSequence
		 *  @dtopt Columns
		 *
		 *  @example
		 *    // Using `columnDefs`
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "columnDefs": [
		 *          { "orderSequence": [ "asc" ], "targets": [ 1 ] },
		 *          { "orderSequence": [ "desc", "asc", "asc" ], "targets": [ 2 ] },
		 *          { "orderSequence": [ "desc" ], "targets": [ 3 ] }
		 *        ]
		 *      } );
		 *    } );
		 *
		 *  @example
		 *    // Using `columns`
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "columns": [
		 *          null,
		 *          { "orderSequence": [ "asc" ] },
		 *          { "orderSequence": [ "desc", "asc", "asc" ] },
		 *          { "orderSequence": [ "desc" ] },
		 *          null
		 *        ]
		 *      } );
		 *    } );
		 */
		"asSorting": [ 'asc', 'desc' ],
	
	
		/**
		 * Enable or disable filtering on the data in this column.
		 *  @type boolean
		 *  @default true
		 *
		 *  @name DataTable.defaults.column.searchable
		 *  @dtopt Columns
		 *
		 *  @example
		 *    // Using `columnDefs`
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "columnDefs": [
		 *          { "searchable": false, "targets": [ 0 ] }
		 *        ] } );
		 *    } );
		 *
		 *  @example
		 *    // Using `columns`
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "columns": [
		 *          { "searchable": false },
		 *          null,
		 *          null,
		 *          null,
		 *          null
		 *        ] } );
		 *    } );
		 */
		"bSearchable": true,
	
	
		/**
		 * Enable or disable ordering on this column.
		 *  @type boolean
		 *  @default true
		 *
		 *  @name DataTable.defaults.column.orderable
		 *  @dtopt Columns
		 *
		 *  @example
		 *    // Using `columnDefs`
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "columnDefs": [
		 *          { "orderable": false, "targets": [ 0 ] }
		 *        ] } );
		 *    } );
		 *
		 *  @example
		 *    // Using `columns`
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "columns": [
		 *          { "orderable": false },
		 *          null,
		 *          null,
		 *          null,
		 *          null
		 *        ] } );
		 *    } );
		 */
		"bSortable": true,
	
	
		/**
		 * Enable or disable the display of this column.
		 *  @type boolean
		 *  @default true
		 *
		 *  @name DataTable.defaults.column.visible
		 *  @dtopt Columns
		 *
		 *  @example
		 *    // Using `columnDefs`
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "columnDefs": [
		 *          { "visible": false, "targets": [ 0 ] }
		 *        ] } );
		 *    } );
		 *
		 *  @example
		 *    // Using `columns`
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "columns": [
		 *          { "visible": false },
		 *          null,
		 *          null,
		 *          null,
		 *          null
		 *        ] } );
		 *    } );
		 */
		"bVisible": true,
	
	
		/**
		 * Developer definable function that is called whenever a cell is created (Ajax source,
		 * etc) or processed for input (DOM source). This can be used as a compliment to mRender
		 * allowing you to modify the DOM element (add background colour for example) when the
		 * element is available.
		 *  @type function
		 *  @param {element} td The TD node that has been created
		 *  @param {*} cellData The Data for the cell
		 *  @param {array|object} rowData The data for the whole row
		 *  @param {int} row The row index for the aoData data store
		 *  @param {int} col The column index for aoColumns
		 *
		 *  @name DataTable.defaults.column.createdCell
		 *  @dtopt Columns
		 *
		 *  @example
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "columnDefs": [ {
		 *          "targets": [3],
		 *          "createdCell": function (td, cellData, rowData, row, col) {
		 *            if ( cellData == "1.7" ) {
		 *              $(td).css('color', 'blue')
		 *            }
		 *          }
		 *        } ]
		 *      });
		 *    } );
		 */
		"fnCreatedCell": null,
	
	
		/**
		 * This parameter has been replaced by `data` in DataTables to ensure naming
		 * consistency. `dataProp` can still be used, as there is backwards
		 * compatibility in DataTables for this option, but it is strongly
		 * recommended that you use `data` in preference to `dataProp`.
		 *  @name DataTable.defaults.column.dataProp
		 */
	
	
		/**
		 * This property can be used to read data from any data source property,
		 * including deeply nested objects / properties. `data` can be given in a
		 * number of different ways which effect its behaviour:
		 *
		 * * `integer` - treated as an array index for the data source. This is the
		 *   default that DataTables uses (incrementally increased for each column).
		 * * `string` - read an object property from the data source. There are
		 *   three 'special' options that can be used in the string to alter how
		 *   DataTables reads the data from the source object:
		 *    * `.` - Dotted Javascript notation. Just as you use a `.` in
		 *      Javascript to read from nested objects, so to can the options
		 *      specified in `data`. For example: `browser.version` or
		 *      `browser.name`. If your object parameter name contains a period, use
		 *      `\\` to escape it - i.e. `first\\.name`.
		 *    * `[]` - Array notation. DataTables can automatically combine data
		 *      from and array source, joining the data with the characters provided
		 *      between the two brackets. For example: `name[, ]` would provide a
		 *      comma-space separated list from the source array. If no characters
		 *      are provided between the brackets, the original array source is
		 *      returned.
		 *    * `()` - Function notation. Adding `()` to the end of a parameter will
		 *      execute a function of the name given. For example: `browser()` for a
		 *      simple function on the data source, `browser.version()` for a
		 *      function in a nested property or even `browser().version` to get an
		 *      object property if the function called returns an object. Note that
		 *      function notation is recommended for use in `render` rather than
		 *      `data` as it is much simpler to use as a renderer.
		 * * `null` - use the original data source for the row rather than plucking
		 *   data directly from it. This action has effects on two other
		 *   initialisation options:
		 *    * `defaultContent` - When null is given as the `data` option and
		 *      `defaultContent` is specified for the column, the value defined by
		 *      `defaultContent` will be used for the cell.
		 *    * `render` - When null is used for the `data` option and the `render`
		 *      option is specified for the column, the whole data source for the
		 *      row is used for the renderer.
		 * * `function` - the function given will be executed whenever DataTables
		 *   needs to set or get the data for a cell in the column. The function
		 *   takes three parameters:
		 *    * Parameters:
		 *      * `{array|object}` The data source for the row
		 *      * `{string}` The type call data requested - this will be 'set' when
		 *        setting data or 'filter', 'display', 'type', 'sort' or undefined
		 *        when gathering data. Note that when `undefined` is given for the
		 *        type DataTables expects to get the raw data for the object back<
		 *      * `{*}` Data to set when the second parameter is 'set'.
		 *    * Return:
		 *      * The return value from the function is not required when 'set' is
		 *        the type of call, but otherwise the return is what will be used
		 *        for the data requested.
		 *
		 * Note that `data` is a getter and setter option. If you just require
		 * formatting of data for output, you will likely want to use `render` which
		 * is simply a getter and thus simpler to use.
		 *
		 * Note that prior to DataTables 1.9.2 `data` was called `mDataProp`. The
		 * name change reflects the flexibility of this property and is consistent
		 * with the naming of mRender. If 'mDataProp' is given, then it will still
		 * be used by DataTables, as it automatically maps the old name to the new
		 * if required.
		 *
		 *  @type string|int|function|null
		 *  @default null <i>Use automatically calculated column index</i>
		 *
		 *  @name DataTable.defaults.column.data
		 *  @dtopt Columns
		 *
		 *  @example
		 *    // Read table data from objects
		 *    // JSON structure for each row:
		 *    //   {
		 *    //      "engine": {value},
		 *    //      "browser": {value},
		 *    //      "platform": {value},
		 *    //      "version": {value},
		 *    //      "grade": {value}
		 *    //   }
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "ajaxSource": "sources/objects.txt",
		 *        "columns": [
		 *          { "data": "engine" },
		 *          { "data": "browser" },
		 *          { "data": "platform" },
		 *          { "data": "version" },
		 *          { "data": "grade" }
		 *        ]
		 *      } );
		 *    } );
		 *
		 *  @example
		 *    // Read information from deeply nested objects
		 *    // JSON structure for each row:
		 *    //   {
		 *    //      "engine": {value},
		 *    //      "browser": {value},
		 *    //      "platform": {
		 *    //         "inner": {value}
		 *    //      },
		 *    //      "details": [
		 *    //         {value}, {value}
		 *    //      ]
		 *    //   }
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "ajaxSource": "sources/deep.txt",
		 *        "columns": [
		 *          { "data": "engine" },
		 *          { "data": "browser" },
		 *          { "data": "platform.inner" },
		 *          { "data": "platform.details.0" },
		 *          { "data": "platform.details.1" }
		 *        ]
		 *      } );
		 *    } );
		 *
		 *  @example
		 *    // Using `data` as a function to provide different information for
		 *    // sorting, filtering and display. In this case, currency (price)
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "columnDefs": [ {
		 *          "targets": [ 0 ],
		 *          "data": function ( source, type, val ) {
		 *            if (type === 'set') {
		 *              source.price = val;
		 *              // Store the computed dislay and filter values for efficiency
		 *              source.price_display = val=="" ? "" : "$"+numberFormat(val);
		 *              source.price_filter  = val=="" ? "" : "$"+numberFormat(val)+" "+val;
		 *              return;
		 *            }
		 *            else if (type === 'display') {
		 *              return source.price_display;
		 *            }
		 *            else if (type === 'filter') {
		 *              return source.price_filter;
		 *            }
		 *            // 'sort', 'type' and undefined all just use the integer
		 *            return source.price;
		 *          }
		 *        } ]
		 *      } );
		 *    } );
		 *
		 *  @example
		 *    // Using default content
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "columnDefs": [ {
		 *          "targets": [ 0 ],
		 *          "data": null,
		 *          "defaultContent": "Click to edit"
		 *        } ]
		 *      } );
		 *    } );
		 *
		 *  @example
		 *    // Using array notation - outputting a list from an array
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "columnDefs": [ {
		 *          "targets": [ 0 ],
		 *          "data": "name[, ]"
		 *        } ]
		 *      } );
		 *    } );
		 *
		 */
		"mData": null,
	
	
		/**
		 * This property is the rendering partner to `data` and it is suggested that
		 * when you want to manipulate data for display (including filtering,
		 * sorting etc) without altering the underlying data for the table, use this
		 * property. `render` can be considered to be the the read only companion to
		 * `data` which is read / write (then as such more complex). Like `data`
		 * this option can be given in a number of different ways to effect its
		 * behaviour:
		 *
		 * * `integer` - treated as an array index for the data source. This is the
		 *   default that DataTables uses (incrementally increased for each column).
		 * * `string` - read an object property from the data source. There are
		 *   three 'special' options that can be used in the string to alter how
		 *   DataTables reads the data from the source object:
		 *    * `.` - Dotted Javascript notation. Just as you use a `.` in
		 *      Javascript to read from nested objects, so to can the options
		 *      specified in `data`. For example: `browser.version` or
		 *      `browser.name`. If your object parameter name contains a period, use
		 *      `\\` to escape it - i.e. `first\\.name`.
		 *    * `[]` - Array notation. DataTables can automatically combine data
		 *      from and array source, joining the data with the characters provided
		 *      between the two brackets. For example: `name[, ]` would provide a
		 *      comma-space separated list from the source array. If no characters
		 *      are provided between the brackets, the original array source is
		 *      returned.
		 *    * `()` - Function notation. Adding `()` to the end of a parameter will
		 *      execute a function of the name given. For example: `browser()` for a
		 *      simple function on the data source, `browser.version()` for a
		 *      function in a nested property or even `browser().version` to get an
		 *      object property if the function called returns an object.
		 * * `object` - use different data for the different data types requested by
		 *   DataTables ('filter', 'display', 'type' or 'sort'). The property names
		 *   of the object is the data type the property refers to and the value can
		 *   defined using an integer, string or function using the same rules as
		 *   `render` normally does. Note that an `_` option _must_ be specified.
		 *   This is the default value to use if you haven't specified a value for
		 *   the data type requested by DataTables.
		 * * `function` - the function given will be executed whenever DataTables
		 *   needs to set or get the data for a cell in the column. The function
		 *   takes three parameters:
		 *    * Parameters:
		 *      * {array|object} The data source for the row (based on `data`)
		 *      * {string} The type call data requested - this will be 'filter',
		 *        'display', 'type' or 'sort'.
		 *      * {array|object} The full data source for the row (not based on
		 *        `data`)
		 *    * Return:
		 *      * The return value from the function is what will be used for the
		 *        data requested.
		 *
		 *  @type string|int|function|object|null
		 *  @default null Use the data source value.
		 *
		 *  @name DataTable.defaults.column.render
		 *  @dtopt Columns
		 *
		 *  @example
		 *    // Create a comma separated list from an array of objects
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "ajaxSource": "sources/deep.txt",
		 *        "columns": [
		 *          { "data": "engine" },
		 *          { "data": "browser" },
		 *          {
		 *            "data": "platform",
		 *            "render": "[, ].name"
		 *          }
		 *        ]
		 *      } );
		 *    } );
		 *
		 *  @example
		 *    // Execute a function to obtain data
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "columnDefs": [ {
		 *          "targets": [ 0 ],
		 *          "data": null, // Use the full data source object for the renderer's source
		 *          "render": "browserName()"
		 *        } ]
		 *      } );
		 *    } );
		 *
		 *  @example
		 *    // As an object, extracting different data for the different types
		 *    // This would be used with a data source such as:
		 *    //   { "phone": 5552368, "phone_filter": "5552368 555-2368", "phone_display": "555-2368" }
		 *    // Here the `phone` integer is used for sorting and type detection, while `phone_filter`
		 *    // (which has both forms) is used for filtering for if a user inputs either format, while
		 *    // the formatted phone number is the one that is shown in the table.
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "columnDefs": [ {
		 *          "targets": [ 0 ],
		 *          "data": null, // Use the full data source object for the renderer's source
		 *          "render": {
		 *            "_": "phone",
		 *            "filter": "phone_filter",
		 *            "display": "phone_display"
		 *          }
		 *        } ]
		 *      } );
		 *    } );
		 *
		 *  @example
		 *    // Use as a function to create a link from the data source
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "columnDefs": [ {
		 *          "targets": [ 0 ],
		 *          "data": "download_link",
		 *          "render": function ( data, type, full ) {
		 *            return '<a href="'+data+'">Download</a>';
		 *          }
		 *        } ]
		 *      } );
		 *    } );
		 */
		"mRender": null,
	
	
		/**
		 * Change the cell type created for the column - either TD cells or TH cells. This
		 * can be useful as TH cells have semantic meaning in the table body, allowing them
		 * to act as a header for a row (you may wish to add scope='row' to the TH elements).
		 *  @type string
		 *  @default td
		 *
		 *  @name DataTable.defaults.column.cellType
		 *  @dtopt Columns
		 *
		 *  @example
		 *    // Make the first column use TH cells
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "columnDefs": [ {
		 *          "targets": [ 0 ],
		 *          "cellType": "th"
		 *        } ]
		 *      } );
		 *    } );
		 */
		"sCellType": "td",
	
	
		/**
		 * Class to give to each cell in this column.
		 *  @type string
		 *  @default <i>Empty string</i>
		 *
		 *  @name DataTable.defaults.column.class
		 *  @dtopt Columns
		 *
		 *  @example
		 *    // Using `columnDefs`
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "columnDefs": [
		 *          { "class": "my_class", "targets": [ 0 ] }
		 *        ]
		 *      } );
		 *    } );
		 *
		 *  @example
		 *    // Using `columns`
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "columns": [
		 *          { "class": "my_class" },
		 *          null,
		 *          null,
		 *          null,
		 *          null
		 *        ]
		 *      } );
		 *    } );
		 */
		"sClass": "",
	
		/**
		 * When DataTables calculates the column widths to assign to each column,
		 * it finds the longest string in each column and then constructs a
		 * temporary table and reads the widths from that. The problem with this
		 * is that "mmm" is much wider then "iiii", but the latter is a longer
		 * string - thus the calculation can go wrong (doing it properly and putting
		 * it into an DOM object and measuring that is horribly(!) slow). Thus as
		 * a "work around" we provide this option. It will append its value to the
		 * text that is found to be the longest string for the column - i.e. padding.
		 * Generally you shouldn't need this!
		 *  @type string
		 *  @default <i>Empty string<i>
		 *
		 *  @name DataTable.defaults.column.contentPadding
		 *  @dtopt Columns
		 *
		 *  @example
		 *    // Using `columns`
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "columns": [
		 *          null,
		 *          null,
		 *          null,
		 *          {
		 *            "contentPadding": "mmm"
		 *          }
		 *        ]
		 *      } );
		 *    } );
		 */
		"sContentPadding": "",
	
	
		/**
		 * Allows a default value to be given for a column's data, and will be used
		 * whenever a null data source is encountered (this can be because `data`
		 * is set to null, or because the data source itself is null).
		 *  @type string
		 *  @default null
		 *
		 *  @name DataTable.defaults.column.defaultContent
		 *  @dtopt Columns
		 *
		 *  @example
		 *    // Using `columnDefs`
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "columnDefs": [
		 *          {
		 *            "data": null,
		 *            "defaultContent": "Edit",
		 *            "targets": [ -1 ]
		 *          }
		 *        ]
		 *      } );
		 *    } );
		 *
		 *  @example
		 *    // Using `columns`
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "columns": [
		 *          null,
		 *          null,
		 *          null,
		 *          {
		 *            "data": null,
		 *            "defaultContent": "Edit"
		 *          }
		 *        ]
		 *      } );
		 *    } );
		 */
		"sDefaultContent": null,
	
	
		/**
		 * This parameter is only used in DataTables' server-side processing. It can
		 * be exceptionally useful to know what columns are being displayed on the
		 * client side, and to map these to database fields. When defined, the names
		 * also allow DataTables to reorder information from the server if it comes
		 * back in an unexpected order (i.e. if you switch your columns around on the
		 * client-side, your server-side code does not also need updating).
		 *  @type string
		 *  @default <i>Empty string</i>
		 *
		 *  @name DataTable.defaults.column.name
		 *  @dtopt Columns
		 *
		 *  @example
		 *    // Using `columnDefs`
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "columnDefs": [
		 *          { "name": "engine", "targets": [ 0 ] },
		 *          { "name": "browser", "targets": [ 1 ] },
		 *          { "name": "platform", "targets": [ 2 ] },
		 *          { "name": "version", "targets": [ 3 ] },
		 *          { "name": "grade", "targets": [ 4 ] }
		 *        ]
		 *      } );
		 *    } );
		 *
		 *  @example
		 *    // Using `columns`
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "columns": [
		 *          { "name": "engine" },
		 *          { "name": "browser" },
		 *          { "name": "platform" },
		 *          { "name": "version" },
		 *          { "name": "grade" }
		 *        ]
		 *      } );
		 *    } );
		 */
		"sName": "",
	
	
		/**
		 * Defines a data source type for the ordering which can be used to read
		 * real-time information from the table (updating the internally cached
		 * version) prior to ordering. This allows ordering to occur on user
		 * editable elements such as form inputs.
		 *  @type string
		 *  @default std
		 *
		 *  @name DataTable.defaults.column.orderDataType
		 *  @dtopt Columns
		 *
		 *  @example
		 *    // Using `columnDefs`
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "columnDefs": [
		 *          { "orderDataType": "dom-text", "targets": [ 2, 3 ] },
		 *          { "type": "numeric", "targets": [ 3 ] },
		 *          { "orderDataType": "dom-select", "targets": [ 4 ] },
		 *          { "orderDataType": "dom-checkbox", "targets": [ 5 ] }
		 *        ]
		 *      } );
		 *    } );
		 *
		 *  @example
		 *    // Using `columns`
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "columns": [
		 *          null,
		 *          null,
		 *          { "orderDataType": "dom-text" },
		 *          { "orderDataType": "dom-text", "type": "numeric" },
		 *          { "orderDataType": "dom-select" },
		 *          { "orderDataType": "dom-checkbox" }
		 *        ]
		 *      } );
		 *    } );
		 */
		"sSortDataType": "std",
	
	
		/**
		 * The title of this column.
		 *  @type string
		 *  @default null <i>Derived from the 'TH' value for this column in the
		 *    original HTML table.</i>
		 *
		 *  @name DataTable.defaults.column.title
		 *  @dtopt Columns
		 *
		 *  @example
		 *    // Using `columnDefs`
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "columnDefs": [
		 *          { "title": "My column title", "targets": [ 0 ] }
		 *        ]
		 *      } );
		 *    } );
		 *
		 *  @example
		 *    // Using `columns`
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "columns": [
		 *          { "title": "My column title" },
		 *          null,
		 *          null,
		 *          null,
		 *          null
		 *        ]
		 *      } );
		 *    } );
		 */
		"sTitle": null,
	
	
		/**
		 * The type allows you to specify how the data for this column will be
		 * ordered. Four types (string, numeric, date and html (which will strip
		 * HTML tags before ordering)) are currently available. Note that only date
		 * formats understood by Javascript's Date() object will be accepted as type
		 * date. For example: "Mar 26, 2008 5:03 PM". May take the values: 'string',
		 * 'numeric', 'date' or 'html' (by default). Further types can be adding
		 * through plug-ins.
		 *  @type string
		 *  @default null <i>Auto-detected from raw data</i>
		 *
		 *  @name DataTable.defaults.column.type
		 *  @dtopt Columns
		 *
		 *  @example
		 *    // Using `columnDefs`
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "columnDefs": [
		 *          { "type": "html", "targets": [ 0 ] }
		 *        ]
		 *      } );
		 *    } );
		 *
		 *  @example
		 *    // Using `columns`
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "columns": [
		 *          { "type": "html" },
		 *          null,
		 *          null,
		 *          null,
		 *          null
		 *        ]
		 *      } );
		 *    } );
		 */
		"sType": null,
	
	
		/**
		 * Defining the width of the column, this parameter may take any CSS value
		 * (3em, 20px etc). DataTables applies 'smart' widths to columns which have not
		 * been given a specific width through this interface ensuring that the table
		 * remains readable.
		 *  @type string
		 *  @default null <i>Automatic</i>
		 *
		 *  @name DataTable.defaults.column.width
		 *  @dtopt Columns
		 *
		 *  @example
		 *    // Using `columnDefs`
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "columnDefs": [
		 *          { "width": "20%", "targets": [ 0 ] }
		 *        ]
		 *      } );
		 *    } );
		 *
		 *  @example
		 *    // Using `columns`
		 *    $(document).ready( function() {
		 *      $('#example').dataTable( {
		 *        "columns": [
		 *          { "width": "20%" },
		 *          null,
		 *          null,
		 *          null,
		 *          null
		 *        ]
		 *      } );
		 *    } );
		 */
		"sWidth": null
	};
	
	_fnHungarianMap( DataTable.defaults.column );
	
	
	
	/**
	 * DataTables settings object - this holds all the information needed for a
	 * given table, including configuration, data and current application of the
	 * table options. DataTables does not have a single instance for each DataTable
	 * with the settings attached to that instance, but rather instances of the
	 * DataTable "class" are created on-the-fly as needed (typically by a
	 * $().dataTable() call) and the settings object is then applied to that
	 * instance.
	 *
	 * Note that this object is related to {@link DataTable.defaults} but this
	 * one is the internal data store for DataTables's cache of columns. It should
	 * NOT be manipulated outside of DataTables. Any configuration should be done
	 * through the initialisation options.
	 *  @namespace
	 *  @todo Really should attach the settings object to individual instances so we
	 *    don't need to create new instances on each $().dataTable() call (if the
	 *    table already exists). It would also save passing oSettings around and
	 *    into every single function. However, this is a very significant
	 *    architecture change for DataTables and will almost certainly break
	 *    backwards compatibility with older installations. This is something that
	 *    will be done in 2.0.
	 */
	DataTable.models.oSettings = {
		/**
		 * Primary features of DataTables and their enablement state.
		 *  @namespace
		 */
		"oFeatures": {
	
			/**
			 * Flag to say if DataTables should automatically try to calculate the
			 * optimum table and columns widths (true) or not (false).
			 * Note that this parameter will be set by the initialisation routine. To
			 * set a default use {@link DataTable.defaults}.
			 *  @type boolean
			 */
			"bAutoWidth": null,
	
			/**
			 * Delay the creation of TR and TD elements until they are actually
			 * needed by a driven page draw. This can give a significant speed
			 * increase for Ajax source and Javascript source data, but makes no
			 * difference at all fro DOM and server-side processing tables.
			 * Note that this parameter will be set by the initialisation routine. To
			 * set a default use {@link DataTable.defaults}.
			 *  @type boolean
			 */
			"bDeferRender": null,
	
			/**
			 * Enable filtering on the table or not. Note that if this is disabled
			 * then there is no filtering at all on the table, including fnFilter.
			 * To just remove the filtering input use sDom and remove the 'f' option.
			 * Note that this parameter will be set by the initialisation routine. To
			 * set a default use {@link DataTable.defaults}.
			 *  @type boolean
			 */
			"bFilter": null,
	
			/**
			 * Table information element (the 'Showing x of y records' div) enable
			 * flag.
			 * Note that this parameter will be set by the initialisation routine. To
			 * set a default use {@link DataTable.defaults}.
			 *  @type boolean
			 */
			"bInfo": null,
	
			/**
			 * Present a user control allowing the end user to change the page size
			 * when pagination is enabled.
			 * Note that this parameter will be set by the initialisation routine. To
			 * set a default use {@link DataTable.defaults}.
			 *  @type boolean
			 */
			"bLengthChange": null,
	
			/**
			 * Pagination enabled or not. Note that if this is disabled then length
			 * changing must also be disabled.
			 * Note that this parameter will be set by the initialisation routine. To
			 * set a default use {@link DataTable.defaults}.
			 *  @type boolean
			 */
			"bPaginate": null,
	
			/**
			 * Processing indicator enable flag whenever DataTables is enacting a
			 * user request - typically an Ajax request for server-side processing.
			 * Note that this parameter will be set by the initialisation routine. To
			 * set a default use {@link DataTable.defaults}.
			 *  @type boolean
			 */
			"bProcessing": null,
	
			/**
			 * Server-side processing enabled flag - when enabled DataTables will
			 * get all data from the server for every draw - there is no filtering,
			 * sorting or paging done on the client-side.
			 * Note that this parameter will be set by the initialisation routine. To
			 * set a default use {@link DataTable.defaults}.
			 *  @type boolean
			 */
			"bServerSide": null,
	
			/**
			 * Sorting enablement flag.
			 * Note that this parameter will be set by the initialisation routine. To
			 * set a default use {@link DataTable.defaults}.
			 *  @type boolean
			 */
			"bSort": null,
	
			/**
			 * Multi-column sorting
			 * Note that this parameter will be set by the initialisation routine. To
			 * set a default use {@link DataTable.defaults}.
			 *  @type boolean
			 */
			"bSortMulti": null,
	
			/**
			 * Apply a class to the columns which are being sorted to provide a
			 * visual highlight or not. This can slow things down when enabled since
			 * there is a lot of DOM interaction.
			 * Note that this parameter will be set by the initialisation routine. To
			 * set a default use {@link DataTable.defaults}.
			 *  @type boolean
			 */
			"bSortClasses": null,
	
			/**
			 * State saving enablement flag.
			 * Note that this parameter will be set by the initialisation routine. To
			 * set a default use {@link DataTable.defaults}.
			 *  @type boolean
			 */
			"bStateSave": null
		},
	
	
		/**
		 * Scrolling settings for a table.
		 *  @namespace
		 */
		"oScroll": {
			/**
			 * When the table is shorter in height than sScrollY, collapse the
			 * table container down to the height of the table (when true).
			 * Note that this parameter will be set by the initialisation routine. To
			 * set a default use {@link DataTable.defaults}.
			 *  @type boolean
			 */
			"bCollapse": null,
	
			/**
			 * Width of the scrollbar for the web-browser's platform. Calculated
			 * during table initialisation.
			 *  @type int
			 *  @default 0
			 */
			"iBarWidth": 0,
	
			/**
			 * Viewport width for horizontal scrolling. Horizontal scrolling is
			 * disabled if an empty string.
			 * Note that this parameter will be set by the initialisation routine. To
			 * set a default use {@link DataTable.defaults}.
			 *  @type string
			 */
			"sX": null,
	
			/**
			 * Width to expand the table to when using x-scrolling. Typically you
			 * should not need to use this.
			 * Note that this parameter will be set by the initialisation routine. To
			 * set a default use {@link DataTable.defaults}.
			 *  @type string
			 *  @deprecated
			 */
			"sXInner": null,
	
			/**
			 * Viewport height for vertical scrolling. Vertical scrolling is disabled
			 * if an empty string.
			 * Note that this parameter will be set by the initialisation routine. To
			 * set a default use {@link DataTable.defaults}.
			 *  @type string
			 */
			"sY": null
		},
	
		/**
		 * Language information for the table.
		 *  @namespace
		 *  @extends DataTable.defaults.oLanguage
		 */
		"oLanguage": {
			/**
			 * Information callback function. See
			 * {@link DataTable.defaults.fnInfoCallback}
			 *  @type function
			 *  @default null
			 */
			"fnInfoCallback": null
		},
	
		/**
		 * Browser support parameters
		 *  @namespace
		 */
		"oBrowser": {
			/**
			 * Indicate if the browser incorrectly calculates width:100% inside a
			 * scrolling element (IE6/7)
			 *  @type boolean
			 *  @default false
			 */
			"bScrollOversize": false,
	
			/**
			 * Determine if the vertical scrollbar is on the right or left of the
			 * scrolling container - needed for rtl language layout, although not
			 * all browsers move the scrollbar (Safari).
			 *  @type boolean
			 *  @default false
			 */
			"bScrollbarLeft": false,
	
			/**
			 * Flag for if `getBoundingClientRect` is fully supported or not
			 *  @type boolean
			 *  @default false
			 */
			"bBounding": false,
	
			/**
			 * Browser scrollbar width
			 *  @type integer
			 *  @default 0
			 */
			"barWidth": 0
		},
	
	
		"ajax": null,
	
	
		/**
		 * Array referencing the nodes which are used for the features. The
		 * parameters of this object match what is allowed by sDom - i.e.
		 *   <ul>
		 *     <li>'l' - Length changing</li>
		 *     <li>'f' - Filtering input</li>
		 *     <li>'t' - The table!</li>
		 *     <li>'i' - Information</li>
		 *     <li>'p' - Pagination</li>
		 *     <li>'r' - pRocessing</li>
		 *   </ul>
		 *  @type array
		 *  @default []
		 */
		"aanFeatures": [],
	
		/**
		 * Store data information - see {@link DataTable.models.oRow} for detailed
		 * information.
		 *  @type array
		 *  @default []
		 */
		"aoData": [],
	
		/**
		 * Array of indexes which are in the current display (after filtering etc)
		 *  @type array
		 *  @default []
		 */
		"aiDisplay": [],
	
		/**
		 * Array of indexes for display - no filtering
		 *  @type array
		 *  @default []
		 */
		"aiDisplayMaster": [],
	
		/**
		 * Map of row ids to data indexes
		 *  @type object
		 *  @default {}
		 */
		"aIds": {},
	
		/**
		 * Store information about each column that is in use
		 *  @type array
		 *  @default []
		 */
		"aoColumns": [],
	
		/**
		 * Store information about the table's header
		 *  @type array
		 *  @default []
		 */
		"aoHeader": [],
	
		/**
		 * Store information about the table's footer
		 *  @type array
		 *  @default []
		 */
		"aoFooter": [],
	
		/**
		 * Store the applied global search information in case we want to force a
		 * research or compare the old search to a new one.
		 * Note that this parameter will be set by the initialisation routine. To
		 * set a default use {@link DataTable.defaults}.
		 *  @namespace
		 *  @extends DataTable.models.oSearch
		 */
		"oPreviousSearch": {},
	
		/**
		 * Store the applied search for each column - see
		 * {@link DataTable.models.oSearch} for the format that is used for the
		 * filtering information for each column.
		 *  @type array
		 *  @default []
		 */
		"aoPreSearchCols": [],
	
		/**
		 * Sorting that is applied to the table. Note that the inner arrays are
		 * used in the following manner:
		 * <ul>
		 *   <li>Index 0 - column number</li>
		 *   <li>Index 1 - current sorting direction</li>
		 * </ul>
		 * Note that this parameter will be set by the initialisation routine. To
		 * set a default use {@link DataTable.defaults}.
		 *  @type array
		 *  @todo These inner arrays should really be objects
		 */
		"aaSorting": null,
	
		/**
		 * Sorting that is always applied to the table (i.e. prefixed in front of
		 * aaSorting).
		 * Note that this parameter will be set by the initialisation routine. To
		 * set a default use {@link DataTable.defaults}.
		 *  @type array
		 *  @default []
		 */
		"aaSortingFixed": [],
	
		/**
		 * Classes to use for the striping of a table.
		 * Note that this parameter will be set by the initialisation routine. To
		 * set a default use {@link DataTable.defaults}.
		 *  @type array
		 *  @default []
		 */
		"asStripeClasses": null,
	
		/**
		 * If restoring a table - we should restore its striping classes as well
		 *  @type array
		 *  @default []
		 */
		"asDestroyStripes": [],
	
		/**
		 * If restoring a table - we should restore its width
		 *  @type int
		 *  @default 0
		 */
		"sDestroyWidth": 0,
	
		/**
		 * Callback functions array for every time a row is inserted (i.e. on a draw).
		 *  @type array
		 *  @default []
		 */
		"aoRowCallback": [],
	
		/**
		 * Callback functions for the header on each draw.
		 *  @type array
		 *  @default []
		 */
		"aoHeaderCallback": [],
	
		/**
		 * Callback function for the footer on each draw.
		 *  @type array
		 *  @default []
		 */
		"aoFooterCallback": [],
	
		/**
		 * Array of callback functions for draw callback functions
		 *  @type array
		 *  @default []
		 */
		"aoDrawCallback": [],
	
		/**
		 * Array of callback functions for row created function
		 *  @type array
		 *  @default []
		 */
		"aoRowCreatedCallback": [],
	
		/**
		 * Callback functions for just before the table is redrawn. A return of
		 * false will be used to cancel the draw.
		 *  @type array
		 *  @default []
		 */
		"aoPreDrawCallback": [],
	
		/**
		 * Callback functions for when the table has been initialised.
		 *  @type array
		 *  @default []
		 */
		"aoInitComplete": [],
	
	
		/**
		 * Callbacks for modifying the settings to be stored for state saving, prior to
		 * saving state.
		 *  @type array
		 *  @default []
		 */
		"aoStateSaveParams": [],
	
		/**
		 * Callbacks for modifying the settings that have been stored for state saving
		 * prior to using the stored values to restore the state.
		 *  @type array
		 *  @default []
		 */
		"aoStateLoadParams": [],
	
		/**
		 * Callbacks for operating on the settings object once the saved state has been
		 * loaded
		 *  @type array
		 *  @default []
		 */
		"aoStateLoaded": [],
	
		/**
		 * Cache the table ID for quick access
		 *  @type string
		 *  @default <i>Empty string</i>
		 */
		"sTableId": "",
	
		/**
		 * The TABLE node for the main table
		 *  @type node
		 *  @default null
		 */
		"nTable": null,
	
		/**
		 * Permanent ref to the thead element
		 *  @type node
		 *  @default null
		 */
		"nTHead": null,
	
		/**
		 * Permanent ref to the tfoot element - if it exists
		 *  @type node
		 *  @default null
		 */
		"nTFoot": null,
	
		/**
		 * Permanent ref to the tbody element
		 *  @type node
		 *  @default null
		 */
		"nTBody": null,
	
		/**
		 * Cache the wrapper node (contains all DataTables controlled elements)
		 *  @type node
		 *  @default null
		 */
		"nTableWrapper": null,
	
		/**
		 * Indicate if when using server-side processing the loading of data
		 * should be deferred until the second draw.
		 * Note that this parameter will be set by the initialisation routine. To
		 * set a default use {@link DataTable.defaults}.
		 *  @type boolean
		 *  @default false
		 */
		"bDeferLoading": false,
	
		/**
		 * Indicate if all required information has been read in
		 *  @type boolean
		 *  @default false
		 */
		"bInitialised": false,
	
		/**
		 * Information about open rows. Each object in the array has the parameters
		 * 'nTr' and 'nParent'
		 *  @type array
		 *  @default []
		 */
		"aoOpenRows": [],
	
		/**
		 * Dictate the positioning of DataTables' control elements - see
		 * {@link DataTable.model.oInit.sDom}.
		 * Note that this parameter will be set by the initialisation routine. To
		 * set a default use {@link DataTable.defaults}.
		 *  @type string
		 *  @default null
		 */
		"sDom": null,
	
		/**
		 * Search delay (in mS)
		 *  @type integer
		 *  @default null
		 */
		"searchDelay": null,
	
		/**
		 * Which type of pagination should be used.
		 * Note that this parameter will be set by the initialisation routine. To
		 * set a default use {@link DataTable.defaults}.
		 *  @type string
		 *  @default two_button
		 */
		"sPaginationType": "two_button",
	
		/**
		 * The state duration (for `stateSave`) in seconds.
		 * Note that this parameter will be set by the initialisation routine. To
		 * set a default use {@link DataTable.defaults}.
		 *  @type int
		 *  @default 0
		 */
		"iStateDuration": 0,
	
		/**
		 * Array of callback functions for state saving. Each array element is an
		 * object with the following parameters:
		 *   <ul>
		 *     <li>function:fn - function to call. Takes two parameters, oSettings
		 *       and the JSON string to save that has been thus far created. Returns
		 *       a JSON string to be inserted into a json object
		 *       (i.e. '"param": [ 0, 1, 2]')</li>
		 *     <li>string:sName - name of callback</li>
		 *   </ul>
		 *  @type array
		 *  @default []
		 */
		"aoStateSave": [],
	
		/**
		 * Array of callback functions for state loading. Each array element is an
		 * object with the following parameters:
		 *   <ul>
		 *     <li>function:fn - function to call. Takes two parameters, oSettings
		 *       and the object stored. May return false to cancel state loading</li>
		 *     <li>string:sName - name of callback</li>
		 *   </ul>
		 *  @type array
		 *  @default []
		 */
		"aoStateLoad": [],
	
		/**
		 * State that was saved. Useful for back reference
		 *  @type object
		 *  @default null
		 */
		"oSavedState": null,
	
		/**
		 * State that was loaded. Useful for back reference
		 *  @type object
		 *  @default null
		 */
		"oLoadedState": null,
	
		/**
		 * Source url for AJAX data for the table.
		 * Note that this parameter will be set by the initialisation routine. To
		 * set a default use {@link DataTable.defaults}.
		 *  @type string
		 *  @default null
		 */
		"sAjaxSource": null,
	
		/**
		 * Property from a given object from which to read the table data from. This
		 * can be an empty string (when not server-side processing), in which case
		 * it is  assumed an an array is given directly.
		 * Note that this parameter will be set by the initialisation routine. To
		 * set a default use {@link DataTable.defaults}.
		 *  @type string
		 */
		"sAjaxDataProp": null,
	
		/**
		 * Note if draw should be blocked while getting data
		 *  @type boolean
		 *  @default true
		 */
		"bAjaxDataGet": true,
	
		/**
		 * The last jQuery XHR object that was used for server-side data gathering.
		 * This can be used for working with the XHR information in one of the
		 * callbacks
		 *  @type object
		 *  @default null
		 */
		"jqXHR": null,
	
		/**
		 * JSON returned from the server in the last Ajax request
		 *  @type object
		 *  @default undefined
		 */
		"json": undefined,
	
		/**
		 * Data submitted as part of the last Ajax request
		 *  @type object
		 *  @default undefined
		 */
		"oAjaxData": undefined,
	
		/**
		 * Function to get the server-side data.
		 * Note that this parameter will be set by the initialisation routine. To
		 * set a default use {@link DataTable.defaults}.
		 *  @type function
		 */
		"fnServerData": null,
	
		/**
		 * Functions which are called prior to sending an Ajax request so extra
		 * parameters can easily be sent to the server
		 *  @type array
		 *  @default []
		 */
		"aoServerParams": [],
	
		/**
		 * Send the XHR HTTP method - GET or POST (could be PUT or DELETE if
		 * required).
		 * Note that this parameter will be set by the initialisation routine. To
		 * set a default use {@link DataTable.defaults}.
		 *  @type string
		 */
		"sServerMethod": null,
	
		/**
		 * Format numbers for display.
		 * Note that this parameter will be set by the initialisation routine. To
		 * set a default use {@link DataTable.defaults}.
		 *  @type function
		 */
		"fnFormatNumber": null,
	
		/**
		 * List of options that can be used for the user selectable length menu.
		 * Note that this parameter will be set by the initialisation routine. To
		 * set a default use {@link DataTable.defaults}.
		 *  @type array
		 *  @default []
		 */
		"aLengthMenu": null,
	
		/**
		 * Counter for the draws that the table does. Also used as a tracker for
		 * server-side processing
		 *  @type int
		 *  @default 0
		 */
		"iDraw": 0,
	
		/**
		 * Indicate if a redraw is being done - useful for Ajax
		 *  @type boolean
		 *  @default false
		 */
		"bDrawing": false,
	
		/**
		 * Draw index (iDraw) of the last error when parsing the returned data
		 *  @type int
		 *  @default -1
		 */
		"iDrawError": -1,
	
		/**
		 * Paging display length
		 *  @type int
		 *  @default 10
		 */
		"_iDisplayLength": 10,
	
		/**
		 * Paging start point - aiDisplay index
		 *  @type int
		 *  @default 0
		 */
		"_iDisplayStart": 0,
	
		/**
		 * Server-side processing - number of records in the result set
		 * (i.e. before filtering), Use fnRecordsTotal rather than
		 * this property to get the value of the number of records, regardless of
		 * the server-side processing setting.
		 *  @type int
		 *  @default 0
		 *  @private
		 */
		"_iRecordsTotal": 0,
	
		/**
		 * Server-side processing - number of records in the current display set
		 * (i.e. after filtering). Use fnRecordsDisplay rather than
		 * this property to get the value of the number of records, regardless of
		 * the server-side processing setting.
		 *  @type boolean
		 *  @default 0
		 *  @private
		 */
		"_iRecordsDisplay": 0,
	
		/**
		 * The classes to use for the table
		 *  @type object
		 *  @default {}
		 */
		"oClasses": {},
	
		/**
		 * Flag attached to the settings object so you can check in the draw
		 * callback if filtering has been done in the draw. Deprecated in favour of
		 * events.
		 *  @type boolean
		 *  @default false
		 *  @deprecated
		 */
		"bFiltered": false,
	
		/**
		 * Flag attached to the settings object so you can check in the draw
		 * callback if sorting has been done in the draw. Deprecated in favour of
		 * events.
		 *  @type boolean
		 *  @default false
		 *  @deprecated
		 */
		"bSorted": false,
	
		/**
		 * Indicate that if multiple rows are in the header and there is more than
		 * one unique cell per column, if the top one (true) or bottom one (false)
		 * should be used for sorting / title by DataTables.
		 * Note that this parameter will be set by the initialisation routine. To
		 * set a default use {@link DataTable.defaults}.
		 *  @type boolean
		 */
		"bSortCellsTop": null,
	
		/**
		 * Initialisation object that is used for the table
		 *  @type object
		 *  @default null
		 */
		"oInit": null,
	
		/**
		 * Destroy callback functions - for plug-ins to attach themselves to the
		 * destroy so they can clean up markup and events.
		 *  @type array
		 *  @default []
		 */
		"aoDestroyCallback": [],
	
	
		/**
		 * Get the number of records in the current record set, before filtering
		 *  @type function
		 */
		"fnRecordsTotal": function ()
		{
			return _fnDataSource( this ) == 'ssp' ?
				this._iRecordsTotal * 1 :
				this.aiDisplayMaster.length;
		},
	
		/**
		 * Get the number of records in the current record set, after filtering
		 *  @type function
		 */
		"fnRecordsDisplay": function ()
		{
			return _fnDataSource( this ) == 'ssp' ?
				this._iRecordsDisplay * 1 :
				this.aiDisplay.length;
		},
	
		/**
		 * Get the display end point - aiDisplay index
		 *  @type function
		 */
		"fnDisplayEnd": function ()
		{
			var
				len      = this._iDisplayLength,
				start    = this._iDisplayStart,
				calc     = start + len,
				records  = this.aiDisplay.length,
				features = this.oFeatures,
				paginate = features.bPaginate;
	
			if ( features.bServerSide ) {
				return paginate === false || len === -1 ?
					start + records :
					Math.min( start+len, this._iRecordsDisplay );
			}
			else {
				return ! paginate || calc>records || len===-1 ?
					records :
					calc;
			}
		},
	
		/**
		 * The DataTables object for this table
		 *  @type object
		 *  @default null
		 */
		"oInstance": null,
	
		/**
		 * Unique identifier for each instance of the DataTables object. If there
		 * is an ID on the table node, then it takes that value, otherwise an
		 * incrementing internal counter is used.
		 *  @type string
		 *  @default null
		 */
		"sInstance": null,
	
		/**
		 * tabindex attribute value that is added to DataTables control elements, allowing
		 * keyboard navigation of the table and its controls.
		 */
		"iTabIndex": 0,
	
		/**
		 * DIV container for the footer scrolling table if scrolling
		 */
		"nScrollHead": null,
	
		/**
		 * DIV container for the footer scrolling table if scrolling
		 */
		"nScrollFoot": null,
	
		/**
		 * Last applied sort
		 *  @type array
		 *  @default []
		 */
		"aLastSort": [],
	
		/**
		 * Stored plug-in instances
		 *  @type object
		 *  @default {}
		 */
		"oPlugins": {},
	
		/**
		 * Function used to get a row's id from the row's data
		 *  @type function
		 *  @default null
		 */
		"rowIdFn": null,
	
		/**
		 * Data location where to store a row's id
		 *  @type string
		 *  @default null
		 */
		"rowId": null
	};

	/**
	 * Extension object for DataTables that is used to provide all extension
	 * options.
	 *
	 * Note that the `DataTable.ext` object is available through
	 * `jQuery.fn.dataTable.ext` where it may be accessed and manipulated. It is
	 * also aliased to `jQuery.fn.dataTableExt` for historic reasons.
	 *  @namespace
	 *  @extends DataTable.models.ext
	 */
	
	
	/**
	 * DataTables extensions
	 * 
	 * This namespace acts as a collection area for plug-ins that can be used to
	 * extend DataTables capabilities. Indeed many of the build in methods
	 * use this method to provide their own capabilities (sorting methods for
	 * example).
	 *
	 * Note that this namespace is aliased to `jQuery.fn.dataTableExt` for legacy
	 * reasons
	 *
	 *  @namespace
	 */
	DataTable.ext = _ext = {
		/**
		 * Buttons. For use with the Buttons extension for DataTables. This is
		 * defined here so other extensions can define buttons regardless of load
		 * order. It is _not_ used by DataTables core.
		 *
		 *  @type object
		 *  @default {}
		 */
		buttons: {},
	
	
		/**
		 * Element class names
		 *
		 *  @type object
		 *  @default {}
		 */
		classes: {},
	
	
		/**
		 * DataTables build type (expanded by the download builder)
		 *
		 *  @type string
		 */
		builder: "-source-",
	
	
		/**
		 * Error reporting.
		 * 
		 * How should DataTables report an error. Can take the value 'alert',
		 * 'throw', 'none' or a function.
		 *
		 *  @type string|function
		 *  @default alert
		 */
		errMode: "alert",
	
	
		/**
		 * Feature plug-ins.
		 * 
		 * This is an array of objects which describe the feature plug-ins that are
		 * available to DataTables. These feature plug-ins are then available for
		 * use through the `dom` initialisation option.
		 * 
		 * Each feature plug-in is described by an object which must have the
		 * following properties:
		 * 
		 * * `fnInit` - function that is used to initialise the plug-in,
		 * * `cFeature` - a character so the feature can be enabled by the `dom`
		 *   instillation option. This is case sensitive.
		 *
		 * The `fnInit` function has the following input parameters:
		 *
		 * 1. `{object}` DataTables settings object: see
		 *    {@link DataTable.models.oSettings}
		 *
		 * And the following return is expected:
		 * 
		 * * {node|null} The element which contains your feature. Note that the
		 *   return may also be void if your plug-in does not require to inject any
		 *   DOM elements into DataTables control (`dom`) - for example this might
		 *   be useful when developing a plug-in which allows table control via
		 *   keyboard entry
		 *
		 *  @type array
		 *
		 *  @example
		 *    $.fn.dataTable.ext.features.push( {
		 *      "fnInit": function( oSettings ) {
		 *        return new TableTools( { "oDTSettings": oSettings } );
		 *      },
		 *      "cFeature": "T"
		 *    } );
		 */
		feature: [],
	
	
		/**
		 * Row searching.
		 * 
		 * This method of searching is complimentary to the default type based
		 * searching, and a lot more comprehensive as it allows you complete control
		 * over the searching logic. Each element in this array is a function
		 * (parameters described below) that is called for every row in the table,
		 * and your logic decides if it should be included in the searching data set
		 * or not.
		 *
		 * Searching functions have the following input parameters:
		 *
		 * 1. `{object}` DataTables settings object: see
		 *    {@link DataTable.models.oSettings}
		 * 2. `{array|object}` Data for the row to be processed (same as the
		 *    original format that was passed in as the data source, or an array
		 *    from a DOM data source
		 * 3. `{int}` Row index ({@link DataTable.models.oSettings.aoData}), which
		 *    can be useful to retrieve the `TR` element if you need DOM interaction.
		 *
		 * And the following return is expected:
		 *
		 * * {boolean} Include the row in the searched result set (true) or not
		 *   (false)
		 *
		 * Note that as with the main search ability in DataTables, technically this
		 * is "filtering", since it is subtractive. However, for consistency in
		 * naming we call it searching here.
		 *
		 *  @type array
		 *  @default []
		 *
		 *  @example
		 *    // The following example shows custom search being applied to the
		 *    // fourth column (i.e. the data[3] index) based on two input values
		 *    // from the end-user, matching the data in a certain range.
		 *    $.fn.dataTable.ext.search.push(
		 *      function( settings, data, dataIndex ) {
		 *        var min = document.getElementById('min').value * 1;
		 *        var max = document.getElementById('max').value * 1;
		 *        var version = data[3] == "-" ? 0 : data[3]*1;
		 *
		 *        if ( min == "" && max == "" ) {
		 *          return true;
		 *        }
		 *        else if ( min == "" && version < max ) {
		 *          return true;
		 *        }
		 *        else if ( min < version && "" == max ) {
		 *          return true;
		 *        }
		 *        else if ( min < version && version < max ) {
		 *          return true;
		 *        }
		 *        return false;
		 *      }
		 *    );
		 */
		search: [],
	
	
		/**
		 * Selector extensions
		 *
		 * The `selector` option can be used to extend the options available for the
		 * selector modifier options (`selector-modifier` object data type) that
		 * each of the three built in selector types offer (row, column and cell +
		 * their plural counterparts). For example the Select extension uses this
		 * mechanism to provide an option to select only rows, columns and cells
		 * that have been marked as selected by the end user (`{selected: true}`),
		 * which can be used in conjunction with the existing built in selector
		 * options.
		 *
		 * Each property is an array to which functions can be pushed. The functions
		 * take three attributes:
		 *
		 * * Settings object for the host table
		 * * Options object (`selector-modifier` object type)
		 * * Array of selected item indexes
		 *
		 * The return is an array of the resulting item indexes after the custom
		 * selector has been applied.
		 *
		 *  @type object
		 */
		selector: {
			cell: [],
			column: [],
			row: []
		},
	
	
		/**
		 * Internal functions, exposed for used in plug-ins.
		 * 
		 * Please note that you should not need to use the internal methods for
		 * anything other than a plug-in (and even then, try to avoid if possible).
		 * The internal function may change between releases.
		 *
		 *  @type object
		 *  @default {}
		 */
		internal: {},
	
	
		/**
		 * Legacy configuration options. Enable and disable legacy options that
		 * are available in DataTables.
		 *
		 *  @type object
		 */
		legacy: {
			/**
			 * Enable / disable DataTables 1.9 compatible server-side processing
			 * requests
			 *
			 *  @type boolean
			 *  @default null
			 */
			ajax: null
		},
	
	
		/**
		 * Pagination plug-in methods.
		 * 
		 * Each entry in this object is a function and defines which buttons should
		 * be shown by the pagination rendering method that is used for the table:
		 * {@link DataTable.ext.renderer.pageButton}. The renderer addresses how the
		 * buttons are displayed in the document, while the functions here tell it
		 * what buttons to display. This is done by returning an array of button
		 * descriptions (what each button will do).
		 *
		 * Pagination types (the four built in options and any additional plug-in
		 * options defined here) can be used through the `paginationType`
		 * initialisation parameter.
		 *
		 * The functions defined take two parameters:
		 *
		 * 1. `{int} page` The current page index
		 * 2. `{int} pages` The number of pages in the table
		 *
		 * Each function is expected to return an array where each element of the
		 * array can be one of:
		 *
		 * * `first` - Jump to first page when activated
		 * * `last` - Jump to last page when activated
		 * * `previous` - Show previous page when activated
		 * * `next` - Show next page when activated
		 * * `{int}` - Show page of the index given
		 * * `{array}` - A nested array containing the above elements to add a
		 *   containing 'DIV' element (might be useful for styling).
		 *
		 * Note that DataTables v1.9- used this object slightly differently whereby
		 * an object with two functions would be defined for each plug-in. That
		 * ability is still supported by DataTables 1.10+ to provide backwards
		 * compatibility, but this option of use is now decremented and no longer
		 * documented in DataTables 1.10+.
		 *
		 *  @type object
		 *  @default {}
		 *
		 *  @example
		 *    // Show previous, next and current page buttons only
		 *    $.fn.dataTableExt.oPagination.current = function ( page, pages ) {
		 *      return [ 'previous', page, 'next' ];
		 *    };
		 */
		pager: {},
	
	
		renderer: {
			pageButton: {},
			header: {}
		},
	
	
		/**
		 * Ordering plug-ins - custom data source
		 * 
		 * The extension options for ordering of data available here is complimentary
		 * to the default type based ordering that DataTables typically uses. It
		 * allows much greater control over the the data that is being used to
		 * order a column, but is necessarily therefore more complex.
		 * 
		 * This type of ordering is useful if you want to do ordering based on data
		 * live from the DOM (for example the contents of an 'input' element) rather
		 * than just the static string that DataTables knows of.
		 * 
		 * The way these plug-ins work is that you create an array of the values you
		 * wish to be ordering for the column in question and then return that
		 * array. The data in the array much be in the index order of the rows in
		 * the table (not the currently ordering order!). Which order data gathering
		 * function is run here depends on the `dt-init columns.orderDataType`
		 * parameter that is used for the column (if any).
		 *
		 * The functions defined take two parameters:
		 *
		 * 1. `{object}` DataTables settings object: see
		 *    {@link DataTable.models.oSettings}
		 * 2. `{int}` Target column index
		 *
		 * Each function is expected to return an array:
		 *
		 * * `{array}` Data for the column to be ordering upon
		 *
		 *  @type array
		 *
		 *  @example
		 *    // Ordering using `input` node values
		 *    $.fn.dataTable.ext.order['dom-text'] = function  ( settings, col )
		 *    {
		 *      return this.api().column( col, {order:'index'} ).nodes().map( function ( td, i ) {
		 *        return $('input', td).val();
		 *      } );
		 *    }
		 */
		order: {},
	
	
		/**
		 * Type based plug-ins.
		 *
		 * Each column in DataTables has a type assigned to it, either by automatic
		 * detection or by direct assignment using the `type` option for the column.
		 * The type of a column will effect how it is ordering and search (plug-ins
		 * can also make use of the column type if required).
		 *
		 * @namespace
		 */
		type: {
			/**
			 * Type detection functions.
			 *
			 * The functions defined in this object are used to automatically detect
			 * a column's type, making initialisation of DataTables super easy, even
			 * when complex data is in the table.
			 *
			 * The functions defined take two parameters:
			 *
		     *  1. `{*}` Data from the column cell to be analysed
		     *  2. `{settings}` DataTables settings object. This can be used to
		     *     perform context specific type detection - for example detection
		     *     based on language settings such as using a comma for a decimal
		     *     place. Generally speaking the options from the settings will not
		     *     be required
			 *
			 * Each function is expected to return:
			 *
			 * * `{string|null}` Data type detected, or null if unknown (and thus
			 *   pass it on to the other type detection functions.
			 *
			 *  @type array
			 *
			 *  @example
			 *    // Currency type detection plug-in:
			 *    $.fn.dataTable.ext.type.detect.push(
			 *      function ( data, settings ) {
			 *        // Check the numeric part
			 *        if ( ! $.isNumeric( data.substring(1) ) ) {
			 *          return null;
			 *        }
			 *
			 *        // Check prefixed by currency
			 *        if ( data.charAt(0) == '$' || data.charAt(0) == '&pound;' ) {
			 *          return 'currency';
			 *        }
			 *        return null;
			 *      }
			 *    );
			 */
			detect: [],
	
	
			/**
			 * Type based search formatting.
			 *
			 * The type based searching functions can be used to pre-format the
			 * data to be search on. For example, it can be used to strip HTML
			 * tags or to de-format telephone numbers for numeric only searching.
			 *
			 * Note that is a search is not defined for a column of a given type,
			 * no search formatting will be performed.
			 * 
			 * Pre-processing of searching data plug-ins - When you assign the sType
			 * for a column (or have it automatically detected for you by DataTables
			 * or a type detection plug-in), you will typically be using this for
			 * custom sorting, but it can also be used to provide custom searching
			 * by allowing you to pre-processing the data and returning the data in
			 * the format that should be searched upon. This is done by adding
			 * functions this object with a parameter name which matches the sType
			 * for that target column. This is the corollary of <i>afnSortData</i>
			 * for searching data.
			 *
			 * The functions defined take a single parameter:
			 *
		     *  1. `{*}` Data from the column cell to be prepared for searching
			 *
			 * Each function is expected to return:
			 *
			 * * `{string|null}` Formatted string that will be used for the searching.
			 *
			 *  @type object
			 *  @default {}
			 *
			 *  @example
			 *    $.fn.dataTable.ext.type.search['title-numeric'] = function ( d ) {
			 *      return d.replace(/\n/g," ").replace( /<.*?>/g, "" );
			 *    }
			 */
			search: {},
	
	
			/**
			 * Type based ordering.
			 *
			 * The column type tells DataTables what ordering to apply to the table
			 * when a column is sorted upon. The order for each type that is defined,
			 * is defined by the functions available in this object.
			 *
			 * Each ordering option can be described by three properties added to
			 * this object:
			 *
			 * * `{type}-pre` - Pre-formatting function
			 * * `{type}-asc` - Ascending order function
			 * * `{type}-desc` - Descending order function
			 *
			 * All three can be used together, only `{type}-pre` or only
			 * `{type}-asc` and `{type}-desc` together. It is generally recommended
			 * that only `{type}-pre` is used, as this provides the optimal
			 * implementation in terms of speed, although the others are provided
			 * for compatibility with existing Javascript sort functions.
			 *
			 * `{type}-pre`: Functions defined take a single parameter:
			 *
		     *  1. `{*}` Data from the column cell to be prepared for ordering
			 *
			 * And return:
			 *
			 * * `{*}` Data to be sorted upon
			 *
			 * `{type}-asc` and `{type}-desc`: Functions are typical Javascript sort
			 * functions, taking two parameters:
			 *
		     *  1. `{*}` Data to compare to the second parameter
		     *  2. `{*}` Data to compare to the first parameter
			 *
			 * And returning:
			 *
			 * * `{*}` Ordering match: <0 if first parameter should be sorted lower
			 *   than the second parameter, ===0 if the two parameters are equal and
			 *   >0 if the first parameter should be sorted height than the second
			 *   parameter.
			 * 
			 *  @type object
			 *  @default {}
			 *
			 *  @example
			 *    // Numeric ordering of formatted numbers with a pre-formatter
			 *    $.extend( $.fn.dataTable.ext.type.order, {
			 *      "string-pre": function(x) {
			 *        a = (a === "-" || a === "") ? 0 : a.replace( /[^\d\-\.]/g, "" );
			 *        return parseFloat( a );
			 *      }
			 *    } );
			 *
			 *  @example
			 *    // Case-sensitive string ordering, with no pre-formatting method
			 *    $.extend( $.fn.dataTable.ext.order, {
			 *      "string-case-asc": function(x,y) {
			 *        return ((x < y) ? -1 : ((x > y) ? 1 : 0));
			 *      },
			 *      "string-case-desc": function(x,y) {
			 *        return ((x < y) ? 1 : ((x > y) ? -1 : 0));
			 *      }
			 *    } );
			 */
			order: {}
		},
	
		/**
		 * Unique DataTables instance counter
		 *
		 * @type int
		 * @private
		 */
		_unique: 0,
	
	
		//
		// Depreciated
		// The following properties are retained for backwards compatiblity only.
		// The should not be used in new projects and will be removed in a future
		// version
		//
	
		/**
		 * Version check function.
		 *  @type function
		 *  @depreciated Since 1.10
		 */
		fnVersionCheck: DataTable.fnVersionCheck,
	
	
		/**
		 * Index for what 'this' index API functions should use
		 *  @type int
		 *  @deprecated Since v1.10
		 */
		iApiIndex: 0,
	
	
		/**
		 * jQuery UI class container
		 *  @type object
		 *  @deprecated Since v1.10
		 */
		oJUIClasses: {},
	
	
		/**
		 * Software version
		 *  @type string
		 *  @deprecated Since v1.10
		 */
		sVersion: DataTable.version
	};
	
	
	//
	// Backwards compatibility. Alias to pre 1.10 Hungarian notation counter parts
	//
	$.extend( _ext, {
		afnFiltering: _ext.search,
		aTypes:       _ext.type.detect,
		ofnSearch:    _ext.type.search,
		oSort:        _ext.type.order,
		afnSortData:  _ext.order,
		aoFeatures:   _ext.feature,
		oApi:         _ext.internal,
		oStdClasses:  _ext.classes,
		oPagination:  _ext.pager
	} );
	
	
	$.extend( DataTable.ext.classes, {
		"sTable": "dataTable",
		"sNoFooter": "no-footer",
	
		/* Paging buttons */
		"sPageButton": "paginate_button",
		"sPageButtonActive": "current",
		"sPageButtonDisabled": "disabled",
	
		/* Striping classes */
		"sStripeOdd": "odd",
		"sStripeEven": "even",
	
		/* Empty row */
		"sRowEmpty": "dataTables_empty",
	
		/* Features */
		"sWrapper": "dataTables_wrapper",
		"sFilter": "dataTables_filter",
		"sInfo": "dataTables_info",
		"sPaging": "dataTables_paginate paging_", /* Note that the type is postfixed */
		"sLength": "dataTables_length",
		"sProcessing": "dataTables_processing",
	
		/* Sorting */
		"sSortAsc": "sorting_asc",
		"sSortDesc": "sorting_desc",
		"sSortable": "sorting", /* Sortable in both directions */
		"sSortableAsc": "sorting_asc_disabled",
		"sSortableDesc": "sorting_desc_disabled",
		"sSortableNone": "sorting_disabled",
		"sSortColumn": "sorting_", /* Note that an int is postfixed for the sorting order */
	
		/* Filtering */
		"sFilterInput": "",
	
		/* Page length */
		"sLengthSelect": "",
	
		/* Scrolling */
		"sScrollWrapper": "dataTables_scroll",
		"sScrollHead": "dataTables_scrollHead",
		"sScrollHeadInner": "dataTables_scrollHeadInner",
		"sScrollBody": "dataTables_scrollBody",
		"sScrollFoot": "dataTables_scrollFoot",
		"sScrollFootInner": "dataTables_scrollFootInner",
	
		/* Misc */
		"sHeaderTH": "",
		"sFooterTH": "",
	
		// Deprecated
		"sSortJUIAsc": "",
		"sSortJUIDesc": "",
		"sSortJUI": "",
		"sSortJUIAscAllowed": "",
		"sSortJUIDescAllowed": "",
		"sSortJUIWrapper": "",
		"sSortIcon": "",
		"sJUIHeader": "",
		"sJUIFooter": ""
	} );
	
	
	var extPagination = DataTable.ext.pager;
	
	function _numbers ( page, pages ) {
		var
			numbers = [],
			buttons = extPagination.numbers_length,
			half = Math.floor( buttons / 2 ),
			i = 1;
	
		if ( pages <= buttons ) {
			numbers = _range( 0, pages );
		}
		else if ( page <= half ) {
			numbers = _range( 0, buttons-2 );
			numbers.push( 'ellipsis' );
			numbers.push( pages-1 );
		}
		else if ( page >= pages - 1 - half ) {
			numbers = _range( pages-(buttons-2), pages );
			numbers.splice( 0, 0, 'ellipsis' ); // no unshift in ie6
			numbers.splice( 0, 0, 0 );
		}
		else {
			numbers = _range( page-half+2, page+half-1 );
			numbers.push( 'ellipsis' );
			numbers.push( pages-1 );
			numbers.splice( 0, 0, 'ellipsis' );
			numbers.splice( 0, 0, 0 );
		}
	
		numbers.DT_el = 'span';
		return numbers;
	}
	
	
	$.extend( extPagination, {
		simple: function ( page, pages ) {
			return [ 'previous', 'next' ];
		},
	
		full: function ( page, pages ) {
			return [  'first', 'previous', 'next', 'last' ];
		},
	
		numbers: function ( page, pages ) {
			return [ _numbers(page, pages) ];
		},
	
		simple_numbers: function ( page, pages ) {
			return [ 'previous', _numbers(page, pages), 'next' ];
		},
	
		full_numbers: function ( page, pages ) {
			return [ 'first', 'previous', _numbers(page, pages), 'next', 'last' ];
		},
		
		first_last_numbers: function (page, pages) {
	 		return ['first', _numbers(page, pages), 'last'];
	 	},
	
		// For testing and plug-ins to use
		_numbers: _numbers,
	
		// Number of number buttons (including ellipsis) to show. _Must be odd!_
		numbers_length: 7
	} );
	
	
	$.extend( true, DataTable.ext.renderer, {
		pageButton: {
			_: function ( settings, host, idx, buttons, page, pages ) {
				var classes = settings.oClasses;
				var lang = settings.oLanguage.oPaginate;
				var aria = settings.oLanguage.oAria.paginate || {};
				var btnDisplay, btnClass, counter=0;
	
				var attach = function( container, buttons ) {
					var i, ien, node, button;
					var clickHandler = function ( e ) {
						_fnPageChange( settings, e.data.action, true );
					};
	
					for ( i=0, ien=buttons.length ; i<ien ; i++ ) {
						button = buttons[i];
	
						if ( $.isArray( button ) ) {
							var inner = $( '<'+(button.DT_el || 'div')+'/>' )
								.appendTo( container );
							attach( inner, button );
						}
						else {
							btnDisplay = null;
							btnClass = '';
	
							switch ( button ) {
								case 'ellipsis':
									container.append('<span class="ellipsis">&#x2026;</span>');
									break;
	
								case 'first':
									btnDisplay = lang.sFirst;
									btnClass = button + (page > 0 ?
										'' : ' '+classes.sPageButtonDisabled);
									break;
	
								case 'previous':
									btnDisplay = lang.sPrevious;
									btnClass = button + (page > 0 ?
										'' : ' '+classes.sPageButtonDisabled);
									break;
	
								case 'next':
									btnDisplay = lang.sNext;
									btnClass = button + (page < pages-1 ?
										'' : ' '+classes.sPageButtonDisabled);
									break;
	
								case 'last':
									btnDisplay = lang.sLast;
									btnClass = button + (page < pages-1 ?
										'' : ' '+classes.sPageButtonDisabled);
									break;
	
								default:
									btnDisplay = button + 1;
									btnClass = page === button ?
										classes.sPageButtonActive : '';
									break;
							}
	
							if ( btnDisplay !== null ) {
								node = $('<a>', {
										'class': classes.sPageButton+' '+btnClass,
										'aria-controls': settings.sTableId,
										'aria-label': aria[ button ],
										'data-dt-idx': counter,
										'tabindex': settings.iTabIndex,
										'id': idx === 0 && typeof button === 'string' ?
											settings.sTableId +'_'+ button :
											null
									} )
									.html( btnDisplay )
									.appendTo( container );
	
								_fnBindAction(
									node, {action: button}, clickHandler
								);
	
								counter++;
							}
						}
					}
				};
	
				// IE9 throws an 'unknown error' if document.activeElement is used
				// inside an iframe or frame. Try / catch the error. Not good for
				// accessibility, but neither are frames.
				var activeEl;
	
				try {
					// Because this approach is destroying and recreating the paging
					// elements, focus is lost on the select button which is bad for
					// accessibility. So we want to restore focus once the draw has
					// completed
					activeEl = $(host).find(document.activeElement).data('dt-idx');
				}
				catch (e) {}
	
				attach( $(host).empty(), buttons );
	
				if ( activeEl !== undefined ) {
					$(host).find( '[data-dt-idx='+activeEl+']' ).focus();
				}
			}
		}
	} );
	
	
	
	// Built in type detection. See model.ext.aTypes for information about
	// what is required from this methods.
	$.extend( DataTable.ext.type.detect, [
		// Plain numbers - first since V8 detects some plain numbers as dates
		// e.g. Date.parse('55') (but not all, e.g. Date.parse('22')...).
		function ( d, settings )
		{
			var decimal = settings.oLanguage.sDecimal;
			return _isNumber( d, decimal ) ? 'num'+decimal : null;
		},
	
		// Dates (only those recognised by the browser's Date.parse)
		function ( d, settings )
		{
			// V8 tries _very_ hard to make a string passed into `Date.parse()`
			// valid, so we need to use a regex to restrict date formats. Use a
			// plug-in for anything other than ISO8601 style strings
			if ( d && !(d instanceof Date) && ! _re_date.test(d) ) {
				return null;
			}
			var parsed = Date.parse(d);
			return (parsed !== null && !isNaN(parsed)) || _empty(d) ? 'date' : null;
		},
	
		// Formatted numbers
		function ( d, settings )
		{
			var decimal = settings.oLanguage.sDecimal;
			return _isNumber( d, decimal, true ) ? 'num-fmt'+decimal : null;
		},
	
		// HTML numeric
		function ( d, settings )
		{
			var decimal = settings.oLanguage.sDecimal;
			return _htmlNumeric( d, decimal ) ? 'html-num'+decimal : null;
		},
	
		// HTML numeric, formatted
		function ( d, settings )
		{
			var decimal = settings.oLanguage.sDecimal;
			return _htmlNumeric( d, decimal, true ) ? 'html-num-fmt'+decimal : null;
		},
	
		// HTML (this is strict checking - there must be html)
		function ( d, settings )
		{
			return _empty( d ) || (typeof d === 'string' && d.indexOf('<') !== -1) ?
				'html' : null;
		}
	] );
	
	
	
	// Filter formatting functions. See model.ext.ofnSearch for information about
	// what is required from these methods.
	// 
	// Note that additional search methods are added for the html numbers and
	// html formatted numbers by `_addNumericSort()` when we know what the decimal
	// place is
	
	
	$.extend( DataTable.ext.type.search, {
		html: function ( data ) {
			return _empty(data) ?
				data :
				typeof data === 'string' ?
					data
						.replace( _re_new_lines, " " )
						.replace( _re_html, "" ) :
					'';
		},
	
		string: function ( data ) {
			return _empty(data) ?
				data :
				typeof data === 'string' ?
					data.replace( _re_new_lines, " " ) :
					data;
		}
	} );
	
	
	
	var __numericReplace = function ( d, decimalPlace, re1, re2 ) {
		if ( d !== 0 && (!d || d === '-') ) {
			return -Infinity;
		}
	
		// If a decimal place other than `.` is used, it needs to be given to the
		// function so we can detect it and replace with a `.` which is the only
		// decimal place Javascript recognises - it is not locale aware.
		if ( decimalPlace ) {
			d = _numToDecimal( d, decimalPlace );
		}
	
		if ( d.replace ) {
			if ( re1 ) {
				d = d.replace( re1, '' );
			}
	
			if ( re2 ) {
				d = d.replace( re2, '' );
			}
		}
	
		return d * 1;
	};
	
	
	// Add the numeric 'deformatting' functions for sorting and search. This is done
	// in a function to provide an easy ability for the language options to add
	// additional methods if a non-period decimal place is used.
	function _addNumericSort ( decimalPlace ) {
		$.each(
			{
				// Plain numbers
				"num": function ( d ) {
					return __numericReplace( d, decimalPlace );
				},
	
				// Formatted numbers
				"num-fmt": function ( d ) {
					return __numericReplace( d, decimalPlace, _re_formatted_numeric );
				},
	
				// HTML numeric
				"html-num": function ( d ) {
					return __numericReplace( d, decimalPlace, _re_html );
				},
	
				// HTML numeric, formatted
				"html-num-fmt": function ( d ) {
					return __numericReplace( d, decimalPlace, _re_html, _re_formatted_numeric );
				}
			},
			function ( key, fn ) {
				// Add the ordering method
				_ext.type.order[ key+decimalPlace+'-pre' ] = fn;
	
				// For HTML types add a search formatter that will strip the HTML
				if ( key.match(/^html\-/) ) {
					_ext.type.search[ key+decimalPlace ] = _ext.type.search.html;
				}
			}
		);
	}
	
	
	// Default sort methods
	$.extend( _ext.type.order, {
		// Dates
		"date-pre": function ( d ) {
			return Date.parse( d ) || -Infinity;
		},
	
		// html
		"html-pre": function ( a ) {
			return _empty(a) ?
				'' :
				a.replace ?
					a.replace( /<.*?>/g, "" ).toLowerCase() :
					a+'';
		},
	
		// string
		"string-pre": function ( a ) {
			// This is a little complex, but faster than always calling toString,
			// http://jsperf.com/tostring-v-check
			return _empty(a) ?
				'' :
				typeof a === 'string' ?
					a.toLowerCase() :
					! a.toString ?
						'' :
						a.toString();
		},
	
		// string-asc and -desc are retained only for compatibility with the old
		// sort methods
		"string-asc": function ( x, y ) {
			return ((x < y) ? -1 : ((x > y) ? 1 : 0));
		},
	
		"string-desc": function ( x, y ) {
			return ((x < y) ? 1 : ((x > y) ? -1 : 0));
		}
	} );
	
	
	// Numeric sorting types - order doesn't matter here
	_addNumericSort( '' );
	
	
	$.extend( true, DataTable.ext.renderer, {
		header: {
			_: function ( settings, cell, column, classes ) {
				// No additional mark-up required
				// Attach a sort listener to update on sort - note that using the
				// `DT` namespace will allow the event to be removed automatically
				// on destroy, while the `dt` namespaced event is the one we are
				// listening for
				$(settings.nTable).on( 'order.dt.DT', function ( e, ctx, sorting, columns ) {
					if ( settings !== ctx ) { // need to check this this is the host
						return;               // table, not a nested one
					}
	
					var colIdx = column.idx;
	
					cell
						.removeClass(
							column.sSortingClass +' '+
							classes.sSortAsc +' '+
							classes.sSortDesc
						)
						.addClass( columns[ colIdx ] == 'asc' ?
							classes.sSortAsc : columns[ colIdx ] == 'desc' ?
								classes.sSortDesc :
								column.sSortingClass
						);
				} );
			},
	
			jqueryui: function ( settings, cell, column, classes ) {
				$('<div/>')
					.addClass( classes.sSortJUIWrapper )
					.append( cell.contents() )
					.append( $('<span/>')
						.addClass( classes.sSortIcon+' '+column.sSortingClassJUI )
					)
					.appendTo( cell );
	
				// Attach a sort listener to update on sort
				$(settings.nTable).on( 'order.dt.DT', function ( e, ctx, sorting, columns ) {
					if ( settings !== ctx ) {
						return;
					}
	
					var colIdx = column.idx;
	
					cell
						.removeClass( classes.sSortAsc +" "+classes.sSortDesc )
						.addClass( columns[ colIdx ] == 'asc' ?
							classes.sSortAsc : columns[ colIdx ] == 'desc' ?
								classes.sSortDesc :
								column.sSortingClass
						);
	
					cell
						.find( 'span.'+classes.sSortIcon )
						.removeClass(
							classes.sSortJUIAsc +" "+
							classes.sSortJUIDesc +" "+
							classes.sSortJUI +" "+
							classes.sSortJUIAscAllowed +" "+
							classes.sSortJUIDescAllowed
						)
						.addClass( columns[ colIdx ] == 'asc' ?
							classes.sSortJUIAsc : columns[ colIdx ] == 'desc' ?
								classes.sSortJUIDesc :
								column.sSortingClassJUI
						);
				} );
			}
		}
	} );
	
	/*
	 * Public helper functions. These aren't used internally by DataTables, or
	 * called by any of the options passed into DataTables, but they can be used
	 * externally by developers working with DataTables. They are helper functions
	 * to make working with DataTables a little bit easier.
	 */
	
	var __htmlEscapeEntities = function ( d ) {
		return typeof d === 'string' ?
			d.replace(/</g, '&lt;').replace(/>/g, '&gt;').replace(/"/g, '&quot;') :
			d;
	};
	
	/**
	 * Helpers for `columns.render`.
	 *
	 * The options defined here can be used with the `columns.render` initialisation
	 * option to provide a display renderer. The following functions are defined:
	 *
	 * * `number` - Will format numeric data (defined by `columns.data`) for
	 *   display, retaining the original unformatted data for sorting and filtering.
	 *   It takes 5 parameters:
	 *   * `string` - Thousands grouping separator
	 *   * `string` - Decimal point indicator
	 *   * `integer` - Number of decimal points to show
	 *   * `string` (optional) - Prefix.
	 *   * `string` (optional) - Postfix (/suffix).
	 * * `text` - Escape HTML to help prevent XSS attacks. It has no optional
	 *   parameters.
	 *
	 * @example
	 *   // Column definition using the number renderer
	 *   {
	 *     data: "salary",
	 *     render: $.fn.dataTable.render.number( '\'', '.', 0, '$' )
	 *   }
	 *
	 * @namespace
	 */
	DataTable.render = {
		number: function ( thousands, decimal, precision, prefix, postfix ) {
			return {
				display: function ( d ) {
					if ( typeof d !== 'number' && typeof d !== 'string' ) {
						return d;
					}
	
					var negative = d < 0 ? '-' : '';
					var flo = parseFloat( d );
	
					// If NaN then there isn't much formatting that we can do - just
					// return immediately, escaping any HTML (this was supposed to
					// be a number after all)
					if ( isNaN( flo ) ) {
						return __htmlEscapeEntities( d );
					}
	
					flo = flo.toFixed( precision );
					d = Math.abs( flo );
	
					var intPart = parseInt( d, 10 );
					var floatPart = precision ?
						decimal+(d - intPart).toFixed( precision ).substring( 2 ):
						'';
	
					return negative + (prefix||'') +
						intPart.toString().replace(
							/\B(?=(\d{3})+(?!\d))/g, thousands
						) +
						floatPart +
						(postfix||'');
				}
			};
		},
	
		text: function () {
			return {
				display: __htmlEscapeEntities
			};
		}
	};
	
	
	/*
	 * This is really a good bit rubbish this method of exposing the internal methods
	 * publicly... - To be fixed in 2.0 using methods on the prototype
	 */
	
	
	/**
	 * Create a wrapper function for exporting an internal functions to an external API.
	 *  @param {string} fn API function name
	 *  @returns {function} wrapped function
	 *  @memberof DataTable#internal
	 */
	function _fnExternApiFunc (fn)
	{
		return function() {
			var args = [_fnSettingsFromNode( this[DataTable.ext.iApiIndex] )].concat(
				Array.prototype.slice.call(arguments)
			);
			return DataTable.ext.internal[fn].apply( this, args );
		};
	}
	
	
	/**
	 * Reference to internal functions for use by plug-in developers. Note that
	 * these methods are references to internal functions and are considered to be
	 * private. If you use these methods, be aware that they are liable to change
	 * between versions.
	 *  @namespace
	 */
	$.extend( DataTable.ext.internal, {
		_fnExternApiFunc: _fnExternApiFunc,
		_fnBuildAjax: _fnBuildAjax,
		_fnAjaxUpdate: _fnAjaxUpdate,
		_fnAjaxParameters: _fnAjaxParameters,
		_fnAjaxUpdateDraw: _fnAjaxUpdateDraw,
		_fnAjaxDataSrc: _fnAjaxDataSrc,
		_fnAddColumn: _fnAddColumn,
		_fnColumnOptions: _fnColumnOptions,
		_fnAdjustColumnSizing: _fnAdjustColumnSizing,
		_fnVisibleToColumnIndex: _fnVisibleToColumnIndex,
		_fnColumnIndexToVisible: _fnColumnIndexToVisible,
		_fnVisbleColumns: _fnVisbleColumns,
		_fnGetColumns: _fnGetColumns,
		_fnColumnTypes: _fnColumnTypes,
		_fnApplyColumnDefs: _fnApplyColumnDefs,
		_fnHungarianMap: _fnHungarianMap,
		_fnCamelToHungarian: _fnCamelToHungarian,
		_fnLanguageCompat: _fnLanguageCompat,
		_fnBrowserDetect: _fnBrowserDetect,
		_fnAddData: _fnAddData,
		_fnAddTr: _fnAddTr,
		_fnNodeToDataIndex: _fnNodeToDataIndex,
		_fnNodeToColumnIndex: _fnNodeToColumnIndex,
		_fnGetCellData: _fnGetCellData,
		_fnSetCellData: _fnSetCellData,
		_fnSplitObjNotation: _fnSplitObjNotation,
		_fnGetObjectDataFn: _fnGetObjectDataFn,
		_fnSetObjectDataFn: _fnSetObjectDataFn,
		_fnGetDataMaster: _fnGetDataMaster,
		_fnClearTable: _fnClearTable,
		_fnDeleteIndex: _fnDeleteIndex,
		_fnInvalidate: _fnInvalidate,
		_fnGetRowElements: _fnGetRowElements,
		_fnCreateTr: _fnCreateTr,
		_fnBuildHead: _fnBuildHead,
		_fnDrawHead: _fnDrawHead,
		_fnDraw: _fnDraw,
		_fnReDraw: _fnReDraw,
		_fnAddOptionsHtml: _fnAddOptionsHtml,
		_fnDetectHeader: _fnDetectHeader,
		_fnGetUniqueThs: _fnGetUniqueThs,
		_fnFeatureHtmlFilter: _fnFeatureHtmlFilter,
		_fnFilterComplete: _fnFilterComplete,
		_fnFilterCustom: _fnFilterCustom,
		_fnFilterColumn: _fnFilterColumn,
		_fnFilter: _fnFilter,
		_fnFilterCreateSearch: _fnFilterCreateSearch,
		_fnEscapeRegex: _fnEscapeRegex,
		_fnFilterData: _fnFilterData,
		_fnFeatureHtmlInfo: _fnFeatureHtmlInfo,
		_fnUpdateInfo: _fnUpdateInfo,
		_fnInfoMacros: _fnInfoMacros,
		_fnInitialise: _fnInitialise,
		_fnInitComplete: _fnInitComplete,
		_fnLengthChange: _fnLengthChange,
		_fnFeatureHtmlLength: _fnFeatureHtmlLength,
		_fnFeatureHtmlPaginate: _fnFeatureHtmlPaginate,
		_fnPageChange: _fnPageChange,
		_fnFeatureHtmlProcessing: _fnFeatureHtmlProcessing,
		_fnProcessingDisplay: _fnProcessingDisplay,
		_fnFeatureHtmlTable: _fnFeatureHtmlTable,
		_fnScrollDraw: _fnScrollDraw,
		_fnApplyToChildren: _fnApplyToChildren,
		_fnCalculateColumnWidths: _fnCalculateColumnWidths,
		_fnThrottle: _fnThrottle,
		_fnConvertToWidth: _fnConvertToWidth,
		_fnGetWidestNode: _fnGetWidestNode,
		_fnGetMaxLenString: _fnGetMaxLenString,
		_fnStringToCss: _fnStringToCss,
		_fnSortFlatten: _fnSortFlatten,
		_fnSort: _fnSort,
		_fnSortAria: _fnSortAria,
		_fnSortListener: _fnSortListener,
		_fnSortAttachListener: _fnSortAttachListener,
		_fnSortingClasses: _fnSortingClasses,
		_fnSortData: _fnSortData,
		_fnSaveState: _fnSaveState,
		_fnLoadState: _fnLoadState,
		_fnSettingsFromNode: _fnSettingsFromNode,
		_fnLog: _fnLog,
		_fnMap: _fnMap,
		_fnBindAction: _fnBindAction,
		_fnCallbackReg: _fnCallbackReg,
		_fnCallbackFire: _fnCallbackFire,
		_fnLengthOverflow: _fnLengthOverflow,
		_fnRenderer: _fnRenderer,
		_fnDataSource: _fnDataSource,
		_fnRowAttributes: _fnRowAttributes,
		_fnCalculateEnd: function () {} // Used by a lot of plug-ins, but redundant
		                                // in 1.10, so this dead-end function is
		                                // added to prevent errors
	} );
	

	// jQuery access
	$.fn.dataTable = DataTable;

	// Provide access to the host jQuery object (circular reference)
	DataTable.$ = $;

	// Legacy aliases
	$.fn.dataTableSettings = DataTable.settings;
	$.fn.dataTableExt = DataTable.ext;

	// With a capital `D` we return a DataTables API instance rather than a
	// jQuery object
	$.fn.DataTable = function ( opts ) {
		return $(this).dataTable( opts ).api();
	};

	// All properties that are available to $.fn.dataTable should also be
	// available on $.fn.DataTable
	$.each( DataTable, function ( prop, val ) {
		$.fn.DataTable[ prop ] = val;
	} );


	// Information about events fired by DataTables - for documentation.
	/**
	 * Draw event, fired whenever the table is redrawn on the page, at the same
	 * point as fnDrawCallback. This may be useful for binding events or
	 * performing calculations when the table is altered at all.
	 *  @name DataTable#draw.dt
	 *  @event
	 *  @param {event} e jQuery event object
	 *  @param {object} o DataTables settings object {@link DataTable.models.oSettings}
	 */

	/**
	 * Search event, fired when the searching applied to the table (using the
	 * built-in global search, or column filters) is altered.
	 *  @name DataTable#search.dt
	 *  @event
	 *  @param {event} e jQuery event object
	 *  @param {object} o DataTables settings object {@link DataTable.models.oSettings}
	 */

	/**
	 * Page change event, fired when the paging of the table is altered.
	 *  @name DataTable#page.dt
	 *  @event
	 *  @param {event} e jQuery event object
	 *  @param {object} o DataTables settings object {@link DataTable.models.oSettings}
	 */

	/**
	 * Order event, fired when the ordering applied to the table is altered.
	 *  @name DataTable#order.dt
	 *  @event
	 *  @param {event} e jQuery event object
	 *  @param {object} o DataTables settings object {@link DataTable.models.oSettings}
	 */

	/**
	 * DataTables initialisation complete event, fired when the table is fully
	 * drawn, including Ajax data loaded, if Ajax data is required.
	 *  @name DataTable#init.dt
	 *  @event
	 *  @param {event} e jQuery event object
	 *  @param {object} oSettings DataTables settings object
	 *  @param {object} json The JSON object request from the server - only
	 *    present if client-side Ajax sourced data is used</li></ol>
	 */

	/**
	 * State save event, fired when the table has changed state a new state save
	 * is required. This event allows modification of the state saving object
	 * prior to actually doing the save, including addition or other state
	 * properties (for plug-ins) or modification of a DataTables core property.
	 *  @name DataTable#stateSaveParams.dt
	 *  @event
	 *  @param {event} e jQuery event object
	 *  @param {object} oSettings DataTables settings object
	 *  @param {object} json The state information to be saved
	 */

	/**
	 * State load event, fired when the table is loading state from the stored
	 * data, but prior to the settings object being modified by the saved state
	 * - allowing modification of the saved state is required or loading of
	 * state for a plug-in.
	 *  @name DataTable#stateLoadParams.dt
	 *  @event
	 *  @param {event} e jQuery event object
	 *  @param {object} oSettings DataTables settings object
	 *  @param {object} json The saved state information
	 */

	/**
	 * State loaded event, fired when state has been loaded from stored data and
	 * the settings object has been modified by the loaded data.
	 *  @name DataTable#stateLoaded.dt
	 *  @event
	 *  @param {event} e jQuery event object
	 *  @param {object} oSettings DataTables settings object
	 *  @param {object} json The saved state information
	 */

	/**
	 * Processing event, fired when DataTables is doing some kind of processing
	 * (be it, order, searcg or anything else). It can be used to indicate to
	 * the end user that there is something happening, or that something has
	 * finished.
	 *  @name DataTable#processing.dt
	 *  @event
	 *  @param {event} e jQuery event object
	 *  @param {object} oSettings DataTables settings object
	 *  @param {boolean} bShow Flag for if DataTables is doing processing or not
	 */

	/**
	 * Ajax (XHR) event, fired whenever an Ajax request is completed from a
	 * request to made to the server for new data. This event is called before
	 * DataTables processed the returned data, so it can also be used to pre-
	 * process the data returned from the server, if needed.
	 *
	 * Note that this trigger is called in `fnServerData`, if you override
	 * `fnServerData` and which to use this event, you need to trigger it in you
	 * success function.
	 *  @name DataTable#xhr.dt
	 *  @event
	 *  @param {event} e jQuery event object
	 *  @param {object} o DataTables settings object {@link DataTable.models.oSettings}
	 *  @param {object} json JSON returned from the server
	 *
	 *  @example
	 *     // Use a custom property returned from the server in another DOM element
	 *     $('#table').dataTable().on('xhr.dt', function (e, settings, json) {
	 *       $('#status').html( json.status );
	 *     } );
	 *
	 *  @example
	 *     // Pre-process the data returned from the server
	 *     $('#table').dataTable().on('xhr.dt', function (e, settings, json) {
	 *       for ( var i=0, ien=json.aaData.length ; i<ien ; i++ ) {
	 *         json.aaData[i].sum = json.aaData[i].one + json.aaData[i].two;
	 *       }
	 *       // Note no return - manipulate the data directly in the JSON object.
	 *     } );
	 */

	/**
	 * Destroy event, fired when the DataTable is destroyed by calling fnDestroy
	 * or passing the bDestroy:true parameter in the initialisation object. This
	 * can be used to remove bound events, added DOM nodes, etc.
	 *  @name DataTable#destroy.dt
	 *  @event
	 *  @param {event} e jQuery event object
	 *  @param {object} o DataTables settings object {@link DataTable.models.oSettings}
	 */

	/**
	 * Page length change event, fired when number of records to show on each
	 * page (the length) is changed.
	 *  @name DataTable#length.dt
	 *  @event
	 *  @param {event} e jQuery event object
	 *  @param {object} o DataTables settings object {@link DataTable.models.oSettings}
	 *  @param {integer} len New length
	 */

	/**
	 * Column sizing has changed.
	 *  @name DataTable#column-sizing.dt
	 *  @event
	 *  @param {event} e jQuery event object
	 *  @param {object} o DataTables settings object {@link DataTable.models.oSettings}
	 */

	/**
	 * Column visibility has changed.
	 *  @name DataTable#column-visibility.dt
	 *  @event
	 *  @param {event} e jQuery event object
	 *  @param {object} o DataTables settings object {@link DataTable.models.oSettings}
	 *  @param {int} column Column index
	 *  @param {bool} vis `false` if column now hidden, or `true` if visible
	 */

	return $.fn.dataTable;
}));


/***/ }),
/* 5 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_RESULT__;/*
 * JavaScript Load Image
 * https://github.com/blueimp/JavaScript-Load-Image
 *
 * Copyright 2011, Sebastian Tschan
 * https://blueimp.net
 *
 * Licensed under the MIT license:
 * http://www.opensource.org/licenses/MIT
 */

/*global define, module, window, document, URL, webkitURL, FileReader */

;(function ($) {
  'use strict'

  // Loads an image for a given File object.
  // Invokes the callback with an img or optional canvas
  // element (if supported by the browser) as parameter:
  var loadImage = function (file, callback, options) {
    var img = document.createElement('img')
    var url
    var oUrl
    img.onerror = callback
    img.onload = function () {
      if (oUrl && !(options && options.noRevoke)) {
        loadImage.revokeObjectURL(oUrl)
      }
      if (callback) {
        callback(loadImage.scale(img, options))
      }
    }
    if (loadImage.isInstanceOf('Blob', file) ||
      // Files are also Blob instances, but some browsers
      // (Firefox 3.6) support the File API but not Blobs:
      loadImage.isInstanceOf('File', file)) {
      url = oUrl = loadImage.createObjectURL(file)
      // Store the file type for resize processing:
      img._type = file.type
    } else if (typeof file === 'string') {
      url = file
      if (options && options.crossOrigin) {
        img.crossOrigin = options.crossOrigin
      }
    } else {
      return false
    }
    if (url) {
      img.src = url
      return img
    }
    return loadImage.readFile(file, function (e) {
      var target = e.target
      if (target && target.result) {
        img.src = target.result
      } else {
        if (callback) {
          callback(e)
        }
      }
    })
  }
  // The check for URL.revokeObjectURL fixes an issue with Opera 12,
  // which provides URL.createObjectURL but doesn't properly implement it:
  var urlAPI = (window.createObjectURL && window) ||
                (window.URL && URL.revokeObjectURL && URL) ||
                (window.webkitURL && webkitURL)

  loadImage.isInstanceOf = function (type, obj) {
    // Cross-frame instanceof check
    return Object.prototype.toString.call(obj) === '[object ' + type + ']'
  }

  // Transform image coordinates, allows to override e.g.
  // the canvas orientation based on the orientation option,
  // gets canvas, options passed as arguments:
  loadImage.transformCoordinates = function () {
    return
  }

  // Returns transformed options, allows to override e.g.
  // maxWidth, maxHeight and crop options based on the aspectRatio.
  // gets img, options passed as arguments:
  loadImage.getTransformedOptions = function (img, options) {
    var aspectRatio = options.aspectRatio
    var newOptions
    var i
    var width
    var height
    if (!aspectRatio) {
      return options
    }
    newOptions = {}
    for (i in options) {
      if (options.hasOwnProperty(i)) {
        newOptions[i] = options[i]
      }
    }
    newOptions.crop = true
    width = img.naturalWidth || img.width
    height = img.naturalHeight || img.height
    if (width / height > aspectRatio) {
      newOptions.maxWidth = height * aspectRatio
      newOptions.maxHeight = height
    } else {
      newOptions.maxWidth = width
      newOptions.maxHeight = width / aspectRatio
    }
    return newOptions
  }

  // Canvas render method, allows to implement a different rendering algorithm:
  loadImage.renderImageToCanvas = function (
    canvas,
    img,
    sourceX,
    sourceY,
    sourceWidth,
    sourceHeight,
    destX,
    destY,
    destWidth,
    destHeight
  ) {
    canvas.getContext('2d').drawImage(
      img,
      sourceX,
      sourceY,
      sourceWidth,
      sourceHeight,
      destX,
      destY,
      destWidth,
      destHeight
    )
    return canvas
  }

  // This method is used to determine if the target image
  // should be a canvas element:
  loadImage.hasCanvasOption = function (options) {
    return options.canvas || options.crop || !!options.aspectRatio
  }

  // Scales and/or crops the given image (img or canvas HTML element)
  // using the given options.
  // Returns a canvas object if the browser supports canvas
  // and the hasCanvasOption method returns true or a canvas
  // object is passed as image, else the scaled image:
  loadImage.scale = function (img, options) {
    options = options || {}
    var canvas = document.createElement('canvas')
    var useCanvas = img.getContext ||
                    (loadImage.hasCanvasOption(options) && canvas.getContext)
    var width = img.naturalWidth || img.width
    var height = img.naturalHeight || img.height
    var destWidth = width
    var destHeight = height
    var maxWidth
    var maxHeight
    var minWidth
    var minHeight
    var sourceWidth
    var sourceHeight
    var sourceX
    var sourceY
    var pixelRatio
    var downsamplingRatio
    var tmp
    function scaleUp () {
      var scale = Math.max(
        (minWidth || destWidth) / destWidth,
        (minHeight || destHeight) / destHeight
      )
      if (scale > 1) {
        destWidth *= scale
        destHeight *= scale
      }
    }
    function scaleDown () {
      var scale = Math.min(
        (maxWidth || destWidth) / destWidth,
        (maxHeight || destHeight) / destHeight
      )
      if (scale < 1) {
        destWidth *= scale
        destHeight *= scale
      }
    }
    if (useCanvas) {
      options = loadImage.getTransformedOptions(img, options)
      sourceX = options.left || 0
      sourceY = options.top || 0
      if (options.sourceWidth) {
        sourceWidth = options.sourceWidth
        if (options.right !== undefined && options.left === undefined) {
          sourceX = width - sourceWidth - options.right
        }
      } else {
        sourceWidth = width - sourceX - (options.right || 0)
      }
      if (options.sourceHeight) {
        sourceHeight = options.sourceHeight
        if (options.bottom !== undefined && options.top === undefined) {
          sourceY = height - sourceHeight - options.bottom
        }
      } else {
        sourceHeight = height - sourceY - (options.bottom || 0)
      }
      destWidth = sourceWidth
      destHeight = sourceHeight
    }
    maxWidth = options.maxWidth
    maxHeight = options.maxHeight
    minWidth = options.minWidth
    minHeight = options.minHeight
    if (useCanvas && maxWidth && maxHeight && options.crop) {
      destWidth = maxWidth
      destHeight = maxHeight
      tmp = sourceWidth / sourceHeight - maxWidth / maxHeight
      if (tmp < 0) {
        sourceHeight = maxHeight * sourceWidth / maxWidth
        if (options.top === undefined && options.bottom === undefined) {
          sourceY = (height - sourceHeight) / 2
        }
      } else if (tmp > 0) {
        sourceWidth = maxWidth * sourceHeight / maxHeight
        if (options.left === undefined && options.right === undefined) {
          sourceX = (width - sourceWidth) / 2
        }
      }
    } else {
      if (options.contain || options.cover) {
        minWidth = maxWidth = maxWidth || minWidth
        minHeight = maxHeight = maxHeight || minHeight
      }
      if (options.cover) {
        scaleDown()
        scaleUp()
      } else {
        scaleUp()
        scaleDown()
      }
    }
    if (useCanvas) {
      pixelRatio = options.pixelRatio
      if (pixelRatio > 1) {
        canvas.style.width = destWidth + 'px'
        canvas.style.height = destHeight + 'px'
        destWidth *= pixelRatio
        destHeight *= pixelRatio
        canvas.getContext('2d').scale(pixelRatio, pixelRatio)
      }
      downsamplingRatio = options.downsamplingRatio
      if (downsamplingRatio > 0 && downsamplingRatio < 1 &&
            destWidth < sourceWidth && destHeight < sourceHeight) {
        while (sourceWidth * downsamplingRatio > destWidth) {
          canvas.width = sourceWidth * downsamplingRatio
          canvas.height = sourceHeight * downsamplingRatio
          loadImage.renderImageToCanvas(
            canvas,
            img,
            sourceX,
            sourceY,
            sourceWidth,
            sourceHeight,
            0,
            0,
            canvas.width,
            canvas.height
          )
          sourceWidth = canvas.width
          sourceHeight = canvas.height
          img = document.createElement('canvas')
          img.width = sourceWidth
          img.height = sourceHeight
          loadImage.renderImageToCanvas(
            img,
            canvas,
            0,
            0,
            sourceWidth,
            sourceHeight,
            0,
            0,
            sourceWidth,
            sourceHeight
          )
        }
      }
      canvas.width = destWidth
      canvas.height = destHeight
      loadImage.transformCoordinates(
        canvas,
        options
      )
      return loadImage.renderImageToCanvas(
        canvas,
        img,
        sourceX,
        sourceY,
        sourceWidth,
        sourceHeight,
        0,
        0,
        destWidth,
        destHeight
      )
    }
    img.width = destWidth
    img.height = destHeight
    return img
  }

  loadImage.createObjectURL = function (file) {
    return urlAPI ? urlAPI.createObjectURL(file) : false
  }

  loadImage.revokeObjectURL = function (url) {
    return urlAPI ? urlAPI.revokeObjectURL(url) : false
  }

  // Loads a given File object via FileReader interface,
  // invokes the callback with the event object (load or error).
  // The result can be read via event.target.result:
  loadImage.readFile = function (file, callback, method) {
    if (window.FileReader) {
      var fileReader = new FileReader()
      fileReader.onload = fileReader.onerror = callback
      method = method || 'readAsDataURL'
      if (fileReader[method]) {
        fileReader[method](file)
        return fileReader
      }
    }
    return false
  }

  if (true) {
    !(__WEBPACK_AMD_DEFINE_RESULT__ = function () {
      return loadImage
    }.call(exports, __webpack_require__, exports, module),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__))
  } else if (typeof module === 'object' && module.exports) {
    module.exports = loadImage
  } else {
    $.loadImage = loadImage
  }
}(window))


/***/ }),
/* 6 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function(jQuery) {var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*!
 * Copyright 2016 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 */

/**
 * Un menú contextual consta de un menú dentro de una interfaz gráfica que se muestra a partir de una interacción del usuario. El menú contextual muestra una serie de opciones disponibles en el contexto o estado actual de la aplicación.
 *
 * @summary Componente RUP ContextMenu.
 * @module rup_contextMenu
 * @example
 * var properties = {
 *  items : {
 *       "edit": {name: "Edit", icon: "edit"},
 *       "cut": {name: "Cut", icon: "cut"},
 *       "copy": {name: "Copy", icon: "copy"},
 *       "paste": {name: "Paste", icon: "paste"},
 *       "delete": {name: "Delete", icon: "delete"},
 *       "sep1": "---------",
 *       "quit": {name: "Quit", icon: "quit"}
 *   }
 * };
 *
 * $('#contextMenu').rup_contextMenu(properties);
 */

/*global define */
/*global jQuery */

(function (factory) {
  if (true) {

    // AMD. Register as an anonymous module.
    !(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(2), __webpack_require__(265)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
  } else {

    // Browser globals
    factory(jQuery);
  }
})(function ($) {

  //****************************************************************************************************************
  // DEFINICIÓN BASE DEL PATRÓN (definición de la variable privada que contendrá los métodos y la función de jQuery)
  //****************************************************************************************************************


  var rup_contextMenu = {};

  //Se configura el arranque de UDA para que alberge el nuevo patrón
  $.extend($.rup.iniRup, $.rup.rupSelectorObjectConstructor('rup_contextMenu', rup_contextMenu));

  //*******************************
  // DEFINICIÓN DE MÉTODOS PÚBLICOS
  //*******************************
  $.fn.rup_contextMenu('extend', {
    /**
       * Muestra el menú contextual.
       *
       * @name show
       * @function
       * @example
       * $("#contextMenu").rup_contextMenu("show");
       */
    show: function show(position) {
      $(this).contextMenu(position);
    },
    /**
       * Oculta el menú contextual.
       *
       * @name jQuery.rup_contextMenu#hide
       * @function
       * @example
       * $("#contextMenu").rup_contextMenu("hide");
       */
    hide: function hide() {
      $(this).contextMenu('hide');
    },
    /**
       * Habilita el menú contextual. El menú se mostrará al lanzarse el evento asociado.
       *
       * @name enable
       * @function
       * @example
       * $("#contextMenu").rup_contextMenu("enable");
       */
    enable: function enable() {
      $(this).contextMenu(true);
    },
    /**
       * Deshabilita el menú contextual. El menú no se mostrará aunque se lance el evento asociado.
       *
       * @name disable
       * @function
       * @example
       * $("#contextMenu").rup_contextMenu("disable");
       */
    disable: function disable() {
      $(this).contextMenu(false);
    },
    /**
       * Elimina el menú contextual.
       *
       * @name destroy
       * @function
       * @example
       * $("#contextMenu").rup_contextMenu("destroy");
       */
    destroy: function destroy() {
      $.contextMenu('destroy', this.selector);
    }
  });

  //*******************************
  // DEFINICIÓN DE MÉTODOS PRIVADOS
  //*******************************
  $.fn.rup_contextMenu('extend', {
    /**
       * Método de inicialización del componente.
       *
       * @name _init
       * @function
       * @private
       * @param {object} args - Parámetros de inicialización del componente.
       */
    _init: function _init(args) {
      if (args.length > 1) {
        $.rup.errorGestor($.rup.i18nParse($.rup.i18n.base, 'rup_global.initError') + $(this).attr('id'));
      } else {
        //Se recogen y cruzan las paremetrizaciones del objeto
        var $self = this,
            settings = $.extend({}, $.fn.rup_contextMenu.defaults, args[0]),
            background_image,
            background_position;

        //Asociar el selector
        settings.selector = $self.selector;

        //TODO:ejemplo de title en el contextMenu
        //Procesar items para i18n

        if ($.rup_utils.aplicatioInPortal()) {
          settings.appendTo = '.r01gContainer';
        }

        //Lanzar el plugin subyaciente
        jQuery.contextMenu(settings);

        /* Añadir el estilo para la modificación del estilo del puntero del ratón */
        $self.addClass('context-menu-cursor');
        if (jQuery.rup.browser.isIE) {
          $self.css('cursor', settings.msieCursorCss);
        }

        /* Adecuar los cssSprites */
        $.each($('.context-menu-list.context-menu-root'), function (index, elem) {
          var $elem = jQuery(elem);
          if ($elem.data('contextMenuRoot').selector === settings.selector) {
            $elem.attr('id', $elem.data('contextMenuRoot').ns.substring(1));
            $.each($('.context-menu-item'), function (index, item) {
              var $item = jQuery(item),
                  contextMenuKey = $item.data('contextMenuKey'),
                  cssSprite,
                  itemCfg;
              if (contextMenuKey !== undefined) {
                itemCfg = settings.items[contextMenuKey];
                if (itemCfg !== undefined) {
                  cssSprite = itemCfg.cssSprite;
                  if (cssSprite !== undefined && !$item.hasClass('rup-css-sprite')) {
                    $item.addClass('rup-css-sprite');
                    $item.prepend($('<span>').addClass(cssSprite));
                  }
                  if (itemCfg.id !== undefined) {
                    $item.attr('id', itemCfg.id);
                  }
                }
              }
            });
          }
        });
      }
    }
  });

  //******************************************************
  // DEFINICIÓN DE LA CONFIGURACION POR DEFECTO DEL PATRON
  //******************************************************

  /**
    * Función de callback a ejecutar cuando se muestra el menú contextual.
    *
    * @callback jQuery.rup_contextMenu~onShowEvent
    * @param {object} opt - Opciones de configuración.
    * @return {boolean} - En caso de devolver false no se termina mostrando el menú.
    */

  /**
    * Función de callback a ejecutar cuando se oculta el menú contextual.
    *
    * @callback jQuery.rup_contextMenu~onHideEvent
    * @param {object} opt - Opciones de configuración.
    * @return {boolean} - En caso de devolver false no se termina ocultando el menú.
    */

  /**
    * Función de callback a ejecutar a partir de los eventos indicados en la propiedad trigger.
    *
    * @callback jQuery.rup_contextMenu~position
    * @param {jQuery} $menu - Referencia jQuery al objeto propio.
    * @param {number} x - Coordenada x proporcionada por el evento de mostrar el menú.
    * @param {number} y - Coordenada y proporcionada por el evento de mostrar el menú.
    */

  /**
    * Esta propiedad permite especificar una función de callback por defecto para aquellos ítems que no hayan especificado una función propia.
    *
    * @callback jQuery.rup_contextMenu~callback
    * @param {string} key - Key de la opción seleccionada.
    * @param {number} options - Opciones de configuración con los que se ha inicializado el componente.
    * @example
    * callback: function(key, options) {
    *    alert("clicked: " + key);
    * }
    */

  /**
    * Función de callback que devuelve el objeto de configuración del componente.
    *
    * @callback jQuery.rup_contextMenu~build
    * @param {jQuery} $trigger - Referencia jQuery del objeto disparador del callback.
    * @param {object} e - Objeto event correspondiente al evento que desencadena el callback.
    * @return {object} - Objeto de configuración del componente.
    * @example
    * $(".contextMenu-other").rup_contextMenu({
    *      trigger: 'none',
    *      build: function($trigger, e) {
    *          return {
    *              callback: function(key, options) {
    *              alert("clicked: " + key);
    *          },
    *          items: {
    *              "edit": {name: "Edit", icon: "edit"},
    *              "cut": {name: "Cut", icon: "cut"},
    *              "copy": {name: "Copy", icon: "copy"},
    *              "paste": {name: "Paste", icon: "paste"},
    *              "delete": {name: "Delete", icon: "delete"},
    *              "sep1": "---------",
    *              "quit": {name: "Quit", icon: "quit"}
    *          }
    *      };
    *  }
    * });
    */

  /**
    * @description Propiedades de configuración del componente.
    *
    * @name defaults
    * @property {object} items - Objeto que define los elementos que van a mostrarse en el menú contextual. En el siguiente apartado se explicará más en detalle como realizar esta definición.
    * @property {string} [appendTo] - Selector de jQuery que identifica el elemento del DOM a partir del cual se va a añadir el menú contextual generado.
    * @property {string} [trigger] - Determina el evento que va a lanzar la visualización del menú contextual. ("right","left", "hover", "none").
    * @property {boolean} [reposition] - Determina si un menú debe ser reposicionado (true) o reconstruido (false) en el caso de que el evento que lanza la visualización del menú contextual se ejecute por segunda vez.
    * @property {number} [delay=200] - Determina el tiempo de retardo antes de mostrar el menú contextual. Solo se aplica sobre el evento “hover”.
    * @property {boolean} [autoHide=false] - Indica si el menú contextual debe de ocultarse automáticamente cuando el cursor del ratón abandona la posición del menú contextual y el elemento que lo lanza.
    * @property {number} [zIndex=1] - Especifica el desplazamiento de zIndex que se aplica al calculado.
    * @property {string} [className] - Nombres de clases adicionales que se van a aplicar al menú contextual.
    * @property {object} animation - Determina la animación que se va a aplicar a la hora de mostrar/ocultar el menúcontextual. La configuración es la misma que la que utiliza para realizar la de los métodos show y hide de jQuery.
    * @property {object} [events] - Los eventos show y hide se ejecutan antes de el menú se muestre o se oculte. Mediante esta propiedad es posible indicar funciones de callback para ser ejecutadas en estos casos. Permiten devolver false para evitar continuar con el evento.
    * @property {jQuery.rup_contextMenu~onShowEvent} events.show - Función a ejecutar antes de que se muestre el menú.
    * @property {jQuery.rup_contextMenu~onHideEvent} events.hide - Función a ejecutar antes de que se oculte el menú.
    * @property {jQuery.rup_contextMenu~position} position - Función de callback que se ejecuta a partir de los eventos indicados en la propiedad trigger.
    * @property {string} determinePosition - Determina la posición del menú contextual de acuerdo al elemento disparador.
    * @property {jQuery.rup_contextMenu~callback} [callback] - Esta propiedad permite especificar una función de callback por defecto para aquellos ítems que no hayan especificado una función propia.
    * @property {jQuery.rup_contextMenu~build} [build] - Función de callback que devuelve el objeto de configuración del componente. En caso de especificar una función para la propiedad build la creación del menú no se realiza inicialmente sino que se demora hasta que se ejecuta el evento que lo muestra.
    * @property {boolean} [showCursor=true] - Determina si se va a modificar el estilo del puntero del ratón al posicionarse sobre el elemento que dispone de menú contextual. El tipo de puntero se determina mediante la clase CSS context-menu-cursor.
    * @property {string} [msieCursorCss="url("+$.rup.RUP+"/css/cursors/context-menu.cur),default"] - Esta propiedad se emplea para poder modificar la apariencia del cursor en Internet Explorer al posicionarse sobre un elemento que dispone de un menú contextual. Esto es debido a que el modo en el que hay que realizar la asignación del nuevo cursor no se puede realizar mediante un class
    */

  $.fn.rup_contextMenu.defaults = {
    autoHide: true,
    showCursor: true,
    msieCursorCss: 'url(' + $.rup.RUP + '/css/cursors/context-menu.cur),default'
  };
});
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))

/***/ }),
/* 7 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*
 * jQuery File Upload Processing Plugin
 * https://github.com/blueimp/jQuery-File-Upload
 *
 * Copyright 2012, Sebastian Tschan
 * https://blueimp.net
 *
 * Licensed under the MIT license:
 * http://www.opensource.org/licenses/MIT
 */

/* jshint nomen:false */
/* global define, require, window */

;(function (factory) {
    'use strict';
    if (true) {
        // Register as an anonymous AMD module:
        !(__WEBPACK_AMD_DEFINE_ARRAY__ = [
            __webpack_require__(0),
            __webpack_require__(219)
        ], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
    } else if (typeof exports === 'object') {
        // Node/CommonJS:
        factory(require('jquery'));
    } else {
        // Browser globals:
        factory(
            window.jQuery
        );
    }
}(function ($) {
    'use strict';

    var originalAdd = $.blueimp.fileupload.prototype.options.add;

    // The File Upload Processing plugin extends the fileupload widget
    // with file processing functionality:
    $.widget('blueimp.fileupload', $.blueimp.fileupload, {

        options: {
            // The list of processing actions:
            processQueue: [
                /*
                {
                    action: 'log',
                    type: 'debug'
                }
                */
            ],
            add: function (e, data) {
                var $this = $(this);
                data.process(function () {
                    return $this.fileupload('process', data);
                });
                originalAdd.call(this, e, data);
            }
        },

        processActions: {
            /*
            log: function (data, options) {
                console[options.type](
                    'Processing "' + data.files[data.index].name + '"'
                );
            }
            */
        },

        _processFile: function (data, originalData) {
            var that = this,
                dfd = $.Deferred().resolveWith(that, [data]),
                chain = dfd.promise();
            this._trigger('process', null, data);
            $.each(data.processQueue, function (i, settings) {
                var func = function (data) {
                    if (originalData.errorThrown) {
                        return $.Deferred()
                                .rejectWith(that, [originalData]).promise();
                    }
                    return that.processActions[settings.action].call(
                        that,
                        data,
                        settings
                    );
                };
                chain = chain.then(func, settings.always && func);
            });
            chain
                .done(function () {
                    that._trigger('processdone', null, data);
                    that._trigger('processalways', null, data);
                })
                .fail(function () {
                    that._trigger('processfail', null, data);
                    that._trigger('processalways', null, data);
                });
            return chain;
        },

        // Replaces the settings of each processQueue item that
        // are strings starting with an "@", using the remaining
        // substring as key for the option map,
        // e.g. "@autoUpload" is replaced with options.autoUpload:
        _transformProcessQueue: function (options) {
            var processQueue = [];
            $.each(options.processQueue, function () {
                var settings = {},
                    action = this.action,
                    prefix = this.prefix === true ? action : this.prefix;
                $.each(this, function (key, value) {
                    if ($.type(value) === 'string' &&
                            value.charAt(0) === '@') {
                        settings[key] = options[
                            value.slice(1) || (prefix ? prefix +
                                key.charAt(0).toUpperCase() + key.slice(1) : key)
                        ];
                    } else {
                        settings[key] = value;
                    }

                });
                processQueue.push(settings);
            });
            options.processQueue = processQueue;
        },

        // Returns the number of files currently in the processsing queue:
        processing: function () {
            return this._processing;
        },

        // Processes the files given as files property of the data parameter,
        // returns a Promise object that allows to bind callbacks:
        process: function (data) {
            var that = this,
                options = $.extend({}, this.options, data);
            if (options.processQueue && options.processQueue.length) {
                this._transformProcessQueue(options);
                if (this._processing === 0) {
                    this._trigger('processstart');
                }
                $.each(data.files, function (index) {
                    var opts = index ? $.extend({}, options) : options,
                        func = function () {
                            if (data.errorThrown) {
                                return $.Deferred()
                                        .rejectWith(that, [data]).promise();
                            }
                            return that._processFile(opts, data);
                        };
                    opts.index = index;
                    that._processing += 1;
                    that._processingQueue = that._processingQueue.then(func, func)
                        .always(function () {
                            that._processing -= 1;
                            if (that._processing === 0) {
                                that._trigger('processstop');
                            }
                        });
                });
            }
            return this._processingQueue;
        },

        _create: function () {
            this._super();
            this._processing = 0;
            this._processingQueue = $.Deferred().resolveWith(this)
                .promise();
        }

    });

}));


/***/ }),
/* 8 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function(jQuery) {var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*!
 * Copyright 2013 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 */

/**
 * Se informa al usuario de cómo interactuar con los elementos de la aplicación y del resultado de cualquier acción que realice o cualquier problema que tenga y de cómo solucionarlo.
 *
 * @summary Componente RUP Feedback.
 * @module rup_feedback
 * @example
 * var properties = {
 *   type: "ok",
 *   delay: 500,
 *   fadeSpeed: 600,
 *   gotoTop: false,
 *   block: false,
 *   closeLink: true
 * };
 * $("#id_capa").rup_feedback (properties);
 */

/*global define */
/*global jQuery */

(function (factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(2), __webpack_require__(9)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		factory(jQuery);
	}
})(function ($) {

	$.widget('$.rup_feedback', {
		/**
         * @description Opciones por defecto de configuración del widget.
         * @name options
         *
         * @property {string}  [type=null] - Tipo de feedback a mostrar [ok, alert, error].
         * @property {string}  [message]  -  Mensaje que se mostrará en el feedback. Si no se define simplemente se creará el objeto donde se mostrarán los mensajes
         * @property {Number}  [imgClass=null] - Clase que determina el estilo que se va a aplicar en el icono del feedback.
         * @property {Number}  [delay=null] - Espera (ms) que va a aplicarse antes de ocultar el feedback.
         * @property {Number}  [fadeSpeed=null] - Tiempo (ms) que va a durar la animación de ocultación del feedback.
         * @property {boolean} [gotoTop=true] - Drmina si cuando se muestre el feedback se debe desplazar la
  página hasta la parte superior de la misma.
         * @property {boolean}  [block=true] - Indica si la capa que contendrá el mensaje de feedback debe tener o
  no un espacio fijo en la pantalla.
         * @property {closeLink}  [closeLink=true] - Indica si la capa de feedback tendrá un enlace para que el usuario
  de la aplicación pueda cerrar la capa manualmente.
         */
		options: {
			type: null, //[ok, alert, error]
			imgClass: null,
			delay: null,
			fadeSpeed: null,
			gotoTop: true,
			block: true,
			closeLink: true,
			//uso privado
			_idFeedback: null,
			_divClose: null
		},
		/**
     * @function	_setOption
     * @private
     * @description Modifica las opciones de configuración del componente.
     */
		_setOption: function _setOption(key, value) {
			var opciones = this.options,
			    element = this.element;
			switch (key) {
				case 'type':
					//Eliminar imagenes anteriores y poner el tipo indicado
					if (value !== null) {
						element.removeClass(opciones.imgClass + ' rup-feedback_image_' + opciones.type);
						element.addClass('rup-feedback_image rup-feedback_image_' + value);
					} else {
						element.removeClass('rup-feedback_image rup-feedback_image_' + opciones.type);
					}
					break;
				case 'imgClass':
					//Eliminar imagenes anteriores y poner la personal
					if (value !== null) {
						element.removeClass(opciones.imgClass + ' rup-feedback_image rup-feedback_image_' + opciones.type);
						element.addClass(value);
					} else {
						element.removeClass(opciones.imgClass);
					}
					break;
				case 'closeLink':
					//Gestionar capa enlace cierre
					if (value) {
						this._addCloseLink();
					} else {
						$('#' + this.options._idFeedback + '_closeDiv').remove();
					}
					break;
			}
			$.Widget.prototype._setOption.apply(this, arguments);
		},
		/**
     * @function	_create
     * @private
     * @description Crea en el DOM los elementos que conforman el componente.
     */
		_create: function _create() {
			var opciones = this.options;
			opciones._idFeedback = this.element.addClass('rup-feedback ui-widget ui-widget-content ui-corner-all').addClass(opciones.imgClass != null ? opciones.imgClass : opciones.type != null ? 'rup-feedback_image rup-feedback_image_' + opciones.type : '').attr({
				role: 'alert'
			}).css('display', opciones.block ? 'block' : 'none').css('visibility', 'hidden').append('<span class=\'rup-feedback-icon\'>').context.id;

			//Crear capa cierre

			var clase = $.rup.adapter[$.fn.rup_feedback.defaults.adapter].classComponent();
			opciones._divClose = $('<div />').html($.rup.adapter[$.fn.rup_feedback.defaults.adapter].closeLiteral()).attr('id', opciones._idFeedback + '_closeDiv').attr('title', $.rup.i18nParse($.rup.i18n.base, 'rup_feedback.closingLiteral')).addClass('rup-feedback_closeLink').addClass(clase);

			//Si se define texto sacarlo
			if (opciones.message) {
				this.set(opciones.message, opciones.type, opciones.imgClass);
			}
		},
		/**
     * @description Añade el enlace de cierre.
     *
     * @function	_addCloseLink
     * @private
     */
		_addCloseLink: function _addCloseLink() {
			var opciones = this.options;
			opciones._divClose.click(function () {
				$('#' + opciones._idFeedback).rup_feedback('close');
			});
			this.element.prepend(opciones._divClose);
		},
		/**
     * Elimina las modificaciones realizadas sobre la capa para convertirla en feedback volviendo a ser una simple capa.
     *
     * @function	destroy
     * @example
     * // Elimina el feedback
     * jQuery("#feedback").rup_feedback("destroy");
     */
		destroy: function destroy() {
			var opciones = this.options;
			this.element.removeClass().removeAttr('role').css('cssText', '').html('').stop().animate({
				opacity: '100'
			}); //Por si está desapareciendo (hide)
			$.Widget.prototype.destroy.apply(this, arguments);
		},
		/**
     * Establece el texto (msg) a mostrar en el feedback, que podrá ser tanto texto plano como html. <br/><br/>
     * En caso de sólo definirse el parámetro msg, se mostrará como imagen aquella definida anteriormente ya sea de un tipo por defecto o de una imagen con estilo personalizado (si es que se había definido). <br/><br/>
     * En caso de que se envíe el parámetro type informado de modificará la capa para mostrar la imagen por defecto asociada al tipo, borrando algún posible estilos personalizado establecido anteriormente. <br/><br/>
     * Por último para realizar el cambio a un estilo personalizado se pasará como parámetro type null y como imgClass la clase con el estilo a establecer.
     * @function	set
     * @param {string} message - Texto del mensaje que se va a mostrar en el feedback.
     * @param {string} type - Identificador del tipo de feedback [ok, alert, error].
     * @param {string} imgClass - Clase que determina el estilo que se va a aplicar en el icono del feedback.
     * @example <caption>Feedback simple:</caption>
     * $("#id_capa").rup_feedback("set","Texto a mostrar");
     * @example <caption>Feedback cambiando a imagen de un tipo por defecto (Ej. error):</caption>
     * $("#id_capa").rup_feedback("set", "...", "error");
     * @example <caption>Feedback estableciendo un estilo personalizado:</caption>
     * $("#id_capa").rup_feedback("set", "...", null, "imgPropio");
     */
		set: function set(message, type, imgClass) {
			var element = this.element,
			    opciones = this.options;

			//En caso de que está desapareciendo parar animación
			element.stop().animate({
				opacity: '100'
			});

			//Gestión 'type'
			if (type != undefined) {
				element.removeClass(opciones.imgClass);
				//Si se recibe type xxx se eliminan posibles tipo anterior y se establece ese
				if (opciones.type != null) {
					element.removeClass('rup-feedback_image_' + opciones.type);
				} else {
					element.addClass('rup-feedback_image');
				}
				element.addClass('rup-feedback_image_' + type);
				opciones.type = type;
			} else if (type === null) {
				//Si se recibe type 'null' se eliminan posibles tipos anteriores
				element.removeClass('rup-feedback_image rup-feedback_image_' + opciones.type);
				opciones.type = null;
			}

			//Gestión 'imgClass'
			if (imgClass != undefined) {
				if (opciones.imgClass != null) {
					element.removeClass(opciones.imgClass);
				}
				element.addClass(imgClass);
				opciones.imgClass = imgClass;
			}

			//Sacar mensaje
			$('#' + opciones._idFeedback + '_content').remove();
			element.append($('<div/>').attr('id', opciones._idFeedback + '_content').html(message));
			//Añadir cierre (evento y capa)
			if (opciones.closeLink) {
				this._addCloseLink();
			}
			this.show();

			//Ir al inicio
			if (opciones.gotoTop) {
				$('html, body').animate({
					scrollTop: '0px'
				}, 0);
			}
			//Ocultacion mensaje
			if (opciones.delay != null) {
				this.hide();
			}
		},
		/**
     * Oculta la capa del feedback con una animación. <br/><br/>
     * Si no se definen los parámetros se tomaran los definidos con anterioridad (creación del feedback por ejemplo) o si no los valores por defecto (null, null) que implica una animación sin espera con una “velocidad” de 400 ms.
     *
     * @function	hide
     * @param {Number} [delay] - Espera (ms) que va a aplicarse antes de ocultar el feedback.
     * @param {Number} [fadeSpeed] - Tiempo (ms) que va a durar la animación de ocultación del feedback.
     *
     * @example
     * // Ocultar el feedback.
     * jQuery("#feedback").rup_feedback("hide");
     * @example
     * // Ocultar el feedback. Se realiza con una demora de 1000ms y la transición dura 500ms.
     * jQuery("#feedback").rup_feedback("hide",1000,500);
     */
		hide: function hide(delay, fadeSpeed) {
			var opciones = this.options,
			    element = this.element;

			//Si no se reciben parámetros se toman los valores de la configuración inicial
			if (delay == undefined) {
				delay = opciones.delay;
			}
			if (fadeSpeed == undefined) {
				fadeSpeed = opciones.fadeSpeed;
			}

			element.delay(delay).fadeOut(eval(fadeSpeed), function () {
				$('#' + opciones._idFeedback).rup_feedback('close', true);
			});

			$('#' + this.options._idFeedback + '_closeDiv').hide();
		},
		/**
     * Oculta la capa del feedback sin animación alguna.<br/>
     * Esta función será invocada por el enlace de cierre (parámetro closeLink) en caso de que se muestre.
     *
     * @function	close
     * @param {boolean} [notEmpty=false] - Determina si se debe ejecutar empty() sobre el feedback.
     *
     * @example
     * // Cierra el feedback.
     * jQuery("#feedback").rup_feedback("close");
     */
		close: function close(notEmpty) {
			var element = this.element;
			element.css('display', this.options.block ? 'block' : 'none');
			element.css('visibility', 'hidden');
			if (notEmpty === undefined) {
				element.empty();
			}
		},
		/**
     * Muesta la capa del feedback. <br/><br/>
     * Esta función será invocada automáticamente cada vez que se invoque la función set(…)
     *
     * @function	show
     * @fires module:rup_feedback#rupFeedback_show
     * @example
     * // Muestra el feedback.
     * jQuery("#feedback").rup_feedback("show");
     */

		show: function show() {
			var element = this.element;
			element.css('display', 'block');
			element.css('visibility', 'visible');

			//Se comprueba que el icono esta
			if ($('.rup-feedback-icon', element).length === 0) {
				element.prepend('<span class=\'rup-feedback-icon\'>');
			}
			// Se aplica el tooltip
			this.element.find('[title]').rup_tooltip({
				position: {
					at: 'bottom center',
					my: 'top center'
				},
				applyToPortal: true
			});

			$('#' + this.options._idFeedback + '_closeDiv').show();

			/**
       * Permite asociar una función que se ejecutará cuando se muestre el feedback.
       * @event module:rup_feedback#rupFeedback_show
       * @example
       * $("#feedback").on("rupFeedback_show", function(event){});
       */
			jQuery(this.element).triggerHandler('rupFeedback_show');
		}

		//*******************************************************
		// DEFINICIÓN DE LA CONFIGURACION POR DEFECTO DEL PATRON
		//*******************************************************
		/*  $.fn.rup_feedback.defaults = {
        adapter = "feedback_bootstrap"
      };*/

		/**
     * Permite cambiar las propiedades definidas en el feedback.<br/><br/>
     * Puede invocarase antes que la funcion set(…) para modificar cualquiera de los parámetros del mensaje a mostar: icono, imagen personalizada, tiempo de espera hasta desaparecer…
     *
     * @name jQuery.rup_feedback#option
     * @function
     * @param {Object|string} param1 - Primer parámetro de invocación.<br/>
     * Puede tratarse de un Object que contenga varios parámetros o un string que indica el nombre del parámetro.
     * @param {*} [param2] - Segundo parámetro de invocación.<br/>
     * En caso de que el primer parámetro sea un string este será el valor correspondiente del parámetro identificado con el nombre de param1.
     * @example
     * // Feedback cambio propiedad simple
     * $("#id_capa").rup_feedback("option","closeLink", false);
     * @example
     * //Feedback cambio varias propiedades
     * var properties = {"closeLink":false, "block":false};
     * $("#id_capa").rup_feedback("option", properties);
     */
	});
	/*  $.fn.rup_feedback.defaults = {
      adapter = "feedback_bootstrap"
    };*/

	var rup_feedback = {};

	//Se configura el arranque de UDA para que alberge el nuevo patrón
	$.extend($.rup.iniRup, $.rup.rupSelectorObjectConstructor('rup_feedback', rup_feedback));

	$.fn.rup_feedback.defaults = {
		adapter: 'feedback_bootstrap'
	};
});
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))

/***/ }),
/* 9 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*!
 * Copyright 2016 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 */

/**
 * Se les presenta a los usuarios una barra de botones con diversas funcionalidades relacionadas a elementos de la página. Gracias a este componente se presentan, ordenan y agrupan las distintas funcionalidades gestionadas por las aplicaciones.
 *
 * @summary Componente RUP Tooltip.
 * @module rup_tooltip
 * @see El componente está basado en el plugin {@link http://qtip2.com/options|qTip2}. Para mas información acerca de las funcionalidades y opciones de configuración pinche {@link http://qtip2.com/options|aquí}.
 * @example
 * $("[title]").rup_tooltip({});
 */

/*global define */
/*global jQuery */

(function (factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(2), __webpack_require__(271)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		factory(jQuery);
	}
})(function ($) {

	//****************************************************************************************************************
	// DEFINICIÓN BASE DEL PATRÓN (definición de la variable privada que contendrá los métodos y la función de jQuery)
	//****************************************************************************************************************


	var rup_tooltip = {};

	//Se configura el arranque de UDA para que alberge el nuevo patrón
	$.extend($.rup.iniRup, $.rup.rupSelectorObjectConstructor('rup_tooltip', rup_tooltip));

	//*******************************
	// DEFINICIÓN DE MÉTODOS PÚBLICOS
	//*******************************
	$.fn.rup_tooltip('extend', {
		/**
         * Muestra el tooltip.
         *
         * @function open
         * @example
         * $("#idTooltip").rup_tooltip("open");
         */
		open: function open() {
			$(this).qtip('show', true);
		},
		/**
         * Oculta el tooltip.
         *
         * @function close
         * @example
         * $("#idTooltip").rup_tooltip("close");
         */
		close: function close() {
			$(this).qtip('hide', true);
		},
		/**
         * Habilita el tooltip.
         *
         * @function  enable
         * @example
         * $("#idTooltip").rup_tooltip("enable");
         */
		enable: function enable() {
			$(this).qtip('enable', true);
		},
		/**
         * Deshabilita el tooltip.
         *
         * @function  disable
         * @example
         * $("#idTooltip").rup_tooltip("disable");
         */
		disable: function disable() {
			$(this).rup_tooltip('close');
			$(this).qtip('disable', true);
		},
		/**
         * Elimina el tooltip.
         *
         * @function  destroy
         * @example
         * $("#idTooltip").rup_tooltip("destroy");
         */
		destroy: function destroy() {
			$(this).rup_tooltip('disable');
			$(this).qtip('destroy');
		},
		/**
         * Obtiene o establece la configuración del tooltip.
         *
         * @param {string} option - Nombre de la propiedad que se desea gestionar.
         * @param {*} [value] - Corresponde al valor de la propiedad en caso de haberse especificado el nombre de la misma en el primér parámetro.
         * @function  option
         * @example
         * // Obtener el valor de la posición
         * $("#idTooltip").rup_tooltip("option", "position");
         * // Establecer el valor de la posición
         * $("#idTooltip").rup_tooltip("option", "position", {offset: "15 15"});
         */
		option: function option(_option, value) {
			return $(this).qtip('option', _option, value);
		}
	});

	//*******************************
	// DEFINICIÓN DE MÉTODOS PRIVADOS
	//*******************************
	$.fn.rup_tooltip('extend', {
		_init: function _init(args) {
			if (args.length > 1) {
				$.rup.errorGestor($.rup.i18nParse($.rup.i18n.base, 'rup_global.initError') + $(this).attr('id'));
			} else {
				if ($(this).length > 0) {
					//Evitar invocaciones sin objetos (grid)

					var settings = $.extend({}, $.fn.rup_tooltip.defaults, args[0]),
					    isGrid = this[0].className.indexOf('rup-grid') !== -1,
					    openUserEvent;

					//Identificador de la capa del tooltip
					if (settings.id === undefined) {
						settings.id = $(this).attr('id');
					}

					if (isGrid) {
						var elems = $(this)
						//Modificar atributo 'title' por 'rup_tooltip'
						.each(function (index, element) {
							$.attr(this, 'rup_tooltip', $.attr(this, 'title'));
							if (element.localName === 'img') {
								$(element).parents('td').attr('rup_tooltip', $(element).attr('rup_tooltip'));
							}
						})
						//Eliminar atributo 'title'
						.removeAttr('title');

						settings = {
							content: ' ',
							position: {
								target: 'event',
								effect: false
							},
							show: {
								delay: settings.show.delay
							},
							hide: {
								delay: 0 //Para que funcione correctamente en las tablas
							},
							events: {
								show: function show(event, api) {
									var target = $(event.originalEvent.target);
									if (target.length) {
										//Recorrer hasta encontrar atributo o ser columna
										while (target.attr('rup_tooltip') === undefined && target[0].nodeName !== 'TD') {
											target = $(target).parent();
										}

										//Correción para datos vacíos
										api.set('content.text', target.attr('rup_tooltip') === '' ? ' ' : target.attr('rup_tooltip'));
										if (target.attr('rup_tooltip') === '' || target.attr('rup_tooltip') === ' ') {
											target.qtip('destroy');
										}

										//Si es última columna que comience en la izquierda
										//Obtenemos la columna (puede que el target sea A, IMG, ...)
										if (target[0].nodeName !== 'TD') {
											target = $(target).parents('td');
										}
										//Cambiamos posición tooltip
										if (target.nextAll('td:visible').length == 0) {
											api.set('position.my.x', 'right'); //Última columna
										} else {
											api.set('position.my.x', 'left'); //Otra columna
										}

										//Cambiamos el objetivo del tooltip (puede que el target sea A, IMG, ...)
										api.set('position.target', target);
									}
								},
								render: function render(event, api) {
									if ($.rup_utils.aplicatioInPortal()) {
										$('div.r01gContainer').append($(this));
										if (!($('#qtip-overlay').size() === 0)) {
											$('div.r01gContainer').append($('#qtip-overlay'));
										}
									}
								}
							}
						};

						//Unificar en una capa el TOOLTIP
						$(this).qtip(settings);
					} else {
						var thisPortal;

						if ($.rup_utils.aplicatioInPortal() && !settings.applyToPortal) {
							thisPortal = $('div.r01gContainer ' + $(this).selector);
						} else {
							thisPortal = this;
						}

						if (settings.open !== undefined) {
							settings.events.show = settings.open;
						}

						if (settings.close !== undefined) {
							settings.events.hide = settings.close;
						}

						settings.events.render = function (event, api) {
							if ($.rup_utils.aplicatioInPortal()) {
								$('div.r01gContainer').append($(this));
								if (!($('#qtip-overlay').size() === 0)) {
									$('div.r01gContainer').append($('#qtip-overlay'));
								}
								// api.set('position.my.x', api.get('position.my.x'));
							}
						};

						$(thisPortal).qtip(settings);

						if (settings.disabled) {
							$(thisPortal).qtip('disable');
						}
					}
				}
			}
		}
	});

	//******************************************************
	// DEFINICIÓN DE LA CONFIGURACION POR DEFECTO DEL PATRON
	//******************************************************
	$.fn.rup_tooltip.defaults = {
		disabled: false,
		applyToPortal: false,
		show: {
			delay: 0
		},
		//tooltip
		position: {
			my: 'top left',
			at: 'bottom right',
			target: 'event',
			effect: false
		},
		events: {}
	};

	/**
     * Función que se ejecutará cuando se muestre el tooltip.
     *
     * @callback jQuery.rup_tooltip~onOpen
     * @example
     * $("#idTooltip").rup_tooltip({
     *   open: function(){
     *   }
     * });
     */

	/**
     * Función que se ejecutará cuando se oculte el tooltip.
     *
     * @callback jQuery.rup_tooltip~onClose
     * @example
     * $("#idTooltip").rup_tooltip({
     *   close: function(){
     *   }
     * });
     */

	/**
     * @description Propiedades de configuración del componente.
     * @see Para mas información consulte la documentación acerca de las opciones de configuración del plugin {@link http://qtip2.com/options|qTip2}.
     *
     * @name jQuery.rup_tooltip#options
     * @property {boolean} [disabled=false] - booleano que indica si el tooltip está habilitado o no.
     * @property {boolean} [applyToPortal=false] - Parámetro encargado de determinar si el componente tooltip se aplica, también, al código html adscrito a los portales de la infraestructura de EJIE. El parámetro acepta el valor true, para indicar que se aplique al portal, y el valor false, para indicar que no se aplique al portal.
     * @property {object} [content] - Configura el texto del tooltip (si no se ha definido en el title).
     * @property {string} [content.text] - Texto del tooltip.
     * @property {string} [content.title] - Tooltip en formato diálogo y este parámetro define el título del mismo.
     * @property {object} [position] - Configura la posición del tooltip y tiene (entre otros) los siguientes parámetros.
     * @property {string} position.my=top left - Posición en la que es colocado el tooltip a mostrar parámetros.
     * @property {string} position.at=bottom left - Posición respecto al objeto al que se aplica el tooltip.
     * @property {string} position.target - Si se quiere definir sobre qué elemento debe aplicarse el tooltip. parámetros.
     * @property {object} [show] - Configura el modo/evento en el que se despliega el tooltip.
     * @property {string} show.event=mouseenter - Evento con el que se muestra el tooltip.
     * @property {object} show.modal - Configura el modo/evento en el que se despliega el tooltip.
     * @property {object} [hide] - Configura el modo/evento en el que se oculta el tooltip.
     * @property {object} hide.event=mouseleave - Evento con el que se oculta el tooltip.
     * @property {jQuery.rup_tooltip~onOpen} [open] - Permite asociar una función que se ejecutará cuando se muestre el tooltip.
     * @property {jQuery.rup_tooltip~onClose} [close] - Permite asociar una función que se ejecutará cuando se oculte el tooltip.
     */
});

/***/ }),
/* 10 */
/***/ (function(module, exports) {

var g;

// This works in non-strict mode
g = (function() {
	return this;
})();

try {
	// This works if eval is allowed (see CSP)
	g = g || Function("return this")() || (1,eval)("this");
} catch(e) {
	// This works if the window reference is available
	if(typeof window === "object")
		g = window;
}

// g can still be undefined, but nothing to do about it...
// We return undefined, instead of nothing here, so it's
// easier to handle this case. if(!global) { ...}

module.exports = g;


/***/ }),
/* 11 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*! jQuery UI - v1.12.0 - 2016-07-08
* http://jqueryui.com
* Includes: widget.js, position.js, data.js, disable-selection.js, effect.js, effects/effect-blind.js, effects/effect-bounce.js, effects/effect-clip.js, effects/effect-drop.js, effects/effect-explode.js, effects/effect-fade.js, effects/effect-fold.js, effects/effect-highlight.js, effects/effect-puff.js, effects/effect-pulsate.js, effects/effect-scale.js, effects/effect-shake.js, effects/effect-size.js, effects/effect-slide.js, effects/effect-transfer.js, focusable.js, form-reset-mixin.js, jquery-1-7.js, keycode.js, labels.js, scroll-parent.js, tabbable.js, unique-id.js, widgets/accordion.js, widgets/autocomplete.js, widgets/button.js, widgets/checkboxradio.js, widgets/controlgroup.js, widgets/datepicker.js, widgets/dialog.js, widgets/draggable.js, widgets/droppable.js, widgets/menu.js, widgets/mouse.js, widgets/progressbar.js, widgets/resizable.js, widgets/selectable.js, widgets/selectmenu.js, widgets/slider.js, widgets/sortable.js, widgets/spinner.js, widgets/tabs.js, widgets/tooltip.js
* Copyright jQuery Foundation and other contributors; Licensed MIT */

(function( factory ) {
	if ( true ) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [ __webpack_require__(0) ], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		factory( jQuery );
	}
}(function( $ ) {

$.ui = $.ui || {};

var version = $.ui.version = "1.12.0";


/*!
 * jQuery UI Widget 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: Widget
//>>group: Core
//>>description: Provides a factory for creating stateful widgets with a common API.
//>>docs: http://api.jqueryui.com/jQuery.widget/
//>>demos: http://jqueryui.com/widget/



var widgetUuid = 0;
var widgetSlice = Array.prototype.slice;

$.cleanData = ( function( orig ) {
	return function( elems ) {
		var events, elem, i;
		for ( i = 0; ( elem = elems[ i ] ) != null; i++ ) {
			try {

				// Only trigger remove when necessary to save time
				events = $._data( elem, "events" );
				if ( events && events.remove ) {
					$( elem ).triggerHandler( "remove" );
				}

			// Http://bugs.jquery.com/ticket/8235
			} catch ( e ) {}
		}
		orig( elems );
	};
} )( $.cleanData );

$.widget = function( name, base, prototype ) {
	var existingConstructor, constructor, basePrototype;

	// ProxiedPrototype allows the provided prototype to remain unmodified
	// so that it can be used as a mixin for multiple widgets (#8876)
	var proxiedPrototype = {};

	var namespace = name.split( "." )[ 0 ];
	name = name.split( "." )[ 1 ];
	var fullName = namespace + "-" + name;

	if ( !prototype ) {
		prototype = base;
		base = $.Widget;
	}

	if ( $.isArray( prototype ) ) {
		prototype = $.extend.apply( null, [ {} ].concat( prototype ) );
	}

	// Create selector for plugin
	$.expr[ ":" ][ fullName.toLowerCase() ] = function( elem ) {
		return !!$.data( elem, fullName );
	};

	$[ namespace ] = $[ namespace ] || {};
	existingConstructor = $[ namespace ][ name ];
	constructor = $[ namespace ][ name ] = function( options, element ) {

		// Allow instantiation without "new" keyword
		if ( !this._createWidget ) {
			return new constructor( options, element );
		}

		// Allow instantiation without initializing for simple inheritance
		// must use "new" keyword (the code above always passes args)
		if ( arguments.length ) {
			this._createWidget( options, element );
		}
	};

	// Extend with the existing constructor to carry over any static properties
	$.extend( constructor, existingConstructor, {
		version: prototype.version,

		// Copy the object used to create the prototype in case we need to
		// redefine the widget later
		_proto: $.extend( {}, prototype ),

		// Track widgets that inherit from this widget in case this widget is
		// redefined after a widget inherits from it
		_childConstructors: []
	} );

	basePrototype = new base();

	// We need to make the options hash a property directly on the new instance
	// otherwise we'll modify the options hash on the prototype that we're
	// inheriting from
	basePrototype.options = $.widget.extend( {}, basePrototype.options );
	$.each( prototype, function( prop, value ) {
		if ( !$.isFunction( value ) ) {
			proxiedPrototype[ prop ] = value;
			return;
		}
		proxiedPrototype[ prop ] = ( function() {
			function _super() {
				return base.prototype[ prop ].apply( this, arguments );
			}

			function _superApply( args ) {
				return base.prototype[ prop ].apply( this, args );
			}

			return function() {
				var __super = this._super;
				var __superApply = this._superApply;
				var returnValue;

				this._super = _super;
				this._superApply = _superApply;

				returnValue = value.apply( this, arguments );

				this._super = __super;
				this._superApply = __superApply;

				return returnValue;
			};
		} )();
	} );
	constructor.prototype = $.widget.extend( basePrototype, {

		// TODO: remove support for widgetEventPrefix
		// always use the name + a colon as the prefix, e.g., draggable:start
		// don't prefix for widgets that aren't DOM-based
		widgetEventPrefix: existingConstructor ? ( basePrototype.widgetEventPrefix || name ) : name
	}, proxiedPrototype, {
		constructor: constructor,
		namespace: namespace,
		widgetName: name,
		widgetFullName: fullName
	} );

	// If this widget is being redefined then we need to find all widgets that
	// are inheriting from it and redefine all of them so that they inherit from
	// the new version of this widget. We're essentially trying to replace one
	// level in the prototype chain.
	if ( existingConstructor ) {
		$.each( existingConstructor._childConstructors, function( i, child ) {
			var childPrototype = child.prototype;

			// Redefine the child widget using the same prototype that was
			// originally used, but inherit from the new version of the base
			$.widget( childPrototype.namespace + "." + childPrototype.widgetName, constructor,
				child._proto );
		} );

		// Remove the list of existing child constructors from the old constructor
		// so the old child constructors can be garbage collected
		delete existingConstructor._childConstructors;
	} else {
		base._childConstructors.push( constructor );
	}

	$.widget.bridge( name, constructor );

	return constructor;
};

$.widget.extend = function( target ) {
	var input = widgetSlice.call( arguments, 1 );
	var inputIndex = 0;
	var inputLength = input.length;
	var key;
	var value;

	for ( ; inputIndex < inputLength; inputIndex++ ) {
		for ( key in input[ inputIndex ] ) {
			value = input[ inputIndex ][ key ];
			if ( input[ inputIndex ].hasOwnProperty( key ) && value !== undefined ) {

				// Clone objects
				if ( $.isPlainObject( value ) ) {
					target[ key ] = $.isPlainObject( target[ key ] ) ?
						$.widget.extend( {}, target[ key ], value ) :

						// Don't extend strings, arrays, etc. with objects
						$.widget.extend( {}, value );

				// Copy everything else by reference
				} else {
					target[ key ] = value;
				}
			}
		}
	}
	return target;
};

$.widget.bridge = function( name, object ) {
	var fullName = object.prototype.widgetFullName || name;
	$.fn[ name ] = function( options ) {
		var isMethodCall = typeof options === "string";
		var args = widgetSlice.call( arguments, 1 );
		var returnValue = this;

		if ( isMethodCall ) {
			this.each( function() {
				var methodValue;
				var instance = $.data( this, fullName );

				if ( options === "instance" ) {
					returnValue = instance;
					return false;
				}

				if ( !instance ) {
					return $.error( "cannot call methods on " + name +
						" prior to initialization; " +
						"attempted to call method '" + options + "'" );
				}

				if ( !$.isFunction( instance[ options ] ) || options.charAt( 0 ) === "_" ) {
					return $.error( "no such method '" + options + "' for " + name +
						" widget instance" );
				}

				methodValue = instance[ options ].apply( instance, args );

				if ( methodValue !== instance && methodValue !== undefined ) {
					returnValue = methodValue && methodValue.jquery ?
						returnValue.pushStack( methodValue.get() ) :
						methodValue;
					return false;
				}
			} );
		} else {

			// Allow multiple hashes to be passed on init
			if ( args.length ) {
				options = $.widget.extend.apply( null, [ options ].concat( args ) );
			}

			this.each( function() {
				var instance = $.data( this, fullName );
				if ( instance ) {
					instance.option( options || {} );
					if ( instance._init ) {
						instance._init();
					}
				} else {
					$.data( this, fullName, new object( options, this ) );
				}
			} );
		}

		return returnValue;
	};
};

$.Widget = function( /* options, element */ ) {};
$.Widget._childConstructors = [];

$.Widget.prototype = {
	widgetName: "widget",
	widgetEventPrefix: "",
	defaultElement: "<div>",

	options: {
		classes: {},
		disabled: false,

		// Callbacks
		create: null
	},

	_createWidget: function( options, element ) {
		element = $( element || this.defaultElement || this )[ 0 ];
		this.element = $( element );
		this.uuid = widgetUuid++;
		this.eventNamespace = "." + this.widgetName + this.uuid;

		this.bindings = $();
		this.hoverable = $();
		this.focusable = $();
		this.classesElementLookup = {};

		if ( element !== this ) {
			$.data( element, this.widgetFullName, this );
			this._on( true, this.element, {
				remove: function( event ) {
					if ( event.target === element ) {
						this.destroy();
					}
				}
			} );
			this.document = $( element.style ?

				// Element within the document
				element.ownerDocument :

				// Element is window or document
				element.document || element );
			this.window = $( this.document[ 0 ].defaultView || this.document[ 0 ].parentWindow );
		}

		this.options = $.widget.extend( {},
			this.options,
			this._getCreateOptions(),
			options );

		this._create();

		if ( this.options.disabled ) {
			this._setOptionDisabled( this.options.disabled );
		}

		this._trigger( "create", null, this._getCreateEventData() );
		this._init();
	},

	_getCreateOptions: function() {
		return {};
	},

	_getCreateEventData: $.noop,

	_create: $.noop,

	_init: $.noop,

	destroy: function() {
		var that = this;

		this._destroy();
		$.each( this.classesElementLookup, function( key, value ) {
			that._removeClass( value, key );
		} );

		// We can probably remove the unbind calls in 2.0
		// all event bindings should go through this._on()
		this.element
			.off( this.eventNamespace )
			.removeData( this.widgetFullName );
		this.widget()
			.off( this.eventNamespace )
			.removeAttr( "aria-disabled" );

		// Clean up events and states
		this.bindings.off( this.eventNamespace );
	},

	_destroy: $.noop,

	widget: function() {
		return this.element;
	},

	option: function( key, value ) {
		var options = key;
		var parts;
		var curOption;
		var i;

		if ( arguments.length === 0 ) {

			// Don't return a reference to the internal hash
			return $.widget.extend( {}, this.options );
		}

		if ( typeof key === "string" ) {

			// Handle nested keys, e.g., "foo.bar" => { foo: { bar: ___ } }
			options = {};
			parts = key.split( "." );
			key = parts.shift();
			if ( parts.length ) {
				curOption = options[ key ] = $.widget.extend( {}, this.options[ key ] );
				for ( i = 0; i < parts.length - 1; i++ ) {
					curOption[ parts[ i ] ] = curOption[ parts[ i ] ] || {};
					curOption = curOption[ parts[ i ] ];
				}
				key = parts.pop();
				if ( arguments.length === 1 ) {
					return curOption[ key ] === undefined ? null : curOption[ key ];
				}
				curOption[ key ] = value;
			} else {
				if ( arguments.length === 1 ) {
					return this.options[ key ] === undefined ? null : this.options[ key ];
				}
				options[ key ] = value;
			}
		}

		this._setOptions( options );

		return this;
	},

	_setOptions: function( options ) {
		var key;

		for ( key in options ) {
			this._setOption( key, options[ key ] );
		}

		return this;
	},

	_setOption: function( key, value ) {
		if ( key === "classes" ) {
			this._setOptionClasses( value );
		}

		this.options[ key ] = value;

		if ( key === "disabled" ) {
			this._setOptionDisabled( value );
		}

		return this;
	},

	_setOptionClasses: function( value ) {
		var classKey, elements, currentElements;

		for ( classKey in value ) {
			currentElements = this.classesElementLookup[ classKey ];
			if ( value[ classKey ] === this.options.classes[ classKey ] ||
					!currentElements ||
					!currentElements.length ) {
				continue;
			}

			// We are doing this to create a new jQuery object because the _removeClass() call
			// on the next line is going to destroy the reference to the current elements being
			// tracked. We need to save a copy of this collection so that we can add the new classes
			// below.
			elements = $( currentElements.get() );
			this._removeClass( currentElements, classKey );

			// We don't use _addClass() here, because that uses this.options.classes
			// for generating the string of classes. We want to use the value passed in from
			// _setOption(), this is the new value of the classes option which was passed to
			// _setOption(). We pass this value directly to _classes().
			elements.addClass( this._classes( {
				element: elements,
				keys: classKey,
				classes: value,
				add: true
			} ) );
		}
	},

	_setOptionDisabled: function( value ) {
		this._toggleClass( this.widget(), this.widgetFullName + "-disabled", null, !!value );

		// If the widget is becoming disabled, then nothing is interactive
		if ( value ) {
			this._removeClass( this.hoverable, null, "ui-state-hover" );
			this._removeClass( this.focusable, null, "ui-state-focus" );
		}
	},

	enable: function() {
		return this._setOptions( { disabled: false } );
	},

	disable: function() {
		return this._setOptions( { disabled: true } );
	},

	_classes: function( options ) {
		var full = [];
		var that = this;

		options = $.extend( {
			element: this.element,
			classes: this.options.classes || {}
		}, options );

		function processClassString( classes, checkOption ) {
			var current, i;
			for ( i = 0; i < classes.length; i++ ) {
				current = that.classesElementLookup[ classes[ i ] ] || $();
				if ( options.add ) {
					current = $( $.unique( current.get().concat( options.element.get() ) ) );
				} else {
					current = $( current.not( options.element ).get() );
				}
				that.classesElementLookup[ classes[ i ] ] = current;
				full.push( classes[ i ] );
				if ( checkOption && options.classes[ classes[ i ] ] ) {
					full.push( options.classes[ classes[ i ] ] );
				}
			}
		}

		if ( options.keys ) {
			processClassString( options.keys.match( /\S+/g ) || [], true );
		}
		if ( options.extra ) {
			processClassString( options.extra.match( /\S+/g ) || [] );
		}

		return full.join( " " );
	},

	_removeClass: function( element, keys, extra ) {
		return this._toggleClass( element, keys, extra, false );
	},

	_addClass: function( element, keys, extra ) {
		return this._toggleClass( element, keys, extra, true );
	},

	_toggleClass: function( element, keys, extra, add ) {
		add = ( typeof add === "boolean" ) ? add : extra;
		var shift = ( typeof element === "string" || element === null ),
			options = {
				extra: shift ? keys : extra,
				keys: shift ? element : keys,
				element: shift ? this.element : element,
				add: add
			};
		options.element.toggleClass( this._classes( options ), add );
		return this;
	},

	_on: function( suppressDisabledCheck, element, handlers ) {
		var delegateElement;
		var instance = this;

		// No suppressDisabledCheck flag, shuffle arguments
		if ( typeof suppressDisabledCheck !== "boolean" ) {
			handlers = element;
			element = suppressDisabledCheck;
			suppressDisabledCheck = false;
		}

		// No element argument, shuffle and use this.element
		if ( !handlers ) {
			handlers = element;
			element = this.element;
			delegateElement = this.widget();
		} else {
			element = delegateElement = $( element );
			this.bindings = this.bindings.add( element );
		}

		$.each( handlers, function( event, handler ) {
			function handlerProxy() {

				// Allow widgets to customize the disabled handling
				// - disabled as an array instead of boolean
				// - disabled class as method for disabling individual parts
				if ( !suppressDisabledCheck &&
						( instance.options.disabled === true ||
						$( this ).hasClass( "ui-state-disabled" ) ) ) {
					return;
				}
				return ( typeof handler === "string" ? instance[ handler ] : handler )
					.apply( instance, arguments );
			}

			// Copy the guid so direct unbinding works
			if ( typeof handler !== "string" ) {
				handlerProxy.guid = handler.guid =
					handler.guid || handlerProxy.guid || $.guid++;
			}

			var match = event.match( /^([\w:-]*)\s*(.*)$/ );
			var eventName = match[ 1 ] + instance.eventNamespace;
			var selector = match[ 2 ];

			if ( selector ) {
				delegateElement.on( eventName, selector, handlerProxy );
			} else {
				element.on( eventName, handlerProxy );
			}
		} );
	},

	_off: function( element, eventName ) {
		eventName = ( eventName || "" ).split( " " ).join( this.eventNamespace + " " ) +
			this.eventNamespace;
		element.off( eventName ).off( eventName );

		// Clear the stack to avoid memory leaks (#10056)
		this.bindings = $( this.bindings.not( element ).get() );
		this.focusable = $( this.focusable.not( element ).get() );
		this.hoverable = $( this.hoverable.not( element ).get() );
	},

	_delay: function( handler, delay ) {
		function handlerProxy() {
			return ( typeof handler === "string" ? instance[ handler ] : handler )
				.apply( instance, arguments );
		}
		var instance = this;
		return setTimeout( handlerProxy, delay || 0 );
	},

	_hoverable: function( element ) {
		this.hoverable = this.hoverable.add( element );
		this._on( element, {
			mouseenter: function( event ) {
				this._addClass( $( event.currentTarget ), null, "ui-state-hover" );
			},
			mouseleave: function( event ) {
				this._removeClass( $( event.currentTarget ), null, "ui-state-hover" );
			}
		} );
	},

	_focusable: function( element ) {
		this.focusable = this.focusable.add( element );
		this._on( element, {
			focusin: function( event ) {
				this._addClass( $( event.currentTarget ), null, "ui-state-focus" );
			},
			focusout: function( event ) {
				this._removeClass( $( event.currentTarget ), null, "ui-state-focus" );
			}
		} );
	},

	_trigger: function( type, event, data ) {
		var prop, orig;
		var callback = this.options[ type ];

		data = data || {};
		event = $.Event( event );
		event.type = ( type === this.widgetEventPrefix ?
			type :
			this.widgetEventPrefix + type ).toLowerCase();

		// The original event may come from any element
		// so we need to reset the target on the new event
		event.target = this.element[ 0 ];

		// Copy original event properties over to the new event
		orig = event.originalEvent;
		if ( orig ) {
			for ( prop in orig ) {
				if ( !( prop in event ) ) {
					event[ prop ] = orig[ prop ];
				}
			}
		}

		this.element.trigger( event, data );
		return !( $.isFunction( callback ) &&
			callback.apply( this.element[ 0 ], [ event ].concat( data ) ) === false ||
			event.isDefaultPrevented() );
	}
};

$.each( { show: "fadeIn", hide: "fadeOut" }, function( method, defaultEffect ) {
	$.Widget.prototype[ "_" + method ] = function( element, options, callback ) {
		if ( typeof options === "string" ) {
			options = { effect: options };
		}

		var hasOptions;
		var effectName = !options ?
			method :
			options === true || typeof options === "number" ?
				defaultEffect :
				options.effect || defaultEffect;

		options = options || {};
		if ( typeof options === "number" ) {
			options = { duration: options };
		}

		hasOptions = !$.isEmptyObject( options );
		options.complete = callback;

		if ( options.delay ) {
			element.delay( options.delay );
		}

		if ( hasOptions && $.effects && $.effects.effect[ effectName ] ) {
			element[ method ]( options );
		} else if ( effectName !== method && element[ effectName ] ) {
			element[ effectName ]( options.duration, options.easing, callback );
		} else {
			element.queue( function( next ) {
				$( this )[ method ]();
				if ( callback ) {
					callback.call( element[ 0 ] );
				}
				next();
			} );
		}
	};
} );

var widget = $.widget;


/*!
 * jQuery UI Position 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 *
 * http://api.jqueryui.com/position/
 */

//>>label: Position
//>>group: Core
//>>description: Positions elements relative to other elements.
//>>docs: http://api.jqueryui.com/position/
//>>demos: http://jqueryui.com/position/


( function() {
var cachedScrollbarWidth, supportsOffsetFractions,
	max = Math.max,
	abs = Math.abs,
	round = Math.round,
	rhorizontal = /left|center|right/,
	rvertical = /top|center|bottom/,
	roffset = /[\+\-]\d+(\.[\d]+)?%?/,
	rposition = /^\w+/,
	rpercent = /%$/,
	_position = $.fn.position;

// Support: IE <=9 only
supportsOffsetFractions = function() {
	var element = $( "<div>" )
			.css( "position", "absolute" )
			.appendTo( "body" )
			.offset( {
				top: 1.5,
				left: 1.5
			} ),
		support = element.offset().top === 1.5;

	element.remove();

	supportsOffsetFractions = function() {
		return support;
	};

	return support;
};

function getOffsets( offsets, width, height ) {
	return [
		parseFloat( offsets[ 0 ] ) * ( rpercent.test( offsets[ 0 ] ) ? width / 100 : 1 ),
		parseFloat( offsets[ 1 ] ) * ( rpercent.test( offsets[ 1 ] ) ? height / 100 : 1 )
	];
}

function parseCss( element, property ) {
	return parseInt( $.css( element, property ), 10 ) || 0;
}

function getDimensions( elem ) {
	var raw = elem[ 0 ];
	if ( raw.nodeType === 9 ) {
		return {
			width: elem.width(),
			height: elem.height(),
			offset: { top: 0, left: 0 }
		};
	}
	if ( $.isWindow( raw ) ) {
		return {
			width: elem.width(),
			height: elem.height(),
			offset: { top: elem.scrollTop(), left: elem.scrollLeft() }
		};
	}
	if ( raw.preventDefault ) {
		return {
			width: 0,
			height: 0,
			offset: { top: raw.pageY, left: raw.pageX }
		};
	}
	return {
		width: elem.outerWidth(),
		height: elem.outerHeight(),
		offset: elem.offset()
	};
}

$.position = {
	scrollbarWidth: function() {
		if ( cachedScrollbarWidth !== undefined ) {
			return cachedScrollbarWidth;
		}
		var w1, w2,
			div = $( "<div " +
				"style='display:block;position:absolute;width:50px;height:50px;overflow:hidden;'>" +
				"<div style='height:100px;width:auto;'></div></div>" ),
			innerDiv = div.children()[ 0 ];

		$( "body" ).append( div );
		w1 = innerDiv.offsetWidth;
		div.css( "overflow", "scroll" );

		w2 = innerDiv.offsetWidth;

		if ( w1 === w2 ) {
			w2 = div[ 0 ].clientWidth;
		}

		div.remove();

		return ( cachedScrollbarWidth = w1 - w2 );
	},
	getScrollInfo: function( within ) {
		var overflowX = within.isWindow || within.isDocument ? "" :
				within.element.css( "overflow-x" ),
			overflowY = within.isWindow || within.isDocument ? "" :
				within.element.css( "overflow-y" ),
			hasOverflowX = overflowX === "scroll" ||
				( overflowX === "auto" && within.width < within.element[ 0 ].scrollWidth ),
			hasOverflowY = overflowY === "scroll" ||
				( overflowY === "auto" && within.height < within.element[ 0 ].scrollHeight );
		return {
			width: hasOverflowY ? $.position.scrollbarWidth() : 0,
			height: hasOverflowX ? $.position.scrollbarWidth() : 0
		};
	},
	getWithinInfo: function( element ) {
		var withinElement = $( element || window ),
			isWindow = $.isWindow( withinElement[ 0 ] ),
			isDocument = !!withinElement[ 0 ] && withinElement[ 0 ].nodeType === 9,
			hasOffset = !isWindow && !isDocument;
		return {
			element: withinElement,
			isWindow: isWindow,
			isDocument: isDocument,
			offset: hasOffset ? $( element ).offset() : { left: 0, top: 0 },
			scrollLeft: withinElement.scrollLeft(),
			scrollTop: withinElement.scrollTop(),
			width: withinElement.outerWidth(),
			height: withinElement.outerHeight()
		};
	}
};

$.fn.position = function( options ) {
	if ( !options || !options.of ) {
		return _position.apply( this, arguments );
	}

	// Make a copy, we don't want to modify arguments
	options = $.extend( {}, options );

	var atOffset, targetWidth, targetHeight, targetOffset, basePosition, dimensions,
		target = $( options.of ),
		within = $.position.getWithinInfo( options.within ),
		scrollInfo = $.position.getScrollInfo( within ),
		collision = ( options.collision || "flip" ).split( " " ),
		offsets = {};

	dimensions = getDimensions( target );
	if ( target[ 0 ].preventDefault ) {

		// Force left top to allow flipping
		options.at = "left top";
	}
	targetWidth = dimensions.width;
	targetHeight = dimensions.height;
	targetOffset = dimensions.offset;

	// Clone to reuse original targetOffset later
	basePosition = $.extend( {}, targetOffset );

	// Force my and at to have valid horizontal and vertical positions
	// if a value is missing or invalid, it will be converted to center
	$.each( [ "my", "at" ], function() {
		var pos = ( options[ this ] || "" ).split( " " ),
			horizontalOffset,
			verticalOffset;

		if ( pos.length === 1 ) {
			pos = rhorizontal.test( pos[ 0 ] ) ?
				pos.concat( [ "center" ] ) :
				rvertical.test( pos[ 0 ] ) ?
					[ "center" ].concat( pos ) :
					[ "center", "center" ];
		}
		pos[ 0 ] = rhorizontal.test( pos[ 0 ] ) ? pos[ 0 ] : "center";
		pos[ 1 ] = rvertical.test( pos[ 1 ] ) ? pos[ 1 ] : "center";

		// Calculate offsets
		horizontalOffset = roffset.exec( pos[ 0 ] );
		verticalOffset = roffset.exec( pos[ 1 ] );
		offsets[ this ] = [
			horizontalOffset ? horizontalOffset[ 0 ] : 0,
			verticalOffset ? verticalOffset[ 0 ] : 0
		];

		// Reduce to just the positions without the offsets
		options[ this ] = [
			rposition.exec( pos[ 0 ] )[ 0 ],
			rposition.exec( pos[ 1 ] )[ 0 ]
		];
	} );

	// Normalize collision option
	if ( collision.length === 1 ) {
		collision[ 1 ] = collision[ 0 ];
	}

	if ( options.at[ 0 ] === "right" ) {
		basePosition.left += targetWidth;
	} else if ( options.at[ 0 ] === "center" ) {
		basePosition.left += targetWidth / 2;
	}

	if ( options.at[ 1 ] === "bottom" ) {
		basePosition.top += targetHeight;
	} else if ( options.at[ 1 ] === "center" ) {
		basePosition.top += targetHeight / 2;
	}

	atOffset = getOffsets( offsets.at, targetWidth, targetHeight );
	basePosition.left += atOffset[ 0 ];
	basePosition.top += atOffset[ 1 ];

	return this.each( function() {
		var collisionPosition, using,
			elem = $( this ),
			elemWidth = elem.outerWidth(),
			elemHeight = elem.outerHeight(),
			marginLeft = parseCss( this, "marginLeft" ),
			marginTop = parseCss( this, "marginTop" ),
			collisionWidth = elemWidth + marginLeft + parseCss( this, "marginRight" ) +
				scrollInfo.width,
			collisionHeight = elemHeight + marginTop + parseCss( this, "marginBottom" ) +
				scrollInfo.height,
			position = $.extend( {}, basePosition ),
			myOffset = getOffsets( offsets.my, elem.outerWidth(), elem.outerHeight() );

		if ( options.my[ 0 ] === "right" ) {
			position.left -= elemWidth;
		} else if ( options.my[ 0 ] === "center" ) {
			position.left -= elemWidth / 2;
		}

		if ( options.my[ 1 ] === "bottom" ) {
			position.top -= elemHeight;
		} else if ( options.my[ 1 ] === "center" ) {
			position.top -= elemHeight / 2;
		}

		position.left += myOffset[ 0 ];
		position.top += myOffset[ 1 ];

		// If the browser doesn't support fractions, then round for consistent results
		if ( !supportsOffsetFractions() ) {
			position.left = round( position.left );
			position.top = round( position.top );
		}

		collisionPosition = {
			marginLeft: marginLeft,
			marginTop: marginTop
		};

		$.each( [ "left", "top" ], function( i, dir ) {
			if ( $.ui.position[ collision[ i ] ] ) {
				$.ui.position[ collision[ i ] ][ dir ]( position, {
					targetWidth: targetWidth,
					targetHeight: targetHeight,
					elemWidth: elemWidth,
					elemHeight: elemHeight,
					collisionPosition: collisionPosition,
					collisionWidth: collisionWidth,
					collisionHeight: collisionHeight,
					offset: [ atOffset[ 0 ] + myOffset[ 0 ], atOffset [ 1 ] + myOffset[ 1 ] ],
					my: options.my,
					at: options.at,
					within: within,
					elem: elem
				} );
			}
		} );

		if ( options.using ) {

			// Adds feedback as second argument to using callback, if present
			using = function( props ) {
				var left = targetOffset.left - position.left,
					right = left + targetWidth - elemWidth,
					top = targetOffset.top - position.top,
					bottom = top + targetHeight - elemHeight,
					feedback = {
						target: {
							element: target,
							left: targetOffset.left,
							top: targetOffset.top,
							width: targetWidth,
							height: targetHeight
						},
						element: {
							element: elem,
							left: position.left,
							top: position.top,
							width: elemWidth,
							height: elemHeight
						},
						horizontal: right < 0 ? "left" : left > 0 ? "right" : "center",
						vertical: bottom < 0 ? "top" : top > 0 ? "bottom" : "middle"
					};
				if ( targetWidth < elemWidth && abs( left + right ) < targetWidth ) {
					feedback.horizontal = "center";
				}
				if ( targetHeight < elemHeight && abs( top + bottom ) < targetHeight ) {
					feedback.vertical = "middle";
				}
				if ( max( abs( left ), abs( right ) ) > max( abs( top ), abs( bottom ) ) ) {
					feedback.important = "horizontal";
				} else {
					feedback.important = "vertical";
				}
				options.using.call( this, props, feedback );
			};
		}

		elem.offset( $.extend( position, { using: using } ) );
	} );
};

$.ui.position = {
	fit: {
		left: function( position, data ) {
			var within = data.within,
				withinOffset = within.isWindow ? within.scrollLeft : within.offset.left,
				outerWidth = within.width,
				collisionPosLeft = position.left - data.collisionPosition.marginLeft,
				overLeft = withinOffset - collisionPosLeft,
				overRight = collisionPosLeft + data.collisionWidth - outerWidth - withinOffset,
				newOverRight;

			// Element is wider than within
			if ( data.collisionWidth > outerWidth ) {

				// Element is initially over the left side of within
				if ( overLeft > 0 && overRight <= 0 ) {
					newOverRight = position.left + overLeft + data.collisionWidth - outerWidth -
						withinOffset;
					position.left += overLeft - newOverRight;

				// Element is initially over right side of within
				} else if ( overRight > 0 && overLeft <= 0 ) {
					position.left = withinOffset;

				// Element is initially over both left and right sides of within
				} else {
					if ( overLeft > overRight ) {
						position.left = withinOffset + outerWidth - data.collisionWidth;
					} else {
						position.left = withinOffset;
					}
				}

			// Too far left -> align with left edge
			} else if ( overLeft > 0 ) {
				position.left += overLeft;

			// Too far right -> align with right edge
			} else if ( overRight > 0 ) {
				position.left -= overRight;

			// Adjust based on position and margin
			} else {
				position.left = max( position.left - collisionPosLeft, position.left );
			}
		},
		top: function( position, data ) {
			var within = data.within,
				withinOffset = within.isWindow ? within.scrollTop : within.offset.top,
				outerHeight = data.within.height,
				collisionPosTop = position.top - data.collisionPosition.marginTop,
				overTop = withinOffset - collisionPosTop,
				overBottom = collisionPosTop + data.collisionHeight - outerHeight - withinOffset,
				newOverBottom;

			// Element is taller than within
			if ( data.collisionHeight > outerHeight ) {

				// Element is initially over the top of within
				if ( overTop > 0 && overBottom <= 0 ) {
					newOverBottom = position.top + overTop + data.collisionHeight - outerHeight -
						withinOffset;
					position.top += overTop - newOverBottom;

				// Element is initially over bottom of within
				} else if ( overBottom > 0 && overTop <= 0 ) {
					position.top = withinOffset;

				// Element is initially over both top and bottom of within
				} else {
					if ( overTop > overBottom ) {
						position.top = withinOffset + outerHeight - data.collisionHeight;
					} else {
						position.top = withinOffset;
					}
				}

			// Too far up -> align with top
			} else if ( overTop > 0 ) {
				position.top += overTop;

			// Too far down -> align with bottom edge
			} else if ( overBottom > 0 ) {
				position.top -= overBottom;

			// Adjust based on position and margin
			} else {
				position.top = max( position.top - collisionPosTop, position.top );
			}
		}
	},
	flip: {
		left: function( position, data ) {
			var within = data.within,
				withinOffset = within.offset.left + within.scrollLeft,
				outerWidth = within.width,
				offsetLeft = within.isWindow ? within.scrollLeft : within.offset.left,
				collisionPosLeft = position.left - data.collisionPosition.marginLeft,
				overLeft = collisionPosLeft - offsetLeft,
				overRight = collisionPosLeft + data.collisionWidth - outerWidth - offsetLeft,
				myOffset = data.my[ 0 ] === "left" ?
					-data.elemWidth :
					data.my[ 0 ] === "right" ?
						data.elemWidth :
						0,
				atOffset = data.at[ 0 ] === "left" ?
					data.targetWidth :
					data.at[ 0 ] === "right" ?
						-data.targetWidth :
						0,
				offset = -2 * data.offset[ 0 ],
				newOverRight,
				newOverLeft;

			if ( overLeft < 0 ) {
				newOverRight = position.left + myOffset + atOffset + offset + data.collisionWidth -
					outerWidth - withinOffset;
				if ( newOverRight < 0 || newOverRight < abs( overLeft ) ) {
					position.left += myOffset + atOffset + offset;
				}
			} else if ( overRight > 0 ) {
				newOverLeft = position.left - data.collisionPosition.marginLeft + myOffset +
					atOffset + offset - offsetLeft;
				if ( newOverLeft > 0 || abs( newOverLeft ) < overRight ) {
					position.left += myOffset + atOffset + offset;
				}
			}
		},
		top: function( position, data ) {
			var within = data.within,
				withinOffset = within.offset.top + within.scrollTop,
				outerHeight = within.height,
				offsetTop = within.isWindow ? within.scrollTop : within.offset.top,
				collisionPosTop = position.top - data.collisionPosition.marginTop,
				overTop = collisionPosTop - offsetTop,
				overBottom = collisionPosTop + data.collisionHeight - outerHeight - offsetTop,
				top = data.my[ 1 ] === "top",
				myOffset = top ?
					-data.elemHeight :
					data.my[ 1 ] === "bottom" ?
						data.elemHeight :
						0,
				atOffset = data.at[ 1 ] === "top" ?
					data.targetHeight :
					data.at[ 1 ] === "bottom" ?
						-data.targetHeight :
						0,
				offset = -2 * data.offset[ 1 ],
				newOverTop,
				newOverBottom;
			if ( overTop < 0 ) {
				newOverBottom = position.top + myOffset + atOffset + offset + data.collisionHeight -
					outerHeight - withinOffset;
				if ( newOverBottom < 0 || newOverBottom < abs( overTop ) ) {
					position.top += myOffset + atOffset + offset;
				}
			} else if ( overBottom > 0 ) {
				newOverTop = position.top - data.collisionPosition.marginTop + myOffset + atOffset +
					offset - offsetTop;
				if ( newOverTop > 0 || abs( newOverTop ) < overBottom ) {
					position.top += myOffset + atOffset + offset;
				}
			}
		}
	},
	flipfit: {
		left: function() {
			$.ui.position.flip.left.apply( this, arguments );
			$.ui.position.fit.left.apply( this, arguments );
		},
		top: function() {
			$.ui.position.flip.top.apply( this, arguments );
			$.ui.position.fit.top.apply( this, arguments );
		}
	}
};

} )();

var position = $.ui.position;


/*!
 * jQuery UI :data 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: :data Selector
//>>group: Core
//>>description: Selects elements which have data stored under the specified key.
//>>docs: http://api.jqueryui.com/data-selector/


var data = $.extend( $.expr[ ":" ], {
	data: $.expr.createPseudo ?
		$.expr.createPseudo( function( dataName ) {
			return function( elem ) {
				return !!$.data( elem, dataName );
			};
		} ) :

		// Support: jQuery <1.8
		function( elem, i, match ) {
			return !!$.data( elem, match[ 3 ] );
		}
} );

/*!
 * jQuery UI Disable Selection 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: disableSelection
//>>group: Core
//>>description: Disable selection of text content within the set of matched elements.
//>>docs: http://api.jqueryui.com/disableSelection/

// This file is deprecated


var disableSelection = $.fn.extend( {
	disableSelection: ( function() {
		var eventType = "onselectstart" in document.createElement( "div" ) ?
			"selectstart" :
			"mousedown";

		return function() {
			return this.on( eventType + ".ui-disableSelection", function( event ) {
				event.preventDefault();
			} );
		};
	} )(),

	enableSelection: function() {
		return this.off( ".ui-disableSelection" );
	}
} );


/*!
 * jQuery UI Effects 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: Effects Core
//>>group: Effects
// jscs:disable maximumLineLength
//>>description: Extends the internal jQuery effects. Includes morphing and easing. Required by all other effects.
// jscs:enable maximumLineLength
//>>docs: http://api.jqueryui.com/category/effects-core/
//>>demos: http://jqueryui.com/effect/



var dataSpace = "ui-effects-",
	dataSpaceStyle = "ui-effects-style",
	dataSpaceAnimated = "ui-effects-animated",

	// Create a local jQuery because jQuery Color relies on it and the
	// global may not exist with AMD and a custom build (#10199)
	jQuery = $;

$.effects = {
	effect: {}
};

/*!
 * jQuery Color Animations v2.1.2
 * https://github.com/jquery/jquery-color
 *
 * Copyright 2014 jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 *
 * Date: Wed Jan 16 08:47:09 2013 -0600
 */
( function( jQuery, undefined ) {

	var stepHooks = "backgroundColor borderBottomColor borderLeftColor borderRightColor " +
		"borderTopColor color columnRuleColor outlineColor textDecorationColor textEmphasisColor",

	// Plusequals test for += 100 -= 100
	rplusequals = /^([\-+])=\s*(\d+\.?\d*)/,

	// A set of RE's that can match strings and generate color tuples.
	stringParsers = [ {
			re: /rgba?\(\s*(\d{1,3})\s*,\s*(\d{1,3})\s*,\s*(\d{1,3})\s*(?:,\s*(\d?(?:\.\d+)?)\s*)?\)/,
			parse: function( execResult ) {
				return [
					execResult[ 1 ],
					execResult[ 2 ],
					execResult[ 3 ],
					execResult[ 4 ]
				];
			}
		}, {
			re: /rgba?\(\s*(\d+(?:\.\d+)?)\%\s*,\s*(\d+(?:\.\d+)?)\%\s*,\s*(\d+(?:\.\d+)?)\%\s*(?:,\s*(\d?(?:\.\d+)?)\s*)?\)/,
			parse: function( execResult ) {
				return [
					execResult[ 1 ] * 2.55,
					execResult[ 2 ] * 2.55,
					execResult[ 3 ] * 2.55,
					execResult[ 4 ]
				];
			}
		}, {

			// This regex ignores A-F because it's compared against an already lowercased string
			re: /#([a-f0-9]{2})([a-f0-9]{2})([a-f0-9]{2})/,
			parse: function( execResult ) {
				return [
					parseInt( execResult[ 1 ], 16 ),
					parseInt( execResult[ 2 ], 16 ),
					parseInt( execResult[ 3 ], 16 )
				];
			}
		}, {

			// This regex ignores A-F because it's compared against an already lowercased string
			re: /#([a-f0-9])([a-f0-9])([a-f0-9])/,
			parse: function( execResult ) {
				return [
					parseInt( execResult[ 1 ] + execResult[ 1 ], 16 ),
					parseInt( execResult[ 2 ] + execResult[ 2 ], 16 ),
					parseInt( execResult[ 3 ] + execResult[ 3 ], 16 )
				];
			}
		}, {
			re: /hsla?\(\s*(\d+(?:\.\d+)?)\s*,\s*(\d+(?:\.\d+)?)\%\s*,\s*(\d+(?:\.\d+)?)\%\s*(?:,\s*(\d?(?:\.\d+)?)\s*)?\)/,
			space: "hsla",
			parse: function( execResult ) {
				return [
					execResult[ 1 ],
					execResult[ 2 ] / 100,
					execResult[ 3 ] / 100,
					execResult[ 4 ]
				];
			}
		} ],

	// JQuery.Color( )
	color = jQuery.Color = function( color, green, blue, alpha ) {
		return new jQuery.Color.fn.parse( color, green, blue, alpha );
	},
	spaces = {
		rgba: {
			props: {
				red: {
					idx: 0,
					type: "byte"
				},
				green: {
					idx: 1,
					type: "byte"
				},
				blue: {
					idx: 2,
					type: "byte"
				}
			}
		},

		hsla: {
			props: {
				hue: {
					idx: 0,
					type: "degrees"
				},
				saturation: {
					idx: 1,
					type: "percent"
				},
				lightness: {
					idx: 2,
					type: "percent"
				}
			}
		}
	},
	propTypes = {
		"byte": {
			floor: true,
			max: 255
		},
		"percent": {
			max: 1
		},
		"degrees": {
			mod: 360,
			floor: true
		}
	},
	support = color.support = {},

	// Element for support tests
	supportElem = jQuery( "<p>" )[ 0 ],

	// Colors = jQuery.Color.names
	colors,

	// Local aliases of functions called often
	each = jQuery.each;

// Determine rgba support immediately
supportElem.style.cssText = "background-color:rgba(1,1,1,.5)";
support.rgba = supportElem.style.backgroundColor.indexOf( "rgba" ) > -1;

// Define cache name and alpha properties
// for rgba and hsla spaces
each( spaces, function( spaceName, space ) {
	space.cache = "_" + spaceName;
	space.props.alpha = {
		idx: 3,
		type: "percent",
		def: 1
	};
} );

function clamp( value, prop, allowEmpty ) {
	var type = propTypes[ prop.type ] || {};

	if ( value == null ) {
		return ( allowEmpty || !prop.def ) ? null : prop.def;
	}

	// ~~ is an short way of doing floor for positive numbers
	value = type.floor ? ~~value : parseFloat( value );

	// IE will pass in empty strings as value for alpha,
	// which will hit this case
	if ( isNaN( value ) ) {
		return prop.def;
	}

	if ( type.mod ) {

		// We add mod before modding to make sure that negatives values
		// get converted properly: -10 -> 350
		return ( value + type.mod ) % type.mod;
	}

	// For now all property types without mod have min and max
	return 0 > value ? 0 : type.max < value ? type.max : value;
}

function stringParse( string ) {
	var inst = color(),
		rgba = inst._rgba = [];

	string = string.toLowerCase();

	each( stringParsers, function( i, parser ) {
		var parsed,
			match = parser.re.exec( string ),
			values = match && parser.parse( match ),
			spaceName = parser.space || "rgba";

		if ( values ) {
			parsed = inst[ spaceName ]( values );

			// If this was an rgba parse the assignment might happen twice
			// oh well....
			inst[ spaces[ spaceName ].cache ] = parsed[ spaces[ spaceName ].cache ];
			rgba = inst._rgba = parsed._rgba;

			// Exit each( stringParsers ) here because we matched
			return false;
		}
	} );

	// Found a stringParser that handled it
	if ( rgba.length ) {

		// If this came from a parsed string, force "transparent" when alpha is 0
		// chrome, (and maybe others) return "transparent" as rgba(0,0,0,0)
		if ( rgba.join() === "0,0,0,0" ) {
			jQuery.extend( rgba, colors.transparent );
		}
		return inst;
	}

	// Named colors
	return colors[ string ];
}

color.fn = jQuery.extend( color.prototype, {
	parse: function( red, green, blue, alpha ) {
		if ( red === undefined ) {
			this._rgba = [ null, null, null, null ];
			return this;
		}
		if ( red.jquery || red.nodeType ) {
			red = jQuery( red ).css( green );
			green = undefined;
		}

		var inst = this,
			type = jQuery.type( red ),
			rgba = this._rgba = [];

		// More than 1 argument specified - assume ( red, green, blue, alpha )
		if ( green !== undefined ) {
			red = [ red, green, blue, alpha ];
			type = "array";
		}

		if ( type === "string" ) {
			return this.parse( stringParse( red ) || colors._default );
		}

		if ( type === "array" ) {
			each( spaces.rgba.props, function( key, prop ) {
				rgba[ prop.idx ] = clamp( red[ prop.idx ], prop );
			} );
			return this;
		}

		if ( type === "object" ) {
			if ( red instanceof color ) {
				each( spaces, function( spaceName, space ) {
					if ( red[ space.cache ] ) {
						inst[ space.cache ] = red[ space.cache ].slice();
					}
				} );
			} else {
				each( spaces, function( spaceName, space ) {
					var cache = space.cache;
					each( space.props, function( key, prop ) {

						// If the cache doesn't exist, and we know how to convert
						if ( !inst[ cache ] && space.to ) {

							// If the value was null, we don't need to copy it
							// if the key was alpha, we don't need to copy it either
							if ( key === "alpha" || red[ key ] == null ) {
								return;
							}
							inst[ cache ] = space.to( inst._rgba );
						}

						// This is the only case where we allow nulls for ALL properties.
						// call clamp with alwaysAllowEmpty
						inst[ cache ][ prop.idx ] = clamp( red[ key ], prop, true );
					} );

					// Everything defined but alpha?
					if ( inst[ cache ] &&
							jQuery.inArray( null, inst[ cache ].slice( 0, 3 ) ) < 0 ) {

						// Use the default of 1
						inst[ cache ][ 3 ] = 1;
						if ( space.from ) {
							inst._rgba = space.from( inst[ cache ] );
						}
					}
				} );
			}
			return this;
		}
	},
	is: function( compare ) {
		var is = color( compare ),
			same = true,
			inst = this;

		each( spaces, function( _, space ) {
			var localCache,
				isCache = is[ space.cache ];
			if ( isCache ) {
				localCache = inst[ space.cache ] || space.to && space.to( inst._rgba ) || [];
				each( space.props, function( _, prop ) {
					if ( isCache[ prop.idx ] != null ) {
						same = ( isCache[ prop.idx ] === localCache[ prop.idx ] );
						return same;
					}
				} );
			}
			return same;
		} );
		return same;
	},
	_space: function() {
		var used = [],
			inst = this;
		each( spaces, function( spaceName, space ) {
			if ( inst[ space.cache ] ) {
				used.push( spaceName );
			}
		} );
		return used.pop();
	},
	transition: function( other, distance ) {
		var end = color( other ),
			spaceName = end._space(),
			space = spaces[ spaceName ],
			startColor = this.alpha() === 0 ? color( "transparent" ) : this,
			start = startColor[ space.cache ] || space.to( startColor._rgba ),
			result = start.slice();

		end = end[ space.cache ];
		each( space.props, function( key, prop ) {
			var index = prop.idx,
				startValue = start[ index ],
				endValue = end[ index ],
				type = propTypes[ prop.type ] || {};

			// If null, don't override start value
			if ( endValue === null ) {
				return;
			}

			// If null - use end
			if ( startValue === null ) {
				result[ index ] = endValue;
			} else {
				if ( type.mod ) {
					if ( endValue - startValue > type.mod / 2 ) {
						startValue += type.mod;
					} else if ( startValue - endValue > type.mod / 2 ) {
						startValue -= type.mod;
					}
				}
				result[ index ] = clamp( ( endValue - startValue ) * distance + startValue, prop );
			}
		} );
		return this[ spaceName ]( result );
	},
	blend: function( opaque ) {

		// If we are already opaque - return ourself
		if ( this._rgba[ 3 ] === 1 ) {
			return this;
		}

		var rgb = this._rgba.slice(),
			a = rgb.pop(),
			blend = color( opaque )._rgba;

		return color( jQuery.map( rgb, function( v, i ) {
			return ( 1 - a ) * blend[ i ] + a * v;
		} ) );
	},
	toRgbaString: function() {
		var prefix = "rgba(",
			rgba = jQuery.map( this._rgba, function( v, i ) {
				return v == null ? ( i > 2 ? 1 : 0 ) : v;
			} );

		if ( rgba[ 3 ] === 1 ) {
			rgba.pop();
			prefix = "rgb(";
		}

		return prefix + rgba.join() + ")";
	},
	toHslaString: function() {
		var prefix = "hsla(",
			hsla = jQuery.map( this.hsla(), function( v, i ) {
				if ( v == null ) {
					v = i > 2 ? 1 : 0;
				}

				// Catch 1 and 2
				if ( i && i < 3 ) {
					v = Math.round( v * 100 ) + "%";
				}
				return v;
			} );

		if ( hsla[ 3 ] === 1 ) {
			hsla.pop();
			prefix = "hsl(";
		}
		return prefix + hsla.join() + ")";
	},
	toHexString: function( includeAlpha ) {
		var rgba = this._rgba.slice(),
			alpha = rgba.pop();

		if ( includeAlpha ) {
			rgba.push( ~~( alpha * 255 ) );
		}

		return "#" + jQuery.map( rgba, function( v ) {

			// Default to 0 when nulls exist
			v = ( v || 0 ).toString( 16 );
			return v.length === 1 ? "0" + v : v;
		} ).join( "" );
	},
	toString: function() {
		return this._rgba[ 3 ] === 0 ? "transparent" : this.toRgbaString();
	}
} );
color.fn.parse.prototype = color.fn;

// Hsla conversions adapted from:
// https://code.google.com/p/maashaack/source/browse/packages/graphics/trunk/src/graphics/colors/HUE2RGB.as?r=5021

function hue2rgb( p, q, h ) {
	h = ( h + 1 ) % 1;
	if ( h * 6 < 1 ) {
		return p + ( q - p ) * h * 6;
	}
	if ( h * 2 < 1 ) {
		return q;
	}
	if ( h * 3 < 2 ) {
		return p + ( q - p ) * ( ( 2 / 3 ) - h ) * 6;
	}
	return p;
}

spaces.hsla.to = function( rgba ) {
	if ( rgba[ 0 ] == null || rgba[ 1 ] == null || rgba[ 2 ] == null ) {
		return [ null, null, null, rgba[ 3 ] ];
	}
	var r = rgba[ 0 ] / 255,
		g = rgba[ 1 ] / 255,
		b = rgba[ 2 ] / 255,
		a = rgba[ 3 ],
		max = Math.max( r, g, b ),
		min = Math.min( r, g, b ),
		diff = max - min,
		add = max + min,
		l = add * 0.5,
		h, s;

	if ( min === max ) {
		h = 0;
	} else if ( r === max ) {
		h = ( 60 * ( g - b ) / diff ) + 360;
	} else if ( g === max ) {
		h = ( 60 * ( b - r ) / diff ) + 120;
	} else {
		h = ( 60 * ( r - g ) / diff ) + 240;
	}

	// Chroma (diff) == 0 means greyscale which, by definition, saturation = 0%
	// otherwise, saturation is based on the ratio of chroma (diff) to lightness (add)
	if ( diff === 0 ) {
		s = 0;
	} else if ( l <= 0.5 ) {
		s = diff / add;
	} else {
		s = diff / ( 2 - add );
	}
	return [ Math.round( h ) % 360, s, l, a == null ? 1 : a ];
};

spaces.hsla.from = function( hsla ) {
	if ( hsla[ 0 ] == null || hsla[ 1 ] == null || hsla[ 2 ] == null ) {
		return [ null, null, null, hsla[ 3 ] ];
	}
	var h = hsla[ 0 ] / 360,
		s = hsla[ 1 ],
		l = hsla[ 2 ],
		a = hsla[ 3 ],
		q = l <= 0.5 ? l * ( 1 + s ) : l + s - l * s,
		p = 2 * l - q;

	return [
		Math.round( hue2rgb( p, q, h + ( 1 / 3 ) ) * 255 ),
		Math.round( hue2rgb( p, q, h ) * 255 ),
		Math.round( hue2rgb( p, q, h - ( 1 / 3 ) ) * 255 ),
		a
	];
};

each( spaces, function( spaceName, space ) {
	var props = space.props,
		cache = space.cache,
		to = space.to,
		from = space.from;

	// Makes rgba() and hsla()
	color.fn[ spaceName ] = function( value ) {

		// Generate a cache for this space if it doesn't exist
		if ( to && !this[ cache ] ) {
			this[ cache ] = to( this._rgba );
		}
		if ( value === undefined ) {
			return this[ cache ].slice();
		}

		var ret,
			type = jQuery.type( value ),
			arr = ( type === "array" || type === "object" ) ? value : arguments,
			local = this[ cache ].slice();

		each( props, function( key, prop ) {
			var val = arr[ type === "object" ? key : prop.idx ];
			if ( val == null ) {
				val = local[ prop.idx ];
			}
			local[ prop.idx ] = clamp( val, prop );
		} );

		if ( from ) {
			ret = color( from( local ) );
			ret[ cache ] = local;
			return ret;
		} else {
			return color( local );
		}
	};

	// Makes red() green() blue() alpha() hue() saturation() lightness()
	each( props, function( key, prop ) {

		// Alpha is included in more than one space
		if ( color.fn[ key ] ) {
			return;
		}
		color.fn[ key ] = function( value ) {
			var vtype = jQuery.type( value ),
				fn = ( key === "alpha" ? ( this._hsla ? "hsla" : "rgba" ) : spaceName ),
				local = this[ fn ](),
				cur = local[ prop.idx ],
				match;

			if ( vtype === "undefined" ) {
				return cur;
			}

			if ( vtype === "function" ) {
				value = value.call( this, cur );
				vtype = jQuery.type( value );
			}
			if ( value == null && prop.empty ) {
				return this;
			}
			if ( vtype === "string" ) {
				match = rplusequals.exec( value );
				if ( match ) {
					value = cur + parseFloat( match[ 2 ] ) * ( match[ 1 ] === "+" ? 1 : -1 );
				}
			}
			local[ prop.idx ] = value;
			return this[ fn ]( local );
		};
	} );
} );

// Add cssHook and .fx.step function for each named hook.
// accept a space separated string of properties
color.hook = function( hook ) {
	var hooks = hook.split( " " );
	each( hooks, function( i, hook ) {
		jQuery.cssHooks[ hook ] = {
			set: function( elem, value ) {
				var parsed, curElem,
					backgroundColor = "";

				if ( value !== "transparent" && ( jQuery.type( value ) !== "string" ||
						( parsed = stringParse( value ) ) ) ) {
					value = color( parsed || value );
					if ( !support.rgba && value._rgba[ 3 ] !== 1 ) {
						curElem = hook === "backgroundColor" ? elem.parentNode : elem;
						while (
							( backgroundColor === "" || backgroundColor === "transparent" ) &&
							curElem && curElem.style
						) {
							try {
								backgroundColor = jQuery.css( curElem, "backgroundColor" );
								curElem = curElem.parentNode;
							} catch ( e ) {
							}
						}

						value = value.blend( backgroundColor && backgroundColor !== "transparent" ?
							backgroundColor :
							"_default" );
					}

					value = value.toRgbaString();
				}
				try {
					elem.style[ hook ] = value;
				} catch ( e ) {

					// Wrapped to prevent IE from throwing errors on "invalid" values like
					// 'auto' or 'inherit'
				}
			}
		};
		jQuery.fx.step[ hook ] = function( fx ) {
			if ( !fx.colorInit ) {
				fx.start = color( fx.elem, hook );
				fx.end = color( fx.end );
				fx.colorInit = true;
			}
			jQuery.cssHooks[ hook ].set( fx.elem, fx.start.transition( fx.end, fx.pos ) );
		};
	} );

};

color.hook( stepHooks );

jQuery.cssHooks.borderColor = {
	expand: function( value ) {
		var expanded = {};

		each( [ "Top", "Right", "Bottom", "Left" ], function( i, part ) {
			expanded[ "border" + part + "Color" ] = value;
		} );
		return expanded;
	}
};

// Basic color names only.
// Usage of any of the other color names requires adding yourself or including
// jquery.color.svg-names.js.
colors = jQuery.Color.names = {

	// 4.1. Basic color keywords
	aqua: "#00ffff",
	black: "#000000",
	blue: "#0000ff",
	fuchsia: "#ff00ff",
	gray: "#808080",
	green: "#008000",
	lime: "#00ff00",
	maroon: "#800000",
	navy: "#000080",
	olive: "#808000",
	purple: "#800080",
	red: "#ff0000",
	silver: "#c0c0c0",
	teal: "#008080",
	white: "#ffffff",
	yellow: "#ffff00",

	// 4.2.3. "transparent" color keyword
	transparent: [ null, null, null, 0 ],

	_default: "#ffffff"
};

} )( jQuery );

/******************************************************************************/
/****************************** CLASS ANIMATIONS ******************************/
/******************************************************************************/
( function() {

var classAnimationActions = [ "add", "remove", "toggle" ],
	shorthandStyles = {
		border: 1,
		borderBottom: 1,
		borderColor: 1,
		borderLeft: 1,
		borderRight: 1,
		borderTop: 1,
		borderWidth: 1,
		margin: 1,
		padding: 1
	};

$.each(
	[ "borderLeftStyle", "borderRightStyle", "borderBottomStyle", "borderTopStyle" ],
	function( _, prop ) {
		$.fx.step[ prop ] = function( fx ) {
			if ( fx.end !== "none" && !fx.setAttr || fx.pos === 1 && !fx.setAttr ) {
				jQuery.style( fx.elem, prop, fx.end );
				fx.setAttr = true;
			}
		};
	}
);

function getElementStyles( elem ) {
	var key, len,
		style = elem.ownerDocument.defaultView ?
			elem.ownerDocument.defaultView.getComputedStyle( elem, null ) :
			elem.currentStyle,
		styles = {};

	if ( style && style.length && style[ 0 ] && style[ style[ 0 ] ] ) {
		len = style.length;
		while ( len-- ) {
			key = style[ len ];
			if ( typeof style[ key ] === "string" ) {
				styles[ $.camelCase( key ) ] = style[ key ];
			}
		}

	// Support: Opera, IE <9
	} else {
		for ( key in style ) {
			if ( typeof style[ key ] === "string" ) {
				styles[ key ] = style[ key ];
			}
		}
	}

	return styles;
}

function styleDifference( oldStyle, newStyle ) {
	var diff = {},
		name, value;

	for ( name in newStyle ) {
		value = newStyle[ name ];
		if ( oldStyle[ name ] !== value ) {
			if ( !shorthandStyles[ name ] ) {
				if ( $.fx.step[ name ] || !isNaN( parseFloat( value ) ) ) {
					diff[ name ] = value;
				}
			}
		}
	}

	return diff;
}

// Support: jQuery <1.8
if ( !$.fn.addBack ) {
	$.fn.addBack = function( selector ) {
		return this.add( selector == null ?
			this.prevObject : this.prevObject.filter( selector )
		);
	};
}

$.effects.animateClass = function( value, duration, easing, callback ) {
	var o = $.speed( duration, easing, callback );

	return this.queue( function() {
		var animated = $( this ),
			baseClass = animated.attr( "class" ) || "",
			applyClassChange,
			allAnimations = o.children ? animated.find( "*" ).addBack() : animated;

		// Map the animated objects to store the original styles.
		allAnimations = allAnimations.map( function() {
			var el = $( this );
			return {
				el: el,
				start: getElementStyles( this )
			};
		} );

		// Apply class change
		applyClassChange = function() {
			$.each( classAnimationActions, function( i, action ) {
				if ( value[ action ] ) {
					animated[ action + "Class" ]( value[ action ] );
				}
			} );
		};
		applyClassChange();

		// Map all animated objects again - calculate new styles and diff
		allAnimations = allAnimations.map( function() {
			this.end = getElementStyles( this.el[ 0 ] );
			this.diff = styleDifference( this.start, this.end );
			return this;
		} );

		// Apply original class
		animated.attr( "class", baseClass );

		// Map all animated objects again - this time collecting a promise
		allAnimations = allAnimations.map( function() {
			var styleInfo = this,
				dfd = $.Deferred(),
				opts = $.extend( {}, o, {
					queue: false,
					complete: function() {
						dfd.resolve( styleInfo );
					}
				} );

			this.el.animate( this.diff, opts );
			return dfd.promise();
		} );

		// Once all animations have completed:
		$.when.apply( $, allAnimations.get() ).done( function() {

			// Set the final class
			applyClassChange();

			// For each animated element,
			// clear all css properties that were animated
			$.each( arguments, function() {
				var el = this.el;
				$.each( this.diff, function( key ) {
					el.css( key, "" );
				} );
			} );

			// This is guarnteed to be there if you use jQuery.speed()
			// it also handles dequeuing the next anim...
			o.complete.call( animated[ 0 ] );
		} );
	} );
};

$.fn.extend( {
	addClass: ( function( orig ) {
		return function( classNames, speed, easing, callback ) {
			return speed ?
				$.effects.animateClass.call( this,
					{ add: classNames }, speed, easing, callback ) :
				orig.apply( this, arguments );
		};
	} )( $.fn.addClass ),

	removeClass: ( function( orig ) {
		return function( classNames, speed, easing, callback ) {
			return arguments.length > 1 ?
				$.effects.animateClass.call( this,
					{ remove: classNames }, speed, easing, callback ) :
				orig.apply( this, arguments );
		};
	} )( $.fn.removeClass ),

	toggleClass: ( function( orig ) {
		return function( classNames, force, speed, easing, callback ) {
			if ( typeof force === "boolean" || force === undefined ) {
				if ( !speed ) {

					// Without speed parameter
					return orig.apply( this, arguments );
				} else {
					return $.effects.animateClass.call( this,
						( force ? { add: classNames } : { remove: classNames } ),
						speed, easing, callback );
				}
			} else {

				// Without force parameter
				return $.effects.animateClass.call( this,
					{ toggle: classNames }, force, speed, easing );
			}
		};
	} )( $.fn.toggleClass ),

	switchClass: function( remove, add, speed, easing, callback ) {
		return $.effects.animateClass.call( this, {
			add: add,
			remove: remove
		}, speed, easing, callback );
	}
} );

} )();

/******************************************************************************/
/*********************************** EFFECTS **********************************/
/******************************************************************************/

( function() {

if ( $.expr && $.expr.filters && $.expr.filters.animated ) {
	$.expr.filters.animated = ( function( orig ) {
		return function( elem ) {
			return !!$( elem ).data( dataSpaceAnimated ) || orig( elem );
		};
	} )( $.expr.filters.animated );
}

if ( $.uiBackCompat !== false ) {
	$.extend( $.effects, {

		// Saves a set of properties in a data storage
		save: function( element, set ) {
			var i = 0, length = set.length;
			for ( ; i < length; i++ ) {
				if ( set[ i ] !== null ) {
					element.data( dataSpace + set[ i ], element[ 0 ].style[ set[ i ] ] );
				}
			}
		},

		// Restores a set of previously saved properties from a data storage
		restore: function( element, set ) {
			var val, i = 0, length = set.length;
			for ( ; i < length; i++ ) {
				if ( set[ i ] !== null ) {
					val = element.data( dataSpace + set[ i ] );
					element.css( set[ i ], val );
				}
			}
		},

		setMode: function( el, mode ) {
			if ( mode === "toggle" ) {
				mode = el.is( ":hidden" ) ? "show" : "hide";
			}
			return mode;
		},

		// Wraps the element around a wrapper that copies position properties
		createWrapper: function( element ) {

			// If the element is already wrapped, return it
			if ( element.parent().is( ".ui-effects-wrapper" ) ) {
				return element.parent();
			}

			// Wrap the element
			var props = {
					width: element.outerWidth( true ),
					height: element.outerHeight( true ),
					"float": element.css( "float" )
				},
				wrapper = $( "<div></div>" )
					.addClass( "ui-effects-wrapper" )
					.css( {
						fontSize: "100%",
						background: "transparent",
						border: "none",
						margin: 0,
						padding: 0
					} ),

				// Store the size in case width/height are defined in % - Fixes #5245
				size = {
					width: element.width(),
					height: element.height()
				},
				active = document.activeElement;

			// Support: Firefox
			// Firefox incorrectly exposes anonymous content
			// https://bugzilla.mozilla.org/show_bug.cgi?id=561664
			try {
				active.id;
			} catch ( e ) {
				active = document.body;
			}

			element.wrap( wrapper );

			// Fixes #7595 - Elements lose focus when wrapped.
			if ( element[ 0 ] === active || $.contains( element[ 0 ], active ) ) {
				$( active ).trigger( "focus" );
			}

			// Hotfix for jQuery 1.4 since some change in wrap() seems to actually
			// lose the reference to the wrapped element
			wrapper = element.parent();

			// Transfer positioning properties to the wrapper
			if ( element.css( "position" ) === "static" ) {
				wrapper.css( { position: "relative" } );
				element.css( { position: "relative" } );
			} else {
				$.extend( props, {
					position: element.css( "position" ),
					zIndex: element.css( "z-index" )
				} );
				$.each( [ "top", "left", "bottom", "right" ], function( i, pos ) {
					props[ pos ] = element.css( pos );
					if ( isNaN( parseInt( props[ pos ], 10 ) ) ) {
						props[ pos ] = "auto";
					}
				} );
				element.css( {
					position: "relative",
					top: 0,
					left: 0,
					right: "auto",
					bottom: "auto"
				} );
			}
			element.css( size );

			return wrapper.css( props ).show();
		},

		removeWrapper: function( element ) {
			var active = document.activeElement;

			if ( element.parent().is( ".ui-effects-wrapper" ) ) {
				element.parent().replaceWith( element );

				// Fixes #7595 - Elements lose focus when wrapped.
				if ( element[ 0 ] === active || $.contains( element[ 0 ], active ) ) {
					$( active ).trigger( "focus" );
				}
			}

			return element;
		}
	} );
}

$.extend( $.effects, {
	version: "1.12.0",

	define: function( name, mode, effect ) {
		if ( !effect ) {
			effect = mode;
			mode = "effect";
		}

		$.effects.effect[ name ] = effect;
		$.effects.effect[ name ].mode = mode;

		return effect;
	},

	scaledDimensions: function( element, percent, direction ) {
		if ( percent === 0 ) {
			return {
				height: 0,
				width: 0,
				outerHeight: 0,
				outerWidth: 0
			};
		}

		var x = direction !== "horizontal" ? ( ( percent || 100 ) / 100 ) : 1,
			y = direction !== "vertical" ? ( ( percent || 100 ) / 100 ) : 1;

		return {
			height: element.height() * y,
			width: element.width() * x,
			outerHeight: element.outerHeight() * y,
			outerWidth: element.outerWidth() * x
		};

	},

	clipToBox: function( animation ) {
		return {
			width: animation.clip.right - animation.clip.left,
			height: animation.clip.bottom - animation.clip.top,
			left: animation.clip.left,
			top: animation.clip.top
		};
	},

	// Injects recently queued functions to be first in line (after "inprogress")
	unshift: function( element, queueLength, count ) {
		var queue = element.queue();

		if ( queueLength > 1 ) {
			queue.splice.apply( queue,
				[ 1, 0 ].concat( queue.splice( queueLength, count ) ) );
		}
		element.dequeue();
	},

	saveStyle: function( element ) {
		element.data( dataSpaceStyle, element[ 0 ].style.cssText );
	},

	restoreStyle: function( element ) {
		element[ 0 ].style.cssText = element.data( dataSpaceStyle ) || "";
		element.removeData( dataSpaceStyle );
	},

	mode: function( element, mode ) {
		var hidden = element.is( ":hidden" );

		if ( mode === "toggle" ) {
			mode = hidden ? "show" : "hide";
		}
		if ( hidden ? mode === "hide" : mode === "show" ) {
			mode = "none";
		}
		return mode;
	},

	// Translates a [top,left] array into a baseline value
	getBaseline: function( origin, original ) {
		var y, x;

		switch ( origin[ 0 ] ) {
		case "top":
			y = 0;
			break;
		case "middle":
			y = 0.5;
			break;
		case "bottom":
			y = 1;
			break;
		default:
			y = origin[ 0 ] / original.height;
		}

		switch ( origin[ 1 ] ) {
		case "left":
			x = 0;
			break;
		case "center":
			x = 0.5;
			break;
		case "right":
			x = 1;
			break;
		default:
			x = origin[ 1 ] / original.width;
		}

		return {
			x: x,
			y: y
		};
	},

	// Creates a placeholder element so that the original element can be made absolute
	createPlaceholder: function( element ) {
		var placeholder,
			cssPosition = element.css( "position" ),
			position = element.position();

		// Lock in margins first to account for form elements, which
		// will change margin if you explicitly set height
		// see: http://jsfiddle.net/JZSMt/3/ https://bugs.webkit.org/show_bug.cgi?id=107380
		// Support: Safari
		element.css( {
			marginTop: element.css( "marginTop" ),
			marginBottom: element.css( "marginBottom" ),
			marginLeft: element.css( "marginLeft" ),
			marginRight: element.css( "marginRight" )
		} )
		.outerWidth( element.outerWidth() )
		.outerHeight( element.outerHeight() );

		if ( /^(static|relative)/.test( cssPosition ) ) {
			cssPosition = "absolute";

			placeholder = $( "<" + element[ 0 ].nodeName + ">" ).insertAfter( element ).css( {

				// Convert inline to inline block to account for inline elements
				// that turn to inline block based on content (like img)
				display: /^(inline|ruby)/.test( element.css( "display" ) ) ?
					"inline-block" :
					"block",
				visibility: "hidden",

				// Margins need to be set to account for margin collapse
				marginTop: element.css( "marginTop" ),
				marginBottom: element.css( "marginBottom" ),
				marginLeft: element.css( "marginLeft" ),
				marginRight: element.css( "marginRight" ),
				"float": element.css( "float" )
			} )
			.outerWidth( element.outerWidth() )
			.outerHeight( element.outerHeight() )
			.addClass( "ui-effects-placeholder" );

			element.data( dataSpace + "placeholder", placeholder );
		}

		element.css( {
			position: cssPosition,
			left: position.left,
			top: position.top
		} );

		return placeholder;
	},

	removePlaceholder: function( element ) {
		var dataKey = dataSpace + "placeholder",
				placeholder = element.data( dataKey );

		if ( placeholder ) {
			placeholder.remove();
			element.removeData( dataKey );
		}
	},

	// Removes a placeholder if it exists and restores
	// properties that were modified during placeholder creation
	cleanUp: function( element ) {
		$.effects.restoreStyle( element );
		$.effects.removePlaceholder( element );
	},

	setTransition: function( element, list, factor, value ) {
		value = value || {};
		$.each( list, function( i, x ) {
			var unit = element.cssUnit( x );
			if ( unit[ 0 ] > 0 ) {
				value[ x ] = unit[ 0 ] * factor + unit[ 1 ];
			}
		} );
		return value;
	}
} );

// Return an effect options object for the given parameters:
function _normalizeArguments( effect, options, speed, callback ) {

	// Allow passing all options as the first parameter
	if ( $.isPlainObject( effect ) ) {
		options = effect;
		effect = effect.effect;
	}

	// Convert to an object
	effect = { effect: effect };

	// Catch (effect, null, ...)
	if ( options == null ) {
		options = {};
	}

	// Catch (effect, callback)
	if ( $.isFunction( options ) ) {
		callback = options;
		speed = null;
		options = {};
	}

	// Catch (effect, speed, ?)
	if ( typeof options === "number" || $.fx.speeds[ options ] ) {
		callback = speed;
		speed = options;
		options = {};
	}

	// Catch (effect, options, callback)
	if ( $.isFunction( speed ) ) {
		callback = speed;
		speed = null;
	}

	// Add options to effect
	if ( options ) {
		$.extend( effect, options );
	}

	speed = speed || options.duration;
	effect.duration = $.fx.off ? 0 :
		typeof speed === "number" ? speed :
		speed in $.fx.speeds ? $.fx.speeds[ speed ] :
		$.fx.speeds._default;

	effect.complete = callback || options.complete;

	return effect;
}

function standardAnimationOption( option ) {

	// Valid standard speeds (nothing, number, named speed)
	if ( !option || typeof option === "number" || $.fx.speeds[ option ] ) {
		return true;
	}

	// Invalid strings - treat as "normal" speed
	if ( typeof option === "string" && !$.effects.effect[ option ] ) {
		return true;
	}

	// Complete callback
	if ( $.isFunction( option ) ) {
		return true;
	}

	// Options hash (but not naming an effect)
	if ( typeof option === "object" && !option.effect ) {
		return true;
	}

	// Didn't match any standard API
	return false;
}

$.fn.extend( {
	effect: function( /* effect, options, speed, callback */ ) {
		var args = _normalizeArguments.apply( this, arguments ),
			effectMethod = $.effects.effect[ args.effect ],
			defaultMode = effectMethod.mode,
			queue = args.queue,
			queueName = queue || "fx",
			complete = args.complete,
			mode = args.mode,
			modes = [],
			prefilter = function( next ) {
				var el = $( this ),
					normalizedMode = $.effects.mode( el, mode ) || defaultMode;

				// Sentinel for duck-punching the :animated psuedo-selector
				el.data( dataSpaceAnimated, true );

				// Save effect mode for later use,
				// we can't just call $.effects.mode again later,
				// as the .show() below destroys the initial state
				modes.push( normalizedMode );

				// See $.uiBackCompat inside of run() for removal of defaultMode in 1.13
				if ( defaultMode && ( normalizedMode === "show" ||
						( normalizedMode === defaultMode && normalizedMode === "hide" ) ) ) {
					el.show();
				}

				if ( !defaultMode || normalizedMode !== "none" ) {
					$.effects.saveStyle( el );
				}

				if ( $.isFunction( next ) ) {
					next();
				}
			};

		if ( $.fx.off || !effectMethod ) {

			// Delegate to the original method (e.g., .show()) if possible
			if ( mode ) {
				return this[ mode ]( args.duration, complete );
			} else {
				return this.each( function() {
					if ( complete ) {
						complete.call( this );
					}
				} );
			}
		}

		function run( next ) {
			var elem = $( this );

			function cleanup() {
				elem.removeData( dataSpaceAnimated );

				$.effects.cleanUp( elem );

				if ( args.mode === "hide" ) {
					elem.hide();
				}

				done();
			}

			function done() {
				if ( $.isFunction( complete ) ) {
					complete.call( elem[ 0 ] );
				}

				if ( $.isFunction( next ) ) {
					next();
				}
			}

			// Override mode option on a per element basis,
			// as toggle can be either show or hide depending on element state
			args.mode = modes.shift();

			if ( $.uiBackCompat !== false && !defaultMode ) {
				if ( elem.is( ":hidden" ) ? mode === "hide" : mode === "show" ) {

					// Call the core method to track "olddisplay" properly
					elem[ mode ]();
					done();
				} else {
					effectMethod.call( elem[ 0 ], args, done );
				}
			} else {
				if ( args.mode === "none" ) {

					// Call the core method to track "olddisplay" properly
					elem[ mode ]();
					done();
				} else {
					effectMethod.call( elem[ 0 ], args, cleanup );
				}
			}
		}

		// Run prefilter on all elements first to ensure that
		// any showing or hiding happens before placeholder creation,
		// which ensures that any layout changes are correctly captured.
		return queue === false ?
			this.each( prefilter ).each( run ) :
			this.queue( queueName, prefilter ).queue( queueName, run );
	},

	show: ( function( orig ) {
		return function( option ) {
			if ( standardAnimationOption( option ) ) {
				return orig.apply( this, arguments );
			} else {
				var args = _normalizeArguments.apply( this, arguments );
				args.mode = "show";
				return this.effect.call( this, args );
			}
		};
	} )( $.fn.show ),

	hide: ( function( orig ) {
		return function( option ) {
			if ( standardAnimationOption( option ) ) {
				return orig.apply( this, arguments );
			} else {
				var args = _normalizeArguments.apply( this, arguments );
				args.mode = "hide";
				return this.effect.call( this, args );
			}
		};
	} )( $.fn.hide ),

	toggle: ( function( orig ) {
		return function( option ) {
			if ( standardAnimationOption( option ) || typeof option === "boolean" ) {
				return orig.apply( this, arguments );
			} else {
				var args = _normalizeArguments.apply( this, arguments );
				args.mode = "toggle";
				return this.effect.call( this, args );
			}
		};
	} )( $.fn.toggle ),

	cssUnit: function( key ) {
		var style = this.css( key ),
			val = [];

		$.each( [ "em", "px", "%", "pt" ], function( i, unit ) {
			if ( style.indexOf( unit ) > 0 ) {
				val = [ parseFloat( style ), unit ];
			}
		} );
		return val;
	},

	cssClip: function( clipObj ) {
		if ( clipObj ) {
			return this.css( "clip", "rect(" + clipObj.top + "px " + clipObj.right + "px " +
				clipObj.bottom + "px " + clipObj.left + "px)" );
		}
		return parseClip( this.css( "clip" ), this );
	},

	transfer: function( options, done ) {
		var element = $( this ),
			target = $( options.to ),
			targetFixed = target.css( "position" ) === "fixed",
			body = $( "body" ),
			fixTop = targetFixed ? body.scrollTop() : 0,
			fixLeft = targetFixed ? body.scrollLeft() : 0,
			endPosition = target.offset(),
			animation = {
				top: endPosition.top - fixTop,
				left: endPosition.left - fixLeft,
				height: target.innerHeight(),
				width: target.innerWidth()
			},
			startPosition = element.offset(),
			transfer = $( "<div class='ui-effects-transfer'></div>" )
				.appendTo( "body" )
				.addClass( options.className )
				.css( {
					top: startPosition.top - fixTop,
					left: startPosition.left - fixLeft,
					height: element.innerHeight(),
					width: element.innerWidth(),
					position: targetFixed ? "fixed" : "absolute"
				} )
				.animate( animation, options.duration, options.easing, function() {
					transfer.remove();
					if ( $.isFunction( done ) ) {
						done();
					}
				} );
	}
} );

function parseClip( str, element ) {
		var outerWidth = element.outerWidth(),
			outerHeight = element.outerHeight(),
			clipRegex = /^rect\((-?\d*\.?\d*px|-?\d+%|auto),?\s*(-?\d*\.?\d*px|-?\d+%|auto),?\s*(-?\d*\.?\d*px|-?\d+%|auto),?\s*(-?\d*\.?\d*px|-?\d+%|auto)\)$/,
			values = clipRegex.exec( str ) || [ "", 0, outerWidth, outerHeight, 0 ];

		return {
			top: parseFloat( values[ 1 ] ) || 0,
			right: values[ 2 ] === "auto" ? outerWidth : parseFloat( values[ 2 ] ),
			bottom: values[ 3 ] === "auto" ? outerHeight : parseFloat( values[ 3 ] ),
			left: parseFloat( values[ 4 ] ) || 0
		};
}

$.fx.step.clip = function( fx ) {
	if ( !fx.clipInit ) {
		fx.start = $( fx.elem ).cssClip();
		if ( typeof fx.end === "string" ) {
			fx.end = parseClip( fx.end, fx.elem );
		}
		fx.clipInit = true;
	}

	$( fx.elem ).cssClip( {
		top: fx.pos * ( fx.end.top - fx.start.top ) + fx.start.top,
		right: fx.pos * ( fx.end.right - fx.start.right ) + fx.start.right,
		bottom: fx.pos * ( fx.end.bottom - fx.start.bottom ) + fx.start.bottom,
		left: fx.pos * ( fx.end.left - fx.start.left ) + fx.start.left
	} );
};

} )();

/******************************************************************************/
/*********************************** EASING ***********************************/
/******************************************************************************/

( function() {

// Based on easing equations from Robert Penner (http://www.robertpenner.com/easing)

var baseEasings = {};

$.each( [ "Quad", "Cubic", "Quart", "Quint", "Expo" ], function( i, name ) {
	baseEasings[ name ] = function( p ) {
		return Math.pow( p, i + 2 );
	};
} );

$.extend( baseEasings, {
	Sine: function( p ) {
		return 1 - Math.cos( p * Math.PI / 2 );
	},
	Circ: function( p ) {
		return 1 - Math.sqrt( 1 - p * p );
	},
	Elastic: function( p ) {
		return p === 0 || p === 1 ? p :
			-Math.pow( 2, 8 * ( p - 1 ) ) * Math.sin( ( ( p - 1 ) * 80 - 7.5 ) * Math.PI / 15 );
	},
	Back: function( p ) {
		return p * p * ( 3 * p - 2 );
	},
	Bounce: function( p ) {
		var pow2,
			bounce = 4;

		while ( p < ( ( pow2 = Math.pow( 2, --bounce ) ) - 1 ) / 11 ) {}
		return 1 / Math.pow( 4, 3 - bounce ) - 7.5625 * Math.pow( ( pow2 * 3 - 2 ) / 22 - p, 2 );
	}
} );

$.each( baseEasings, function( name, easeIn ) {
	$.easing[ "easeIn" + name ] = easeIn;
	$.easing[ "easeOut" + name ] = function( p ) {
		return 1 - easeIn( 1 - p );
	};
	$.easing[ "easeInOut" + name ] = function( p ) {
		return p < 0.5 ?
			easeIn( p * 2 ) / 2 :
			1 - easeIn( p * -2 + 2 ) / 2;
	};
} );

} )();

var effect = $.effects;


/*!
 * jQuery UI Effects Blind 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: Blind Effect
//>>group: Effects
//>>description: Blinds the element.
//>>docs: http://api.jqueryui.com/blind-effect/
//>>demos: http://jqueryui.com/effect/



var effectsEffectBlind = $.effects.define( "blind", "hide", function( options, done ) {
	var map = {
			up: [ "bottom", "top" ],
			vertical: [ "bottom", "top" ],
			down: [ "top", "bottom" ],
			left: [ "right", "left" ],
			horizontal: [ "right", "left" ],
			right: [ "left", "right" ]
		},
		element = $( this ),
		direction = options.direction || "up",
		start = element.cssClip(),
		animate = { clip: $.extend( {}, start ) },
		placeholder = $.effects.createPlaceholder( element );

	animate.clip[ map[ direction ][ 0 ] ] = animate.clip[ map[ direction ][ 1 ] ];

	if ( options.mode === "show" ) {
		element.cssClip( animate.clip );
		if ( placeholder ) {
			placeholder.css( $.effects.clipToBox( animate ) );
		}

		animate.clip = start;
	}

	if ( placeholder ) {
		placeholder.animate( $.effects.clipToBox( animate ), options.duration, options.easing );
	}

	element.animate( animate, {
		queue: false,
		duration: options.duration,
		easing: options.easing,
		complete: done
	} );
} );


/*!
 * jQuery UI Effects Bounce 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: Bounce Effect
//>>group: Effects
//>>description: Bounces an element horizontally or vertically n times.
//>>docs: http://api.jqueryui.com/bounce-effect/
//>>demos: http://jqueryui.com/effect/



var effectsEffectBounce = $.effects.define( "bounce", function( options, done ) {
	var upAnim, downAnim, refValue,
		element = $( this ),

		// Defaults:
		mode = options.mode,
		hide = mode === "hide",
		show = mode === "show",
		direction = options.direction || "up",
		distance = options.distance,
		times = options.times || 5,

		// Number of internal animations
		anims = times * 2 + ( show || hide ? 1 : 0 ),
		speed = options.duration / anims,
		easing = options.easing,

		// Utility:
		ref = ( direction === "up" || direction === "down" ) ? "top" : "left",
		motion = ( direction === "up" || direction === "left" ),
		i = 0,

		queuelen = element.queue().length;

	$.effects.createPlaceholder( element );

	refValue = element.css( ref );

	// Default distance for the BIGGEST bounce is the outer Distance / 3
	if ( !distance ) {
		distance = element[ ref === "top" ? "outerHeight" : "outerWidth" ]() / 3;
	}

	if ( show ) {
		downAnim = { opacity: 1 };
		downAnim[ ref ] = refValue;

		// If we are showing, force opacity 0 and set the initial position
		// then do the "first" animation
		element
			.css( "opacity", 0 )
			.css( ref, motion ? -distance * 2 : distance * 2 )
			.animate( downAnim, speed, easing );
	}

	// Start at the smallest distance if we are hiding
	if ( hide ) {
		distance = distance / Math.pow( 2, times - 1 );
	}

	downAnim = {};
	downAnim[ ref ] = refValue;

	// Bounces up/down/left/right then back to 0 -- times * 2 animations happen here
	for ( ; i < times; i++ ) {
		upAnim = {};
		upAnim[ ref ] = ( motion ? "-=" : "+=" ) + distance;

		element
			.animate( upAnim, speed, easing )
			.animate( downAnim, speed, easing );

		distance = hide ? distance * 2 : distance / 2;
	}

	// Last Bounce when Hiding
	if ( hide ) {
		upAnim = { opacity: 0 };
		upAnim[ ref ] = ( motion ? "-=" : "+=" ) + distance;

		element.animate( upAnim, speed, easing );
	}

	element.queue( done );

	$.effects.unshift( element, queuelen, anims + 1 );
} );


/*!
 * jQuery UI Effects Clip 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: Clip Effect
//>>group: Effects
//>>description: Clips the element on and off like an old TV.
//>>docs: http://api.jqueryui.com/clip-effect/
//>>demos: http://jqueryui.com/effect/



var effectsEffectClip = $.effects.define( "clip", "hide", function( options, done ) {
	var start,
		animate = {},
		element = $( this ),
		direction = options.direction || "vertical",
		both = direction === "both",
		horizontal = both || direction === "horizontal",
		vertical = both || direction === "vertical";

	start = element.cssClip();
	animate.clip = {
		top: vertical ? ( start.bottom - start.top ) / 2 : start.top,
		right: horizontal ? ( start.right - start.left ) / 2 : start.right,
		bottom: vertical ? ( start.bottom - start.top ) / 2 : start.bottom,
		left: horizontal ? ( start.right - start.left ) / 2 : start.left
	};

	$.effects.createPlaceholder( element );

	if ( options.mode === "show" ) {
		element.cssClip( animate.clip );
		animate.clip = start;
	}

	element.animate( animate, {
		queue: false,
		duration: options.duration,
		easing: options.easing,
		complete: done
	} );

} );


/*!
 * jQuery UI Effects Drop 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: Drop Effect
//>>group: Effects
//>>description: Moves an element in one direction and hides it at the same time.
//>>docs: http://api.jqueryui.com/drop-effect/
//>>demos: http://jqueryui.com/effect/



var effectsEffectDrop = $.effects.define( "drop", "hide", function( options, done ) {

	var distance,
		element = $( this ),
		mode = options.mode,
		show = mode === "show",
		direction = options.direction || "left",
		ref = ( direction === "up" || direction === "down" ) ? "top" : "left",
		motion = ( direction === "up" || direction === "left" ) ? "-=" : "+=",
		oppositeMotion = ( motion === "+=" ) ? "-=" : "+=",
		animation = {
			opacity: 0
		};

	$.effects.createPlaceholder( element );

	distance = options.distance ||
		element[ ref === "top" ? "outerHeight" : "outerWidth" ]( true ) / 2;

	animation[ ref ] = motion + distance;

	if ( show ) {
		element.css( animation );

		animation[ ref ] = oppositeMotion + distance;
		animation.opacity = 1;
	}

	// Animate
	element.animate( animation, {
		queue: false,
		duration: options.duration,
		easing: options.easing,
		complete: done
	} );
} );


/*!
 * jQuery UI Effects Explode 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: Explode Effect
//>>group: Effects
// jscs:disable maximumLineLength
//>>description: Explodes an element in all directions into n pieces. Implodes an element to its original wholeness.
// jscs:enable maximumLineLength
//>>docs: http://api.jqueryui.com/explode-effect/
//>>demos: http://jqueryui.com/effect/



var effectsEffectExplode = $.effects.define( "explode", "hide", function( options, done ) {

	var i, j, left, top, mx, my,
		rows = options.pieces ? Math.round( Math.sqrt( options.pieces ) ) : 3,
		cells = rows,
		element = $( this ),
		mode = options.mode,
		show = mode === "show",

		// Show and then visibility:hidden the element before calculating offset
		offset = element.show().css( "visibility", "hidden" ).offset(),

		// Width and height of a piece
		width = Math.ceil( element.outerWidth() / cells ),
		height = Math.ceil( element.outerHeight() / rows ),
		pieces = [];

	// Children animate complete:
	function childComplete() {
		pieces.push( this );
		if ( pieces.length === rows * cells ) {
			animComplete();
		}
	}

	// Clone the element for each row and cell.
	for ( i = 0; i < rows; i++ ) { // ===>
		top = offset.top + i * height;
		my = i - ( rows - 1 ) / 2;

		for ( j = 0; j < cells; j++ ) { // |||
			left = offset.left + j * width;
			mx = j - ( cells - 1 ) / 2;

			// Create a clone of the now hidden main element that will be absolute positioned
			// within a wrapper div off the -left and -top equal to size of our pieces
			element
				.clone()
				.appendTo( "body" )
				.wrap( "<div></div>" )
				.css( {
					position: "absolute",
					visibility: "visible",
					left: -j * width,
					top: -i * height
				} )

				// Select the wrapper - make it overflow: hidden and absolute positioned based on
				// where the original was located +left and +top equal to the size of pieces
				.parent()
					.addClass( "ui-effects-explode" )
					.css( {
						position: "absolute",
						overflow: "hidden",
						width: width,
						height: height,
						left: left + ( show ? mx * width : 0 ),
						top: top + ( show ? my * height : 0 ),
						opacity: show ? 0 : 1
					} )
					.animate( {
						left: left + ( show ? 0 : mx * width ),
						top: top + ( show ? 0 : my * height ),
						opacity: show ? 1 : 0
					}, options.duration || 500, options.easing, childComplete );
		}
	}

	function animComplete() {
		element.css( {
			visibility: "visible"
		} );
		$( pieces ).remove();
		done();
	}
} );


/*!
 * jQuery UI Effects Fade 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: Fade Effect
//>>group: Effects
//>>description: Fades the element.
//>>docs: http://api.jqueryui.com/fade-effect/
//>>demos: http://jqueryui.com/effect/



var effectsEffectFade = $.effects.define( "fade", "toggle", function( options, done ) {
	var show = options.mode === "show";

	$( this )
		.css( "opacity", show ? 0 : 1 )
		.animate( {
			opacity: show ? 1 : 0
		}, {
			queue: false,
			duration: options.duration,
			easing: options.easing,
			complete: done
		} );
} );


/*!
 * jQuery UI Effects Fold 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: Fold Effect
//>>group: Effects
//>>description: Folds an element first horizontally and then vertically.
//>>docs: http://api.jqueryui.com/fold-effect/
//>>demos: http://jqueryui.com/effect/



var effectsEffectFold = $.effects.define( "fold", "hide", function( options, done ) {

	// Create element
	var element = $( this ),
		mode = options.mode,
		show = mode === "show",
		hide = mode === "hide",
		size = options.size || 15,
		percent = /([0-9]+)%/.exec( size ),
		horizFirst = !!options.horizFirst,
		ref = horizFirst ? [ "right", "bottom" ] : [ "bottom", "right" ],
		duration = options.duration / 2,

		placeholder = $.effects.createPlaceholder( element ),

		start = element.cssClip(),
		animation1 = { clip: $.extend( {}, start ) },
		animation2 = { clip: $.extend( {}, start ) },

		distance = [ start[ ref[ 0 ] ], start[ ref[ 1 ] ] ],

		queuelen = element.queue().length;

	if ( percent ) {
		size = parseInt( percent[ 1 ], 10 ) / 100 * distance[ hide ? 0 : 1 ];
	}
	animation1.clip[ ref[ 0 ] ] = size;
	animation2.clip[ ref[ 0 ] ] = size;
	animation2.clip[ ref[ 1 ] ] = 0;

	if ( show ) {
		element.cssClip( animation2.clip );
		if ( placeholder ) {
			placeholder.css( $.effects.clipToBox( animation2 ) );
		}

		animation2.clip = start;
	}

	// Animate
	element
		.queue( function( next ) {
			if ( placeholder ) {
				placeholder
					.animate( $.effects.clipToBox( animation1 ), duration, options.easing )
					.animate( $.effects.clipToBox( animation2 ), duration, options.easing );
			}

			next();
		} )
		.animate( animation1, duration, options.easing )
		.animate( animation2, duration, options.easing )
		.queue( done );

	$.effects.unshift( element, queuelen, 4 );
} );


/*!
 * jQuery UI Effects Highlight 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: Highlight Effect
//>>group: Effects
//>>description: Highlights the background of an element in a defined color for a custom duration.
//>>docs: http://api.jqueryui.com/highlight-effect/
//>>demos: http://jqueryui.com/effect/



var effectsEffectHighlight = $.effects.define( "highlight", "show", function( options, done ) {
	var element = $( this ),
		animation = {
			backgroundColor: element.css( "backgroundColor" )
		};

	if ( options.mode === "hide" ) {
		animation.opacity = 0;
	}

	$.effects.saveStyle( element );

	element
		.css( {
			backgroundImage: "none",
			backgroundColor: options.color || "#ffff99"
		} )
		.animate( animation, {
			queue: false,
			duration: options.duration,
			easing: options.easing,
			complete: done
		} );
} );


/*!
 * jQuery UI Effects Size 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: Size Effect
//>>group: Effects
//>>description: Resize an element to a specified width and height.
//>>docs: http://api.jqueryui.com/size-effect/
//>>demos: http://jqueryui.com/effect/



var effectsEffectSize = $.effects.define( "size", function( options, done ) {

	// Create element
	var baseline, factor, temp,
		element = $( this ),

		// Copy for children
		cProps = [ "fontSize" ],
		vProps = [ "borderTopWidth", "borderBottomWidth", "paddingTop", "paddingBottom" ],
		hProps = [ "borderLeftWidth", "borderRightWidth", "paddingLeft", "paddingRight" ],

		// Set options
		mode = options.mode,
		restore = mode !== "effect",
		scale = options.scale || "both",
		origin = options.origin || [ "middle", "center" ],
		position = element.css( "position" ),
		pos = element.position(),
		original = $.effects.scaledDimensions( element ),
		from = options.from || original,
		to = options.to || $.effects.scaledDimensions( element, 0 );

	$.effects.createPlaceholder( element );

	if ( mode === "show" ) {
		temp = from;
		from = to;
		to = temp;
	}

	// Set scaling factor
	factor = {
		from: {
			y: from.height / original.height,
			x: from.width / original.width
		},
		to: {
			y: to.height / original.height,
			x: to.width / original.width
		}
	};

	// Scale the css box
	if ( scale === "box" || scale === "both" ) {

		// Vertical props scaling
		if ( factor.from.y !== factor.to.y ) {
			from = $.effects.setTransition( element, vProps, factor.from.y, from );
			to = $.effects.setTransition( element, vProps, factor.to.y, to );
		}

		// Horizontal props scaling
		if ( factor.from.x !== factor.to.x ) {
			from = $.effects.setTransition( element, hProps, factor.from.x, from );
			to = $.effects.setTransition( element, hProps, factor.to.x, to );
		}
	}

	// Scale the content
	if ( scale === "content" || scale === "both" ) {

		// Vertical props scaling
		if ( factor.from.y !== factor.to.y ) {
			from = $.effects.setTransition( element, cProps, factor.from.y, from );
			to = $.effects.setTransition( element, cProps, factor.to.y, to );
		}
	}

	// Adjust the position properties based on the provided origin points
	if ( origin ) {
		baseline = $.effects.getBaseline( origin, original );
		from.top = ( original.outerHeight - from.outerHeight ) * baseline.y + pos.top;
		from.left = ( original.outerWidth - from.outerWidth ) * baseline.x + pos.left;
		to.top = ( original.outerHeight - to.outerHeight ) * baseline.y + pos.top;
		to.left = ( original.outerWidth - to.outerWidth ) * baseline.x + pos.left;
	}
	element.css( from );

	// Animate the children if desired
	if ( scale === "content" || scale === "both" ) {

		vProps = vProps.concat( [ "marginTop", "marginBottom" ] ).concat( cProps );
		hProps = hProps.concat( [ "marginLeft", "marginRight" ] );

		// Only animate children with width attributes specified
		// TODO: is this right? should we include anything with css width specified as well
		element.find( "*[width]" ).each( function() {
			var child = $( this ),
				childOriginal = $.effects.scaledDimensions( child ),
				childFrom = {
					height: childOriginal.height * factor.from.y,
					width: childOriginal.width * factor.from.x,
					outerHeight: childOriginal.outerHeight * factor.from.y,
					outerWidth: childOriginal.outerWidth * factor.from.x
				},
				childTo = {
					height: childOriginal.height * factor.to.y,
					width: childOriginal.width * factor.to.x,
					outerHeight: childOriginal.height * factor.to.y,
					outerWidth: childOriginal.width * factor.to.x
				};

			// Vertical props scaling
			if ( factor.from.y !== factor.to.y ) {
				childFrom = $.effects.setTransition( child, vProps, factor.from.y, childFrom );
				childTo = $.effects.setTransition( child, vProps, factor.to.y, childTo );
			}

			// Horizontal props scaling
			if ( factor.from.x !== factor.to.x ) {
				childFrom = $.effects.setTransition( child, hProps, factor.from.x, childFrom );
				childTo = $.effects.setTransition( child, hProps, factor.to.x, childTo );
			}

			if ( restore ) {
				$.effects.saveStyle( child );
			}

			// Animate children
			child.css( childFrom );
			child.animate( childTo, options.duration, options.easing, function() {

				// Restore children
				if ( restore ) {
					$.effects.restoreStyle( child );
				}
			} );
		} );
	}

	// Animate
	element.animate( to, {
		queue: false,
		duration: options.duration,
		easing: options.easing,
		complete: function() {

			var offset = element.offset();

			if ( to.opacity === 0 ) {
				element.css( "opacity", from.opacity );
			}

			if ( !restore ) {
				element
					.css( "position", position === "static" ? "relative" : position )
					.offset( offset );

				// Need to save style here so that automatic style restoration
				// doesn't restore to the original styles from before the animation.
				$.effects.saveStyle( element );
			}

			done();
		}
	} );

} );


/*!
 * jQuery UI Effects Scale 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: Scale Effect
//>>group: Effects
//>>description: Grows or shrinks an element and its content.
//>>docs: http://api.jqueryui.com/scale-effect/
//>>demos: http://jqueryui.com/effect/



var effectsEffectScale = $.effects.define( "scale", function( options, done ) {

	// Create element
	var el = $( this ),
		mode = options.mode,
		percent = parseInt( options.percent, 10 ) ||
			( parseInt( options.percent, 10 ) === 0 ? 0 : ( mode !== "effect" ? 0 : 100 ) ),

		newOptions = $.extend( true, {
			from: $.effects.scaledDimensions( el ),
			to: $.effects.scaledDimensions( el, percent, options.direction || "both" ),
			origin: options.origin || [ "middle", "center" ]
		}, options );

	// Fade option to support puff
	if ( options.fade ) {
		newOptions.from.opacity = 1;
		newOptions.to.opacity = 0;
	}

	$.effects.effect.size.call( this, newOptions, done );
} );


/*!
 * jQuery UI Effects Puff 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: Puff Effect
//>>group: Effects
//>>description: Creates a puff effect by scaling the element up and hiding it at the same time.
//>>docs: http://api.jqueryui.com/puff-effect/
//>>demos: http://jqueryui.com/effect/



var effectsEffectPuff = $.effects.define( "puff", "hide", function( options, done ) {
	var newOptions = $.extend( true, {}, options, {
		fade: true,
		percent: parseInt( options.percent, 10 ) || 150
	} );

	$.effects.effect.scale.call( this, newOptions, done );
} );


/*!
 * jQuery UI Effects Pulsate 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: Pulsate Effect
//>>group: Effects
//>>description: Pulsates an element n times by changing the opacity to zero and back.
//>>docs: http://api.jqueryui.com/pulsate-effect/
//>>demos: http://jqueryui.com/effect/



var effectsEffectPulsate = $.effects.define( "pulsate", "show", function( options, done ) {
	var element = $( this ),
		mode = options.mode,
		show = mode === "show",
		hide = mode === "hide",
		showhide = show || hide,

		// Showing or hiding leaves off the "last" animation
		anims = ( ( options.times || 5 ) * 2 ) + ( showhide ? 1 : 0 ),
		duration = options.duration / anims,
		animateTo = 0,
		i = 1,
		queuelen = element.queue().length;

	if ( show || !element.is( ":visible" ) ) {
		element.css( "opacity", 0 ).show();
		animateTo = 1;
	}

	// Anims - 1 opacity "toggles"
	for ( ; i < anims; i++ ) {
		element.animate( { opacity: animateTo }, duration, options.easing );
		animateTo = 1 - animateTo;
	}

	element.animate( { opacity: animateTo }, duration, options.easing );

	element.queue( done );

	$.effects.unshift( element, queuelen, anims + 1 );
} );


/*!
 * jQuery UI Effects Shake 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: Shake Effect
//>>group: Effects
//>>description: Shakes an element horizontally or vertically n times.
//>>docs: http://api.jqueryui.com/shake-effect/
//>>demos: http://jqueryui.com/effect/



var effectsEffectShake = $.effects.define( "shake", function( options, done ) {

	var i = 1,
		element = $( this ),
		direction = options.direction || "left",
		distance = options.distance || 20,
		times = options.times || 3,
		anims = times * 2 + 1,
		speed = Math.round( options.duration / anims ),
		ref = ( direction === "up" || direction === "down" ) ? "top" : "left",
		positiveMotion = ( direction === "up" || direction === "left" ),
		animation = {},
		animation1 = {},
		animation2 = {},

		queuelen = element.queue().length;

	$.effects.createPlaceholder( element );

	// Animation
	animation[ ref ] = ( positiveMotion ? "-=" : "+=" ) + distance;
	animation1[ ref ] = ( positiveMotion ? "+=" : "-=" ) + distance * 2;
	animation2[ ref ] = ( positiveMotion ? "-=" : "+=" ) + distance * 2;

	// Animate
	element.animate( animation, speed, options.easing );

	// Shakes
	for ( ; i < times; i++ ) {
		element
			.animate( animation1, speed, options.easing )
			.animate( animation2, speed, options.easing );
	}

	element
		.animate( animation1, speed, options.easing )
		.animate( animation, speed / 2, options.easing )
		.queue( done );

	$.effects.unshift( element, queuelen, anims + 1 );
} );


/*!
 * jQuery UI Effects Slide 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: Slide Effect
//>>group: Effects
//>>description: Slides an element in and out of the viewport.
//>>docs: http://api.jqueryui.com/slide-effect/
//>>demos: http://jqueryui.com/effect/



var effectsEffectSlide = $.effects.define( "slide", "show", function( options, done ) {
	var startClip, startRef,
		element = $( this ),
		map = {
			up: [ "bottom", "top" ],
			down: [ "top", "bottom" ],
			left: [ "right", "left" ],
			right: [ "left", "right" ]
		},
		mode = options.mode,
		direction = options.direction || "left",
		ref = ( direction === "up" || direction === "down" ) ? "top" : "left",
		positiveMotion = ( direction === "up" || direction === "left" ),
		distance = options.distance ||
			element[ ref === "top" ? "outerHeight" : "outerWidth" ]( true ),
		animation = {};

	$.effects.createPlaceholder( element );

	startClip = element.cssClip();
	startRef = element.position()[ ref ];

	// Define hide animation
	animation[ ref ] = ( positiveMotion ? -1 : 1 ) * distance + startRef;
	animation.clip = element.cssClip();
	animation.clip[ map[ direction ][ 1 ] ] = animation.clip[ map[ direction ][ 0 ] ];

	// Reverse the animation if we're showing
	if ( mode === "show" ) {
		element.cssClip( animation.clip );
		element.css( ref, animation[ ref ] );
		animation.clip = startClip;
		animation[ ref ] = startRef;
	}

	// Actually animate
	element.animate( animation, {
		queue: false,
		duration: options.duration,
		easing: options.easing,
		complete: done
	} );
} );


/*!
 * jQuery UI Effects Transfer 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: Transfer Effect
//>>group: Effects
//>>description: Displays a transfer effect from one element to another.
//>>docs: http://api.jqueryui.com/transfer-effect/
//>>demos: http://jqueryui.com/effect/



var effect;
if ( $.uiBackCompat !== false ) {
	effect = $.effects.define( "transfer", function( options, done ) {
		$( this ).transfer( options, done );
	} );
}
var effectsEffectTransfer = effect;


/*!
 * jQuery UI Focusable 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: :focusable Selector
//>>group: Core
//>>description: Selects elements which can be focused.
//>>docs: http://api.jqueryui.com/focusable-selector/



// Selectors
$.ui.focusable = function( element, hasTabindex ) {
	var map, mapName, img, focusableIfVisible, fieldset,
		nodeName = element.nodeName.toLowerCase();

	if ( "area" === nodeName ) {
		map = element.parentNode;
		mapName = map.name;
		if ( !element.href || !mapName || map.nodeName.toLowerCase() !== "map" ) {
			return false;
		}
		img = $( "img[usemap='#" + mapName + "']" );
		return img.length > 0 && img.is( ":visible" );
	}

	if ( /^(input|select|textarea|button|object)$/.test( nodeName ) ) {
		focusableIfVisible = !element.disabled;

		if ( focusableIfVisible ) {

			// Form controls within a disabled fieldset are disabled.
			// However, controls within the fieldset's legend do not get disabled.
			// Since controls generally aren't placed inside legends, we skip
			// this portion of the check.
			fieldset = $( element ).closest( "fieldset" )[ 0 ];
			if ( fieldset ) {
				focusableIfVisible = !fieldset.disabled;
			}
		}
	} else if ( "a" === nodeName ) {
		focusableIfVisible = element.href || hasTabindex;
	} else {
		focusableIfVisible = hasTabindex;
	}

	return focusableIfVisible && $( element ).is( ":visible" ) && visible( $( element ) );
};

// Support: IE 8 only
// IE 8 doesn't resolve inherit to visible/hidden for computed values
function visible( element ) {
	var visibility = element.css( "visibility" );
	while ( visibility === "inherit" ) {
		element = element.parent();
		visibility = element.css( "visibility" );
	}
	return visibility !== "hidden";
}

$.extend( $.expr[ ":" ], {
	focusable: function( element ) {
		return $.ui.focusable( element, $.attr( element, "tabindex" ) != null );
	}
} );

var focusable = $.ui.focusable;




// Support: IE8 Only
// IE8 does not support the form attribute and when it is supplied. It overwrites the form prop
// with a string, so we need to find the proper form.
var form = $.fn.form = function() {
	return typeof this[ 0 ].form === "string" ? this.closest( "form" ) : $( this[ 0 ].form );
};


/*!
 * jQuery UI Form Reset Mixin 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: Form Reset Mixin
//>>group: Core
//>>description: Refresh input widgets when their form is reset
//>>docs: http://api.jqueryui.com/form-reset-mixin/



var formResetMixin = $.ui.formResetMixin = {
	_formResetHandler: function() {
		var form = $( this );

		// Wait for the form reset to actually happen before refreshing
		setTimeout( function() {
			var instances = form.data( "ui-form-reset-instances" );
			$.each( instances, function() {
				this.refresh();
			} );
		} );
	},

	_bindFormResetHandler: function() {
		this.form = this.element.form();
		if ( !this.form.length ) {
			return;
		}

		var instances = this.form.data( "ui-form-reset-instances" ) || [];
		if ( !instances.length ) {

			// We don't use _on() here because we use a single event handler per form
			this.form.on( "reset.ui-form-reset", this._formResetHandler );
		}
		instances.push( this );
		this.form.data( "ui-form-reset-instances", instances );
	},

	_unbindFormResetHandler: function() {
		if ( !this.form.length ) {
			return;
		}

		var instances = this.form.data( "ui-form-reset-instances" );
		instances.splice( $.inArray( this, instances ), 1 );
		if ( instances.length ) {
			this.form.data( "ui-form-reset-instances", instances );
		} else {
			this.form
				.removeData( "ui-form-reset-instances" )
				.off( "reset.ui-form-reset" );
		}
	}
};


/*!
 * jQuery UI Support for jQuery core 1.7.x 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 *
 */

//>>label: jQuery 1.7 Support
//>>group: Core
//>>description: Support version 1.7.x of jQuery core



// Support: jQuery 1.7 only
// Not a great way to check versions, but since we only support 1.7+ and only
// need to detect <1.8, this is a simple check that should suffice. Checking
// for "1.7." would be a bit safer, but the version string is 1.7, not 1.7.0
// and we'll never reach 1.70.0 (if we do, we certainly won't be supporting
// 1.7 anymore). See #11197 for why we're not using feature detection.
if ( $.fn.jquery.substring( 0, 3 ) === "1.7" ) {

	// Setters for .innerWidth(), .innerHeight(), .outerWidth(), .outerHeight()
	// Unlike jQuery Core 1.8+, these only support numeric values to set the
	// dimensions in pixels
	$.each( [ "Width", "Height" ], function( i, name ) {
		var side = name === "Width" ? [ "Left", "Right" ] : [ "Top", "Bottom" ],
			type = name.toLowerCase(),
			orig = {
				innerWidth: $.fn.innerWidth,
				innerHeight: $.fn.innerHeight,
				outerWidth: $.fn.outerWidth,
				outerHeight: $.fn.outerHeight
			};

		function reduce( elem, size, border, margin ) {
			$.each( side, function() {
				size -= parseFloat( $.css( elem, "padding" + this ) ) || 0;
				if ( border ) {
					size -= parseFloat( $.css( elem, "border" + this + "Width" ) ) || 0;
				}
				if ( margin ) {
					size -= parseFloat( $.css( elem, "margin" + this ) ) || 0;
				}
			} );
			return size;
		}

		$.fn[ "inner" + name ] = function( size ) {
			if ( size === undefined ) {
				return orig[ "inner" + name ].call( this );
			}

			return this.each( function() {
				$( this ).css( type, reduce( this, size ) + "px" );
			} );
		};

		$.fn[ "outer" + name ] = function( size, margin ) {
			if ( typeof size !== "number" ) {
				return orig[ "outer" + name ].call( this, size );
			}

			return this.each( function() {
				$( this ).css( type, reduce( this, size, true, margin ) + "px" );
			} );
		};
	} );

	$.fn.addBack = function( selector ) {
		return this.add( selector == null ?
			this.prevObject : this.prevObject.filter( selector )
		);
	};
}

;
/*!
 * jQuery UI Keycode 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: Keycode
//>>group: Core
//>>description: Provide keycodes as keynames
//>>docs: http://api.jqueryui.com/jQuery.ui.keyCode/


var keycode = $.ui.keyCode = {
	BACKSPACE: 8,
	COMMA: 188,
	DELETE: 46,
	DOWN: 40,
	END: 35,
	ENTER: 13,
	ESCAPE: 27,
	HOME: 36,
	LEFT: 37,
	PAGE_DOWN: 34,
	PAGE_UP: 33,
	PERIOD: 190,
	RIGHT: 39,
	SPACE: 32,
	TAB: 9,
	UP: 38
};




// Internal use only
var escapeSelector = $.ui.escapeSelector = ( function() {
	var selectorEscape = /([!"#$%&'()*+,./:;<=>?@[\]^`{|}~])/g;
	return function( selector ) {
		return selector.replace( selectorEscape, "\\$1" );
	};
} )();


/*!
 * jQuery UI Labels 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: labels
//>>group: Core
//>>description: Find all the labels associated with a given input
//>>docs: http://api.jqueryui.com/labels/



var labels = $.fn.labels = function() {
	var ancestor, selector, id, labels, ancestors;

	// Check control.labels first
	if ( this[ 0 ].labels && this[ 0 ].labels.length ) {
		return this.pushStack( this[ 0 ].labels );
	}

	// Support: IE <= 11, FF <= 37, Android <= 2.3 only
	// Above browsers do not support control.labels. Everything below is to support them
	// as well as document fragments. control.labels does not work on document fragments
	labels = this.eq( 0 ).parents( "label" );

	// Look for the label based on the id
	id = this.attr( "id" );
	if ( id ) {

		// We don't search against the document in case the element
		// is disconnected from the DOM
		ancestor = this.eq( 0 ).parents().last();

		// Get a full set of top level ancestors
		ancestors = ancestor.add( ancestor.length ? ancestor.siblings() : this.siblings() );

		// Create a selector for the label based on the id
		selector = "label[for='" + $.ui.escapeSelector( id ) + "']";

		labels = labels.add( ancestors.find( selector ).addBack( selector ) );

	}

	// Return whatever we have found for labels
	return this.pushStack( labels );
};


/*!
 * jQuery UI Scroll Parent 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: scrollParent
//>>group: Core
//>>description: Get the closest ancestor element that is scrollable.
//>>docs: http://api.jqueryui.com/scrollParent/



var scrollParent = $.fn.scrollParent = function( includeHidden ) {
	var position = this.css( "position" ),
		excludeStaticParent = position === "absolute",
		overflowRegex = includeHidden ? /(auto|scroll|hidden)/ : /(auto|scroll)/,
		scrollParent = this.parents().filter( function() {
			var parent = $( this );
			if ( excludeStaticParent && parent.css( "position" ) === "static" ) {
				return false;
			}
			return overflowRegex.test( parent.css( "overflow" ) + parent.css( "overflow-y" ) +
				parent.css( "overflow-x" ) );
		} ).eq( 0 );

	return position === "fixed" || !scrollParent.length ?
		$( this[ 0 ].ownerDocument || document ) :
		scrollParent;
};


/*!
 * jQuery UI Tabbable 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: :tabbable Selector
//>>group: Core
//>>description: Selects elements which can be tabbed to.
//>>docs: http://api.jqueryui.com/tabbable-selector/



var tabbable = $.extend( $.expr[ ":" ], {
	tabbable: function( element ) {
		var tabIndex = $.attr( element, "tabindex" ),
			hasTabindex = tabIndex != null;
		return ( !hasTabindex || tabIndex >= 0 ) && $.ui.focusable( element, hasTabindex );
	}
} );


/*!
 * jQuery UI Unique ID 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: uniqueId
//>>group: Core
//>>description: Functions to generate and remove uniqueId's
//>>docs: http://api.jqueryui.com/uniqueId/



var uniqueId = $.fn.extend( {
	uniqueId: ( function() {
		var uuid = 0;

		return function() {
			return this.each( function() {
				if ( !this.id ) {
					this.id = "ui-id-" + ( ++uuid );
				}
			} );
		};
	} )(),

	removeUniqueId: function() {
		return this.each( function() {
			if ( /^ui-id-\d+$/.test( this.id ) ) {
				$( this ).removeAttr( "id" );
			}
		} );
	}
} );


/*!
 * jQuery UI Accordion 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: Accordion
//>>group: Widgets
// jscs:disable maximumLineLength
//>>description: Displays collapsible content panels for presenting information in a limited amount of space.
// jscs:enable maximumLineLength
//>>docs: http://api.jqueryui.com/accordion/
//>>demos: http://jqueryui.com/accordion/
//>>css.structure: ../../themes/base/core.css
//>>css.structure: ../../themes/base/accordion.css
//>>css.theme: ../../themes/base/theme.css



var widgetsAccordion = $.widget( "ui.accordion", {
	version: "1.12.0",
	options: {
		active: 0,
		animate: {},
		classes: {
			"ui-accordion-header": "ui-corner-top",
			"ui-accordion-header-collapsed": "ui-corner-all",
			"ui-accordion-content": "ui-corner-bottom"
		},
		collapsible: false,
		event: "click",
		header: "> li > :first-child, > :not(li):even",
		heightStyle: "auto",
		icons: {
			activeHeader: "ui-icon-triangle-1-s",
			header: "ui-icon-triangle-1-e"
		},

		// Callbacks
		activate: null,
		beforeActivate: null
	},

	hideProps: {
		borderTopWidth: "hide",
		borderBottomWidth: "hide",
		paddingTop: "hide",
		paddingBottom: "hide",
		height: "hide"
	},

	showProps: {
		borderTopWidth: "show",
		borderBottomWidth: "show",
		paddingTop: "show",
		paddingBottom: "show",
		height: "show"
	},

	_create: function() {
		var options = this.options;

		this.prevShow = this.prevHide = $();
		this._addClass( "ui-accordion", "ui-widget ui-helper-reset" );
		this.element.attr( "role", "tablist" );

		// Don't allow collapsible: false and active: false / null
		if ( !options.collapsible && ( options.active === false || options.active == null ) ) {
			options.active = 0;
		}

		this._processPanels();

		// handle negative values
		if ( options.active < 0 ) {
			options.active += this.headers.length;
		}
		this._refresh();
	},

	_getCreateEventData: function() {
		return {
			header: this.active,
			panel: !this.active.length ? $() : this.active.next()
		};
	},

	_createIcons: function() {
		var icon, children,
			icons = this.options.icons;

		if ( icons ) {
			icon = $( "<span>" );
			this._addClass( icon, "ui-accordion-header-icon", "ui-icon " + icons.header );
			icon.prependTo( this.headers );
			children = this.active.children( ".ui-accordion-header-icon" );
			this._removeClass( children, icons.header )
				._addClass( children, null, icons.activeHeader )
				._addClass( this.headers, "ui-accordion-icons" );
		}
	},

	_destroyIcons: function() {
		this._removeClass( this.headers, "ui-accordion-icons" );
		this.headers.children( ".ui-accordion-header-icon" ).remove();
	},

	_destroy: function() {
		var contents;

		// Clean up main element
		this.element.removeAttr( "role" );

		// Clean up headers
		this.headers
			.removeAttr( "role aria-expanded aria-selected aria-controls tabIndex" )
			.removeUniqueId();

		this._destroyIcons();

		// Clean up content panels
		contents = this.headers.next()
			.css( "display", "" )
			.removeAttr( "role aria-hidden aria-labelledby" )
			.removeUniqueId();

		if ( this.options.heightStyle !== "content" ) {
			contents.css( "height", "" );
		}
	},

	_setOption: function( key, value ) {
		if ( key === "active" ) {

			// _activate() will handle invalid values and update this.options
			this._activate( value );
			return;
		}

		if ( key === "event" ) {
			if ( this.options.event ) {
				this._off( this.headers, this.options.event );
			}
			this._setupEvents( value );
		}

		this._super( key, value );

		// Setting collapsible: false while collapsed; open first panel
		if ( key === "collapsible" && !value && this.options.active === false ) {
			this._activate( 0 );
		}

		if ( key === "icons" ) {
			this._destroyIcons();
			if ( value ) {
				this._createIcons();
			}
		}
	},

	_setOptionDisabled: function( value ) {
		this._super( value );

		this.element.attr( "aria-disabled", value );

		// Support: IE8 Only
		// #5332 / #6059 - opacity doesn't cascade to positioned elements in IE
		// so we need to add the disabled class to the headers and panels
		this._toggleClass( null, "ui-state-disabled", !!value );
		this._toggleClass( this.headers.add( this.headers.next() ), null, "ui-state-disabled",
			!!value );
	},

	_keydown: function( event ) {
		if ( event.altKey || event.ctrlKey ) {
			return;
		}

		var keyCode = $.ui.keyCode,
			length = this.headers.length,
			currentIndex = this.headers.index( event.target ),
			toFocus = false;

		switch ( event.keyCode ) {
		case keyCode.RIGHT:
		case keyCode.DOWN:
			toFocus = this.headers[ ( currentIndex + 1 ) % length ];
			break;
		case keyCode.LEFT:
		case keyCode.UP:
			toFocus = this.headers[ ( currentIndex - 1 + length ) % length ];
			break;
		case keyCode.SPACE:
		case keyCode.ENTER:
			this._eventHandler( event );
			break;
		case keyCode.HOME:
			toFocus = this.headers[ 0 ];
			break;
		case keyCode.END:
			toFocus = this.headers[ length - 1 ];
			break;
		}

		if ( toFocus ) {
			$( event.target ).attr( "tabIndex", -1 );
			$( toFocus ).attr( "tabIndex", 0 );
			$( toFocus ).trigger( "focus" );
			event.preventDefault();
		}
	},

	_panelKeyDown: function( event ) {
		if ( event.keyCode === $.ui.keyCode.UP && event.ctrlKey ) {
			$( event.currentTarget ).prev().trigger( "focus" );
		}
	},

	refresh: function() {
		var options = this.options;
		this._processPanels();

		// Was collapsed or no panel
		if ( ( options.active === false && options.collapsible === true ) ||
				!this.headers.length ) {
			options.active = false;
			this.active = $();

		// active false only when collapsible is true
		} else if ( options.active === false ) {
			this._activate( 0 );

		// was active, but active panel is gone
		} else if ( this.active.length && !$.contains( this.element[ 0 ], this.active[ 0 ] ) ) {

			// all remaining panel are disabled
			if ( this.headers.length === this.headers.find( ".ui-state-disabled" ).length ) {
				options.active = false;
				this.active = $();

			// activate previous panel
			} else {
				this._activate( Math.max( 0, options.active - 1 ) );
			}

		// was active, active panel still exists
		} else {

			// make sure active index is correct
			options.active = this.headers.index( this.active );
		}

		this._destroyIcons();

		this._refresh();
	},

	_processPanels: function() {
		var prevHeaders = this.headers,
			prevPanels = this.panels;

		this.headers = this.element.find( this.options.header );
		this._addClass( this.headers, "ui-accordion-header ui-accordion-header-collapsed",
			"ui-state-default" );

		this.panels = this.headers.next().filter( ":not(.ui-accordion-content-active)" ).hide();
		this._addClass( this.panels, "ui-accordion-content", "ui-helper-reset ui-widget-content" );

		// Avoid memory leaks (#10056)
		if ( prevPanels ) {
			this._off( prevHeaders.not( this.headers ) );
			this._off( prevPanels.not( this.panels ) );
		}
	},

	_refresh: function() {
		var maxHeight,
			options = this.options,
			heightStyle = options.heightStyle,
			parent = this.element.parent();

		this.active = this._findActive( options.active );
		this._addClass( this.active, "ui-accordion-header-active", "ui-state-active" )
			._removeClass( this.active, "ui-accordion-header-collapsed" );
		this._addClass( this.active.next(), "ui-accordion-content-active" );
		this.active.next().show();

		this.headers
			.attr( "role", "tab" )
			.each( function() {
				var header = $( this ),
					headerId = header.uniqueId().attr( "id" ),
					panel = header.next(),
					panelId = panel.uniqueId().attr( "id" );
				header.attr( "aria-controls", panelId );
				panel.attr( "aria-labelledby", headerId );
			} )
			.next()
				.attr( "role", "tabpanel" );

		this.headers
			.not( this.active )
				.attr( {
					"aria-selected": "false",
					"aria-expanded": "false",
					tabIndex: -1
				} )
				.next()
					.attr( {
						"aria-hidden": "true"
					} )
					.hide();

		// Make sure at least one header is in the tab order
		if ( !this.active.length ) {
			this.headers.eq( 0 ).attr( "tabIndex", 0 );
		} else {
			this.active.attr( {
				"aria-selected": "true",
				"aria-expanded": "true",
				tabIndex: 0
			} )
				.next()
					.attr( {
						"aria-hidden": "false"
					} );
		}

		this._createIcons();

		this._setupEvents( options.event );

		if ( heightStyle === "fill" ) {
			maxHeight = parent.height();
			this.element.siblings( ":visible" ).each( function() {
				var elem = $( this ),
					position = elem.css( "position" );

				if ( position === "absolute" || position === "fixed" ) {
					return;
				}
				maxHeight -= elem.outerHeight( true );
			} );

			this.headers.each( function() {
				maxHeight -= $( this ).outerHeight( true );
			} );

			this.headers.next()
				.each( function() {
					$( this ).height( Math.max( 0, maxHeight -
						$( this ).innerHeight() + $( this ).height() ) );
				} )
				.css( "overflow", "auto" );
		} else if ( heightStyle === "auto" ) {
			maxHeight = 0;
			this.headers.next()
				.each( function() {
					var isVisible = $( this ).is( ":visible" );
					if ( !isVisible ) {
						$( this ).show();
					}
					maxHeight = Math.max( maxHeight, $( this ).css( "height", "" ).height() );
					if ( !isVisible ) {
						$( this ).hide();
					}
				} )
				.height( maxHeight );
		}
	},

	_activate: function( index ) {
		var active = this._findActive( index )[ 0 ];

		// Trying to activate the already active panel
		if ( active === this.active[ 0 ] ) {
			return;
		}

		// Trying to collapse, simulate a click on the currently active header
		active = active || this.active[ 0 ];

		this._eventHandler( {
			target: active,
			currentTarget: active,
			preventDefault: $.noop
		} );
	},

	_findActive: function( selector ) {
		return typeof selector === "number" ? this.headers.eq( selector ) : $();
	},

	_setupEvents: function( event ) {
		var events = {
			keydown: "_keydown"
		};
		if ( event ) {
			$.each( event.split( " " ), function( index, eventName ) {
				events[ eventName ] = "_eventHandler";
			} );
		}

		this._off( this.headers.add( this.headers.next() ) );
		this._on( this.headers, events );
		this._on( this.headers.next(), { keydown: "_panelKeyDown" } );
		this._hoverable( this.headers );
		this._focusable( this.headers );
	},

	_eventHandler: function( event ) {
		var activeChildren, clickedChildren,
			options = this.options,
			active = this.active,
			clicked = $( event.currentTarget ),
			clickedIsActive = clicked[ 0 ] === active[ 0 ],
			collapsing = clickedIsActive && options.collapsible,
			toShow = collapsing ? $() : clicked.next(),
			toHide = active.next(),
			eventData = {
				oldHeader: active,
				oldPanel: toHide,
				newHeader: collapsing ? $() : clicked,
				newPanel: toShow
			};

		event.preventDefault();

		if (

				// click on active header, but not collapsible
				( clickedIsActive && !options.collapsible ) ||

				// allow canceling activation
				( this._trigger( "beforeActivate", event, eventData ) === false ) ) {
			return;
		}

		options.active = collapsing ? false : this.headers.index( clicked );

		// When the call to ._toggle() comes after the class changes
		// it causes a very odd bug in IE 8 (see #6720)
		this.active = clickedIsActive ? $() : clicked;
		this._toggle( eventData );

		// Switch classes
		// corner classes on the previously active header stay after the animation
		this._removeClass( active, "ui-accordion-header-active", "ui-state-active" );
		if ( options.icons ) {
			activeChildren = active.children( ".ui-accordion-header-icon" );
			this._removeClass( activeChildren, null, options.icons.activeHeader )
				._addClass( activeChildren, null, options.icons.header );
		}

		if ( !clickedIsActive ) {
			this._removeClass( clicked, "ui-accordion-header-collapsed" )
				._addClass( clicked, "ui-accordion-header-active", "ui-state-active" );
			if ( options.icons ) {
				clickedChildren = clicked.children( ".ui-accordion-header-icon" );
				this._removeClass( clickedChildren, null, options.icons.header )
					._addClass( clickedChildren, null, options.icons.activeHeader );
			}

			this._addClass( clicked.next(), "ui-accordion-content-active" );
		}
	},

	_toggle: function( data ) {
		var toShow = data.newPanel,
			toHide = this.prevShow.length ? this.prevShow : data.oldPanel;

		// Handle activating a panel during the animation for another activation
		this.prevShow.add( this.prevHide ).stop( true, true );
		this.prevShow = toShow;
		this.prevHide = toHide;

		if ( this.options.animate ) {
			this._animate( toShow, toHide, data );
		} else {
			toHide.hide();
			toShow.show();
			this._toggleComplete( data );
		}

		toHide.attr( {
			"aria-hidden": "true"
		} );
		toHide.prev().attr( {
			"aria-selected": "false",
			"aria-expanded": "false"
		} );

		// if we're switching panels, remove the old header from the tab order
		// if we're opening from collapsed state, remove the previous header from the tab order
		// if we're collapsing, then keep the collapsing header in the tab order
		if ( toShow.length && toHide.length ) {
			toHide.prev().attr( {
				"tabIndex": -1,
				"aria-expanded": "false"
			} );
		} else if ( toShow.length ) {
			this.headers.filter( function() {
				return parseInt( $( this ).attr( "tabIndex" ), 10 ) === 0;
			} )
				.attr( "tabIndex", -1 );
		}

		toShow
			.attr( "aria-hidden", "false" )
			.prev()
				.attr( {
					"aria-selected": "true",
					"aria-expanded": "true",
					tabIndex: 0
				} );
	},

	_animate: function( toShow, toHide, data ) {
		var total, easing, duration,
			that = this,
			adjust = 0,
			boxSizing = toShow.css( "box-sizing" ),
			down = toShow.length &&
				( !toHide.length || ( toShow.index() < toHide.index() ) ),
			animate = this.options.animate || {},
			options = down && animate.down || animate,
			complete = function() {
				that._toggleComplete( data );
			};

		if ( typeof options === "number" ) {
			duration = options;
		}
		if ( typeof options === "string" ) {
			easing = options;
		}

		// fall back from options to animation in case of partial down settings
		easing = easing || options.easing || animate.easing;
		duration = duration || options.duration || animate.duration;

		if ( !toHide.length ) {
			return toShow.animate( this.showProps, duration, easing, complete );
		}
		if ( !toShow.length ) {
			return toHide.animate( this.hideProps, duration, easing, complete );
		}

		total = toShow.show().outerHeight();
		toHide.animate( this.hideProps, {
			duration: duration,
			easing: easing,
			step: function( now, fx ) {
				fx.now = Math.round( now );
			}
		} );
		toShow
			.hide()
			.animate( this.showProps, {
				duration: duration,
				easing: easing,
				complete: complete,
				step: function( now, fx ) {
					fx.now = Math.round( now );
					if ( fx.prop !== "height" ) {
						if ( boxSizing === "content-box" ) {
							adjust += fx.now;
						}
					} else if ( that.options.heightStyle !== "content" ) {
						fx.now = Math.round( total - toHide.outerHeight() - adjust );
						adjust = 0;
					}
				}
			} );
	},

	_toggleComplete: function( data ) {
		var toHide = data.oldPanel,
			prev = toHide.prev();

		this._removeClass( toHide, "ui-accordion-content-active" );
		this._removeClass( prev, "ui-accordion-header-active" )
			._addClass( prev, "ui-accordion-header-collapsed" );

		// Work around for rendering bug in IE (#5421)
		if ( toHide.length ) {
			toHide.parent()[ 0 ].className = toHide.parent()[ 0 ].className;
		}
		this._trigger( "activate", null, data );
	}
} );



var safeActiveElement = $.ui.safeActiveElement = function( document ) {
	var activeElement;

	// Support: IE 9 only
	// IE9 throws an "Unspecified error" accessing document.activeElement from an <iframe>
	try {
		activeElement = document.activeElement;
	} catch ( error ) {
		activeElement = document.body;
	}

	// Support: IE 9 - 11 only
	// IE may return null instead of an element
	// Interestingly, this only seems to occur when NOT in an iframe
	if ( !activeElement ) {
		activeElement = document.body;
	}

	// Support: IE 11 only
	// IE11 returns a seemingly empty object in some cases when accessing
	// document.activeElement from an <iframe>
	if ( !activeElement.nodeName ) {
		activeElement = document.body;
	}

	return activeElement;
};


/*!
 * jQuery UI Menu 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: Menu
//>>group: Widgets
//>>description: Creates nestable menus.
//>>docs: http://api.jqueryui.com/menu/
//>>demos: http://jqueryui.com/menu/
//>>css.structure: ../../themes/base/core.css
//>>css.structure: ../../themes/base/menu.css
//>>css.theme: ../../themes/base/theme.css



var widgetsMenu = $.widget( "ui.menu", {
	version: "1.12.0",
	defaultElement: "<ul>",
	delay: 300,
	options: {
		icons: {
			submenu: "ui-icon-caret-1-e"
		},
		items: "> *",
		menus: "ul",
		position: {
			my: "left top",
			at: "right top"
		},
		role: "menu",

		// Callbacks
		blur: null,
		focus: null,
		select: null
	},

	_create: function() {
		this.activeMenu = this.element;

		// Flag used to prevent firing of the click handler
		// as the event bubbles up through nested menus
		this.mouseHandled = false;
		this.element
			.uniqueId()
			.attr( {
				role: this.options.role,
				tabIndex: 0
			} );

		this._addClass( "ui-menu", "ui-widget ui-widget-content" );
		this._on( {

			// Prevent focus from sticking to links inside menu after clicking
			// them (focus should always stay on UL during navigation).
			"mousedown .ui-menu-item": function( event ) {
				event.preventDefault();
			},
			"click .ui-menu-item": function( event ) {
				var target = $( event.target );
				var active = $( $.ui.safeActiveElement( this.document[ 0 ] ) );
				if ( !this.mouseHandled && target.not( ".ui-state-disabled" ).length ) {
					this.select( event );

					// Only set the mouseHandled flag if the event will bubble, see #9469.
					if ( !event.isPropagationStopped() ) {
						this.mouseHandled = true;
					}

					// Open submenu on click
					if ( target.has( ".ui-menu" ).length ) {
						this.expand( event );
					} else if ( !this.element.is( ":focus" ) &&
							active.closest( ".ui-menu" ).length ) {

						// Redirect focus to the menu
						this.element.trigger( "focus", [ true ] );

						// If the active item is on the top level, let it stay active.
						// Otherwise, blur the active item since it is no longer visible.
						if ( this.active && this.active.parents( ".ui-menu" ).length === 1 ) {
							clearTimeout( this.timer );
						}
					}
				}
			},
			"mouseenter .ui-menu-item": function( event ) {

				// Ignore mouse events while typeahead is active, see #10458.
				// Prevents focusing the wrong item when typeahead causes a scroll while the mouse
				// is over an item in the menu
				if ( this.previousFilter ) {
					return;
				}

				var actualTarget = $( event.target ).closest( ".ui-menu-item" ),
					target = $( event.currentTarget );

				// Ignore bubbled events on parent items, see #11641
				if ( actualTarget[ 0 ] !== target[ 0 ] ) {
					return;
				}

				// Remove ui-state-active class from siblings of the newly focused menu item
				// to avoid a jump caused by adjacent elements both having a class with a border
				this._removeClass( target.siblings().children( ".ui-state-active" ),
					null, "ui-state-active" );
				this.focus( event, target );
			},
			mouseleave: "collapseAll",
			"mouseleave .ui-menu": "collapseAll",
			focus: function( event, keepActiveItem ) {

				// If there's already an active item, keep it active
				// If not, activate the first item
				var item = this.active || this.element.find( this.options.items ).eq( 0 );

				if ( !keepActiveItem ) {
					this.focus( event, item );
				}
			},
			blur: function( event ) {
				this._delay( function() {
					var notContained = !$.contains(
						this.element[ 0 ],
						$.ui.safeActiveElement( this.document[ 0 ] )
					);
					if ( notContained ) {
						this.collapseAll( event );
					}
				} );
			},
			keydown: "_keydown"
		} );

		this.refresh();

		// Clicks outside of a menu collapse any open menus
		this._on( this.document, {
			click: function( event ) {
				if ( this._closeOnDocumentClick( event ) ) {
					this.collapseAll( event );
				}

				// Reset the mouseHandled flag
				this.mouseHandled = false;
			}
		} );
	},

	_destroy: function() {
		var items = this.element.find( ".ui-menu-item" )
				.removeAttr( "role aria-disabled" ),
			submenus = items.children( ".ui-menu-item-wrapper" )
				.removeUniqueId()
				.removeAttr( "tabIndex role aria-haspopup" );

		// Destroy (sub)menus
		this.element
			.removeAttr( "aria-activedescendant" )
			.find( ".ui-menu" ).addBack()
				.removeAttr( "role aria-labelledby aria-expanded aria-hidden aria-disabled " +
					"tabIndex" )
				.removeUniqueId()
				.show();

		submenus.children().each( function() {
			var elem = $( this );
			if ( elem.data( "ui-menu-submenu-caret" ) ) {
				elem.remove();
			}
		} );
	},

	_keydown: function( event ) {
		var match, prev, character, skip,
			preventDefault = true;

		switch ( event.keyCode ) {
		case $.ui.keyCode.PAGE_UP:
			this.previousPage( event );
			break;
		case $.ui.keyCode.PAGE_DOWN:
			this.nextPage( event );
			break;
		case $.ui.keyCode.HOME:
			this._move( "first", "first", event );
			break;
		case $.ui.keyCode.END:
			this._move( "last", "last", event );
			break;
		case $.ui.keyCode.UP:
			this.previous( event );
			break;
		case $.ui.keyCode.DOWN:
			this.next( event );
			break;
		case $.ui.keyCode.LEFT:
			this.collapse( event );
			break;
		case $.ui.keyCode.RIGHT:
			if ( this.active && !this.active.is( ".ui-state-disabled" ) ) {
				this.expand( event );
			}
			break;
		case $.ui.keyCode.ENTER:
		case $.ui.keyCode.SPACE:
			this._activate( event );
			break;
		case $.ui.keyCode.ESCAPE:
			this.collapse( event );
			break;
		default:
			preventDefault = false;
			prev = this.previousFilter || "";
			character = String.fromCharCode( event.keyCode );
			skip = false;

			clearTimeout( this.filterTimer );

			if ( character === prev ) {
				skip = true;
			} else {
				character = prev + character;
			}

			match = this._filterMenuItems( character );
			match = skip && match.index( this.active.next() ) !== -1 ?
				this.active.nextAll( ".ui-menu-item" ) :
				match;

			// If no matches on the current filter, reset to the last character pressed
			// to move down the menu to the first item that starts with that character
			if ( !match.length ) {
				character = String.fromCharCode( event.keyCode );
				match = this._filterMenuItems( character );
			}

			if ( match.length ) {
				this.focus( event, match );
				this.previousFilter = character;
				this.filterTimer = this._delay( function() {
					delete this.previousFilter;
				}, 1000 );
			} else {
				delete this.previousFilter;
			}
		}

		if ( preventDefault ) {
			event.preventDefault();
		}
	},

	_activate: function( event ) {
		if ( this.active && !this.active.is( ".ui-state-disabled" ) ) {
			if ( this.active.children( "[aria-haspopup='true']" ).length ) {
				this.expand( event );
			} else {
				this.select( event );
			}
		}
	},

	refresh: function() {
		var menus, items, newSubmenus, newItems, newWrappers,
			that = this,
			icon = this.options.icons.submenu,
			submenus = this.element.find( this.options.menus );

		this._toggleClass( "ui-menu-icons", null, !!this.element.find( ".ui-icon" ).length );

		// Initialize nested menus
		newSubmenus = submenus.filter( ":not(.ui-menu)" )
			.hide()
			.attr( {
				role: this.options.role,
				"aria-hidden": "true",
				"aria-expanded": "false"
			} )
			.each( function() {
				var menu = $( this ),
					item = menu.prev(),
					submenuCaret = $( "<span>" ).data( "ui-menu-submenu-caret", true );

				that._addClass( submenuCaret, "ui-menu-icon", "ui-icon " + icon );
				item
					.attr( "aria-haspopup", "true" )
					.prepend( submenuCaret );
				menu.attr( "aria-labelledby", item.attr( "id" ) );
			} );

		this._addClass( newSubmenus, "ui-menu", "ui-widget ui-widget-content ui-front" );

		menus = submenus.add( this.element );
		items = menus.find( this.options.items );

		// Initialize menu-items containing spaces and/or dashes only as dividers
		items.not( ".ui-menu-item" ).each( function() {
			var item = $( this );
			if ( that._isDivider( item ) ) {
				that._addClass( item, "ui-menu-divider", "ui-widget-content" );
			}
		} );

		// Don't refresh list items that are already adapted
		newItems = items.not( ".ui-menu-item, .ui-menu-divider" );
		newWrappers = newItems.children()
			.not( ".ui-menu" )
				.uniqueId()
				.attr( {
					tabIndex: -1,
					role: this._itemRole()
				} );
		this._addClass( newItems, "ui-menu-item" )
			._addClass( newWrappers, "ui-menu-item-wrapper" );

		// Add aria-disabled attribute to any disabled menu item
		items.filter( ".ui-state-disabled" ).attr( "aria-disabled", "true" );

		// If the active item has been removed, blur the menu
		if ( this.active && !$.contains( this.element[ 0 ], this.active[ 0 ] ) ) {
			this.blur();
		}
	},

	_itemRole: function() {
		return {
			menu: "menuitem",
			listbox: "option"
		}[ this.options.role ];
	},

	_setOption: function( key, value ) {
		if ( key === "icons" ) {
			var icons = this.element.find( ".ui-menu-icon" );
			this._removeClass( icons, null, this.options.icons.submenu )
				._addClass( icons, null, value.submenu );
		}
		this._super( key, value );
	},

	_setOptionDisabled: function( value ) {
		this._super( value );

		this.element.attr( "aria-disabled", String( value ) );
		this._toggleClass( null, "ui-state-disabled", !!value );
	},

	focus: function( event, item ) {
		var nested, focused, activeParent;
		this.blur( event, event && event.type === "focus" );

		this._scrollIntoView( item );

		this.active = item.first();

		focused = this.active.children( ".ui-menu-item-wrapper" );
		this._addClass( focused, null, "ui-state-active" );

		// Only update aria-activedescendant if there's a role
		// otherwise we assume focus is managed elsewhere
		if ( this.options.role ) {
			this.element.attr( "aria-activedescendant", focused.attr( "id" ) );
		}

		// Highlight active parent menu item, if any
		activeParent = this.active
			.parent()
				.closest( ".ui-menu-item" )
					.children( ".ui-menu-item-wrapper" );
		this._addClass( activeParent, null, "ui-state-active" );

		if ( event && event.type === "keydown" ) {
			this._close();
		} else {
			this.timer = this._delay( function() {
				this._close();
			}, this.delay );
		}

		nested = item.children( ".ui-menu" );
		if ( nested.length && event && ( /^mouse/.test( event.type ) ) ) {
			this._startOpening( nested );
		}
		this.activeMenu = item.parent();

		this._trigger( "focus", event, { item: item } );
	},

	_scrollIntoView: function( item ) {
		var borderTop, paddingTop, offset, scroll, elementHeight, itemHeight;
		if ( this._hasScroll() ) {
			borderTop = parseFloat( $.css( this.activeMenu[ 0 ], "borderTopWidth" ) ) || 0;
			paddingTop = parseFloat( $.css( this.activeMenu[ 0 ], "paddingTop" ) ) || 0;
			offset = item.offset().top - this.activeMenu.offset().top - borderTop - paddingTop;
			scroll = this.activeMenu.scrollTop();
			elementHeight = this.activeMenu.height();
			itemHeight = item.outerHeight();

			if ( offset < 0 ) {
				this.activeMenu.scrollTop( scroll + offset );
			} else if ( offset + itemHeight > elementHeight ) {
				this.activeMenu.scrollTop( scroll + offset - elementHeight + itemHeight );
			}
		}
	},

	blur: function( event, fromFocus ) {
		if ( !fromFocus ) {
			clearTimeout( this.timer );
		}

		if ( !this.active ) {
			return;
		}

		this._removeClass( this.active.children( ".ui-menu-item-wrapper" ),
			null, "ui-state-active" );

		this._trigger( "blur", event, { item: this.active } );
		this.active = null;
	},

	_startOpening: function( submenu ) {
		clearTimeout( this.timer );

		// Don't open if already open fixes a Firefox bug that caused a .5 pixel
		// shift in the submenu position when mousing over the caret icon
		if ( submenu.attr( "aria-hidden" ) !== "true" ) {
			return;
		}

		this.timer = this._delay( function() {
			this._close();
			this._open( submenu );
		}, this.delay );
	},

	_open: function( submenu ) {
		var position = $.extend( {
			of: this.active
		}, this.options.position );

		clearTimeout( this.timer );
		this.element.find( ".ui-menu" ).not( submenu.parents( ".ui-menu" ) )
			.hide()
			.attr( "aria-hidden", "true" );

		submenu
			.show()
			.removeAttr( "aria-hidden" )
			.attr( "aria-expanded", "true" )
			.position( position );
	},

	collapseAll: function( event, all ) {
		clearTimeout( this.timer );
		this.timer = this._delay( function() {

			// If we were passed an event, look for the submenu that contains the event
			var currentMenu = all ? this.element :
				$( event && event.target ).closest( this.element.find( ".ui-menu" ) );

			// If we found no valid submenu ancestor, use the main menu to close all
			// sub menus anyway
			if ( !currentMenu.length ) {
				currentMenu = this.element;
			}

			this._close( currentMenu );

			this.blur( event );

			// Work around active item staying active after menu is blurred
			this._removeClass( currentMenu.find( ".ui-state-active" ), null, "ui-state-active" );

			this.activeMenu = currentMenu;
		}, this.delay );
	},

	// With no arguments, closes the currently active menu - if nothing is active
	// it closes all menus.  If passed an argument, it will search for menus BELOW
	_close: function( startMenu ) {
		if ( !startMenu ) {
			startMenu = this.active ? this.active.parent() : this.element;
		}

		startMenu.find( ".ui-menu" )
			.hide()
			.attr( "aria-hidden", "true" )
			.attr( "aria-expanded", "false" );
	},

	_closeOnDocumentClick: function( event ) {
		return !$( event.target ).closest( ".ui-menu" ).length;
	},

	_isDivider: function( item ) {

		// Match hyphen, em dash, en dash
		return !/[^\-\u2014\u2013\s]/.test( item.text() );
	},

	collapse: function( event ) {
		var newItem = this.active &&
			this.active.parent().closest( ".ui-menu-item", this.element );
		if ( newItem && newItem.length ) {
			this._close();
			this.focus( event, newItem );
		}
	},

	expand: function( event ) {
		var newItem = this.active &&
			this.active
				.children( ".ui-menu " )
					.find( this.options.items )
						.first();

		if ( newItem && newItem.length ) {
			this._open( newItem.parent() );

			// Delay so Firefox will not hide activedescendant change in expanding submenu from AT
			this._delay( function() {
				this.focus( event, newItem );
			} );
		}
	},

	next: function( event ) {
		this._move( "next", "first", event );
	},

	previous: function( event ) {
		this._move( "prev", "last", event );
	},

	isFirstItem: function() {
		return this.active && !this.active.prevAll( ".ui-menu-item" ).length;
	},

	isLastItem: function() {
		return this.active && !this.active.nextAll( ".ui-menu-item" ).length;
	},

	_move: function( direction, filter, event ) {
		var next;
		if ( this.active ) {
			if ( direction === "first" || direction === "last" ) {
				next = this.active
					[ direction === "first" ? "prevAll" : "nextAll" ]( ".ui-menu-item" )
					.eq( -1 );
			} else {
				next = this.active
					[ direction + "All" ]( ".ui-menu-item" )
					.eq( 0 );
			}
		}
		if ( !next || !next.length || !this.active ) {
			next = this.activeMenu.find( this.options.items )[ filter ]();
		}

		this.focus( event, next );
	},

	nextPage: function( event ) {
		var item, base, height;

		if ( !this.active ) {
			this.next( event );
			return;
		}
		if ( this.isLastItem() ) {
			return;
		}
		if ( this._hasScroll() ) {
			base = this.active.offset().top;
			height = this.element.height();
			this.active.nextAll( ".ui-menu-item" ).each( function() {
				item = $( this );
				return item.offset().top - base - height < 0;
			} );

			this.focus( event, item );
		} else {
			this.focus( event, this.activeMenu.find( this.options.items )
				[ !this.active ? "first" : "last" ]() );
		}
	},

	previousPage: function( event ) {
		var item, base, height;
		if ( !this.active ) {
			this.next( event );
			return;
		}
		if ( this.isFirstItem() ) {
			return;
		}
		if ( this._hasScroll() ) {
			base = this.active.offset().top;
			height = this.element.height();
			this.active.prevAll( ".ui-menu-item" ).each( function() {
				item = $( this );
				return item.offset().top - base + height > 0;
			} );

			this.focus( event, item );
		} else {
			this.focus( event, this.activeMenu.find( this.options.items ).first() );
		}
	},

	_hasScroll: function() {
		return this.element.outerHeight() < this.element.prop( "scrollHeight" );
	},

	select: function( event ) {

		// TODO: It should never be possible to not have an active item at this
		// point, but the tests don't trigger mouseenter before click.
		this.active = this.active || $( event.target ).closest( ".ui-menu-item" );
		var ui = { item: this.active };
		if ( !this.active.has( ".ui-menu" ).length ) {
			this.collapseAll( event, true );
		}
		this._trigger( "select", event, ui );
	},

	_filterMenuItems: function( character ) {
		var escapedCharacter = character.replace( /[\-\[\]{}()*+?.,\\\^$|#\s]/g, "\\$&" ),
			regex = new RegExp( "^" + escapedCharacter, "i" );

		return this.activeMenu
			.find( this.options.items )

				// Only match on items, not dividers or other content (#10571)
				.filter( ".ui-menu-item" )
					.filter( function() {
						return regex.test(
							$.trim( $( this ).children( ".ui-menu-item-wrapper" ).text() ) );
					} );
	}
} );


/*!
 * jQuery UI Autocomplete 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: Autocomplete
//>>group: Widgets
//>>description: Lists suggested words as the user is typing.
//>>docs: http://api.jqueryui.com/autocomplete/
//>>demos: http://jqueryui.com/autocomplete/
//>>css.structure: ../../themes/base/core.css
//>>css.structure: ../../themes/base/autocomplete.css
//>>css.theme: ../../themes/base/theme.css



$.widget( "ui.autocomplete", {
	version: "1.12.0",
	defaultElement: "<input>",
	options: {
		appendTo: null,
		autoFocus: false,
		delay: 300,
		minLength: 1,
		position: {
			my: "left top",
			at: "left bottom",
			collision: "none"
		},
		source: null,

		// Callbacks
		change: null,
		close: null,
		focus: null,
		open: null,
		response: null,
		search: null,
		select: null
	},

	requestIndex: 0,
	pending: 0,

	_create: function() {

		// Some browsers only repeat keydown events, not keypress events,
		// so we use the suppressKeyPress flag to determine if we've already
		// handled the keydown event. #7269
		// Unfortunately the code for & in keypress is the same as the up arrow,
		// so we use the suppressKeyPressRepeat flag to avoid handling keypress
		// events when we know the keydown event was used to modify the
		// search term. #7799
		var suppressKeyPress, suppressKeyPressRepeat, suppressInput,
			nodeName = this.element[ 0 ].nodeName.toLowerCase(),
			isTextarea = nodeName === "textarea",
			isInput = nodeName === "input";

		// Textareas are always multi-line
		// Inputs are always single-line, even if inside a contentEditable element
		// IE also treats inputs as contentEditable
		// All other element types are determined by whether or not they're contentEditable
		this.isMultiLine = isTextarea || !isInput && this._isContentEditable( this.element );

		this.valueMethod = this.element[ isTextarea || isInput ? "val" : "text" ];
		this.isNewMenu = true;

		this._addClass( "ui-autocomplete-input" );
		this.element.attr( "autocomplete", "off" );

		this._on( this.element, {
			keydown: function( event ) {
				if ( this.element.prop( "readOnly" ) ) {
					suppressKeyPress = true;
					suppressInput = true;
					suppressKeyPressRepeat = true;
					return;
				}

				suppressKeyPress = false;
				suppressInput = false;
				suppressKeyPressRepeat = false;
				var keyCode = $.ui.keyCode;
				switch ( event.keyCode ) {
				case keyCode.PAGE_UP:
					suppressKeyPress = true;
					this._move( "previousPage", event );
					break;
				case keyCode.PAGE_DOWN:
					suppressKeyPress = true;
					this._move( "nextPage", event );
					break;
				case keyCode.UP:
					suppressKeyPress = true;
					this._keyEvent( "previous", event );
					break;
				case keyCode.DOWN:
					suppressKeyPress = true;
					this._keyEvent( "next", event );
					break;
				case keyCode.ENTER:

					// when menu is open and has focus
					if ( this.menu.active ) {

						// #6055 - Opera still allows the keypress to occur
						// which causes forms to submit
						suppressKeyPress = true;
						event.preventDefault();
						this.menu.select( event );

					}
					break;
				case keyCode.TAB:
					if ( this.menu.active ) {
						this.menu.select( event );
					}
					break;
				case keyCode.ESCAPE:
					if ( this.menu.element.is( ":visible" ) ) {
						if ( !this.isMultiLine ) {
							this._value( this.term );
						}
						this.close( event );

						// Different browsers have different default behavior for escape
						// Single press can mean undo or clear
						// Double press in IE means clear the whole form
						event.preventDefault();
					}
					break;
				default:
					suppressKeyPressRepeat = true;

					// search timeout should be triggered before the input value is changed
					this._searchTimeout( event );
					break;
				}
			},
			keypress: function( event ) {
				if ( suppressKeyPress ) {
					suppressKeyPress = false;
					if ( !this.isMultiLine || this.menu.element.is( ":visible" ) ) {
						event.preventDefault();
					}
					return;
				}
				if ( suppressKeyPressRepeat ) {
					return;
				}

				// Replicate some key handlers to allow them to repeat in Firefox and Opera
				var keyCode = $.ui.keyCode;
				switch ( event.keyCode ) {
				case keyCode.PAGE_UP:
					this._move( "previousPage", event );
					break;
				case keyCode.PAGE_DOWN:
					this._move( "nextPage", event );
					break;
				case keyCode.UP:
					this._keyEvent( "previous", event );
					break;
				case keyCode.DOWN:
					this._keyEvent( "next", event );
					break;
				}
			},
			input: function( event ) {
				if ( suppressInput ) {
					suppressInput = false;
					event.preventDefault();
					return;
				}
				this._searchTimeout( event );
			},
			focus: function() {
				this.selectedItem = null;
				this.previous = this._value();
			},
			blur: function( event ) {
				if ( this.cancelBlur ) {
					delete this.cancelBlur;
					return;
				}

				clearTimeout( this.searching );
				this.close( event );
				this._change( event );
			}
		} );

		this._initSource();
		this.menu = $( "<ul>" )
			.appendTo( this._appendTo() )
			.menu( {

				// disable ARIA support, the live region takes care of that
				role: null
			} )
			.hide()
			.menu( "instance" );

		this._addClass( this.menu.element, "ui-autocomplete", "ui-front" );
		this._on( this.menu.element, {
			mousedown: function( event ) {

				// prevent moving focus out of the text field
				event.preventDefault();

				// IE doesn't prevent moving focus even with event.preventDefault()
				// so we set a flag to know when we should ignore the blur event
				this.cancelBlur = true;
				this._delay( function() {
					delete this.cancelBlur;

					// Support: IE 8 only
					// Right clicking a menu item or selecting text from the menu items will
					// result in focus moving out of the input. However, we've already received
					// and ignored the blur event because of the cancelBlur flag set above. So
					// we restore focus to ensure that the menu closes properly based on the user's
					// next actions.
					if ( this.element[ 0 ] !== $.ui.safeActiveElement( this.document[ 0 ] ) ) {
						this.element.trigger( "focus" );
					}
				} );
			},
			menufocus: function( event, ui ) {
				var label, item;

				// support: Firefox
				// Prevent accidental activation of menu items in Firefox (#7024 #9118)
				if ( this.isNewMenu ) {
					this.isNewMenu = false;
					if ( event.originalEvent && /^mouse/.test( event.originalEvent.type ) ) {
						this.menu.blur();

						this.document.one( "mousemove", function() {
							$( event.target ).trigger( event.originalEvent );
						} );

						return;
					}
				}

				item = ui.item.data( "ui-autocomplete-item" );
				if ( false !== this._trigger( "focus", event, { item: item } ) ) {

					// use value to match what will end up in the input, if it was a key event
					if ( event.originalEvent && /^key/.test( event.originalEvent.type ) ) {
						this._value( item.value );
					}
				}

				// Announce the value in the liveRegion
				label = ui.item.attr( "aria-label" ) || item.value;
				if ( label && $.trim( label ).length ) {
					this.liveRegion.children().hide();
					$( "<div>" ).text( label ).appendTo( this.liveRegion );
				}
			},
			menuselect: function( event, ui ) {
				var item = ui.item.data( "ui-autocomplete-item" ),
					previous = this.previous;

				// Only trigger when focus was lost (click on menu)
				if ( this.element[ 0 ] !== $.ui.safeActiveElement( this.document[ 0 ] ) ) {
					this.element.trigger( "focus" );
					this.previous = previous;

					// #6109 - IE triggers two focus events and the second
					// is asynchronous, so we need to reset the previous
					// term synchronously and asynchronously :-(
					this._delay( function() {
						this.previous = previous;
						this.selectedItem = item;
					} );
				}

				if ( false !== this._trigger( "select", event, { item: item } ) ) {
					this._value( item.value );
				}

				// reset the term after the select event
				// this allows custom select handling to work properly
				this.term = this._value();

				this.close( event );
				this.selectedItem = item;
			}
		} );

		this.liveRegion = $( "<div>", {
			role: "status",
			"aria-live": "assertive",
			"aria-relevant": "additions"
		} )
			.appendTo( this.document[ 0 ].body );

		this._addClass( this.liveRegion, null, "ui-helper-hidden-accessible" );

		// Turning off autocomplete prevents the browser from remembering the
		// value when navigating through history, so we re-enable autocomplete
		// if the page is unloaded before the widget is destroyed. #7790
		this._on( this.window, {
			beforeunload: function() {
				this.element.removeAttr( "autocomplete" );
			}
		} );
	},

	_destroy: function() {
		clearTimeout( this.searching );
		this.element.removeAttr( "autocomplete" );
		this.menu.element.remove();
		this.liveRegion.remove();
	},

	_setOption: function( key, value ) {
		this._super( key, value );
		if ( key === "source" ) {
			this._initSource();
		}
		if ( key === "appendTo" ) {
			this.menu.element.appendTo( this._appendTo() );
		}
		if ( key === "disabled" && value && this.xhr ) {
			this.xhr.abort();
		}
	},

	_isEventTargetInWidget: function( event ) {
		var menuElement = this.menu.element[ 0 ];

		return event.target === this.element[ 0 ] ||
			event.target === menuElement ||
			$.contains( menuElement, event.target );
	},

	_closeOnClickOutside: function( event ) {
		if ( !this._isEventTargetInWidget( event ) ) {
			this.close();
		}
	},

	_appendTo: function() {
		var element = this.options.appendTo;

		if ( element ) {
			element = element.jquery || element.nodeType ?
				$( element ) :
				this.document.find( element ).eq( 0 );
		}

		if ( !element || !element[ 0 ] ) {
			element = this.element.closest( ".ui-front, dialog" );
		}

		if ( !element.length ) {
			element = this.document[ 0 ].body;
		}

		return element;
	},

	_initSource: function() {
		var array, url,
			that = this;
		if ( $.isArray( this.options.source ) ) {
			array = this.options.source;
			this.source = function( request, response ) {
				response( $.ui.autocomplete.filter( array, request.term ) );
			};
		} else if ( typeof this.options.source === "string" ) {
			url = this.options.source;
			this.source = function( request, response ) {
				if ( that.xhr ) {
					that.xhr.abort();
				}
				that.xhr = $.ajax( {
					url: url,
					data: request,
					dataType: "json",
					success: function( data ) {
						response( data );
					},
					error: function() {
						response( [] );
					}
				} );
			};
		} else {
			this.source = this.options.source;
		}
	},

	_searchTimeout: function( event ) {
		clearTimeout( this.searching );
		this.searching = this._delay( function() {

			// Search if the value has changed, or if the user retypes the same value (see #7434)
			var equalValues = this.term === this._value(),
				menuVisible = this.menu.element.is( ":visible" ),
				modifierKey = event.altKey || event.ctrlKey || event.metaKey || event.shiftKey;

			if ( !equalValues || ( equalValues && !menuVisible && !modifierKey ) ) {
				this.selectedItem = null;
				this.search( null, event );
			}
		}, this.options.delay );
	},

	search: function( value, event ) {
		value = value != null ? value : this._value();

		// Always save the actual value, not the one passed as an argument
		this.term = this._value();

		if ( value.length < this.options.minLength ) {
			return this.close( event );
		}

		if ( this._trigger( "search", event ) === false ) {
			return;
		}

		return this._search( value );
	},

	_search: function( value ) {
		this.pending++;
		this._addClass( "ui-autocomplete-loading" );
		this.cancelSearch = false;

		this.source( { term: value }, this._response() );
	},

	_response: function() {
		var index = ++this.requestIndex;

		return $.proxy( function( content ) {
			if ( index === this.requestIndex ) {
				this.__response( content );
			}

			this.pending--;
			if ( !this.pending ) {
				this._removeClass( "ui-autocomplete-loading" );
			}
		}, this );
	},

	__response: function( content ) {
		if ( content ) {
			content = this._normalize( content );
		}
		this._trigger( "response", null, { content: content } );
		if ( !this.options.disabled && content && content.length && !this.cancelSearch ) {
			this._suggest( content );
			this._trigger( "open" );
		} else {

			// use ._close() instead of .close() so we don't cancel future searches
			this._close();
		}
	},

	close: function( event ) {
		this.cancelSearch = true;
		this._close( event );
	},

	_close: function( event ) {

		// Remove the handler that closes the menu on outside clicks
		this._off( this.document, "mousedown" );

		if ( this.menu.element.is( ":visible" ) ) {
			this.menu.element.hide();
			this.menu.blur();
			this.isNewMenu = true;
			this._trigger( "close", event );
		}
	},

	_change: function( event ) {
		if ( this.previous !== this._value() ) {
			this._trigger( "change", event, { item: this.selectedItem } );
		}
	},

	_normalize: function( items ) {

		// assume all items have the right format when the first item is complete
		if ( items.length && items[ 0 ].label && items[ 0 ].value ) {
			return items;
		}
		return $.map( items, function( item ) {
			if ( typeof item === "string" ) {
				return {
					label: item,
					value: item
				};
			}
			return $.extend( {}, item, {
				label: item.label || item.value,
				value: item.value || item.label
			} );
		} );
	},

	_suggest: function( items ) {
		var ul = this.menu.element.empty();
		this._renderMenu( ul, items );
		this.isNewMenu = true;
		this.menu.refresh();

		// Size and position menu
		ul.show();
		this._resizeMenu();
		ul.position( $.extend( {
			of: this.element
		}, this.options.position ) );

		if ( this.options.autoFocus ) {
			this.menu.next();
		}

		// Listen for interactions outside of the widget (#6642)
		this._on( this.document, {
			mousedown: "_closeOnClickOutside"
		} );
	},

	_resizeMenu: function() {
		var ul = this.menu.element;
		ul.outerWidth( Math.max(

			// Firefox wraps long text (possibly a rounding bug)
			// so we add 1px to avoid the wrapping (#7513)
			ul.width( "" ).outerWidth() + 1,
			this.element.outerWidth()
		) );
	},

	_renderMenu: function( ul, items ) {
		var that = this;
		$.each( items, function( index, item ) {
			that._renderItemData( ul, item );
		} );
	},

	_renderItemData: function( ul, item ) {
		return this._renderItem( ul, item ).data( "ui-autocomplete-item", item );
	},

	_renderItem: function( ul, item ) {
		return $( "<li>" )
			.append( $( "<div>" ).text( item.label ) )
			.appendTo( ul );
	},

	_move: function( direction, event ) {
		if ( !this.menu.element.is( ":visible" ) ) {
			this.search( null, event );
			return;
		}
		if ( this.menu.isFirstItem() && /^previous/.test( direction ) ||
				this.menu.isLastItem() && /^next/.test( direction ) ) {

			if ( !this.isMultiLine ) {
				this._value( this.term );
			}

			this.menu.blur();
			return;
		}
		this.menu[ direction ]( event );
	},

	widget: function() {
		return this.menu.element;
	},

	_value: function() {
		return this.valueMethod.apply( this.element, arguments );
	},

	_keyEvent: function( keyEvent, event ) {
		if ( !this.isMultiLine || this.menu.element.is( ":visible" ) ) {
			this._move( keyEvent, event );

			// Prevents moving cursor to beginning/end of the text field in some browsers
			event.preventDefault();
		}
	},

	// Support: Chrome <=50
	// We should be able to just use this.element.prop( "isContentEditable" )
	// but hidden elements always report false in Chrome.
	// https://code.google.com/p/chromium/issues/detail?id=313082
	_isContentEditable: function( element ) {
		if ( !element.length ) {
			return false;
		}

		var editable = element.prop( "contentEditable" );

		if ( editable === "inherit" ) {
		  return this._isContentEditable( element.parent() );
		}

		return editable === "true";
	}
} );

$.extend( $.ui.autocomplete, {
	escapeRegex: function( value ) {
		return value.replace( /[\-\[\]{}()*+?.,\\\^$|#\s]/g, "\\$&" );
	},
	filter: function( array, term ) {
		var matcher = new RegExp( $.ui.autocomplete.escapeRegex( term ), "i" );
		return $.grep( array, function( value ) {
			return matcher.test( value.label || value.value || value );
		} );
	}
} );

// Live region extension, adding a `messages` option
// NOTE: This is an experimental API. We are still investigating
// a full solution for string manipulation and internationalization.
$.widget( "ui.autocomplete", $.ui.autocomplete, {
	options: {
		messages: {
			noResults: "No search results.",
			results: function( amount ) {
				return amount + ( amount > 1 ? " results are" : " result is" ) +
					" available, use up and down arrow keys to navigate.";
			}
		}
	},

	__response: function( content ) {
		var message;
		this._superApply( arguments );
		if ( this.options.disabled || this.cancelSearch ) {
			return;
		}
		if ( content && content.length ) {
			message = this.options.messages.results( content.length );
		} else {
			message = this.options.messages.noResults;
		}
		this.liveRegion.children().hide();
		$( "<div>" ).text( message ).appendTo( this.liveRegion );
	}
} );

var widgetsAutocomplete = $.ui.autocomplete;


/*!
 * jQuery UI Controlgroup 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: Controlgroup
//>>group: Widgets
//>>description: Visually groups form control widgets
//>>docs: http://api.jqueryui.com/controlgroup/
//>>demos: http://jqueryui.com/controlgroup/
//>>css.structure: ../../themes/base/core.css
//>>css.structure: ../../themes/base/controlgroup.css
//>>css.theme: ../../themes/base/theme.css


var controlgroupCornerRegex = /ui-corner-([a-z]){2,6}/g;

var widgetsControlgroup = $.widget( "ui.controlgroup", {
	version: "1.12.0",
	defaultElement: "<div>",
	options: {
		direction: "horizontal",
		disabled: null,
		onlyVisible: true,
		items: {
			"button": "input[type=button], input[type=submit], input[type=reset], button, a",
			"controlgroupLabel": ".ui-controlgroup-label",
			"checkboxradio": "input[type='checkbox'], input[type='radio']",
			"selectmenu": "select",
			"spinner": ".ui-spinner-input"
		}
	},

	_create: function() {
		this._enhance();
	},

	// To support the enhanced option in jQuery Mobile, we isolate DOM manipulation
	_enhance: function() {
		this.element.attr( "role", "toolbar" );
		this.refresh();
	},

	_destroy: function() {
		this._callChildMethod( "destroy" );
		this.childWidgets.removeData( "ui-controlgroup-data" );
		this.element.removeAttr( "role" );
		if ( this.options.items.controlgroupLabel ) {
			this.element
				.find( this.options.items.controlgroupLabel )
				.find( ".ui-controlgroup-label-contents" )
				.contents().unwrap();
		}
	},

	_initWidgets: function() {
		var that = this,
			childWidgets = [];

		// First we iterate over each of the items options
		$.each( this.options.items, function( widget, selector ) {
			var labels;
			var options = {};

			// Make sure the widget has a selector set
			if ( !selector ) {
				return;
			}

			if ( widget === "controlgroupLabel" ) {
				labels = that.element.find( selector );
				labels.each( function() {
					var element = $( this );

					if ( element.children( ".ui-controlgroup-label-contents" ).length ) {
						return;
					}
					element.contents()
						.wrapAll( "<span class='ui-controlgroup-label-contents'></span>" );
				} );
				that._addClass( labels, null, "ui-widget ui-widget-content ui-state-default" );
				childWidgets = childWidgets.concat( labels.get() );
				return;
			}

			// Make sure the widget actually exists
			if ( !$.fn[ widget ] ) {
				return;
			}

			// We assume everything is in the middle to start because we can't determine
			// first / last elements until all enhancments are done.
			if ( that[ "_" + widget + "Options" ] ) {
				options = that[ "_" + widget + "Options" ]( "middle" );
			}

			// Find instances of this widget inside controlgroup and init them
			that.element
				.find( selector )
				.each( function() {
					var element = $( this );
					var instance = element[ widget ]( "instance" );

					// We need to clone the default options for this type of widget to avoid
					// polluting the variable options which has a wider scope than a single widget.
					var instanceOptions = $.widget.extend( {}, options );

					// If the button is the child of a spinner ignore it
					// TODO: Find a more generic solution
					if ( widget === "button" && element.parent( ".ui-spinner" ).length ) {
						return;
					}

					// Create the widget if it doesn't exist
					if ( !instance ) {
						instance = element[ widget ]()[ widget ]( "instance" );
					}
					if ( instance ) {
						instanceOptions.classes =
							that._resolveClassesValues( instanceOptions.classes, instance );
					}
					element[ widget ]( instanceOptions );

					// Store an instance of the controlgroup to be able to reference
					// from the outermost element for changing options and refresh
					var widgetElement = element[ widget ]( "widget" );
					$.data( widgetElement[ 0 ], "ui-controlgroup-data",
						instance ? instance : element[ widget ]( "instance" ) );

					childWidgets.push( widgetElement[ 0 ] );
				} );
		} );

		this.childWidgets = $( $.unique( childWidgets ) );
		this._addClass( this.childWidgets, "ui-controlgroup-item" );
	},

	_callChildMethod: function( method ) {
		this.childWidgets.each( function() {
			var element = $( this ),
				data = element.data( "ui-controlgroup-data" );
			if ( data && data[ method ] ) {
				data[ method ]();
			}
		} );
	},

	_updateCornerClass: function( element, position ) {
		var remove = "ui-corner-top ui-corner-bottom ui-corner-left ui-corner-right ui-corner-all";
		var add = this._buildSimpleOptions( position, "label" ).classes.label;

		this._removeClass( element, null, remove );
		this._addClass( element, null, add );
	},

	_buildSimpleOptions: function( position, key ) {
		var direction = this.options.direction === "vertical";
		var result = {
			classes: {}
		};
		result.classes[ key ] = {
			"middle": "",
			"first": "ui-corner-" + ( direction ? "top" : "left" ),
			"last": "ui-corner-" + ( direction ? "bottom" : "right" ),
			"only": "ui-corner-all"
		}[ position ];

		return result;
	},

	_spinnerOptions: function( position ) {
		var options = this._buildSimpleOptions( position, "ui-spinner" );

		options.classes[ "ui-spinner-up" ] = "";
		options.classes[ "ui-spinner-down" ] = "";

		return options;
	},

	_buttonOptions: function( position ) {
		return this._buildSimpleOptions( position, "ui-button" );
	},

	_checkboxradioOptions: function( position ) {
		return this._buildSimpleOptions( position, "ui-checkboxradio-label" );
	},

	_selectmenuOptions: function( position ) {
		var direction = this.options.direction === "vertical";
		return {
			width: direction ? "auto" : false,
			classes: {
				middle: {
					"ui-selectmenu-button-open": "",
					"ui-selectmenu-button-closed": ""
				},
				first: {
					"ui-selectmenu-button-open": "ui-corner-" + ( direction ? "top" : "tl" ),
					"ui-selectmenu-button-closed": "ui-corner-" + ( direction ? "top" : "left" )
				},
				last: {
					"ui-selectmenu-button-open": direction ? "" : "ui-corner-tr",
					"ui-selectmenu-button-closed": "ui-corner-" + ( direction ? "bottom" : "right" )
				},
				only: {
					"ui-selectmenu-button-open": "ui-corner-top",
					"ui-selectmenu-button-closed": "ui-corner-all"
				}

			}[ position ]
		};
	},

	_resolveClassesValues: function( classes, instance ) {
		var result = {};
		$.each( classes, function( key ) {
			var current = instance.options.classes[ key ] || "";
			current = current.replace( controlgroupCornerRegex, "" ).trim();
			result[ key ] = ( current + " " + classes[ key ] ).replace( /\s+/g, " " );
		} );
		return result;
	},

	_setOption: function( key, value ) {
		if ( key === "direction" ) {
			this._removeClass( "ui-controlgroup-" + this.options.direction );
		}

		this._super( key, value );
		if ( key === "disabled" ) {
			this._callChildMethod( value ? "disable" : "enable" );
			return;
		}

		this.refresh();
	},

	refresh: function() {
		var children,
			that = this;

		this._addClass( "ui-controlgroup ui-controlgroup-" + this.options.direction );

		if ( this.options.direction === "horizontal" ) {
			this._addClass( null, "ui-helper-clearfix" );
		}
		this._initWidgets();

		children = this.childWidgets;

		// We filter here because we need to track all childWidgets not just the visible ones
		if ( this.options.onlyVisible ) {
			children = children.filter( ":visible" );
		}

		if ( children.length ) {

			// We do this last because we need to make sure all enhancment is done
			// before determining first and last
			$.each( [ "first", "last" ], function( index, value ) {
				var instance = children[ value ]().data( "ui-controlgroup-data" );

				if ( instance && that[ "_" + instance.widgetName + "Options" ] ) {
					var options = that[ "_" + instance.widgetName + "Options" ](
						children.length === 1 ? "only" : value
					);
					options.classes = that._resolveClassesValues( options.classes, instance );
					instance.element[ instance.widgetName ]( options );
				} else {
					that._updateCornerClass( children[ value ](), value );
				}
			} );

			// Finally call the refresh method on each of the child widgets.
			this._callChildMethod( "refresh" );
		}
	}
} );

/*!
 * jQuery UI Checkboxradio 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: Checkboxradio
//>>group: Widgets
//>>description: Enhances a form with multiple themeable checkboxes or radio buttons.
//>>docs: http://api.jqueryui.com/checkboxradio/
//>>demos: http://jqueryui.com/checkboxradio/
//>>css.structure: ../../themes/base/core.css
//>>css.structure: ../../themes/base/button.css
//>>css.structure: ../../themes/base/checkboxradio.css
//>>css.theme: ../../themes/base/theme.css



$.widget( "ui.checkboxradio", [ $.ui.formResetMixin, {
	version: "1.12.0",
	options: {
		disabled: null,
		label: null,
		icon: true,
		classes: {
			"ui-checkboxradio-label": "ui-corner-all",
			"ui-checkboxradio-icon": "ui-corner-all"
		}
	},

	_getCreateOptions: function() {
		var disabled, labels;
		var that = this;
		var options = this._super() || {};

		// We read the type here, because it makes more sense to throw a element type error first,
		// rather then the error for lack of a label. Often if its the wrong type, it
		// won't have a label (e.g. calling on a div, btn, etc)
		this._readType();

		labels = this.element.labels();

		// If there are multiple labels, use the last one
		this.label = $( labels[ labels.length - 1 ] );
		if ( !this.label.length ) {
			$.error( "No label found for checkboxradio widget" );
		}

		this.originalLabel = "";

		// We need to get the label text but this may also need to make sure it does not contain the
		// input itself.
		this.label.contents().not( this.element ).each( function() {

			// The label contents could be text, html, or a mix. We concat each element to get a
			// string representation of the label, without the input as part of it.
			that.originalLabel += this.nodeType === 3 ? $( this ).text() : this.outerHTML;
		} );

		// Set the label option if we found label text
		if ( this.originalLabel ) {
			options.label = this.originalLabel;
		}

		disabled = this.element[ 0 ].disabled;
		if ( disabled != null ) {
			options.disabled = disabled;
		}
		return options;
	},

	_create: function() {
		var checked = this.element[ 0 ].checked;

		this._bindFormResetHandler();

		if ( this.options.disabled == null ) {
			this.options.disabled = this.element[ 0 ].disabled;
		}

		this._setOption( "disabled", this.options.disabled );
		this._addClass( "ui-checkboxradio", "ui-helper-hidden-accessible" );
		this._addClass( this.label, "ui-checkboxradio-label", "ui-button ui-widget" );

		if ( this.type === "radio" ) {
			this._addClass( this.label, "ui-checkboxradio-radio-label" );
		}

		if ( this.options.label && this.options.label !== this.originalLabel ) {
			this._updateLabel();
		} else if ( this.originalLabel ) {
			this.options.label = this.originalLabel;
		}

		this._enhance();

		if ( checked ) {
			this._addClass( this.label, "ui-checkboxradio-checked", "ui-state-active" );
			if ( this.icon ) {
				this._addClass( this.icon, null, "ui-state-hover" );
			}
		}

		this._on( {
			change: "_toggleClasses",
			focus: function() {
				this._addClass( this.label, null, "ui-state-focus ui-visual-focus" );
			},
			blur: function() {
				this._removeClass( this.label, null, "ui-state-focus ui-visual-focus" );
			}
		} );
	},

	_readType: function() {
		var nodeName = this.element[ 0 ].nodeName.toLowerCase();
		this.type = this.element[ 0 ].type;
		if ( nodeName !== "input" || !/radio|checkbox/.test( this.type ) ) {
			$.error( "Can't create checkboxradio on element.nodeName=" + nodeName +
				" and element.type=" + this.type );
		}
	},

	// Support jQuery Mobile enhanced option
	_enhance: function() {
		this._updateIcon( this.element[ 0 ].checked );
	},

	widget: function() {
		return this.label;
	},

	_getRadioGroup: function() {
		var group;
		var name = this.element[ 0 ].name;
		var nameSelector = "input[name='" + $.ui.escapeSelector( name ) + "']";

		if ( !name ) {
			return $( [] );
		}

		if ( this.form.length ) {
			group = $( this.form[ 0 ].elements ).filter( nameSelector );
		} else {

			// Not inside a form, check all inputs that also are not inside a form
			group = $( nameSelector ).filter( function() {
				return $( this ).form().length === 0;
			} );
		}

		return group.not( this.element );
	},

	_toggleClasses: function() {
		var checked = this.element[ 0 ].checked;
		this._toggleClass( this.label, "ui-checkboxradio-checked", "ui-state-active", checked );

		if ( this.options.icon && this.type === "checkbox" ) {
			this._toggleClass( this.icon, null, "ui-icon-check ui-state-checked", checked )
				._toggleClass( this.icon, null, "ui-icon-blank", !checked );
		}

		if ( this.type === "radio" ) {
			this._getRadioGroup()
				.each( function() {
					var instance = $( this ).checkboxradio( "instance" );

					if ( instance ) {
						instance._removeClass( instance.label,
							"ui-checkboxradio-checked", "ui-state-active" );
					}
				} );
		}
	},

	_destroy: function() {
		this._unbindFormResetHandler();

		if ( this.icon ) {
			this.icon.remove();
			this.iconSpace.remove();
		}
	},

	_setOption: function( key, value ) {

		// We don't allow the value to be set to nothing
		if ( key === "label" && !value ) {
			return;
		}

		this._super( key, value );

		if ( key === "disabled" ) {
			this._toggleClass( this.label, null, "ui-state-disabled", value );
			this.element[ 0 ].disabled = value;

			// Don't refresh when setting disabled
			return;
		}
		this.refresh();
	},

	_updateIcon: function( checked ) {
		var toAdd = "ui-icon ui-icon-background ";

		if ( this.options.icon ) {
			if ( !this.icon ) {
				this.icon = $( "<span>" );
				this.iconSpace = $( "<span> </span>" );
				this._addClass( this.iconSpace, "ui-checkboxradio-icon-space" );
			}

			if ( this.type === "checkbox" ) {
				toAdd += checked ? "ui-icon-check ui-state-checked" : "ui-icon-blank";
				this._removeClass( this.icon, null, checked ? "ui-icon-blank" : "ui-icon-check" );
			} else {
				toAdd += "ui-icon-blank";
			}
			this._addClass( this.icon, "ui-checkboxradio-icon", toAdd );
			if ( !checked ) {
				this._removeClass( this.icon, null, "ui-icon-check ui-state-checked" );
			}
			this.icon.prependTo( this.label ).after( this.iconSpace );
		} else if ( this.icon !== undefined ) {
			this.icon.remove();
			this.iconSpace.remove();
			delete this.icon;
		}
	},

	_updateLabel: function() {

		// Remove the contents of the label ( minus the icon, icon space, and input )
		this.label.contents().not( this.element.add( this.icon ).add( this.iconSpace ) ).remove();
		this.label.append( this.options.label );
	},

	refresh: function() {
		var checked = this.element[ 0 ].checked,
			isDisabled = this.element[ 0 ].disabled;

		this._updateIcon( checked );
		this._toggleClass( this.label, "ui-checkboxradio-checked", "ui-state-active", checked );
		if ( this.options.label !== null ) {
			this._updateLabel();
		}

		if ( isDisabled !== this.options.disabled ) {
			this._setOptions( { "disabled": isDisabled } );
		}
	}

} ] );

var widgetsCheckboxradio = $.ui.checkboxradio;


/*!
 * jQuery UI Button 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: Button
//>>group: Widgets
//>>description: Enhances a form with themeable buttons.
//>>docs: http://api.jqueryui.com/button/
//>>demos: http://jqueryui.com/button/
//>>css.structure: ../../themes/base/core.css
//>>css.structure: ../../themes/base/button.css
//>>css.theme: ../../themes/base/theme.css



$.widget( "ui.button", {
	version: "1.12.0",
	defaultElement: "<button>",
	options: {
		classes: {
			"ui-button": "ui-corner-all"
		},
		disabled: null,
		icon: null,
		iconPosition: "beginning",
		label: null,
		showLabel: true
	},

	_getCreateOptions: function() {
		var disabled,

			// This is to support cases like in jQuery Mobile where the base widget does have
			// an implementation of _getCreateOptions
			options = this._super() || {};

		this.isInput = this.element.is( "input" );

		disabled = this.element[ 0 ].disabled;
		if ( disabled != null ) {
			options.disabled = disabled;
		}

		this.originalLabel = this.isInput ? this.element.val() : this.element.html();
		if ( this.originalLabel ) {
			options.label = this.originalLabel;
		}

		return options;
	},

	_create: function() {
		if ( !this.option.showLabel & !this.options.icon ) {
			this.options.showLabel = true;
		}

		// We have to check the option again here even though we did in _getCreateOptions,
		// because null may have been passed on init which would override what was set in
		// _getCreateOptions
		if ( this.options.disabled == null ) {
			this.options.disabled = this.element[ 0 ].disabled || false;
		}

		this.hasTitle = !!this.element.attr( "title" );

		// Check to see if the label needs to be set or if its already correct
		if ( this.options.label && this.options.label !== this.originalLabel ) {
			if ( this.isInput ) {
				this.element.val( this.options.label );
			} else {
				this.element.html( this.options.label );
			}
		}
		this._addClass( "ui-button", "ui-widget" );
		this._setOption( "disabled", this.options.disabled );
		this._enhance();

		if ( this.element.is( "a" ) ) {
			this._on( {
				"keyup": function( event ) {
					if ( event.keyCode === $.ui.keyCode.SPACE ) {
						event.preventDefault();

						// Support: PhantomJS <= 1.9, IE 8 Only
						// If a native click is available use it so we actually cause navigation
						// otherwise just trigger a click event
						if ( this.element[ 0 ].click ) {
							this.element[ 0 ].click();
						} else {
							this.element.trigger( "click" );
						}
					}
				}
			} );
		}
	},

	_enhance: function() {
		if ( !this.element.is( "button" ) ) {
			this.element.attr( "role", "button" );
		}

		if ( this.options.icon ) {
			this._updateIcon( "icon", this.options.icon );
			this._updateTooltip();
		}
	},

	_updateTooltip: function() {
		this.title = this.element.attr( "title" );

		if ( !this.options.showLabel && !this.title ) {
			this.element.attr( "title", this.options.label );
		}
	},

	_updateIcon: function( option, value ) {
		var icon = option !== "iconPosition",
			position = icon ? this.options.iconPosition : value,
			displayBlock = position === "top" || position === "bottom";

		// Create icon
		if ( !this.icon ) {
			this.icon = $( "<span>" );

			this._addClass( this.icon, "ui-button-icon", "ui-icon" );

			if ( !this.options.showLabel ) {
				this._addClass( "ui-button-icon-only" );
			}
		} else if ( icon ) {

			// If we are updating the icon remove the old icon class
			this._removeClass( this.icon, null, this.options.icon );
		}

		// If we are updating the icon add the new icon class
		if ( icon ) {
			this._addClass( this.icon, null, value );
		}

		this._attachIcon( position );

		// If the icon is on top or bottom we need to add the ui-widget-icon-block class and remove
		// the iconSpace if there is one.
		if ( displayBlock ) {
			this._addClass( this.icon, null, "ui-widget-icon-block" );
			if ( this.iconSpace ) {
				this.iconSpace.remove();
			}
		} else {

			// Position is beginning or end so remove the ui-widget-icon-block class and add the
			// space if it does not exist
			if ( !this.iconSpace ) {
				this.iconSpace = $( "<span> </span>" );
				this._addClass( this.iconSpace, "ui-button-icon-space" );
			}
			this._removeClass( this.icon, null, "ui-wiget-icon-block" );
			this._attachIconSpace( position );
		}
	},

	_destroy: function() {
		this.element.removeAttr( "role" );

		if ( this.icon ) {
			this.icon.remove();
		}
		if ( this.iconSpace ) {
			this.iconSpace.remove();
		}
		if ( !this.hasTitle ) {
			this.element.removeAttr( "title" );
		}
	},

	_attachIconSpace: function( iconPosition ) {
		this.icon[ /^(?:end|bottom)/.test( iconPosition ) ? "before" : "after" ]( this.iconSpace );
	},

	_attachIcon: function( iconPosition ) {
		this.element[ /^(?:end|bottom)/.test( iconPosition ) ? "append" : "prepend" ]( this.icon );
	},

	_setOptions: function( options ) {
		var newShowLabel = options.showLabel === undefined ?
				this.options.showLabel :
				options.showLabel,
			newIcon = options.icon === undefined ? this.options.icon : options.icon;

		if ( !newShowLabel && !newIcon ) {
			options.showLabel = true;
		}
		this._super( options );
	},

	_setOption: function( key, value ) {
		if ( key === "icon" ) {
			if ( value ) {
				this._updateIcon( key, value );
			} else if ( this.icon ) {
				this.icon.remove();
				if ( this.iconSpace ) {
					this.iconSpace.remove();
				}
			}
		}

		if ( key === "iconPosition" ) {
			this._updateIcon( key, value );
		}

		// Make sure we can't end up with a button that has neither text nor icon
		if ( key === "showLabel" ) {
				this._toggleClass( "ui-button-icon-only", null, !value );
				this._updateTooltip();
		}

		if ( key === "label" ) {
			if ( this.isInput ) {
				this.element.val( value );
			} else {

				// If there is an icon, append it, else nothing then append the value
				// this avoids removal of the icon when setting label text
				this.element.html( value );
				if ( this.icon ) {
					this._attachIcon( this.options.iconPosition );
					this._attachIconSpace( this.options.iconPosition );
				}
			}
		}

		this._super( key, value );

		if ( key === "disabled" ) {
			this._toggleClass( null, "ui-state-disabled", value );
			this.element[ 0 ].disabled = value;
			if ( value ) {
				this.element.blur();
			}
		}
	},

	refresh: function() {

		// Make sure to only check disabled if its an element that supports this otherwise
		// check for the disabled class to determine state
		var isDisabled = this.element.is( "input, button" ) ?
			this.element[ 0 ].disabled : this.element.hasClass( "ui-button-disabled" );

		if ( isDisabled !== this.options.disabled ) {
			this._setOptions( { disabled: isDisabled } );
		}

		this._updateTooltip();
	}
} );

// DEPRECATED
if ( $.uiBackCompat !== false ) {

	// Text and Icons options
	$.widget( "ui.button", $.ui.button, {
		options: {
			text: true,
			icons: {
				primary: null,
				secondary: null
			}
		},

		_create: function() {
			if ( this.options.showLabel && !this.options.text ) {
				this.options.showLabel = this.options.text;
			}
			if ( !this.options.showLabel && this.options.text ) {
				this.options.text = this.options.showLabel;
			}
			if ( !this.options.icon && ( this.options.icons.primary ||
					this.options.icons.secondary ) ) {
				if ( this.options.icons.primary ) {
					this.options.icon = this.options.icons.primary;
				} else {
					this.options.icon = this.options.icons.secondary;
					this.options.iconPosition = "end";
				}
			} else if ( this.options.icon ) {
				this.options.icons.primary = this.options.icon;
			}
			this._super();
		},

		_setOption: function( key, value ) {
			if ( key === "text" ) {
				this._super( "showLabel", value );
				return;
			}
			if ( key === "showLabel" ) {
				this.options.text = value;
			}
			if ( key === "icon" ) {
				this.options.icons.primary = value;
			}
			if ( key === "icons" ) {
				if ( value.primary ) {
					this._super( "icon", value.primary );
					this._super( "iconPosition", "beginning" );
				} else if ( value.secondary ) {
					this._super( "icon", value.secondary );
					this._super( "iconPosition", "end" );
				}
			}
			this._superApply( arguments );
		}
	} );

	$.fn.button = ( function( orig ) {
		return function() {
			if ( !this.length || ( this.length && this[ 0 ].tagName !== "INPUT" ) ||
					( this.length && this[ 0 ].tagName === "INPUT" && (
						this.attr( "type" ) !== "checkbox" && this.attr( "type" ) !== "radio"
					) ) ) {
				return orig.apply( this, arguments );
			}
			if ( !$.ui.checkboxradio ) {
				$.error( "Checkboxradio widget missing" );
			}
			if ( arguments.length === 0 ) {
				return this.checkboxradio( {
					"icon": false
				} );
			}
			return this.checkboxradio.apply( this, arguments );
		};
	} )( $.fn.button );

	$.fn.buttonset = function() {
		if ( !$.ui.controlgroup ) {
			$.error( "Controlgroup widget missing" );
		}
		if ( arguments[ 0 ] === "option" && arguments[ 1 ] === "items" && arguments[ 2 ] ) {
			return this.controlgroup.apply( this,
				[ arguments[ 0 ], "items.button", arguments[ 2 ] ] );
		}
		if ( arguments[ 0 ] === "option" && arguments[ 1 ] === "items" ) {
			return this.controlgroup.apply( this, [ arguments[ 0 ], "items.button" ] );
		}
		if ( typeof arguments[ 0 ] === "object" && arguments[ 0 ].items ) {
			arguments[ 0 ].items = {
				button: arguments[ 0 ].items
			};
		}
		return this.controlgroup.apply( this, arguments );
	};
}

var widgetsButton = $.ui.button;


// jscs:disable maximumLineLength
/* jscs:disable requireCamelCaseOrUpperCaseIdentifiers */
/*!
 * jQuery UI Datepicker 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: Datepicker
//>>group: Widgets
//>>description: Displays a calendar from an input or inline for selecting dates.
//>>docs: http://api.jqueryui.com/datepicker/
//>>demos: http://jqueryui.com/datepicker/
//>>css.structure: ../../themes/base/core.css
//>>css.structure: ../../themes/base/datepicker.css
//>>css.theme: ../../themes/base/theme.css



$.extend( $.ui, { datepicker: { version: "1.12.0" } } );

var datepicker_instActive;

function datepicker_getZindex( elem ) {
	var position, value;
	while ( elem.length && elem[ 0 ] !== document ) {

		// Ignore z-index if position is set to a value where z-index is ignored by the browser
		// This makes behavior of this function consistent across browsers
		// WebKit always returns auto if the element is positioned
		position = elem.css( "position" );
		if ( position === "absolute" || position === "relative" || position === "fixed" ) {

			// IE returns 0 when zIndex is not specified
			// other browsers return a string
			// we ignore the case of nested elements with an explicit value of 0
			// <div style="z-index: -10;"><div style="z-index: 0;"></div></div>
			value = parseInt( elem.css( "zIndex" ), 10 );
			if ( !isNaN( value ) && value !== 0 ) {
				return value;
			}
		}
		elem = elem.parent();
	}

	return 0;
}
/* Date picker manager.
   Use the singleton instance of this class, $.datepicker, to interact with the date picker.
   Settings for (groups of) date pickers are maintained in an instance object,
   allowing multiple different settings on the same page. */

function Datepicker() {
	this._curInst = null; // The current instance in use
	this._keyEvent = false; // If the last event was a key event
	this._disabledInputs = []; // List of date picker inputs that have been disabled
	this._datepickerShowing = false; // True if the popup picker is showing , false if not
	this._inDialog = false; // True if showing within a "dialog", false if not
	this._mainDivId = "ui-datepicker-div"; // The ID of the main datepicker division
	this._inlineClass = "ui-datepicker-inline"; // The name of the inline marker class
	this._appendClass = "ui-datepicker-append"; // The name of the append marker class
	this._triggerClass = "ui-datepicker-trigger"; // The name of the trigger marker class
	this._dialogClass = "ui-datepicker-dialog"; // The name of the dialog marker class
	this._disableClass = "ui-datepicker-disabled"; // The name of the disabled covering marker class
	this._unselectableClass = "ui-datepicker-unselectable"; // The name of the unselectable cell marker class
	this._currentClass = "ui-datepicker-current-day"; // The name of the current day marker class
	this._dayOverClass = "ui-datepicker-days-cell-over"; // The name of the day hover marker class
	this.regional = []; // Available regional settings, indexed by language code
	this.regional[ "" ] = { // Default regional settings
		closeText: "Done", // Display text for close link
		prevText: "Prev", // Display text for previous month link
		nextText: "Next", // Display text for next month link
		currentText: "Today", // Display text for current month link
		monthNames: [ "January","February","March","April","May","June",
			"July","August","September","October","November","December" ], // Names of months for drop-down and formatting
		monthNamesShort: [ "Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep", "Oct", "Nov", "Dec" ], // For formatting
		dayNames: [ "Sunday", "Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday" ], // For formatting
		dayNamesShort: [ "Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat" ], // For formatting
		dayNamesMin: [ "Su","Mo","Tu","We","Th","Fr","Sa" ], // Column headings for days starting at Sunday
		weekHeader: "Wk", // Column header for week of the year
		dateFormat: "mm/dd/yy", // See format options on parseDate
		firstDay: 0, // The first day of the week, Sun = 0, Mon = 1, ...
		isRTL: false, // True if right-to-left language, false if left-to-right
		showMonthAfterYear: false, // True if the year select precedes month, false for month then year
		yearSuffix: "" // Additional text to append to the year in the month headers
	};
	this._defaults = { // Global defaults for all the date picker instances
		showOn: "focus", // "focus" for popup on focus,
			// "button" for trigger button, or "both" for either
		showAnim: "fadeIn", // Name of jQuery animation for popup
		showOptions: {}, // Options for enhanced animations
		defaultDate: null, // Used when field is blank: actual date,
			// +/-number for offset from today, null for today
		appendText: "", // Display text following the input box, e.g. showing the format
		buttonText: "...", // Text for trigger button
		buttonImage: "", // URL for trigger button image
		buttonImageOnly: false, // True if the image appears alone, false if it appears on a button
		hideIfNoPrevNext: false, // True to hide next/previous month links
			// if not applicable, false to just disable them
		navigationAsDateFormat: false, // True if date formatting applied to prev/today/next links
		gotoCurrent: false, // True if today link goes back to current selection instead
		changeMonth: false, // True if month can be selected directly, false if only prev/next
		changeYear: false, // True if year can be selected directly, false if only prev/next
		yearRange: "c-10:c+10", // Range of years to display in drop-down,
			// either relative to today's year (-nn:+nn), relative to currently displayed year
			// (c-nn:c+nn), absolute (nnnn:nnnn), or a combination of the above (nnnn:-n)
		showOtherMonths: false, // True to show dates in other months, false to leave blank
		selectOtherMonths: false, // True to allow selection of dates in other months, false for unselectable
		showWeek: false, // True to show week of the year, false to not show it
		calculateWeek: this.iso8601Week, // How to calculate the week of the year,
			// takes a Date and returns the number of the week for it
		shortYearCutoff: "+10", // Short year values < this are in the current century,
			// > this are in the previous century,
			// string value starting with "+" for current year + value
		minDate: null, // The earliest selectable date, or null for no limit
		maxDate: null, // The latest selectable date, or null for no limit
		duration: "fast", // Duration of display/closure
		beforeShowDay: null, // Function that takes a date and returns an array with
			// [0] = true if selectable, false if not, [1] = custom CSS class name(s) or "",
			// [2] = cell title (optional), e.g. $.datepicker.noWeekends
		beforeShow: null, // Function that takes an input field and
			// returns a set of custom settings for the date picker
		onSelect: null, // Define a callback function when a date is selected
		onChangeMonthYear: null, // Define a callback function when the month or year is changed
		onClose: null, // Define a callback function when the datepicker is closed
		numberOfMonths: 1, // Number of months to show at a time
		showCurrentAtPos: 0, // The position in multipe months at which to show the current month (starting at 0)
		stepMonths: 1, // Number of months to step back/forward
		stepBigMonths: 12, // Number of months to step back/forward for the big links
		altField: "", // Selector for an alternate field to store selected dates into
		altFormat: "", // The date format to use for the alternate field
		constrainInput: true, // The input is constrained by the current date format
		showButtonPanel: false, // True to show button panel, false to not show it
		autoSize: false, // True to size the input for the date format, false to leave as is
		disabled: false // The initial disabled state
	};
	$.extend( this._defaults, this.regional[ "" ] );
	this.regional.en = $.extend( true, {}, this.regional[ "" ] );
	this.regional[ "en-US" ] = $.extend( true, {}, this.regional.en );
	this.dpDiv = datepicker_bindHover( $( "<div id='" + this._mainDivId + "' class='ui-datepicker ui-widget ui-widget-content ui-helper-clearfix ui-corner-all'></div>" ) );
}

$.extend( Datepicker.prototype, {
	/* Class name added to elements to indicate already configured with a date picker. */
	markerClassName: "hasDatepicker",

	//Keep track of the maximum number of rows displayed (see #7043)
	maxRows: 4,

	// TODO rename to "widget" when switching to widget factory
	_widgetDatepicker: function() {
		return this.dpDiv;
	},

	/* Override the default settings for all instances of the date picker.
	 * @param  settings  object - the new settings to use as defaults (anonymous object)
	 * @return the manager object
	 */
	setDefaults: function( settings ) {
		datepicker_extendRemove( this._defaults, settings || {} );
		return this;
	},

	/* Attach the date picker to a jQuery selection.
	 * @param  target	element - the target input field or division or span
	 * @param  settings  object - the new settings to use for this date picker instance (anonymous)
	 */
	_attachDatepicker: function( target, settings ) {
		var nodeName, inline, inst;
		nodeName = target.nodeName.toLowerCase();
		inline = ( nodeName === "div" || nodeName === "span" );
		if ( !target.id ) {
			this.uuid += 1;
			target.id = "dp" + this.uuid;
		}
		inst = this._newInst( $( target ), inline );
		inst.settings = $.extend( {}, settings || {} );
		if ( nodeName === "input" ) {
			this._connectDatepicker( target, inst );
		} else if ( inline ) {
			this._inlineDatepicker( target, inst );
		}
	},

	/* Create a new instance object. */
	_newInst: function( target, inline ) {
		var id = target[ 0 ].id.replace( /([^A-Za-z0-9_\-])/g, "\\\\$1" ); // escape jQuery meta chars
		return { id: id, input: target, // associated target
			selectedDay: 0, selectedMonth: 0, selectedYear: 0, // current selection
			drawMonth: 0, drawYear: 0, // month being drawn
			inline: inline, // is datepicker inline or not
			dpDiv: ( !inline ? this.dpDiv : // presentation div
			datepicker_bindHover( $( "<div class='" + this._inlineClass + " ui-datepicker ui-widget ui-widget-content ui-helper-clearfix ui-corner-all'></div>" ) ) ) };
	},

	/* Attach the date picker to an input field. */
	_connectDatepicker: function( target, inst ) {
		var input = $( target );
		inst.append = $( [] );
		inst.trigger = $( [] );
		if ( input.hasClass( this.markerClassName ) ) {
			return;
		}
		this._attachments( input, inst );
		input.addClass( this.markerClassName ).on( "keydown", this._doKeyDown ).
			on( "keypress", this._doKeyPress ).on( "keyup", this._doKeyUp );
		this._autoSize( inst );
		$.data( target, "datepicker", inst );

		//If disabled option is true, disable the datepicker once it has been attached to the input (see ticket #5665)
		if ( inst.settings.disabled ) {
			this._disableDatepicker( target );
		}
	},

	/* Make attachments based on settings. */
	_attachments: function( input, inst ) {
		var showOn, buttonText, buttonImage,
			appendText = this._get( inst, "appendText" ),
			isRTL = this._get( inst, "isRTL" );

		if ( inst.append ) {
			inst.append.remove();
		}
		if ( appendText ) {
			inst.append = $( "<span class='" + this._appendClass + "'>" + appendText + "</span>" );
			input[ isRTL ? "before" : "after" ]( inst.append );
		}

		input.off( "focus", this._showDatepicker );

		if ( inst.trigger ) {
			inst.trigger.remove();
		}

		showOn = this._get( inst, "showOn" );
		if ( showOn === "focus" || showOn === "both" ) { // pop-up date picker when in the marked field
			input.on( "focus", this._showDatepicker );
		}
		if ( showOn === "button" || showOn === "both" ) { // pop-up date picker when button clicked
			buttonText = this._get( inst, "buttonText" );
			buttonImage = this._get( inst, "buttonImage" );
			inst.trigger = $( this._get( inst, "buttonImageOnly" ) ?
				$( "<img/>" ).addClass( this._triggerClass ).
					attr( { src: buttonImage, alt: buttonText, title: buttonText } ) :
				$( "<button type='button'></button>" ).addClass( this._triggerClass ).
					html( !buttonImage ? buttonText : $( "<img/>" ).attr(
					{ src:buttonImage, alt:buttonText, title:buttonText } ) ) );
			input[ isRTL ? "before" : "after" ]( inst.trigger );
			inst.trigger.on( "click", function() {
				if ( $.datepicker._datepickerShowing && $.datepicker._lastInput === input[ 0 ] ) {
					$.datepicker._hideDatepicker();
				} else if ( $.datepicker._datepickerShowing && $.datepicker._lastInput !== input[ 0 ] ) {
					$.datepicker._hideDatepicker();
					$.datepicker._showDatepicker( input[ 0 ] );
				} else {
					$.datepicker._showDatepicker( input[ 0 ] );
				}
				return false;
			} );
		}
	},

	/* Apply the maximum length for the date format. */
	_autoSize: function( inst ) {
		if ( this._get( inst, "autoSize" ) && !inst.inline ) {
			var findMax, max, maxI, i,
				date = new Date( 2009, 12 - 1, 20 ), // Ensure double digits
				dateFormat = this._get( inst, "dateFormat" );

			if ( dateFormat.match( /[DM]/ ) ) {
				findMax = function( names ) {
					max = 0;
					maxI = 0;
					for ( i = 0; i < names.length; i++ ) {
						if ( names[ i ].length > max ) {
							max = names[ i ].length;
							maxI = i;
						}
					}
					return maxI;
				};
				date.setMonth( findMax( this._get( inst, ( dateFormat.match( /MM/ ) ?
					"monthNames" : "monthNamesShort" ) ) ) );
				date.setDate( findMax( this._get( inst, ( dateFormat.match( /DD/ ) ?
					"dayNames" : "dayNamesShort" ) ) ) + 20 - date.getDay() );
			}
			inst.input.attr( "size", this._formatDate( inst, date ).length );
		}
	},

	/* Attach an inline date picker to a div. */
	_inlineDatepicker: function( target, inst ) {
		var divSpan = $( target );
		if ( divSpan.hasClass( this.markerClassName ) ) {
			return;
		}
		divSpan.addClass( this.markerClassName ).append( inst.dpDiv );
		$.data( target, "datepicker", inst );
		this._setDate( inst, this._getDefaultDate( inst ), true );
		this._updateDatepicker( inst );
		this._updateAlternate( inst );

		//If disabled option is true, disable the datepicker before showing it (see ticket #5665)
		if ( inst.settings.disabled ) {
			this._disableDatepicker( target );
		}

		// Set display:block in place of inst.dpDiv.show() which won't work on disconnected elements
		// http://bugs.jqueryui.com/ticket/7552 - A Datepicker created on a detached div has zero height
		inst.dpDiv.css( "display", "block" );
	},

	/* Pop-up the date picker in a "dialog" box.
	 * @param  input element - ignored
	 * @param  date	string or Date - the initial date to display
	 * @param  onSelect  function - the function to call when a date is selected
	 * @param  settings  object - update the dialog date picker instance's settings (anonymous object)
	 * @param  pos int[2] - coordinates for the dialog's position within the screen or
	 *					event - with x/y coordinates or
	 *					leave empty for default (screen centre)
	 * @return the manager object
	 */
	_dialogDatepicker: function( input, date, onSelect, settings, pos ) {
		var id, browserWidth, browserHeight, scrollX, scrollY,
			inst = this._dialogInst; // internal instance

		if ( !inst ) {
			this.uuid += 1;
			id = "dp" + this.uuid;
			this._dialogInput = $( "<input type='text' id='" + id +
				"' style='position: absolute; top: -100px; width: 0px;'/>" );
			this._dialogInput.on( "keydown", this._doKeyDown );
			$( "body" ).append( this._dialogInput );
			inst = this._dialogInst = this._newInst( this._dialogInput, false );
			inst.settings = {};
			$.data( this._dialogInput[ 0 ], "datepicker", inst );
		}
		datepicker_extendRemove( inst.settings, settings || {} );
		date = ( date && date.constructor === Date ? this._formatDate( inst, date ) : date );
		this._dialogInput.val( date );

		this._pos = ( pos ? ( pos.length ? pos : [ pos.pageX, pos.pageY ] ) : null );
		if ( !this._pos ) {
			browserWidth = document.documentElement.clientWidth;
			browserHeight = document.documentElement.clientHeight;
			scrollX = document.documentElement.scrollLeft || document.body.scrollLeft;
			scrollY = document.documentElement.scrollTop || document.body.scrollTop;
			this._pos = // should use actual width/height below
				[ ( browserWidth / 2 ) - 100 + scrollX, ( browserHeight / 2 ) - 150 + scrollY ];
		}

		// Move input on screen for focus, but hidden behind dialog
		this._dialogInput.css( "left", ( this._pos[ 0 ] + 20 ) + "px" ).css( "top", this._pos[ 1 ] + "px" );
		inst.settings.onSelect = onSelect;
		this._inDialog = true;
		this.dpDiv.addClass( this._dialogClass );
		this._showDatepicker( this._dialogInput[ 0 ] );
		if ( $.blockUI ) {
			$.blockUI( this.dpDiv );
		}
		$.data( this._dialogInput[ 0 ], "datepicker", inst );
		return this;
	},

	/* Detach a datepicker from its control.
	 * @param  target	element - the target input field or division or span
	 */
	_destroyDatepicker: function( target ) {
		var nodeName,
			$target = $( target ),
			inst = $.data( target, "datepicker" );

		if ( !$target.hasClass( this.markerClassName ) ) {
			return;
		}

		nodeName = target.nodeName.toLowerCase();
		$.removeData( target, "datepicker" );
		if ( nodeName === "input" ) {
			inst.append.remove();
			inst.trigger.remove();
			$target.removeClass( this.markerClassName ).
				off( "focus", this._showDatepicker ).
				off( "keydown", this._doKeyDown ).
				off( "keypress", this._doKeyPress ).
				off( "keyup", this._doKeyUp );
		} else if ( nodeName === "div" || nodeName === "span" ) {
			$target.removeClass( this.markerClassName ).empty();
		}

		if ( datepicker_instActive === inst ) {
			datepicker_instActive = null;
		}
	},

	/* Enable the date picker to a jQuery selection.
	 * @param  target	element - the target input field or division or span
	 */
	_enableDatepicker: function( target ) {
		var nodeName, inline,
			$target = $( target ),
			inst = $.data( target, "datepicker" );

		if ( !$target.hasClass( this.markerClassName ) ) {
			return;
		}

		nodeName = target.nodeName.toLowerCase();
		if ( nodeName === "input" ) {
			target.disabled = false;
			inst.trigger.filter( "button" ).
				each( function() { this.disabled = false; } ).end().
				filter( "img" ).css( { opacity: "1.0", cursor: "" } );
		} else if ( nodeName === "div" || nodeName === "span" ) {
			inline = $target.children( "." + this._inlineClass );
			inline.children().removeClass( "ui-state-disabled" );
			inline.find( "select.ui-datepicker-month, select.ui-datepicker-year" ).
				prop( "disabled", false );
		}
		this._disabledInputs = $.map( this._disabledInputs,
			function( value ) { return ( value === target ? null : value ); } ); // delete entry
	},

	/* Disable the date picker to a jQuery selection.
	 * @param  target	element - the target input field or division or span
	 */
	_disableDatepicker: function( target ) {
		var nodeName, inline,
			$target = $( target ),
			inst = $.data( target, "datepicker" );

		if ( !$target.hasClass( this.markerClassName ) ) {
			return;
		}

		nodeName = target.nodeName.toLowerCase();
		if ( nodeName === "input" ) {
			target.disabled = true;
			inst.trigger.filter( "button" ).
				each( function() { this.disabled = true; } ).end().
				filter( "img" ).css( { opacity: "0.5", cursor: "default" } );
		} else if ( nodeName === "div" || nodeName === "span" ) {
			inline = $target.children( "." + this._inlineClass );
			inline.children().addClass( "ui-state-disabled" );
			inline.find( "select.ui-datepicker-month, select.ui-datepicker-year" ).
				prop( "disabled", true );
		}
		this._disabledInputs = $.map( this._disabledInputs,
			function( value ) { return ( value === target ? null : value ); } ); // delete entry
		this._disabledInputs[ this._disabledInputs.length ] = target;
	},

	/* Is the first field in a jQuery collection disabled as a datepicker?
	 * @param  target	element - the target input field or division or span
	 * @return boolean - true if disabled, false if enabled
	 */
	_isDisabledDatepicker: function( target ) {
		if ( !target ) {
			return false;
		}
		for ( var i = 0; i < this._disabledInputs.length; i++ ) {
			if ( this._disabledInputs[ i ] === target ) {
				return true;
			}
		}
		return false;
	},

	/* Retrieve the instance data for the target control.
	 * @param  target  element - the target input field or division or span
	 * @return  object - the associated instance data
	 * @throws  error if a jQuery problem getting data
	 */
	_getInst: function( target ) {
		try {
			return $.data( target, "datepicker" );
		}
		catch ( err ) {
			throw "Missing instance data for this datepicker";
		}
	},

	/* Update or retrieve the settings for a date picker attached to an input field or division.
	 * @param  target  element - the target input field or division or span
	 * @param  name	object - the new settings to update or
	 *				string - the name of the setting to change or retrieve,
	 *				when retrieving also "all" for all instance settings or
	 *				"defaults" for all global defaults
	 * @param  value   any - the new value for the setting
	 *				(omit if above is an object or to retrieve a value)
	 */
	_optionDatepicker: function( target, name, value ) {
		var settings, date, minDate, maxDate,
			inst = this._getInst( target );

		if ( arguments.length === 2 && typeof name === "string" ) {
			return ( name === "defaults" ? $.extend( {}, $.datepicker._defaults ) :
				( inst ? ( name === "all" ? $.extend( {}, inst.settings ) :
				this._get( inst, name ) ) : null ) );
		}

		settings = name || {};
		if ( typeof name === "string" ) {
			settings = {};
			settings[ name ] = value;
		}

		if ( inst ) {
			if ( this._curInst === inst ) {
				this._hideDatepicker();
			}

			date = this._getDateDatepicker( target, true );
			minDate = this._getMinMaxDate( inst, "min" );
			maxDate = this._getMinMaxDate( inst, "max" );
			datepicker_extendRemove( inst.settings, settings );

			// reformat the old minDate/maxDate values if dateFormat changes and a new minDate/maxDate isn't provided
			if ( minDate !== null && settings.dateFormat !== undefined && settings.minDate === undefined ) {
				inst.settings.minDate = this._formatDate( inst, minDate );
			}
			if ( maxDate !== null && settings.dateFormat !== undefined && settings.maxDate === undefined ) {
				inst.settings.maxDate = this._formatDate( inst, maxDate );
			}
			if ( "disabled" in settings ) {
				if ( settings.disabled ) {
					this._disableDatepicker( target );
				} else {
					this._enableDatepicker( target );
				}
			}
			this._attachments( $( target ), inst );
			this._autoSize( inst );
			this._setDate( inst, date );
			this._updateAlternate( inst );
			this._updateDatepicker( inst );
		}
	},

	// Change method deprecated
	_changeDatepicker: function( target, name, value ) {
		this._optionDatepicker( target, name, value );
	},

	/* Redraw the date picker attached to an input field or division.
	 * @param  target  element - the target input field or division or span
	 */
	_refreshDatepicker: function( target ) {
		var inst = this._getInst( target );
		if ( inst ) {
			this._updateDatepicker( inst );
		}
	},

	/* Set the dates for a jQuery selection.
	 * @param  target element - the target input field or division or span
	 * @param  date	Date - the new date
	 */
	_setDateDatepicker: function( target, date ) {
		var inst = this._getInst( target );
		if ( inst ) {
			this._setDate( inst, date );
			this._updateDatepicker( inst );
			this._updateAlternate( inst );
		}
	},

	/* Get the date(s) for the first entry in a jQuery selection.
	 * @param  target element - the target input field or division or span
	 * @param  noDefault boolean - true if no default date is to be used
	 * @return Date - the current date
	 */
	_getDateDatepicker: function( target, noDefault ) {
		var inst = this._getInst( target );
		if ( inst && !inst.inline ) {
			this._setDateFromField( inst, noDefault );
		}
		return ( inst ? this._getDate( inst ) : null );
	},

	/* Handle keystrokes. */
	_doKeyDown: function( event ) {
		var onSelect, dateStr, sel,
			inst = $.datepicker._getInst( event.target ),
			handled = true,
			isRTL = inst.dpDiv.is( ".ui-datepicker-rtl" );

		inst._keyEvent = true;
		if ( $.datepicker._datepickerShowing ) {
			switch ( event.keyCode ) {
				case 9: $.datepicker._hideDatepicker();
						handled = false;
						break; // hide on tab out
				case 13: sel = $( "td." + $.datepicker._dayOverClass + ":not(." +
									$.datepicker._currentClass + ")", inst.dpDiv );
						if ( sel[ 0 ] ) {
							$.datepicker._selectDay( event.target, inst.selectedMonth, inst.selectedYear, sel[ 0 ] );
						}

						onSelect = $.datepicker._get( inst, "onSelect" );
						if ( onSelect ) {
							dateStr = $.datepicker._formatDate( inst );

							// Trigger custom callback
							onSelect.apply( ( inst.input ? inst.input[ 0 ] : null ), [ dateStr, inst ] );
						} else {
							$.datepicker._hideDatepicker();
						}

						return false; // don't submit the form
				case 27: $.datepicker._hideDatepicker();
						break; // hide on escape
				case 33: $.datepicker._adjustDate( event.target, ( event.ctrlKey ?
							-$.datepicker._get( inst, "stepBigMonths" ) :
							-$.datepicker._get( inst, "stepMonths" ) ), "M" );
						break; // previous month/year on page up/+ ctrl
				case 34: $.datepicker._adjustDate( event.target, ( event.ctrlKey ?
							+$.datepicker._get( inst, "stepBigMonths" ) :
							+$.datepicker._get( inst, "stepMonths" ) ), "M" );
						break; // next month/year on page down/+ ctrl
				case 35: if ( event.ctrlKey || event.metaKey ) {
							$.datepicker._clearDate( event.target );
						}
						handled = event.ctrlKey || event.metaKey;
						break; // clear on ctrl or command +end
				case 36: if ( event.ctrlKey || event.metaKey ) {
							$.datepicker._gotoToday( event.target );
						}
						handled = event.ctrlKey || event.metaKey;
						break; // current on ctrl or command +home
				case 37: if ( event.ctrlKey || event.metaKey ) {
							$.datepicker._adjustDate( event.target, ( isRTL ? +1 : -1 ), "D" );
						}
						handled = event.ctrlKey || event.metaKey;

						// -1 day on ctrl or command +left
						if ( event.originalEvent.altKey ) {
							$.datepicker._adjustDate( event.target, ( event.ctrlKey ?
								-$.datepicker._get( inst, "stepBigMonths" ) :
								-$.datepicker._get( inst, "stepMonths" ) ), "M" );
						}

						// next month/year on alt +left on Mac
						break;
				case 38: if ( event.ctrlKey || event.metaKey ) {
							$.datepicker._adjustDate( event.target, -7, "D" );
						}
						handled = event.ctrlKey || event.metaKey;
						break; // -1 week on ctrl or command +up
				case 39: if ( event.ctrlKey || event.metaKey ) {
							$.datepicker._adjustDate( event.target, ( isRTL ? -1 : +1 ), "D" );
						}
						handled = event.ctrlKey || event.metaKey;

						// +1 day on ctrl or command +right
						if ( event.originalEvent.altKey ) {
							$.datepicker._adjustDate( event.target, ( event.ctrlKey ?
								+$.datepicker._get( inst, "stepBigMonths" ) :
								+$.datepicker._get( inst, "stepMonths" ) ), "M" );
						}

						// next month/year on alt +right
						break;
				case 40: if ( event.ctrlKey || event.metaKey ) {
							$.datepicker._adjustDate( event.target, +7, "D" );
						}
						handled = event.ctrlKey || event.metaKey;
						break; // +1 week on ctrl or command +down
				default: handled = false;
			}
		} else if ( event.keyCode === 36 && event.ctrlKey ) { // display the date picker on ctrl+home
			$.datepicker._showDatepicker( this );
		} else {
			handled = false;
		}

		if ( handled ) {
			event.preventDefault();
			event.stopPropagation();
		}
	},

	/* Filter entered characters - based on date format. */
	_doKeyPress: function( event ) {
		var chars, chr,
			inst = $.datepicker._getInst( event.target );

		if ( $.datepicker._get( inst, "constrainInput" ) ) {
			chars = $.datepicker._possibleChars( $.datepicker._get( inst, "dateFormat" ) );
			chr = String.fromCharCode( event.charCode == null ? event.keyCode : event.charCode );
			return event.ctrlKey || event.metaKey || ( chr < " " || !chars || chars.indexOf( chr ) > -1 );
		}
	},

	/* Synchronise manual entry and field/alternate field. */
	_doKeyUp: function( event ) {
		var date,
			inst = $.datepicker._getInst( event.target );

		if ( inst.input.val() !== inst.lastVal ) {
			try {
				date = $.datepicker.parseDate( $.datepicker._get( inst, "dateFormat" ),
					( inst.input ? inst.input.val() : null ),
					$.datepicker._getFormatConfig( inst ) );

				if ( date ) { // only if valid
					$.datepicker._setDateFromField( inst );
					$.datepicker._updateAlternate( inst );
					$.datepicker._updateDatepicker( inst );
				}
			}
			catch ( err ) {
			}
		}
		return true;
	},

	/* Pop-up the date picker for a given input field.
	 * If false returned from beforeShow event handler do not show.
	 * @param  input  element - the input field attached to the date picker or
	 *					event - if triggered by focus
	 */
	_showDatepicker: function( input ) {
		input = input.target || input;
		if ( input.nodeName.toLowerCase() !== "input" ) { // find from button/image trigger
			input = $( "input", input.parentNode )[ 0 ];
		}

		if ( $.datepicker._isDisabledDatepicker( input ) || $.datepicker._lastInput === input ) { // already here
			return;
		}

		var inst, beforeShow, beforeShowSettings, isFixed,
			offset, showAnim, duration;

		inst = $.datepicker._getInst( input );
		if ( $.datepicker._curInst && $.datepicker._curInst !== inst ) {
			$.datepicker._curInst.dpDiv.stop( true, true );
			if ( inst && $.datepicker._datepickerShowing ) {
				$.datepicker._hideDatepicker( $.datepicker._curInst.input[ 0 ] );
			}
		}

		beforeShow = $.datepicker._get( inst, "beforeShow" );
		beforeShowSettings = beforeShow ? beforeShow.apply( input, [ input, inst ] ) : {};
		if ( beforeShowSettings === false ) {
			return;
		}
		datepicker_extendRemove( inst.settings, beforeShowSettings );

		inst.lastVal = null;
		$.datepicker._lastInput = input;
		$.datepicker._setDateFromField( inst );

		if ( $.datepicker._inDialog ) { // hide cursor
			input.value = "";
		}
		if ( !$.datepicker._pos ) { // position below input
			$.datepicker._pos = $.datepicker._findPos( input );
			$.datepicker._pos[ 1 ] += input.offsetHeight; // add the height
		}

		isFixed = false;
		$( input ).parents().each( function() {
			isFixed |= $( this ).css( "position" ) === "fixed";
			return !isFixed;
		} );

		offset = { left: $.datepicker._pos[ 0 ], top: $.datepicker._pos[ 1 ] };
		$.datepicker._pos = null;

		//to avoid flashes on Firefox
		inst.dpDiv.empty();

		// determine sizing offscreen
		inst.dpDiv.css( { position: "absolute", display: "block", top: "-1000px" } );
		$.datepicker._updateDatepicker( inst );

		// fix width for dynamic number of date pickers
		// and adjust position before showing
		offset = $.datepicker._checkOffset( inst, offset, isFixed );
		inst.dpDiv.css( { position: ( $.datepicker._inDialog && $.blockUI ?
			"static" : ( isFixed ? "fixed" : "absolute" ) ), display: "none",
			left: offset.left + "px", top: offset.top + "px" } );

		if ( !inst.inline ) {
			showAnim = $.datepicker._get( inst, "showAnim" );
			duration = $.datepicker._get( inst, "duration" );
			inst.dpDiv.css( "z-index", datepicker_getZindex( $( input ) ) + 1 );
			$.datepicker._datepickerShowing = true;

			if ( $.effects && $.effects.effect[ showAnim ] ) {
				inst.dpDiv.show( showAnim, $.datepicker._get( inst, "showOptions" ), duration );
			} else {
				inst.dpDiv[ showAnim || "show" ]( showAnim ? duration : null );
			}

			if ( $.datepicker._shouldFocusInput( inst ) ) {
				inst.input.trigger( "focus" );
			}

			$.datepicker._curInst = inst;
		}
	},

	/* Generate the date picker content. */
	_updateDatepicker: function( inst ) {
		this.maxRows = 4; //Reset the max number of rows being displayed (see #7043)
		datepicker_instActive = inst; // for delegate hover events
		inst.dpDiv.empty().append( this._generateHTML( inst ) );
		this._attachHandlers( inst );

		var origyearshtml,
			numMonths = this._getNumberOfMonths( inst ),
			cols = numMonths[ 1 ],
			width = 17,
			activeCell = inst.dpDiv.find( "." + this._dayOverClass + " a" );

		if ( activeCell.length > 0 ) {
			datepicker_handleMouseover.apply( activeCell.get( 0 ) );
		}

		inst.dpDiv.removeClass( "ui-datepicker-multi-2 ui-datepicker-multi-3 ui-datepicker-multi-4" ).width( "" );
		if ( cols > 1 ) {
			inst.dpDiv.addClass( "ui-datepicker-multi-" + cols ).css( "width", ( width * cols ) + "em" );
		}
		inst.dpDiv[ ( numMonths[ 0 ] !== 1 || numMonths[ 1 ] !== 1 ? "add" : "remove" ) +
			"Class" ]( "ui-datepicker-multi" );
		inst.dpDiv[ ( this._get( inst, "isRTL" ) ? "add" : "remove" ) +
			"Class" ]( "ui-datepicker-rtl" );

		if ( inst === $.datepicker._curInst && $.datepicker._datepickerShowing && $.datepicker._shouldFocusInput( inst ) ) {
			inst.input.trigger( "focus" );
		}

		// Deffered render of the years select (to avoid flashes on Firefox)
		if ( inst.yearshtml ) {
			origyearshtml = inst.yearshtml;
			setTimeout( function() {

				//assure that inst.yearshtml didn't change.
				if ( origyearshtml === inst.yearshtml && inst.yearshtml ) {
					inst.dpDiv.find( "select.ui-datepicker-year:first" ).replaceWith( inst.yearshtml );
				}
				origyearshtml = inst.yearshtml = null;
			}, 0 );
		}
	},

	// #6694 - don't focus the input if it's already focused
	// this breaks the change event in IE
	// Support: IE and jQuery <1.9
	_shouldFocusInput: function( inst ) {
		return inst.input && inst.input.is( ":visible" ) && !inst.input.is( ":disabled" ) && !inst.input.is( ":focus" );
	},

	/* Check positioning to remain on screen. */
	_checkOffset: function( inst, offset, isFixed ) {
		var dpWidth = inst.dpDiv.outerWidth(),
			dpHeight = inst.dpDiv.outerHeight(),
			inputWidth = inst.input ? inst.input.outerWidth() : 0,
			inputHeight = inst.input ? inst.input.outerHeight() : 0,
			viewWidth = document.documentElement.clientWidth + ( isFixed ? 0 : $( document ).scrollLeft() ),
			viewHeight = document.documentElement.clientHeight + ( isFixed ? 0 : $( document ).scrollTop() );

		offset.left -= ( this._get( inst, "isRTL" ) ? ( dpWidth - inputWidth ) : 0 );
		offset.left -= ( isFixed && offset.left === inst.input.offset().left ) ? $( document ).scrollLeft() : 0;
		offset.top -= ( isFixed && offset.top === ( inst.input.offset().top + inputHeight ) ) ? $( document ).scrollTop() : 0;

		// Now check if datepicker is showing outside window viewport - move to a better place if so.
		offset.left -= Math.min( offset.left, ( offset.left + dpWidth > viewWidth && viewWidth > dpWidth ) ?
			Math.abs( offset.left + dpWidth - viewWidth ) : 0 );
		offset.top -= Math.min( offset.top, ( offset.top + dpHeight > viewHeight && viewHeight > dpHeight ) ?
			Math.abs( dpHeight + inputHeight ) : 0 );

		return offset;
	},

	/* Find an object's position on the screen. */
	_findPos: function( obj ) {
		var position,
			inst = this._getInst( obj ),
			isRTL = this._get( inst, "isRTL" );

		while ( obj && ( obj.type === "hidden" || obj.nodeType !== 1 || $.expr.filters.hidden( obj ) ) ) {
			obj = obj[ isRTL ? "previousSibling" : "nextSibling" ];
		}

		position = $( obj ).offset();
		return [ position.left, position.top ];
	},

	/* Hide the date picker from view.
	 * @param  input  element - the input field attached to the date picker
	 */
	_hideDatepicker: function( input ) {
		var showAnim, duration, postProcess, onClose,
			inst = this._curInst;

		if ( !inst || ( input && inst !== $.data( input, "datepicker" ) ) ) {
			return;
		}

		if ( this._datepickerShowing ) {
			showAnim = this._get( inst, "showAnim" );
			duration = this._get( inst, "duration" );
			postProcess = function() {
				$.datepicker._tidyDialog( inst );
			};

			// DEPRECATED: after BC for 1.8.x $.effects[ showAnim ] is not needed
			if ( $.effects && ( $.effects.effect[ showAnim ] || $.effects[ showAnim ] ) ) {
				inst.dpDiv.hide( showAnim, $.datepicker._get( inst, "showOptions" ), duration, postProcess );
			} else {
				inst.dpDiv[ ( showAnim === "slideDown" ? "slideUp" :
					( showAnim === "fadeIn" ? "fadeOut" : "hide" ) ) ]( ( showAnim ? duration : null ), postProcess );
			}

			if ( !showAnim ) {
				postProcess();
			}
			this._datepickerShowing = false;

			onClose = this._get( inst, "onClose" );
			if ( onClose ) {
				onClose.apply( ( inst.input ? inst.input[ 0 ] : null ), [ ( inst.input ? inst.input.val() : "" ), inst ] );
			}

			this._lastInput = null;
			if ( this._inDialog ) {
				this._dialogInput.css( { position: "absolute", left: "0", top: "-100px" } );
				if ( $.blockUI ) {
					$.unblockUI();
					$( "body" ).append( this.dpDiv );
				}
			}
			this._inDialog = false;
		}
	},

	/* Tidy up after a dialog display. */
	_tidyDialog: function( inst ) {
		inst.dpDiv.removeClass( this._dialogClass ).off( ".ui-datepicker-calendar" );
	},

	/* Close date picker if clicked elsewhere. */
	_checkExternalClick: function( event ) {
		if ( !$.datepicker._curInst ) {
			return;
		}

		var $target = $( event.target ),
			inst = $.datepicker._getInst( $target[ 0 ] );

		if ( ( ( $target[ 0 ].id !== $.datepicker._mainDivId &&
				$target.parents( "#" + $.datepicker._mainDivId ).length === 0 &&
				!$target.hasClass( $.datepicker.markerClassName ) &&
				!$target.closest( "." + $.datepicker._triggerClass ).length &&
				$.datepicker._datepickerShowing && !( $.datepicker._inDialog && $.blockUI ) ) ) ||
			( $target.hasClass( $.datepicker.markerClassName ) && $.datepicker._curInst !== inst ) ) {
				$.datepicker._hideDatepicker();
		}
	},

	/* Adjust one of the date sub-fields. */
	_adjustDate: function( id, offset, period ) {
		var target = $( id ),
			inst = this._getInst( target[ 0 ] );

		if ( this._isDisabledDatepicker( target[ 0 ] ) ) {
			return;
		}
		this._adjustInstDate( inst, offset +
			( period === "M" ? this._get( inst, "showCurrentAtPos" ) : 0 ), // undo positioning
			period );
		this._updateDatepicker( inst );
	},

	/* Action for current link. */
	_gotoToday: function( id ) {
		var date,
			target = $( id ),
			inst = this._getInst( target[ 0 ] );

		if ( this._get( inst, "gotoCurrent" ) && inst.currentDay ) {
			inst.selectedDay = inst.currentDay;
			inst.drawMonth = inst.selectedMonth = inst.currentMonth;
			inst.drawYear = inst.selectedYear = inst.currentYear;
		} else {
			date = new Date();
			inst.selectedDay = date.getDate();
			inst.drawMonth = inst.selectedMonth = date.getMonth();
			inst.drawYear = inst.selectedYear = date.getFullYear();
		}
		this._notifyChange( inst );
		this._adjustDate( target );
	},

	/* Action for selecting a new month/year. */
	_selectMonthYear: function( id, select, period ) {
		var target = $( id ),
			inst = this._getInst( target[ 0 ] );

		inst[ "selected" + ( period === "M" ? "Month" : "Year" ) ] =
		inst[ "draw" + ( period === "M" ? "Month" : "Year" ) ] =
			parseInt( select.options[ select.selectedIndex ].value, 10 );

		this._notifyChange( inst );
		this._adjustDate( target );
	},

	/* Action for selecting a day. */
	_selectDay: function( id, month, year, td ) {
		var inst,
			target = $( id );

		if ( $( td ).hasClass( this._unselectableClass ) || this._isDisabledDatepicker( target[ 0 ] ) ) {
			return;
		}

		inst = this._getInst( target[ 0 ] );
		inst.selectedDay = inst.currentDay = $( "a", td ).html();
		inst.selectedMonth = inst.currentMonth = month;
		inst.selectedYear = inst.currentYear = year;
		this._selectDate( id, this._formatDate( inst,
			inst.currentDay, inst.currentMonth, inst.currentYear ) );
	},

	/* Erase the input field and hide the date picker. */
	_clearDate: function( id ) {
		var target = $( id );
		this._selectDate( target, "" );
	},

	/* Update the input field with the selected date. */
	_selectDate: function( id, dateStr ) {
		var onSelect,
			target = $( id ),
			inst = this._getInst( target[ 0 ] );

		dateStr = ( dateStr != null ? dateStr : this._formatDate( inst ) );
		if ( inst.input ) {
			inst.input.val( dateStr );
		}
		this._updateAlternate( inst );

		onSelect = this._get( inst, "onSelect" );
		if ( onSelect ) {
			onSelect.apply( ( inst.input ? inst.input[ 0 ] : null ), [ dateStr, inst ] );  // trigger custom callback
		} else if ( inst.input ) {
			inst.input.trigger( "change" ); // fire the change event
		}

		if ( inst.inline ) {
			this._updateDatepicker( inst );
		} else {
			this._hideDatepicker();
			this._lastInput = inst.input[ 0 ];
			if ( typeof( inst.input[ 0 ] ) !== "object" ) {
				inst.input.trigger( "focus" ); // restore focus
			}
			this._lastInput = null;
		}
	},

	/* Update any alternate field to synchronise with the main field. */
	_updateAlternate: function( inst ) {
		var altFormat, date, dateStr,
			altField = this._get( inst, "altField" );

		if ( altField ) { // update alternate field too
			altFormat = this._get( inst, "altFormat" ) || this._get( inst, "dateFormat" );
			date = this._getDate( inst );
			dateStr = this.formatDate( altFormat, date, this._getFormatConfig( inst ) );
			$( altField ).val( dateStr );
		}
	},

	/* Set as beforeShowDay function to prevent selection of weekends.
	 * @param  date  Date - the date to customise
	 * @return [boolean, string] - is this date selectable?, what is its CSS class?
	 */
	noWeekends: function( date ) {
		var day = date.getDay();
		return [ ( day > 0 && day < 6 ), "" ];
	},

	/* Set as calculateWeek to determine the week of the year based on the ISO 8601 definition.
	 * @param  date  Date - the date to get the week for
	 * @return  number - the number of the week within the year that contains this date
	 */
	iso8601Week: function( date ) {
		var time,
			checkDate = new Date( date.getTime() );

		// Find Thursday of this week starting on Monday
		checkDate.setDate( checkDate.getDate() + 4 - ( checkDate.getDay() || 7 ) );

		time = checkDate.getTime();
		checkDate.setMonth( 0 ); // Compare with Jan 1
		checkDate.setDate( 1 );
		return Math.floor( Math.round( ( time - checkDate ) / 86400000 ) / 7 ) + 1;
	},

	/* Parse a string value into a date object.
	 * See formatDate below for the possible formats.
	 *
	 * @param  format string - the expected format of the date
	 * @param  value string - the date in the above format
	 * @param  settings Object - attributes include:
	 *					shortYearCutoff  number - the cutoff year for determining the century (optional)
	 *					dayNamesShort	string[7] - abbreviated names of the days from Sunday (optional)
	 *					dayNames		string[7] - names of the days from Sunday (optional)
	 *					monthNamesShort string[12] - abbreviated names of the months (optional)
	 *					monthNames		string[12] - names of the months (optional)
	 * @return  Date - the extracted date value or null if value is blank
	 */
	parseDate: function( format, value, settings ) {
		if ( format == null || value == null ) {
			throw "Invalid arguments";
		}

		value = ( typeof value === "object" ? value.toString() : value + "" );
		if ( value === "" ) {
			return null;
		}

		var iFormat, dim, extra,
			iValue = 0,
			shortYearCutoffTemp = ( settings ? settings.shortYearCutoff : null ) || this._defaults.shortYearCutoff,
			shortYearCutoff = ( typeof shortYearCutoffTemp !== "string" ? shortYearCutoffTemp :
				new Date().getFullYear() % 100 + parseInt( shortYearCutoffTemp, 10 ) ),
			dayNamesShort = ( settings ? settings.dayNamesShort : null ) || this._defaults.dayNamesShort,
			dayNames = ( settings ? settings.dayNames : null ) || this._defaults.dayNames,
			monthNamesShort = ( settings ? settings.monthNamesShort : null ) || this._defaults.monthNamesShort,
			monthNames = ( settings ? settings.monthNames : null ) || this._defaults.monthNames,
			year = -1,
			month = -1,
			day = -1,
			doy = -1,
			literal = false,
			date,

			// Check whether a format character is doubled
			lookAhead = function( match ) {
				var matches = ( iFormat + 1 < format.length && format.charAt( iFormat + 1 ) === match );
				if ( matches ) {
					iFormat++;
				}
				return matches;
			},

			// Extract a number from the string value
			getNumber = function( match ) {
				var isDoubled = lookAhead( match ),
					size = ( match === "@" ? 14 : ( match === "!" ? 20 :
					( match === "y" && isDoubled ? 4 : ( match === "o" ? 3 : 2 ) ) ) ),
					minSize = ( match === "y" ? size : 1 ),
					digits = new RegExp( "^\\d{" + minSize + "," + size + "}" ),
					num = value.substring( iValue ).match( digits );
				if ( !num ) {
					throw "Missing number at position " + iValue;
				}
				iValue += num[ 0 ].length;
				return parseInt( num[ 0 ], 10 );
			},

			// Extract a name from the string value and convert to an index
			getName = function( match, shortNames, longNames ) {
				var index = -1,
					names = $.map( lookAhead( match ) ? longNames : shortNames, function( v, k ) {
						return [ [ k, v ] ];
					} ).sort( function( a, b ) {
						return -( a[ 1 ].length - b[ 1 ].length );
					} );

				$.each( names, function( i, pair ) {
					var name = pair[ 1 ];
					if ( value.substr( iValue, name.length ).toLowerCase() === name.toLowerCase() ) {
						index = pair[ 0 ];
						iValue += name.length;
						return false;
					}
				} );
				if ( index !== -1 ) {
					return index + 1;
				} else {
					throw "Unknown name at position " + iValue;
				}
			},

			// Confirm that a literal character matches the string value
			checkLiteral = function() {
				if ( value.charAt( iValue ) !== format.charAt( iFormat ) ) {
					throw "Unexpected literal at position " + iValue;
				}
				iValue++;
			};

		for ( iFormat = 0; iFormat < format.length; iFormat++ ) {
			if ( literal ) {
				if ( format.charAt( iFormat ) === "'" && !lookAhead( "'" ) ) {
					literal = false;
				} else {
					checkLiteral();
				}
			} else {
				switch ( format.charAt( iFormat ) ) {
					case "d":
						day = getNumber( "d" );
						break;
					case "D":
						getName( "D", dayNamesShort, dayNames );
						break;
					case "o":
						doy = getNumber( "o" );
						break;
					case "m":
						month = getNumber( "m" );
						break;
					case "M":
						month = getName( "M", monthNamesShort, monthNames );
						break;
					case "y":
						year = getNumber( "y" );
						break;
					case "@":
						date = new Date( getNumber( "@" ) );
						year = date.getFullYear();
						month = date.getMonth() + 1;
						day = date.getDate();
						break;
					case "!":
						date = new Date( ( getNumber( "!" ) - this._ticksTo1970 ) / 10000 );
						year = date.getFullYear();
						month = date.getMonth() + 1;
						day = date.getDate();
						break;
					case "'":
						if ( lookAhead( "'" ) ) {
							checkLiteral();
						} else {
							literal = true;
						}
						break;
					default:
						checkLiteral();
				}
			}
		}

		if ( iValue < value.length ) {
			extra = value.substr( iValue );
			if ( !/^\s+/.test( extra ) ) {
				throw "Extra/unparsed characters found in date: " + extra;
			}
		}

		if ( year === -1 ) {
			year = new Date().getFullYear();
		} else if ( year < 100 ) {
			year += new Date().getFullYear() - new Date().getFullYear() % 100 +
				( year <= shortYearCutoff ? 0 : -100 );
		}

		if ( doy > -1 ) {
			month = 1;
			day = doy;
			do {
				dim = this._getDaysInMonth( year, month - 1 );
				if ( day <= dim ) {
					break;
				}
				month++;
				day -= dim;
			} while ( true );
		}

		date = this._daylightSavingAdjust( new Date( year, month - 1, day ) );
		if ( date.getFullYear() !== year || date.getMonth() + 1 !== month || date.getDate() !== day ) {
			throw "Invalid date"; // E.g. 31/02/00
		}
		return date;
	},

	/* Standard date formats. */
	ATOM: "yy-mm-dd", // RFC 3339 (ISO 8601)
	COOKIE: "D, dd M yy",
	ISO_8601: "yy-mm-dd",
	RFC_822: "D, d M y",
	RFC_850: "DD, dd-M-y",
	RFC_1036: "D, d M y",
	RFC_1123: "D, d M yy",
	RFC_2822: "D, d M yy",
	RSS: "D, d M y", // RFC 822
	TICKS: "!",
	TIMESTAMP: "@",
	W3C: "yy-mm-dd", // ISO 8601

	_ticksTo1970: ( ( ( 1970 - 1 ) * 365 + Math.floor( 1970 / 4 ) - Math.floor( 1970 / 100 ) +
		Math.floor( 1970 / 400 ) ) * 24 * 60 * 60 * 10000000 ),

	/* Format a date object into a string value.
	 * The format can be combinations of the following:
	 * d  - day of month (no leading zero)
	 * dd - day of month (two digit)
	 * o  - day of year (no leading zeros)
	 * oo - day of year (three digit)
	 * D  - day name short
	 * DD - day name long
	 * m  - month of year (no leading zero)
	 * mm - month of year (two digit)
	 * M  - month name short
	 * MM - month name long
	 * y  - year (two digit)
	 * yy - year (four digit)
	 * @ - Unix timestamp (ms since 01/01/1970)
	 * ! - Windows ticks (100ns since 01/01/0001)
	 * "..." - literal text
	 * '' - single quote
	 *
	 * @param  format string - the desired format of the date
	 * @param  date Date - the date value to format
	 * @param  settings Object - attributes include:
	 *					dayNamesShort	string[7] - abbreviated names of the days from Sunday (optional)
	 *					dayNames		string[7] - names of the days from Sunday (optional)
	 *					monthNamesShort string[12] - abbreviated names of the months (optional)
	 *					monthNames		string[12] - names of the months (optional)
	 * @return  string - the date in the above format
	 */
	formatDate: function( format, date, settings ) {
		if ( !date ) {
			return "";
		}

		var iFormat,
			dayNamesShort = ( settings ? settings.dayNamesShort : null ) || this._defaults.dayNamesShort,
			dayNames = ( settings ? settings.dayNames : null ) || this._defaults.dayNames,
			monthNamesShort = ( settings ? settings.monthNamesShort : null ) || this._defaults.monthNamesShort,
			monthNames = ( settings ? settings.monthNames : null ) || this._defaults.monthNames,

			// Check whether a format character is doubled
			lookAhead = function( match ) {
				var matches = ( iFormat + 1 < format.length && format.charAt( iFormat + 1 ) === match );
				if ( matches ) {
					iFormat++;
				}
				return matches;
			},

			// Format a number, with leading zero if necessary
			formatNumber = function( match, value, len ) {
				var num = "" + value;
				if ( lookAhead( match ) ) {
					while ( num.length < len ) {
						num = "0" + num;
					}
				}
				return num;
			},

			// Format a name, short or long as requested
			formatName = function( match, value, shortNames, longNames ) {
				return ( lookAhead( match ) ? longNames[ value ] : shortNames[ value ] );
			},
			output = "",
			literal = false;

		if ( date ) {
			for ( iFormat = 0; iFormat < format.length; iFormat++ ) {
				if ( literal ) {
					if ( format.charAt( iFormat ) === "'" && !lookAhead( "'" ) ) {
						literal = false;
					} else {
						output += format.charAt( iFormat );
					}
				} else {
					switch ( format.charAt( iFormat ) ) {
						case "d":
							output += formatNumber( "d", date.getDate(), 2 );
							break;
						case "D":
							output += formatName( "D", date.getDay(), dayNamesShort, dayNames );
							break;
						case "o":
							output += formatNumber( "o",
								Math.round( ( new Date( date.getFullYear(), date.getMonth(), date.getDate() ).getTime() - new Date( date.getFullYear(), 0, 0 ).getTime() ) / 86400000 ), 3 );
							break;
						case "m":
							output += formatNumber( "m", date.getMonth() + 1, 2 );
							break;
						case "M":
							output += formatName( "M", date.getMonth(), monthNamesShort, monthNames );
							break;
						case "y":
							output += ( lookAhead( "y" ) ? date.getFullYear() :
								( date.getFullYear() % 100 < 10 ? "0" : "" ) + date.getFullYear() % 100 );
							break;
						case "@":
							output += date.getTime();
							break;
						case "!":
							output += date.getTime() * 10000 + this._ticksTo1970;
							break;
						case "'":
							if ( lookAhead( "'" ) ) {
								output += "'";
							} else {
								literal = true;
							}
							break;
						default:
							output += format.charAt( iFormat );
					}
				}
			}
		}
		return output;
	},

	/* Extract all possible characters from the date format. */
	_possibleChars: function( format ) {
		var iFormat,
			chars = "",
			literal = false,

			// Check whether a format character is doubled
			lookAhead = function( match ) {
				var matches = ( iFormat + 1 < format.length && format.charAt( iFormat + 1 ) === match );
				if ( matches ) {
					iFormat++;
				}
				return matches;
			};

		for ( iFormat = 0; iFormat < format.length; iFormat++ ) {
			if ( literal ) {
				if ( format.charAt( iFormat ) === "'" && !lookAhead( "'" ) ) {
					literal = false;
				} else {
					chars += format.charAt( iFormat );
				}
			} else {
				switch ( format.charAt( iFormat ) ) {
					case "d": case "m": case "y": case "@":
						chars += "0123456789";
						break;
					case "D": case "M":
						return null; // Accept anything
					case "'":
						if ( lookAhead( "'" ) ) {
							chars += "'";
						} else {
							literal = true;
						}
						break;
					default:
						chars += format.charAt( iFormat );
				}
			}
		}
		return chars;
	},

	/* Get a setting value, defaulting if necessary. */
	_get: function( inst, name ) {
		return inst.settings[ name ] !== undefined ?
			inst.settings[ name ] : this._defaults[ name ];
	},

	/* Parse existing date and initialise date picker. */
	_setDateFromField: function( inst, noDefault ) {
		if ( inst.input.val() === inst.lastVal ) {
			return;
		}

		var dateFormat = this._get( inst, "dateFormat" ),
			dates = inst.lastVal = inst.input ? inst.input.val() : null,
			defaultDate = this._getDefaultDate( inst ),
			date = defaultDate,
			settings = this._getFormatConfig( inst );

		try {
			date = this.parseDate( dateFormat, dates, settings ) || defaultDate;
		} catch ( event ) {
			dates = ( noDefault ? "" : dates );
		}
		inst.selectedDay = date.getDate();
		inst.drawMonth = inst.selectedMonth = date.getMonth();
		inst.drawYear = inst.selectedYear = date.getFullYear();
		inst.currentDay = ( dates ? date.getDate() : 0 );
		inst.currentMonth = ( dates ? date.getMonth() : 0 );
		inst.currentYear = ( dates ? date.getFullYear() : 0 );
		this._adjustInstDate( inst );
	},

	/* Retrieve the default date shown on opening. */
	_getDefaultDate: function( inst ) {
		return this._restrictMinMax( inst,
			this._determineDate( inst, this._get( inst, "defaultDate" ), new Date() ) );
	},

	/* A date may be specified as an exact value or a relative one. */
	_determineDate: function( inst, date, defaultDate ) {
		var offsetNumeric = function( offset ) {
				var date = new Date();
				date.setDate( date.getDate() + offset );
				return date;
			},
			offsetString = function( offset ) {
				try {
					return $.datepicker.parseDate( $.datepicker._get( inst, "dateFormat" ),
						offset, $.datepicker._getFormatConfig( inst ) );
				}
				catch ( e ) {

					// Ignore
				}

				var date = ( offset.toLowerCase().match( /^c/ ) ?
					$.datepicker._getDate( inst ) : null ) || new Date(),
					year = date.getFullYear(),
					month = date.getMonth(),
					day = date.getDate(),
					pattern = /([+\-]?[0-9]+)\s*(d|D|w|W|m|M|y|Y)?/g,
					matches = pattern.exec( offset );

				while ( matches ) {
					switch ( matches[ 2 ] || "d" ) {
						case "d" : case "D" :
							day += parseInt( matches[ 1 ], 10 ); break;
						case "w" : case "W" :
							day += parseInt( matches[ 1 ], 10 ) * 7; break;
						case "m" : case "M" :
							month += parseInt( matches[ 1 ], 10 );
							day = Math.min( day, $.datepicker._getDaysInMonth( year, month ) );
							break;
						case "y": case "Y" :
							year += parseInt( matches[ 1 ], 10 );
							day = Math.min( day, $.datepicker._getDaysInMonth( year, month ) );
							break;
					}
					matches = pattern.exec( offset );
				}
				return new Date( year, month, day );
			},
			newDate = ( date == null || date === "" ? defaultDate : ( typeof date === "string" ? offsetString( date ) :
				( typeof date === "number" ? ( isNaN( date ) ? defaultDate : offsetNumeric( date ) ) : new Date( date.getTime() ) ) ) );

		newDate = ( newDate && newDate.toString() === "Invalid Date" ? defaultDate : newDate );
		if ( newDate ) {
			newDate.setHours( 0 );
			newDate.setMinutes( 0 );
			newDate.setSeconds( 0 );
			newDate.setMilliseconds( 0 );
		}
		return this._daylightSavingAdjust( newDate );
	},

	/* Handle switch to/from daylight saving.
	 * Hours may be non-zero on daylight saving cut-over:
	 * > 12 when midnight changeover, but then cannot generate
	 * midnight datetime, so jump to 1AM, otherwise reset.
	 * @param  date  (Date) the date to check
	 * @return  (Date) the corrected date
	 */
	_daylightSavingAdjust: function( date ) {
		if ( !date ) {
			return null;
		}
		date.setHours( date.getHours() > 12 ? date.getHours() + 2 : 0 );
		return date;
	},

	/* Set the date(s) directly. */
	_setDate: function( inst, date, noChange ) {
		var clear = !date,
			origMonth = inst.selectedMonth,
			origYear = inst.selectedYear,
			newDate = this._restrictMinMax( inst, this._determineDate( inst, date, new Date() ) );

		inst.selectedDay = inst.currentDay = newDate.getDate();
		inst.drawMonth = inst.selectedMonth = inst.currentMonth = newDate.getMonth();
		inst.drawYear = inst.selectedYear = inst.currentYear = newDate.getFullYear();
		if ( ( origMonth !== inst.selectedMonth || origYear !== inst.selectedYear ) && !noChange ) {
			this._notifyChange( inst );
		}
		this._adjustInstDate( inst );
		if ( inst.input ) {
			inst.input.val( clear ? "" : this._formatDate( inst ) );
		}
	},

	/* Retrieve the date(s) directly. */
	_getDate: function( inst ) {
		var startDate = ( !inst.currentYear || ( inst.input && inst.input.val() === "" ) ? null :
			this._daylightSavingAdjust( new Date(
			inst.currentYear, inst.currentMonth, inst.currentDay ) ) );
			return startDate;
	},

	/* Attach the onxxx handlers.  These are declared statically so
	 * they work with static code transformers like Caja.
	 */
	_attachHandlers: function( inst ) {
		var stepMonths = this._get( inst, "stepMonths" ),
			id = "#" + inst.id.replace( /\\\\/g, "\\" );
		inst.dpDiv.find( "[data-handler]" ).map( function() {
			var handler = {
				prev: function() {
					$.datepicker._adjustDate( id, -stepMonths, "M" );
				},
				next: function() {
					$.datepicker._adjustDate( id, +stepMonths, "M" );
				},
				hide: function() {
					$.datepicker._hideDatepicker();
				},
				today: function() {
					$.datepicker._gotoToday( id );
				},
				selectDay: function() {
					$.datepicker._selectDay( id, +this.getAttribute( "data-month" ), +this.getAttribute( "data-year" ), this );
					return false;
				},
				selectMonth: function() {
					$.datepicker._selectMonthYear( id, this, "M" );
					return false;
				},
				selectYear: function() {
					$.datepicker._selectMonthYear( id, this, "Y" );
					return false;
				}
			};
			$( this ).on( this.getAttribute( "data-event" ), handler[ this.getAttribute( "data-handler" ) ] );
		} );
	},

	/* Generate the HTML for the current state of the date picker. */
	_generateHTML: function( inst ) {
		var maxDraw, prevText, prev, nextText, next, currentText, gotoDate,
			controls, buttonPanel, firstDay, showWeek, dayNames, dayNamesMin,
			monthNames, monthNamesShort, beforeShowDay, showOtherMonths,
			selectOtherMonths, defaultDate, html, dow, row, group, col, selectedDate,
			cornerClass, calender, thead, day, daysInMonth, leadDays, curRows, numRows,
			printDate, dRow, tbody, daySettings, otherMonth, unselectable,
			tempDate = new Date(),
			today = this._daylightSavingAdjust(
				new Date( tempDate.getFullYear(), tempDate.getMonth(), tempDate.getDate() ) ), // clear time
			isRTL = this._get( inst, "isRTL" ),
			showButtonPanel = this._get( inst, "showButtonPanel" ),
			hideIfNoPrevNext = this._get( inst, "hideIfNoPrevNext" ),
			navigationAsDateFormat = this._get( inst, "navigationAsDateFormat" ),
			numMonths = this._getNumberOfMonths( inst ),
			showCurrentAtPos = this._get( inst, "showCurrentAtPos" ),
			stepMonths = this._get( inst, "stepMonths" ),
			isMultiMonth = ( numMonths[ 0 ] !== 1 || numMonths[ 1 ] !== 1 ),
			currentDate = this._daylightSavingAdjust( ( !inst.currentDay ? new Date( 9999, 9, 9 ) :
				new Date( inst.currentYear, inst.currentMonth, inst.currentDay ) ) ),
			minDate = this._getMinMaxDate( inst, "min" ),
			maxDate = this._getMinMaxDate( inst, "max" ),
			drawMonth = inst.drawMonth - showCurrentAtPos,
			drawYear = inst.drawYear;

		if ( drawMonth < 0 ) {
			drawMonth += 12;
			drawYear--;
		}
		if ( maxDate ) {
			maxDraw = this._daylightSavingAdjust( new Date( maxDate.getFullYear(),
				maxDate.getMonth() - ( numMonths[ 0 ] * numMonths[ 1 ] ) + 1, maxDate.getDate() ) );
			maxDraw = ( minDate && maxDraw < minDate ? minDate : maxDraw );
			while ( this._daylightSavingAdjust( new Date( drawYear, drawMonth, 1 ) ) > maxDraw ) {
				drawMonth--;
				if ( drawMonth < 0 ) {
					drawMonth = 11;
					drawYear--;
				}
			}
		}
		inst.drawMonth = drawMonth;
		inst.drawYear = drawYear;

		prevText = this._get( inst, "prevText" );
		prevText = ( !navigationAsDateFormat ? prevText : this.formatDate( prevText,
			this._daylightSavingAdjust( new Date( drawYear, drawMonth - stepMonths, 1 ) ),
			this._getFormatConfig( inst ) ) );

		prev = ( this._canAdjustMonth( inst, -1, drawYear, drawMonth ) ?
			"<a class='ui-datepicker-prev ui-corner-all' data-handler='prev' data-event='click'" +
			" title='" + prevText + "'><span class='ui-icon ui-icon-circle-triangle-" + ( isRTL ? "e" : "w" ) + "'>" + prevText + "</span></a>" :
			( hideIfNoPrevNext ? "" : "<a class='ui-datepicker-prev ui-corner-all ui-state-disabled' title='" + prevText + "'><span class='ui-icon ui-icon-circle-triangle-" + ( isRTL ? "e" : "w" ) + "'>" + prevText + "</span></a>" ) );

		nextText = this._get( inst, "nextText" );
		nextText = ( !navigationAsDateFormat ? nextText : this.formatDate( nextText,
			this._daylightSavingAdjust( new Date( drawYear, drawMonth + stepMonths, 1 ) ),
			this._getFormatConfig( inst ) ) );

		next = ( this._canAdjustMonth( inst, +1, drawYear, drawMonth ) ?
			"<a class='ui-datepicker-next ui-corner-all' data-handler='next' data-event='click'" +
			" title='" + nextText + "'><span class='ui-icon ui-icon-circle-triangle-" + ( isRTL ? "w" : "e" ) + "'>" + nextText + "</span></a>" :
			( hideIfNoPrevNext ? "" : "<a class='ui-datepicker-next ui-corner-all ui-state-disabled' title='" + nextText + "'><span class='ui-icon ui-icon-circle-triangle-" + ( isRTL ? "w" : "e" ) + "'>" + nextText + "</span></a>" ) );

		currentText = this._get( inst, "currentText" );
		gotoDate = ( this._get( inst, "gotoCurrent" ) && inst.currentDay ? currentDate : today );
		currentText = ( !navigationAsDateFormat ? currentText :
			this.formatDate( currentText, gotoDate, this._getFormatConfig( inst ) ) );

		controls = ( !inst.inline ? "<button type='button' class='ui-datepicker-close ui-state-default ui-priority-primary ui-corner-all' data-handler='hide' data-event='click'>" +
			this._get( inst, "closeText" ) + "</button>" : "" );

		buttonPanel = ( showButtonPanel ) ? "<div class='ui-datepicker-buttonpane ui-widget-content'>" + ( isRTL ? controls : "" ) +
			( this._isInRange( inst, gotoDate ) ? "<button type='button' class='ui-datepicker-current ui-state-default ui-priority-secondary ui-corner-all' data-handler='today' data-event='click'" +
			">" + currentText + "</button>" : "" ) + ( isRTL ? "" : controls ) + "</div>" : "";

		firstDay = parseInt( this._get( inst, "firstDay" ), 10 );
		firstDay = ( isNaN( firstDay ) ? 0 : firstDay );

		showWeek = this._get( inst, "showWeek" );
		dayNames = this._get( inst, "dayNames" );
		dayNamesMin = this._get( inst, "dayNamesMin" );
		monthNames = this._get( inst, "monthNames" );
		monthNamesShort = this._get( inst, "monthNamesShort" );
		beforeShowDay = this._get( inst, "beforeShowDay" );
		showOtherMonths = this._get( inst, "showOtherMonths" );
		selectOtherMonths = this._get( inst, "selectOtherMonths" );
		defaultDate = this._getDefaultDate( inst );
		html = "";

		for ( row = 0; row < numMonths[ 0 ]; row++ ) {
			group = "";
			this.maxRows = 4;
			for ( col = 0; col < numMonths[ 1 ]; col++ ) {
				selectedDate = this._daylightSavingAdjust( new Date( drawYear, drawMonth, inst.selectedDay ) );
				cornerClass = " ui-corner-all";
				calender = "";
				if ( isMultiMonth ) {
					calender += "<div class='ui-datepicker-group";
					if ( numMonths[ 1 ] > 1 ) {
						switch ( col ) {
							case 0: calender += " ui-datepicker-group-first";
								cornerClass = " ui-corner-" + ( isRTL ? "right" : "left" ); break;
							case numMonths[ 1 ] - 1: calender += " ui-datepicker-group-last";
								cornerClass = " ui-corner-" + ( isRTL ? "left" : "right" ); break;
							default: calender += " ui-datepicker-group-middle"; cornerClass = ""; break;
						}
					}
					calender += "'>";
				}
				calender += "<div class='ui-datepicker-header ui-widget-header ui-helper-clearfix" + cornerClass + "'>" +
					( /all|left/.test( cornerClass ) && row === 0 ? ( isRTL ? next : prev ) : "" ) +
					( /all|right/.test( cornerClass ) && row === 0 ? ( isRTL ? prev : next ) : "" ) +
					this._generateMonthYearHeader( inst, drawMonth, drawYear, minDate, maxDate,
					row > 0 || col > 0, monthNames, monthNamesShort ) + // draw month headers
					"</div><table class='ui-datepicker-calendar'><thead>" +
					"<tr>";
				thead = ( showWeek ? "<th class='ui-datepicker-week-col'>" + this._get( inst, "weekHeader" ) + "</th>" : "" );
				for ( dow = 0; dow < 7; dow++ ) { // days of the week
					day = ( dow + firstDay ) % 7;
					thead += "<th scope='col'" + ( ( dow + firstDay + 6 ) % 7 >= 5 ? " class='ui-datepicker-week-end'" : "" ) + ">" +
						"<span title='" + dayNames[ day ] + "'>" + dayNamesMin[ day ] + "</span></th>";
				}
				calender += thead + "</tr></thead><tbody>";
				daysInMonth = this._getDaysInMonth( drawYear, drawMonth );
				if ( drawYear === inst.selectedYear && drawMonth === inst.selectedMonth ) {
					inst.selectedDay = Math.min( inst.selectedDay, daysInMonth );
				}
				leadDays = ( this._getFirstDayOfMonth( drawYear, drawMonth ) - firstDay + 7 ) % 7;
				curRows = Math.ceil( ( leadDays + daysInMonth ) / 7 ); // calculate the number of rows to generate
				numRows = ( isMultiMonth ? this.maxRows > curRows ? this.maxRows : curRows : curRows ); //If multiple months, use the higher number of rows (see #7043)
				this.maxRows = numRows;
				printDate = this._daylightSavingAdjust( new Date( drawYear, drawMonth, 1 - leadDays ) );
				for ( dRow = 0; dRow < numRows; dRow++ ) { // create date picker rows
					calender += "<tr>";
					tbody = ( !showWeek ? "" : "<td class='ui-datepicker-week-col'>" +
						this._get( inst, "calculateWeek" )( printDate ) + "</td>" );
					for ( dow = 0; dow < 7; dow++ ) { // create date picker days
						daySettings = ( beforeShowDay ?
							beforeShowDay.apply( ( inst.input ? inst.input[ 0 ] : null ), [ printDate ] ) : [ true, "" ] );
						otherMonth = ( printDate.getMonth() !== drawMonth );
						unselectable = ( otherMonth && !selectOtherMonths ) || !daySettings[ 0 ] ||
							( minDate && printDate < minDate ) || ( maxDate && printDate > maxDate );
						tbody += "<td class='" +
							( ( dow + firstDay + 6 ) % 7 >= 5 ? " ui-datepicker-week-end" : "" ) + // highlight weekends
							( otherMonth ? " ui-datepicker-other-month" : "" ) + // highlight days from other months
							( ( printDate.getTime() === selectedDate.getTime() && drawMonth === inst.selectedMonth && inst._keyEvent ) || // user pressed key
							( defaultDate.getTime() === printDate.getTime() && defaultDate.getTime() === selectedDate.getTime() ) ?

							// or defaultDate is current printedDate and defaultDate is selectedDate
							" " + this._dayOverClass : "" ) + // highlight selected day
							( unselectable ? " " + this._unselectableClass + " ui-state-disabled" : "" ) +  // highlight unselectable days
							( otherMonth && !showOtherMonths ? "" : " " + daySettings[ 1 ] + // highlight custom dates
							( printDate.getTime() === currentDate.getTime() ? " " + this._currentClass : "" ) + // highlight selected day
							( printDate.getTime() === today.getTime() ? " ui-datepicker-today" : "" ) ) + "'" + // highlight today (if different)
							( ( !otherMonth || showOtherMonths ) && daySettings[ 2 ] ? " title='" + daySettings[ 2 ].replace( /'/g, "&#39;" ) + "'" : "" ) + // cell title
							( unselectable ? "" : " data-handler='selectDay' data-event='click' data-month='" + printDate.getMonth() + "' data-year='" + printDate.getFullYear() + "'" ) + ">" + // actions
							( otherMonth && !showOtherMonths ? "&#xa0;" : // display for other months
							( unselectable ? "<span class='ui-state-default'>" + printDate.getDate() + "</span>" : "<a class='ui-state-default" +
							( printDate.getTime() === today.getTime() ? " ui-state-highlight" : "" ) +
							( printDate.getTime() === currentDate.getTime() ? " ui-state-active" : "" ) + // highlight selected day
							( otherMonth ? " ui-priority-secondary" : "" ) + // distinguish dates from other months
							"' href='#'>" + printDate.getDate() + "</a>" ) ) + "</td>"; // display selectable date
						printDate.setDate( printDate.getDate() + 1 );
						printDate = this._daylightSavingAdjust( printDate );
					}
					calender += tbody + "</tr>";
				}
				drawMonth++;
				if ( drawMonth > 11 ) {
					drawMonth = 0;
					drawYear++;
				}
				calender += "</tbody></table>" + ( isMultiMonth ? "</div>" +
							( ( numMonths[ 0 ] > 0 && col === numMonths[ 1 ] - 1 ) ? "<div class='ui-datepicker-row-break'></div>" : "" ) : "" );
				group += calender;
			}
			html += group;
		}
		html += buttonPanel;
		inst._keyEvent = false;
		return html;
	},

	/* Generate the month and year header. */
	_generateMonthYearHeader: function( inst, drawMonth, drawYear, minDate, maxDate,
			secondary, monthNames, monthNamesShort ) {

		var inMinYear, inMaxYear, month, years, thisYear, determineYear, year, endYear,
			changeMonth = this._get( inst, "changeMonth" ),
			changeYear = this._get( inst, "changeYear" ),
			showMonthAfterYear = this._get( inst, "showMonthAfterYear" ),
			html = "<div class='ui-datepicker-title'>",
			monthHtml = "";

		// Month selection
		if ( secondary || !changeMonth ) {
			monthHtml += "<span class='ui-datepicker-month'>" + monthNames[ drawMonth ] + "</span>";
		} else {
			inMinYear = ( minDate && minDate.getFullYear() === drawYear );
			inMaxYear = ( maxDate && maxDate.getFullYear() === drawYear );
			monthHtml += "<select class='ui-datepicker-month' data-handler='selectMonth' data-event='change'>";
			for ( month = 0; month < 12; month++ ) {
				if ( ( !inMinYear || month >= minDate.getMonth() ) && ( !inMaxYear || month <= maxDate.getMonth() ) ) {
					monthHtml += "<option value='" + month + "'" +
						( month === drawMonth ? " selected='selected'" : "" ) +
						">" + monthNamesShort[ month ] + "</option>";
				}
			}
			monthHtml += "</select>";
		}

		if ( !showMonthAfterYear ) {
			html += monthHtml + ( secondary || !( changeMonth && changeYear ) ? "&#xa0;" : "" );
		}

		// Year selection
		if ( !inst.yearshtml ) {
			inst.yearshtml = "";
			if ( secondary || !changeYear ) {
				html += "<span class='ui-datepicker-year'>" + drawYear + "</span>";
			} else {

				// determine range of years to display
				years = this._get( inst, "yearRange" ).split( ":" );
				thisYear = new Date().getFullYear();
				determineYear = function( value ) {
					var year = ( value.match( /c[+\-].*/ ) ? drawYear + parseInt( value.substring( 1 ), 10 ) :
						( value.match( /[+\-].*/ ) ? thisYear + parseInt( value, 10 ) :
						parseInt( value, 10 ) ) );
					return ( isNaN( year ) ? thisYear : year );
				};
				year = determineYear( years[ 0 ] );
				endYear = Math.max( year, determineYear( years[ 1 ] || "" ) );
				year = ( minDate ? Math.max( year, minDate.getFullYear() ) : year );
				endYear = ( maxDate ? Math.min( endYear, maxDate.getFullYear() ) : endYear );
				inst.yearshtml += "<select class='ui-datepicker-year' data-handler='selectYear' data-event='change'>";
				for ( ; year <= endYear; year++ ) {
					inst.yearshtml += "<option value='" + year + "'" +
						( year === drawYear ? " selected='selected'" : "" ) +
						">" + year + "</option>";
				}
				inst.yearshtml += "</select>";

				html += inst.yearshtml;
				inst.yearshtml = null;
			}
		}

		html += this._get( inst, "yearSuffix" );
		if ( showMonthAfterYear ) {
			html += ( secondary || !( changeMonth && changeYear ) ? "&#xa0;" : "" ) + monthHtml;
		}
		html += "</div>"; // Close datepicker_header
		return html;
	},

	/* Adjust one of the date sub-fields. */
	_adjustInstDate: function( inst, offset, period ) {
		var year = inst.selectedYear + ( period === "Y" ? offset : 0 ),
			month = inst.selectedMonth + ( period === "M" ? offset : 0 ),
			day = Math.min( inst.selectedDay, this._getDaysInMonth( year, month ) ) + ( period === "D" ? offset : 0 ),
			date = this._restrictMinMax( inst, this._daylightSavingAdjust( new Date( year, month, day ) ) );

		inst.selectedDay = date.getDate();
		inst.drawMonth = inst.selectedMonth = date.getMonth();
		inst.drawYear = inst.selectedYear = date.getFullYear();
		if ( period === "M" || period === "Y" ) {
			this._notifyChange( inst );
		}
	},

	/* Ensure a date is within any min/max bounds. */
	_restrictMinMax: function( inst, date ) {
		var minDate = this._getMinMaxDate( inst, "min" ),
			maxDate = this._getMinMaxDate( inst, "max" ),
			newDate = ( minDate && date < minDate ? minDate : date );
		return ( maxDate && newDate > maxDate ? maxDate : newDate );
	},

	/* Notify change of month/year. */
	_notifyChange: function( inst ) {
		var onChange = this._get( inst, "onChangeMonthYear" );
		if ( onChange ) {
			onChange.apply( ( inst.input ? inst.input[ 0 ] : null ),
				[ inst.selectedYear, inst.selectedMonth + 1, inst ] );
		}
	},

	/* Determine the number of months to show. */
	_getNumberOfMonths: function( inst ) {
		var numMonths = this._get( inst, "numberOfMonths" );
		return ( numMonths == null ? [ 1, 1 ] : ( typeof numMonths === "number" ? [ 1, numMonths ] : numMonths ) );
	},

	/* Determine the current maximum date - ensure no time components are set. */
	_getMinMaxDate: function( inst, minMax ) {
		return this._determineDate( inst, this._get( inst, minMax + "Date" ), null );
	},

	/* Find the number of days in a given month. */
	_getDaysInMonth: function( year, month ) {
		return 32 - this._daylightSavingAdjust( new Date( year, month, 32 ) ).getDate();
	},

	/* Find the day of the week of the first of a month. */
	_getFirstDayOfMonth: function( year, month ) {
		return new Date( year, month, 1 ).getDay();
	},

	/* Determines if we should allow a "next/prev" month display change. */
	_canAdjustMonth: function( inst, offset, curYear, curMonth ) {
		var numMonths = this._getNumberOfMonths( inst ),
			date = this._daylightSavingAdjust( new Date( curYear,
			curMonth + ( offset < 0 ? offset : numMonths[ 0 ] * numMonths[ 1 ] ), 1 ) );

		if ( offset < 0 ) {
			date.setDate( this._getDaysInMonth( date.getFullYear(), date.getMonth() ) );
		}
		return this._isInRange( inst, date );
	},

	/* Is the given date in the accepted range? */
	_isInRange: function( inst, date ) {
		var yearSplit, currentYear,
			minDate = this._getMinMaxDate( inst, "min" ),
			maxDate = this._getMinMaxDate( inst, "max" ),
			minYear = null,
			maxYear = null,
			years = this._get( inst, "yearRange" );
			if ( years ) {
				yearSplit = years.split( ":" );
				currentYear = new Date().getFullYear();
				minYear = parseInt( yearSplit[ 0 ], 10 );
				maxYear = parseInt( yearSplit[ 1 ], 10 );
				if ( yearSplit[ 0 ].match( /[+\-].*/ ) ) {
					minYear += currentYear;
				}
				if ( yearSplit[ 1 ].match( /[+\-].*/ ) ) {
					maxYear += currentYear;
				}
			}

		return ( ( !minDate || date.getTime() >= minDate.getTime() ) &&
			( !maxDate || date.getTime() <= maxDate.getTime() ) &&
			( !minYear || date.getFullYear() >= minYear ) &&
			( !maxYear || date.getFullYear() <= maxYear ) );
	},

	/* Provide the configuration settings for formatting/parsing. */
	_getFormatConfig: function( inst ) {
		var shortYearCutoff = this._get( inst, "shortYearCutoff" );
		shortYearCutoff = ( typeof shortYearCutoff !== "string" ? shortYearCutoff :
			new Date().getFullYear() % 100 + parseInt( shortYearCutoff, 10 ) );
		return { shortYearCutoff: shortYearCutoff,
			dayNamesShort: this._get( inst, "dayNamesShort" ), dayNames: this._get( inst, "dayNames" ),
			monthNamesShort: this._get( inst, "monthNamesShort" ), monthNames: this._get( inst, "monthNames" ) };
	},

	/* Format the given date for display. */
	_formatDate: function( inst, day, month, year ) {
		if ( !day ) {
			inst.currentDay = inst.selectedDay;
			inst.currentMonth = inst.selectedMonth;
			inst.currentYear = inst.selectedYear;
		}
		var date = ( day ? ( typeof day === "object" ? day :
			this._daylightSavingAdjust( new Date( year, month, day ) ) ) :
			this._daylightSavingAdjust( new Date( inst.currentYear, inst.currentMonth, inst.currentDay ) ) );
		return this.formatDate( this._get( inst, "dateFormat" ), date, this._getFormatConfig( inst ) );
	}
} );

/*
 * Bind hover events for datepicker elements.
 * Done via delegate so the binding only occurs once in the lifetime of the parent div.
 * Global datepicker_instActive, set by _updateDatepicker allows the handlers to find their way back to the active picker.
 */
function datepicker_bindHover( dpDiv ) {
	var selector = "button, .ui-datepicker-prev, .ui-datepicker-next, .ui-datepicker-calendar td a";
	return dpDiv.on( "mouseout", selector, function() {
			$( this ).removeClass( "ui-state-hover" );
			if ( this.className.indexOf( "ui-datepicker-prev" ) !== -1 ) {
				$( this ).removeClass( "ui-datepicker-prev-hover" );
			}
			if ( this.className.indexOf( "ui-datepicker-next" ) !== -1 ) {
				$( this ).removeClass( "ui-datepicker-next-hover" );
			}
		} )
		.on( "mouseover", selector, datepicker_handleMouseover );
}

function datepicker_handleMouseover() {
	if ( !$.datepicker._isDisabledDatepicker( datepicker_instActive.inline ? datepicker_instActive.dpDiv.parent()[ 0 ] : datepicker_instActive.input[ 0 ] ) ) {
		$( this ).parents( ".ui-datepicker-calendar" ).find( "a" ).removeClass( "ui-state-hover" );
		$( this ).addClass( "ui-state-hover" );
		if ( this.className.indexOf( "ui-datepicker-prev" ) !== -1 ) {
			$( this ).addClass( "ui-datepicker-prev-hover" );
		}
		if ( this.className.indexOf( "ui-datepicker-next" ) !== -1 ) {
			$( this ).addClass( "ui-datepicker-next-hover" );
		}
	}
}

/* jQuery extend now ignores nulls! */
function datepicker_extendRemove( target, props ) {
	$.extend( target, props );
	for ( var name in props ) {
		if ( props[ name ] == null ) {
			target[ name ] = props[ name ];
		}
	}
	return target;
}

/* Invoke the datepicker functionality.
   @param  options  string - a command, optionally followed by additional parameters or
					Object - settings for attaching new datepicker functionality
   @return  jQuery object */
$.fn.datepicker = function( options ) {

	/* Verify an empty collection wasn't passed - Fixes #6976 */
	if ( !this.length ) {
		return this;
	}

	/* Initialise the date picker. */
	if ( !$.datepicker.initialized ) {
		$( document ).on( "mousedown", $.datepicker._checkExternalClick );
		$.datepicker.initialized = true;
	}

	/* Append datepicker main container to body if not exist. */
	if ( $( "#" + $.datepicker._mainDivId ).length === 0 ) {
		$( "body" ).append( $.datepicker.dpDiv );
	}

	var otherArgs = Array.prototype.slice.call( arguments, 1 );
	if ( typeof options === "string" && ( options === "isDisabled" || options === "getDate" || options === "widget" ) ) {
		return $.datepicker[ "_" + options + "Datepicker" ].
			apply( $.datepicker, [ this[ 0 ] ].concat( otherArgs ) );
	}
	if ( options === "option" && arguments.length === 2 && typeof arguments[ 1 ] === "string" ) {
		return $.datepicker[ "_" + options + "Datepicker" ].
			apply( $.datepicker, [ this[ 0 ] ].concat( otherArgs ) );
	}
	return this.each( function() {
		typeof options === "string" ?
			$.datepicker[ "_" + options + "Datepicker" ].
				apply( $.datepicker, [ this ].concat( otherArgs ) ) :
			$.datepicker._attachDatepicker( this, options );
	} );
};

$.datepicker = new Datepicker(); // singleton instance
$.datepicker.initialized = false;
$.datepicker.uuid = new Date().getTime();
$.datepicker.version = "1.12.0";

var widgetsDatepicker = $.datepicker;




// This file is deprecated
var ie = $.ui.ie = !!/msie [\w.]+/.exec( navigator.userAgent.toLowerCase() );

/*!
 * jQuery UI Mouse 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: Mouse
//>>group: Widgets
//>>description: Abstracts mouse-based interactions to assist in creating certain widgets.
//>>docs: http://api.jqueryui.com/mouse/



var mouseHandled = false;
$( document ).on( "mouseup", function() {
	mouseHandled = false;
} );

var widgetsMouse = $.widget( "ui.mouse", {
	version: "1.12.0",
	options: {
		cancel: "input, textarea, button, select, option",
		distance: 1,
		delay: 0
	},
	_mouseInit: function() {
		var that = this;

		this.element
			.on( "mousedown." + this.widgetName, function( event ) {
				return that._mouseDown( event );
			} )
			.on( "click." + this.widgetName, function( event ) {
				if ( true === $.data( event.target, that.widgetName + ".preventClickEvent" ) ) {
					$.removeData( event.target, that.widgetName + ".preventClickEvent" );
					event.stopImmediatePropagation();
					return false;
				}
			} );

		this.started = false;
	},

	// TODO: make sure destroying one instance of mouse doesn't mess with
	// other instances of mouse
	_mouseDestroy: function() {
		this.element.off( "." + this.widgetName );
		if ( this._mouseMoveDelegate ) {
			this.document
				.off( "mousemove." + this.widgetName, this._mouseMoveDelegate )
				.off( "mouseup." + this.widgetName, this._mouseUpDelegate );
		}
	},

	_mouseDown: function( event ) {

		// don't let more than one widget handle mouseStart
		if ( mouseHandled ) {
			return;
		}

		this._mouseMoved = false;

		// We may have missed mouseup (out of window)
		( this._mouseStarted && this._mouseUp( event ) );

		this._mouseDownEvent = event;

		var that = this,
			btnIsLeft = ( event.which === 1 ),

			// event.target.nodeName works around a bug in IE 8 with
			// disabled inputs (#7620)
			elIsCancel = ( typeof this.options.cancel === "string" && event.target.nodeName ?
				$( event.target ).closest( this.options.cancel ).length : false );
		if ( !btnIsLeft || elIsCancel || !this._mouseCapture( event ) ) {
			return true;
		}

		this.mouseDelayMet = !this.options.delay;
		if ( !this.mouseDelayMet ) {
			this._mouseDelayTimer = setTimeout( function() {
				that.mouseDelayMet = true;
			}, this.options.delay );
		}

		if ( this._mouseDistanceMet( event ) && this._mouseDelayMet( event ) ) {
			this._mouseStarted = ( this._mouseStart( event ) !== false );
			if ( !this._mouseStarted ) {
				event.preventDefault();
				return true;
			}
		}

		// Click event may never have fired (Gecko & Opera)
		if ( true === $.data( event.target, this.widgetName + ".preventClickEvent" ) ) {
			$.removeData( event.target, this.widgetName + ".preventClickEvent" );
		}

		// These delegates are required to keep context
		this._mouseMoveDelegate = function( event ) {
			return that._mouseMove( event );
		};
		this._mouseUpDelegate = function( event ) {
			return that._mouseUp( event );
		};

		this.document
			.on( "mousemove." + this.widgetName, this._mouseMoveDelegate )
			.on( "mouseup." + this.widgetName, this._mouseUpDelegate );

		event.preventDefault();

		mouseHandled = true;
		return true;
	},

	_mouseMove: function( event ) {

		// Only check for mouseups outside the document if you've moved inside the document
		// at least once. This prevents the firing of mouseup in the case of IE<9, which will
		// fire a mousemove event if content is placed under the cursor. See #7778
		// Support: IE <9
		if ( this._mouseMoved ) {

			// IE mouseup check - mouseup happened when mouse was out of window
			if ( $.ui.ie && ( !document.documentMode || document.documentMode < 9 ) &&
					!event.button ) {
				return this._mouseUp( event );

			// Iframe mouseup check - mouseup occurred in another document
			} else if ( !event.which ) {

				// Support: Safari <=8 - 9
				// Safari sets which to 0 if you press any of the following keys
				// during a drag (#14461)
				if ( event.originalEvent.altKey || event.originalEvent.ctrlKey ||
						event.originalEvent.metaKey || event.originalEvent.shiftKey ) {
					this.ignoreMissingWhich = true;
				} else if ( !this.ignoreMissingWhich ) {
					return this._mouseUp( event );
				}
			}
		}

		if ( event.which || event.button ) {
			this._mouseMoved = true;
		}

		if ( this._mouseStarted ) {
			this._mouseDrag( event );
			return event.preventDefault();
		}

		if ( this._mouseDistanceMet( event ) && this._mouseDelayMet( event ) ) {
			this._mouseStarted =
				( this._mouseStart( this._mouseDownEvent, event ) !== false );
			( this._mouseStarted ? this._mouseDrag( event ) : this._mouseUp( event ) );
		}

		return !this._mouseStarted;
	},

	_mouseUp: function( event ) {
		this.document
			.off( "mousemove." + this.widgetName, this._mouseMoveDelegate )
			.off( "mouseup." + this.widgetName, this._mouseUpDelegate );

		if ( this._mouseStarted ) {
			this._mouseStarted = false;

			if ( event.target === this._mouseDownEvent.target ) {
				$.data( event.target, this.widgetName + ".preventClickEvent", true );
			}

			this._mouseStop( event );
		}

		if ( this._mouseDelayTimer ) {
			clearTimeout( this._mouseDelayTimer );
			delete this._mouseDelayTimer;
		}

		this.ignoreMissingWhich = false;
		mouseHandled = false;
		event.preventDefault();
	},

	_mouseDistanceMet: function( event ) {
		return ( Math.max(
				Math.abs( this._mouseDownEvent.pageX - event.pageX ),
				Math.abs( this._mouseDownEvent.pageY - event.pageY )
			) >= this.options.distance
		);
	},

	_mouseDelayMet: function( /* event */ ) {
		return this.mouseDelayMet;
	},

	// These are placeholder methods, to be overriden by extending plugin
	_mouseStart: function( /* event */ ) {},
	_mouseDrag: function( /* event */ ) {},
	_mouseStop: function( /* event */ ) {},
	_mouseCapture: function( /* event */ ) { return true; }
} );




// $.ui.plugin is deprecated. Use $.widget() extensions instead.
var plugin = $.ui.plugin = {
	add: function( module, option, set ) {
		var i,
			proto = $.ui[ module ].prototype;
		for ( i in set ) {
			proto.plugins[ i ] = proto.plugins[ i ] || [];
			proto.plugins[ i ].push( [ option, set[ i ] ] );
		}
	},
	call: function( instance, name, args, allowDisconnected ) {
		var i,
			set = instance.plugins[ name ];

		if ( !set ) {
			return;
		}

		if ( !allowDisconnected && ( !instance.element[ 0 ].parentNode ||
				instance.element[ 0 ].parentNode.nodeType === 11 ) ) {
			return;
		}

		for ( i = 0; i < set.length; i++ ) {
			if ( instance.options[ set[ i ][ 0 ] ] ) {
				set[ i ][ 1 ].apply( instance.element, args );
			}
		}
	}
};



var safeBlur = $.ui.safeBlur = function( element ) {

	// Support: IE9 - 10 only
	// If the <body> is blurred, IE will switch windows, see #9420
	if ( element && element.nodeName.toLowerCase() !== "body" ) {
		$( element ).trigger( "blur" );
	}
};


/*!
 * jQuery UI Draggable 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: Draggable
//>>group: Interactions
//>>description: Enables dragging functionality for any element.
//>>docs: http://api.jqueryui.com/draggable/
//>>demos: http://jqueryui.com/draggable/
//>>css.structure: ../../themes/base/draggable.css



$.widget( "ui.draggable", $.ui.mouse, {
	version: "1.12.0",
	widgetEventPrefix: "drag",
	options: {
		addClasses: true,
		appendTo: "parent",
		axis: false,
		connectToSortable: false,
		containment: false,
		cursor: "auto",
		cursorAt: false,
		grid: false,
		handle: false,
		helper: "original",
		iframeFix: false,
		opacity: false,
		refreshPositions: false,
		revert: false,
		revertDuration: 500,
		scope: "default",
		scroll: true,
		scrollSensitivity: 20,
		scrollSpeed: 20,
		snap: false,
		snapMode: "both",
		snapTolerance: 20,
		stack: false,
		zIndex: false,

		// Callbacks
		drag: null,
		start: null,
		stop: null
	},
	_create: function() {

		if ( this.options.helper === "original" ) {
			this._setPositionRelative();
		}
		if ( this.options.addClasses ) {
			this._addClass( "ui-draggable" );
		}
		this._setHandleClassName();

		this._mouseInit();
	},

	_setOption: function( key, value ) {
		this._super( key, value );
		if ( key === "handle" ) {
			this._removeHandleClassName();
			this._setHandleClassName();
		}
	},

	_destroy: function() {
		if ( ( this.helper || this.element ).is( ".ui-draggable-dragging" ) ) {
			this.destroyOnClear = true;
			return;
		}
		this._removeHandleClassName();
		this._mouseDestroy();
	},

	_mouseCapture: function( event ) {
		var o = this.options;

		this._blurActiveElement( event );

		// Among others, prevent a drag on a resizable-handle
		if ( this.helper || o.disabled ||
				$( event.target ).closest( ".ui-resizable-handle" ).length > 0 ) {
			return false;
		}

		//Quit if we're not on a valid handle
		this.handle = this._getHandle( event );
		if ( !this.handle ) {
			return false;
		}

		this._blockFrames( o.iframeFix === true ? "iframe" : o.iframeFix );

		return true;

	},

	_blockFrames: function( selector ) {
		this.iframeBlocks = this.document.find( selector ).map( function() {
			var iframe = $( this );

			return $( "<div>" )
				.css( "position", "absolute" )
				.appendTo( iframe.parent() )
				.outerWidth( iframe.outerWidth() )
				.outerHeight( iframe.outerHeight() )
				.offset( iframe.offset() )[ 0 ];
		} );
	},

	_unblockFrames: function() {
		if ( this.iframeBlocks ) {
			this.iframeBlocks.remove();
			delete this.iframeBlocks;
		}
	},

	_blurActiveElement: function( event ) {
		var activeElement = $.ui.safeActiveElement( this.document[ 0 ] ),
			target = $( event.target );

		// Only blur if the event occurred on an element that is:
		// 1) within the draggable handle
		// 2) but not within the currently focused element
		// See #10527, #12472
		if ( this._getHandle( event ) && target.closest( activeElement ).length ) {
			return;
		}

		// Blur any element that currently has focus, see #4261
		$.ui.safeBlur( activeElement );
	},

	_mouseStart: function( event ) {

		var o = this.options;

		//Create and append the visible helper
		this.helper = this._createHelper( event );

		this._addClass( this.helper, "ui-draggable-dragging" );

		//Cache the helper size
		this._cacheHelperProportions();

		//If ddmanager is used for droppables, set the global draggable
		if ( $.ui.ddmanager ) {
			$.ui.ddmanager.current = this;
		}

		/*
		 * - Position generation -
		 * This block generates everything position related - it's the core of draggables.
		 */

		//Cache the margins of the original element
		this._cacheMargins();

		//Store the helper's css position
		this.cssPosition = this.helper.css( "position" );
		this.scrollParent = this.helper.scrollParent( true );
		this.offsetParent = this.helper.offsetParent();
		this.hasFixedAncestor = this.helper.parents().filter( function() {
				return $( this ).css( "position" ) === "fixed";
			} ).length > 0;

		//The element's absolute position on the page minus margins
		this.positionAbs = this.element.offset();
		this._refreshOffsets( event );

		//Generate the original position
		this.originalPosition = this.position = this._generatePosition( event, false );
		this.originalPageX = event.pageX;
		this.originalPageY = event.pageY;

		//Adjust the mouse offset relative to the helper if "cursorAt" is supplied
		( o.cursorAt && this._adjustOffsetFromHelper( o.cursorAt ) );

		//Set a containment if given in the options
		this._setContainment();

		//Trigger event + callbacks
		if ( this._trigger( "start", event ) === false ) {
			this._clear();
			return false;
		}

		//Recache the helper size
		this._cacheHelperProportions();

		//Prepare the droppable offsets
		if ( $.ui.ddmanager && !o.dropBehaviour ) {
			$.ui.ddmanager.prepareOffsets( this, event );
		}

		// Execute the drag once - this causes the helper not to be visible before getting its
		// correct position
		this._mouseDrag( event, true );

		// If the ddmanager is used for droppables, inform the manager that dragging has started
		// (see #5003)
		if ( $.ui.ddmanager ) {
			$.ui.ddmanager.dragStart( this, event );
		}

		return true;
	},

	_refreshOffsets: function( event ) {
		this.offset = {
			top: this.positionAbs.top - this.margins.top,
			left: this.positionAbs.left - this.margins.left,
			scroll: false,
			parent: this._getParentOffset(),
			relative: this._getRelativeOffset()
		};

		this.offset.click = {
			left: event.pageX - this.offset.left,
			top: event.pageY - this.offset.top
		};
	},

	_mouseDrag: function( event, noPropagation ) {

		// reset any necessary cached properties (see #5009)
		if ( this.hasFixedAncestor ) {
			this.offset.parent = this._getParentOffset();
		}

		//Compute the helpers position
		this.position = this._generatePosition( event, true );
		this.positionAbs = this._convertPositionTo( "absolute" );

		//Call plugins and callbacks and use the resulting position if something is returned
		if ( !noPropagation ) {
			var ui = this._uiHash();
			if ( this._trigger( "drag", event, ui ) === false ) {
				this._mouseUp( new $.Event( "mouseup", event ) );
				return false;
			}
			this.position = ui.position;
		}

		this.helper[ 0 ].style.left = this.position.left + "px";
		this.helper[ 0 ].style.top = this.position.top + "px";

		if ( $.ui.ddmanager ) {
			$.ui.ddmanager.drag( this, event );
		}

		return false;
	},

	_mouseStop: function( event ) {

		//If we are using droppables, inform the manager about the drop
		var that = this,
			dropped = false;
		if ( $.ui.ddmanager && !this.options.dropBehaviour ) {
			dropped = $.ui.ddmanager.drop( this, event );
		}

		//if a drop comes from outside (a sortable)
		if ( this.dropped ) {
			dropped = this.dropped;
			this.dropped = false;
		}

		if ( ( this.options.revert === "invalid" && !dropped ) ||
				( this.options.revert === "valid" && dropped ) ||
				this.options.revert === true || ( $.isFunction( this.options.revert ) &&
				this.options.revert.call( this.element, dropped ) )
		) {
			$( this.helper ).animate(
				this.originalPosition,
				parseInt( this.options.revertDuration, 10 ),
				function() {
					if ( that._trigger( "stop", event ) !== false ) {
						that._clear();
					}
				}
			);
		} else {
			if ( this._trigger( "stop", event ) !== false ) {
				this._clear();
			}
		}

		return false;
	},

	_mouseUp: function( event ) {
		this._unblockFrames();

		// If the ddmanager is used for droppables, inform the manager that dragging has stopped
		// (see #5003)
		if ( $.ui.ddmanager ) {
			$.ui.ddmanager.dragStop( this, event );
		}

		// Only need to focus if the event occurred on the draggable itself, see #10527
		if ( this.handleElement.is( event.target ) ) {

			// The interaction is over; whether or not the click resulted in a drag,
			// focus the element
			this.element.trigger( "focus" );
		}

		return $.ui.mouse.prototype._mouseUp.call( this, event );
	},

	cancel: function() {

		if ( this.helper.is( ".ui-draggable-dragging" ) ) {
			this._mouseUp( new $.Event( "mouseup", { target: this.element[ 0 ] } ) );
		} else {
			this._clear();
		}

		return this;

	},

	_getHandle: function( event ) {
		return this.options.handle ?
			!!$( event.target ).closest( this.element.find( this.options.handle ) ).length :
			true;
	},

	_setHandleClassName: function() {
		this.handleElement = this.options.handle ?
			this.element.find( this.options.handle ) : this.element;
		this._addClass( this.handleElement, "ui-draggable-handle" );
	},

	_removeHandleClassName: function() {
		this._removeClass( this.handleElement, "ui-draggable-handle" );
	},

	_createHelper: function( event ) {

		var o = this.options,
			helperIsFunction = $.isFunction( o.helper ),
			helper = helperIsFunction ?
				$( o.helper.apply( this.element[ 0 ], [ event ] ) ) :
				( o.helper === "clone" ?
					this.element.clone().removeAttr( "id" ) :
					this.element );

		if ( !helper.parents( "body" ).length ) {
			helper.appendTo( ( o.appendTo === "parent" ?
				this.element[ 0 ].parentNode :
				o.appendTo ) );
		}

		// Http://bugs.jqueryui.com/ticket/9446
		// a helper function can return the original element
		// which wouldn't have been set to relative in _create
		if ( helperIsFunction && helper[ 0 ] === this.element[ 0 ] ) {
			this._setPositionRelative();
		}

		if ( helper[ 0 ] !== this.element[ 0 ] &&
				!( /(fixed|absolute)/ ).test( helper.css( "position" ) ) ) {
			helper.css( "position", "absolute" );
		}

		return helper;

	},

	_setPositionRelative: function() {
		if ( !( /^(?:r|a|f)/ ).test( this.element.css( "position" ) ) ) {
			this.element[ 0 ].style.position = "relative";
		}
	},

	_adjustOffsetFromHelper: function( obj ) {
		if ( typeof obj === "string" ) {
			obj = obj.split( " " );
		}
		if ( $.isArray( obj ) ) {
			obj = { left: +obj[ 0 ], top: +obj[ 1 ] || 0 };
		}
		if ( "left" in obj ) {
			this.offset.click.left = obj.left + this.margins.left;
		}
		if ( "right" in obj ) {
			this.offset.click.left = this.helperProportions.width - obj.right + this.margins.left;
		}
		if ( "top" in obj ) {
			this.offset.click.top = obj.top + this.margins.top;
		}
		if ( "bottom" in obj ) {
			this.offset.click.top = this.helperProportions.height - obj.bottom + this.margins.top;
		}
	},

	_isRootNode: function( element ) {
		return ( /(html|body)/i ).test( element.tagName ) || element === this.document[ 0 ];
	},

	_getParentOffset: function() {

		//Get the offsetParent and cache its position
		var po = this.offsetParent.offset(),
			document = this.document[ 0 ];

		// This is a special case where we need to modify a offset calculated on start, since the
		// following happened:
		// 1. The position of the helper is absolute, so it's position is calculated based on the
		// next positioned parent
		// 2. The actual offset parent is a child of the scroll parent, and the scroll parent isn't
		// the document, which means that the scroll is included in the initial calculation of the
		// offset of the parent, and never recalculated upon drag
		if ( this.cssPosition === "absolute" && this.scrollParent[ 0 ] !== document &&
				$.contains( this.scrollParent[ 0 ], this.offsetParent[ 0 ] ) ) {
			po.left += this.scrollParent.scrollLeft();
			po.top += this.scrollParent.scrollTop();
		}

		if ( this._isRootNode( this.offsetParent[ 0 ] ) ) {
			po = { top: 0, left: 0 };
		}

		return {
			top: po.top + ( parseInt( this.offsetParent.css( "borderTopWidth" ), 10 ) || 0 ),
			left: po.left + ( parseInt( this.offsetParent.css( "borderLeftWidth" ), 10 ) || 0 )
		};

	},

	_getRelativeOffset: function() {
		if ( this.cssPosition !== "relative" ) {
			return { top: 0, left: 0 };
		}

		var p = this.element.position(),
			scrollIsRootNode = this._isRootNode( this.scrollParent[ 0 ] );

		return {
			top: p.top - ( parseInt( this.helper.css( "top" ), 10 ) || 0 ) +
				( !scrollIsRootNode ? this.scrollParent.scrollTop() : 0 ),
			left: p.left - ( parseInt( this.helper.css( "left" ), 10 ) || 0 ) +
				( !scrollIsRootNode ? this.scrollParent.scrollLeft() : 0 )
		};

	},

	_cacheMargins: function() {
		this.margins = {
			left: ( parseInt( this.element.css( "marginLeft" ), 10 ) || 0 ),
			top: ( parseInt( this.element.css( "marginTop" ), 10 ) || 0 ),
			right: ( parseInt( this.element.css( "marginRight" ), 10 ) || 0 ),
			bottom: ( parseInt( this.element.css( "marginBottom" ), 10 ) || 0 )
		};
	},

	_cacheHelperProportions: function() {
		this.helperProportions = {
			width: this.helper.outerWidth(),
			height: this.helper.outerHeight()
		};
	},

	_setContainment: function() {

		var isUserScrollable, c, ce,
			o = this.options,
			document = this.document[ 0 ];

		this.relativeContainer = null;

		if ( !o.containment ) {
			this.containment = null;
			return;
		}

		if ( o.containment === "window" ) {
			this.containment = [
				$( window ).scrollLeft() - this.offset.relative.left - this.offset.parent.left,
				$( window ).scrollTop() - this.offset.relative.top - this.offset.parent.top,
				$( window ).scrollLeft() + $( window ).width() -
					this.helperProportions.width - this.margins.left,
				$( window ).scrollTop() +
					( $( window ).height() || document.body.parentNode.scrollHeight ) -
					this.helperProportions.height - this.margins.top
			];
			return;
		}

		if ( o.containment === "document" ) {
			this.containment = [
				0,
				0,
				$( document ).width() - this.helperProportions.width - this.margins.left,
				( $( document ).height() || document.body.parentNode.scrollHeight ) -
					this.helperProportions.height - this.margins.top
			];
			return;
		}

		if ( o.containment.constructor === Array ) {
			this.containment = o.containment;
			return;
		}

		if ( o.containment === "parent" ) {
			o.containment = this.helper[ 0 ].parentNode;
		}

		c = $( o.containment );
		ce = c[ 0 ];

		if ( !ce ) {
			return;
		}

		isUserScrollable = /(scroll|auto)/.test( c.css( "overflow" ) );

		this.containment = [
			( parseInt( c.css( "borderLeftWidth" ), 10 ) || 0 ) +
				( parseInt( c.css( "paddingLeft" ), 10 ) || 0 ),
			( parseInt( c.css( "borderTopWidth" ), 10 ) || 0 ) +
				( parseInt( c.css( "paddingTop" ), 10 ) || 0 ),
			( isUserScrollable ? Math.max( ce.scrollWidth, ce.offsetWidth ) : ce.offsetWidth ) -
				( parseInt( c.css( "borderRightWidth" ), 10 ) || 0 ) -
				( parseInt( c.css( "paddingRight" ), 10 ) || 0 ) -
				this.helperProportions.width -
				this.margins.left -
				this.margins.right,
			( isUserScrollable ? Math.max( ce.scrollHeight, ce.offsetHeight ) : ce.offsetHeight ) -
				( parseInt( c.css( "borderBottomWidth" ), 10 ) || 0 ) -
				( parseInt( c.css( "paddingBottom" ), 10 ) || 0 ) -
				this.helperProportions.height -
				this.margins.top -
				this.margins.bottom
		];
		this.relativeContainer = c;
	},

	_convertPositionTo: function( d, pos ) {

		if ( !pos ) {
			pos = this.position;
		}

		var mod = d === "absolute" ? 1 : -1,
			scrollIsRootNode = this._isRootNode( this.scrollParent[ 0 ] );

		return {
			top: (

				// The absolute mouse position
				pos.top	+

				// Only for relative positioned nodes: Relative offset from element to offset parent
				this.offset.relative.top * mod +

				// The offsetParent's offset without borders (offset + border)
				this.offset.parent.top * mod -
				( ( this.cssPosition === "fixed" ?
					-this.offset.scroll.top :
					( scrollIsRootNode ? 0 : this.offset.scroll.top ) ) * mod )
			),
			left: (

				// The absolute mouse position
				pos.left +

				// Only for relative positioned nodes: Relative offset from element to offset parent
				this.offset.relative.left * mod +

				// The offsetParent's offset without borders (offset + border)
				this.offset.parent.left * mod	-
				( ( this.cssPosition === "fixed" ?
					-this.offset.scroll.left :
					( scrollIsRootNode ? 0 : this.offset.scroll.left ) ) * mod )
			)
		};

	},

	_generatePosition: function( event, constrainPosition ) {

		var containment, co, top, left,
			o = this.options,
			scrollIsRootNode = this._isRootNode( this.scrollParent[ 0 ] ),
			pageX = event.pageX,
			pageY = event.pageY;

		// Cache the scroll
		if ( !scrollIsRootNode || !this.offset.scroll ) {
			this.offset.scroll = {
				top: this.scrollParent.scrollTop(),
				left: this.scrollParent.scrollLeft()
			};
		}

		/*
		 * - Position constraining -
		 * Constrain the position to a mix of grid, containment.
		 */

		// If we are not dragging yet, we won't check for options
		if ( constrainPosition ) {
			if ( this.containment ) {
				if ( this.relativeContainer ) {
					co = this.relativeContainer.offset();
					containment = [
						this.containment[ 0 ] + co.left,
						this.containment[ 1 ] + co.top,
						this.containment[ 2 ] + co.left,
						this.containment[ 3 ] + co.top
					];
				} else {
					containment = this.containment;
				}

				if ( event.pageX - this.offset.click.left < containment[ 0 ] ) {
					pageX = containment[ 0 ] + this.offset.click.left;
				}
				if ( event.pageY - this.offset.click.top < containment[ 1 ] ) {
					pageY = containment[ 1 ] + this.offset.click.top;
				}
				if ( event.pageX - this.offset.click.left > containment[ 2 ] ) {
					pageX = containment[ 2 ] + this.offset.click.left;
				}
				if ( event.pageY - this.offset.click.top > containment[ 3 ] ) {
					pageY = containment[ 3 ] + this.offset.click.top;
				}
			}

			if ( o.grid ) {

				//Check for grid elements set to 0 to prevent divide by 0 error causing invalid
				// argument errors in IE (see ticket #6950)
				top = o.grid[ 1 ] ? this.originalPageY + Math.round( ( pageY -
					this.originalPageY ) / o.grid[ 1 ] ) * o.grid[ 1 ] : this.originalPageY;
				pageY = containment ? ( ( top - this.offset.click.top >= containment[ 1 ] ||
					top - this.offset.click.top > containment[ 3 ] ) ?
						top :
						( ( top - this.offset.click.top >= containment[ 1 ] ) ?
							top - o.grid[ 1 ] : top + o.grid[ 1 ] ) ) : top;

				left = o.grid[ 0 ] ? this.originalPageX +
					Math.round( ( pageX - this.originalPageX ) / o.grid[ 0 ] ) * o.grid[ 0 ] :
					this.originalPageX;
				pageX = containment ? ( ( left - this.offset.click.left >= containment[ 0 ] ||
					left - this.offset.click.left > containment[ 2 ] ) ?
						left :
						( ( left - this.offset.click.left >= containment[ 0 ] ) ?
							left - o.grid[ 0 ] : left + o.grid[ 0 ] ) ) : left;
			}

			if ( o.axis === "y" ) {
				pageX = this.originalPageX;
			}

			if ( o.axis === "x" ) {
				pageY = this.originalPageY;
			}
		}

		return {
			top: (

				// The absolute mouse position
				pageY -

				// Click offset (relative to the element)
				this.offset.click.top -

				// Only for relative positioned nodes: Relative offset from element to offset parent
				this.offset.relative.top -

				// The offsetParent's offset without borders (offset + border)
				this.offset.parent.top +
				( this.cssPosition === "fixed" ?
					-this.offset.scroll.top :
					( scrollIsRootNode ? 0 : this.offset.scroll.top ) )
			),
			left: (

				// The absolute mouse position
				pageX -

				// Click offset (relative to the element)
				this.offset.click.left -

				// Only for relative positioned nodes: Relative offset from element to offset parent
				this.offset.relative.left -

				// The offsetParent's offset without borders (offset + border)
				this.offset.parent.left +
				( this.cssPosition === "fixed" ?
					-this.offset.scroll.left :
					( scrollIsRootNode ? 0 : this.offset.scroll.left ) )
			)
		};

	},

	_clear: function() {
		this._removeClass( this.helper, "ui-draggable-dragging" );
		if ( this.helper[ 0 ] !== this.element[ 0 ] && !this.cancelHelperRemoval ) {
			this.helper.remove();
		}
		this.helper = null;
		this.cancelHelperRemoval = false;
		if ( this.destroyOnClear ) {
			this.destroy();
		}
	},

	// From now on bulk stuff - mainly helpers

	_trigger: function( type, event, ui ) {
		ui = ui || this._uiHash();
		$.ui.plugin.call( this, type, [ event, ui, this ], true );

		// Absolute position and offset (see #6884 ) have to be recalculated after plugins
		if ( /^(drag|start|stop)/.test( type ) ) {
			this.positionAbs = this._convertPositionTo( "absolute" );
			ui.offset = this.positionAbs;
		}
		return $.Widget.prototype._trigger.call( this, type, event, ui );
	},

	plugins: {},

	_uiHash: function() {
		return {
			helper: this.helper,
			position: this.position,
			originalPosition: this.originalPosition,
			offset: this.positionAbs
		};
	}

} );

$.ui.plugin.add( "draggable", "connectToSortable", {
	start: function( event, ui, draggable ) {
		var uiSortable = $.extend( {}, ui, {
			item: draggable.element
		} );

		draggable.sortables = [];
		$( draggable.options.connectToSortable ).each( function() {
			var sortable = $( this ).sortable( "instance" );

			if ( sortable && !sortable.options.disabled ) {
				draggable.sortables.push( sortable );

				// RefreshPositions is called at drag start to refresh the containerCache
				// which is used in drag. This ensures it's initialized and synchronized
				// with any changes that might have happened on the page since initialization.
				sortable.refreshPositions();
				sortable._trigger( "activate", event, uiSortable );
			}
		} );
	},
	stop: function( event, ui, draggable ) {
		var uiSortable = $.extend( {}, ui, {
			item: draggable.element
		} );

		draggable.cancelHelperRemoval = false;

		$.each( draggable.sortables, function() {
			var sortable = this;

			if ( sortable.isOver ) {
				sortable.isOver = 0;

				// Allow this sortable to handle removing the helper
				draggable.cancelHelperRemoval = true;
				sortable.cancelHelperRemoval = false;

				// Use _storedCSS To restore properties in the sortable,
				// as this also handles revert (#9675) since the draggable
				// may have modified them in unexpected ways (#8809)
				sortable._storedCSS = {
					position: sortable.placeholder.css( "position" ),
					top: sortable.placeholder.css( "top" ),
					left: sortable.placeholder.css( "left" )
				};

				sortable._mouseStop( event );

				// Once drag has ended, the sortable should return to using
				// its original helper, not the shared helper from draggable
				sortable.options.helper = sortable.options._helper;
			} else {

				// Prevent this Sortable from removing the helper.
				// However, don't set the draggable to remove the helper
				// either as another connected Sortable may yet handle the removal.
				sortable.cancelHelperRemoval = true;

				sortable._trigger( "deactivate", event, uiSortable );
			}
		} );
	},
	drag: function( event, ui, draggable ) {
		$.each( draggable.sortables, function() {
			var innermostIntersecting = false,
				sortable = this;

			// Copy over variables that sortable's _intersectsWith uses
			sortable.positionAbs = draggable.positionAbs;
			sortable.helperProportions = draggable.helperProportions;
			sortable.offset.click = draggable.offset.click;

			if ( sortable._intersectsWith( sortable.containerCache ) ) {
				innermostIntersecting = true;

				$.each( draggable.sortables, function() {

					// Copy over variables that sortable's _intersectsWith uses
					this.positionAbs = draggable.positionAbs;
					this.helperProportions = draggable.helperProportions;
					this.offset.click = draggable.offset.click;

					if ( this !== sortable &&
							this._intersectsWith( this.containerCache ) &&
							$.contains( sortable.element[ 0 ], this.element[ 0 ] ) ) {
						innermostIntersecting = false;
					}

					return innermostIntersecting;
				} );
			}

			if ( innermostIntersecting ) {

				// If it intersects, we use a little isOver variable and set it once,
				// so that the move-in stuff gets fired only once.
				if ( !sortable.isOver ) {
					sortable.isOver = 1;

					// Store draggable's parent in case we need to reappend to it later.
					draggable._parent = ui.helper.parent();

					sortable.currentItem = ui.helper
						.appendTo( sortable.element )
						.data( "ui-sortable-item", true );

					// Store helper option to later restore it
					sortable.options._helper = sortable.options.helper;

					sortable.options.helper = function() {
						return ui.helper[ 0 ];
					};

					// Fire the start events of the sortable with our passed browser event,
					// and our own helper (so it doesn't create a new one)
					event.target = sortable.currentItem[ 0 ];
					sortable._mouseCapture( event, true );
					sortable._mouseStart( event, true, true );

					// Because the browser event is way off the new appended portlet,
					// modify necessary variables to reflect the changes
					sortable.offset.click.top = draggable.offset.click.top;
					sortable.offset.click.left = draggable.offset.click.left;
					sortable.offset.parent.left -= draggable.offset.parent.left -
						sortable.offset.parent.left;
					sortable.offset.parent.top -= draggable.offset.parent.top -
						sortable.offset.parent.top;

					draggable._trigger( "toSortable", event );

					// Inform draggable that the helper is in a valid drop zone,
					// used solely in the revert option to handle "valid/invalid".
					draggable.dropped = sortable.element;

					// Need to refreshPositions of all sortables in the case that
					// adding to one sortable changes the location of the other sortables (#9675)
					$.each( draggable.sortables, function() {
						this.refreshPositions();
					} );

					// Hack so receive/update callbacks work (mostly)
					draggable.currentItem = draggable.element;
					sortable.fromOutside = draggable;
				}

				if ( sortable.currentItem ) {
					sortable._mouseDrag( event );

					// Copy the sortable's position because the draggable's can potentially reflect
					// a relative position, while sortable is always absolute, which the dragged
					// element has now become. (#8809)
					ui.position = sortable.position;
				}
			} else {

				// If it doesn't intersect with the sortable, and it intersected before,
				// we fake the drag stop of the sortable, but make sure it doesn't remove
				// the helper by using cancelHelperRemoval.
				if ( sortable.isOver ) {

					sortable.isOver = 0;
					sortable.cancelHelperRemoval = true;

					// Calling sortable's mouseStop would trigger a revert,
					// so revert must be temporarily false until after mouseStop is called.
					sortable.options._revert = sortable.options.revert;
					sortable.options.revert = false;

					sortable._trigger( "out", event, sortable._uiHash( sortable ) );
					sortable._mouseStop( event, true );

					// Restore sortable behaviors that were modfied
					// when the draggable entered the sortable area (#9481)
					sortable.options.revert = sortable.options._revert;
					sortable.options.helper = sortable.options._helper;

					if ( sortable.placeholder ) {
						sortable.placeholder.remove();
					}

					// Restore and recalculate the draggable's offset considering the sortable
					// may have modified them in unexpected ways. (#8809, #10669)
					ui.helper.appendTo( draggable._parent );
					draggable._refreshOffsets( event );
					ui.position = draggable._generatePosition( event, true );

					draggable._trigger( "fromSortable", event );

					// Inform draggable that the helper is no longer in a valid drop zone
					draggable.dropped = false;

					// Need to refreshPositions of all sortables just in case removing
					// from one sortable changes the location of other sortables (#9675)
					$.each( draggable.sortables, function() {
						this.refreshPositions();
					} );
				}
			}
		} );
	}
} );

$.ui.plugin.add( "draggable", "cursor", {
	start: function( event, ui, instance ) {
		var t = $( "body" ),
			o = instance.options;

		if ( t.css( "cursor" ) ) {
			o._cursor = t.css( "cursor" );
		}
		t.css( "cursor", o.cursor );
	},
	stop: function( event, ui, instance ) {
		var o = instance.options;
		if ( o._cursor ) {
			$( "body" ).css( "cursor", o._cursor );
		}
	}
} );

$.ui.plugin.add( "draggable", "opacity", {
	start: function( event, ui, instance ) {
		var t = $( ui.helper ),
			o = instance.options;
		if ( t.css( "opacity" ) ) {
			o._opacity = t.css( "opacity" );
		}
		t.css( "opacity", o.opacity );
	},
	stop: function( event, ui, instance ) {
		var o = instance.options;
		if ( o._opacity ) {
			$( ui.helper ).css( "opacity", o._opacity );
		}
	}
} );

$.ui.plugin.add( "draggable", "scroll", {
	start: function( event, ui, i ) {
		if ( !i.scrollParentNotHidden ) {
			i.scrollParentNotHidden = i.helper.scrollParent( false );
		}

		if ( i.scrollParentNotHidden[ 0 ] !== i.document[ 0 ] &&
				i.scrollParentNotHidden[ 0 ].tagName !== "HTML" ) {
			i.overflowOffset = i.scrollParentNotHidden.offset();
		}
	},
	drag: function( event, ui, i  ) {

		var o = i.options,
			scrolled = false,
			scrollParent = i.scrollParentNotHidden[ 0 ],
			document = i.document[ 0 ];

		if ( scrollParent !== document && scrollParent.tagName !== "HTML" ) {
			if ( !o.axis || o.axis !== "x" ) {
				if ( ( i.overflowOffset.top + scrollParent.offsetHeight ) - event.pageY <
						o.scrollSensitivity ) {
					scrollParent.scrollTop = scrolled = scrollParent.scrollTop + o.scrollSpeed;
				} else if ( event.pageY - i.overflowOffset.top < o.scrollSensitivity ) {
					scrollParent.scrollTop = scrolled = scrollParent.scrollTop - o.scrollSpeed;
				}
			}

			if ( !o.axis || o.axis !== "y" ) {
				if ( ( i.overflowOffset.left + scrollParent.offsetWidth ) - event.pageX <
						o.scrollSensitivity ) {
					scrollParent.scrollLeft = scrolled = scrollParent.scrollLeft + o.scrollSpeed;
				} else if ( event.pageX - i.overflowOffset.left < o.scrollSensitivity ) {
					scrollParent.scrollLeft = scrolled = scrollParent.scrollLeft - o.scrollSpeed;
				}
			}

		} else {

			if ( !o.axis || o.axis !== "x" ) {
				if ( event.pageY - $( document ).scrollTop() < o.scrollSensitivity ) {
					scrolled = $( document ).scrollTop( $( document ).scrollTop() - o.scrollSpeed );
				} else if ( $( window ).height() - ( event.pageY - $( document ).scrollTop() ) <
						o.scrollSensitivity ) {
					scrolled = $( document ).scrollTop( $( document ).scrollTop() + o.scrollSpeed );
				}
			}

			if ( !o.axis || o.axis !== "y" ) {
				if ( event.pageX - $( document ).scrollLeft() < o.scrollSensitivity ) {
					scrolled = $( document ).scrollLeft(
						$( document ).scrollLeft() - o.scrollSpeed
					);
				} else if ( $( window ).width() - ( event.pageX - $( document ).scrollLeft() ) <
						o.scrollSensitivity ) {
					scrolled = $( document ).scrollLeft(
						$( document ).scrollLeft() + o.scrollSpeed
					);
				}
			}

		}

		if ( scrolled !== false && $.ui.ddmanager && !o.dropBehaviour ) {
			$.ui.ddmanager.prepareOffsets( i, event );
		}

	}
} );

$.ui.plugin.add( "draggable", "snap", {
	start: function( event, ui, i ) {

		var o = i.options;

		i.snapElements = [];

		$( o.snap.constructor !== String ? ( o.snap.items || ":data(ui-draggable)" ) : o.snap )
			.each( function() {
				var $t = $( this ),
					$o = $t.offset();
				if ( this !== i.element[ 0 ] ) {
					i.snapElements.push( {
						item: this,
						width: $t.outerWidth(), height: $t.outerHeight(),
						top: $o.top, left: $o.left
					} );
				}
			} );

	},
	drag: function( event, ui, inst ) {

		var ts, bs, ls, rs, l, r, t, b, i, first,
			o = inst.options,
			d = o.snapTolerance,
			x1 = ui.offset.left, x2 = x1 + inst.helperProportions.width,
			y1 = ui.offset.top, y2 = y1 + inst.helperProportions.height;

		for ( i = inst.snapElements.length - 1; i >= 0; i-- ) {

			l = inst.snapElements[ i ].left - inst.margins.left;
			r = l + inst.snapElements[ i ].width;
			t = inst.snapElements[ i ].top - inst.margins.top;
			b = t + inst.snapElements[ i ].height;

			if ( x2 < l - d || x1 > r + d || y2 < t - d || y1 > b + d ||
					!$.contains( inst.snapElements[ i ].item.ownerDocument,
					inst.snapElements[ i ].item ) ) {
				if ( inst.snapElements[ i ].snapping ) {
					( inst.options.snap.release &&
						inst.options.snap.release.call(
							inst.element,
							event,
							$.extend( inst._uiHash(), { snapItem: inst.snapElements[ i ].item } )
						) );
				}
				inst.snapElements[ i ].snapping = false;
				continue;
			}

			if ( o.snapMode !== "inner" ) {
				ts = Math.abs( t - y2 ) <= d;
				bs = Math.abs( b - y1 ) <= d;
				ls = Math.abs( l - x2 ) <= d;
				rs = Math.abs( r - x1 ) <= d;
				if ( ts ) {
					ui.position.top = inst._convertPositionTo( "relative", {
						top: t - inst.helperProportions.height,
						left: 0
					} ).top;
				}
				if ( bs ) {
					ui.position.top = inst._convertPositionTo( "relative", {
						top: b,
						left: 0
					} ).top;
				}
				if ( ls ) {
					ui.position.left = inst._convertPositionTo( "relative", {
						top: 0,
						left: l - inst.helperProportions.width
					} ).left;
				}
				if ( rs ) {
					ui.position.left = inst._convertPositionTo( "relative", {
						top: 0,
						left: r
					} ).left;
				}
			}

			first = ( ts || bs || ls || rs );

			if ( o.snapMode !== "outer" ) {
				ts = Math.abs( t - y1 ) <= d;
				bs = Math.abs( b - y2 ) <= d;
				ls = Math.abs( l - x1 ) <= d;
				rs = Math.abs( r - x2 ) <= d;
				if ( ts ) {
					ui.position.top = inst._convertPositionTo( "relative", {
						top: t,
						left: 0
					} ).top;
				}
				if ( bs ) {
					ui.position.top = inst._convertPositionTo( "relative", {
						top: b - inst.helperProportions.height,
						left: 0
					} ).top;
				}
				if ( ls ) {
					ui.position.left = inst._convertPositionTo( "relative", {
						top: 0,
						left: l
					} ).left;
				}
				if ( rs ) {
					ui.position.left = inst._convertPositionTo( "relative", {
						top: 0,
						left: r - inst.helperProportions.width
					} ).left;
				}
			}

			if ( !inst.snapElements[ i ].snapping && ( ts || bs || ls || rs || first ) ) {
				( inst.options.snap.snap &&
					inst.options.snap.snap.call(
						inst.element,
						event,
						$.extend( inst._uiHash(), {
							snapItem: inst.snapElements[ i ].item
						} ) ) );
			}
			inst.snapElements[ i ].snapping = ( ts || bs || ls || rs || first );

		}

	}
} );

$.ui.plugin.add( "draggable", "stack", {
	start: function( event, ui, instance ) {
		var min,
			o = instance.options,
			group = $.makeArray( $( o.stack ) ).sort( function( a, b ) {
				return ( parseInt( $( a ).css( "zIndex" ), 10 ) || 0 ) -
					( parseInt( $( b ).css( "zIndex" ), 10 ) || 0 );
			} );

		if ( !group.length ) { return; }

		min = parseInt( $( group[ 0 ] ).css( "zIndex" ), 10 ) || 0;
		$( group ).each( function( i ) {
			$( this ).css( "zIndex", min + i );
		} );
		this.css( "zIndex", ( min + group.length ) );
	}
} );

$.ui.plugin.add( "draggable", "zIndex", {
	start: function( event, ui, instance ) {
		var t = $( ui.helper ),
			o = instance.options;

		if ( t.css( "zIndex" ) ) {
			o._zIndex = t.css( "zIndex" );
		}
		t.css( "zIndex", o.zIndex );
	},
	stop: function( event, ui, instance ) {
		var o = instance.options;

		if ( o._zIndex ) {
			$( ui.helper ).css( "zIndex", o._zIndex );
		}
	}
} );

var widgetsDraggable = $.ui.draggable;


/*!
 * jQuery UI Resizable 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: Resizable
//>>group: Interactions
//>>description: Enables resize functionality for any element.
//>>docs: http://api.jqueryui.com/resizable/
//>>demos: http://jqueryui.com/resizable/
//>>css.structure: ../../themes/base/core.css
//>>css.structure: ../../themes/base/resizable.css
//>>css.theme: ../../themes/base/theme.css



$.widget( "ui.resizable", $.ui.mouse, {
	version: "1.12.0",
	widgetEventPrefix: "resize",
	options: {
		alsoResize: false,
		animate: false,
		animateDuration: "slow",
		animateEasing: "swing",
		aspectRatio: false,
		autoHide: false,
		classes: {
			"ui-resizable-se": "ui-icon ui-icon-gripsmall-diagonal-se"
		},
		containment: false,
		ghost: false,
		grid: false,
		handles: "e,s,se",
		helper: false,
		maxHeight: null,
		maxWidth: null,
		minHeight: 10,
		minWidth: 10,

		// See #7960
		zIndex: 90,

		// Callbacks
		resize: null,
		start: null,
		stop: null
	},

	_num: function( value ) {
		return parseFloat( value ) || 0;
	},

	_isNumber: function( value ) {
		return !isNaN( parseFloat( value ) );
	},

	_hasScroll: function( el, a ) {

		if ( $( el ).css( "overflow" ) === "hidden" ) {
			return false;
		}

		var scroll = ( a && a === "left" ) ? "scrollLeft" : "scrollTop",
			has = false;

		if ( el[ scroll ] > 0 ) {
			return true;
		}

		// TODO: determine which cases actually cause this to happen
		// if the element doesn't have the scroll set, see if it's possible to
		// set the scroll
		el[ scroll ] = 1;
		has = ( el[ scroll ] > 0 );
		el[ scroll ] = 0;
		return has;
	},

	_create: function() {

		var margins,
			o = this.options,
			that = this;
		this._addClass( "ui-resizable" );

		$.extend( this, {
			_aspectRatio: !!( o.aspectRatio ),
			aspectRatio: o.aspectRatio,
			originalElement: this.element,
			_proportionallyResizeElements: [],
			_helper: o.helper || o.ghost || o.animate ? o.helper || "ui-resizable-helper" : null
		} );

		// Wrap the element if it cannot hold child nodes
		if ( this.element[ 0 ].nodeName.match( /^(canvas|textarea|input|select|button|img)$/i ) ) {

			this.element.wrap(
				$( "<div class='ui-wrapper' style='overflow: hidden;'></div>" ).css( {
					position: this.element.css( "position" ),
					width: this.element.outerWidth(),
					height: this.element.outerHeight(),
					top: this.element.css( "top" ),
					left: this.element.css( "left" )
				} )
			);

			this.element = this.element.parent().data(
				"ui-resizable", this.element.resizable( "instance" )
			);

			this.elementIsWrapper = true;

			margins = {
				marginTop: this.originalElement.css( "marginTop" ),
				marginRight: this.originalElement.css( "marginRight" ),
				marginBottom: this.originalElement.css( "marginBottom" ),
				marginLeft: this.originalElement.css( "marginLeft" )
			};

			this.element.css( margins );
			this.originalElement.css( "margin", 0 );

			// support: Safari
			// Prevent Safari textarea resize
			this.originalResizeStyle = this.originalElement.css( "resize" );
			this.originalElement.css( "resize", "none" );

			this._proportionallyResizeElements.push( this.originalElement.css( {
				position: "static",
				zoom: 1,
				display: "block"
			} ) );

			// Support: IE9
			// avoid IE jump (hard set the margin)
			this.originalElement.css( margins );

			this._proportionallyResize();
		}

		this._setupHandles();

		if ( o.autoHide ) {
			$( this.element )
				.on( "mouseenter", function() {
					if ( o.disabled ) {
						return;
					}
					that._removeClass( "ui-resizable-autohide" );
					that._handles.show();
				} )
				.on( "mouseleave", function() {
					if ( o.disabled ) {
						return;
					}
					if ( !that.resizing ) {
						that._addClass( "ui-resizable-autohide" );
						that._handles.hide();
					}
				} );
		}

		this._mouseInit();
	},

	_destroy: function() {

		this._mouseDestroy();

		var wrapper,
			_destroy = function( exp ) {
				$( exp )
					.removeData( "resizable" )
					.removeData( "ui-resizable" )
					.off( ".resizable" )
					.find( ".ui-resizable-handle" )
						.remove();
			};

		// TODO: Unwrap at same DOM position
		if ( this.elementIsWrapper ) {
			_destroy( this.element );
			wrapper = this.element;
			this.originalElement.css( {
				position: wrapper.css( "position" ),
				width: wrapper.outerWidth(),
				height: wrapper.outerHeight(),
				top: wrapper.css( "top" ),
				left: wrapper.css( "left" )
			} ).insertAfter( wrapper );
			wrapper.remove();
		}

		this.originalElement.css( "resize", this.originalResizeStyle );
		_destroy( this.originalElement );

		return this;
	},

	_setOption: function( key, value ) {
		this._super( key, value );

		switch ( key ) {
		case "handles":
			this._removeHandles();
			this._setupHandles();
			break;
		default:
			break;
		}
	},

	_setupHandles: function() {
		var o = this.options, handle, i, n, hname, axis, that = this;
		this.handles = o.handles ||
			( !$( ".ui-resizable-handle", this.element ).length ?
				"e,s,se" : {
					n: ".ui-resizable-n",
					e: ".ui-resizable-e",
					s: ".ui-resizable-s",
					w: ".ui-resizable-w",
					se: ".ui-resizable-se",
					sw: ".ui-resizable-sw",
					ne: ".ui-resizable-ne",
					nw: ".ui-resizable-nw"
				} );

		this._handles = $();
		if ( this.handles.constructor === String ) {

			if ( this.handles === "all" ) {
				this.handles = "n,e,s,w,se,sw,ne,nw";
			}

			n = this.handles.split( "," );
			this.handles = {};

			for ( i = 0; i < n.length; i++ ) {

				handle = $.trim( n[ i ] );
				hname = "ui-resizable-" + handle;
				axis = $( "<div>" );
				this._addClass( axis, "ui-resizable-handle " + hname );

				axis.css( { zIndex: o.zIndex } );

				this.handles[ handle ] = ".ui-resizable-" + handle;
				this.element.append( axis );
			}

		}

		this._renderAxis = function( target ) {

			var i, axis, padPos, padWrapper;

			target = target || this.element;

			for ( i in this.handles ) {

				if ( this.handles[ i ].constructor === String ) {
					this.handles[ i ] = this.element.children( this.handles[ i ] ).first().show();
				} else if ( this.handles[ i ].jquery || this.handles[ i ].nodeType ) {
					this.handles[ i ] = $( this.handles[ i ] );
					this._on( this.handles[ i ], { "mousedown": that._mouseDown } );
				}

				if ( this.elementIsWrapper &&
						this.originalElement[ 0 ]
							.nodeName
							.match( /^(textarea|input|select|button)$/i ) ) {
					axis = $( this.handles[ i ], this.element );

					padWrapper = /sw|ne|nw|se|n|s/.test( i ) ?
						axis.outerHeight() :
						axis.outerWidth();

					padPos = [ "padding",
						/ne|nw|n/.test( i ) ? "Top" :
						/se|sw|s/.test( i ) ? "Bottom" :
						/^e$/.test( i ) ? "Right" : "Left" ].join( "" );

					target.css( padPos, padWrapper );

					this._proportionallyResize();
				}

				this._handles = this._handles.add( this.handles[ i ] );
			}
		};

		// TODO: make renderAxis a prototype function
		this._renderAxis( this.element );

		this._handles = this._handles.add( this.element.find( ".ui-resizable-handle" ) );
		this._handles.disableSelection();

		this._handles.on( "mouseover", function() {
			if ( !that.resizing ) {
				if ( this.className ) {
					axis = this.className.match( /ui-resizable-(se|sw|ne|nw|n|e|s|w)/i );
				}
				that.axis = axis && axis[ 1 ] ? axis[ 1 ] : "se";
			}
		} );

		if ( o.autoHide ) {
			this._handles.hide();
			this._addClass( "ui-resizable-autohide" );
		}
	},

	_removeHandles: function() {
		this._handles.remove();
	},

	_mouseCapture: function( event ) {
		var i, handle,
			capture = false;

		for ( i in this.handles ) {
			handle = $( this.handles[ i ] )[ 0 ];
			if ( handle === event.target || $.contains( handle, event.target ) ) {
				capture = true;
			}
		}

		return !this.options.disabled && capture;
	},

	_mouseStart: function( event ) {

		var curleft, curtop, cursor,
			o = this.options,
			el = this.element;

		this.resizing = true;

		this._renderProxy();

		curleft = this._num( this.helper.css( "left" ) );
		curtop = this._num( this.helper.css( "top" ) );

		if ( o.containment ) {
			curleft += $( o.containment ).scrollLeft() || 0;
			curtop += $( o.containment ).scrollTop() || 0;
		}

		this.offset = this.helper.offset();
		this.position = { left: curleft, top: curtop };

		this.size = this._helper ? {
				width: this.helper.width(),
				height: this.helper.height()
			} : {
				width: el.width(),
				height: el.height()
			};

		this.originalSize = this._helper ? {
				width: el.outerWidth(),
				height: el.outerHeight()
			} : {
				width: el.width(),
				height: el.height()
			};

		this.sizeDiff = {
			width: el.outerWidth() - el.width(),
			height: el.outerHeight() - el.height()
		};

		this.originalPosition = { left: curleft, top: curtop };
		this.originalMousePosition = { left: event.pageX, top: event.pageY };

		this.aspectRatio = ( typeof o.aspectRatio === "number" ) ?
			o.aspectRatio :
			( ( this.originalSize.width / this.originalSize.height ) || 1 );

		cursor = $( ".ui-resizable-" + this.axis ).css( "cursor" );
		$( "body" ).css( "cursor", cursor === "auto" ? this.axis + "-resize" : cursor );

		this._addClass( "ui-resizable-resizing" );
		this._propagate( "start", event );
		return true;
	},

	_mouseDrag: function( event ) {

		var data, props,
			smp = this.originalMousePosition,
			a = this.axis,
			dx = ( event.pageX - smp.left ) || 0,
			dy = ( event.pageY - smp.top ) || 0,
			trigger = this._change[ a ];

		this._updatePrevProperties();

		if ( !trigger ) {
			return false;
		}

		data = trigger.apply( this, [ event, dx, dy ] );

		this._updateVirtualBoundaries( event.shiftKey );
		if ( this._aspectRatio || event.shiftKey ) {
			data = this._updateRatio( data, event );
		}

		data = this._respectSize( data, event );

		this._updateCache( data );

		this._propagate( "resize", event );

		props = this._applyChanges();

		if ( !this._helper && this._proportionallyResizeElements.length ) {
			this._proportionallyResize();
		}

		if ( !$.isEmptyObject( props ) ) {
			this._updatePrevProperties();
			this._trigger( "resize", event, this.ui() );
			this._applyChanges();
		}

		return false;
	},

	_mouseStop: function( event ) {

		this.resizing = false;
		var pr, ista, soffseth, soffsetw, s, left, top,
			o = this.options, that = this;

		if ( this._helper ) {

			pr = this._proportionallyResizeElements;
			ista = pr.length && ( /textarea/i ).test( pr[ 0 ].nodeName );
			soffseth = ista && this._hasScroll( pr[ 0 ], "left" ) ? 0 : that.sizeDiff.height;
			soffsetw = ista ? 0 : that.sizeDiff.width;

			s = {
				width: ( that.helper.width()  - soffsetw ),
				height: ( that.helper.height() - soffseth )
			};
			left = ( parseFloat( that.element.css( "left" ) ) +
				( that.position.left - that.originalPosition.left ) ) || null;
			top = ( parseFloat( that.element.css( "top" ) ) +
				( that.position.top - that.originalPosition.top ) ) || null;

			if ( !o.animate ) {
				this.element.css( $.extend( s, { top: top, left: left } ) );
			}

			that.helper.height( that.size.height );
			that.helper.width( that.size.width );

			if ( this._helper && !o.animate ) {
				this._proportionallyResize();
			}
		}

		$( "body" ).css( "cursor", "auto" );

		this._removeClass( "ui-resizable-resizing" );

		this._propagate( "stop", event );

		if ( this._helper ) {
			this.helper.remove();
		}

		return false;

	},

	_updatePrevProperties: function() {
		this.prevPosition = {
			top: this.position.top,
			left: this.position.left
		};
		this.prevSize = {
			width: this.size.width,
			height: this.size.height
		};
	},

	_applyChanges: function() {
		var props = {};

		if ( this.position.top !== this.prevPosition.top ) {
			props.top = this.position.top + "px";
		}
		if ( this.position.left !== this.prevPosition.left ) {
			props.left = this.position.left + "px";
		}
		if ( this.size.width !== this.prevSize.width ) {
			props.width = this.size.width + "px";
		}
		if ( this.size.height !== this.prevSize.height ) {
			props.height = this.size.height + "px";
		}

		this.helper.css( props );

		return props;
	},

	_updateVirtualBoundaries: function( forceAspectRatio ) {
		var pMinWidth, pMaxWidth, pMinHeight, pMaxHeight, b,
			o = this.options;

		b = {
			minWidth: this._isNumber( o.minWidth ) ? o.minWidth : 0,
			maxWidth: this._isNumber( o.maxWidth ) ? o.maxWidth : Infinity,
			minHeight: this._isNumber( o.minHeight ) ? o.minHeight : 0,
			maxHeight: this._isNumber( o.maxHeight ) ? o.maxHeight : Infinity
		};

		if ( this._aspectRatio || forceAspectRatio ) {
			pMinWidth = b.minHeight * this.aspectRatio;
			pMinHeight = b.minWidth / this.aspectRatio;
			pMaxWidth = b.maxHeight * this.aspectRatio;
			pMaxHeight = b.maxWidth / this.aspectRatio;

			if ( pMinWidth > b.minWidth ) {
				b.minWidth = pMinWidth;
			}
			if ( pMinHeight > b.minHeight ) {
				b.minHeight = pMinHeight;
			}
			if ( pMaxWidth < b.maxWidth ) {
				b.maxWidth = pMaxWidth;
			}
			if ( pMaxHeight < b.maxHeight ) {
				b.maxHeight = pMaxHeight;
			}
		}
		this._vBoundaries = b;
	},

	_updateCache: function( data ) {
		this.offset = this.helper.offset();
		if ( this._isNumber( data.left ) ) {
			this.position.left = data.left;
		}
		if ( this._isNumber( data.top ) ) {
			this.position.top = data.top;
		}
		if ( this._isNumber( data.height ) ) {
			this.size.height = data.height;
		}
		if ( this._isNumber( data.width ) ) {
			this.size.width = data.width;
		}
	},

	_updateRatio: function( data ) {

		var cpos = this.position,
			csize = this.size,
			a = this.axis;

		if ( this._isNumber( data.height ) ) {
			data.width = ( data.height * this.aspectRatio );
		} else if ( this._isNumber( data.width ) ) {
			data.height = ( data.width / this.aspectRatio );
		}

		if ( a === "sw" ) {
			data.left = cpos.left + ( csize.width - data.width );
			data.top = null;
		}
		if ( a === "nw" ) {
			data.top = cpos.top + ( csize.height - data.height );
			data.left = cpos.left + ( csize.width - data.width );
		}

		return data;
	},

	_respectSize: function( data ) {

		var o = this._vBoundaries,
			a = this.axis,
			ismaxw = this._isNumber( data.width ) && o.maxWidth && ( o.maxWidth < data.width ),
			ismaxh = this._isNumber( data.height ) && o.maxHeight && ( o.maxHeight < data.height ),
			isminw = this._isNumber( data.width ) && o.minWidth && ( o.minWidth > data.width ),
			isminh = this._isNumber( data.height ) && o.minHeight && ( o.minHeight > data.height ),
			dw = this.originalPosition.left + this.originalSize.width,
			dh = this.originalPosition.top + this.originalSize.height,
			cw = /sw|nw|w/.test( a ), ch = /nw|ne|n/.test( a );
		if ( isminw ) {
			data.width = o.minWidth;
		}
		if ( isminh ) {
			data.height = o.minHeight;
		}
		if ( ismaxw ) {
			data.width = o.maxWidth;
		}
		if ( ismaxh ) {
			data.height = o.maxHeight;
		}

		if ( isminw && cw ) {
			data.left = dw - o.minWidth;
		}
		if ( ismaxw && cw ) {
			data.left = dw - o.maxWidth;
		}
		if ( isminh && ch ) {
			data.top = dh - o.minHeight;
		}
		if ( ismaxh && ch ) {
			data.top = dh - o.maxHeight;
		}

		// Fixing jump error on top/left - bug #2330
		if ( !data.width && !data.height && !data.left && data.top ) {
			data.top = null;
		} else if ( !data.width && !data.height && !data.top && data.left ) {
			data.left = null;
		}

		return data;
	},

	_getPaddingPlusBorderDimensions: function( element ) {
		var i = 0,
			widths = [],
			borders = [
				element.css( "borderTopWidth" ),
				element.css( "borderRightWidth" ),
				element.css( "borderBottomWidth" ),
				element.css( "borderLeftWidth" )
			],
			paddings = [
				element.css( "paddingTop" ),
				element.css( "paddingRight" ),
				element.css( "paddingBottom" ),
				element.css( "paddingLeft" )
			];

		for ( ; i < 4; i++ ) {
			widths[ i ] = ( parseFloat( borders[ i ] ) || 0 );
			widths[ i ] += ( parseFloat( paddings[ i ] ) || 0 );
		}

		return {
			height: widths[ 0 ] + widths[ 2 ],
			width: widths[ 1 ] + widths[ 3 ]
		};
	},

	_proportionallyResize: function() {

		if ( !this._proportionallyResizeElements.length ) {
			return;
		}

		var prel,
			i = 0,
			element = this.helper || this.element;

		for ( ; i < this._proportionallyResizeElements.length; i++ ) {

			prel = this._proportionallyResizeElements[ i ];

			// TODO: Seems like a bug to cache this.outerDimensions
			// considering that we are in a loop.
			if ( !this.outerDimensions ) {
				this.outerDimensions = this._getPaddingPlusBorderDimensions( prel );
			}

			prel.css( {
				height: ( element.height() - this.outerDimensions.height ) || 0,
				width: ( element.width() - this.outerDimensions.width ) || 0
			} );

		}

	},

	_renderProxy: function() {

		var el = this.element, o = this.options;
		this.elementOffset = el.offset();

		if ( this._helper ) {

			this.helper = this.helper || $( "<div style='overflow:hidden;'></div>" );

			this._addClass( this.helper, this._helper );
			this.helper.css( {
				width: this.element.outerWidth(),
				height: this.element.outerHeight(),
				position: "absolute",
				left: this.elementOffset.left + "px",
				top: this.elementOffset.top + "px",
				zIndex: ++o.zIndex //TODO: Don't modify option
			} );

			this.helper
				.appendTo( "body" )
				.disableSelection();

		} else {
			this.helper = this.element;
		}

	},

	_change: {
		e: function( event, dx ) {
			return { width: this.originalSize.width + dx };
		},
		w: function( event, dx ) {
			var cs = this.originalSize, sp = this.originalPosition;
			return { left: sp.left + dx, width: cs.width - dx };
		},
		n: function( event, dx, dy ) {
			var cs = this.originalSize, sp = this.originalPosition;
			return { top: sp.top + dy, height: cs.height - dy };
		},
		s: function( event, dx, dy ) {
			return { height: this.originalSize.height + dy };
		},
		se: function( event, dx, dy ) {
			return $.extend( this._change.s.apply( this, arguments ),
				this._change.e.apply( this, [ event, dx, dy ] ) );
		},
		sw: function( event, dx, dy ) {
			return $.extend( this._change.s.apply( this, arguments ),
				this._change.w.apply( this, [ event, dx, dy ] ) );
		},
		ne: function( event, dx, dy ) {
			return $.extend( this._change.n.apply( this, arguments ),
				this._change.e.apply( this, [ event, dx, dy ] ) );
		},
		nw: function( event, dx, dy ) {
			return $.extend( this._change.n.apply( this, arguments ),
				this._change.w.apply( this, [ event, dx, dy ] ) );
		}
	},

	_propagate: function( n, event ) {
		$.ui.plugin.call( this, n, [ event, this.ui() ] );
		( n !== "resize" && this._trigger( n, event, this.ui() ) );
	},

	plugins: {},

	ui: function() {
		return {
			originalElement: this.originalElement,
			element: this.element,
			helper: this.helper,
			position: this.position,
			size: this.size,
			originalSize: this.originalSize,
			originalPosition: this.originalPosition
		};
	}

} );

/*
 * Resizable Extensions
 */

$.ui.plugin.add( "resizable", "animate", {

	stop: function( event ) {
		var that = $( this ).resizable( "instance" ),
			o = that.options,
			pr = that._proportionallyResizeElements,
			ista = pr.length && ( /textarea/i ).test( pr[ 0 ].nodeName ),
			soffseth = ista && that._hasScroll( pr[ 0 ], "left" ) ? 0 : that.sizeDiff.height,
			soffsetw = ista ? 0 : that.sizeDiff.width,
			style = {
				width: ( that.size.width - soffsetw ),
				height: ( that.size.height - soffseth )
			},
			left = ( parseFloat( that.element.css( "left" ) ) +
				( that.position.left - that.originalPosition.left ) ) || null,
			top = ( parseFloat( that.element.css( "top" ) ) +
				( that.position.top - that.originalPosition.top ) ) || null;

		that.element.animate(
			$.extend( style, top && left ? { top: top, left: left } : {} ), {
				duration: o.animateDuration,
				easing: o.animateEasing,
				step: function() {

					var data = {
						width: parseFloat( that.element.css( "width" ) ),
						height: parseFloat( that.element.css( "height" ) ),
						top: parseFloat( that.element.css( "top" ) ),
						left: parseFloat( that.element.css( "left" ) )
					};

					if ( pr && pr.length ) {
						$( pr[ 0 ] ).css( { width: data.width, height: data.height } );
					}

					// Propagating resize, and updating values for each animation step
					that._updateCache( data );
					that._propagate( "resize", event );

				}
			}
		);
	}

} );

$.ui.plugin.add( "resizable", "containment", {

	start: function() {
		var element, p, co, ch, cw, width, height,
			that = $( this ).resizable( "instance" ),
			o = that.options,
			el = that.element,
			oc = o.containment,
			ce = ( oc instanceof $ ) ?
				oc.get( 0 ) :
				( /parent/.test( oc ) ) ? el.parent().get( 0 ) : oc;

		if ( !ce ) {
			return;
		}

		that.containerElement = $( ce );

		if ( /document/.test( oc ) || oc === document ) {
			that.containerOffset = {
				left: 0,
				top: 0
			};
			that.containerPosition = {
				left: 0,
				top: 0
			};

			that.parentData = {
				element: $( document ),
				left: 0,
				top: 0,
				width: $( document ).width(),
				height: $( document ).height() || document.body.parentNode.scrollHeight
			};
		} else {
			element = $( ce );
			p = [];
			$( [ "Top", "Right", "Left", "Bottom" ] ).each( function( i, name ) {
				p[ i ] = that._num( element.css( "padding" + name ) );
			} );

			that.containerOffset = element.offset();
			that.containerPosition = element.position();
			that.containerSize = {
				height: ( element.innerHeight() - p[ 3 ] ),
				width: ( element.innerWidth() - p[ 1 ] )
			};

			co = that.containerOffset;
			ch = that.containerSize.height;
			cw = that.containerSize.width;
			width = ( that._hasScroll ( ce, "left" ) ? ce.scrollWidth : cw );
			height = ( that._hasScroll ( ce ) ? ce.scrollHeight : ch ) ;

			that.parentData = {
				element: ce,
				left: co.left,
				top: co.top,
				width: width,
				height: height
			};
		}
	},

	resize: function( event ) {
		var woset, hoset, isParent, isOffsetRelative,
			that = $( this ).resizable( "instance" ),
			o = that.options,
			co = that.containerOffset,
			cp = that.position,
			pRatio = that._aspectRatio || event.shiftKey,
			cop = {
				top: 0,
				left: 0
			},
			ce = that.containerElement,
			continueResize = true;

		if ( ce[ 0 ] !== document && ( /static/ ).test( ce.css( "position" ) ) ) {
			cop = co;
		}

		if ( cp.left < ( that._helper ? co.left : 0 ) ) {
			that.size.width = that.size.width +
				( that._helper ?
					( that.position.left - co.left ) :
					( that.position.left - cop.left ) );

			if ( pRatio ) {
				that.size.height = that.size.width / that.aspectRatio;
				continueResize = false;
			}
			that.position.left = o.helper ? co.left : 0;
		}

		if ( cp.top < ( that._helper ? co.top : 0 ) ) {
			that.size.height = that.size.height +
				( that._helper ?
					( that.position.top - co.top ) :
					that.position.top );

			if ( pRatio ) {
				that.size.width = that.size.height * that.aspectRatio;
				continueResize = false;
			}
			that.position.top = that._helper ? co.top : 0;
		}

		isParent = that.containerElement.get( 0 ) === that.element.parent().get( 0 );
		isOffsetRelative = /relative|absolute/.test( that.containerElement.css( "position" ) );

		if ( isParent && isOffsetRelative ) {
			that.offset.left = that.parentData.left + that.position.left;
			that.offset.top = that.parentData.top + that.position.top;
		} else {
			that.offset.left = that.element.offset().left;
			that.offset.top = that.element.offset().top;
		}

		woset = Math.abs( that.sizeDiff.width +
			( that._helper ?
				that.offset.left - cop.left :
				( that.offset.left - co.left ) ) );

		hoset = Math.abs( that.sizeDiff.height +
			( that._helper ?
				that.offset.top - cop.top :
				( that.offset.top - co.top ) ) );

		if ( woset + that.size.width >= that.parentData.width ) {
			that.size.width = that.parentData.width - woset;
			if ( pRatio ) {
				that.size.height = that.size.width / that.aspectRatio;
				continueResize = false;
			}
		}

		if ( hoset + that.size.height >= that.parentData.height ) {
			that.size.height = that.parentData.height - hoset;
			if ( pRatio ) {
				that.size.width = that.size.height * that.aspectRatio;
				continueResize = false;
			}
		}

		if ( !continueResize ) {
			that.position.left = that.prevPosition.left;
			that.position.top = that.prevPosition.top;
			that.size.width = that.prevSize.width;
			that.size.height = that.prevSize.height;
		}
	},

	stop: function() {
		var that = $( this ).resizable( "instance" ),
			o = that.options,
			co = that.containerOffset,
			cop = that.containerPosition,
			ce = that.containerElement,
			helper = $( that.helper ),
			ho = helper.offset(),
			w = helper.outerWidth() - that.sizeDiff.width,
			h = helper.outerHeight() - that.sizeDiff.height;

		if ( that._helper && !o.animate && ( /relative/ ).test( ce.css( "position" ) ) ) {
			$( this ).css( {
				left: ho.left - cop.left - co.left,
				width: w,
				height: h
			} );
		}

		if ( that._helper && !o.animate && ( /static/ ).test( ce.css( "position" ) ) ) {
			$( this ).css( {
				left: ho.left - cop.left - co.left,
				width: w,
				height: h
			} );
		}
	}
} );

$.ui.plugin.add( "resizable", "alsoResize", {

	start: function() {
		var that = $( this ).resizable( "instance" ),
			o = that.options;

		$( o.alsoResize ).each( function() {
			var el = $( this );
			el.data( "ui-resizable-alsoresize", {
				width: parseFloat( el.width() ), height: parseFloat( el.height() ),
				left: parseFloat( el.css( "left" ) ), top: parseFloat( el.css( "top" ) )
			} );
		} );
	},

	resize: function( event, ui ) {
		var that = $( this ).resizable( "instance" ),
			o = that.options,
			os = that.originalSize,
			op = that.originalPosition,
			delta = {
				height: ( that.size.height - os.height ) || 0,
				width: ( that.size.width - os.width ) || 0,
				top: ( that.position.top - op.top ) || 0,
				left: ( that.position.left - op.left ) || 0
			};

			$( o.alsoResize ).each( function() {
				var el = $( this ), start = $( this ).data( "ui-resizable-alsoresize" ), style = {},
					css = el.parents( ui.originalElement[ 0 ] ).length ?
							[ "width", "height" ] :
							[ "width", "height", "top", "left" ];

				$.each( css, function( i, prop ) {
					var sum = ( start[ prop ] || 0 ) + ( delta[ prop ] || 0 );
					if ( sum && sum >= 0 ) {
						style[ prop ] = sum || null;
					}
				} );

				el.css( style );
			} );
	},

	stop: function() {
		$( this ).removeData( "ui-resizable-alsoresize" );
	}
} );

$.ui.plugin.add( "resizable", "ghost", {

	start: function() {

		var that = $( this ).resizable( "instance" ), cs = that.size;

		that.ghost = that.originalElement.clone();
		that.ghost.css( {
			opacity: 0.25,
			display: "block",
			position: "relative",
			height: cs.height,
			width: cs.width,
			margin: 0,
			left: 0,
			top: 0
		} );

		that._addClass( that.ghost, "ui-resizable-ghost" );

		// DEPRECATED
		// TODO: remove after 1.12
		if ( $.uiBackCompat !== false && typeof that.options.ghost === "string" ) {

			// Ghost option
			that.ghost.addClass( this.options.ghost );
		}

		that.ghost.appendTo( that.helper );

	},

	resize: function() {
		var that = $( this ).resizable( "instance" );
		if ( that.ghost ) {
			that.ghost.css( {
				position: "relative",
				height: that.size.height,
				width: that.size.width
			} );
		}
	},

	stop: function() {
		var that = $( this ).resizable( "instance" );
		if ( that.ghost && that.helper ) {
			that.helper.get( 0 ).removeChild( that.ghost.get( 0 ) );
		}
	}

} );

$.ui.plugin.add( "resizable", "grid", {

	resize: function() {
		var outerDimensions,
			that = $( this ).resizable( "instance" ),
			o = that.options,
			cs = that.size,
			os = that.originalSize,
			op = that.originalPosition,
			a = that.axis,
			grid = typeof o.grid === "number" ? [ o.grid, o.grid ] : o.grid,
			gridX = ( grid[ 0 ] || 1 ),
			gridY = ( grid[ 1 ] || 1 ),
			ox = Math.round( ( cs.width - os.width ) / gridX ) * gridX,
			oy = Math.round( ( cs.height - os.height ) / gridY ) * gridY,
			newWidth = os.width + ox,
			newHeight = os.height + oy,
			isMaxWidth = o.maxWidth && ( o.maxWidth < newWidth ),
			isMaxHeight = o.maxHeight && ( o.maxHeight < newHeight ),
			isMinWidth = o.minWidth && ( o.minWidth > newWidth ),
			isMinHeight = o.minHeight && ( o.minHeight > newHeight );

		o.grid = grid;

		if ( isMinWidth ) {
			newWidth += gridX;
		}
		if ( isMinHeight ) {
			newHeight += gridY;
		}
		if ( isMaxWidth ) {
			newWidth -= gridX;
		}
		if ( isMaxHeight ) {
			newHeight -= gridY;
		}

		if ( /^(se|s|e)$/.test( a ) ) {
			that.size.width = newWidth;
			that.size.height = newHeight;
		} else if ( /^(ne)$/.test( a ) ) {
			that.size.width = newWidth;
			that.size.height = newHeight;
			that.position.top = op.top - oy;
		} else if ( /^(sw)$/.test( a ) ) {
			that.size.width = newWidth;
			that.size.height = newHeight;
			that.position.left = op.left - ox;
		} else {
			if ( newHeight - gridY <= 0 || newWidth - gridX <= 0 ) {
				outerDimensions = that._getPaddingPlusBorderDimensions( this );
			}

			if ( newHeight - gridY > 0 ) {
				that.size.height = newHeight;
				that.position.top = op.top - oy;
			} else {
				newHeight = gridY - outerDimensions.height;
				that.size.height = newHeight;
				that.position.top = op.top + os.height - newHeight;
			}
			if ( newWidth - gridX > 0 ) {
				that.size.width = newWidth;
				that.position.left = op.left - ox;
			} else {
				newWidth = gridX - outerDimensions.width;
				that.size.width = newWidth;
				that.position.left = op.left + os.width - newWidth;
			}
		}
	}

} );

var widgetsResizable = $.ui.resizable;


/*!
 * jQuery UI Dialog 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: Dialog
//>>group: Widgets
//>>description: Displays customizable dialog windows.
//>>docs: http://api.jqueryui.com/dialog/
//>>demos: http://jqueryui.com/dialog/
//>>css.structure: ../../themes/base/core.css
//>>css.structure: ../../themes/base/dialog.css
//>>css.theme: ../../themes/base/theme.css



$.widget( "ui.dialog", {
	version: "1.12.0",
	options: {
		appendTo: "body",
		autoOpen: true,
		buttons: [],
		classes: {
			"ui-dialog": "ui-corner-all",
			"ui-dialog-titlebar": "ui-corner-all"
		},
		closeOnEscape: true,
		closeText: "Close",
		draggable: true,
		hide: null,
		height: "auto",
		maxHeight: null,
		maxWidth: null,
		minHeight: 150,
		minWidth: 150,
		modal: false,
		position: {
			my: "center",
			at: "center",
			of: window,
			collision: "fit",

			// Ensure the titlebar is always visible
			using: function( pos ) {
				var topOffset = $( this ).css( pos ).offset().top;
				if ( topOffset < 0 ) {
					$( this ).css( "top", pos.top - topOffset );
				}
			}
		},
		resizable: true,
		show: null,
		title: null,
		width: 300,

		// Callbacks
		beforeClose: null,
		close: null,
		drag: null,
		dragStart: null,
		dragStop: null,
		focus: null,
		open: null,
		resize: null,
		resizeStart: null,
		resizeStop: null
	},

	sizeRelatedOptions: {
		buttons: true,
		height: true,
		maxHeight: true,
		maxWidth: true,
		minHeight: true,
		minWidth: true,
		width: true
	},

	resizableRelatedOptions: {
		maxHeight: true,
		maxWidth: true,
		minHeight: true,
		minWidth: true
	},

	_create: function() {
		this.originalCss = {
			display: this.element[ 0 ].style.display,
			width: this.element[ 0 ].style.width,
			minHeight: this.element[ 0 ].style.minHeight,
			maxHeight: this.element[ 0 ].style.maxHeight,
			height: this.element[ 0 ].style.height
		};
		this.originalPosition = {
			parent: this.element.parent(),
			index: this.element.parent().children().index( this.element )
		};
		this.originalTitle = this.element.attr( "title" );
		if ( this.options.title == null && this.originalTitle != null ) {
			this.options.title = this.originalTitle;
		}

		// Dialogs can't be disabled
		if ( this.options.disabled ) {
			this.options.disabled = false;
		}

		this._createWrapper();

		this.element
			.show()
			.removeAttr( "title" )
			.appendTo( this.uiDialog );

		this._addClass( "ui-dialog-content", "ui-widget-content" );

		this._createTitlebar();
		this._createButtonPane();

		if ( this.options.draggable && $.fn.draggable ) {
			this._makeDraggable();
		}
		if ( this.options.resizable && $.fn.resizable ) {
			this._makeResizable();
		}

		this._isOpen = false;

		this._trackFocus();
	},

	_init: function() {
		if ( this.options.autoOpen ) {
			this.open();
		}
	},

	_appendTo: function() {
		var element = this.options.appendTo;
		if ( element && ( element.jquery || element.nodeType ) ) {
			return $( element );
		}
		return this.document.find( element || "body" ).eq( 0 );
	},

	_destroy: function() {
		var next,
			originalPosition = this.originalPosition;

		this._untrackInstance();
		this._destroyOverlay();

		this.element
			.removeUniqueId()
			.css( this.originalCss )

			// Without detaching first, the following becomes really slow
			.detach();

		this.uiDialog.remove();

		if ( this.originalTitle ) {
			this.element.attr( "title", this.originalTitle );
		}

		next = originalPosition.parent.children().eq( originalPosition.index );

		// Don't try to place the dialog next to itself (#8613)
		if ( next.length && next[ 0 ] !== this.element[ 0 ] ) {
			next.before( this.element );
		} else {
			originalPosition.parent.append( this.element );
		}
	},

	widget: function() {
		return this.uiDialog;
	},

	disable: $.noop,
	enable: $.noop,

	close: function( event ) {
		var that = this;

		if ( !this._isOpen || this._trigger( "beforeClose", event ) === false ) {
			return;
		}

		this._isOpen = false;
		this._focusedElement = null;
		this._destroyOverlay();
		this._untrackInstance();

		if ( !this.opener.filter( ":focusable" ).trigger( "focus" ).length ) {

			// Hiding a focused element doesn't trigger blur in WebKit
			// so in case we have nothing to focus on, explicitly blur the active element
			// https://bugs.webkit.org/show_bug.cgi?id=47182
			$.ui.safeBlur( $.ui.safeActiveElement( this.document[ 0 ] ) );
		}

		this._hide( this.uiDialog, this.options.hide, function() {
			that._trigger( "close", event );
		} );
	},

	isOpen: function() {
		return this._isOpen;
	},

	moveToTop: function() {
		this._moveToTop();
	},

	_moveToTop: function( event, silent ) {
		var moved = false,
			zIndices = this.uiDialog.siblings( ".ui-front:visible" ).map( function() {
				return +$( this ).css( "z-index" );
			} ).get(),
			zIndexMax = Math.max.apply( null, zIndices );

		if ( zIndexMax >= +this.uiDialog.css( "z-index" ) ) {
			this.uiDialog.css( "z-index", zIndexMax + 1 );
			moved = true;
		}

		if ( moved && !silent ) {
			this._trigger( "focus", event );
		}
		return moved;
	},

	open: function() {
		var that = this;
		if ( this._isOpen ) {
			if ( this._moveToTop() ) {
				this._focusTabbable();
			}
			return;
		}

		this._isOpen = true;
		this.opener = $( $.ui.safeActiveElement( this.document[ 0 ] ) );

		this._size();
		this._position();
		this._createOverlay();
		this._moveToTop( null, true );

		// Ensure the overlay is moved to the top with the dialog, but only when
		// opening. The overlay shouldn't move after the dialog is open so that
		// modeless dialogs opened after the modal dialog stack properly.
		if ( this.overlay ) {
			this.overlay.css( "z-index", this.uiDialog.css( "z-index" ) - 1 );
		}

		this._show( this.uiDialog, this.options.show, function() {
			that._focusTabbable();
			that._trigger( "focus" );
		} );

		// Track the dialog immediately upon openening in case a focus event
		// somehow occurs outside of the dialog before an element inside the
		// dialog is focused (#10152)
		this._makeFocusTarget();

		this._trigger( "open" );
	},

	_focusTabbable: function() {

		// Set focus to the first match:
		// 1. An element that was focused previously
		// 2. First element inside the dialog matching [autofocus]
		// 3. Tabbable element inside the content element
		// 4. Tabbable element inside the buttonpane
		// 5. The close button
		// 6. The dialog itself
		var hasFocus = this._focusedElement;
		if ( !hasFocus ) {
			hasFocus = this.element.find( "[autofocus]" );
		}
		if ( !hasFocus.length ) {
			hasFocus = this.element.find( ":tabbable" );
		}
		if ( !hasFocus.length ) {
			hasFocus = this.uiDialogButtonPane.find( ":tabbable" );
		}
		if ( !hasFocus.length ) {
			hasFocus = this.uiDialogTitlebarClose.filter( ":tabbable" );
		}
		if ( !hasFocus.length ) {
			hasFocus = this.uiDialog;
		}
		hasFocus.eq( 0 ).trigger( "focus" );
	},

	_keepFocus: function( event ) {
		function checkFocus() {
			var activeElement = $.ui.safeActiveElement( this.document[ 0 ] ),
				isActive = this.uiDialog[ 0 ] === activeElement ||
					$.contains( this.uiDialog[ 0 ], activeElement );
			if ( !isActive ) {
				this._focusTabbable();
			}
		}
		event.preventDefault();
		checkFocus.call( this );

		// support: IE
		// IE <= 8 doesn't prevent moving focus even with event.preventDefault()
		// so we check again later
		this._delay( checkFocus );
	},

	_createWrapper: function() {
		this.uiDialog = $( "<div>" )
			.hide()
			.attr( {

				// Setting tabIndex makes the div focusable
				tabIndex: -1,
				role: "dialog"
			} )
			.appendTo( this._appendTo() );

		this._addClass( this.uiDialog, "ui-dialog", "ui-widget ui-widget-content ui-front" );
		this._on( this.uiDialog, {
			keydown: function( event ) {
				if ( this.options.closeOnEscape && !event.isDefaultPrevented() && event.keyCode &&
						event.keyCode === $.ui.keyCode.ESCAPE ) {
					event.preventDefault();
					this.close( event );
					return;
				}

				// Prevent tabbing out of dialogs
				if ( event.keyCode !== $.ui.keyCode.TAB || event.isDefaultPrevented() ) {
					return;
				}
				var tabbables = this.uiDialog.find( ":tabbable" ),
					first = tabbables.filter( ":first" ),
					last = tabbables.filter( ":last" );

				if ( ( event.target === last[ 0 ] || event.target === this.uiDialog[ 0 ] ) &&
						!event.shiftKey ) {
					this._delay( function() {
						first.trigger( "focus" );
					} );
					event.preventDefault();
				} else if ( ( event.target === first[ 0 ] ||
						event.target === this.uiDialog[ 0 ] ) && event.shiftKey ) {
					this._delay( function() {
						last.trigger( "focus" );
					} );
					event.preventDefault();
				}
			},
			mousedown: function( event ) {
				if ( this._moveToTop( event ) ) {
					this._focusTabbable();
				}
			}
		} );

		// We assume that any existing aria-describedby attribute means
		// that the dialog content is marked up properly
		// otherwise we brute force the content as the description
		if ( !this.element.find( "[aria-describedby]" ).length ) {
			this.uiDialog.attr( {
				"aria-describedby": this.element.uniqueId().attr( "id" )
			} );
		}
	},

	_createTitlebar: function() {
		var uiDialogTitle;

		this.uiDialogTitlebar = $( "<div>" );
		this._addClass( this.uiDialogTitlebar,
			"ui-dialog-titlebar", "ui-widget-header ui-helper-clearfix" );
		this._on( this.uiDialogTitlebar, {
			mousedown: function( event ) {

				// Don't prevent click on close button (#8838)
				// Focusing a dialog that is partially scrolled out of view
				// causes the browser to scroll it into view, preventing the click event
				if ( !$( event.target ).closest( ".ui-dialog-titlebar-close" ) ) {

					// Dialog isn't getting focus when dragging (#8063)
					this.uiDialog.trigger( "focus" );
				}
			}
		} );

		// Support: IE
		// Use type="button" to prevent enter keypresses in textboxes from closing the
		// dialog in IE (#9312)
		this.uiDialogTitlebarClose = $( "<button type='button'></button>" )
			.button( {
				label: $( "<a>" ).text( this.options.closeText ).html(),
				icon: "ui-icon-closethick",
				showLabel: false
			} )
			.appendTo( this.uiDialogTitlebar );

		this._addClass( this.uiDialogTitlebarClose, "ui-dialog-titlebar-close" );
		this._on( this.uiDialogTitlebarClose, {
			click: function( event ) {
				event.preventDefault();
				this.close( event );
			}
		} );

		uiDialogTitle = $( "<span>" ).uniqueId().prependTo( this.uiDialogTitlebar );
		this._addClass( uiDialogTitle, "ui-dialog-title" );
		this._title( uiDialogTitle );

		this.uiDialogTitlebar.prependTo( this.uiDialog );

		this.uiDialog.attr( {
			"aria-labelledby": uiDialogTitle.attr( "id" )
		} );
	},

	_title: function( title ) {
		if ( this.options.title ) {
			title.text( this.options.title );
		} else {
			title.html( "&#160;" );
		}
	},

	_createButtonPane: function() {
		this.uiDialogButtonPane = $( "<div>" );
		this._addClass( this.uiDialogButtonPane, "ui-dialog-buttonpane",
			"ui-widget-content ui-helper-clearfix" );

		this.uiButtonSet = $( "<div>" )
			.appendTo( this.uiDialogButtonPane );
		this._addClass( this.uiButtonSet, "ui-dialog-buttonset" );

		this._createButtons();
	},

	_createButtons: function() {
		var that = this,
			buttons = this.options.buttons;

		// If we already have a button pane, remove it
		this.uiDialogButtonPane.remove();
		this.uiButtonSet.empty();

		if ( $.isEmptyObject( buttons ) || ( $.isArray( buttons ) && !buttons.length ) ) {
			this._removeClass( this.uiDialog, "ui-dialog-buttons" );
			return;
		}

		$.each( buttons, function( name, props ) {
			var click, buttonOptions;
			props = $.isFunction( props ) ?
				{ click: props, text: name } :
				props;

			// Default to a non-submitting button
			props = $.extend( { type: "button" }, props );

			// Change the context for the click callback to be the main element
			click = props.click;
			buttonOptions = {
				icon: props.icon,
				iconPosition: props.iconPosition,
				showLabel: props.showLabel
			};

			delete props.click;
			delete props.icon;
			delete props.iconPosition;
			delete props.showLabel;

			$( "<button></button>", props )
				.button( buttonOptions )
				.appendTo( that.uiButtonSet )
				.on( "click", function() {
					click.apply( that.element[ 0 ], arguments );
				} );
		} );
		this._addClass( this.uiDialog, "ui-dialog-buttons" );
		this.uiDialogButtonPane.appendTo( this.uiDialog );
	},

	_makeDraggable: function() {
		var that = this,
			options = this.options;

		function filteredUi( ui ) {
			return {
				position: ui.position,
				offset: ui.offset
			};
		}

		this.uiDialog.draggable( {
			cancel: ".ui-dialog-content, .ui-dialog-titlebar-close",
			handle: ".ui-dialog-titlebar",
			containment: "document",
			start: function( event, ui ) {
				that._addClass( $( this ), "ui-dialog-dragging" );
				that._blockFrames();
				that._trigger( "dragStart", event, filteredUi( ui ) );
			},
			drag: function( event, ui ) {
				that._trigger( "drag", event, filteredUi( ui ) );
			},
			stop: function( event, ui ) {
				var left = ui.offset.left - that.document.scrollLeft(),
					top = ui.offset.top - that.document.scrollTop();

				options.position = {
					my: "left top",
					at: "left" + ( left >= 0 ? "+" : "" ) + left + " " +
						"top" + ( top >= 0 ? "+" : "" ) + top,
					of: that.window
				};
				that._removeClass( $( this ), "ui-dialog-dragging" );
				that._unblockFrames();
				that._trigger( "dragStop", event, filteredUi( ui ) );
			}
		} );
	},

	_makeResizable: function() {
		var that = this,
			options = this.options,
			handles = options.resizable,

			// .ui-resizable has position: relative defined in the stylesheet
			// but dialogs have to use absolute or fixed positioning
			position = this.uiDialog.css( "position" ),
			resizeHandles = typeof handles === "string" ?
				handles :
				"n,e,s,w,se,sw,ne,nw";

		function filteredUi( ui ) {
			return {
				originalPosition: ui.originalPosition,
				originalSize: ui.originalSize,
				position: ui.position,
				size: ui.size
			};
		}

		this.uiDialog.resizable( {
			cancel: ".ui-dialog-content",
			containment: "document",
			alsoResize: this.element,
			maxWidth: options.maxWidth,
			maxHeight: options.maxHeight,
			minWidth: options.minWidth,
			minHeight: this._minHeight(),
			handles: resizeHandles,
			start: function( event, ui ) {
				that._addClass( $( this ), "ui-dialog-resizing" );
				that._blockFrames();
				that._trigger( "resizeStart", event, filteredUi( ui ) );
			},
			resize: function( event, ui ) {
				that._trigger( "resize", event, filteredUi( ui ) );
			},
			stop: function( event, ui ) {
				var offset = that.uiDialog.offset(),
					left = offset.left - that.document.scrollLeft(),
					top = offset.top - that.document.scrollTop();

				options.height = that.uiDialog.height();
				options.width = that.uiDialog.width();
				options.position = {
					my: "left top",
					at: "left" + ( left >= 0 ? "+" : "" ) + left + " " +
						"top" + ( top >= 0 ? "+" : "" ) + top,
					of: that.window
				};
				that._removeClass( $( this ), "ui-dialog-resizing" );
				that._unblockFrames();
				that._trigger( "resizeStop", event, filteredUi( ui ) );
			}
		} )
			.css( "position", position );
	},

	_trackFocus: function() {
		this._on( this.widget(), {
			focusin: function( event ) {
				this._makeFocusTarget();
				this._focusedElement = $( event.target );
			}
		} );
	},

	_makeFocusTarget: function() {
		this._untrackInstance();
		this._trackingInstances().unshift( this );
	},

	_untrackInstance: function() {
		var instances = this._trackingInstances(),
			exists = $.inArray( this, instances );
		if ( exists !== -1 ) {
			instances.splice( exists, 1 );
		}
	},

	_trackingInstances: function() {
		var instances = this.document.data( "ui-dialog-instances" );
		if ( !instances ) {
			instances = [];
			this.document.data( "ui-dialog-instances", instances );
		}
		return instances;
	},

	_minHeight: function() {
		var options = this.options;

		return options.height === "auto" ?
			options.minHeight :
			Math.min( options.minHeight, options.height );
	},

	_position: function() {

		// Need to show the dialog to get the actual offset in the position plugin
		var isVisible = this.uiDialog.is( ":visible" );
		if ( !isVisible ) {
			this.uiDialog.show();
		}
		this.uiDialog.position( this.options.position );
		if ( !isVisible ) {
			this.uiDialog.hide();
		}
	},

	_setOptions: function( options ) {
		var that = this,
			resize = false,
			resizableOptions = {};

		$.each( options, function( key, value ) {
			that._setOption( key, value );

			if ( key in that.sizeRelatedOptions ) {
				resize = true;
			}
			if ( key in that.resizableRelatedOptions ) {
				resizableOptions[ key ] = value;
			}
		} );

		if ( resize ) {
			this._size();
			this._position();
		}
		if ( this.uiDialog.is( ":data(ui-resizable)" ) ) {
			this.uiDialog.resizable( "option", resizableOptions );
		}
	},

	_setOption: function( key, value ) {
		var isDraggable, isResizable,
			uiDialog = this.uiDialog;

		if ( key === "disabled" ) {
			return;
		}

		this._super( key, value );

		if ( key === "appendTo" ) {
			this.uiDialog.appendTo( this._appendTo() );
		}

		if ( key === "buttons" ) {
			this._createButtons();
		}

		if ( key === "closeText" ) {
			this.uiDialogTitlebarClose.button( {

				// Ensure that we always pass a string
				label: $( "<a>" ).text( "" + this.options.closeText ).html()
			} );
		}

		if ( key === "draggable" ) {
			isDraggable = uiDialog.is( ":data(ui-draggable)" );
			if ( isDraggable && !value ) {
				uiDialog.draggable( "destroy" );
			}

			if ( !isDraggable && value ) {
				this._makeDraggable();
			}
		}

		if ( key === "position" ) {
			this._position();
		}

		if ( key === "resizable" ) {

			// currently resizable, becoming non-resizable
			isResizable = uiDialog.is( ":data(ui-resizable)" );
			if ( isResizable && !value ) {
				uiDialog.resizable( "destroy" );
			}

			// Currently resizable, changing handles
			if ( isResizable && typeof value === "string" ) {
				uiDialog.resizable( "option", "handles", value );
			}

			// Currently non-resizable, becoming resizable
			if ( !isResizable && value !== false ) {
				this._makeResizable();
			}
		}

		if ( key === "title" ) {
			this._title( this.uiDialogTitlebar.find( ".ui-dialog-title" ) );
		}
	},

	_size: function() {

		// If the user has resized the dialog, the .ui-dialog and .ui-dialog-content
		// divs will both have width and height set, so we need to reset them
		var nonContentHeight, minContentHeight, maxContentHeight,
			options = this.options;

		// Reset content sizing
		this.element.show().css( {
			width: "auto",
			minHeight: 0,
			maxHeight: "none",
			height: 0
		} );

		if ( options.minWidth > options.width ) {
			options.width = options.minWidth;
		}

		// Reset wrapper sizing
		// determine the height of all the non-content elements
		nonContentHeight = this.uiDialog.css( {
			height: "auto",
			width: options.width
		} )
			.outerHeight();
		minContentHeight = Math.max( 0, options.minHeight - nonContentHeight );
		maxContentHeight = typeof options.maxHeight === "number" ?
			Math.max( 0, options.maxHeight - nonContentHeight ) :
			"none";

		if ( options.height === "auto" ) {
			this.element.css( {
				minHeight: minContentHeight,
				maxHeight: maxContentHeight,
				height: "auto"
			} );
		} else {
			this.element.height( Math.max( 0, options.height - nonContentHeight ) );
		}

		if ( this.uiDialog.is( ":data(ui-resizable)" ) ) {
			this.uiDialog.resizable( "option", "minHeight", this._minHeight() );
		}
	},

	_blockFrames: function() {
		this.iframeBlocks = this.document.find( "iframe" ).map( function() {
			var iframe = $( this );

			return $( "<div>" )
				.css( {
					position: "absolute",
					width: iframe.outerWidth(),
					height: iframe.outerHeight()
				} )
				.appendTo( iframe.parent() )
				.offset( iframe.offset() )[ 0 ];
		} );
	},

	_unblockFrames: function() {
		if ( this.iframeBlocks ) {
			this.iframeBlocks.remove();
			delete this.iframeBlocks;
		}
	},

	_allowInteraction: function( event ) {
		if ( $( event.target ).closest( ".ui-dialog" ).length ) {
			return true;
		}

		// TODO: Remove hack when datepicker implements
		// the .ui-front logic (#8989)
		return !!$( event.target ).closest( ".ui-datepicker" ).length;
	},

	_createOverlay: function() {
		if ( !this.options.modal ) {
			return;
		}

		// We use a delay in case the overlay is created from an
		// event that we're going to be cancelling (#2804)
		var isOpening = true;
		this._delay( function() {
			isOpening = false;
		} );

		if ( !this.document.data( "ui-dialog-overlays" ) ) {

			// Prevent use of anchors and inputs
			// Using _on() for an event handler shared across many instances is
			// safe because the dialogs stack and must be closed in reverse order
			this._on( this.document, {
				focusin: function( event ) {
					if ( isOpening ) {
						return;
					}

					if ( !this._allowInteraction( event ) ) {
						event.preventDefault();
						this._trackingInstances()[ 0 ]._focusTabbable();
					}
				}
			} );
		}

		this.overlay = $( "<div>" )
			.appendTo( this._appendTo() );

		this._addClass( this.overlay, null, "ui-widget-overlay ui-front" );
		this._on( this.overlay, {
			mousedown: "_keepFocus"
		} );
		this.document.data( "ui-dialog-overlays",
			( this.document.data( "ui-dialog-overlays" ) || 0 ) + 1 );
	},

	_destroyOverlay: function() {
		if ( !this.options.modal ) {
			return;
		}

		if ( this.overlay ) {
			var overlays = this.document.data( "ui-dialog-overlays" ) - 1;

			if ( !overlays ) {
				this._off( this.document, "focusin" );
				this.document.removeData( "ui-dialog-overlays" );
			} else {
				this.document.data( "ui-dialog-overlays", overlays );
			}

			this.overlay.remove();
			this.overlay = null;
		}
	}
} );

// DEPRECATED
// TODO: switch return back to widget declaration at top of file when this is removed
if ( $.uiBackCompat !== false ) {

	// Backcompat for dialogClass option
	$.widget( "ui.dialog", $.ui.dialog, {
		options: {
			dialogClass: ""
		},
		_createWrapper: function() {
			this._super();
			this.uiDialog.addClass( this.options.dialogClass );
		},
		_setOption: function( key, value ) {
			if ( key === "dialogClass" ) {
				this.uiDialog
					.removeClass( this.options.dialogClass )
					.addClass( value );
			}
			this._superApply( arguments );
		}
	} );
}

var widgetsDialog = $.ui.dialog;


/*!
 * jQuery UI Droppable 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: Droppable
//>>group: Interactions
//>>description: Enables drop targets for draggable elements.
//>>docs: http://api.jqueryui.com/droppable/
//>>demos: http://jqueryui.com/droppable/



$.widget( "ui.droppable", {
	version: "1.12.0",
	widgetEventPrefix: "drop",
	options: {
		accept: "*",
		addClasses: true,
		greedy: false,
		scope: "default",
		tolerance: "intersect",

		// Callbacks
		activate: null,
		deactivate: null,
		drop: null,
		out: null,
		over: null
	},
	_create: function() {

		var proportions,
			o = this.options,
			accept = o.accept;

		this.isover = false;
		this.isout = true;

		this.accept = $.isFunction( accept ) ? accept : function( d ) {
			return d.is( accept );
		};

		this.proportions = function( /* valueToWrite */ ) {
			if ( arguments.length ) {

				// Store the droppable's proportions
				proportions = arguments[ 0 ];
			} else {

				// Retrieve or derive the droppable's proportions
				return proportions ?
					proportions :
					proportions = {
						width: this.element[ 0 ].offsetWidth,
						height: this.element[ 0 ].offsetHeight
					};
			}
		};

		this._addToManager( o.scope );

		o.addClasses && this._addClass( "ui-droppable" );

	},

	_addToManager: function( scope ) {

		// Add the reference and positions to the manager
		$.ui.ddmanager.droppables[ scope ] = $.ui.ddmanager.droppables[ scope ] || [];
		$.ui.ddmanager.droppables[ scope ].push( this );
	},

	_splice: function( drop ) {
		var i = 0;
		for ( ; i < drop.length; i++ ) {
			if ( drop[ i ] === this ) {
				drop.splice( i, 1 );
			}
		}
	},

	_destroy: function() {
		var drop = $.ui.ddmanager.droppables[ this.options.scope ];

		this._splice( drop );
	},

	_setOption: function( key, value ) {

		if ( key === "accept" ) {
			this.accept = $.isFunction( value ) ? value : function( d ) {
				return d.is( value );
			};
		} else if ( key === "scope" ) {
			var drop = $.ui.ddmanager.droppables[ this.options.scope ];

			this._splice( drop );
			this._addToManager( value );
		}

		this._super( key, value );
	},

	_activate: function( event ) {
		var draggable = $.ui.ddmanager.current;

		this._addActiveClass();
		if ( draggable ) {
			this._trigger( "activate", event, this.ui( draggable ) );
		}
	},

	_deactivate: function( event ) {
		var draggable = $.ui.ddmanager.current;

		this._removeActiveClass();
		if ( draggable ) {
			this._trigger( "deactivate", event, this.ui( draggable ) );
		}
	},

	_over: function( event ) {

		var draggable = $.ui.ddmanager.current;

		// Bail if draggable and droppable are same element
		if ( !draggable || ( draggable.currentItem ||
				draggable.element )[ 0 ] === this.element[ 0 ] ) {
			return;
		}

		if ( this.accept.call( this.element[ 0 ], ( draggable.currentItem ||
				draggable.element ) ) ) {
			this._addHoverClass();
			this._trigger( "over", event, this.ui( draggable ) );
		}

	},

	_out: function( event ) {

		var draggable = $.ui.ddmanager.current;

		// Bail if draggable and droppable are same element
		if ( !draggable || ( draggable.currentItem ||
				draggable.element )[ 0 ] === this.element[ 0 ] ) {
			return;
		}

		if ( this.accept.call( this.element[ 0 ], ( draggable.currentItem ||
				draggable.element ) ) ) {
			this._removeHoverClass();
			this._trigger( "out", event, this.ui( draggable ) );
		}

	},

	_drop: function( event, custom ) {

		var draggable = custom || $.ui.ddmanager.current,
			childrenIntersection = false;

		// Bail if draggable and droppable are same element
		if ( !draggable || ( draggable.currentItem ||
				draggable.element )[ 0 ] === this.element[ 0 ] ) {
			return false;
		}

		this.element
			.find( ":data(ui-droppable)" )
			.not( ".ui-draggable-dragging" )
			.each( function() {
				var inst = $( this ).droppable( "instance" );
				if (
					inst.options.greedy &&
					!inst.options.disabled &&
					inst.options.scope === draggable.options.scope &&
					inst.accept.call(
						inst.element[ 0 ], ( draggable.currentItem || draggable.element )
					) &&
					intersect(
						draggable,
						$.extend( inst, { offset: inst.element.offset() } ),
						inst.options.tolerance, event
					)
				) {
					childrenIntersection = true;
					return false; }
			} );
		if ( childrenIntersection ) {
			return false;
		}

		if ( this.accept.call( this.element[ 0 ],
				( draggable.currentItem || draggable.element ) ) ) {
			this._removeActiveClass();
			this._removeHoverClass();

			this._trigger( "drop", event, this.ui( draggable ) );
			return this.element;
		}

		return false;

	},

	ui: function( c ) {
		return {
			draggable: ( c.currentItem || c.element ),
			helper: c.helper,
			position: c.position,
			offset: c.positionAbs
		};
	},

	// Extension points just to make backcompat sane and avoid duplicating logic
	// TODO: Remove in 1.13 along with call to it below
	_addHoverClass: function() {
		this._addClass( "ui-droppable-hover" );
	},

	_removeHoverClass: function() {
		this._removeClass( "ui-droppable-hover" );
	},

	_addActiveClass: function() {
		this._addClass( "ui-droppable-active" );
	},

	_removeActiveClass: function() {
		this._removeClass( "ui-droppable-active" );
	}
} );

var intersect = $.ui.intersect = ( function() {
	function isOverAxis( x, reference, size ) {
		return ( x >= reference ) && ( x < ( reference + size ) );
	}

	return function( draggable, droppable, toleranceMode, event ) {

		if ( !droppable.offset ) {
			return false;
		}

		var x1 = ( draggable.positionAbs ||
				draggable.position.absolute ).left + draggable.margins.left,
			y1 = ( draggable.positionAbs ||
				draggable.position.absolute ).top + draggable.margins.top,
			x2 = x1 + draggable.helperProportions.width,
			y2 = y1 + draggable.helperProportions.height,
			l = droppable.offset.left,
			t = droppable.offset.top,
			r = l + droppable.proportions().width,
			b = t + droppable.proportions().height;

		switch ( toleranceMode ) {
		case "fit":
			return ( l <= x1 && x2 <= r && t <= y1 && y2 <= b );
		case "intersect":
			return ( l < x1 + ( draggable.helperProportions.width / 2 ) && // Right Half
				x2 - ( draggable.helperProportions.width / 2 ) < r && // Left Half
				t < y1 + ( draggable.helperProportions.height / 2 ) && // Bottom Half
				y2 - ( draggable.helperProportions.height / 2 ) < b ); // Top Half
		case "pointer":
			return isOverAxis( event.pageY, t, droppable.proportions().height ) &&
				isOverAxis( event.pageX, l, droppable.proportions().width );
		case "touch":
			return (
				( y1 >= t && y1 <= b ) || // Top edge touching
				( y2 >= t && y2 <= b ) || // Bottom edge touching
				( y1 < t && y2 > b ) // Surrounded vertically
			) && (
				( x1 >= l && x1 <= r ) || // Left edge touching
				( x2 >= l && x2 <= r ) || // Right edge touching
				( x1 < l && x2 > r ) // Surrounded horizontally
			);
		default:
			return false;
		}
	};
} )();

/*
	This manager tracks offsets of draggables and droppables
*/
$.ui.ddmanager = {
	current: null,
	droppables: { "default": [] },
	prepareOffsets: function( t, event ) {

		var i, j,
			m = $.ui.ddmanager.droppables[ t.options.scope ] || [],
			type = event ? event.type : null, // workaround for #2317
			list = ( t.currentItem || t.element ).find( ":data(ui-droppable)" ).addBack();

		droppablesLoop: for ( i = 0; i < m.length; i++ ) {

			// No disabled and non-accepted
			if ( m[ i ].options.disabled || ( t && !m[ i ].accept.call( m[ i ].element[ 0 ],
					( t.currentItem || t.element ) ) ) ) {
				continue;
			}

			// Filter out elements in the current dragged item
			for ( j = 0; j < list.length; j++ ) {
				if ( list[ j ] === m[ i ].element[ 0 ] ) {
					m[ i ].proportions().height = 0;
					continue droppablesLoop;
				}
			}

			m[ i ].visible = m[ i ].element.css( "display" ) !== "none";
			if ( !m[ i ].visible ) {
				continue;
			}

			// Activate the droppable if used directly from draggables
			if ( type === "mousedown" ) {
				m[ i ]._activate.call( m[ i ], event );
			}

			m[ i ].offset = m[ i ].element.offset();
			m[ i ].proportions( {
				width: m[ i ].element[ 0 ].offsetWidth,
				height: m[ i ].element[ 0 ].offsetHeight
			} );

		}

	},
	drop: function( draggable, event ) {

		var dropped = false;

		// Create a copy of the droppables in case the list changes during the drop (#9116)
		$.each( ( $.ui.ddmanager.droppables[ draggable.options.scope ] || [] ).slice(), function() {

			if ( !this.options ) {
				return;
			}
			if ( !this.options.disabled && this.visible &&
					intersect( draggable, this, this.options.tolerance, event ) ) {
				dropped = this._drop.call( this, event ) || dropped;
			}

			if ( !this.options.disabled && this.visible && this.accept.call( this.element[ 0 ],
					( draggable.currentItem || draggable.element ) ) ) {
				this.isout = true;
				this.isover = false;
				this._deactivate.call( this, event );
			}

		} );
		return dropped;

	},
	dragStart: function( draggable, event ) {

		// Listen for scrolling so that if the dragging causes scrolling the position of the
		// droppables can be recalculated (see #5003)
		draggable.element.parentsUntil( "body" ).on( "scroll.droppable", function() {
			if ( !draggable.options.refreshPositions ) {
				$.ui.ddmanager.prepareOffsets( draggable, event );
			}
		} );
	},
	drag: function( draggable, event ) {

		// If you have a highly dynamic page, you might try this option. It renders positions
		// every time you move the mouse.
		if ( draggable.options.refreshPositions ) {
			$.ui.ddmanager.prepareOffsets( draggable, event );
		}

		// Run through all droppables and check their positions based on specific tolerance options
		$.each( $.ui.ddmanager.droppables[ draggable.options.scope ] || [], function() {

			if ( this.options.disabled || this.greedyChild || !this.visible ) {
				return;
			}

			var parentInstance, scope, parent,
				intersects = intersect( draggable, this, this.options.tolerance, event ),
				c = !intersects && this.isover ?
					"isout" :
					( intersects && !this.isover ? "isover" : null );
			if ( !c ) {
				return;
			}

			if ( this.options.greedy ) {

				// find droppable parents with same scope
				scope = this.options.scope;
				parent = this.element.parents( ":data(ui-droppable)" ).filter( function() {
					return $( this ).droppable( "instance" ).options.scope === scope;
				} );

				if ( parent.length ) {
					parentInstance = $( parent[ 0 ] ).droppable( "instance" );
					parentInstance.greedyChild = ( c === "isover" );
				}
			}

			// We just moved into a greedy child
			if ( parentInstance && c === "isover" ) {
				parentInstance.isover = false;
				parentInstance.isout = true;
				parentInstance._out.call( parentInstance, event );
			}

			this[ c ] = true;
			this[ c === "isout" ? "isover" : "isout" ] = false;
			this[ c === "isover" ? "_over" : "_out" ].call( this, event );

			// We just moved out of a greedy child
			if ( parentInstance && c === "isout" ) {
				parentInstance.isout = false;
				parentInstance.isover = true;
				parentInstance._over.call( parentInstance, event );
			}
		} );

	},
	dragStop: function( draggable, event ) {
		draggable.element.parentsUntil( "body" ).off( "scroll.droppable" );

		// Call prepareOffsets one final time since IE does not fire return scroll events when
		// overflow was caused by drag (see #5003)
		if ( !draggable.options.refreshPositions ) {
			$.ui.ddmanager.prepareOffsets( draggable, event );
		}
	}
};

// DEPRECATED
// TODO: switch return back to widget declaration at top of file when this is removed
if ( $.uiBackCompat !== false ) {

	// Backcompat for activeClass and hoverClass options
	$.widget( "ui.droppable", $.ui.droppable, {
		options: {
			hoverClass: false,
			activeClass: false
		},
		_addActiveClass: function() {
			this._super();
			if ( this.options.activeClass ) {
				this.element.addClass( this.options.activeClass );
			}
		},
		_removeActiveClass: function() {
			this._super();
			if ( this.options.activeClass ) {
				this.element.removeClass( this.options.activeClass );
			}
		},
		_addHoverClass: function() {
			this._super();
			if ( this.options.hoverClass ) {
				this.element.addClass( this.options.hoverClass );
			}
		},
		_removeHoverClass: function() {
			this._super();
			if ( this.options.hoverClass ) {
				this.element.removeClass( this.options.hoverClass );
			}
		}
	} );
}

var widgetsDroppable = $.ui.droppable;


/*!
 * jQuery UI Progressbar 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: Progressbar
//>>group: Widgets
// jscs:disable maximumLineLength
//>>description: Displays a status indicator for loading state, standard percentage, and other progress indicators.
// jscs:enable maximumLineLength
//>>docs: http://api.jqueryui.com/progressbar/
//>>demos: http://jqueryui.com/progressbar/
//>>css.structure: ../../themes/base/core.css
//>>css.structure: ../../themes/base/progressbar.css
//>>css.theme: ../../themes/base/theme.css



var widgetsProgressbar = $.widget( "ui.progressbar", {
	version: "1.12.0",
	options: {
		classes: {
			"ui-progressbar": "ui-corner-all",
			"ui-progressbar-value": "ui-corner-left",
			"ui-progressbar-complete": "ui-corner-right"
		},
		max: 100,
		value: 0,

		change: null,
		complete: null
	},

	min: 0,

	_create: function() {

		// Constrain initial value
		this.oldValue = this.options.value = this._constrainedValue();

		this.element.attr( {

			// Only set static values; aria-valuenow and aria-valuemax are
			// set inside _refreshValue()
			role: "progressbar",
			"aria-valuemin": this.min
		} );
		this._addClass( "ui-progressbar", "ui-widget ui-widget-content" );

		this.valueDiv = $( "<div>" ).appendTo( this.element );
		this._addClass( this.valueDiv, "ui-progressbar-value", "ui-widget-header" );
		this._refreshValue();
	},

	_destroy: function() {
		this.element.removeAttr( "role aria-valuemin aria-valuemax aria-valuenow" );

		this.valueDiv.remove();
	},

	value: function( newValue ) {
		if ( newValue === undefined ) {
			return this.options.value;
		}

		this.options.value = this._constrainedValue( newValue );
		this._refreshValue();
	},

	_constrainedValue: function( newValue ) {
		if ( newValue === undefined ) {
			newValue = this.options.value;
		}

		this.indeterminate = newValue === false;

		// Sanitize value
		if ( typeof newValue !== "number" ) {
			newValue = 0;
		}

		return this.indeterminate ? false :
			Math.min( this.options.max, Math.max( this.min, newValue ) );
	},

	_setOptions: function( options ) {

		// Ensure "value" option is set after other values (like max)
		var value = options.value;
		delete options.value;

		this._super( options );

		this.options.value = this._constrainedValue( value );
		this._refreshValue();
	},

	_setOption: function( key, value ) {
		if ( key === "max" ) {

			// Don't allow a max less than min
			value = Math.max( this.min, value );
		}
		this._super( key, value );
	},

	_setOptionDisabled: function( value ) {
		this._super( value );

		this.element.attr( "aria-disabled", value );
		this._toggleClass( null, "ui-state-disabled", !!value );
	},

	_percentage: function() {
		return this.indeterminate ?
			100 :
			100 * ( this.options.value - this.min ) / ( this.options.max - this.min );
	},

	_refreshValue: function() {
		var value = this.options.value,
			percentage = this._percentage();

		this.valueDiv
			.toggle( this.indeterminate || value > this.min )
			.width( percentage.toFixed( 0 ) + "%" );

		this
			._toggleClass( this.valueDiv, "ui-progressbar-complete", null,
				value === this.options.max )
			._toggleClass( "ui-progressbar-indeterminate", null, this.indeterminate );

		if ( this.indeterminate ) {
			this.element.removeAttr( "aria-valuenow" );
			if ( !this.overlayDiv ) {
				this.overlayDiv = $( "<div>" ).appendTo( this.valueDiv );
				this._addClass( this.overlayDiv, "ui-progressbar-overlay" );
			}
		} else {
			this.element.attr( {
				"aria-valuemax": this.options.max,
				"aria-valuenow": value
			} );
			if ( this.overlayDiv ) {
				this.overlayDiv.remove();
				this.overlayDiv = null;
			}
		}

		if ( this.oldValue !== value ) {
			this.oldValue = value;
			this._trigger( "change" );
		}
		if ( value === this.options.max ) {
			this._trigger( "complete" );
		}
	}
} );


/*!
 * jQuery UI Selectable 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: Selectable
//>>group: Interactions
//>>description: Allows groups of elements to be selected with the mouse.
//>>docs: http://api.jqueryui.com/selectable/
//>>demos: http://jqueryui.com/selectable/
//>>css.structure: ../../themes/base/selectable.css



var widgetsSelectable = $.widget( "ui.selectable", $.ui.mouse, {
	version: "1.12.0",
	options: {
		appendTo: "body",
		autoRefresh: true,
		distance: 0,
		filter: "*",
		tolerance: "touch",

		// Callbacks
		selected: null,
		selecting: null,
		start: null,
		stop: null,
		unselected: null,
		unselecting: null
	},
	_create: function() {
		var that = this;

		this._addClass( "ui-selectable" );

		this.dragged = false;

		// Cache selectee children based on filter
		this.refresh = function() {
			that.elementPos = $( that.element[ 0 ] ).offset();
			that.selectees = $( that.options.filter, that.element[ 0 ] );
			that._addClass( that.selectees, "ui-selectee" );
			that.selectees.each( function() {
				var $this = $( this ),
					selecteeOffset = $this.offset(),
					pos = {
						left: selecteeOffset.left - that.elementPos.left,
						top: selecteeOffset.top - that.elementPos.top
					};
				$.data( this, "selectable-item", {
					element: this,
					$element: $this,
					left: pos.left,
					top: pos.top,
					right: pos.left + $this.outerWidth(),
					bottom: pos.top + $this.outerHeight(),
					startselected: false,
					selected: $this.hasClass( "ui-selected" ),
					selecting: $this.hasClass( "ui-selecting" ),
					unselecting: $this.hasClass( "ui-unselecting" )
				} );
			} );
		};
		this.refresh();

		this._mouseInit();

		this.helper = $( "<div>" );
		this._addClass( this.helper, "ui-selectable-helper" );
	},

	_destroy: function() {
		this.selectees.removeData( "selectable-item" );
		this._mouseDestroy();
	},

	_mouseStart: function( event ) {
		var that = this,
			options = this.options;

		this.opos = [ event.pageX, event.pageY ];
		this.elementPos = $( this.element[ 0 ] ).offset();

		if ( this.options.disabled ) {
			return;
		}

		this.selectees = $( options.filter, this.element[ 0 ] );

		this._trigger( "start", event );

		$( options.appendTo ).append( this.helper );

		// position helper (lasso)
		this.helper.css( {
			"left": event.pageX,
			"top": event.pageY,
			"width": 0,
			"height": 0
		} );

		if ( options.autoRefresh ) {
			this.refresh();
		}

		this.selectees.filter( ".ui-selected" ).each( function() {
			var selectee = $.data( this, "selectable-item" );
			selectee.startselected = true;
			if ( !event.metaKey && !event.ctrlKey ) {
				that._removeClass( selectee.$element, "ui-selected" );
				selectee.selected = false;
				that._addClass( selectee.$element, "ui-unselecting" );
				selectee.unselecting = true;

				// selectable UNSELECTING callback
				that._trigger( "unselecting", event, {
					unselecting: selectee.element
				} );
			}
		} );

		$( event.target ).parents().addBack().each( function() {
			var doSelect,
				selectee = $.data( this, "selectable-item" );
			if ( selectee ) {
				doSelect = ( !event.metaKey && !event.ctrlKey ) ||
					!selectee.$element.hasClass( "ui-selected" );
				that._removeClass( selectee.$element, doSelect ? "ui-unselecting" : "ui-selected" )
					._addClass( selectee.$element, doSelect ? "ui-selecting" : "ui-unselecting" );
				selectee.unselecting = !doSelect;
				selectee.selecting = doSelect;
				selectee.selected = doSelect;

				// selectable (UN)SELECTING callback
				if ( doSelect ) {
					that._trigger( "selecting", event, {
						selecting: selectee.element
					} );
				} else {
					that._trigger( "unselecting", event, {
						unselecting: selectee.element
					} );
				}
				return false;
			}
		} );

	},

	_mouseDrag: function( event ) {

		this.dragged = true;

		if ( this.options.disabled ) {
			return;
		}

		var tmp,
			that = this,
			options = this.options,
			x1 = this.opos[ 0 ],
			y1 = this.opos[ 1 ],
			x2 = event.pageX,
			y2 = event.pageY;

		if ( x1 > x2 ) { tmp = x2; x2 = x1; x1 = tmp; }
		if ( y1 > y2 ) { tmp = y2; y2 = y1; y1 = tmp; }
		this.helper.css( { left: x1, top: y1, width: x2 - x1, height: y2 - y1 } );

		this.selectees.each( function() {
			var selectee = $.data( this, "selectable-item" ),
				hit = false,
				offset = {};

			//prevent helper from being selected if appendTo: selectable
			if ( !selectee || selectee.element === that.element[ 0 ] ) {
				return;
			}

			offset.left   = selectee.left   + that.elementPos.left;
			offset.right  = selectee.right  + that.elementPos.left;
			offset.top    = selectee.top    + that.elementPos.top;
			offset.bottom = selectee.bottom + that.elementPos.top;

			if ( options.tolerance === "touch" ) {
				hit = ( !( offset.left > x2 || offset.right < x1 || offset.top > y2 ||
                    offset.bottom < y1 ) );
			} else if ( options.tolerance === "fit" ) {
				hit = ( offset.left > x1 && offset.right < x2 && offset.top > y1 &&
                    offset.bottom < y2 );
			}

			if ( hit ) {

				// SELECT
				if ( selectee.selected ) {
					that._removeClass( selectee.$element, "ui-selected" );
					selectee.selected = false;
				}
				if ( selectee.unselecting ) {
					that._removeClass( selectee.$element, "ui-unselecting" );
					selectee.unselecting = false;
				}
				if ( !selectee.selecting ) {
					that._addClass( selectee.$element, "ui-selecting" );
					selectee.selecting = true;

					// selectable SELECTING callback
					that._trigger( "selecting", event, {
						selecting: selectee.element
					} );
				}
			} else {

				// UNSELECT
				if ( selectee.selecting ) {
					if ( ( event.metaKey || event.ctrlKey ) && selectee.startselected ) {
						that._removeClass( selectee.$element, "ui-selecting" );
						selectee.selecting = false;
						that._addClass( selectee.$element, "ui-selected" );
						selectee.selected = true;
					} else {
						that._removeClass( selectee.$element, "ui-selecting" );
						selectee.selecting = false;
						if ( selectee.startselected ) {
							that._addClass( selectee.$element, "ui-unselecting" );
							selectee.unselecting = true;
						}

						// selectable UNSELECTING callback
						that._trigger( "unselecting", event, {
							unselecting: selectee.element
						} );
					}
				}
				if ( selectee.selected ) {
					if ( !event.metaKey && !event.ctrlKey && !selectee.startselected ) {
						that._removeClass( selectee.$element, "ui-selected" );
						selectee.selected = false;

						that._addClass( selectee.$element, "ui-unselecting" );
						selectee.unselecting = true;

						// selectable UNSELECTING callback
						that._trigger( "unselecting", event, {
							unselecting: selectee.element
						} );
					}
				}
			}
		} );

		return false;
	},

	_mouseStop: function( event ) {
		var that = this;

		this.dragged = false;

		$( ".ui-unselecting", this.element[ 0 ] ).each( function() {
			var selectee = $.data( this, "selectable-item" );
			that._removeClass( selectee.$element, "ui-unselecting" );
			selectee.unselecting = false;
			selectee.startselected = false;
			that._trigger( "unselected", event, {
				unselected: selectee.element
			} );
		} );
		$( ".ui-selecting", this.element[ 0 ] ).each( function() {
			var selectee = $.data( this, "selectable-item" );
			that._removeClass( selectee.$element, "ui-selecting" )
				._addClass( selectee.$element, "ui-selected" );
			selectee.selecting = false;
			selectee.selected = true;
			selectee.startselected = true;
			that._trigger( "selected", event, {
				selected: selectee.element
			} );
		} );
		this._trigger( "stop", event );

		this.helper.remove();

		return false;
	}

} );


/*!
 * jQuery UI Selectmenu 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: Selectmenu
//>>group: Widgets
// jscs:disable maximumLineLength
//>>description: Duplicates and extends the functionality of a native HTML select element, allowing it to be customizable in behavior and appearance far beyond the limitations of a native select.
// jscs:enable maximumLineLength
//>>docs: http://api.jqueryui.com/selectmenu/
//>>demos: http://jqueryui.com/selectmenu/
//>>css.structure: ../../themes/base/core.css
//>>css.structure: ../../themes/base/selectmenu.css, ../../themes/base/button.css
//>>css.theme: ../../themes/base/theme.css



var widgetsSelectmenu = $.widget( "ui.selectmenu", [ $.ui.formResetMixin, {
	version: "1.12.0",
	defaultElement: "<select>",
	options: {
		appendTo: null,
		classes: {
			"ui-selectmenu-button-open": "ui-corner-top",
			"ui-selectmenu-button-closed": "ui-corner-all"
		},
		disabled: null,
		icons: {
			button: "ui-icon-triangle-1-s"
		},
		position: {
			my: "left top",
			at: "left bottom",
			collision: "none"
		},
		width: false,

		// Callbacks
		change: null,
		close: null,
		focus: null,
		open: null,
		select: null
	},

	_create: function() {
		var selectmenuId = this.element.uniqueId().attr( "id" );
		this.ids = {
			element: selectmenuId,
			button: selectmenuId + "-button",
			menu: selectmenuId + "-menu"
		};

		this._drawButton();
		this._drawMenu();
		this._bindFormResetHandler();

		this._rendered = false;
		this.menuItems = $();
	},

	_drawButton: function() {
		var icon,
			that = this,
			item = this._parseOption(
				this.element.find( "option:selected" ),
				this.element[ 0 ].selectedIndex
			);

		// Associate existing label with the new button
		this.labels = this.element.labels().attr( "for", this.ids.button );
		this._on( this.labels, {
			click: function( event ) {
				this.button.focus();
				event.preventDefault();
			}
		} );

		// Hide original select element
		this.element.hide();

		// Create button
		this.button = $( "<span>", {
			tabindex: this.options.disabled ? -1 : 0,
			id: this.ids.button,
			role: "combobox",
			"aria-expanded": "false",
			"aria-autocomplete": "list",
			"aria-owns": this.ids.menu,
			"aria-haspopup": "true",
			title: this.element.attr( "title" )
		} )
			.insertAfter( this.element );

		this._addClass( this.button, "ui-selectmenu-button ui-selectmenu-button-closed",
			"ui-button ui-widget" );

		icon = $( "<span>" ).appendTo( this.button );
		this._addClass( icon, "ui-selectmenu-icon", "ui-icon " + this.options.icons.button );
		this.buttonItem = this._renderButtonItem( item )
			.appendTo( this.button );

		if ( this.options.width !== false ) {
			this._resizeButton();
		}

		this._on( this.button, this._buttonEvents );
		this.button.one( "focusin", function() {

			// Delay rendering the menu items until the button receives focus.
			// The menu may have already been rendered via a programmatic open.
			if ( !that._rendered ) {
				that._refreshMenu();
			}
		} );
	},

	_drawMenu: function() {
		var that = this;

		// Create menu
		this.menu = $( "<ul>", {
			"aria-hidden": "true",
			"aria-labelledby": this.ids.button,
			id: this.ids.menu
		} );

		// Wrap menu
		this.menuWrap = $( "<div>" ).append( this.menu );
		this._addClass( this.menuWrap, "ui-selectmenu-menu", "ui-front" );
		this.menuWrap.appendTo( this._appendTo() );

		// Initialize menu widget
		this.menuInstance = this.menu
			.menu( {
				classes: {
					"ui-menu": "ui-corner-bottom"
				},
				role: "listbox",
				select: function( event, ui ) {
					event.preventDefault();

					// Support: IE8
					// If the item was selected via a click, the text selection
					// will be destroyed in IE
					that._setSelection();

					that._select( ui.item.data( "ui-selectmenu-item" ), event );
				},
				focus: function( event, ui ) {
					var item = ui.item.data( "ui-selectmenu-item" );

					// Prevent inital focus from firing and check if its a newly focused item
					if ( that.focusIndex != null && item.index !== that.focusIndex ) {
						that._trigger( "focus", event, { item: item } );
						if ( !that.isOpen ) {
							that._select( item, event );
						}
					}
					that.focusIndex = item.index;

					that.button.attr( "aria-activedescendant",
						that.menuItems.eq( item.index ).attr( "id" ) );
				}
			} )
			.menu( "instance" );

		// Don't close the menu on mouseleave
		this.menuInstance._off( this.menu, "mouseleave" );

		// Cancel the menu's collapseAll on document click
		this.menuInstance._closeOnDocumentClick = function() {
			return false;
		};

		// Selects often contain empty items, but never contain dividers
		this.menuInstance._isDivider = function() {
			return false;
		};
	},

	refresh: function() {
		this._refreshMenu();
		this.buttonItem.replaceWith(
			this.buttonItem = this._renderButtonItem(

				// Fall back to an empty object in case there are no options
				this._getSelectedItem().data( "ui-selectmenu-item" ) || {}
			)
		);
		if ( this.options.width === null ) {
			this._resizeButton();
		}
	},

	_refreshMenu: function() {
		var item,
			options = this.element.find( "option" );

		this.menu.empty();

		this._parseOptions( options );
		this._renderMenu( this.menu, this.items );

		this.menuInstance.refresh();
		this.menuItems = this.menu.find( "li" )
			.not( ".ui-selectmenu-optgroup" )
				.find( ".ui-menu-item-wrapper" );

		this._rendered = true;

		if ( !options.length ) {
			return;
		}

		item = this._getSelectedItem();

		// Update the menu to have the correct item focused
		this.menuInstance.focus( null, item );
		this._setAria( item.data( "ui-selectmenu-item" ) );

		// Set disabled state
		this._setOption( "disabled", this.element.prop( "disabled" ) );
	},

	open: function( event ) {
		if ( this.options.disabled ) {
			return;
		}

		// If this is the first time the menu is being opened, render the items
		if ( !this._rendered ) {
			this._refreshMenu();
		} else {

			// Menu clears focus on close, reset focus to selected item
			this._removeClass( this.menu.find( ".ui-state-active" ), null, "ui-state-active" );
			this.menuInstance.focus( null, this._getSelectedItem() );
		}

		// If there are no options, don't open the menu
		if ( !this.menuItems.length ) {
			return;
		}

		this.isOpen = true;
		this._toggleAttr();
		this._resizeMenu();
		this._position();

		this._on( this.document, this._documentClick );

		this._trigger( "open", event );
	},

	_position: function() {
		this.menuWrap.position( $.extend( { of: this.button }, this.options.position ) );
	},

	close: function( event ) {
		if ( !this.isOpen ) {
			return;
		}

		this.isOpen = false;
		this._toggleAttr();

		this.range = null;
		this._off( this.document );

		this._trigger( "close", event );
	},

	widget: function() {
		return this.button;
	},

	menuWidget: function() {
		return this.menu;
	},

	_renderButtonItem: function( item ) {
		var buttonItem = $( "<span>" );

		this._setText( buttonItem, item.label );
		this._addClass( buttonItem, "ui-selectmenu-text" );

		return buttonItem;
	},

	_renderMenu: function( ul, items ) {
		var that = this,
			currentOptgroup = "";

		$.each( items, function( index, item ) {
			var li;

			if ( item.optgroup !== currentOptgroup ) {
				li = $( "<li>", {
					text: item.optgroup
				} );
				that._addClass( li, "ui-selectmenu-optgroup", "ui-menu-divider" +
					( item.element.parent( "optgroup" ).prop( "disabled" ) ?
						" ui-state-disabled" :
						"" ) );

				li.appendTo( ul );

				currentOptgroup = item.optgroup;
			}

			that._renderItemData( ul, item );
		} );
	},

	_renderItemData: function( ul, item ) {
		return this._renderItem( ul, item ).data( "ui-selectmenu-item", item );
	},

	_renderItem: function( ul, item ) {
		var li = $( "<li>" ),
			wrapper = $( "<div>", {
				title: item.element.attr( "title" )
			} );

		if ( item.disabled ) {
			this._addClass( li, null, "ui-state-disabled" );
		}
		this._setText( wrapper, item.label );

		return li.append( wrapper ).appendTo( ul );
	},

	_setText: function( element, value ) {
		if ( value ) {
			element.text( value );
		} else {
			element.html( "&#160;" );
		}
	},

	_move: function( direction, event ) {
		var item, next,
			filter = ".ui-menu-item";

		if ( this.isOpen ) {
			item = this.menuItems.eq( this.focusIndex ).parent( "li" );
		} else {
			item = this.menuItems.eq( this.element[ 0 ].selectedIndex ).parent( "li" );
			filter += ":not(.ui-state-disabled)";
		}

		if ( direction === "first" || direction === "last" ) {
			next = item[ direction === "first" ? "prevAll" : "nextAll" ]( filter ).eq( -1 );
		} else {
			next = item[ direction + "All" ]( filter ).eq( 0 );
		}

		if ( next.length ) {
			this.menuInstance.focus( event, next );
		}
	},

	_getSelectedItem: function() {
		return this.menuItems.eq( this.element[ 0 ].selectedIndex ).parent( "li" );
	},

	_toggle: function( event ) {
		this[ this.isOpen ? "close" : "open" ]( event );
	},

	_setSelection: function() {
		var selection;

		if ( !this.range ) {
			return;
		}

		if ( window.getSelection ) {
			selection = window.getSelection();
			selection.removeAllRanges();
			selection.addRange( this.range );

		// Support: IE8
		} else {
			this.range.select();
		}

		// Support: IE
		// Setting the text selection kills the button focus in IE, but
		// restoring the focus doesn't kill the selection.
		this.button.focus();
	},

	_documentClick: {
		mousedown: function( event ) {
			if ( !this.isOpen ) {
				return;
			}

			if ( !$( event.target ).closest( ".ui-selectmenu-menu, #" +
					$.ui.escapeSelector( this.ids.button ) ).length ) {
				this.close( event );
			}
		}
	},

	_buttonEvents: {

		// Prevent text selection from being reset when interacting with the selectmenu (#10144)
		mousedown: function() {
			var selection;

			if ( window.getSelection ) {
				selection = window.getSelection();
				if ( selection.rangeCount ) {
					this.range = selection.getRangeAt( 0 );
				}

			// Support: IE8
			} else {
				this.range = document.selection.createRange();
			}
		},

		click: function( event ) {
			this._setSelection();
			this._toggle( event );
		},

		keydown: function( event ) {
			var preventDefault = true;
			switch ( event.keyCode ) {
			case $.ui.keyCode.TAB:
			case $.ui.keyCode.ESCAPE:
				this.close( event );
				preventDefault = false;
				break;
			case $.ui.keyCode.ENTER:
				if ( this.isOpen ) {
					this._selectFocusedItem( event );
				}
				break;
			case $.ui.keyCode.UP:
				if ( event.altKey ) {
					this._toggle( event );
				} else {
					this._move( "prev", event );
				}
				break;
			case $.ui.keyCode.DOWN:
				if ( event.altKey ) {
					this._toggle( event );
				} else {
					this._move( "next", event );
				}
				break;
			case $.ui.keyCode.SPACE:
				if ( this.isOpen ) {
					this._selectFocusedItem( event );
				} else {
					this._toggle( event );
				}
				break;
			case $.ui.keyCode.LEFT:
				this._move( "prev", event );
				break;
			case $.ui.keyCode.RIGHT:
				this._move( "next", event );
				break;
			case $.ui.keyCode.HOME:
			case $.ui.keyCode.PAGE_UP:
				this._move( "first", event );
				break;
			case $.ui.keyCode.END:
			case $.ui.keyCode.PAGE_DOWN:
				this._move( "last", event );
				break;
			default:
				this.menu.trigger( event );
				preventDefault = false;
			}

			if ( preventDefault ) {
				event.preventDefault();
			}
		}
	},

	_selectFocusedItem: function( event ) {
		var item = this.menuItems.eq( this.focusIndex ).parent( "li" );
		if ( !item.hasClass( "ui-state-disabled" ) ) {
			this._select( item.data( "ui-selectmenu-item" ), event );
		}
	},

	_select: function( item, event ) {
		var oldIndex = this.element[ 0 ].selectedIndex;

		// Change native select element
		this.element[ 0 ].selectedIndex = item.index;
		this.buttonItem.replaceWith( this.buttonItem = this._renderButtonItem( item ) );
		this._setAria( item );
		this._trigger( "select", event, { item: item } );

		if ( item.index !== oldIndex ) {
			this._trigger( "change", event, { item: item } );
		}

		this.close( event );
	},

	_setAria: function( item ) {
		var id = this.menuItems.eq( item.index ).attr( "id" );

		this.button.attr( {
			"aria-labelledby": id,
			"aria-activedescendant": id
		} );
		this.menu.attr( "aria-activedescendant", id );
	},

	_setOption: function( key, value ) {
		if ( key === "icons" ) {
			var icon = this.button.find( "span.ui-icon" );
			this._removeClass( icon, null, this.options.icons.button )
				._addClass( icon, null, value.button );
		}

		this._super( key, value );

		if ( key === "appendTo" ) {
			this.menuWrap.appendTo( this._appendTo() );
		}

		if ( key === "width" ) {
			this._resizeButton();
		}
	},

	_setOptionDisabled: function( value ) {
		this._super( value );

		this.menuInstance.option( "disabled", value );
		this.button.attr( "aria-disabled", value );
		this._toggleClass( this.button, null, "ui-state-disabled", value );

		this.element.prop( "disabled", value );
		if ( value ) {
			this.button.attr( "tabindex", -1 );
			this.close();
		} else {
			this.button.attr( "tabindex", 0 );
		}
	},

	_appendTo: function() {
		var element = this.options.appendTo;

		if ( element ) {
			element = element.jquery || element.nodeType ?
				$( element ) :
				this.document.find( element ).eq( 0 );
		}

		if ( !element || !element[ 0 ] ) {
			element = this.element.closest( ".ui-front, dialog" );
		}

		if ( !element.length ) {
			element = this.document[ 0 ].body;
		}

		return element;
	},

	_toggleAttr: function() {
		this.button.attr( "aria-expanded", this.isOpen );

		// We can't use two _toggleClass() calls here, because we need to make sure
		// we always remove classes first and add them second, otherwise if both classes have the
		// same theme class, it will be removed after we add it.
		this._removeClass( this.button, "ui-selectmenu-button-" +
			( this.isOpen ? "closed" : "open" ) )
			._addClass( this.button, "ui-selectmenu-button-" +
				( this.isOpen ? "open" : "closed" ) )
			._toggleClass( this.menuWrap, "ui-selectmenu-open", null, this.isOpen );

		this.menu.attr( "aria-hidden", !this.isOpen );
	},

	_resizeButton: function() {
		var width = this.options.width;

		// For `width: false`, just remove inline style and stop
		if ( width === false ) {
			this.button.css( "width", "" );
			return;
		}

		// For `width: null`, match the width of the original element
		if ( width === null ) {
			width = this.element.show().outerWidth();
			this.element.hide();
		}

		this.button.outerWidth( width );
	},

	_resizeMenu: function() {
		this.menu.outerWidth( Math.max(
			this.button.outerWidth(),

			// Support: IE10
			// IE10 wraps long text (possibly a rounding bug)
			// so we add 1px to avoid the wrapping
			this.menu.width( "" ).outerWidth() + 1
		) );
	},

	_getCreateOptions: function() {
		var options = this._super();

		options.disabled = this.element.prop( "disabled" );

		return options;
	},

	_parseOptions: function( options ) {
		var that = this,
			data = [];
		options.each( function( index, item ) {
			data.push( that._parseOption( $( item ), index ) );
		} );
		this.items = data;
	},

	_parseOption: function( option, index ) {
		var optgroup = option.parent( "optgroup" );

		return {
			element: option,
			index: index,
			value: option.val(),
			label: option.text(),
			optgroup: optgroup.attr( "label" ) || "",
			disabled: optgroup.prop( "disabled" ) || option.prop( "disabled" )
		};
	},

	_destroy: function() {
		this._unbindFormResetHandler();
		this.menuWrap.remove();
		this.button.remove();
		this.element.show();
		this.element.removeUniqueId();
		this.labels.attr( "for", this.ids.element );
	}
} ] );


/*!
 * jQuery UI Slider 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: Slider
//>>group: Widgets
//>>description: Displays a flexible slider with ranges and accessibility via keyboard.
//>>docs: http://api.jqueryui.com/slider/
//>>demos: http://jqueryui.com/slider/
//>>css.structure: ../../themes/base/core.css
//>>css.structure: ../../themes/base/slider.css
//>>css.theme: ../../themes/base/theme.css



var widgetsSlider = $.widget( "ui.slider", $.ui.mouse, {
	version: "1.12.0",
	widgetEventPrefix: "slide",

	options: {
		animate: false,
		classes: {
			"ui-slider": "ui-corner-all",
			"ui-slider-handle": "ui-corner-all",

			// Note: ui-widget-header isn't the most fittingly semantic framework class for this
			// element, but worked best visually with a variety of themes
			"ui-slider-range": "ui-corner-all ui-widget-header"
		},
		distance: 0,
		max: 100,
		min: 0,
		orientation: "horizontal",
		range: false,
		step: 1,
		value: 0,
		values: null,

		// Callbacks
		change: null,
		slide: null,
		start: null,
		stop: null
	},

	// Number of pages in a slider
	// (how many times can you page up/down to go through the whole range)
	numPages: 5,

	_create: function() {
		this._keySliding = false;
		this._mouseSliding = false;
		this._animateOff = true;
		this._handleIndex = null;
		this._detectOrientation();
		this._mouseInit();
		this._calculateNewMax();

		this._addClass( "ui-slider ui-slider-" + this.orientation,
			"ui-widget ui-widget-content" );

		this._refresh();

		this._animateOff = false;
	},

	_refresh: function() {
		this._createRange();
		this._createHandles();
		this._setupEvents();
		this._refreshValue();
	},

	_createHandles: function() {
		var i, handleCount,
			options = this.options,
			existingHandles = this.element.find( ".ui-slider-handle" ),
			handle = "<span tabindex='0'></span>",
			handles = [];

		handleCount = ( options.values && options.values.length ) || 1;

		if ( existingHandles.length > handleCount ) {
			existingHandles.slice( handleCount ).remove();
			existingHandles = existingHandles.slice( 0, handleCount );
		}

		for ( i = existingHandles.length; i < handleCount; i++ ) {
			handles.push( handle );
		}

		this.handles = existingHandles.add( $( handles.join( "" ) ).appendTo( this.element ) );

		this._addClass( this.handles, "ui-slider-handle", "ui-state-default" );

		this.handle = this.handles.eq( 0 );

		this.handles.each( function( i ) {
			$( this ).data( "ui-slider-handle-index", i );
		} );
	},

	_createRange: function() {
		var options = this.options;

		if ( options.range ) {
			if ( options.range === true ) {
				if ( !options.values ) {
					options.values = [ this._valueMin(), this._valueMin() ];
				} else if ( options.values.length && options.values.length !== 2 ) {
					options.values = [ options.values[ 0 ], options.values[ 0 ] ];
				} else if ( $.isArray( options.values ) ) {
					options.values = options.values.slice( 0 );
				}
			}

			if ( !this.range || !this.range.length ) {
				this.range = $( "<div>" )
					.appendTo( this.element );

				this._addClass( this.range, "ui-slider-range" );
			} else {
				this._removeClass( this.range, "ui-slider-range-min ui-slider-range-max" );

				// Handle range switching from true to min/max
				this.range.css( {
					"left": "",
					"bottom": ""
				} );
			}
			if ( options.range === "min" || options.range === "max" ) {
				this._addClass( this.range, "ui-slider-range-" + options.range );
			}
		} else {
			if ( this.range ) {
				this.range.remove();
			}
			this.range = null;
		}
	},

	_setupEvents: function() {
		this._off( this.handles );
		this._on( this.handles, this._handleEvents );
		this._hoverable( this.handles );
		this._focusable( this.handles );
	},

	_destroy: function() {
		this.handles.remove();
		if ( this.range ) {
			this.range.remove();
		}

		this._mouseDestroy();
	},

	_mouseCapture: function( event ) {
		var position, normValue, distance, closestHandle, index, allowed, offset, mouseOverHandle,
			that = this,
			o = this.options;

		if ( o.disabled ) {
			return false;
		}

		this.elementSize = {
			width: this.element.outerWidth(),
			height: this.element.outerHeight()
		};
		this.elementOffset = this.element.offset();

		position = { x: event.pageX, y: event.pageY };
		normValue = this._normValueFromMouse( position );
		distance = this._valueMax() - this._valueMin() + 1;
		this.handles.each( function( i ) {
			var thisDistance = Math.abs( normValue - that.values( i ) );
			if ( ( distance > thisDistance ) ||
				( distance === thisDistance &&
					( i === that._lastChangedValue || that.values( i ) === o.min ) ) ) {
				distance = thisDistance;
				closestHandle = $( this );
				index = i;
			}
		} );

		allowed = this._start( event, index );
		if ( allowed === false ) {
			return false;
		}
		this._mouseSliding = true;

		this._handleIndex = index;

		this._addClass( closestHandle, null, "ui-state-active" );
		closestHandle.trigger( "focus" );

		offset = closestHandle.offset();
		mouseOverHandle = !$( event.target ).parents().addBack().is( ".ui-slider-handle" );
		this._clickOffset = mouseOverHandle ? { left: 0, top: 0 } : {
			left: event.pageX - offset.left - ( closestHandle.width() / 2 ),
			top: event.pageY - offset.top -
				( closestHandle.height() / 2 ) -
				( parseInt( closestHandle.css( "borderTopWidth" ), 10 ) || 0 ) -
				( parseInt( closestHandle.css( "borderBottomWidth" ), 10 ) || 0 ) +
				( parseInt( closestHandle.css( "marginTop" ), 10 ) || 0 )
		};

		if ( !this.handles.hasClass( "ui-state-hover" ) ) {
			this._slide( event, index, normValue );
		}
		this._animateOff = true;
		return true;
	},

	_mouseStart: function() {
		return true;
	},

	_mouseDrag: function( event ) {
		var position = { x: event.pageX, y: event.pageY },
			normValue = this._normValueFromMouse( position );

		this._slide( event, this._handleIndex, normValue );

		return false;
	},

	_mouseStop: function( event ) {
		this._removeClass( this.handles, null, "ui-state-active" );
		this._mouseSliding = false;

		this._stop( event, this._handleIndex );
		this._change( event, this._handleIndex );

		this._handleIndex = null;
		this._clickOffset = null;
		this._animateOff = false;

		return false;
	},

	_detectOrientation: function() {
		this.orientation = ( this.options.orientation === "vertical" ) ? "vertical" : "horizontal";
	},

	_normValueFromMouse: function( position ) {
		var pixelTotal,
			pixelMouse,
			percentMouse,
			valueTotal,
			valueMouse;

		if ( this.orientation === "horizontal" ) {
			pixelTotal = this.elementSize.width;
			pixelMouse = position.x - this.elementOffset.left -
				( this._clickOffset ? this._clickOffset.left : 0 );
		} else {
			pixelTotal = this.elementSize.height;
			pixelMouse = position.y - this.elementOffset.top -
				( this._clickOffset ? this._clickOffset.top : 0 );
		}

		percentMouse = ( pixelMouse / pixelTotal );
		if ( percentMouse > 1 ) {
			percentMouse = 1;
		}
		if ( percentMouse < 0 ) {
			percentMouse = 0;
		}
		if ( this.orientation === "vertical" ) {
			percentMouse = 1 - percentMouse;
		}

		valueTotal = this._valueMax() - this._valueMin();
		valueMouse = this._valueMin() + percentMouse * valueTotal;

		return this._trimAlignValue( valueMouse );
	},

	_uiHash: function( index, value, values ) {
		var uiHash = {
			handle: this.handles[ index ],
			handleIndex: index,
			value: value !== undefined ? value : this.value()
		};

		if ( this._hasMultipleValues() ) {
			uiHash.value = value !== undefined ? value : this.values( index );
			uiHash.values = values || this.values();
		}

		return uiHash;
	},

	_hasMultipleValues: function() {
		return this.options.values && this.options.values.length;
	},

	_start: function( event, index ) {
		return this._trigger( "start", event, this._uiHash( index ) );
	},

	_slide: function( event, index, newVal ) {
		var allowed, otherVal,
			currentValue = this.value(),
			newValues = this.values();

		if ( this._hasMultipleValues() ) {
			otherVal = this.values( index ? 0 : 1 );
			currentValue = this.values( index );

			if ( this.options.values.length === 2 && this.options.range === true ) {
				newVal =  index === 0 ? Math.min( otherVal, newVal ) : Math.max( otherVal, newVal );
			}

			newValues[ index ] = newVal;
		}

		if ( newVal === currentValue ) {
			return;
		}

		allowed = this._trigger( "slide", event, this._uiHash( index, newVal, newValues ) );

		// A slide can be canceled by returning false from the slide callback
		if ( allowed === false ) {
			return;
		}

		if ( this._hasMultipleValues() ) {
			this.values( index, newVal );
		} else {
			this.value( newVal );
		}
	},

	_stop: function( event, index ) {
		this._trigger( "stop", event, this._uiHash( index ) );
	},

	_change: function( event, index ) {
		if ( !this._keySliding && !this._mouseSliding ) {

			//store the last changed value index for reference when handles overlap
			this._lastChangedValue = index;
			this._trigger( "change", event, this._uiHash( index ) );
		}
	},

	value: function( newValue ) {
		if ( arguments.length ) {
			this.options.value = this._trimAlignValue( newValue );
			this._refreshValue();
			this._change( null, 0 );
			return;
		}

		return this._value();
	},

	values: function( index, newValue ) {
		var vals,
			newValues,
			i;

		if ( arguments.length > 1 ) {
			this.options.values[ index ] = this._trimAlignValue( newValue );
			this._refreshValue();
			this._change( null, index );
			return;
		}

		if ( arguments.length ) {
			if ( $.isArray( arguments[ 0 ] ) ) {
				vals = this.options.values;
				newValues = arguments[ 0 ];
				for ( i = 0; i < vals.length; i += 1 ) {
					vals[ i ] = this._trimAlignValue( newValues[ i ] );
					this._change( null, i );
				}
				this._refreshValue();
			} else {
				if ( this._hasMultipleValues() ) {
					return this._values( index );
				} else {
					return this.value();
				}
			}
		} else {
			return this._values();
		}
	},

	_setOption: function( key, value ) {
		var i,
			valsLength = 0;

		if ( key === "range" && this.options.range === true ) {
			if ( value === "min" ) {
				this.options.value = this._values( 0 );
				this.options.values = null;
			} else if ( value === "max" ) {
				this.options.value = this._values( this.options.values.length - 1 );
				this.options.values = null;
			}
		}

		if ( $.isArray( this.options.values ) ) {
			valsLength = this.options.values.length;
		}

		this._super( key, value );

		switch ( key ) {
			case "orientation":
				this._detectOrientation();
				this._removeClass( "ui-slider-horizontal ui-slider-vertical" )
					._addClass( "ui-slider-" + this.orientation );
				this._refreshValue();
				if ( this.options.range ) {
					this._refreshRange( value );
				}

				// Reset positioning from previous orientation
				this.handles.css( value === "horizontal" ? "bottom" : "left", "" );
				break;
			case "value":
				this._animateOff = true;
				this._refreshValue();
				this._change( null, 0 );
				this._animateOff = false;
				break;
			case "values":
				this._animateOff = true;
				this._refreshValue();

				// Start from the last handle to prevent unreachable handles (#9046)
				for ( i = valsLength - 1; i >= 0; i-- ) {
					this._change( null, i );
				}
				this._animateOff = false;
				break;
			case "step":
			case "min":
			case "max":
				this._animateOff = true;
				this._calculateNewMax();
				this._refreshValue();
				this._animateOff = false;
				break;
			case "range":
				this._animateOff = true;
				this._refresh();
				this._animateOff = false;
				break;
		}
	},

	_setOptionDisabled: function( value ) {
		this._super( value );

		this._toggleClass( null, "ui-state-disabled", !!value );
	},

	//internal value getter
	// _value() returns value trimmed by min and max, aligned by step
	_value: function() {
		var val = this.options.value;
		val = this._trimAlignValue( val );

		return val;
	},

	//internal values getter
	// _values() returns array of values trimmed by min and max, aligned by step
	// _values( index ) returns single value trimmed by min and max, aligned by step
	_values: function( index ) {
		var val,
			vals,
			i;

		if ( arguments.length ) {
			val = this.options.values[ index ];
			val = this._trimAlignValue( val );

			return val;
		} else if ( this._hasMultipleValues() ) {

			// .slice() creates a copy of the array
			// this copy gets trimmed by min and max and then returned
			vals = this.options.values.slice();
			for ( i = 0; i < vals.length; i += 1 ) {
				vals[ i ] = this._trimAlignValue( vals[ i ] );
			}

			return vals;
		} else {
			return [];
		}
	},

	// Returns the step-aligned value that val is closest to, between (inclusive) min and max
	_trimAlignValue: function( val ) {
		if ( val <= this._valueMin() ) {
			return this._valueMin();
		}
		if ( val >= this._valueMax() ) {
			return this._valueMax();
		}
		var step = ( this.options.step > 0 ) ? this.options.step : 1,
			valModStep = ( val - this._valueMin() ) % step,
			alignValue = val - valModStep;

		if ( Math.abs( valModStep ) * 2 >= step ) {
			alignValue += ( valModStep > 0 ) ? step : ( -step );
		}

		// Since JavaScript has problems with large floats, round
		// the final value to 5 digits after the decimal point (see #4124)
		return parseFloat( alignValue.toFixed( 5 ) );
	},

	_calculateNewMax: function() {
		var max = this.options.max,
			min = this._valueMin(),
			step = this.options.step,
			aboveMin = Math.round( ( max - min ) / step ) * step;
		max = aboveMin + min;
		if ( max > this.options.max ) {

			//If max is not divisible by step, rounding off may increase its value
			max -= step;
		}
		this.max = parseFloat( max.toFixed( this._precision() ) );
	},

	_precision: function() {
		var precision = this._precisionOf( this.options.step );
		if ( this.options.min !== null ) {
			precision = Math.max( precision, this._precisionOf( this.options.min ) );
		}
		return precision;
	},

	_precisionOf: function( num ) {
		var str = num.toString(),
			decimal = str.indexOf( "." );
		return decimal === -1 ? 0 : str.length - decimal - 1;
	},

	_valueMin: function() {
		return this.options.min;
	},

	_valueMax: function() {
		return this.max;
	},

	_refreshRange: function( orientation ) {
		if ( orientation === "vertical" ) {
			this.range.css( { "width": "", "left": "" } );
		}
		if ( orientation === "horizontal" ) {
			this.range.css( { "height": "", "bottom": "" } );
		}
	},

	_refreshValue: function() {
		var lastValPercent, valPercent, value, valueMin, valueMax,
			oRange = this.options.range,
			o = this.options,
			that = this,
			animate = ( !this._animateOff ) ? o.animate : false,
			_set = {};

		if ( this._hasMultipleValues() ) {
			this.handles.each( function( i ) {
				valPercent = ( that.values( i ) - that._valueMin() ) / ( that._valueMax() -
					that._valueMin() ) * 100;
				_set[ that.orientation === "horizontal" ? "left" : "bottom" ] = valPercent + "%";
				$( this ).stop( 1, 1 )[ animate ? "animate" : "css" ]( _set, o.animate );
				if ( that.options.range === true ) {
					if ( that.orientation === "horizontal" ) {
						if ( i === 0 ) {
							that.range.stop( 1, 1 )[ animate ? "animate" : "css" ]( {
								left: valPercent + "%"
							}, o.animate );
						}
						if ( i === 1 ) {
							that.range[ animate ? "animate" : "css" ]( {
								width: ( valPercent - lastValPercent ) + "%"
							}, {
								queue: false,
								duration: o.animate
							} );
						}
					} else {
						if ( i === 0 ) {
							that.range.stop( 1, 1 )[ animate ? "animate" : "css" ]( {
								bottom: ( valPercent ) + "%"
							}, o.animate );
						}
						if ( i === 1 ) {
							that.range[ animate ? "animate" : "css" ]( {
								height: ( valPercent - lastValPercent ) + "%"
							}, {
								queue: false,
								duration: o.animate
							} );
						}
					}
				}
				lastValPercent = valPercent;
			} );
		} else {
			value = this.value();
			valueMin = this._valueMin();
			valueMax = this._valueMax();
			valPercent = ( valueMax !== valueMin ) ?
					( value - valueMin ) / ( valueMax - valueMin ) * 100 :
					0;
			_set[ this.orientation === "horizontal" ? "left" : "bottom" ] = valPercent + "%";
			this.handle.stop( 1, 1 )[ animate ? "animate" : "css" ]( _set, o.animate );

			if ( oRange === "min" && this.orientation === "horizontal" ) {
				this.range.stop( 1, 1 )[ animate ? "animate" : "css" ]( {
					width: valPercent + "%"
				}, o.animate );
			}
			if ( oRange === "max" && this.orientation === "horizontal" ) {
				this.range.stop( 1, 1 )[ animate ? "animate" : "css" ]( {
					width: ( 100 - valPercent ) + "%"
				}, o.animate );
			}
			if ( oRange === "min" && this.orientation === "vertical" ) {
				this.range.stop( 1, 1 )[ animate ? "animate" : "css" ]( {
					height: valPercent + "%"
				}, o.animate );
			}
			if ( oRange === "max" && this.orientation === "vertical" ) {
				this.range.stop( 1, 1 )[ animate ? "animate" : "css" ]( {
					height: ( 100 - valPercent ) + "%"
				}, o.animate );
			}
		}
	},

	_handleEvents: {
		keydown: function( event ) {
			var allowed, curVal, newVal, step,
				index = $( event.target ).data( "ui-slider-handle-index" );

			switch ( event.keyCode ) {
				case $.ui.keyCode.HOME:
				case $.ui.keyCode.END:
				case $.ui.keyCode.PAGE_UP:
				case $.ui.keyCode.PAGE_DOWN:
				case $.ui.keyCode.UP:
				case $.ui.keyCode.RIGHT:
				case $.ui.keyCode.DOWN:
				case $.ui.keyCode.LEFT:
					event.preventDefault();
					if ( !this._keySliding ) {
						this._keySliding = true;
						this._addClass( $( event.target ), null, "ui-state-active" );
						allowed = this._start( event, index );
						if ( allowed === false ) {
							return;
						}
					}
					break;
			}

			step = this.options.step;
			if ( this._hasMultipleValues() ) {
				curVal = newVal = this.values( index );
			} else {
				curVal = newVal = this.value();
			}

			switch ( event.keyCode ) {
				case $.ui.keyCode.HOME:
					newVal = this._valueMin();
					break;
				case $.ui.keyCode.END:
					newVal = this._valueMax();
					break;
				case $.ui.keyCode.PAGE_UP:
					newVal = this._trimAlignValue(
						curVal + ( ( this._valueMax() - this._valueMin() ) / this.numPages )
					);
					break;
				case $.ui.keyCode.PAGE_DOWN:
					newVal = this._trimAlignValue(
						curVal - ( ( this._valueMax() - this._valueMin() ) / this.numPages ) );
					break;
				case $.ui.keyCode.UP:
				case $.ui.keyCode.RIGHT:
					if ( curVal === this._valueMax() ) {
						return;
					}
					newVal = this._trimAlignValue( curVal + step );
					break;
				case $.ui.keyCode.DOWN:
				case $.ui.keyCode.LEFT:
					if ( curVal === this._valueMin() ) {
						return;
					}
					newVal = this._trimAlignValue( curVal - step );
					break;
			}

			this._slide( event, index, newVal );
		},
		keyup: function( event ) {
			var index = $( event.target ).data( "ui-slider-handle-index" );

			if ( this._keySliding ) {
				this._keySliding = false;
				this._stop( event, index );
				this._change( event, index );
				this._removeClass( $( event.target ), null, "ui-state-active" );
			}
		}
	}
} );


/*!
 * jQuery UI Sortable 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: Sortable
//>>group: Interactions
//>>description: Enables items in a list to be sorted using the mouse.
//>>docs: http://api.jqueryui.com/sortable/
//>>demos: http://jqueryui.com/sortable/
//>>css.structure: ../../themes/base/sortable.css



var widgetsSortable = $.widget( "ui.sortable", $.ui.mouse, {
	version: "1.12.0",
	widgetEventPrefix: "sort",
	ready: false,
	options: {
		appendTo: "parent",
		axis: false,
		connectWith: false,
		containment: false,
		cursor: "auto",
		cursorAt: false,
		dropOnEmpty: true,
		forcePlaceholderSize: false,
		forceHelperSize: false,
		grid: false,
		handle: false,
		helper: "original",
		items: "> *",
		opacity: false,
		placeholder: false,
		revert: false,
		scroll: true,
		scrollSensitivity: 20,
		scrollSpeed: 20,
		scope: "default",
		tolerance: "intersect",
		zIndex: 1000,

		// Callbacks
		activate: null,
		beforeStop: null,
		change: null,
		deactivate: null,
		out: null,
		over: null,
		receive: null,
		remove: null,
		sort: null,
		start: null,
		stop: null,
		update: null
	},

	_isOverAxis: function( x, reference, size ) {
		return ( x >= reference ) && ( x < ( reference + size ) );
	},

	_isFloating: function( item ) {
		return ( /left|right/ ).test( item.css( "float" ) ) ||
			( /inline|table-cell/ ).test( item.css( "display" ) );
	},

	_create: function() {
		this.containerCache = {};
		this._addClass( "ui-sortable" );

		//Get the items
		this.refresh();

		//Let's determine the parent's offset
		this.offset = this.element.offset();

		//Initialize mouse events for interaction
		this._mouseInit();

		this._setHandleClassName();

		//We're ready to go
		this.ready = true;

	},

	_setOption: function( key, value ) {
		this._super( key, value );

		if ( key === "handle" ) {
			this._setHandleClassName();
		}
	},

	_setHandleClassName: function() {
		var that = this;
		this._removeClass( this.element.find( ".ui-sortable-handle" ), "ui-sortable-handle" );
		$.each( this.items, function() {
			that._addClass(
				this.instance.options.handle ?
					this.item.find( this.instance.options.handle ) :
					this.item,
				"ui-sortable-handle"
			);
		} );
	},

	_destroy: function() {
		this._mouseDestroy();

		for ( var i = this.items.length - 1; i >= 0; i-- ) {
			this.items[ i ].item.removeData( this.widgetName + "-item" );
		}

		return this;
	},

	_mouseCapture: function( event, overrideHandle ) {
		var currentItem = null,
			validHandle = false,
			that = this;

		if ( this.reverting ) {
			return false;
		}

		if ( this.options.disabled || this.options.type === "static" ) {
			return false;
		}

		//We have to refresh the items data once first
		this._refreshItems( event );

		//Find out if the clicked node (or one of its parents) is a actual item in this.items
		$( event.target ).parents().each( function() {
			if ( $.data( this, that.widgetName + "-item" ) === that ) {
				currentItem = $( this );
				return false;
			}
		} );
		if ( $.data( event.target, that.widgetName + "-item" ) === that ) {
			currentItem = $( event.target );
		}

		if ( !currentItem ) {
			return false;
		}
		if ( this.options.handle && !overrideHandle ) {
			$( this.options.handle, currentItem ).find( "*" ).addBack().each( function() {
				if ( this === event.target ) {
					validHandle = true;
				}
			} );
			if ( !validHandle ) {
				return false;
			}
		}

		this.currentItem = currentItem;
		this._removeCurrentsFromItems();
		return true;

	},

	_mouseStart: function( event, overrideHandle, noActivation ) {

		var i, body,
			o = this.options;

		this.currentContainer = this;

		//We only need to call refreshPositions, because the refreshItems call has been moved to
		// mouseCapture
		this.refreshPositions();

		//Create and append the visible helper
		this.helper = this._createHelper( event );

		//Cache the helper size
		this._cacheHelperProportions();

		/*
		 * - Position generation -
		 * This block generates everything position related - it's the core of draggables.
		 */

		//Cache the margins of the original element
		this._cacheMargins();

		//Get the next scrolling parent
		this.scrollParent = this.helper.scrollParent();

		//The element's absolute position on the page minus margins
		this.offset = this.currentItem.offset();
		this.offset = {
			top: this.offset.top - this.margins.top,
			left: this.offset.left - this.margins.left
		};

		$.extend( this.offset, {
			click: { //Where the click happened, relative to the element
				left: event.pageX - this.offset.left,
				top: event.pageY - this.offset.top
			},
			parent: this._getParentOffset(),

			// This is a relative to absolute position minus the actual position calculation -
			// only used for relative positioned helper
			relative: this._getRelativeOffset()
		} );

		// Only after we got the offset, we can change the helper's position to absolute
		// TODO: Still need to figure out a way to make relative sorting possible
		this.helper.css( "position", "absolute" );
		this.cssPosition = this.helper.css( "position" );

		//Generate the original position
		this.originalPosition = this._generatePosition( event );
		this.originalPageX = event.pageX;
		this.originalPageY = event.pageY;

		//Adjust the mouse offset relative to the helper if "cursorAt" is supplied
		( o.cursorAt && this._adjustOffsetFromHelper( o.cursorAt ) );

		//Cache the former DOM position
		this.domPosition = {
			prev: this.currentItem.prev()[ 0 ],
			parent: this.currentItem.parent()[ 0 ]
		};

		// If the helper is not the original, hide the original so it's not playing any role during
		// the drag, won't cause anything bad this way
		if ( this.helper[ 0 ] !== this.currentItem[ 0 ] ) {
			this.currentItem.hide();
		}

		//Create the placeholder
		this._createPlaceholder();

		//Set a containment if given in the options
		if ( o.containment ) {
			this._setContainment();
		}

		if ( o.cursor && o.cursor !== "auto" ) { // cursor option
			body = this.document.find( "body" );

			// Support: IE
			this.storedCursor = body.css( "cursor" );
			body.css( "cursor", o.cursor );

			this.storedStylesheet =
				$( "<style>*{ cursor: " + o.cursor + " !important; }</style>" ).appendTo( body );
		}

		if ( o.opacity ) { // opacity option
			if ( this.helper.css( "opacity" ) ) {
				this._storedOpacity = this.helper.css( "opacity" );
			}
			this.helper.css( "opacity", o.opacity );
		}

		if ( o.zIndex ) { // zIndex option
			if ( this.helper.css( "zIndex" ) ) {
				this._storedZIndex = this.helper.css( "zIndex" );
			}
			this.helper.css( "zIndex", o.zIndex );
		}

		//Prepare scrolling
		if ( this.scrollParent[ 0 ] !== this.document[ 0 ] &&
				this.scrollParent[ 0 ].tagName !== "HTML" ) {
			this.overflowOffset = this.scrollParent.offset();
		}

		//Call callbacks
		this._trigger( "start", event, this._uiHash() );

		//Recache the helper size
		if ( !this._preserveHelperProportions ) {
			this._cacheHelperProportions();
		}

		//Post "activate" events to possible containers
		if ( !noActivation ) {
			for ( i = this.containers.length - 1; i >= 0; i-- ) {
				this.containers[ i ]._trigger( "activate", event, this._uiHash( this ) );
			}
		}

		//Prepare possible droppables
		if ( $.ui.ddmanager ) {
			$.ui.ddmanager.current = this;
		}

		if ( $.ui.ddmanager && !o.dropBehaviour ) {
			$.ui.ddmanager.prepareOffsets( this, event );
		}

		this.dragging = true;

		this._addClass( this.helper, "ui-sortable-helper" );

		// Execute the drag once - this causes the helper not to be visiblebefore getting its
		// correct position
		this._mouseDrag( event );
		return true;

	},

	_mouseDrag: function( event ) {
		var i, item, itemElement, intersection,
			o = this.options,
			scrolled = false;

		//Compute the helpers position
		this.position = this._generatePosition( event );
		this.positionAbs = this._convertPositionTo( "absolute" );

		if ( !this.lastPositionAbs ) {
			this.lastPositionAbs = this.positionAbs;
		}

		//Do scrolling
		if ( this.options.scroll ) {
			if ( this.scrollParent[ 0 ] !== this.document[ 0 ] &&
					this.scrollParent[ 0 ].tagName !== "HTML" ) {

				if ( ( this.overflowOffset.top + this.scrollParent[ 0 ].offsetHeight ) -
						event.pageY < o.scrollSensitivity ) {
					this.scrollParent[ 0 ].scrollTop =
						scrolled = this.scrollParent[ 0 ].scrollTop + o.scrollSpeed;
				} else if ( event.pageY - this.overflowOffset.top < o.scrollSensitivity ) {
					this.scrollParent[ 0 ].scrollTop =
						scrolled = this.scrollParent[ 0 ].scrollTop - o.scrollSpeed;
				}

				if ( ( this.overflowOffset.left + this.scrollParent[ 0 ].offsetWidth ) -
						event.pageX < o.scrollSensitivity ) {
					this.scrollParent[ 0 ].scrollLeft = scrolled =
						this.scrollParent[ 0 ].scrollLeft + o.scrollSpeed;
				} else if ( event.pageX - this.overflowOffset.left < o.scrollSensitivity ) {
					this.scrollParent[ 0 ].scrollLeft = scrolled =
						this.scrollParent[ 0 ].scrollLeft - o.scrollSpeed;
				}

			} else {

				if ( event.pageY - this.document.scrollTop() < o.scrollSensitivity ) {
					scrolled = this.document.scrollTop( this.document.scrollTop() - o.scrollSpeed );
				} else if ( this.window.height() - ( event.pageY - this.document.scrollTop() ) <
						o.scrollSensitivity ) {
					scrolled = this.document.scrollTop( this.document.scrollTop() + o.scrollSpeed );
				}

				if ( event.pageX - this.document.scrollLeft() < o.scrollSensitivity ) {
					scrolled = this.document.scrollLeft(
						this.document.scrollLeft() - o.scrollSpeed
					);
				} else if ( this.window.width() - ( event.pageX - this.document.scrollLeft() ) <
						o.scrollSensitivity ) {
					scrolled = this.document.scrollLeft(
						this.document.scrollLeft() + o.scrollSpeed
					);
				}

			}

			if ( scrolled !== false && $.ui.ddmanager && !o.dropBehaviour ) {
				$.ui.ddmanager.prepareOffsets( this, event );
			}
		}

		//Regenerate the absolute position used for position checks
		this.positionAbs = this._convertPositionTo( "absolute" );

		//Set the helper position
		if ( !this.options.axis || this.options.axis !== "y" ) {
			this.helper[ 0 ].style.left = this.position.left + "px";
		}
		if ( !this.options.axis || this.options.axis !== "x" ) {
			this.helper[ 0 ].style.top = this.position.top + "px";
		}

		//Rearrange
		for ( i = this.items.length - 1; i >= 0; i-- ) {

			//Cache variables and intersection, continue if no intersection
			item = this.items[ i ];
			itemElement = item.item[ 0 ];
			intersection = this._intersectsWithPointer( item );
			if ( !intersection ) {
				continue;
			}

			// Only put the placeholder inside the current Container, skip all
			// items from other containers. This works because when moving
			// an item from one container to another the
			// currentContainer is switched before the placeholder is moved.
			//
			// Without this, moving items in "sub-sortables" can cause
			// the placeholder to jitter between the outer and inner container.
			if ( item.instance !== this.currentContainer ) {
				continue;
			}

			// Cannot intersect with itself
			// no useless actions that have been done before
			// no action if the item moved is the parent of the item checked
			if ( itemElement !== this.currentItem[ 0 ] &&
				this.placeholder[ intersection === 1 ? "next" : "prev" ]()[ 0 ] !== itemElement &&
				!$.contains( this.placeholder[ 0 ], itemElement ) &&
				( this.options.type === "semi-dynamic" ?
					!$.contains( this.element[ 0 ], itemElement ) :
					true
				)
			) {

				this.direction = intersection === 1 ? "down" : "up";

				if ( this.options.tolerance === "pointer" || this._intersectsWithSides( item ) ) {
					this._rearrange( event, item );
				} else {
					break;
				}

				this._trigger( "change", event, this._uiHash() );
				break;
			}
		}

		//Post events to containers
		this._contactContainers( event );

		//Interconnect with droppables
		if ( $.ui.ddmanager ) {
			$.ui.ddmanager.drag( this, event );
		}

		//Call callbacks
		this._trigger( "sort", event, this._uiHash() );

		this.lastPositionAbs = this.positionAbs;
		return false;

	},

	_mouseStop: function( event, noPropagation ) {

		if ( !event ) {
			return;
		}

		//If we are using droppables, inform the manager about the drop
		if ( $.ui.ddmanager && !this.options.dropBehaviour ) {
			$.ui.ddmanager.drop( this, event );
		}

		if ( this.options.revert ) {
			var that = this,
				cur = this.placeholder.offset(),
				axis = this.options.axis,
				animation = {};

			if ( !axis || axis === "x" ) {
				animation.left = cur.left - this.offset.parent.left - this.margins.left +
					( this.offsetParent[ 0 ] === this.document[ 0 ].body ?
						0 :
						this.offsetParent[ 0 ].scrollLeft
					);
			}
			if ( !axis || axis === "y" ) {
				animation.top = cur.top - this.offset.parent.top - this.margins.top +
					( this.offsetParent[ 0 ] === this.document[ 0 ].body ?
						0 :
						this.offsetParent[ 0 ].scrollTop
					);
			}
			this.reverting = true;
			$( this.helper ).animate(
				animation,
				parseInt( this.options.revert, 10 ) || 500,
				function() {
					that._clear( event );
				}
			);
		} else {
			this._clear( event, noPropagation );
		}

		return false;

	},

	cancel: function() {

		if ( this.dragging ) {

			this._mouseUp( { target: null } );

			if ( this.options.helper === "original" ) {
				this.currentItem.css( this._storedCSS );
				this._removeClass( this.currentItem, "ui-sortable-helper" );
			} else {
				this.currentItem.show();
			}

			//Post deactivating events to containers
			for ( var i = this.containers.length - 1; i >= 0; i-- ) {
				this.containers[ i ]._trigger( "deactivate", null, this._uiHash( this ) );
				if ( this.containers[ i ].containerCache.over ) {
					this.containers[ i ]._trigger( "out", null, this._uiHash( this ) );
					this.containers[ i ].containerCache.over = 0;
				}
			}

		}

		if ( this.placeholder ) {

			//$(this.placeholder[0]).remove(); would have been the jQuery way - unfortunately,
			// it unbinds ALL events from the original node!
			if ( this.placeholder[ 0 ].parentNode ) {
				this.placeholder[ 0 ].parentNode.removeChild( this.placeholder[ 0 ] );
			}
			if ( this.options.helper !== "original" && this.helper &&
					this.helper[ 0 ].parentNode ) {
				this.helper.remove();
			}

			$.extend( this, {
				helper: null,
				dragging: false,
				reverting: false,
				_noFinalSort: null
			} );

			if ( this.domPosition.prev ) {
				$( this.domPosition.prev ).after( this.currentItem );
			} else {
				$( this.domPosition.parent ).prepend( this.currentItem );
			}
		}

		return this;

	},

	serialize: function( o ) {

		var items = this._getItemsAsjQuery( o && o.connected ),
			str = [];
		o = o || {};

		$( items ).each( function() {
			var res = ( $( o.item || this ).attr( o.attribute || "id" ) || "" )
				.match( o.expression || ( /(.+)[\-=_](.+)/ ) );
			if ( res ) {
				str.push(
					( o.key || res[ 1 ] + "[]" ) +
					"=" + ( o.key && o.expression ? res[ 1 ] : res[ 2 ] ) );
			}
		} );

		if ( !str.length && o.key ) {
			str.push( o.key + "=" );
		}

		return str.join( "&" );

	},

	toArray: function( o ) {

		var items = this._getItemsAsjQuery( o && o.connected ),
			ret = [];

		o = o || {};

		items.each( function() {
			ret.push( $( o.item || this ).attr( o.attribute || "id" ) || "" );
		} );
		return ret;

	},

	/* Be careful with the following core functions */
	_intersectsWith: function( item ) {

		var x1 = this.positionAbs.left,
			x2 = x1 + this.helperProportions.width,
			y1 = this.positionAbs.top,
			y2 = y1 + this.helperProportions.height,
			l = item.left,
			r = l + item.width,
			t = item.top,
			b = t + item.height,
			dyClick = this.offset.click.top,
			dxClick = this.offset.click.left,
			isOverElementHeight = ( this.options.axis === "x" ) || ( ( y1 + dyClick ) > t &&
				( y1 + dyClick ) < b ),
			isOverElementWidth = ( this.options.axis === "y" ) || ( ( x1 + dxClick ) > l &&
				( x1 + dxClick ) < r ),
			isOverElement = isOverElementHeight && isOverElementWidth;

		if ( this.options.tolerance === "pointer" ||
			this.options.forcePointerForContainers ||
			( this.options.tolerance !== "pointer" &&
				this.helperProportions[ this.floating ? "width" : "height" ] >
				item[ this.floating ? "width" : "height" ] )
		) {
			return isOverElement;
		} else {

			return ( l < x1 + ( this.helperProportions.width / 2 ) && // Right Half
				x2 - ( this.helperProportions.width / 2 ) < r && // Left Half
				t < y1 + ( this.helperProportions.height / 2 ) && // Bottom Half
				y2 - ( this.helperProportions.height / 2 ) < b ); // Top Half

		}
	},

	_intersectsWithPointer: function( item ) {
		var verticalDirection, horizontalDirection,
			isOverElementHeight = ( this.options.axis === "x" ) ||
				this._isOverAxis(
					this.positionAbs.top + this.offset.click.top, item.top, item.height ),
			isOverElementWidth = ( this.options.axis === "y" ) ||
				this._isOverAxis(
					this.positionAbs.left + this.offset.click.left, item.left, item.width ),
			isOverElement = isOverElementHeight && isOverElementWidth;

		if ( !isOverElement ) {
			return false;
		}

		verticalDirection = this._getDragVerticalDirection();
		horizontalDirection = this._getDragHorizontalDirection();

		return this.floating ?
			( ( horizontalDirection === "right" || verticalDirection === "down" ) ? 2 : 1 )
			: ( verticalDirection && ( verticalDirection === "down" ? 2 : 1 ) );

	},

	_intersectsWithSides: function( item ) {

		var isOverBottomHalf = this._isOverAxis( this.positionAbs.top +
				this.offset.click.top, item.top + ( item.height / 2 ), item.height ),
			isOverRightHalf = this._isOverAxis( this.positionAbs.left +
				this.offset.click.left, item.left + ( item.width / 2 ), item.width ),
			verticalDirection = this._getDragVerticalDirection(),
			horizontalDirection = this._getDragHorizontalDirection();

		if ( this.floating && horizontalDirection ) {
			return ( ( horizontalDirection === "right" && isOverRightHalf ) ||
				( horizontalDirection === "left" && !isOverRightHalf ) );
		} else {
			return verticalDirection && ( ( verticalDirection === "down" && isOverBottomHalf ) ||
				( verticalDirection === "up" && !isOverBottomHalf ) );
		}

	},

	_getDragVerticalDirection: function() {
		var delta = this.positionAbs.top - this.lastPositionAbs.top;
		return delta !== 0 && ( delta > 0 ? "down" : "up" );
	},

	_getDragHorizontalDirection: function() {
		var delta = this.positionAbs.left - this.lastPositionAbs.left;
		return delta !== 0 && ( delta > 0 ? "right" : "left" );
	},

	refresh: function( event ) {
		this._refreshItems( event );
		this._setHandleClassName();
		this.refreshPositions();
		return this;
	},

	_connectWith: function() {
		var options = this.options;
		return options.connectWith.constructor === String ?
			[ options.connectWith ] :
			options.connectWith;
	},

	_getItemsAsjQuery: function( connected ) {

		var i, j, cur, inst,
			items = [],
			queries = [],
			connectWith = this._connectWith();

		if ( connectWith && connected ) {
			for ( i = connectWith.length - 1; i >= 0; i-- ) {
				cur = $( connectWith[ i ], this.document[ 0 ] );
				for ( j = cur.length - 1; j >= 0; j-- ) {
					inst = $.data( cur[ j ], this.widgetFullName );
					if ( inst && inst !== this && !inst.options.disabled ) {
						queries.push( [ $.isFunction( inst.options.items ) ?
							inst.options.items.call( inst.element ) :
							$( inst.options.items, inst.element )
								.not( ".ui-sortable-helper" )
								.not( ".ui-sortable-placeholder" ), inst ] );
					}
				}
			}
		}

		queries.push( [ $.isFunction( this.options.items ) ?
			this.options.items
				.call( this.element, null, { options: this.options, item: this.currentItem } ) :
			$( this.options.items, this.element )
				.not( ".ui-sortable-helper" )
				.not( ".ui-sortable-placeholder" ), this ] );

		function addItems() {
			items.push( this );
		}
		for ( i = queries.length - 1; i >= 0; i-- ) {
			queries[ i ][ 0 ].each( addItems );
		}

		return $( items );

	},

	_removeCurrentsFromItems: function() {

		var list = this.currentItem.find( ":data(" + this.widgetName + "-item)" );

		this.items = $.grep( this.items, function( item ) {
			for ( var j = 0; j < list.length; j++ ) {
				if ( list[ j ] === item.item[ 0 ] ) {
					return false;
				}
			}
			return true;
		} );

	},

	_refreshItems: function( event ) {

		this.items = [];
		this.containers = [ this ];

		var i, j, cur, inst, targetData, _queries, item, queriesLength,
			items = this.items,
			queries = [ [ $.isFunction( this.options.items ) ?
				this.options.items.call( this.element[ 0 ], event, { item: this.currentItem } ) :
				$( this.options.items, this.element ), this ] ],
			connectWith = this._connectWith();

		//Shouldn't be run the first time through due to massive slow-down
		if ( connectWith && this.ready ) {
			for ( i = connectWith.length - 1; i >= 0; i-- ) {
				cur = $( connectWith[ i ], this.document[ 0 ] );
				for ( j = cur.length - 1; j >= 0; j-- ) {
					inst = $.data( cur[ j ], this.widgetFullName );
					if ( inst && inst !== this && !inst.options.disabled ) {
						queries.push( [ $.isFunction( inst.options.items ) ?
							inst.options.items
								.call( inst.element[ 0 ], event, { item: this.currentItem } ) :
							$( inst.options.items, inst.element ), inst ] );
						this.containers.push( inst );
					}
				}
			}
		}

		for ( i = queries.length - 1; i >= 0; i-- ) {
			targetData = queries[ i ][ 1 ];
			_queries = queries[ i ][ 0 ];

			for ( j = 0, queriesLength = _queries.length; j < queriesLength; j++ ) {
				item = $( _queries[ j ] );

				// Data for target checking (mouse manager)
				item.data( this.widgetName + "-item", targetData );

				items.push( {
					item: item,
					instance: targetData,
					width: 0, height: 0,
					left: 0, top: 0
				} );
			}
		}

	},

	refreshPositions: function( fast ) {

		// Determine whether items are being displayed horizontally
		this.floating = this.items.length ?
			this.options.axis === "x" || this._isFloating( this.items[ 0 ].item ) :
			false;

		//This has to be redone because due to the item being moved out/into the offsetParent,
		// the offsetParent's position will change
		if ( this.offsetParent && this.helper ) {
			this.offset.parent = this._getParentOffset();
		}

		var i, item, t, p;

		for ( i = this.items.length - 1; i >= 0; i-- ) {
			item = this.items[ i ];

			//We ignore calculating positions of all connected containers when we're not over them
			if ( item.instance !== this.currentContainer && this.currentContainer &&
					item.item[ 0 ] !== this.currentItem[ 0 ] ) {
				continue;
			}

			t = this.options.toleranceElement ?
				$( this.options.toleranceElement, item.item ) :
				item.item;

			if ( !fast ) {
				item.width = t.outerWidth();
				item.height = t.outerHeight();
			}

			p = t.offset();
			item.left = p.left;
			item.top = p.top;
		}

		if ( this.options.custom && this.options.custom.refreshContainers ) {
			this.options.custom.refreshContainers.call( this );
		} else {
			for ( i = this.containers.length - 1; i >= 0; i-- ) {
				p = this.containers[ i ].element.offset();
				this.containers[ i ].containerCache.left = p.left;
				this.containers[ i ].containerCache.top = p.top;
				this.containers[ i ].containerCache.width =
					this.containers[ i ].element.outerWidth();
				this.containers[ i ].containerCache.height =
					this.containers[ i ].element.outerHeight();
			}
		}

		return this;
	},

	_createPlaceholder: function( that ) {
		that = that || this;
		var className,
			o = that.options;

		if ( !o.placeholder || o.placeholder.constructor === String ) {
			className = o.placeholder;
			o.placeholder = {
				element: function() {

					var nodeName = that.currentItem[ 0 ].nodeName.toLowerCase(),
						element = $( "<" + nodeName + ">", that.document[ 0 ] );

						that._addClass( element, "ui-sortable-placeholder",
								className || that.currentItem[ 0 ].className )
							._removeClass( element, "ui-sortable-helper" );

					if ( nodeName === "tbody" ) {
						that._createTrPlaceholder(
							that.currentItem.find( "tr" ).eq( 0 ),
							$( "<tr>", that.document[ 0 ] ).appendTo( element )
						);
					} else if ( nodeName === "tr" ) {
						that._createTrPlaceholder( that.currentItem, element );
					} else if ( nodeName === "img" ) {
						element.attr( "src", that.currentItem.attr( "src" ) );
					}

					if ( !className ) {
						element.css( "visibility", "hidden" );
					}

					return element;
				},
				update: function( container, p ) {

					// 1. If a className is set as 'placeholder option, we don't force sizes -
					// the class is responsible for that
					// 2. The option 'forcePlaceholderSize can be enabled to force it even if a
					// class name is specified
					if ( className && !o.forcePlaceholderSize ) {
						return;
					}

					//If the element doesn't have a actual height by itself (without styles coming
					// from a stylesheet), it receives the inline height from the dragged item
					if ( !p.height() ) {
						p.height(
							that.currentItem.innerHeight() -
							parseInt( that.currentItem.css( "paddingTop" ) || 0, 10 ) -
							parseInt( that.currentItem.css( "paddingBottom" ) || 0, 10 ) );
					}
					if ( !p.width() ) {
						p.width(
							that.currentItem.innerWidth() -
							parseInt( that.currentItem.css( "paddingLeft" ) || 0, 10 ) -
							parseInt( that.currentItem.css( "paddingRight" ) || 0, 10 ) );
					}
				}
			};
		}

		//Create the placeholder
		that.placeholder = $( o.placeholder.element.call( that.element, that.currentItem ) );

		//Append it after the actual current item
		that.currentItem.after( that.placeholder );

		//Update the size of the placeholder (TODO: Logic to fuzzy, see line 316/317)
		o.placeholder.update( that, that.placeholder );

	},

	_createTrPlaceholder: function( sourceTr, targetTr ) {
		var that = this;

		sourceTr.children().each( function() {
			$( "<td>&#160;</td>", that.document[ 0 ] )
				.attr( "colspan", $( this ).attr( "colspan" ) || 1 )
				.appendTo( targetTr );
		} );
	},

	_contactContainers: function( event ) {
		var i, j, dist, itemWithLeastDistance, posProperty, sizeProperty, cur, nearBottom,
			floating, axis,
			innermostContainer = null,
			innermostIndex = null;

		// Get innermost container that intersects with item
		for ( i = this.containers.length - 1; i >= 0; i-- ) {

			// Never consider a container that's located within the item itself
			if ( $.contains( this.currentItem[ 0 ], this.containers[ i ].element[ 0 ] ) ) {
				continue;
			}

			if ( this._intersectsWith( this.containers[ i ].containerCache ) ) {

				// If we've already found a container and it's more "inner" than this, then continue
				if ( innermostContainer &&
						$.contains(
							this.containers[ i ].element[ 0 ],
							innermostContainer.element[ 0 ] ) ) {
					continue;
				}

				innermostContainer = this.containers[ i ];
				innermostIndex = i;

			} else {

				// container doesn't intersect. trigger "out" event if necessary
				if ( this.containers[ i ].containerCache.over ) {
					this.containers[ i ]._trigger( "out", event, this._uiHash( this ) );
					this.containers[ i ].containerCache.over = 0;
				}
			}

		}

		// If no intersecting containers found, return
		if ( !innermostContainer ) {
			return;
		}

		// Move the item into the container if it's not there already
		if ( this.containers.length === 1 ) {
			if ( !this.containers[ innermostIndex ].containerCache.over ) {
				this.containers[ innermostIndex ]._trigger( "over", event, this._uiHash( this ) );
				this.containers[ innermostIndex ].containerCache.over = 1;
			}
		} else {

			// When entering a new container, we will find the item with the least distance and
			// append our item near it
			dist = 10000;
			itemWithLeastDistance = null;
			floating = innermostContainer.floating || this._isFloating( this.currentItem );
			posProperty = floating ? "left" : "top";
			sizeProperty = floating ? "width" : "height";
			axis = floating ? "pageX" : "pageY";

			for ( j = this.items.length - 1; j >= 0; j-- ) {
				if ( !$.contains(
						this.containers[ innermostIndex ].element[ 0 ], this.items[ j ].item[ 0 ] )
				) {
					continue;
				}
				if ( this.items[ j ].item[ 0 ] === this.currentItem[ 0 ] ) {
					continue;
				}

				cur = this.items[ j ].item.offset()[ posProperty ];
				nearBottom = false;
				if ( event[ axis ] - cur > this.items[ j ][ sizeProperty ] / 2 ) {
					nearBottom = true;
				}

				if ( Math.abs( event[ axis ] - cur ) < dist ) {
					dist = Math.abs( event[ axis ] - cur );
					itemWithLeastDistance = this.items[ j ];
					this.direction = nearBottom ? "up" : "down";
				}
			}

			//Check if dropOnEmpty is enabled
			if ( !itemWithLeastDistance && !this.options.dropOnEmpty ) {
				return;
			}

			if ( this.currentContainer === this.containers[ innermostIndex ] ) {
				if ( !this.currentContainer.containerCache.over ) {
					this.containers[ innermostIndex ]._trigger( "over", event, this._uiHash() );
					this.currentContainer.containerCache.over = 1;
				}
				return;
			}

			itemWithLeastDistance ?
				this._rearrange( event, itemWithLeastDistance, null, true ) :
				this._rearrange( event, null, this.containers[ innermostIndex ].element, true );
			this._trigger( "change", event, this._uiHash() );
			this.containers[ innermostIndex ]._trigger( "change", event, this._uiHash( this ) );
			this.currentContainer = this.containers[ innermostIndex ];

			//Update the placeholder
			this.options.placeholder.update( this.currentContainer, this.placeholder );

			this.containers[ innermostIndex ]._trigger( "over", event, this._uiHash( this ) );
			this.containers[ innermostIndex ].containerCache.over = 1;
		}

	},

	_createHelper: function( event ) {

		var o = this.options,
			helper = $.isFunction( o.helper ) ?
				$( o.helper.apply( this.element[ 0 ], [ event, this.currentItem ] ) ) :
				( o.helper === "clone" ? this.currentItem.clone() : this.currentItem );

		//Add the helper to the DOM if that didn't happen already
		if ( !helper.parents( "body" ).length ) {
			$( o.appendTo !== "parent" ?
				o.appendTo :
				this.currentItem[ 0 ].parentNode )[ 0 ].appendChild( helper[ 0 ] );
		}

		if ( helper[ 0 ] === this.currentItem[ 0 ] ) {
			this._storedCSS = {
				width: this.currentItem[ 0 ].style.width,
				height: this.currentItem[ 0 ].style.height,
				position: this.currentItem.css( "position" ),
				top: this.currentItem.css( "top" ),
				left: this.currentItem.css( "left" )
			};
		}

		if ( !helper[ 0 ].style.width || o.forceHelperSize ) {
			helper.width( this.currentItem.width() );
		}
		if ( !helper[ 0 ].style.height || o.forceHelperSize ) {
			helper.height( this.currentItem.height() );
		}

		return helper;

	},

	_adjustOffsetFromHelper: function( obj ) {
		if ( typeof obj === "string" ) {
			obj = obj.split( " " );
		}
		if ( $.isArray( obj ) ) {
			obj = { left: +obj[ 0 ], top: +obj[ 1 ] || 0 };
		}
		if ( "left" in obj ) {
			this.offset.click.left = obj.left + this.margins.left;
		}
		if ( "right" in obj ) {
			this.offset.click.left = this.helperProportions.width - obj.right + this.margins.left;
		}
		if ( "top" in obj ) {
			this.offset.click.top = obj.top + this.margins.top;
		}
		if ( "bottom" in obj ) {
			this.offset.click.top = this.helperProportions.height - obj.bottom + this.margins.top;
		}
	},

	_getParentOffset: function() {

		//Get the offsetParent and cache its position
		this.offsetParent = this.helper.offsetParent();
		var po = this.offsetParent.offset();

		// This is a special case where we need to modify a offset calculated on start, since the
		// following happened:
		// 1. The position of the helper is absolute, so it's position is calculated based on the
		// next positioned parent
		// 2. The actual offset parent is a child of the scroll parent, and the scroll parent isn't
		// the document, which means that the scroll is included in the initial calculation of the
		// offset of the parent, and never recalculated upon drag
		if ( this.cssPosition === "absolute" && this.scrollParent[ 0 ] !== this.document[ 0 ] &&
				$.contains( this.scrollParent[ 0 ], this.offsetParent[ 0 ] ) ) {
			po.left += this.scrollParent.scrollLeft();
			po.top += this.scrollParent.scrollTop();
		}

		// This needs to be actually done for all browsers, since pageX/pageY includes this
		// information with an ugly IE fix
		if ( this.offsetParent[ 0 ] === this.document[ 0 ].body ||
				( this.offsetParent[ 0 ].tagName &&
				this.offsetParent[ 0 ].tagName.toLowerCase() === "html" && $.ui.ie ) ) {
			po = { top: 0, left: 0 };
		}

		return {
			top: po.top + ( parseInt( this.offsetParent.css( "borderTopWidth" ), 10 ) || 0 ),
			left: po.left + ( parseInt( this.offsetParent.css( "borderLeftWidth" ), 10 ) || 0 )
		};

	},

	_getRelativeOffset: function() {

		if ( this.cssPosition === "relative" ) {
			var p = this.currentItem.position();
			return {
				top: p.top - ( parseInt( this.helper.css( "top" ), 10 ) || 0 ) +
					this.scrollParent.scrollTop(),
				left: p.left - ( parseInt( this.helper.css( "left" ), 10 ) || 0 ) +
					this.scrollParent.scrollLeft()
			};
		} else {
			return { top: 0, left: 0 };
		}

	},

	_cacheMargins: function() {
		this.margins = {
			left: ( parseInt( this.currentItem.css( "marginLeft" ), 10 ) || 0 ),
			top: ( parseInt( this.currentItem.css( "marginTop" ), 10 ) || 0 )
		};
	},

	_cacheHelperProportions: function() {
		this.helperProportions = {
			width: this.helper.outerWidth(),
			height: this.helper.outerHeight()
		};
	},

	_setContainment: function() {

		var ce, co, over,
			o = this.options;
		if ( o.containment === "parent" ) {
			o.containment = this.helper[ 0 ].parentNode;
		}
		if ( o.containment === "document" || o.containment === "window" ) {
			this.containment = [
				0 - this.offset.relative.left - this.offset.parent.left,
				0 - this.offset.relative.top - this.offset.parent.top,
				o.containment === "document" ?
					this.document.width() :
					this.window.width() - this.helperProportions.width - this.margins.left,
				( o.containment === "document" ?
					( this.document.height() || document.body.parentNode.scrollHeight ) :
					this.window.height() || this.document[ 0 ].body.parentNode.scrollHeight
				) - this.helperProportions.height - this.margins.top
			];
		}

		if ( !( /^(document|window|parent)$/ ).test( o.containment ) ) {
			ce = $( o.containment )[ 0 ];
			co = $( o.containment ).offset();
			over = ( $( ce ).css( "overflow" ) !== "hidden" );

			this.containment = [
				co.left + ( parseInt( $( ce ).css( "borderLeftWidth" ), 10 ) || 0 ) +
					( parseInt( $( ce ).css( "paddingLeft" ), 10 ) || 0 ) - this.margins.left,
				co.top + ( parseInt( $( ce ).css( "borderTopWidth" ), 10 ) || 0 ) +
					( parseInt( $( ce ).css( "paddingTop" ), 10 ) || 0 ) - this.margins.top,
				co.left + ( over ? Math.max( ce.scrollWidth, ce.offsetWidth ) : ce.offsetWidth ) -
					( parseInt( $( ce ).css( "borderLeftWidth" ), 10 ) || 0 ) -
					( parseInt( $( ce ).css( "paddingRight" ), 10 ) || 0 ) -
					this.helperProportions.width - this.margins.left,
				co.top + ( over ? Math.max( ce.scrollHeight, ce.offsetHeight ) : ce.offsetHeight ) -
					( parseInt( $( ce ).css( "borderTopWidth" ), 10 ) || 0 ) -
					( parseInt( $( ce ).css( "paddingBottom" ), 10 ) || 0 ) -
					this.helperProportions.height - this.margins.top
			];
		}

	},

	_convertPositionTo: function( d, pos ) {

		if ( !pos ) {
			pos = this.position;
		}
		var mod = d === "absolute" ? 1 : -1,
			scroll = this.cssPosition === "absolute" &&
				!( this.scrollParent[ 0 ] !== this.document[ 0 ] &&
				$.contains( this.scrollParent[ 0 ], this.offsetParent[ 0 ] ) ) ?
					this.offsetParent :
					this.scrollParent,
			scrollIsRootNode = ( /(html|body)/i ).test( scroll[ 0 ].tagName );

		return {
			top: (

				// The absolute mouse position
				pos.top	+

				// Only for relative positioned nodes: Relative offset from element to offset parent
				this.offset.relative.top * mod +

				// The offsetParent's offset without borders (offset + border)
				this.offset.parent.top * mod -
				( ( this.cssPosition === "fixed" ?
					-this.scrollParent.scrollTop() :
					( scrollIsRootNode ? 0 : scroll.scrollTop() ) ) * mod )
			),
			left: (

				// The absolute mouse position
				pos.left +

				// Only for relative positioned nodes: Relative offset from element to offset parent
				this.offset.relative.left * mod +

				// The offsetParent's offset without borders (offset + border)
				this.offset.parent.left * mod	-
				( ( this.cssPosition === "fixed" ?
					-this.scrollParent.scrollLeft() : scrollIsRootNode ? 0 :
					scroll.scrollLeft() ) * mod )
			)
		};

	},

	_generatePosition: function( event ) {

		var top, left,
			o = this.options,
			pageX = event.pageX,
			pageY = event.pageY,
			scroll = this.cssPosition === "absolute" &&
				!( this.scrollParent[ 0 ] !== this.document[ 0 ] &&
				$.contains( this.scrollParent[ 0 ], this.offsetParent[ 0 ] ) ) ?
					this.offsetParent :
					this.scrollParent,
				scrollIsRootNode = ( /(html|body)/i ).test( scroll[ 0 ].tagName );

		// This is another very weird special case that only happens for relative elements:
		// 1. If the css position is relative
		// 2. and the scroll parent is the document or similar to the offset parent
		// we have to refresh the relative offset during the scroll so there are no jumps
		if ( this.cssPosition === "relative" && !( this.scrollParent[ 0 ] !== this.document[ 0 ] &&
				this.scrollParent[ 0 ] !== this.offsetParent[ 0 ] ) ) {
			this.offset.relative = this._getRelativeOffset();
		}

		/*
		 * - Position constraining -
		 * Constrain the position to a mix of grid, containment.
		 */

		if ( this.originalPosition ) { //If we are not dragging yet, we won't check for options

			if ( this.containment ) {
				if ( event.pageX - this.offset.click.left < this.containment[ 0 ] ) {
					pageX = this.containment[ 0 ] + this.offset.click.left;
				}
				if ( event.pageY - this.offset.click.top < this.containment[ 1 ] ) {
					pageY = this.containment[ 1 ] + this.offset.click.top;
				}
				if ( event.pageX - this.offset.click.left > this.containment[ 2 ] ) {
					pageX = this.containment[ 2 ] + this.offset.click.left;
				}
				if ( event.pageY - this.offset.click.top > this.containment[ 3 ] ) {
					pageY = this.containment[ 3 ] + this.offset.click.top;
				}
			}

			if ( o.grid ) {
				top = this.originalPageY + Math.round( ( pageY - this.originalPageY ) /
					o.grid[ 1 ] ) * o.grid[ 1 ];
				pageY = this.containment ?
					( ( top - this.offset.click.top >= this.containment[ 1 ] &&
						top - this.offset.click.top <= this.containment[ 3 ] ) ?
							top :
							( ( top - this.offset.click.top >= this.containment[ 1 ] ) ?
								top - o.grid[ 1 ] : top + o.grid[ 1 ] ) ) :
								top;

				left = this.originalPageX + Math.round( ( pageX - this.originalPageX ) /
					o.grid[ 0 ] ) * o.grid[ 0 ];
				pageX = this.containment ?
					( ( left - this.offset.click.left >= this.containment[ 0 ] &&
						left - this.offset.click.left <= this.containment[ 2 ] ) ?
							left :
							( ( left - this.offset.click.left >= this.containment[ 0 ] ) ?
								left - o.grid[ 0 ] : left + o.grid[ 0 ] ) ) :
								left;
			}

		}

		return {
			top: (

				// The absolute mouse position
				pageY -

				// Click offset (relative to the element)
				this.offset.click.top -

				// Only for relative positioned nodes: Relative offset from element to offset parent
				this.offset.relative.top -

				// The offsetParent's offset without borders (offset + border)
				this.offset.parent.top +
				( ( this.cssPosition === "fixed" ?
					-this.scrollParent.scrollTop() :
					( scrollIsRootNode ? 0 : scroll.scrollTop() ) ) )
			),
			left: (

				// The absolute mouse position
				pageX -

				// Click offset (relative to the element)
				this.offset.click.left -

				// Only for relative positioned nodes: Relative offset from element to offset parent
				this.offset.relative.left -

				// The offsetParent's offset without borders (offset + border)
				this.offset.parent.left +
				( ( this.cssPosition === "fixed" ?
					-this.scrollParent.scrollLeft() :
					scrollIsRootNode ? 0 : scroll.scrollLeft() ) )
			)
		};

	},

	_rearrange: function( event, i, a, hardRefresh ) {

		a ? a[ 0 ].appendChild( this.placeholder[ 0 ] ) :
			i.item[ 0 ].parentNode.insertBefore( this.placeholder[ 0 ],
				( this.direction === "down" ? i.item[ 0 ] : i.item[ 0 ].nextSibling ) );

		//Various things done here to improve the performance:
		// 1. we create a setTimeout, that calls refreshPositions
		// 2. on the instance, we have a counter variable, that get's higher after every append
		// 3. on the local scope, we copy the counter variable, and check in the timeout,
		// if it's still the same
		// 4. this lets only the last addition to the timeout stack through
		this.counter = this.counter ? ++this.counter : 1;
		var counter = this.counter;

		this._delay( function() {
			if ( counter === this.counter ) {

				//Precompute after each DOM insertion, NOT on mousemove
				this.refreshPositions( !hardRefresh );
			}
		} );

	},

	_clear: function( event, noPropagation ) {

		this.reverting = false;

		// We delay all events that have to be triggered to after the point where the placeholder
		// has been removed and everything else normalized again
		var i,
			delayedTriggers = [];

		// We first have to update the dom position of the actual currentItem
		// Note: don't do it if the current item is already removed (by a user), or it gets
		// reappended (see #4088)
		if ( !this._noFinalSort && this.currentItem.parent().length ) {
			this.placeholder.before( this.currentItem );
		}
		this._noFinalSort = null;

		if ( this.helper[ 0 ] === this.currentItem[ 0 ] ) {
			for ( i in this._storedCSS ) {
				if ( this._storedCSS[ i ] === "auto" || this._storedCSS[ i ] === "static" ) {
					this._storedCSS[ i ] = "";
				}
			}
			this.currentItem.css( this._storedCSS );
			this._removeClass( this.currentItem, "ui-sortable-helper" );
		} else {
			this.currentItem.show();
		}

		if ( this.fromOutside && !noPropagation ) {
			delayedTriggers.push( function( event ) {
				this._trigger( "receive", event, this._uiHash( this.fromOutside ) );
			} );
		}
		if ( ( this.fromOutside ||
				this.domPosition.prev !==
				this.currentItem.prev().not( ".ui-sortable-helper" )[ 0 ] ||
				this.domPosition.parent !== this.currentItem.parent()[ 0 ] ) && !noPropagation ) {

			// Trigger update callback if the DOM position has changed
			delayedTriggers.push( function( event ) {
				this._trigger( "update", event, this._uiHash() );
			} );
		}

		// Check if the items Container has Changed and trigger appropriate
		// events.
		if ( this !== this.currentContainer ) {
			if ( !noPropagation ) {
				delayedTriggers.push( function( event ) {
					this._trigger( "remove", event, this._uiHash() );
				} );
				delayedTriggers.push( ( function( c ) {
					return function( event ) {
						c._trigger( "receive", event, this._uiHash( this ) );
					};
				} ).call( this, this.currentContainer ) );
				delayedTriggers.push( ( function( c ) {
					return function( event ) {
						c._trigger( "update", event, this._uiHash( this ) );
					};
				} ).call( this, this.currentContainer ) );
			}
		}

		//Post events to containers
		function delayEvent( type, instance, container ) {
			return function( event ) {
				container._trigger( type, event, instance._uiHash( instance ) );
			};
		}
		for ( i = this.containers.length - 1; i >= 0; i-- ) {
			if ( !noPropagation ) {
				delayedTriggers.push( delayEvent( "deactivate", this, this.containers[ i ] ) );
			}
			if ( this.containers[ i ].containerCache.over ) {
				delayedTriggers.push( delayEvent( "out", this, this.containers[ i ] ) );
				this.containers[ i ].containerCache.over = 0;
			}
		}

		//Do what was originally in plugins
		if ( this.storedCursor ) {
			this.document.find( "body" ).css( "cursor", this.storedCursor );
			this.storedStylesheet.remove();
		}
		if ( this._storedOpacity ) {
			this.helper.css( "opacity", this._storedOpacity );
		}
		if ( this._storedZIndex ) {
			this.helper.css( "zIndex", this._storedZIndex === "auto" ? "" : this._storedZIndex );
		}

		this.dragging = false;

		if ( !noPropagation ) {
			this._trigger( "beforeStop", event, this._uiHash() );
		}

		//$(this.placeholder[0]).remove(); would have been the jQuery way - unfortunately,
		// it unbinds ALL events from the original node!
		this.placeholder[ 0 ].parentNode.removeChild( this.placeholder[ 0 ] );

		if ( !this.cancelHelperRemoval ) {
			if ( this.helper[ 0 ] !== this.currentItem[ 0 ] ) {
				this.helper.remove();
			}
			this.helper = null;
		}

		if ( !noPropagation ) {
			for ( i = 0; i < delayedTriggers.length; i++ ) {

				// Trigger all delayed events
				delayedTriggers[ i ].call( this, event );
			}
			this._trigger( "stop", event, this._uiHash() );
		}

		this.fromOutside = false;
		return !this.cancelHelperRemoval;

	},

	_trigger: function() {
		if ( $.Widget.prototype._trigger.apply( this, arguments ) === false ) {
			this.cancel();
		}
	},

	_uiHash: function( _inst ) {
		var inst = _inst || this;
		return {
			helper: inst.helper,
			placeholder: inst.placeholder || $( [] ),
			position: inst.position,
			originalPosition: inst.originalPosition,
			offset: inst.positionAbs,
			item: inst.currentItem,
			sender: _inst ? _inst.element : null
		};
	}

} );


/*!
 * jQuery UI Spinner 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: Spinner
//>>group: Widgets
//>>description: Displays buttons to easily input numbers via the keyboard or mouse.
//>>docs: http://api.jqueryui.com/spinner/
//>>demos: http://jqueryui.com/spinner/
//>>css.structure: ../../themes/base/core.css
//>>css.structure: ../../themes/base/spinner.css
//>>css.theme: ../../themes/base/theme.css



function spinnerModifer( fn ) {
	return function() {
		var previous = this.element.val();
		fn.apply( this, arguments );
		this._refresh();
		if ( previous !== this.element.val() ) {
			this._trigger( "change" );
		}
	};
}

$.widget( "ui.spinner", {
	version: "1.12.0",
	defaultElement: "<input>",
	widgetEventPrefix: "spin",
	options: {
		classes: {
			"ui-spinner": "ui-corner-all",
			"ui-spinner-down": "ui-corner-br",
			"ui-spinner-up": "ui-corner-tr"
		},
		culture: null,
		icons: {
			down: "ui-icon-triangle-1-s",
			up: "ui-icon-triangle-1-n"
		},
		incremental: true,
		max: null,
		min: null,
		numberFormat: null,
		page: 10,
		step: 1,

		change: null,
		spin: null,
		start: null,
		stop: null
	},

	_create: function() {

		// handle string values that need to be parsed
		this._setOption( "max", this.options.max );
		this._setOption( "min", this.options.min );
		this._setOption( "step", this.options.step );

		// Only format if there is a value, prevents the field from being marked
		// as invalid in Firefox, see #9573.
		if ( this.value() !== "" ) {

			// Format the value, but don't constrain.
			this._value( this.element.val(), true );
		}

		this._draw();
		this._on( this._events );
		this._refresh();

		// Turning off autocomplete prevents the browser from remembering the
		// value when navigating through history, so we re-enable autocomplete
		// if the page is unloaded before the widget is destroyed. #7790
		this._on( this.window, {
			beforeunload: function() {
				this.element.removeAttr( "autocomplete" );
			}
		} );
	},

	_getCreateOptions: function() {
		var options = this._super();
		var element = this.element;

		$.each( [ "min", "max", "step" ], function( i, option ) {
			var value = element.attr( option );
			if ( value != null && value.length ) {
				options[ option ] = value;
			}
		} );

		return options;
	},

	_events: {
		keydown: function( event ) {
			if ( this._start( event ) && this._keydown( event ) ) {
				event.preventDefault();
			}
		},
		keyup: "_stop",
		focus: function() {
			this.previous = this.element.val();
		},
		blur: function( event ) {
			if ( this.cancelBlur ) {
				delete this.cancelBlur;
				return;
			}

			this._stop();
			this._refresh();
			if ( this.previous !== this.element.val() ) {
				this._trigger( "change", event );
			}
		},
		mousewheel: function( event, delta ) {
			if ( !delta ) {
				return;
			}
			if ( !this.spinning && !this._start( event ) ) {
				return false;
			}

			this._spin( ( delta > 0 ? 1 : -1 ) * this.options.step, event );
			clearTimeout( this.mousewheelTimer );
			this.mousewheelTimer = this._delay( function() {
				if ( this.spinning ) {
					this._stop( event );
				}
			}, 100 );
			event.preventDefault();
		},
		"mousedown .ui-spinner-button": function( event ) {
			var previous;

			// We never want the buttons to have focus; whenever the user is
			// interacting with the spinner, the focus should be on the input.
			// If the input is focused then this.previous is properly set from
			// when the input first received focus. If the input is not focused
			// then we need to set this.previous based on the value before spinning.
			previous = this.element[ 0 ] === $.ui.safeActiveElement( this.document[ 0 ] ) ?
				this.previous : this.element.val();
			function checkFocus() {
				var isActive = this.element[ 0 ] === $.ui.safeActiveElement( this.document[ 0 ] );
				if ( !isActive ) {
					this.element.trigger( "focus" );
					this.previous = previous;

					// support: IE
					// IE sets focus asynchronously, so we need to check if focus
					// moved off of the input because the user clicked on the button.
					this._delay( function() {
						this.previous = previous;
					} );
				}
			}

			// Ensure focus is on (or stays on) the text field
			event.preventDefault();
			checkFocus.call( this );

			// Support: IE
			// IE doesn't prevent moving focus even with event.preventDefault()
			// so we set a flag to know when we should ignore the blur event
			// and check (again) if focus moved off of the input.
			this.cancelBlur = true;
			this._delay( function() {
				delete this.cancelBlur;
				checkFocus.call( this );
			} );

			if ( this._start( event ) === false ) {
				return;
			}

			this._repeat( null, $( event.currentTarget )
				.hasClass( "ui-spinner-up" ) ? 1 : -1, event );
		},
		"mouseup .ui-spinner-button": "_stop",
		"mouseenter .ui-spinner-button": function( event ) {

			// button will add ui-state-active if mouse was down while mouseleave and kept down
			if ( !$( event.currentTarget ).hasClass( "ui-state-active" ) ) {
				return;
			}

			if ( this._start( event ) === false ) {
				return false;
			}
			this._repeat( null, $( event.currentTarget )
				.hasClass( "ui-spinner-up" ) ? 1 : -1, event );
		},

		// TODO: do we really want to consider this a stop?
		// shouldn't we just stop the repeater and wait until mouseup before
		// we trigger the stop event?
		"mouseleave .ui-spinner-button": "_stop"
	},

	// Support mobile enhanced option and make backcompat more sane
	_enhance: function() {
		this.uiSpinner = this.element
			.attr( "autocomplete", "off" )
			.wrap( "<span>" )
			.parent()

				// Add buttons
				.append(
					"<a></a><a></a>"
				);
	},

	_draw: function() {
		this._enhance();

		this._addClass( this.uiSpinner, "ui-spinner", "ui-widget ui-widget-content" );
		this._addClass( "ui-spinner-input" );

		this.element.attr( "role", "spinbutton" );

		// Button bindings
		this.buttons = this.uiSpinner.children( "a" )
			.attr( "tabIndex", -1 )
			.attr( "aria-hidden", true )
			.button( {
				classes: {
					"ui-button": ""
				}
			} );

		// TODO: Right now button does not support classes this is already updated in button PR
		this._removeClass( this.buttons, "ui-corner-all" );

		this._addClass( this.buttons.first(), "ui-spinner-button ui-spinner-up" );
		this._addClass( this.buttons.last(), "ui-spinner-button ui-spinner-down" );
		this.buttons.first().button( {
			"icon": this.options.icons.up,
			"showLabel": false
		} );
		this.buttons.last().button( {
			"icon": this.options.icons.down,
			"showLabel": false
		} );

		// IE 6 doesn't understand height: 50% for the buttons
		// unless the wrapper has an explicit height
		if ( this.buttons.height() > Math.ceil( this.uiSpinner.height() * 0.5 ) &&
				this.uiSpinner.height() > 0 ) {
			this.uiSpinner.height( this.uiSpinner.height() );
		}
	},

	_keydown: function( event ) {
		var options = this.options,
			keyCode = $.ui.keyCode;

		switch ( event.keyCode ) {
		case keyCode.UP:
			this._repeat( null, 1, event );
			return true;
		case keyCode.DOWN:
			this._repeat( null, -1, event );
			return true;
		case keyCode.PAGE_UP:
			this._repeat( null, options.page, event );
			return true;
		case keyCode.PAGE_DOWN:
			this._repeat( null, -options.page, event );
			return true;
		}

		return false;
	},

	_start: function( event ) {
		if ( !this.spinning && this._trigger( "start", event ) === false ) {
			return false;
		}

		if ( !this.counter ) {
			this.counter = 1;
		}
		this.spinning = true;
		return true;
	},

	_repeat: function( i, steps, event ) {
		i = i || 500;

		clearTimeout( this.timer );
		this.timer = this._delay( function() {
			this._repeat( 40, steps, event );
		}, i );

		this._spin( steps * this.options.step, event );
	},

	_spin: function( step, event ) {
		var value = this.value() || 0;

		if ( !this.counter ) {
			this.counter = 1;
		}

		value = this._adjustValue( value + step * this._increment( this.counter ) );

		if ( !this.spinning || this._trigger( "spin", event, { value: value } ) !== false ) {
			this._value( value );
			this.counter++;
		}
	},

	_increment: function( i ) {
		var incremental = this.options.incremental;

		if ( incremental ) {
			return $.isFunction( incremental ) ?
				incremental( i ) :
				Math.floor( i * i * i / 50000 - i * i / 500 + 17 * i / 200 + 1 );
		}

		return 1;
	},

	_precision: function() {
		var precision = this._precisionOf( this.options.step );
		if ( this.options.min !== null ) {
			precision = Math.max( precision, this._precisionOf( this.options.min ) );
		}
		return precision;
	},

	_precisionOf: function( num ) {
		var str = num.toString(),
			decimal = str.indexOf( "." );
		return decimal === -1 ? 0 : str.length - decimal - 1;
	},

	_adjustValue: function( value ) {
		var base, aboveMin,
			options = this.options;

		// Make sure we're at a valid step
		// - find out where we are relative to the base (min or 0)
		base = options.min !== null ? options.min : 0;
		aboveMin = value - base;

		// - round to the nearest step
		aboveMin = Math.round( aboveMin / options.step ) * options.step;

		// - rounding is based on 0, so adjust back to our base
		value = base + aboveMin;

		// Fix precision from bad JS floating point math
		value = parseFloat( value.toFixed( this._precision() ) );

		// Clamp the value
		if ( options.max !== null && value > options.max ) {
			return options.max;
		}
		if ( options.min !== null && value < options.min ) {
			return options.min;
		}

		return value;
	},

	_stop: function( event ) {
		if ( !this.spinning ) {
			return;
		}

		clearTimeout( this.timer );
		clearTimeout( this.mousewheelTimer );
		this.counter = 0;
		this.spinning = false;
		this._trigger( "stop", event );
	},

	_setOption: function( key, value ) {
		var prevValue, first, last;

		if ( key === "culture" || key === "numberFormat" ) {
			prevValue = this._parse( this.element.val() );
			this.options[ key ] = value;
			this.element.val( this._format( prevValue ) );
			return;
		}

		if ( key === "max" || key === "min" || key === "step" ) {
			if ( typeof value === "string" ) {
				value = this._parse( value );
			}
		}
		if ( key === "icons" ) {
			first = this.buttons.first().find( ".ui-icon" );
			this._removeClass( first, null, this.options.icons.up );
			this._addClass( first, null, value.up );
			last = this.buttons.last().find( ".ui-icon" );
			this._removeClass( last, null, this.options.icons.down );
			this._addClass( last, null, value.down );
		}

		this._super( key, value );
	},

	_setOptionDisabled: function( value ) {
		this._super( value );

		this._toggleClass( this.uiSpinner, null, "ui-state-disabled", !!value );
		this.element.prop( "disabled", !!value );
		this.buttons.button( value ? "disable" : "enable" );
	},

	_setOptions: spinnerModifer( function( options ) {
		this._super( options );
	} ),

	_parse: function( val ) {
		if ( typeof val === "string" && val !== "" ) {
			val = window.Globalize && this.options.numberFormat ?
				Globalize.parseFloat( val, 10, this.options.culture ) : +val;
		}
		return val === "" || isNaN( val ) ? null : val;
	},

	_format: function( value ) {
		if ( value === "" ) {
			return "";
		}
		return window.Globalize && this.options.numberFormat ?
			Globalize.format( value, this.options.numberFormat, this.options.culture ) :
			value;
	},

	_refresh: function() {
		this.element.attr( {
			"aria-valuemin": this.options.min,
			"aria-valuemax": this.options.max,

			// TODO: what should we do with values that can't be parsed?
			"aria-valuenow": this._parse( this.element.val() )
		} );
	},

	isValid: function() {
		var value = this.value();

		// Null is invalid
		if ( value === null ) {
			return false;
		}

		// If value gets adjusted, it's invalid
		return value === this._adjustValue( value );
	},

	// Update the value without triggering change
	_value: function( value, allowAny ) {
		var parsed;
		if ( value !== "" ) {
			parsed = this._parse( value );
			if ( parsed !== null ) {
				if ( !allowAny ) {
					parsed = this._adjustValue( parsed );
				}
				value = this._format( parsed );
			}
		}
		this.element.val( value );
		this._refresh();
	},

	_destroy: function() {
		this.element
			.prop( "disabled", false )
			.removeAttr( "autocomplete role aria-valuemin aria-valuemax aria-valuenow" );

		this.uiSpinner.replaceWith( this.element );
	},

	stepUp: spinnerModifer( function( steps ) {
		this._stepUp( steps );
	} ),
	_stepUp: function( steps ) {
		if ( this._start() ) {
			this._spin( ( steps || 1 ) * this.options.step );
			this._stop();
		}
	},

	stepDown: spinnerModifer( function( steps ) {
		this._stepDown( steps );
	} ),
	_stepDown: function( steps ) {
		if ( this._start() ) {
			this._spin( ( steps || 1 ) * -this.options.step );
			this._stop();
		}
	},

	pageUp: spinnerModifer( function( pages ) {
		this._stepUp( ( pages || 1 ) * this.options.page );
	} ),

	pageDown: spinnerModifer( function( pages ) {
		this._stepDown( ( pages || 1 ) * this.options.page );
	} ),

	value: function( newVal ) {
		if ( !arguments.length ) {
			return this._parse( this.element.val() );
		}
		spinnerModifer( this._value ).call( this, newVal );
	},

	widget: function() {
		return this.uiSpinner;
	}
} );

// DEPRECATED
// TODO: switch return back to widget declaration at top of file when this is removed
if ( $.uiBackCompat !== false ) {

	// Backcompat for spinner html extension points
	$.widget( "ui.spinner", $.ui.spinner, {
		_enhance: function() {
			this.uiSpinner = this.element
				.attr( "autocomplete", "off" )
				.wrap( this._uiSpinnerHtml() )
				.parent()

					// Add buttons
					.append( this._buttonHtml() );
		},
		_uiSpinnerHtml: function() {
			return "<span>";
		},

		_buttonHtml: function() {
			return "<a></a><a></a>";
		}
	} );
}

var widgetsSpinner = $.ui.spinner;


/*!
 * jQuery UI Tabs 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: Tabs
//>>group: Widgets
//>>description: Transforms a set of container elements into a tab structure.
//>>docs: http://api.jqueryui.com/tabs/
//>>demos: http://jqueryui.com/tabs/
//>>css.structure: ../../themes/base/core.css
//>>css.structure: ../../themes/base/tabs.css
//>>css.theme: ../../themes/base/theme.css



$.widget( "ui.tabs", {
	version: "1.12.0",
	delay: 300,
	options: {
		active: null,
		classes: {
			"ui-tabs": "ui-corner-all",
			"ui-tabs-nav": "ui-corner-all",
			"ui-tabs-panel": "ui-corner-bottom",
			"ui-tabs-tab": "ui-corner-top"
		},
		collapsible: false,
		event: "click",
		heightStyle: "content",
		hide: null,
		show: null,

		// Callbacks
		activate: null,
		beforeActivate: null,
		beforeLoad: null,
		load: null
	},

	_isLocal: ( function() {
		var rhash = /#.*$/;

		return function( anchor ) {
			var anchorUrl, locationUrl;

			anchorUrl = anchor.href.replace( rhash, "" );
			locationUrl = location.href.replace( rhash, "" );

			// Decoding may throw an error if the URL isn't UTF-8 (#9518)
			try {
				anchorUrl = decodeURIComponent( anchorUrl );
			} catch ( error ) {}
			try {
				locationUrl = decodeURIComponent( locationUrl );
			} catch ( error ) {}

			return anchor.hash.length > 1 && anchorUrl === locationUrl;
		};
	} )(),

	_create: function() {
		var that = this,
			options = this.options;

		this.running = false;

		this._addClass( "ui-tabs", "ui-widget ui-widget-content" );
		this._toggleClass( "ui-tabs-collapsible", null, options.collapsible );

		this._processTabs();
		options.active = this._initialActive();

		// Take disabling tabs via class attribute from HTML
		// into account and update option properly.
		if ( $.isArray( options.disabled ) ) {
			options.disabled = $.unique( options.disabled.concat(
				$.map( this.tabs.filter( ".ui-state-disabled" ), function( li ) {
					return that.tabs.index( li );
				} )
			) ).sort();
		}

		// Check for length avoids error when initializing empty list
		if ( this.options.active !== false && this.anchors.length ) {
			this.active = this._findActive( options.active );
		} else {
			this.active = $();
		}

		this._refresh();

		if ( this.active.length ) {
			this.load( options.active );
		}
	},

	_initialActive: function() {
		var active = this.options.active,
			collapsible = this.options.collapsible,
			locationHash = location.hash.substring( 1 );

		if ( active === null ) {

			// check the fragment identifier in the URL
			if ( locationHash ) {
				this.tabs.each( function( i, tab ) {
					if ( $( tab ).attr( "aria-controls" ) === locationHash ) {
						active = i;
						return false;
					}
				} );
			}

			// Check for a tab marked active via a class
			if ( active === null ) {
				active = this.tabs.index( this.tabs.filter( ".ui-tabs-active" ) );
			}

			// No active tab, set to false
			if ( active === null || active === -1 ) {
				active = this.tabs.length ? 0 : false;
			}
		}

		// Handle numbers: negative, out of range
		if ( active !== false ) {
			active = this.tabs.index( this.tabs.eq( active ) );
			if ( active === -1 ) {
				active = collapsible ? false : 0;
			}
		}

		// Don't allow collapsible: false and active: false
		if ( !collapsible && active === false && this.anchors.length ) {
			active = 0;
		}

		return active;
	},

	_getCreateEventData: function() {
		return {
			tab: this.active,
			panel: !this.active.length ? $() : this._getPanelForTab( this.active )
		};
	},

	_tabKeydown: function( event ) {
		var focusedTab = $( $.ui.safeActiveElement( this.document[ 0 ] ) ).closest( "li" ),
			selectedIndex = this.tabs.index( focusedTab ),
			goingForward = true;

		if ( this._handlePageNav( event ) ) {
			return;
		}

		switch ( event.keyCode ) {
		case $.ui.keyCode.RIGHT:
		case $.ui.keyCode.DOWN:
			selectedIndex++;
			break;
		case $.ui.keyCode.UP:
		case $.ui.keyCode.LEFT:
			goingForward = false;
			selectedIndex--;
			break;
		case $.ui.keyCode.END:
			selectedIndex = this.anchors.length - 1;
			break;
		case $.ui.keyCode.HOME:
			selectedIndex = 0;
			break;
		case $.ui.keyCode.SPACE:

			// Activate only, no collapsing
			event.preventDefault();
			clearTimeout( this.activating );
			this._activate( selectedIndex );
			return;
		case $.ui.keyCode.ENTER:

			// Toggle (cancel delayed activation, allow collapsing)
			event.preventDefault();
			clearTimeout( this.activating );

			// Determine if we should collapse or activate
			this._activate( selectedIndex === this.options.active ? false : selectedIndex );
			return;
		default:
			return;
		}

		// Focus the appropriate tab, based on which key was pressed
		event.preventDefault();
		clearTimeout( this.activating );
		selectedIndex = this._focusNextTab( selectedIndex, goingForward );

		// Navigating with control/command key will prevent automatic activation
		if ( !event.ctrlKey && !event.metaKey ) {

			// Update aria-selected immediately so that AT think the tab is already selected.
			// Otherwise AT may confuse the user by stating that they need to activate the tab,
			// but the tab will already be activated by the time the announcement finishes.
			focusedTab.attr( "aria-selected", "false" );
			this.tabs.eq( selectedIndex ).attr( "aria-selected", "true" );

			this.activating = this._delay( function() {
				this.option( "active", selectedIndex );
			}, this.delay );
		}
	},

	_panelKeydown: function( event ) {
		if ( this._handlePageNav( event ) ) {
			return;
		}

		// Ctrl+up moves focus to the current tab
		if ( event.ctrlKey && event.keyCode === $.ui.keyCode.UP ) {
			event.preventDefault();
			this.active.trigger( "focus" );
		}
	},

	// Alt+page up/down moves focus to the previous/next tab (and activates)
	_handlePageNav: function( event ) {
		if ( event.altKey && event.keyCode === $.ui.keyCode.PAGE_UP ) {
			this._activate( this._focusNextTab( this.options.active - 1, false ) );
			return true;
		}
		if ( event.altKey && event.keyCode === $.ui.keyCode.PAGE_DOWN ) {
			this._activate( this._focusNextTab( this.options.active + 1, true ) );
			return true;
		}
	},

	_findNextTab: function( index, goingForward ) {
		var lastTabIndex = this.tabs.length - 1;

		function constrain() {
			if ( index > lastTabIndex ) {
				index = 0;
			}
			if ( index < 0 ) {
				index = lastTabIndex;
			}
			return index;
		}

		while ( $.inArray( constrain(), this.options.disabled ) !== -1 ) {
			index = goingForward ? index + 1 : index - 1;
		}

		return index;
	},

	_focusNextTab: function( index, goingForward ) {
		index = this._findNextTab( index, goingForward );
		this.tabs.eq( index ).trigger( "focus" );
		return index;
	},

	_setOption: function( key, value ) {
		if ( key === "active" ) {

			// _activate() will handle invalid values and update this.options
			this._activate( value );
			return;
		}

		this._super( key, value );

		if ( key === "collapsible" ) {
			this._toggleClass( "ui-tabs-collapsible", null, value );

			// Setting collapsible: false while collapsed; open first panel
			if ( !value && this.options.active === false ) {
				this._activate( 0 );
			}
		}

		if ( key === "event" ) {
			this._setupEvents( value );
		}

		if ( key === "heightStyle" ) {
			this._setupHeightStyle( value );
		}
	},

	_sanitizeSelector: function( hash ) {
		return hash ? hash.replace( /[!"$%&'()*+,.\/:;<=>?@\[\]\^`{|}~]/g, "\\$&" ) : "";
	},

	refresh: function() {
		var options = this.options,
			lis = this.tablist.children( ":has(a[href])" );

		// Get disabled tabs from class attribute from HTML
		// this will get converted to a boolean if needed in _refresh()
		options.disabled = $.map( lis.filter( ".ui-state-disabled" ), function( tab ) {
			return lis.index( tab );
		} );

		this._processTabs();

		// Was collapsed or no tabs
		if ( options.active === false || !this.anchors.length ) {
			options.active = false;
			this.active = $();

		// was active, but active tab is gone
		} else if ( this.active.length && !$.contains( this.tablist[ 0 ], this.active[ 0 ] ) ) {

			// all remaining tabs are disabled
			if ( this.tabs.length === options.disabled.length ) {
				options.active = false;
				this.active = $();

			// activate previous tab
			} else {
				this._activate( this._findNextTab( Math.max( 0, options.active - 1 ), false ) );
			}

		// was active, active tab still exists
		} else {

			// make sure active index is correct
			options.active = this.tabs.index( this.active );
		}

		this._refresh();
	},

	_refresh: function() {
		this._setOptionDisabled( this.options.disabled );
		this._setupEvents( this.options.event );
		this._setupHeightStyle( this.options.heightStyle );

		this.tabs.not( this.active ).attr( {
			"aria-selected": "false",
			"aria-expanded": "false",
			tabIndex: -1
		} );
		this.panels.not( this._getPanelForTab( this.active ) )
			.hide()
			.attr( {
				"aria-hidden": "true"
			} );

		// Make sure one tab is in the tab order
		if ( !this.active.length ) {
			this.tabs.eq( 0 ).attr( "tabIndex", 0 );
		} else {
			this.active
				.attr( {
					"aria-selected": "true",
					"aria-expanded": "true",
					tabIndex: 0
				} );
			this._addClass( this.active, "ui-tabs-active", "ui-state-active" );
			this._getPanelForTab( this.active )
				.show()
				.attr( {
					"aria-hidden": "false"
				} );
		}
	},

	_processTabs: function() {
		var that = this,
			prevTabs = this.tabs,
			prevAnchors = this.anchors,
			prevPanels = this.panels;

		this.tablist = this._getList().attr( "role", "tablist" );
		this._addClass( this.tablist, "ui-tabs-nav",
			"ui-helper-reset ui-helper-clearfix ui-widget-header" );

		// Prevent users from focusing disabled tabs via click
		this.tablist
			.on( "mousedown" + this.eventNamespace, "> li", function( event ) {
				if ( $( this ).is( ".ui-state-disabled" ) ) {
					event.preventDefault();
				}
			} )

			// Support: IE <9
			// Preventing the default action in mousedown doesn't prevent IE
			// from focusing the element, so if the anchor gets focused, blur.
			// We don't have to worry about focusing the previously focused
			// element since clicking on a non-focusable element should focus
			// the body anyway.
			.on( "focus" + this.eventNamespace, ".ui-tabs-anchor", function() {
				if ( $( this ).closest( "li" ).is( ".ui-state-disabled" ) ) {
					this.blur();
				}
			} );

		this.tabs = this.tablist.find( "> li:has(a[href])" )
			.attr( {
				role: "tab",
				tabIndex: -1
			} );
		this._addClass( this.tabs, "ui-tabs-tab", "ui-state-default" );

		this.anchors = this.tabs.map( function() {
			return $( "a", this )[ 0 ];
		} )
			.attr( {
				role: "presentation",
				tabIndex: -1
			} );
		this._addClass( this.anchors, "ui-tabs-anchor" );

		this.panels = $();

		this.anchors.each( function( i, anchor ) {
			var selector, panel, panelId,
				anchorId = $( anchor ).uniqueId().attr( "id" ),
				tab = $( anchor ).closest( "li" ),
				originalAriaControls = tab.attr( "aria-controls" );

			// Inline tab
			if ( that._isLocal( anchor ) ) {
				selector = anchor.hash;
				panelId = selector.substring( 1 );
				panel = that.element.find( that._sanitizeSelector( selector ) );

			// remote tab
			} else {

				// If the tab doesn't already have aria-controls,
				// generate an id by using a throw-away element
				panelId = tab.attr( "aria-controls" ) || $( {} ).uniqueId()[ 0 ].id;
				selector = "#" + panelId;
				panel = that.element.find( selector );
				if ( !panel.length ) {
					panel = that._createPanel( panelId );
					panel.insertAfter( that.panels[ i - 1 ] || that.tablist );
				}
				panel.attr( "aria-live", "polite" );
			}

			if ( panel.length ) {
				that.panels = that.panels.add( panel );
			}
			if ( originalAriaControls ) {
				tab.data( "ui-tabs-aria-controls", originalAriaControls );
			}
			tab.attr( {
				"aria-controls": panelId,
				"aria-labelledby": anchorId
			} );
			panel.attr( "aria-labelledby", anchorId );
		} );

		this.panels.attr( "role", "tabpanel" );
		this._addClass( this.panels, "ui-tabs-panel", "ui-widget-content" );

		// Avoid memory leaks (#10056)
		if ( prevTabs ) {
			this._off( prevTabs.not( this.tabs ) );
			this._off( prevAnchors.not( this.anchors ) );
			this._off( prevPanels.not( this.panels ) );
		}
	},

	// Allow overriding how to find the list for rare usage scenarios (#7715)
	_getList: function() {
		return this.tablist || this.element.find( "ol, ul" ).eq( 0 );
	},

	_createPanel: function( id ) {
		return $( "<div>" )
			.attr( "id", id )
			.data( "ui-tabs-destroy", true );
	},

	_setOptionDisabled: function( disabled ) {
		var currentItem, li, i;

		if ( $.isArray( disabled ) ) {
			if ( !disabled.length ) {
				disabled = false;
			} else if ( disabled.length === this.anchors.length ) {
				disabled = true;
			}
		}

		// Disable tabs
		for ( i = 0; ( li = this.tabs[ i ] ); i++ ) {
			currentItem = $( li );
			if ( disabled === true || $.inArray( i, disabled ) !== -1 ) {
				currentItem.attr( "aria-disabled", "true" );
				this._addClass( currentItem, null, "ui-state-disabled" );
			} else {
				currentItem.removeAttr( "aria-disabled" );
				this._removeClass( currentItem, null, "ui-state-disabled" );
			}
		}

		this.options.disabled = disabled;

		this._toggleClass( this.widget(), this.widgetFullName + "-disabled", null,
			disabled === true );
	},

	_setupEvents: function( event ) {
		var events = {};
		if ( event ) {
			$.each( event.split( " " ), function( index, eventName ) {
				events[ eventName ] = "_eventHandler";
			} );
		}

		this._off( this.anchors.add( this.tabs ).add( this.panels ) );

		// Always prevent the default action, even when disabled
		this._on( true, this.anchors, {
			click: function( event ) {
				event.preventDefault();
			}
		} );
		this._on( this.anchors, events );
		this._on( this.tabs, { keydown: "_tabKeydown" } );
		this._on( this.panels, { keydown: "_panelKeydown" } );

		this._focusable( this.tabs );
		this._hoverable( this.tabs );
	},

	_setupHeightStyle: function( heightStyle ) {
		var maxHeight,
			parent = this.element.parent();

		if ( heightStyle === "fill" ) {
			maxHeight = parent.height();
			maxHeight -= this.element.outerHeight() - this.element.height();

			this.element.siblings( ":visible" ).each( function() {
				var elem = $( this ),
					position = elem.css( "position" );

				if ( position === "absolute" || position === "fixed" ) {
					return;
				}
				maxHeight -= elem.outerHeight( true );
			} );

			this.element.children().not( this.panels ).each( function() {
				maxHeight -= $( this ).outerHeight( true );
			} );

			this.panels.each( function() {
				$( this ).height( Math.max( 0, maxHeight -
					$( this ).innerHeight() + $( this ).height() ) );
			} )
				.css( "overflow", "auto" );
		} else if ( heightStyle === "auto" ) {
			maxHeight = 0;
			this.panels.each( function() {
				maxHeight = Math.max( maxHeight, $( this ).height( "" ).height() );
			} ).height( maxHeight );
		}
	},

	_eventHandler: function( event ) {
		var options = this.options,
			active = this.active,
			anchor = $( event.currentTarget ),
			tab = anchor.closest( "li" ),
			clickedIsActive = tab[ 0 ] === active[ 0 ],
			collapsing = clickedIsActive && options.collapsible,
			toShow = collapsing ? $() : this._getPanelForTab( tab ),
			toHide = !active.length ? $() : this._getPanelForTab( active ),
			eventData = {
				oldTab: active,
				oldPanel: toHide,
				newTab: collapsing ? $() : tab,
				newPanel: toShow
			};

		event.preventDefault();

		if ( tab.hasClass( "ui-state-disabled" ) ||

				// tab is already loading
				tab.hasClass( "ui-tabs-loading" ) ||

				// can't switch durning an animation
				this.running ||

				// click on active header, but not collapsible
				( clickedIsActive && !options.collapsible ) ||

				// allow canceling activation
				( this._trigger( "beforeActivate", event, eventData ) === false ) ) {
			return;
		}

		options.active = collapsing ? false : this.tabs.index( tab );

		this.active = clickedIsActive ? $() : tab;
		if ( this.xhr ) {
			this.xhr.abort();
		}

		if ( !toHide.length && !toShow.length ) {
			$.error( "jQuery UI Tabs: Mismatching fragment identifier." );
		}

		if ( toShow.length ) {
			this.load( this.tabs.index( tab ), event );
		}
		this._toggle( event, eventData );
	},

	// Handles show/hide for selecting tabs
	_toggle: function( event, eventData ) {
		var that = this,
			toShow = eventData.newPanel,
			toHide = eventData.oldPanel;

		this.running = true;

		function complete() {
			that.running = false;
			that._trigger( "activate", event, eventData );
		}

		function show() {
			that._addClass( eventData.newTab.closest( "li" ), "ui-tabs-active", "ui-state-active" );

			if ( toShow.length && that.options.show ) {
				that._show( toShow, that.options.show, complete );
			} else {
				toShow.show();
				complete();
			}
		}

		// Start out by hiding, then showing, then completing
		if ( toHide.length && this.options.hide ) {
			this._hide( toHide, this.options.hide, function() {
				that._removeClass( eventData.oldTab.closest( "li" ),
					"ui-tabs-active", "ui-state-active" );
				show();
			} );
		} else {
			this._removeClass( eventData.oldTab.closest( "li" ),
				"ui-tabs-active", "ui-state-active" );
			toHide.hide();
			show();
		}

		toHide.attr( "aria-hidden", "true" );
		eventData.oldTab.attr( {
			"aria-selected": "false",
			"aria-expanded": "false"
		} );

		// If we're switching tabs, remove the old tab from the tab order.
		// If we're opening from collapsed state, remove the previous tab from the tab order.
		// If we're collapsing, then keep the collapsing tab in the tab order.
		if ( toShow.length && toHide.length ) {
			eventData.oldTab.attr( "tabIndex", -1 );
		} else if ( toShow.length ) {
			this.tabs.filter( function() {
				return $( this ).attr( "tabIndex" ) === 0;
			} )
				.attr( "tabIndex", -1 );
		}

		toShow.attr( "aria-hidden", "false" );
		eventData.newTab.attr( {
			"aria-selected": "true",
			"aria-expanded": "true",
			tabIndex: 0
		} );
	},

	_activate: function( index ) {
		var anchor,
			active = this._findActive( index );

		// Trying to activate the already active panel
		if ( active[ 0 ] === this.active[ 0 ] ) {
			return;
		}

		// Trying to collapse, simulate a click on the current active header
		if ( !active.length ) {
			active = this.active;
		}

		anchor = active.find( ".ui-tabs-anchor" )[ 0 ];
		this._eventHandler( {
			target: anchor,
			currentTarget: anchor,
			preventDefault: $.noop
		} );
	},

	_findActive: function( index ) {
		return index === false ? $() : this.tabs.eq( index );
	},

	_getIndex: function( index ) {

		// meta-function to give users option to provide a href string instead of a numerical index.
		if ( typeof index === "string" ) {
			index = this.anchors.index( this.anchors.filter( "[href$='" +
				$.ui.escapeSelector( index ) + "']" ) );
		}

		return index;
	},

	_destroy: function() {
		if ( this.xhr ) {
			this.xhr.abort();
		}

		this.tablist
			.removeAttr( "role" )
			.off( this.eventNamespace );

		this.anchors
			.removeAttr( "role tabIndex" )
			.removeUniqueId();

		this.tabs.add( this.panels ).each( function() {
			if ( $.data( this, "ui-tabs-destroy" ) ) {
				$( this ).remove();
			} else {
				$( this ).removeAttr( "role tabIndex " +
					"aria-live aria-busy aria-selected aria-labelledby aria-hidden aria-expanded" );
			}
		} );

		this.tabs.each( function() {
			var li = $( this ),
				prev = li.data( "ui-tabs-aria-controls" );
			if ( prev ) {
				li
					.attr( "aria-controls", prev )
					.removeData( "ui-tabs-aria-controls" );
			} else {
				li.removeAttr( "aria-controls" );
			}
		} );

		this.panels.show();

		if ( this.options.heightStyle !== "content" ) {
			this.panels.css( "height", "" );
		}
	},

	enable: function( index ) {
		var disabled = this.options.disabled;
		if ( disabled === false ) {
			return;
		}

		if ( index === undefined ) {
			disabled = false;
		} else {
			index = this._getIndex( index );
			if ( $.isArray( disabled ) ) {
				disabled = $.map( disabled, function( num ) {
					return num !== index ? num : null;
				} );
			} else {
				disabled = $.map( this.tabs, function( li, num ) {
					return num !== index ? num : null;
				} );
			}
		}
		this._setOptionDisabled( disabled );
	},

	disable: function( index ) {
		var disabled = this.options.disabled;
		if ( disabled === true ) {
			return;
		}

		if ( index === undefined ) {
			disabled = true;
		} else {
			index = this._getIndex( index );
			if ( $.inArray( index, disabled ) !== -1 ) {
				return;
			}
			if ( $.isArray( disabled ) ) {
				disabled = $.merge( [ index ], disabled ).sort();
			} else {
				disabled = [ index ];
			}
		}
		this._setOptionDisabled( disabled );
	},

	load: function( index, event ) {
		index = this._getIndex( index );
		var that = this,
			tab = this.tabs.eq( index ),
			anchor = tab.find( ".ui-tabs-anchor" ),
			panel = this._getPanelForTab( tab ),
			eventData = {
				tab: tab,
				panel: panel
			},
			complete = function( jqXHR, status ) {
				if ( status === "abort" ) {
					that.panels.stop( false, true );
				}

				that._removeClass( tab, "ui-tabs-loading" );
				panel.removeAttr( "aria-busy" );

				if ( jqXHR === that.xhr ) {
					delete that.xhr;
				}
			};

		// Not remote
		if ( this._isLocal( anchor[ 0 ] ) ) {
			return;
		}

		this.xhr = $.ajax( this._ajaxSettings( anchor, event, eventData ) );

		// Support: jQuery <1.8
		// jQuery <1.8 returns false if the request is canceled in beforeSend,
		// but as of 1.8, $.ajax() always returns a jqXHR object.
		if ( this.xhr && this.xhr.statusText !== "canceled" ) {
			this._addClass( tab, "ui-tabs-loading" );
			panel.attr( "aria-busy", "true" );

			this.xhr
				.done( function( response, status, jqXHR ) {

					// support: jQuery <1.8
					// http://bugs.jquery.com/ticket/11778
					setTimeout( function() {
						panel.html( response );
						that._trigger( "load", event, eventData );

						complete( jqXHR, status );
					}, 1 );
				} )
				.fail( function( jqXHR, status ) {

					// support: jQuery <1.8
					// http://bugs.jquery.com/ticket/11778
					setTimeout( function() {
						complete( jqXHR, status );
					}, 1 );
				} );
		}
	},

	_ajaxSettings: function( anchor, event, eventData ) {
		var that = this;
		return {
			url: anchor.attr( "href" ),
			beforeSend: function( jqXHR, settings ) {
				return that._trigger( "beforeLoad", event,
					$.extend( { jqXHR: jqXHR, ajaxSettings: settings }, eventData ) );
			}
		};
	},

	_getPanelForTab: function( tab ) {
		var id = $( tab ).attr( "aria-controls" );
		return this.element.find( this._sanitizeSelector( "#" + id ) );
	}
} );

// DEPRECATED
// TODO: Switch return back to widget declaration at top of file when this is removed
if ( $.uiBackCompat !== false ) {

	// Backcompat for ui-tab class (now ui-tabs-tab)
	$.widget( "ui.tabs", $.ui.tabs, {
		_processTabs: function() {
			this._superApply( arguments );
			this._addClass( this.tabs, "ui-tab" );
		}
	} );
}

var widgetsTabs = $.ui.tabs;


/*!
 * jQuery UI Tooltip 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: Tooltip
//>>group: Widgets
//>>description: Shows additional information for any element on hover or focus.
//>>docs: http://api.jqueryui.com/tooltip/
//>>demos: http://jqueryui.com/tooltip/
//>>css.structure: ../../themes/base/core.css
//>>css.structure: ../../themes/base/tooltip.css
//>>css.theme: ../../themes/base/theme.css



$.widget( "ui.tooltip", {
	version: "1.12.0",
	options: {
		classes: {
			"ui-tooltip": "ui-corner-all ui-widget-shadow"
		},
		content: function() {

			// support: IE<9, Opera in jQuery <1.7
			// .text() can't accept undefined, so coerce to a string
			var title = $( this ).attr( "title" ) || "";

			// Escape title, since we're going from an attribute to raw HTML
			return $( "<a>" ).text( title ).html();
		},
		hide: true,

		// Disabled elements have inconsistent behavior across browsers (#8661)
		items: "[title]:not([disabled])",
		position: {
			my: "left top+15",
			at: "left bottom",
			collision: "flipfit flip"
		},
		show: true,
		track: false,

		// Callbacks
		close: null,
		open: null
	},

	_addDescribedBy: function( elem, id ) {
		var describedby = ( elem.attr( "aria-describedby" ) || "" ).split( /\s+/ );
		describedby.push( id );
		elem
			.data( "ui-tooltip-id", id )
			.attr( "aria-describedby", $.trim( describedby.join( " " ) ) );
	},

	_removeDescribedBy: function( elem ) {
		var id = elem.data( "ui-tooltip-id" ),
			describedby = ( elem.attr( "aria-describedby" ) || "" ).split( /\s+/ ),
			index = $.inArray( id, describedby );

		if ( index !== -1 ) {
			describedby.splice( index, 1 );
		}

		elem.removeData( "ui-tooltip-id" );
		describedby = $.trim( describedby.join( " " ) );
		if ( describedby ) {
			elem.attr( "aria-describedby", describedby );
		} else {
			elem.removeAttr( "aria-describedby" );
		}
	},

	_create: function() {
		this._on( {
			mouseover: "open",
			focusin: "open"
		} );

		// IDs of generated tooltips, needed for destroy
		this.tooltips = {};

		// IDs of parent tooltips where we removed the title attribute
		this.parents = {};

		// Append the aria-live region so tooltips announce correctly
		this.liveRegion = $( "<div>" )
			.attr( {
				role: "log",
				"aria-live": "assertive",
				"aria-relevant": "additions"
			} )
			.appendTo( this.document[ 0 ].body );
		this._addClass( this.liveRegion, null, "ui-helper-hidden-accessible" );

		this.disabledTitles = $( [] );
	},

	_setOption: function( key, value ) {
		var that = this;

		this._super( key, value );

		if ( key === "content" ) {
			$.each( this.tooltips, function( id, tooltipData ) {
				that._updateContent( tooltipData.element );
			} );
		}
	},

	_setOptionDisabled: function( value ) {
		this[ value ? "_disable" : "_enable" ]();
	},

	_disable: function() {
		var that = this;

		// Close open tooltips
		$.each( this.tooltips, function( id, tooltipData ) {
			var event = $.Event( "blur" );
			event.target = event.currentTarget = tooltipData.element[ 0 ];
			that.close( event, true );
		} );

		// Remove title attributes to prevent native tooltips
		this.disabledTitles = this.disabledTitles.add(
			this.element.find( this.options.items ).addBack()
				.filter( function() {
					var element = $( this );
					if ( element.is( "[title]" ) ) {
						return element
							.data( "ui-tooltip-title", element.attr( "title" ) )
							.removeAttr( "title" );
					}
				} )
		);
	},

	_enable: function() {

		// restore title attributes
		this.disabledTitles.each( function() {
			var element = $( this );
			if ( element.data( "ui-tooltip-title" ) ) {
				element.attr( "title", element.data( "ui-tooltip-title" ) );
			}
		} );
		this.disabledTitles = $( [] );
	},

	open: function( event ) {
		var that = this,
			target = $( event ? event.target : this.element )

				// we need closest here due to mouseover bubbling,
				// but always pointing at the same event target
				.closest( this.options.items );

		// No element to show a tooltip for or the tooltip is already open
		if ( !target.length || target.data( "ui-tooltip-id" ) ) {
			return;
		}

		if ( target.attr( "title" ) ) {
			target.data( "ui-tooltip-title", target.attr( "title" ) );
		}

		target.data( "ui-tooltip-open", true );

		// Kill parent tooltips, custom or native, for hover
		if ( event && event.type === "mouseover" ) {
			target.parents().each( function() {
				var parent = $( this ),
					blurEvent;
				if ( parent.data( "ui-tooltip-open" ) ) {
					blurEvent = $.Event( "blur" );
					blurEvent.target = blurEvent.currentTarget = this;
					that.close( blurEvent, true );
				}
				if ( parent.attr( "title" ) ) {
					parent.uniqueId();
					that.parents[ this.id ] = {
						element: this,
						title: parent.attr( "title" )
					};
					parent.attr( "title", "" );
				}
			} );
		}

		this._registerCloseHandlers( event, target );
		this._updateContent( target, event );
	},

	_updateContent: function( target, event ) {
		var content,
			contentOption = this.options.content,
			that = this,
			eventType = event ? event.type : null;

		if ( typeof contentOption === "string" || contentOption.nodeType ||
				contentOption.jquery ) {
			return this._open( event, target, contentOption );
		}

		content = contentOption.call( target[ 0 ], function( response ) {

			// IE may instantly serve a cached response for ajax requests
			// delay this call to _open so the other call to _open runs first
			that._delay( function() {

				// Ignore async response if tooltip was closed already
				if ( !target.data( "ui-tooltip-open" ) ) {
					return;
				}

				// JQuery creates a special event for focusin when it doesn't
				// exist natively. To improve performance, the native event
				// object is reused and the type is changed. Therefore, we can't
				// rely on the type being correct after the event finished
				// bubbling, so we set it back to the previous value. (#8740)
				if ( event ) {
					event.type = eventType;
				}
				this._open( event, target, response );
			} );
		} );
		if ( content ) {
			this._open( event, target, content );
		}
	},

	_open: function( event, target, content ) {
		var tooltipData, tooltip, delayedShow, a11yContent,
			positionOption = $.extend( {}, this.options.position );

		if ( !content ) {
			return;
		}

		// Content can be updated multiple times. If the tooltip already
		// exists, then just update the content and bail.
		tooltipData = this._find( target );
		if ( tooltipData ) {
			tooltipData.tooltip.find( ".ui-tooltip-content" ).html( content );
			return;
		}

		// If we have a title, clear it to prevent the native tooltip
		// we have to check first to avoid defining a title if none exists
		// (we don't want to cause an element to start matching [title])
		//
		// We use removeAttr only for key events, to allow IE to export the correct
		// accessible attributes. For mouse events, set to empty string to avoid
		// native tooltip showing up (happens only when removing inside mouseover).
		if ( target.is( "[title]" ) ) {
			if ( event && event.type === "mouseover" ) {
				target.attr( "title", "" );
			} else {
				target.removeAttr( "title" );
			}
		}

		tooltipData = this._tooltip( target );
		tooltip = tooltipData.tooltip;
		this._addDescribedBy( target, tooltip.attr( "id" ) );
		tooltip.find( ".ui-tooltip-content" ).html( content );

		// Support: Voiceover on OS X, JAWS on IE <= 9
		// JAWS announces deletions even when aria-relevant="additions"
		// Voiceover will sometimes re-read the entire log region's contents from the beginning
		this.liveRegion.children().hide();
		a11yContent = $( "<div>" ).html( tooltip.find( ".ui-tooltip-content" ).html() );
		a11yContent.removeAttr( "name" ).find( "[name]" ).removeAttr( "name" );
		a11yContent.removeAttr( "id" ).find( "[id]" ).removeAttr( "id" );
		a11yContent.appendTo( this.liveRegion );

		function position( event ) {
			positionOption.of = event;
			if ( tooltip.is( ":hidden" ) ) {
				return;
			}
			tooltip.position( positionOption );
		}
		if ( this.options.track && event && /^mouse/.test( event.type ) ) {
			this._on( this.document, {
				mousemove: position
			} );

			// trigger once to override element-relative positioning
			position( event );
		} else {
			tooltip.position( $.extend( {
				of: target
			}, this.options.position ) );
		}

		tooltip.hide();

		this._show( tooltip, this.options.show );

		// Handle tracking tooltips that are shown with a delay (#8644). As soon
		// as the tooltip is visible, position the tooltip using the most recent
		// event.
		// Adds the check to add the timers only when both delay and track options are set (#14682)
		if ( this.options.track && this.options.show && this.options.show.delay ) {
			delayedShow = this.delayedShow = setInterval( function() {
				if ( tooltip.is( ":visible" ) ) {
					position( positionOption.of );
					clearInterval( delayedShow );
				}
			}, $.fx.interval );
		}

		this._trigger( "open", event, { tooltip: tooltip } );
	},

	_registerCloseHandlers: function( event, target ) {
		var events = {
			keyup: function( event ) {
				if ( event.keyCode === $.ui.keyCode.ESCAPE ) {
					var fakeEvent = $.Event( event );
					fakeEvent.currentTarget = target[ 0 ];
					this.close( fakeEvent, true );
				}
			}
		};

		// Only bind remove handler for delegated targets. Non-delegated
		// tooltips will handle this in destroy.
		if ( target[ 0 ] !== this.element[ 0 ] ) {
			events.remove = function() {
				this._removeTooltip( this._find( target ).tooltip );
			};
		}

		if ( !event || event.type === "mouseover" ) {
			events.mouseleave = "close";
		}
		if ( !event || event.type === "focusin" ) {
			events.focusout = "close";
		}
		this._on( true, target, events );
	},

	close: function( event ) {
		var tooltip,
			that = this,
			target = $( event ? event.currentTarget : this.element ),
			tooltipData = this._find( target );

		// The tooltip may already be closed
		if ( !tooltipData ) {

			// We set ui-tooltip-open immediately upon open (in open()), but only set the
			// additional data once there's actually content to show (in _open()). So even if the
			// tooltip doesn't have full data, we always remove ui-tooltip-open in case we're in
			// the period between open() and _open().
			target.removeData( "ui-tooltip-open" );
			return;
		}

		tooltip = tooltipData.tooltip;

		// Disabling closes the tooltip, so we need to track when we're closing
		// to avoid an infinite loop in case the tooltip becomes disabled on close
		if ( tooltipData.closing ) {
			return;
		}

		// Clear the interval for delayed tracking tooltips
		clearInterval( this.delayedShow );

		// Only set title if we had one before (see comment in _open())
		// If the title attribute has changed since open(), don't restore
		if ( target.data( "ui-tooltip-title" ) && !target.attr( "title" ) ) {
			target.attr( "title", target.data( "ui-tooltip-title" ) );
		}

		this._removeDescribedBy( target );

		tooltipData.hiding = true;
		tooltip.stop( true );
		this._hide( tooltip, this.options.hide, function() {
			that._removeTooltip( $( this ) );
		} );

		target.removeData( "ui-tooltip-open" );
		this._off( target, "mouseleave focusout keyup" );

		// Remove 'remove' binding only on delegated targets
		if ( target[ 0 ] !== this.element[ 0 ] ) {
			this._off( target, "remove" );
		}
		this._off( this.document, "mousemove" );

		if ( event && event.type === "mouseleave" ) {
			$.each( this.parents, function( id, parent ) {
				$( parent.element ).attr( "title", parent.title );
				delete that.parents[ id ];
			} );
		}

		tooltipData.closing = true;
		this._trigger( "close", event, { tooltip: tooltip } );
		if ( !tooltipData.hiding ) {
			tooltipData.closing = false;
		}
	},

	_tooltip: function( element ) {
		var tooltip = $( "<div>" ).attr( "role", "tooltip" ),
			content = $( "<div>" ).appendTo( tooltip ),
			id = tooltip.uniqueId().attr( "id" );

		this._addClass( content, "ui-tooltip-content" );
		this._addClass( tooltip, "ui-tooltip", "ui-widget ui-widget-content" );

		tooltip.appendTo( this._appendTo( element ) );

		return this.tooltips[ id ] = {
			element: element,
			tooltip: tooltip
		};
	},

	_find: function( target ) {
		var id = target.data( "ui-tooltip-id" );
		return id ? this.tooltips[ id ] : null;
	},

	_removeTooltip: function( tooltip ) {
		tooltip.remove();
		delete this.tooltips[ tooltip.attr( "id" ) ];
	},

	_appendTo: function( target ) {
		var element = target.closest( ".ui-front, dialog" );

		if ( !element.length ) {
			element = this.document[ 0 ].body;
		}

		return element;
	},

	_destroy: function() {
		var that = this;

		// Close open tooltips
		$.each( this.tooltips, function( id, tooltipData ) {

			// Delegate to close method to handle common cleanup
			var event = $.Event( "blur" ),
				element = tooltipData.element;
			event.target = event.currentTarget = element[ 0 ];
			that.close( event, true );

			// Remove immediately; destroying an open tooltip doesn't use the
			// hide animation
			$( "#" + id ).remove();

			// Restore the title
			if ( element.data( "ui-tooltip-title" ) ) {

				// If the title attribute has changed since open(), don't restore
				if ( !element.attr( "title" ) ) {
					element.attr( "title", element.data( "ui-tooltip-title" ) );
				}
				element.removeData( "ui-tooltip-title" );
			}
		} );
		this.liveRegion.remove();
	}
} );

// DEPRECATED
// TODO: Switch return back to widget declaration at top of file when this is removed
if ( $.uiBackCompat !== false ) {

	// Backcompat for tooltipClass option
	$.widget( "ui.tooltip", $.ui.tooltip, {
		options: {
			tooltipClass: null
		},
		_tooltip: function() {
			var tooltipData = this._superApply( arguments );
			if ( this.options.tooltipClass ) {
				tooltipData.tooltip.addClass( this.options.tooltipClass );
			}
			return tooltipData;
		}
	} );
}

var widgetsTooltip = $.ui.tooltip;




}));

/***/ }),
/* 12 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function(jQuery) {var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*!
 * Copyright 2016 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 */

///* Evento del evento de antes de la carga de los datos */
//		var loadBeforeSendUserEvent = settings.loadBeforeSend;
//		settings.loadBeforeSend = function(xhr){
//			if(loadBeforeSendUserEvent !== null){
//		        if(loadBeforeSendUserEvent(xhr) === false){
//		            return false;
//		        }
//		    }
//			//console.log("loadBeforeSend");
//			//Comportamiento por defecto del evento
//			loadBeforeSend_default(xhr);
//		};

/**
 * Permite lanzar un subproceso o un mensaje de confirmación dentro de un proceso principal sin salirse de este. <br/><br/>Es una evolución del patrón mensaje.
 *
 * @summary Componente RUP Dialog.
 * @module rup_dialog
 * @see El componente está basado en el plugin {@link https://jqueryui.com/dialog/|jQuery UI Dialog}. Para mas información acerca de las funcionalidades y opciones de configuración pinche {@link http://api.jqueryui.com/dialog/|aquí}.
 * @example
 * var properties = {
 *   type: $.rup.dialog.TEXT,
 *   autoOpen: true,
 *   modal: true,
 *   resizable: true,
 *   title: "Título del dialog (text) ",
 *   message: "Se esta creando un div con el mensaje puesto por parametro."
 * };
 *
 * $("#selector").rup_dialog(properties);
 */

/*global define */
/*global jQuery */

(function (factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(2), __webpack_require__(23)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		factory(jQuery);
	}
})(function ($) {

	//*********************************************
	// ESPECIFICACÍON DE LOS TIPOS BASE DEL PATRÓN
	//*********************************************

	$.extend($.rup, {
		/**
     * Dialogo creado a partir de un diálogo existente.
     * @typedef {string} module:rup_dialog~DIV
     * @example
     * $.rup.dialog.DIV
     *
     */

		/**
     *  Dialogo creado a partir de un texto.
     * @typedef {string} module:rup_dialog~TEXT
     * @example
     * $.rup.dialog.TEXT
     */
		/**
     *  Dialogo creado a partir de la respuesta de una petición AJAX.
     * @typedef {string} module:rup_dialog~AJAX
     * @example
     * $.rup.dialog.AJAX
     */
		/**
     *   Dialogo creado a partir del contenido de un enlace estático.
     * @typedef {string} module:rup_dialog~LINK
     * @example
     * $.rup.dialog.LINK
     */

		dialog: {
			DIV: 'dialogDIV',
			TEXT: 'textDialog',
			AJAX: 'ajaxDialog',
			LINK: 'linkButton'
		}
	});

	//*****************************************************************************************************************
	// DEFINICIÓN BASE DEL PATRÓN (definición de la variable privada que contendrá los métodos y la función de jQuery)
	//*****************************************************************************************************************


	var rup_dialog = {};

	//Se configura el arranque de UDA para que alberge el nuevo patrón
	$.extend($.rup.iniRup, $.rup.rupSelectorObjectConstructor('rup_dialog', rup_dialog));

	$.widget('ui.dialog', $.ui.dialog, {
		_title: function _title(title) {
			if (this.options.title) {
				title.html(this.options.title);
			} else {
				title.html('&#160;');
			}
		}
	});

	//********************************
	// DEFINICIÓN DE MÉTODOS PÚBLICOS
	//********************************

	$.fn.rup_dialog('extend', {
		/**
     * Abre el diálogo y estable el foco en el primer botón.
     *
     * @function  open
     * @example
     * $("#selector").rup_dialog("open");
     */
		open: function open() {
			//abre el dialogo y estable el foco en el primer botón.
			var settings = $.extend({}, $(this).dialog('option')),
			    $overlayEl;
			//Guardar el elemento que tenía el foco antes de abrir el diálogo
			$(this).data('focus', $(document.activeElement));

			var docHeight = $(document).height(),
			    docWidth = $(document).width();

			if ($(this).dialog('option', 'ajaxCache') === false) {
				settings.id = $(this).attr('id');
				settings.autoOpen = true;
				this._ajaxLoad(settings);
			} else {
				$(this).dialog('open');
			}

			//Ajuste para portales
			if ($.rup_utils.aplicatioInPortal()) {
				if ($(this).data('uiDialog').overlay !== null) {
					$overlayEl = $(this).data('uiDialog').overlay;
					$('.r01gContainer').append($overlayEl);
					$overlayEl.css('height', docHeight).css('width', docWidth);
				}
				if (settings.position === undefined || settings.position === null) {
					$(this).data('uiDialog').uiDialog.css('position', 'absolute').css('top', docHeight / 2 - $('div[aria-describedby=' + this[0].id + ']').height() / 2);
				}
			}

			$('div[aria-describedby=' + this[0].id + '] .ui-dialog-buttonpane button:first').focus();
		},
		/**
     * Borra el dialogo si este estubiera oculto o visible.
     *
     * @function  destroy
     *
     * @example
     * $("#selector").rup_dialog("destroy");
     */
		destroy: function destroy() {
			$(this).dialog('destroy');
		},
		/**
     * Función que deshabilita el dialogo sobre el que se aplica.
     *
     * @function  disable
     *
     * @example
     * $("#selector").rup_dialog("disable");
     */
		disable: function disable() {
			$(this).dialog('disable');
		},
		/**
     * Funcion que, en caso de estar desahibilitado, habilita el dialogo sobre el que se aplica.
     *
     * @function  enable
     *
     * @example
     * $("#selector").rup_dialog("enable");
     */
		enable: function enable() {
			$(this).dialog('enable');
		},
		widget: function widget() {
			return $(this).dialog('widget');
		},
		/**
     * Funcion encargada de poner por encima de todos los dialogos al dialogo sobre el que se aplica. Puede ser muy util se se tiene mas de un dialog abierto a la vez.
     *
     * @function  moveToTop
     *
     * @example
     * $("#selector").rup_dialog("moveToTop");
     */
		moveToTop: function moveToTop() {
			$(this).dialog('moveToTop');
		},
		/**
     * Cierra el dialogo.
     *
     * @function  close
     *
     * @example
     * $("#selector").rup_dialog("close");
     */
		close: function close() {
			//Cierra el dialogo.
			$(this).dialog('close');
		},
		/**
     * Función que devuelve si el dialogo esta abierto o no.
     *
     * @function   isOpen
     * @returns {boolean} - Determina si el diálogo está abierto o no.
     * @example
     * $("#selector").rup_dialog("isOpen");
     */
		isOpen: function isOpen() {
			//Función que devuelve si el dialogo esta abierto.
			return $(this).dialog('isOpen');
		},
		/**
     * Obtiene la propiedad que recibe como parametro.
     *
     * @function  getOption
     * @param {string} opt - Nombre de la propiedad.
     * @returns {Object} - Valor de la propiedad especificada.
     * @example
     * $("#selector").rup_dialog("getOption","width");
     */
		getOption: function getOption(opt) {
			//Obtiene la propiedad que recibe como parametro.
			return $(this).dialog('option', opt);
		},
		/**
     * Establece la propiedad que recibe como parametro.
     *
     * @function  setOption
     * @param {string} opt - Nombre de la propiedad.
     * @param {object} value - Valor de la propiedad a establecer.
     * @example
     * $("#selector").rup_dialog("setOption","width", 200);
     */
		setOption: function setOption(opt, value) {
			//Establece la propiedad que recibe como parametro.
			if (opt === 'buttons') {
				//si establecemos los botones tenemos que tener encuenta lo de los links
				var btnsLength = value.length,
				    aux,
				    i,
				    j,
				    linkButtons = [],
				    linkButtonsLength; //tamaño incial de los botones se o no enlaces
				if (btnsLength > 1) {
					//si tenemos mas de un boton buscamos cual es el link
					aux = value;
					for (i = 0; i < value.length; i++) {
						//se usa el length y no una variable porque se eliminan botones y el tamaño varia
						if (value[i].btnType === $.rup.dialog.LINK) {
							linkButtons.push(value.splice(i, 1));
							i--;
						}
					}
					i = null;
				}
				linkButtonsLength = linkButtons.length;
				//Si tiene mas de dos botones y ninguno de ellos es de tipo link, entonces le mostrar una alerta diciendo que no cumple arista.
				if (btnsLength > 1 && linkButtonsLength === 0 /*&& settings.rupCheckStyle*/) {
						$.rup_messages("msgAlert", {
							message: $.rup.i18nParse($.rup.i18n, 'base.rup_global.rupCheckStyleError')
						});
						return false;
					}
				$(this).dialog('option', opt, value);
				if (linkButtonsLength > 0) {
					//si tenemos enlaces los añadimos
					for (j = 0; j < linkButtonsLength; j++) {
						this.createBtnLinks(linkButtons[j][0], this[0].id);
					}
					j = null;
				}
				return;
			}
			if (opt === 'title') {
				if (value !== undefined) {
					$(this).dialog('option', opt, value);
				} else {
					$(this).dialog('option', opt);
				}
			}
		},
		/**
     * Función que crea los botones como enlaces y se los añade al panel de botones al final de los botones.
     *
     * @function  createBtnLinks
     * @param {object} btn - Objeto de definición del botón.
     * @param {object} id - Identificador del diálogo.
     * @example
     * $("#selector").rup_dialog("createBtnLinks", btnObj, "idDialog");
     */
		createBtnLinks: function createBtnLinks(btn, id) {
			/**
       * Función que crea los botones como enlaces y se los añade al panel de botones al final de los botones
       */
			var buttonHREF = $('<button></button>').attr('type', 'button').attr('id', 'rup_dialog' + btn.text).addClass('btn-outline-primary ui-button ui-corner-all ui-widget').html(btn.text).click(btn.click);
			$('div[aria-describedby=' + id + '] .ui-dialog-buttonset ').append(buttonHREF);
		}
	});

	//********************************
	// DEFINICIÓN DE MÉTODOS PRIVADOS
	//********************************

	$.fn.rup_dialog('extend', {
		/**
     * Método de inicialización del componente
     *
     * @function  _init
     * @private
     */
		_init: function _init(args) {

			if (args.length > 1) {
				$.rup.errorGestor($.rup.i18nParse($.rup.i18n.base, 'rup_global.initError' + $(this).attr('id')));
			} else {
				//Se recogen y cruzan las paremetrizaciones del objeto
				var settings = $.extend({}, $.fn.rup_dialog.defaults, args[0]),
				    json_i18n,
				    dialog = this,
				    msgDiv,
				    codeEventCreate = undefined;

				//Sobrecargar close para recuperar foco en elemento que ha lanzado el diálogo
				settings._close = settings.close;
				settings.close = function (event, ui) {
					if ($(this).data('focus') !== undefined) {
						$(this).data('focus').focus();
					}
					if (settings._close !== undefined) {
						settings._close(event, ui);
					}
				};

				//Se verifica que el selector solo contenga un diálogo
				if (settings.type !== null && $(this).length > 0) {

					$.each($(this), function (index, object) {
						var $self = $(this);

						if ($self.attr('id') !== undefined) {
							settings.id = $self.attr('id');
						} else {
							settings.id = 'rup_' + settings.type + 'DIV';
							msgDiv = $('<div/>').attr('id', settings.id);
							msgDiv.appendTo('body');
						}

						var autopen = false,
						    linkButtons = [],
						    btnsLength,
						    aux,
						    aClose,
						    linkButtonsLength = 0,
						    closeSpan,
						    i,
						    j,
						    created = false,
						    codeEventCreate = undefined;

						//Se determina la ubicación del dialogo físicamente (dentro de la pagina html). Por defecto se ubica en el body de la página pero puede determinarse una ubicación específica.
						//En caso de encontrarnos en portales (Ejie), y no determinar una ubicación específica, se ubica dentro de los rangos apropiados.
						if ($('div[aria-describedby=' + settings.id + ']').length > 0) {
							//comprobamos que no se haya ya creado el dialog sobre ese div para evitar problemas de sobreescritura de propiedades, como el tiulo...
							created = true;
						} else {
							if ($('body #' + settings.id).not('.ui-dialog-content').length > 1) {
								$($('body #' + settings.id).not('.ui-dialog-content')[1]).remove();
							}

							if (settings.specificLocation !== '') {
								codeEventCreate = function codeEventCreate(event, ui) {
									$self.parent('.ui-dialog').insertAfter($('#' + settings.specificLocation));
								};
							} else if ($.rup_utils.aplicatioInPortal()) {
								//Ajuste para portales
								codeEventCreate = function codeEventCreate(event, ui) {
									$('.r01gContainer').append($('.ui-dialog'));
								};
							}
						}

						//Evento de create (respetando las opciones de los usuarios)
						if (codeEventCreate !== undefined) {
							/* Gestion del evento create */
							var createUserEvent = settings.create;
							settings.create = function (event, ui) {
								if (createUserEvent !== undefined && createUserEvent !== null) {
									if (createUserEvent.call(event, ui) === false) {
										return false;
									}
								}
								//Comportamiento por defecto del evento
								codeEventCreate(event, ui);
							};
						}

						switch (settings.type) {
							case $.rup.dialog.DIV:
								//si el dialog es de tipo DIV se utilizara el div creado por el desarrollador para crear el ui dialog
								if (settings.clone !== undefined) {
									$self.clone(true).attr('id', settings.clone).insertAfter($self);
									settings.id = settings.clone;
								}
								break;
							case $.rup.dialog.TEXT:
								$self.html(settings.message);
								break;
							case $.rup.dialog.AJAX:
								dialog._ajaxLoad(settings);
								break;
						}

						//Para que no se abra hasta que terminemos con todas nuestra acciones
						if (settings.autoOpen === true) {
							autopen = true;
							settings.autoOpen = false;
						}

						//controlar que existan los botones
						if (settings.buttons && settings.buttons !== null) {
							btnsLength = settings.buttons.length; //tamaño incial de los botones se o no enlaces
							if (btnsLength > 1) {
								//si tenemos mas de un boton buscamos cual es el link
								aux = settings.buttons;
								for (i = 0; i < settings.buttons.length; i++) {
									//se usa el length y no una variable porque se eliminan botones y el tamaño varia
									if (settings.buttons[i].btnType === $.rup.dialog.LINK) {
										linkButtons.push(settings.buttons.splice(i, 1));
										i--;
									}
								}
								i = null;
							}
							linkButtonsLength = linkButtons.length;
							//Si tiene mas de dos botones y ninguno de ellos es de tipo link, entonces le mostrar una alerta diciendo que no cumple arista.
							if (btnsLength > 1 && linkButtonsLength === 0 && settings.rupCheckStyle) {
								$.rup_messages("msgAlert", {
									message: $.rup.i18nParse($.rup.i18n.base, 'rup_global.rupCheckStyleError')
								});
								settings.stack = false;
								settings.modal = false;
								settings.zIndex = 9999;
							}
						}

						if (!created) {
							//si ha sido creado no hace falta volver a añadir el enlace de cierre
							$self.dialog(settings);

							// Estilos RUP

							$self.data('uiDialog').uiDialog.addClass('rup-dialog');

							closeSpan = '<span id=\'closeText_' + settings.id + '\' style=\'float:right;font-size:0.85em\'>' + $.rup.i18nParse($.rup.i18n.base, 'rup_global.cerrar') + '</span>';
							aClose = $('<a href=\'#\'></a>').attr('role', 'button').css('margin-right', '0.9em').css('float', 'right').css('width', '50px').addClass('ui-dialog-title').html(closeSpan).click(function (event) {
								$self.dialog('close');
								return false;
							}).hover(function (eventObject) {
								//Evento lanzado para que se cambie el icono de la X a hover, marcado por ARISTA
								$('div[aria-labelledby=ui-dialog-title-' + settings.id + '] .ui-dialog-titlebar-close').addClass('ui-state-hover');
								$('div[aria-labelledby=ui-dialog-title-' + settings.id + '] .ui-dialog-titlebar-close').css('padding', '0px');
							}, function (eventObject) {
								$('div[aria-labelledby=ui-dialog-title-' + settings.id + '] .ui-dialog-titlebar-close').removeClass('ui-state-hover');
								$('div[aria-labelledby=ui-dialog-title-' + settings.id + '] .ui-dialog-titlebar-close').attr('style', '');
							}).insertAfter(jQuery('span.ui-dialog-title', jQuery('#' + settings.id).parent()));
							$('div[aria-labelledby=ui-dialog-title-' + settings.id + '] .ui-dialog-titlebar-close').hover(function () {
								aClose.css('text-decoration', 'none');
							}, function () {
								aClose.css('text-decoration', '');
							});

							if (linkButtonsLength > 0) {
								//si tenemos enlaces los añadimos
								for (j = 0; j < linkButtonsLength; j++) {
									$(this).rup_dialog('createBtnLinks', linkButtons[j][0], settings.id);
								}
								j = null;
							}
						} else {
							//borramos todos los posibles enlances que se hayan creado para esa capa
							$('div[aria-labelledby=ui-dialog-title-' + settings.id + '] .ui-dialog-buttonset a').remove();

							if (settings.title) {
								$('#ui-dialog-title-' + settings.id).text(settings.title);
							}
						}

						if (autopen) {
							//si se auto abría lo mostramos
							if (settings.type !== $.rup.dialog.AJAX) {
								$self.rup_dialog('open');
								//le establecemos el foco
								$('div[aria-labelledby=ui-dialog-title-' + settings.id + '] .ui-dialog-buttonpane button:first').focus();
							} else {
								settings.autoOpen = true;
							}
						}
					});
				} else {
					if ($(this).length === 0) {
						$.rup.errorGestor($.rup.i18nParse($.rup.i18n.base, 'rup_global.selectorError'));
					} else {
						$.rup.errorGestor($.rup.i18nParse($.rup.i18n.base, 'rup_global.dialogTypeError'));
					}
				}
			}
		},
		/**
     * Realiza la carga del contenido del diálogo a partir de una petición AJAX.
     *
     * @function  _ajaxLoad
     * @private
     * @param {object} settings - Propiedades de configuración del componente.
     */
		_ajaxLoad: function _ajaxLoad(settings) {
			//Si el tipo de dialogo es AJAX y no se establece url se muestra un error y se devuelve el control
			if (!settings.url || settings.url === null || settings.url === '') {
				$.rup_messages("msgAlert", {
					title: $.rup.i18nParse($.rup.i18n.base, 'rup_global.error'),
					message: $.rup.i18nParse($.rup.i18n.base, 'rup_dialog.noURL')
				});
				return false;
			}

			if (settings.showLoading && settings.autoOpen === true) {
				//si hay que mostrar la capa de cargando por defecto a false
				$.blockUI({
					message: '<img src="' + $.rup.RUP + '/css/images/rup.ajaxLoader.gif" style="position:absolute;top:12px;left:15px;" alt="' + $.rup.i18nParse($.rup.i18n.base, 'rup_blockUI.cargando') + '" ><h1 class="loading">' + $.rup.i18nParse($.rup.i18n.base, 'rup_blockUI.cargando') + '...' + '</h1>'
				});
			}

			//Especificación de las opciones asociadas a las llamada Ajax que carga el diálogo
			var ajaxOptions = $.extend({}, settings.ajaxOptions);
			ajaxOptions.success = function (data, textStatus, XMLHttpRequest) {
				if (data !== '' || data !== null) {
					//si nos devuelve datos los mostramos como HTML y desbloqueamos el ui
					$('#' + settings.id).html(data);
					$.unblockUI();
					if (settings.autoOpen === true) {
						$('#' + settings.id).rup_dialog('open');
						//le establecemos el foco
						$('div[aria-labelledby=ui-dialog-title-' + settings.id + '] .ui-dialog-buttonpane button:first').focus();
					}
				}
				if (settings.ajaxOptions && settings.ajaxOptions.success !== undefined && settings.ajaxOptions.success !== null && typeof settings.ajaxOptions.success === 'function') {
					settings.ajaxOptions.success(data, textStatus, XMLHttpRequest);
				}
			};
			ajaxOptions.error = function (XMLHttpRequest, textStatus, errorThrown) {
				//en caso de error mostramos un mensaje de alerta
				$.unblockUI();

				if (settings.ajaxOptions && settings.ajaxOptions.error !== undefined && settings.ajaxOptions.error !== null && typeof settings.ajaxOptions.error === 'function') {
					settings.ajaxOptions.error(XMLHttpRequest, textStatus, errorThrown);
				} else {
					$.rup_messages("msgAlert", {
						message: $.rup.i18nParse($.rup.i18n.base, 'rup_dialog.errorLoadingData')
					});
				}
			};
			ajaxOptions.url = $.rup_utils.setNoPortalParam(settings.url);
			ajaxOptions.type = 'GET';
			ajaxOptions.cache = false;
			ajaxOptions.dataType = 'text';
			//Peticion ajax para obtener los datos a mostrar
			$.rup_ajax(ajaxOptions);
		}
	});

	//*******************************************************
	// DEFINICIÓN DE LA CONFIGURACION POR DEFECTO DEL PATRON
	//*******************************************************

	/**
   * Propiedades de configuración de la petición Ajax.
   *
   * @typedef {object} ajaxOptions
   * @see {@link http://api.jquery.com/jquery.ajax/#jQuery-ajax-settings|jQuery Ajax Settings}
   */

	/**
   * Evento que se lanza cuando se abre el diálogo.
   *
   * @see {@link http://api.jqueryui.com/dialog/#event-open jQueryUI Dialog}
   * @callback onOpen
   * @param {Event} event - Fecha seleccionada
   * @param {object} ui - Objeto de jQueryUI correspondiente a la interfaz del diálogo.
   * @example
   * $("#idDialog").rup_dialog({
   *  open: function(event, ui) { ... }
   * });
   */

	/**
   * Evento que se lanza a la hora de cerrar el diálogo.
   *
   * @see {@link http://api.jqueryui.com/dialog/#event-open jQueryUI Dialog}
   * @callback jQuery.rup_dialog~onClose
   * @param {Event} event - Fecha seleccionada
   * @param {object} ui - Objeto de jQueryUI correspondiente a la interfaz del diálogo.
   * @example
   * $("#idDialog").rup_dialog({
   *  close: function(event, ui) { ... }
   * });
   */

	/**
   * Evento que se lanza justo antes de que se cierre el dialogo, si este evento devuelve false se anulará las acción de cierre y el dialogo seguirá abierto
   *
   * @see {@link http://api.jqueryui.com/dialog/#event-beforeClose jQueryUI Dialog}
   * @callback onBeforeClose
   * @param {Event} event - Fecha seleccionada
   * @param {object} ui - Objeto de jQueryUI correspondiente a la interfaz del diálogo.
   * @return {boolean} - Si devuelve false se anulará las acción de cierre y el dialogo seguirá abierto.
   * @example
   * $("#idDialog").rup_dialog({
   *  onBeforeClose: function(event, ui) { ... }
   * });
   */

	/**
   * Opciones por defecto de configuración del componente.
   * @name defaults
   *
   * @property {string} [url] - Url de donde se obtendrá el contenido del diálogo.
   * @property {boolean} [rupCheckStyle=true] Propiedad definida por el componentes base, si está a true se mostraran los mensajes específicos del componente base marcados por la guía de estilos, es decir, que si el desarrollador no cumple con la guisa de estilos o desarrollo el objeto base mostrará los mensajes advirtiendo su incumplimiento, si se pone a false no se mostraran. Esta acción queda bajo la responsabilidad de la aplicación, ya que esta propiedad no debería modificarse.
   * @property {module:rup_dialog~DIV | module:rup_dialog~TEXT | module:rup_dialog~AJAX |module:rup_dialog~LINK } type - Propiedad que establece el tipo de diálogo a mostrar.
   * @property {jQuery.rup_dialog~ajaxOptions} ajaxOptions - Establece las todas las propiedades para configurar la petición ajax.
   * @property {boolean} [showLoading=true] - Esta propiedad mostrará una capa de cargando datos en los diálogos de tipo Ajax durante la carga del mismo.
   * @property {boolean} [disabled=false] - Propiedad que deshabilita o no el diálogo.
   * @property {boolean} [autoOpen=true] - Si esta propiedad esta a true el diálogo se abrirá automáticamente cuando se cree, en el caso de que su valor sea false, el diálogo se mantendrá oculto hasta que se invoque a la función “open” (.rup_dialog(“open”)).
   * @property {Object} [buttons] - Define los botones (literales y funciones a las que invocan) que contendrá el diálogo. La propiedad sería de tipo Array. Donde cada elemento del array debe ser un objeto que define las propiedades de cada botón y el tipo del mismo.
   * @property {boolean} [closeOnEscape=true] - Especifica si se debe cerrar el diálogo cuando el tenga el foco y el usuario pulse la tecla ESC.
   * @property {string} dialogClass - Porpiedad que establece el/los estilos que se añadirán al dialogo para dotar al dialogo de estilos diferentes.
   * @property {boolean} [draggable=true] - Si su valor es true el diáologo sera dragable pinchando sobre el título.
   * @property {string | number} [height=auto] - Establece el alto del diálogoen pixeles.
   * @property {string} [hide=null] - Efecto utilizado cuando se cierra el diálogo.
   * @property {boolean | number} [maxHeight=false] - Alto máximo en pixeles al que se puede llegar a redimensionar el diálogo.
   * @property {boolean | number} [maxWidth=false] - Ancho máximo en pixeles al que se puede llegar a redimensionar el diálogo.
   * @property {boolean | number} [minHeight=100] - Alto mínimo en pixeles al que se puede llegar a redimensionar el diálogo.
   * @property {boolean | number} [minWidth=150] - Ancho mínimo en pixeles al que se puede llegar a redimensionar el diálogo.
   * @property {boolean} [modal=false] - Si se establece esta propiedad a true el diálogo se abrirá de forma modal, por encima del resto de elementos.
   * @property {string | string[] | number[]} position - Esta propiedad especifica donde debe mostrarse el diálogo. Sus posibles valores son: Un simple String representando la posición. 'center', 'left', 'right', 'top', 'bottom'. Un array con las coordenadas x, y en pixles (e. [350,100]). Un array con string que representan la posición (e. ['right','top']).
   * @property {boolean} [resizable=true] - Si se establece esta propiedad a true el diálogo se redimensionable.
   * @property {string} [show] - Efecto a realizar cuando se abre el diálogo.
   * @property {string} [title] - Establece el título de la ventana. Puede ser cualquier html válido.
   * @property {number} [width=300] - Establece el ancho del diálogo en pixeles.
   * @property {jQuery.rup_dialog~onOpen} open - Evento que se lanza cuando se abre el diálogo.
   * @property {jQuery.rup_dialog~onClose} close - Evento que se lanza a la hora de cerrar el diálogo.
   * @property {jQuery.rup_dialog~onBeforeClose} beforeClose - Evento que se lanza justo antes de que se cierre el dialogo, si este evento devuelve false se anulará las acción de cierre y el dialogo seguirá abierto.
   */
	$.fn.rup_dialog.defaults = {
		rupCheckStyle: true,
		type: null,
		url: null,
		minHeight: 100,
		ajaxCache: true,
		specificLocation: '',
		clone: undefined
	};
});
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))

/***/ }),
/* 13 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function($) {var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*!
 * Copyright 2013 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 */

/**
 * Permite al usuario introducir datos en una serie de campos para ser enviados al servidor y ser procesados.
 *
 * @summary Componente RUP Form.
 * @module   rup_form
 * @example
 * var properties={
 *   // Propiedades de configuración
 * };
 *
 * $("#formulario").rup_form(properties);
 */

/*global define */
/*global jQuery */

(function (factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(195), __webpack_require__(21), __webpack_require__(2), __webpack_require__(18)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		factory(jQuery);
	}
})(function (jQuery) {

	//*********************************************
	// ESPECIFICACÍON DE LOS TIPOS BASE DEL PATRÓN
	//*********************************************

	//*****************************************************************************************************************
	// DEFINICIÓN BASE DEL PATRÓN (definición de la variable privada que contendrá los métodos y la función de jQuery)
	//*****************************************************************************************************************

	var rup_form = {};

	//Se configura el arranque de UDA para que alberge el nuevo patrón
	$.extend($.rup.iniRup, $.rup.rupSelectorObjectConstructor('rup_form', rup_form));

	//********************************
	// DEFINICIÓN DE MÉTODOS PÚBLICOS
	//********************************

	$.fn.rup_form('extend', {
		/**
         * Realiza la misma función que ajaxSubmit. Se mantiene para asegurar la retrocompatibilidad con versiones anteriores.
         *
         * @function  ajaxFormSubmit
         * @param {object} options - Opciones de configuración.
         * @example
         * var options = {};
         * jQuery("#form").rup_form("ajaxFormSubmit", options);
         */
		ajaxFormSubmit: function ajaxFormSubmit(options) {
			var $self = this;
			// Actiavamos la gestión de las peticiones AJAX mediante la función $.rup_ajax.
			$.set_uda_ajax_mode_on();
			$self.ajaxSubmit(options);
		},
		/**
         * Realiza el envío del formulario. La configuración de este método es la misma que la de ajaxForm.
         *
         * @function  ajaxSubmit
         * @param {object} argOptions - Opciones de configuración.
         * @example
         * var options = {};
         * jQuery("#form").rup_form("ajaxSubmit", options);
         */
		ajaxSubmit: function ajaxSubmit(argOptions) {
			var $self = this,
			    options = $.extend(true, {}, $.fn.rup_form.defaults, argOptions);
			// Actiavamos la gestión de las peticiones AJAX mediante la función $.rup_ajax.
			$.set_uda_ajax_mode_on();
			$self.rup_form('configureOptions', options);
			if (options.formValidationRequired) {
				$self.rup_validate(options.validate);
				if ($self.valid()) {
					$(this).ajaxSubmit(options);
				}
			} else {
				// Necesario utilizar $(this) para invocar al ajaxSubmit del plugin subyacente
				$(this).ajaxSubmit(options);
			}
		},
		/**
         * Elimina la configuración realizada por el componente sobre el formulario html.
         *
         * @function  destroy
         * @example
         * var options = {};
         * jQuery("#form").rup_form("destroy");
         */
		destroy: function destroy() {
			var $self = this;
			$.removeData($self[0]);
			$self.ajaxFormUnbind();
			$self.unbind();
		},
		/**
         * Serializa el contenido del formulario en un query string.
         *
         * @function  formSerialize
         * @return {string} - Retorna una cadena de texto con el formato nombre1=valor1&nombre2=valor2.
         * @example
         * jQuery("#form").rup_form("formSerialize");
         */
		formSerialize: function formSerialize() {
			var $self = this,
			    fieldArray,
			    element,
			    ruptype,
			    fieldArray = [];

			$.each($self.formToArray(), function (key, obj) {
				element = $('[name=\'' + obj.name + '\']', self);

				ruptype = element.attr('ruptype');
				if (ruptype !== undefined) {
					obj.value = element['rup_' + ruptype]('getRupValue');
					fieldArray.push(obj);
				} else {
					fieldArray.push(obj);
				}
			});

			return $.param(fieldArray);
		},
		/**
         * Realiza la serialización de campos del formulario en un objeto json.
         *
         * @function  formToJson
         * @return {string} - Retorna un objeto con el formato {nombre1:valor1, nombre2:valor2…nombreN:valorN}.
         * @example
         * jQuery("#form").rup_form("formToJson");
         */
		formToJson: function formToJson() {
			return form2object(this[0]);
		},
		/**
         * Realiza la serialización de campos del formulario en un query string
         *
         * @function  fieldSerialize
         * @return {string} - Retorna una cadena de texto con el formato nombre1=valor1&nombre2=valor2.
         * @example
         * jQuery("#form .specialFields").rup_form("fieldSerialize");
         */
		fieldSerialize: function fieldSerialize() {
			var a = [];
			this.each(function () {
				var n = $(this).attr('name');
				if (!n) {
					return;
				}
				var v = $(this).rup_form('fieldValue');
				if (v && v.constructor == Array) {
					for (var i = 0, max = v.length; i < max; i++) {
						a.push({
							name: n,
							value: v[i]
						});
					}
				} else if (v !== null && typeof v != 'undefined') {
					a.push({
						name: $(this).attr('name'),
						value: v
					});
				}
			});
			return $.param(a);
		},
		/**
         * Devuelve un array con el valor de los campos indicados.
         *
         * @function  fieldValue
         * @return {string[]} - Retorna una cadena de texto con el formato nombre1=valor1&nombre2=valor2.
         * @example
         * jQuery("#form .specialFields").rup_form("fieldValue");
         */
		fieldValue: function fieldValue() {
			var valuesArray = [],
			    value;
			this.each(function () {
				var ruptype = $(this).attr('ruptype');

				if (ruptype !== undefined) {
					value = $(this)['rup_' + ruptype]('getRupValue');
					valuesArray.push(value);
				} else {
					$.merge(valuesArray, $(this).fieldValue());
				}
			});

			return valuesArray;
		},
		/**
         * Inicializa el formulario con su estado inicial invocando al método reset nativo.
         *
         * @function  resetForm
         * @return {jQuery} - Retorna el propio componente.
         * @example
         * jQuery("#form").rup_form("resetForm");
         */
		resetForm: function resetForm() {
			return this.each(function () {
				$(this).resetForm();
			});
		},
		/**
         * Limpia los elementos del formulario.
         *
         * @function  clearForm
         * @param {boolean} includeHidden - Determina si se deben de limpiar también los elementos hidden que existen en el formulario.
         * @return {jQuery} - Retorna el propio componente.
         * @example
         * // Limpiar los campos del formulario
         * jQuery("#form").rup_form("clearForm");
         * // Limpiar los campos del formulario inlcuyendo los campos hidden
         * jQuery("#form").rup_form("clearForm", true);
         */
		clearForm: function clearForm(includeHidden) {
			return this.each(function () {
				$('input,select,textarea', this).rup_form('clearFields', includeHidden);
			});
		},
		/**
         * Limpia los campos especificados mediante el selector de jQuery.
         *
         * @function  clearFields
         * @param {boolean} includeHidden - Determina si se deben de limpiar también los elementos hidden que existen en el formulario.
         * @return {jQuery} - Retorna el propio componente.
         * @example
         * // Limpiar los campos del formulario
         * jQuery("#form .specialFields").rup_form("clearFields");
         * // Limpiar los campos del formulario inlcuyendo los campos hidden
         * jQuery("#form .specialFields").rup_form("clearFields", true);
         */
		clearFields: function clearFields(includeHidden) {
			return this.each(function () {
				var ruptype = $(this).attr('ruptype');

				if (ruptype === undefined || ruptype !== 'combo') {
					$(this).clearFields(includeHidden);
				} else {
					$(this).rup_combo('clear');
				}
			});
		},
		/**
         * Función de inicialización del componente. Es un método de uso interno. No debería de invocarse de manera directa.
         *
         * @function  configureOptions
         * @param {object} settings - Propiedades de configuración
         */
		configureOptions: function configureOptions(settings) {
			var $self = this,
			    hasFileInputs,
			    beforeSendUserEvent,
			    beforeSubmitUserEvent;

			if (settings.url !== null) {
				$self.attr('action', settings.url);
			}

			hasFileInputs = $('input:file', $self).length > 0;

			if (settings.useJsonIfPossible && !hasFileInputs) {
				settings.contentType = 'application/json';
			} else {
				settings.contentType = 'multipart/form-data';
			}

			// BeforeSend
			beforeSendUserEvent = settings.beforeSend;
			settings.beforeSend = function (xhr, ajaxOptions) {
				var ret = true;
				if ($.isFunction(beforeSendUserEvent)) {
					ret = beforeSendUserEvent.call(this, xhr, ajaxOptions);
				}

				if (ret === false) {
					return false;
				} else if (ret !== 'skip') {
					if (ajaxOptions.contentType !== false && ajaxOptions.contentType.indexOf('application/json') !== -1) {
						var jsonData = $self.rup_form('formToJson');
						if (settings.multimodel !== null) {
							xhr.setRequestHeader('RUP_MULTI_ENTITY', 'true');
							jsonData['rupEntityMapping'] = settings.multimodel;
						}
						if (ajaxOptions.extraData !== undefined && ajaxOptions.extraData !== null) {
							$.extend(jsonData, ajaxOptions.extraData);
						}
						ajaxOptions.data = $.toJSON(jsonData);
					}
				}
			};

			// BeforeSubmit
			beforeSubmitUserEvent = settings.beforeSubmit;
			settings.beforeSubmit = function (arr, $form, options) {
				var httpMethod, error_user, hasFileInputs;
				if ($.isFunction(beforeSubmitUserEvent)) {
					if (beforeSubmitUserEvent.call(this, arr, $form, options) === false) {
						return false;
					}
				}

				hasFileInputs = jQuery('input:file', $form).length > 0;
				// Implementacion para realizar la emulacion de xhr al utilizar iframes
				if (!$.rup.browser.xhrFileUploadSupport && hasFileInputs || options.iframe === true) {

					// Configuracion necesaria para permitir con iframes el uso de metodos http diferentes a GET o POST
					httpMethod = settings.type !== undefined ? settings.type : options.type;
					if ($.inArray(httpMethod.toUpperCase(), $.rup.IFRAME_ONLY_SUPPORTED_METHODS) === -1) {
						options.extraData = $.extend({}, options.extraData, {
							'_method': httpMethod.toUpperCase()
						});
					}

					//Se valida la presencia de portal y, llegados al caso, se adecuan las llamadas ajax para trabajar con portales
					options.url = $.rup_utils.setNoPortalParam(options.url);
					// Envio del parametro emulate_iframe_http_status para activar la emulacion en el lado servidor
					options.extraData = $.extend({}, options.extraData, {
						'_emulate_iframe_http_status': 'true'
					});
					options.url = options.url + (options.url.match('\\?') === null ? '?' : '&') + '_emulate_iframe_http_status=true';

					// Callback de error por defecto a ejecutar cuando se produzca un error al utilizar la emulacion
					error_user = options.error;
					options.error = function (xhr, textStatus, errorThrown) {
						var errorText = $.rup.rupAjaxDefaultError(xhr, textStatus, errorThrown);

						// Si se ha producido un error de los tratados lo mostramos
						if (error_user != null) {
							$(error_user(xhr, textStatus, errorThrown));
						} else {
							if (errorText) {
								$.rup.showErrorToUser(errorText);
							}
						}
					};
				}
			};

			settings.formValidationRequired = settings.validate !== undefined;

			// Configruacion de las validaciones
			if (settings.formValidationRequired) {
				if (settings.error === undefined) {
					settings.error = function (a, b, c, d) {
						try {
							var json = jQuery.parseJSON(a.responseText);
							$self.validate().invalid = json.rupErrorFields;
							$self.validate().submited = json.rupErrorFields;
							$self.validate().showErrors(json.rupErrorFields);
							if (json.rupFeedback !== undefined && $self.validate().settings.feedback !== undefined) {
								$self.validate().settings.feedback.rup_feedback('set', $.rup_utils.printMsg(json.rupFeedback.message), json.rupFeedback.style !== undefined ? json.rupFeedback.style : null);
							}
						} catch (ex) {
							$self.validate().settings.feedback.rup_feedback('set', a.responseText, 'error');
						}
					};
				}
				settings.validate.submitHandler = function (form) {
					jQuery(form).ajaxSubmit($(form).data('ajaxSettings'));
				};

				settings.validate.feedback = settings.feedback;
			}
			$self.data('ajaxSettings', settings);
			$self.data('settings', settings);
		}
	});

	//********************************
	// DEFINICIÓN DE MÉTODOS PRIVADOS
	//********************************
	$.fn.rup_form('extend', {});

	$.fn.rup_form('extend', {
		/**
         * Función de inicialización del componente.
         *
         * @function  _init
         * @private
         * @param {object} args - Propiedades de configuración.
         */
		_init: function _init(args) {
			var $self = this,
			    realizarValidacion,
			    settings,
			    ajaxFormSettings = {},
			    userSettings = {};

			// Determinamos si se ha introducido configuracion para el componente validacion.
			// Settings de configuracion
			settings = $.extend(true, {}, $.fn.rup_form.defaults, args[0]);
			// Anadimos al formulario el class rup_form para identificarlo como componente formulario.
			$self.addClass('rup_form');
			$self.attr('ruptype', 'form');

			$self.rup_form('configureOptions', settings);
			// En caso de que no sehaya configurado el componente validacion se realiza la llamada al plugin jquery.form.
			if (settings.formValidationRequired) {
				$self.rup_validate(settings.validate);
			} else {
				$self.ajaxForm(settings);
			}
		}
	});

	//*******************************************************
	// DEFINICIÓN DE LA CONFIGURACION POR DEFECTO DEL PATRON
	//*******************************************************

	/**
     * Función de callback que será invocada antes de realizarse la serialización del formulario.
     *
     * @callback jQuery.rup_form~beforeSerialize
     * @param {jQuery} $form - Referencia del objeto jQuery del formulario.
     * @param {object} options - Opciones de configuración con las que se ha inicializado el componente.
     * @return {boolean} - En caso de devolver false se cancela el envío del formulario.
     * @example
     * $("#form").rup_form({
     *  beforeSerialize: function($form, options) { ... }
     * });
     */

	/**
     * Función de callback que será invocada antes de realizarse el envío del formulario.
     *
     * @callback jQuery.rup_form~beforeSubmit
     * @param {object[]} arr - Array que contiene la información introducida en el formulario. El array tiene el siguiente formato : [ { name: 'username', value: 'jresig' }, { name: 'password', value: 'secret' } ]
     * @param {jQuery} $form - Referencia del objeto jQuery del formulario.
     * @param {object} options - Opciones de configuración con las que se ha inicializado el componente.
     * @return {boolean} - En caso de devolver false se cancela el envío del formulario.
     * @example
     * $("#form").rup_form({
     *  beforeSubmit: function(arr, $form, options) { ... }
     * });
     */

	/**
     * Función de callback que será invocada cuando se produzca un error.
     *
     * @callback jQuery.rup_form~error
     * @example
     * $("#form").rup_form({
     *  error: function() { ... }
     * });
     */

	/**
     * Función de callback que será invocado cuando se reciba la respuesta del formulario.
     *
     * @callback jQuery.rup_form~suceess
     * @param {string} responseText - Texto identificador de la respuesta obtenida.
     * @param {string} statusText - Código de respuesta http.
     * @param {object} xhr - Objeto xhr con la respuesta enviada del servidor.
     * @param {jQuery} $form - Referencia jQuery al componente formulario.
     * @example
     * $("#form").rup_form({
     *  suceess: function(responseText, statusText, xhr, $form) { ... }
     * });
     */

	/**
     * Función de callback que será invocado cuando se reciba la respuesta del formulario.
     *
     * @callback jQuery.rup_form~uploadProgress
     * @param {Event} event - Objeto Event procedente del navegador.
     * @param {Integer} position - Numero que determina el contenido enviado.
     * @param {Integer} total - Numero que identifica el total del contenido a enviar.
     * @param {Integer} percentComplete - Numero que identifica el porcentaje actual completado en el proceso de envío.
     * @example
     * $("#form").rup_form({
     *  uploadProgress: function(event, position, total, percentComplete) { ... }
     * });
     */

	/**
    * Opciones por defecto de configuración del componente.
    * @name defaults
    *
    * @property {jQuery.rup_form~beforeSerialize} [beforeSerialize=null] - Función de callback que será invocada antes de realizarse la serialización del formulario. Permite la modificación de los datos del formulario antes de que estos sean recuperados para su procesado por el componente.
    * @property {jQuery.rup_form~beforeSubmit} [beforeSubmit=null] - Función de callback que será invocada antes de realizarse el envío del formulario. Permite acceder a la información que será enviada al formulario. En caso de retornar false no se realizará en envío.
    * @property {boolean} [clearForm=null] - Propiedad booleana que determina si el formulario debe de limpiarse después de realizar el envío.
    * @property {object} [data] - Mediante esta propiedad es posible especificar parámetros extra que sean enviados alservidor.
    * @property {string} [dataType] - Tipo de datos esperados en la respuesta. Los valores posibles son null, xml, json y script.
    * @property {jQuery.rup_form~error} [error] - Función de callback que será invocada cuando se produzca un error.
    * @property {boolean} [forceSync=false] - Propiedad booleana. En caso de ser true elimina la corta espera que se produce antes de enviar el formulario cuando se envían ficheros o se utiliza la opción de iframe. La espera se utiliza para permitir al navegador actualizar modificaciones realizadas en el DOM antes de que se realice el
 envío de los datos.
    * @property {boolean} [iframe=false] - Determina si el formulario debe de ser enviado siempre mediante un iframe.
    * @property {string} [iframeSrc] - Propiedad de texto que deberá ser utlizada siempre en conjunción con la propiedad iframe. Por defecto, about:blank. Por defecto para páginas que utlicen el protocolo https, javascript:false.
    * @property {string} [iframeTarget=null] - Identifica el iframe que será utilizado como target en la respuesta en los envíos de ficheros. Por defecto, el componente creará un iframe temporal para capturar la respuesta del envío de ficheros.
    * @property {boolean | object} [multimodel=false] - Permite especificar la configuración que se deberá de aplicar a la hora de realizar el envío de varias entidades en la misma petición. La configuración de este parámetro se detalla en el apartado 9.2.
    * @property {boolean} [replaceTarget=false] - Opcionalmente se utililiza junto con la opción target. En caso de ser true el elemento identificado en la opción target será reemplazado. En caso de ser false solo su contenido será reemplazado.
    * @property {boolean} [resetForm=false] - Propiedad booleana que determina si el formulario debe ser inicializado al realizarse el envío del mismo.
    * @property {bolean} [semantic=false] - Propiedad booleana que determina si los campos del formulario deben ser enviado en estricto orden semántico. Por defecto la serialización normal del formulario se realiza en orden semántico exceptuando los campos img.
    * @property {jQuery.rup_form~suceess} [suceess] - Método callback que será invocado cuando se reciba la respuesta del formulario.
    * @property {string | jQuery | Element} [target] - Identifica los elementos de la página que deberán ser actualizados con la respuesta del servidor. El target puede ser indicado mediante un selector de jQuery, un objeto de jQuery o un objeto DOM.
    * @property {string} [type] - Detemina el método con el que se enviará el formulario, GET o POST. Por defecto el valor de la propiedad method indicada en el formulario o GET en caso de no encontrarse.
    * @property {jQuery.rup_form~uploadProgress} [uploadProgress=null] - Método que será invocado con información de progreso del envío del formulario (en caso de estar soportado por el navegador).
    * @property {string} [url] - URL a la cual se realizará en envío del formulario. Por defecto el valor indicado en la propiedad action del formulario.
    * @property {boolean} [useJsonIfPossible=true] - Mediante este parámetro se especifica al componente que debe de utilizar el formato application/json como prioridad (siempre que sea posible) al realizar el envío del formulario.
    */

	$.fn.rup_form.defaults = {
		ajaxForm: null,
		feedback: null,
		multimodel: null,
		useJsonIfPossible: true // En caso de ser posible realizar en envío mediante json se enviarán los datos en este formato.
	};
});
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))

/***/ }),
/* 14 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function(jQuery) {var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*!
 * Copyright 2016 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 */

/**
 * El objetivo principal del componente es mejorar la experiencia del usuario a la hora de generar informes mediante la presentación de diálogos de espera.
 *
 * @summary Componente RUP Report.
 * @module rup_report
 * @example
 * var properties={
 *   // Propiedades de configuración
 * };
 *
 * $.rup_report(properties);
 */

/*global define */
/*global jQuery */

(function (factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(2), __webpack_require__(194)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		factory(jQuery);
	}
})(function ($) {

	//*****************************************************************************************************************
	// DEFINICIÓN BASE DEL PATRÓN (definición de la variable privada que contendrá los métodos y la función de jQuery)
	//*****************************************************************************************************************


	var rup_report = {};

	//Se configura el arranque de UDA para que alberge el nuevo patrón
	$.extend($.rup.iniRup, $.rup.rupObjectConstructor('rup_report', rup_report));

	//********************************
	// DEFINICIÓN DE MÉTODOS PÚBLICOS
	//********************************

	$.rup_report('extend', {});

	//********************************
	// DEFINICIÓN DE MÉTODOS PRIVADOS
	//********************************

	$.rup_report('extend', {
		/**
     * Función de inicialización del componente.
     *
     * @name _init
     * @function
     * @private
     * @param {object} args - Propiedades de configuración.
     */
		_init: function _init(args) {
			if (args.length > 1) {
				$.rup.errorGestor($.rup.i18n.base.rup_global.initError + $(this).attr('id'));
			} else {
				//Se recogen y cruzan las paremetrizaciones del objeto
				var self = this,
				    settings = $.extend(true, {}, $.rup_report.defaults, args[0]),

				//Objetos componente (params)
				buttons = settings.buttons,
				    defaultDialog = settings.dialog,
				    customDialog = settings.customDialog,

				//Contenedor de botones
				$container = $.find('[id=\'' + settings.appendTo + '\']');

				//Existe capa contenedora ?
				if ($.isEmptyObject($container)) {
					alert('No existe objeto al que añadir el componente');
					return false;
				}
				$container = $($container[0]);

				//Guardar settings
				$container.data('report', settings);

				//Añadir dialogo por defecto
				var $defaultDialog_wait = $('<div />').attr('id', 'reportFileWait').attr('title', defaultDialog.wait.title).text(defaultDialog.wait.msg).addClass('rup_report').hide()
				//progressbar
				.append($('<div />').addClass('ui-progressbar ui-progressbar-value ui-corner-left ui-corner-right')),
				    $defaultDialog_error = $('<div />').attr('id', 'reportFileError').attr('title', defaultDialog.error.title).text(defaultDialog.error.msg).addClass('rup_report').hide(),
				    $defaultDialog = $('<div />').attr('id', 'rup_report_dialogsContainer').append($defaultDialog_wait).append($defaultDialog_error);
				$container.after($defaultDialog);
				//Guardar datos dialogo por defecto
				defaultDialog['waitDiv'] = 'reportFileWait';
				defaultDialog['errorDiv'] = 'reportFileError';

				//El contenedor es un mButton
				var isMButton = false,
				    $mbutton;
				if ($container.hasClass('rup-toolbar_menuButtonContainer')) {
					$mbutton = $('[id=\'' + $container.attr('id').substring('8') + '\']');
					$container = $mbutton.parents('.rup-toolbar');
					isMButton = true;
					if ($.grep(buttons, function (object, index) {
						return object.buttons !== undefined;
					}).length > 0) {
						alert('No se pueden añadir MButtons a un contenedor MButton');
						return false;
					}
				}

				//Recorrer los botones
				var errors = [];
				$.each(buttons, function (index, object) {
					if (object.buttons !== undefined) {
						//MBUTTON
						object['click'] = $container.showMButton;
						$mbutton = $container.addMButton(object, object['json_i18n']);
						$container.addButtonsToMButton(object.buttons, $mbutton, object['json_i18n']);
						//add click
						$.each(object.buttons, function (index, object) {
							self._checkButton(object, errors);
							self._configureButton(object, defaultDialog, customDialog, settings);
						});
					} else {
						//BUTTON
						if (!isMButton) {
							$container.addButton(object, object['json_i18n']);
							object['id'] = $container.attr('id') + '##' + (object.id ? object.id : object.i18nCaption);
						} else {
							//Añadir botones a un MButton ya existente
							$container.addButtonsToMButton(new Array(object), $mbutton, object['json_i18n']);
							//Mover el botón al final
							$mbuttonDiv = $('[id=\'mbutton_' + $mbutton.attr('id') + '\']');
							$mbuttonDiv.find('li:first').appendTo($mbuttonDiv.children('ul'));
						}
						//add click
						self._checkButton(object, errors);
						self._configureButton(object, defaultDialog, customDialog, settings);
					}
				});

				if (errors.length > 0) {
					var txtErrors = '';
					for (var i = 0; i < errors.length; i++) {
						txtErrors += errors[i] + '<br/>';
					}
					alert(txtErrors);
				}
			}
		},
		_checkButton: function _checkButton(button, errors) {
			var buttonId = button.id.substring(button.id.lastIndexOf('##') + 2);
			//Tiene URL?
			if (button.url === undefined) {
				errors.push(buttonId + ': no tiene URL asociada');
			}
			//Existe grid asociado para columnas ?
			if (button.columns !== undefined) {
				//Existe grid asociado ?
				var $grid = $.find('#' + button.columns.grid);
				if ($.isEmptyObject($grid)) {
					errors.push(buttonId + ': no existe el Grid asociado');
				}
			}
		},
		_configureButton: function _configureButton(button, defaultDialog, customDialog, settings) {
			var self = this,
			    dialog = {};
			$.extend(dialog, defaultDialog); //Copiar el dialogo de por defecto
			//isInline a false por defecto
			button.isInline = button.isInline === undefined ? false : button.isInline;

			//Si no es inLine
			if (!button.isInline) {
				$('[id=\'' + button.id + '\']').on('click', function () {

					//Ocultar MButton
					var $container = $(this).parents('div.rup-toolbar_menuButtonContainer');
					if ($container.length > 0) {
						$container.showMButton();
						$container.removeClass('rup-toolbar_menuButtonSlided');
					}

					//Controlar columnas
					var data = {};
					if (button.columns !== undefined) {
						//GridParams
						var $grid = $($.find('#' + button.columns.grid)[0]);
						if (jQuery.isFunction(settings.fncGetGridParam)) {
							data = jQuery.proxy(settings.fncGetGridParam, $grid)();
						} else {
							data = $grid.jqGrid('getGridParam', 'postData');
						}
						data['columns'] = $.toJSON(self._getColumns($grid, button.columns));
					}

					//Dialogo propio?
					var standarDialog = true;
					if (button.customDialog !== undefined) {
						//Buscar el dialogo correspondiente
						var actualDialog = customDialog[button.customDialog];

						/** WAIT **/
						//Sobreescritura del defaultDialog-wait
						if (actualDialog.waitDiv === undefined) {
							dialog.wait = actualDialog.wait;
							//Dialogo propio completo
						} else {
							dialog.waitDiv = actualDialog.waitDiv;
							$('#' + dialog.waitDiv).addClass('rup_report');
						}

						/** ERROR **/
						//Sobreescritura del defaultDialog-error
						if (actualDialog.errorDiv === undefined) {
							dialog.error = actualDialog.error;
							//Dialogo propio completo
						} else {
							dialog.errorDiv = actualDialog.errorDiv;
							$('#' + dialog.errorDiv).addClass('rup_report');
						}

						dialog.successCallback = actualDialog.successCallback;
						dialog.failCallback = actualDialog.failCallback;
					}

					//Dialogo de espera
					var $reportFileWait = $('#' + dialog.waitDiv);
					$reportFileWait.rup_dialog({
						type: $.rup.dialog.TEXT,
						autoOpen: false,
						modal: true,
						resizable: false,
						close: function close(event, ui) {
							if ($.rup.browser.isIE) {
								//IE
								document.execCommand('Stop');
							} else {
								//Netscape/Mozilla/Firefox
								window.stop();
							}
						}
					});
					if (standarDialog) {
						//Titulo
						$reportFileWait.rup_dialog('setOption', 'title', dialog.wait.title);
						//Contenido
						var content = $reportFileWait.html().split($reportFileWait.text()),
						    html = '';
						for (var i = 0; i < content.length; i++) {
							if (content[i] === '') {
								html += dialog.wait.msg;
							} else {
								html += content[i];
							}
						}
						$reportFileWait.html(html);
					}
					$reportFileWait.rup_dialog('open');

					//Lanzar petición
					$.fileDownload($.rup_utils.setNoPortalParam(button.url), {
						httpMethod: 'POST',
						data: jQuery.rup_utils.unnestjson(data),
						successCallback: function successCallback(url) {
							if (dialog.successCallback !== undefined) {
								dialog.successCallback();
							}
							$reportFileWait.rup_dialog('close');
						},
						failCallback: function failCallback(responseHtml, url) {
							$reportFileWait.rup_dialog('close');
							var $reportFileError = $('#' + dialog.errorDiv);
							$reportFileError.rup_dialog({
								type: $.rup.dialog.TEXT,
								autoOpen: false,
								modal: true,
								resizable: false
							});
							if (standarDialog) {
								//Titulo
								$reportFileError.rup_dialog('setOption', 'title', dialog.error.title);
								//Contenido
								$reportFileError.rup_dialog('setOption', 'message', dialog.error.msg);
							}
							$reportFileError.rup_dialog('open');

							if (dialog.failCallback !== undefined) {
								dialog.failCallback(responseHtml, url);
							}
						}
					});
					return false;
				});
			} else {
				$('[id=\'' + button.id + '\']').on('click', function () {
					window.open(button.url + '?isInline=true', '_blank');
				});
			}
		},
		_getColumns: function _getColumns($grid, columns) {
			//Preparar datos
			var colModel = $grid.jqGrid('getGridParam', 'colModel'),
			    colNames = $grid.jqGrid('getGridParam', 'colNames'),
			    colNumber = colNames.length,
			    columnsArray = [],
			    customNames = columns.customNames,
			    hidden = columns.hidden === true ? true : false;

			//Todas las columnas
			if (customNames === undefined) {
				for (var i = 0; i < colNumber; i++) {
					//Omitir columna multiselección
					if (colNames[i].indexOf('type=\'checkbox\'') !== -1) {
						continue;
					}
					//Obtener columna si se requieren todas o si solo se quieren visibles + es visible
					if (hidden || !hidden && colModel[i].hidden === false) {
						var column = [];
						column.push(colModel[i].name);
						column.push(colNames[i]);
						columnsArray.push(column);
					}
				}
				//Columnas por nombre
			} else {
				for (var i = 0; i < colNumber; i++) {
					if ($.inArray(colModel[i].name, customNames) !== -1) {
						var column = [];
						column.push(colModel[i].name);
						column.push(colNames[i]);
						columnsArray.push(column);
					}
				}
			}
			return columnsArray;
		}
	});

	//*******************************************************
	// DEFINICIÓN DE LA CONFIGURACION POR DEFECTO DEL PATRON
	//*******************************************************

	$.rup_report.defaults = {
		fncGetGridParam: null,
		dialog: {
			wait: {
				title: $.rup.i18nParse($.rup.i18n.base, 'rup_report.waitTitle'),
				msg: $.rup.i18nParse($.rup.i18n.base, 'rup_report.waitMsg')
			},
			error: {
				title: $.rup.i18nParse($.rup.i18n.base, 'rup_report.errorTitle'),
				msg: $.rup.i18nParse($.rup.i18n.base, 'rup_report.errorMsg')
			}
		}
	};

	/**
   * Opciones por defecto de configuración del componente.
   *
   * @name options
   *
   * @property {string} appendTo - Identificador del elemento al que se añadirá el botón o botones. Puede ser una capa, una botonera o un mbutton. En el caso de ser un mbutton sólo podrán añadirse botones, no mbuttons.
   * @property {array<module:rup_report~button>} buttons - Array de botones a añadir. Su declaración es similar a los del componente rup.toolbar pero tienen algunos parámetros extra
   * @property {module:rup_report~dialog} dialog - Objeto para sobrescribir los literales por defecto del diálogo del componente y asociar funciones de callback
   * @property {module:rup_report~customDialog} customDialog - Objeto para definir los diálogos propios definidos por el usuario. Puede modificar simplemente los literales para un botón determinado o puede definir sus propias capas para sus diálogos completamente personalizados
   */

	/**
   * @typedef module:rup_report~button
   * @property {string} 	i18nCaption - Texto que se mostrará en el botón. Obtenido del fichero de literales de la aplicación.
   * @property {string} 	json_i18n - Objeto JSON del que se obtienen los literales a mostrar.
   * @property {string} css - Define el estilo a aplicar. Se utilizará para mostrar imágenes a la izquierda del botón.
   * @property {function} click - Función javascript que se ejecutará cuando se pulse el botón al que se ha asociado. La función podrá recibir un parámetro “event” que contendrá el identificador y el texto del botón y se accederá a ellos mediante la sentencia “event.data.id” y “event.data.caption” respectivamente.
   * @property {array<module:rup_report~button>} buttons - Array para definir sub-botones con lo que la definición se convierte en un mbutton.
   * @property {string} url - Ruta al Controller encargado de generar el informe
   * @property {module:rup_report~columns} columns - Objeto que define si se van a enviar los datos de las columnas (nombres y posiciones):
   * @property {string} 	customDialog - Identificador del dialogo propio definido en el componente
   * @property {boolean} 	[isInline=false] - Indica que el informe se genera en una pestaña nueva del navegador. Sólo soportado en PDF
   */

	/**
   * Objeto que define si se van a enviar los datos de las columnas (nombres y posiciones):
   * @typedef module:rup_report~columns
   * @property {string} grid - identificador del grid del que obtener las columnas.
   * @property {array} customNames - array que indica el nombre de las columnas a incluir (atributo name del grid).
   * @property {boolean} [hidden=false] - Indica si se desean incluir las columnas ocultas.
   */

	/**
   *  Objeto para sobrescribir los literales por defecto del diálogo del componente y asociar funciones de callback
   *  @typedef module:rup_report~dialog
   *  @property {object} wait - Objeto para definir el diálogo de espera mientras se genera el informe
   *  @property {string} wait.title - Título del diálogo
   *  @property {string} wait.msg - mensaje del diálogo
   *  @property {object} error - objeto para definir el diálogo que se muestra si se produce un error:
   *  @property {string} error.title - Título del diálogo
   *  @property {string} error.msg - mensaje del diálogo
   *  @property {function} successCallback - Función que se ejecuta cuando se genera correctamente el informe.
   *  @property {fucntion} failCallback - Función que se ejecuta cuando no se genera correctamente el informe
   */

	/**
   *  Objeto para definir los diálogos propios definidos por el usuario. Puede modificar simplemente los literales para un botón determinado o puede definir sus propias capas para sus diálogos completamente personalizados
   *  @typedef module:rup_report~customDialog
   *  @property {string} nombre - identificador del diálogo que se define en el botón
   *  @property {function} successCallback - Función que se ejecuta cuando se genera correctamente el informe.
   *  @property {fucntion} failCallback - Función que se ejecuta cuando no se genera correctamente el informe
   *  @property {object} wait - Objeto para definir el diálogo de espera mientras se genera el informe
   *  @property {string} wait.title - Título del diálogo
   *  @property {string} wait.msg - mensaje del diálogo
   *  @property {object} error - objeto para definir el diálogo que se muestra si se produce un error:
   *  @property {string} error.title - Título del diálogo
   *  @property {string} error.msg - mensaje del diálogo
   *  @property {string} waitDiv - Identificador de la tabla para el diálogo de espera.
   *  @property {string}  errorDiv - Identificador de la capara para el diálogo de error    identificador de la capara para el diálogo de error
   */
});
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))

/***/ }),
/* 15 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/**
  * Encargado de aplicar la propiedad sticky a los componentes
  *
  * @summary 		Componente RUP Sticky
  * @module			"rup.sticky"
  * @version     1.0.0
  * @license
  * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
  * Solo podrá usarse esta obra si se respeta la Licencia.
  * Puede obtenerse una copia de la Licencia en
  *
  *      http://ec.europa.eu/idabc/eupl.html
  *
  * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
  * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
  * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
  * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
  * que establece la Licencia.
  * @copyright   Copyright 2018 E.J.I.E., S.A.
  *
  */

/*global define */
/*global jQuery */

(function (factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(2)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		factory(jQuery);
	}
})(function ($) {

	//****************************************************************************************************************
	// DEFINICIÓN BASE DEL PATRÓN (definición de la variable privada que contendrá los métodos y la función de jQuery)
	//****************************************************************************************************************

	var rup_sticky = {};

	//Se configura el arranque de UDA para que alberge el nuevo patrón
	$.extend($.rup.iniRup, $.rup.rupSelectorObjectConstructor('rup_sticky', rup_sticky));

	//*******************************
	// DEFINICIÓN DE MÉTODOS PÚBLICOS
	//*******************************
	$.fn.rup_sticky('extend', {
		/**
     * Gestiona las inicializaciones de componentes en modo 'sticky'
     *
     * @name stickyManager
  		* @function
  		* @since UDA 3.3.0 // Sticky 1.0.0
  	*
     */
		stickyManager: function stickyManager() {
			var self = this;
			var settings = $.extend({}, $.fn.rup_sticky.defaults);

			if (settings.sticky_nav) {
				self._navbarSticky();
			}

			if (settings.sticky_wizard) {
				self._wizardSticky();
			}
		}
	});

	//*******************************
	// DEFINICIÓN DE MÉTODOS PRIVADOS
	//*******************************

	$.fn.rup_sticky('extend', {
		/**
  	* Aplica el modo 'sticky' al navbar
  	*
     * @name _navbarSticky
  		* @function
  		* @since UDA 3.3.0 // Sticky 1.0.0
  	*
  	*/
		_navbarSticky: function _navbarSticky() {
			var changed = false;

			var headerOuterHeight = $('header').length != 0 ? $('header').outerHeight(true) : 0;
			var headerSize = $('header').length != 0 ? headerOuterHeight - $('header').offset().top : 0;

			var headerNavSize = headerOuterHeight + $('nav').outerHeight(true);

			var headerOuterHeight = $('header').outerHeight();

			window.scrollHeight = 0;
			$(window).scroll(function () {
				headerOuterHeight = $('header').outerHeight();

				if ($(this).scrollTop() < headerOuterHeight) {
					changed = false;
					if ($('.rup-navbar.navbar').hasClass('rup-navbar-sticky')) {
						$('.rup-navbar.navbar').removeClass('rup-navbar-sticky');
					}
				} else if ($(this).scrollTop() >= headerOuterHeight) {
					changed = true;
					$('.rup-navbar.navbar').addClass('rup-navbar-sticky');
				}
			});

			// El reescalado de la pantalla navega al inicio del contenido
			$(window).resize(function () {
				$.rup_utils.swing2Top();
			});
		},

		/**
  	* Aplica el modo 'sticky' al menu del wizard
  	*
     * @name _wizardSticky
  		* @function
  		* @since UDA 3.3.0 // Sticky 1.0.0
  	*
  	*/
		_wizardSticky: function _wizardSticky() {
			var headerOuterHeight = $('header').outerHeight();

			$(window).scroll(function () {
				headerOuterHeight = $('header').outerHeight();

				if ($(this).scrollTop() < headerOuterHeight * 2) {
					if ($('.rup-wizard_stepsDescContainer').hasClass('rup-wizard_stepsDescContainer-sticky')) {
						$('.rup-wizard_stepsDescContainer').removeClass('rup-wizard_stepsDescContainer-sticky');
					}
				} else if ($(this).scrollTop() >= headerOuterHeight * 2) {
					$('.rup-wizard_stepsDescContainer').addClass('rup-wizard_stepsDescContainer-sticky');
				}
			});
		}
	});

	//******************************************************
	// DEFINICIÓN DE LA CONFIGURACION POR DEFECTO DEL PATRON
	//******************************************************
	$.fn.rup_sticky.defaults = {
		sticky_nav: true,
		sticky_wizard: true
	};

	// Inicializamos la gestión de las propiedades 'sticky'
	$.fn.rup_sticky('stickyManager');
});

/***/ }),
/* 16 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*!
 * Copyright 2016 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 */

/**
 * Se les presenta a los usuarios una barra de botones con diversas funcionalidades relacionadas a elementos de la página. Gracias a este componente se presentan, ordenan y agrupan las distintas funcionalidades gestionadas por las aplicaciones.
 *
 * @summary Componente RUP Toolbar.
 * @module rup_toolbar
 * @example
 * var properties = {
 *	width: 1000,
 *	buttons:[
 *		{i18nCaption:"buscar", css:"buscar", click: handlerBoton },
 *       {i18nCaption:"editar", css:"editar", click: handlerMButtons},
 *		{id : "mbuton2", i18nCaption:"ficheros", buttons:[
 *		    {i18nCaption:"DLL", css:"dll", click: handlerMButtons },
 *			{i18nCaption:"DOC", css:"doc", click: handlerMButtons},
 *			{i18nCaption:"EXE", css:"exe", click: handlerMButtons},
 *			{i18nCaption:"GIF", css:"gif", click: handlerMButtons},
 *		]},
 *		{i18nCaption:"filtrar", css:"filtrar", click: handlerMButtons}
 *	]
 * };
 *
 * $("#idToolbar").rup_toolbar(properties);
 */

/*global define */
/*global jQuery */

(function (factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(2), __webpack_require__(23)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		factory(jQuery);
	}
})(function ($) {

	$.rup_toolbar = $.rup_toolbar || {};
	$.extend($.rup_toolbar, {
		extend: function extend(methods) {
			$.fn.extend(methods);
		}
	});

	/**
     * Función de callback a ejecutar cuando se realiza un click sobre un botón de la botonera.
     *
     * @callback module:rup_toolbar~buttonClick
     * @param {Event} event - Objeto correspondiente al evento click realizado sobre el botón.
     * @param {string} event.data.id - Identificador del botón que ha lanzado el evento.
     * @param {string} event.data.caption - Texto del botón que ha lanzado el evento.
     * @example
     * var newButton = {
     *   i18nCaption:"editButton",
     *   click: function(event){
     *
     *   }
     * };
     *
     * $("#idToolbar").rup_toolbar("addButton", newButton);
     */

	/**
     * Definición del tipo de objeto que representa un botón de la botonera.
     *
     * @typedef {Object} module:rup_toolbar~button
     * @property {string} [id] - Identificador único del botón con menú.
     * @property {string} [i18nCaption] - Texto que se mostrará en el botón. Se indica el key del literar que se obtendrá de los ficheros de internacionalización correspondientes.
     * @property {string} [css] - Define el estilo a aplicar. Se utilizará para mostrar imágenes a la izquierda del botón.
     * @property {boolean} [right=false] - Determina si el botón aparece alineado a la derecha (true) o a la izquierda (false).
     * @property {module:rup_toolbar~buttonClick} click - Función javascript que se ejecutará cuando se pulse el botón al que se ha asociado.
     */

	/**
     * Definición del tipo de objeto que representa un mButton de la botonera.
     *
     * @typedef {Object} module:rup_toolbar~mButton
     * @property {string} id - Identificador único del botón con menú.
     * @property {string} [i18nCaption] - Texto que se mostrará en el botón. Se indica el key del literar que se obtendrá de los ficheros de internacionalización correspondientes.
     * @property {string} [css] - Define el estilo a aplicar. Se utilizará para mostrar imágenes a la izquierda del botón.
     * @property {boolean} [right=false] - Determina si el botón aparece alineado a la derecha (true) o a la izquierda (false).
     * @property {module:rup_toolbar~button[]} buttons - Botones que va a incluir el botón con menú.
     */

	//Variable interna del toolbar para gestión de MButtons
	$.rup_toolbar.showingMB = null;

	$.rup_toolbar.extend({
		/**
         * Añade un nuevo botón a la botonera. Las características del botón se especifican en los parámetros del método.
         *
         * @name addButton
         * @function
         * @property {module:rup_toolbar~button} obj - Objeto que define el botón a añadir.
         * @property {object} json_i18n - Objeto json con los recursos de i18n.
         * @example
         * var button = {
         *   i18nCaption:"editButton",
         *   css:"editar"
         * };
         *
         * $("#idToolbar").rup_date("addButton", button);
         */
		addButton: function addButton(obj, json_i18n) {
			return $.proxy(this[0]._ADAPTER.addButton, this)(obj, json_i18n);
		},
		/**
         * Añade un nuevo menu button a la botonera. Las características del mButton se especifican en los parámetros del método.
         *
         * @name addMButton
         * @function
         * @property {module:rup_toolbar~mButton} obj - Objeto que define el mButton a añadir.
         * @property {object} json_i18n - Objeto json con los recursos de i18n.
         * @example
         * var mButton = {
         *   id: "mbuton1", i18nCaption:"otros", buttons:[
         *	    {i18nCaption:"nuevo", css:"nuevo", click: handlerMButtons},
         *       {i18nCaption:"editar", css:"editar", click: handlerMButtons},
         *       {i18nCaption:"cancelar", css:"cancelar", click: handlerMButtons}
         *   ]
         * };
         *
         * $("#idToolbar").rup_date("addMButton", mButton);
         */
		addMButton: function addMButton(obj, json_i18n) {
			return $.proxy(this[0]._ADAPTER.addMButton, this)(obj, json_i18n);
		},

		/**
         * Se añaden un conjunto de botones a un menu button existente.
         *
         * @name addButtonsToMButton
         * @function
         * @property {module:rup_toolbar~button[]} buttons - Array de botones a añadir al menu button.
         * @property {string} menuButton - Identificador del menu button al que vamos a añadir los botones.
         * @property {object} json_i18n - Objeto json con los recursos de i18n.
         * @example
         * var buttons = [
         *	    {i18nCaption:"nuevo", css:"nuevo", click: handlerMButtons},
         *       {i18nCaption:"editar", css:"editar", click: handlerMButtons},
         *       {i18nCaption:"cancelar", css:"cancelar", click: handlerMButtons}
         * ];
         *
         * $("#idToolbar").rup_date("addMButton", "mbuton1", buttons);
         */

		addButtonsToMButton: function addButtonsToMButton(buttons, menuButton, json_i18n) {
			return $.proxy(this[0]._ADAPTER.addButtonsToMButton, this)(buttons, menuButton, json_i18n);
		},

		/**
         * Se muestra la capa con los mButtons
         *
         * @function showMButton
         * @example
         * $("#idToolbar").rup_date("showMButton");
         */
		showMButton: function showMButton() {
			//Muestra la capa con los mbuttons

			var self = $(this),
			    top = self.offset().top + self.getTotalHeight(),
			    showingMB = $.rup_toolbar.showingMB,
			    actualMB = this.id;

			if (showingMB === actualMB) {
				$("ul[id*='" + showingMB + "']").slideUp('fast');
				self.removeClass('rup-toolbar_menuButtonSlided');
				showingMB = null;
				//Se pulsa sobre otro elemento
			} else {
				$("ul[id*='" + showingMB + "']").slideUp('fast');
				$("ul[id*='" + actualMB + "']").slideDown('fast');
				$('[id=\'' + showingMB + '\']').removeClass('rup-toolbar_menuButtonSlided');
				self.addClass('rup-toolbar_menuButtonSlided');
				showingMB = actualMB;
			}

			$.rup_toolbar.showingMB = showingMB;

			return false;
		},
		/**
         * Desabilita el botón correspondiente al identificador indicado.
         *
         * @function  disableButton
         * @param {string} id - Identificador del botón que se desea deshabilitar.
         * @example
         * $("#idToolbar").rup_date("disableButton","idEditButton");
         */
		disableButton: function disableButton(id) {
			if (id.indexOf(this.attr('id')) === -1) {
				id = this.attr('id') + '##' + id;
			}
			$('[id=\'' + id + '\']').button('disable');
		},
		/**
         * Habilita el botón correspondiente al identificador indicado.
         *
         * @function enableButton
         * @param {string} id - Identificador del botón que se desea habilitar.
         * @example
         * $("#idToolbar").rup_date("enableButton","idEditButton");
         */
		enableButton: function enableButton(id) {
			if (id.indexOf(this.attr('id')) === -1) {
				id = this.attr('id') + '##' + id;
			}
			$('[id=\'' + id + '\']').button('enable');
		},
		/**
         * Añade el estilo de css indicado para simular un estado press en el botón.
         *
         * @function pressButton
         * @param {string} id - Identificador del botón.
         * @param {string} css - Css asociado al estado press.
         * @example
         * $("#idToolbar").rup_date("pressButton","idEditButton","preesed-button");
         */
		pressButton: function pressButton(id, css) {
			if (id.indexOf(this.attr('id')) === -1) {
				id = this.attr('id') + '##' + id;
			}
			$('[id=\'' + id + '\']').addClass(css);
		},
		/**
         * Elimina el estilo de css indicado para simular un estado press en el botón.
         *
         * @function  unpressButton
         * @param {string} id - Identificador del botón.
         * @param {string} css - Css asociado al estado press.
         * @example
         * $("#idToolbar").rup_date("unpressButton","idEditButton","preesed-button");
         */
		unpressButton: function unpressButton(id, css) {
			if (id.indexOf(this.attr('id')) === -1) {
				id = this.attr('id') + '##' + id;
			}
			$('[id=\'' + id + '\']').removeClass(css);
		},
		/**
         * Alterna el estado del estilo de css indicado para simular un estado press en el botón.
         *
         * @function  tooglePressButton
         * @param {string} id - Identificador del botón.
         * @param {string} css - Css asociado al estado press.
         * @example
         * $("#idToolbar").rup_date("tooglePressButton","idEditButton","preesed-button");
         */
		tooglePressButton: function tooglePressButton(id, css) {
			if (id.indexOf(this.attr('id')) === -1) {
				id = this.attr('id') + '##' + id;
			}
			$('[id=\'' + id + '\']').toggleClass(css);
		},
		/**
         * Actualiza el botón al estado que determina la configuración actual.
         *
         * @function  refresh
         * @param {string} id - Identificador del botón.
         * @example
         * $("#idToolbar").rup_date("refresh");
         */
		refreshButton: function refreshButton(id) {
			if (id.indexOf(this.attr('id')) === -1) {
				id = this.attr('id') + '##' + id;
			}
			$('[id=\'' + id + '\']').button('refresh');
		},
		/**
         * Configura la gestión de eventos de teclado en el botón.
         *
         * @function  _setKeyDown
         * @private
         * @param {object} boton - Referencia al button.
         */
		_setKeyDown: function _setKeyDown(boton) {
			boton.bind('keydown', function (event) {
				var object = $(event.currentTarget),
				    objectParent = object.parent(),
				    nextObject;
				switch (event.keyCode) {
					case $.ui.keyCode.TAB:
						if (!event.shiftKey) {
							if (object.next().attr('id') !== objectParent.attr('id') + '-rightButtons') {
								//Siguiente boton
								nextObject = object.next(':focusable');
							} else {
								//Primer botón de los alineados derecha
								nextObject = object.next().children(':focusable:first');
							}

							//Navegar entre botones
							if (nextObject.size() === 1) {
								nextObject.focus();
								$.rup_toolbar.focusedExternally[objectParent.attr('id')] = true;
								return false;
							}
						}
				}
			});
		}
	});

	$.rup_toolbar.hideMButtons = function () {
		var showingMB = $.rup_toolbar.showingMB;
		$("ul[id*='" + showingMB + "']").slideUp('fast');
		$('[id=\'' + showingMB + '\']').removeClass('rup-toolbar_menuButtonSlided');
		showingMB = null;
		$.rup_toolbar.showingMB = showingMB;
	};

	$.fn.getTotalHeight = function () {
		//Función auxilliar que obtiene el alto total del boton, teniendo en cuenta todos los posibles paddings
		return $(this).height() + parseInt($(this).css('paddingTop')) + parseInt($(this).css('paddingBottom')) + parseInt($(this).css('borderTopWidth')) + parseInt($(this).css('borderBottomWidth'));
	};

	$.fn.rup_toolbar = function (properties) {
		return this.each(function () {

			//Carga de los valores por defecto para los atributos que no ha introducido el usuario
			var settings = $.extend({}, $.fn.rup_toolbar.defaults, properties),
			    t = $(this),
			    json_i18n,
			    rightButtons = [];

			this._ADAPTER = $.rup.adapter[settings.adapter];
			//Se guarda el marcador de foco de la botonera
			if ($.rup_toolbar.focusedExternally === undefined) {
				$.rup_toolbar.focusedExternally = {};
			}
			$.rup_toolbar.focusedExternally[this.id] = false;

			settings.id = this.id;
			//Literales
			json_i18n = $.rup.i18n.app[settings.id];

			//Anyadir estilo
			t.addClass('rup-toolbar ui-widget-header ui-widget ui-widget-content');

			//Tamanyo
			if (settings.width != null) {
				t.width(settings.width);
			}

			//Asignar evento de ocultación de mbuttons cuando se pinche fuera de ellos
			$(document).add("ul li").on('click', $.rup_toolbar.hideMButtons);
			//Botones
			for (var i = 0; i < settings.buttons.length; i += 1) {
				var obj = settings.buttons[i];

				// Se apartan, para respetar la gestión del tabulador, los botones derechos para ser tratados posteriormente
				if (!(obj.right !== undefined && obj.right === true)) {
					//MButton
					if (obj.buttons) {

						// el boton dispone de una definicion de botones anidados, por lo que es un mbutton
						mbutton = t.addMButton($.extend({
							id: obj.id,
							i18nCaption: obj.i18nCaption,
							css: obj.css,
							click: t.showMButton
						}, obj), json_i18n);

						if (mbutton !== null) {
							t.addButtonsToMButton(obj.buttons, mbutton, json_i18n);
						}
						//Button
					} else {
						t.addButton(obj, json_i18n);
					}
				} else {
					rightButtons.push(obj);
				}
			}

			for (var i = 0; i < rightButtons.length; i += 1) {
				var dObj = rightButtons[i];

				//MButton
				if (dObj.buttons) {
					// el boton dispone de una definicion de botones anidados, por lo que es un mbutton
					mbutton = t.addMButton({
						id: dObj.id,
						i18nCaption: dObj.i18nCaption,
						css: dObj.css,
						click: t.showMButton,
						right: dObj.right
					}, json_i18n);

					if (mbutton !== null) {
						t.addButtonsToMButton(dObj.buttons, mbutton, json_i18n);
					}
					//Button
				} else {
					t.addButton(dObj, json_i18n);
				}
			}
		});
	};

	/* VALORES POR DEFECTO */
	$.fn.rup_toolbar.defaults = {
		width: null,
		buttons: [],
		mbuttons: null,
		adapter: 'toolbar_bootstrap'
	};

	/**
     * @description Propiedades de configuración del componente.
     *
     * @name options
     * @property {Integer} [width=null] - Tamaño que tendrá la botonera. Por defecto ocupará toda la página.
     * @property {module:rup_toolbar~button[]} [buttons] - Array de botones a mostrar.
     * @property {module:rup_toolbar~mButton[]} [mbuttons] - Array de botones con menú a mostrar.
     */
});

/***/ }),
/* 17 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function(jQuery) {var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;var _typeof = typeof Symbol === "function" && typeof Symbol.iterator === "symbol" ? function (obj) { return typeof obj; } : function (obj) { return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj; };

function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; }

/*!
 * Copyright 2016 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 */

/**
 * Módulo de utilidades comunes a todos los componentes RUP. <br/><br/>
 * Implementa métodos para la manipulación de JSON, formularios, formatos...
 *
 * @summary Librería de utilidades para los componentes RUP.
 * @module rup_utils
 * @memberOf jQuery
 */

/*global define */
/*global jQuery */

(function (factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(11), __webpack_require__(198)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		factory(jQuery);
	}
})(function ($) {

	$.rup_utils = {};
	$.rup_utils.arr = [];
	$.rup_utils.autoGenerateIdNum = 0;
	$.rup_utils.swinging = false;

	$.extend($.rup_utils, {
		/**
         * Retorna el idioma actual capitalizado.
         *
         * El idioma actual se obtiene de la variable $.rup.lang
         *
         * @name jQuery.rup_utils#capitalizedLang
         * @function
         * @example
         * // Retorna "Es" para un valor "es" en $.rup.lang.
         * $.rup_utils.capitalizedLang();
         * @returns {string} - Idioma actual capitalizado
         */
		capitalizedLang: function capitalizedLang() {
			if ($.rup.lang == null) {
				return '';
			}
			return $.rup.lang.charAt(0).toUpperCase() + $.rup.lang.slice(1);
		},
		getJson: function getJson(obj, path) {
			var ret = $.extend({}, obj),
			    split = path.split('.');

			if (split.length === 1) {
				return obj[split[0]];
			}
			for (var i = 0; i < split.length; i++) {
				ret = ret[split[i]];
			}

			return ret;
		},
		setJson: function setJson(obj, path, value) {
			var aux = obj,
			    split = path.split('.');

			if (split.length === 1) {
				obj[split[0]] = value;
			} else {
				for (var i = 0; i < split.length - 1; i++) {
					aux = aux[split[i]];
				}

				aux[split[split.length - 1]] = value;
			}
		},
		/**
         * Transforma un objeto JSON en un array Javascript.
         *
         * @name jQuery.rup_utils#jsontoarray
         * @function
         * @param {Object} obj - Objeto JSON que se desea transformar en un array.
         * @returns {Object} - Array JavaScript.
         * @example
         * // Transforma un json obj={'prop':'value'} en un array arr['prop'] -> 'value'
         * var obj={'prop':'value'};
         * $.rup_utils.jsontoarray(obj);
         * @example
         * // Transforma un json obj={'propA':{'propAA':'value'}} en un array arr['propA.propAA'] -> 'value'
         * var obj={'propA':{'propAA':'value'}};
         * $.rup_utils.jsontoarray(obj);
         * @example
         * // Transforma un json obj={'propA':{'propAA':['a','b','c','d']}} en un array arr['propA.propAA[0]']
         * var obj={'propA':{'propAA':['a','b','c','d']}};
         * $.rup_utils.jsontoarray(obj);
         */
		jsontoarray: function jsontoarray(obj) {
			var arr = [];

			function parseJSON(obj, path) {
				// parsea un json a un array
				path = path || '';
				// iteracion a traves (objects / arrays)
				if (obj === undefined || obj === null) {
					// Si no existe un valor para el path indicado se envia ''
					parseJSON('', path);
				} else if (obj.constructor == Object) {
					for (var prop in obj) {
						//var name = path + (path == '' ? prop : '[' + prop + ']');
						var name = path + (path == '' ? prop : '.' + prop);
						parseJSON(obj[prop], name);
					}
				} else if (obj.constructor == Array) {
					if (obj.length == 0) {
						parseJSON('[]', path);
					} else {
						for (var i = 0; i < obj.length; i++) {
							var index = '[' + i + ']',
							    name = path + index;
							parseJSON(obj[i], name);
						}
					}
				} else {
					// assignment (values) if the element name hasn't yet been defined, create it as a single value
					if (arr[path] == undefined) {
						arr[path] = obj;
					} else if (arr[path].constructor != Array) {
						// if the element name HAS been defined, but it's a single value, convert to an array and add the new value
						arr[path] = [arr[path], obj];
					} else {
						// if the element name HAS been defined, and is already an array, push the single value on the end of the stack
						arr[path].push(obj);
					}
				}
			}

			parseJSON(obj);
			return arr;
		},
		/**
         * Realiza una desanidacion del json pasado (p.e.: {entidad:{propiedad:valor}}  --> {'entidad.propiedad':valor}.
         *
         * @name jQuery.rup_utils#unnestjson
         * @function
         * @param {Object} obj - Objeto JSON que se desea desanidar.
         * @returns {Object} -  Objeto JSON desanidado.
         * @example
         * // Transforma un json obj={'propA':{'propAA':'valueAA'}} en un json obj={'propA.propAA':'valueAA'}}
         * var obj={'propA':{'propAA':'valueAA'}};
         * $.rup_utils.unnestjson(obj);
         */
		unnestjson: function unnestjson(obj) {

			var array = $.rup_utils.jsontoarray(obj);

			var json = {};
			for (var key in array) {
				if (!$.isFunction(array[key])) {
					json[key] = array[key];
				}
			}

			return json;
		},
		/**
         * Devuelve el objeto del dom existente en la posición indicada.
         *
         * @name jQuery.rup_utils#elementFromPoint
         * @function
         * @param {number} x - Coordenada x de la posición en la pantalla.
         * @param {number} y - Coordenada y de la posición en la pantalla.
         * @param {boolean} [argCheck=true] - Determina si debe de ajustarse en base al scroll realizado en la pantalla .
         * @returns {Object} -  Objeto del DOM correspodiente a la posición indicada.
         * @example
         * $.rup_utils.elementFromPoint(120,140);
         */
		elementFromPoint: function elementFromPoint(x, y, argCheck) {
			var isRelative = true,
			    check = argCheck || true;
			if (!document.elementFromPoint) return null;

			if (!check) {
				var sl;
				if ((sl = $(document).scrollTop()) > 0) {
					isRelative = document.elementFromPoint(0, sl + $(window).height() - 1) == null;
				} else if ((sl = $(document).scrollLeft()) > 0) {
					isRelative = document.elementFromPoint(sl + $(window).width() - 1, 0) == null;
				}
				check = sl > 0;
			}

			if (!isRelative) {
				x += $(document).scrollLeft();
				y += $(document).scrollTop();
			}

			return document.elementFromPoint(x, y);
		},
		/**
         * Convierte en mínusculas el primer caracter de la cadena de caracteres pasada como parámetro.
         *
         * @name jQuery.rup_utils#firstCharToLowerCase
         * @function
         * @param {string} cadena - Cadena de caracteres inicial.
         * @returns {string} - Cadena de caracteres resultante con su primer caracter convertido a minúsculas.
         * @example
         * // Convierte a minúsculas el primer caracter de la cadena "AbCdEfg" -> "abCdEfg"
         * $.rup_utils.firstCharToLowerCase("AbCdEfg");
         */
		firstCharToLowerCase: function firstCharToLowerCase(cadena) {
			return cadena.substring(0, 1).toLowerCase() + cadena.substring(1);
		},
		/**
         * Devuelve un string que puede ser utilizado como selector de jQuery mediante el id ('#'). El método permite también escapar los caracteres reservados en los selectores de jQuery
         *
         * @name jQuery.rup_utils#firstCharToLowerCase
         * @function
         * @param {string} cadena - Cadena de caracteres inicial.
         * @returns {string} - Cadena de caracteres resultante con su primer caracter convertido a minúsculas.
         * @example
         * // Convierte a minúsculas el primer caracter de la cadena "AbCdEfg" -> "abCdEfg"
         * $.rup_utils.firstCharToLowerCase("AbCdEfg");
         */
		getJQueryId: function getJQueryId(sid, escaped) {
			var returnIdSelector;

			if (typeof sid === 'string') {
				returnIdSelector = sid;
				if (escaped === true) {
					returnIdSelector = String(returnIdSelector).replace(/[!"#$%&'()*+,.\/:; <=>?@\[\\\]\^`{|}~]/g, '\\$&');
				}
				return returnIdSelector[0] === '#' ? returnIdSelector : '#' + returnIdSelector;
			}

			return null;
		},
		/**
         * Convierte una cadena querystring en un objeto json.
         *
         * @name jQuery.rup_utils#queryStringToJson
         * @function
         * @param {string} queryString - Query string a transformar en un objeto json.
         * @returns {object} - Objeto JSON creado a partir de la query string indicada.
         * @example
         * // Obtene un json a partir del query string "keyA=valueA&keyB=valueB&keyC=valueC" -> "{keyA:'valueA', keyB:'valueB', keyC:'valueC'}"
         * $.rup_utils.queryStringToJson("keyA=valueA&keyB=valueB&keyC=valueC");
         */
		queryStringToJson: function queryStringToJson(queryString) {

			function setValue(root, path, value) {
				if (path.length > 1) {
					var dir = path.shift();
					if (typeof root[dir] == 'undefined') {
						root[dir] = path[0] == '' ? [] : {};
					}

					arguments.callee(root[dir], path, value);
				} else {
					if (root instanceof Array) {
						root.push(value);
					} else if (path[0].indexOf(".") != -1) {
						// Entra por aquí en caso de que uno de los path sea un objeto
						var padre = path[0].slice(0, path[0].indexOf("."));
						var hijo = path[0].slice(path[0].indexOf(".") + 1, path[0].length);

						if (root[padre] != undefined) {
							root[padre][hijo] = value;
						} else {
							root[padre] = _defineProperty({}, hijo, value);
						}
					} else {
						root[path] = value;
					}
				}
			}

			var nvp = queryString.split('&'),
			    data = {},
			    pair,
			    name,
			    value,
			    path,
			    first;

			for (var i = 0; i < nvp.length; i++) {
				pair = nvp[i].split('=');
				name = decodeURIComponent(pair[0]);
				value = decodeURIComponent(pair[1]);

				path = name.match(/(^[^\[]+)(\[.*\]$)?/);
				first = path[1];

				if (path[2]) {
					// case of 'array[level1]' ||
					// 'array[level1][level2]'
					path = path[2].match(/(?=\[(.*)\]$)/)[1].split('][');
				} else {
					// case of 'name'
					path = [];
				}
				path.unshift(first);

				setValue(data, path, value);
			}
			return data;
		},
		/**
         * Devuelve un string Con los caracteres sencillos
         *
         * @name jQuery.rup_utils#normalize
         * @function
         * @param {string} cadena - Cadena de caracteres inicial.
         * @returns {string} - Cadena de caracteres sin accentFolding.
         * @example
         * // Convierte los caracteres de la cadena "áéíóu" -> "aeiou"
         * $.rup_utils.normalize("áéíóu");
         */
		normalize: function normalize(texto) {
			var accentMap = {
				'á': 'a',
				'é': 'e',
				'í': 'i',
				'ó': 'o',
				'ú': 'u',
				'Á': 'A',
				'É': 'E',
				'Í': 'I',
				'Ó': 'O',
				'Ú': 'U'
			};
			var cadena = '';
			for (var i = 0; i < texto.length; i++) {
				cadena += accentMap[texto.charAt(i)] || texto.charAt(i);
			}
			return cadena.toLowerCase();
		},
		populateForm: function populateForm(aData, formid) {
			//rellena un formulario que recibe como segundo parametro con los datos que recibe en el segundo parametro
			var ruptype, formElem;
			var tree_data, selectorArray;
			if (aData) {

				for (var i in aData) {
					tree_data = new Array();
					formElem = $('[name=\'' + i + '\']', formid);
					if (formElem.length == 0) {
						selectorArray = i.substr(0, i.indexOf('['));
						formElem = $('[name=\'' + selectorArray + '\']', formid);
					}
					if (formElem.is('[ruptype]')) {
						if (formElem.hasClass('jstree')) {

							for (var a in aData) {
								if (a.substr(0, a.indexOf('[')) == selectorArray) {
									tree_data.push(aData[a]);
								}
							}
							formElem['rup_' + formElem.attr('ruptype')]('setRupValue', tree_data);
							var $arbol = [];
							$arbol[selectorArray] = tree_data;
							formElem.on('loaded.jstree', function (event, data) {
								var selectorArbol = this.id;
								//$(this).rup_tree("setRupValue",$arbol[selectorArbol]);

								$(this).trigger('rup_filter_treeLoaded', $arbol[selectorArbol]);
							});
						} else {
							// Forma de evitar el EVAL
							formElem['rup_' + formElem.attr('ruptype')]('setRupValue', aData[i]);
						}
					} else if (formElem.is('input:radio') || formElem.is('input:checkbox')) {
						formElem.each(function () {
							if ($(this).val() == aData[i]) {
								$(this).attr('checked', 'checked');
							} else {
								$(this).removeAttr('checked');
							}
						});
					} else if (formElem.is('select')) {
						formElem.val(aData[i]).click();
					} else if (formElem.is(':not(img)')) {
						// this is very slow on big table and form.
						formElem.val(aData[i]);
					}
				}
			}
		},

		//DATE UTILS
		createDate: function createDate(day, month, year) {
			return $.datepicker.formatDate($.rup.i18n.base['rup_date'].dateFormat, new Date(year, month - 1, day));
		},
		createTime: function createTime(hour, minute, second) {
			return new Date(null, null, null, hour, minute, second);
		},
		/*!
         * jQuery CooQuery Plugin v2
         * http://cooquery.lenonmarcel.com.br/
         *
         * Copyright 2009, 2010 Lenon Marcel
         * Dual licensed under the MIT and GPL licenses.
         * http://www.opensource.org/licenses/mit-license.php
         * http://www.gnu.org/licenses/gpl.html
         *
         * Date: 2010-01-24 (Sun, 24 January 2010)
         */

		//TODO: Documentacion -> http://plugins.jquery.com/project/cooquery
		setCookie: function setCookie(name, value, options) {
			if (typeof name === 'undefined' || typeof value === 'undefined' || name === null || value === null) {
				$.rup.errorGestor('[' + $.rup.i18nParse($.rup.i18n.base, 'rup_global.metodError') + 'setCookie] - ' + $.rup.i18nParse($.rup.i18n.base, 'rup_utils.paramsError'));
				return false;
			}

			var str = name + '=' + encodeURIComponent(value);

			if (typeof options !== 'undefined' && options !== null) {
				if (options.domain) str += '; domain=' + options.domain;
				if (options.path) str += '; path=' + options.path;
				if (options.duration) {
					var date = new Date();
					date.setTime(date.getTime() + options.duration * 24 * 60 * 60 * 1000);
					str += '; expires=' + date.toGMTString();
				}
				if (options.secure) str += '; secure';
			}

			return document.cookie = str;
		},

		delCookie: function delCookie(name) {
			if (typeof name === 'undefined' || name === null) {
				$.rup.errorGestor('[' + $.rup.i18nParse($.rup.i18n.base, 'rup_global.metodError') + 'delCookie] - ' + $.rup.i18nParse($.rup.i18n.base, 'rup_utils.paramsError'));
				return false;
			}

			return $.rup_utils.setCookie(name, '', {
				duration: -1
			});
		},

		readCookie: function readCookie(name) {
			if (typeof name === 'undefined' || name === null) {
				$.rup.errorGestor('[' + $.rup.i18nParse($.rup.i18n.base, 'rup_global.metodError') + 'readCookie] - ' + $.rup.i18nParse($.rup.i18n.base, 'rup_utils.paramsError'));
				return false;
			}

			var value = document.cookie.match('(?:^|;)\\s*' + name.replace(/([-.*+?^${}()|[\]\/\\])/g, '\\$1') + '=([^;]*)');
			return value ? decodeURIComponent(value[1]) : null;
		},
		get: function get(name, json) {
			var cookieValue = null;
			if (document.cookie && document.cookie != '') {
				var cookies = document.cookie.split(';');
				for (var i = 0; i < cookies.length; i++) {
					var cookie = $.trim(cookies[i]);
					if (cookie.substring(0, name.length + 1) == name + '=') {
						cookieValue = json ? $.JSON.decode(decodeURIComponent(cookie.substring(name.length + 1))) : decodeURIComponent(cookie.substring(name.length + 1));
						break;
					}
				}
			}
			return cookieValue;
		},
		set: function set(name, value, options) {
			options = $.extend({}, options);

			if (value === null) {
				value = '';
				options.expires = -1;
			}
			var expires = '';
			if (options.expires && (typeof options.expires == 'number' || options.expires.toUTCString)) {
				var date;
				if (typeof options.expires == 'number') {
					date = new Date();
					date.setTime(date.getTime() + options.expires * 24 * 60 * 60 * 1000);
				} else {
					date = options.expires;
				}
				expires = '; expires=' + date.toUTCString();
			}

			value = options.json ? encodeURIComponent($.JSON.encode(value)) : encodeURIComponent(value);

			var path = options.path ? '; path=' + options.path : '';
			var domain = options.domain ? '; domain=' + options.domain : '';
			var secure = options.secure ? '; secure' : '';

			document.cookie = [name, '=', value, expires, path, domain, secure].join('');
		},
		//compare objects function
		compareObjects: function (_compareObjects) {
			function compareObjects(_x, _x2) {
				return _compareObjects.apply(this, arguments);
			}

			compareObjects.toString = function () {
				return _compareObjects.toString();
			};

			return compareObjects;
		}(function (x, y) {
			var objectsAreSame = true;
			if (Object.keys(x).length !== Object.keys(y).length) {
				return false;
			}
			for (var propertyName in x) {
				if (_typeof(x[propertyName]) == 'object' && _typeof(y[propertyName]) == 'object') {
					objectsAreSame = compareObjects(x[propertyName], y[propertyName]);
					if (!objectsAreSame) break;
				} else {
					if (x[propertyName] !== y[propertyName]) {
						objectsAreSame = false;
						break;
					}
				}
			}
			return objectsAreSame;
		}),
		escapeId: function escapeId(id) {
			if (id) {
				return id.replace(/([ #;&,.+*~\':"!^$[\]()=>|\/@])/g, '\\$1');
			}

			return '';
		},
		selectorId: function selectorId(id) {
			if (typeof id === 'string' && id.substring(0, 1) !== '#') {
				return '#' + id;
			} else {
				return id;
			}
		},
		//Genera un identificador aleatorio para un objeto determinado
		randomIdGenerator: function randomIdGenerator(selectObject) {
			var id = 'rupRandomLayerId-' + $.rup_utils.autoGenerateIdNum;
			selectObject.attr('id', id).addClass('rupRandomLayerId');
			$.rup_utils.autoGenerateIdNum = $.rup_utils.autoGenerateIdNum + 1;
			return id;
		},
		//Función encargada de gestionar las url's de las aplicaciones en portal
		setNoPortalParam: function setNoPortalParam(url) {
			if (url !== undefined && url !== null) {
				if ($.rup_utils.readCookie('r01PortalInfo') !== null && url.match('R01HNoPortal') === null && $('div.r01gContainer').length > 0 || $('div.r01gApplication').length > 0) {
					return url + (url.match('\\?') === null ? '?' : '&') + 'R01HNoPortal=true';
				}
			}
			return url;
		},
		//Función encargada de detectar si la aplicación esta integrada en portal
		aplicatioInPortal: function aplicatioInPortal() {
			if (!($.rup_utils.readCookie('r01PortalInfo') !== null && $('div.r01gContainer').length > 0)) {
				return false;
			} else {
				return true;
			}
		},
		//Funcion encargada de pasar las urls relativas a absolutas.
		//Esta diseñado para terminar con los problemas de comportamientos anómalo de los navegadores en la redirecciones relativas
		relToAbsUrl: function relToAbsUrl(url) {

			var urlPage = $(location);

			if (typeof url === 'string') {
				var fChar1 = url.substring(0, 1);
				var fChar2 = url.substring(1, 2);

				if ($.url(url).attr('protocol') === undefined || $.url(url).attr('protocol') === '') {
					if (fChar1 === '/') {
						if (fChar2 === undefined || fChar2 !== '/') {
							return urlPage.attr('protocol') + '//' + urlPage.attr('host') + url;
						} else {
							return urlPage.attr('protocol') + url;
						}
					} else if (fChar1 === '.') {
						if (fChar2 === undefined) {
							$.rup.errorGestor($.rup.i18nParse($.rup.i18n.base, 'rup_utils.relToAbsUrlParamError') + url + $.rup.i18nParse($.rup.i18n.base, 'rup_utils.relToAbsUrlParamErrorEnd'));
							return undefined;
						} else if (fChar2 === '/') {
							var analyzedUrl = $.url(urlPage.attr('href'), true);
							return analyzedUrl.attr('base') + analyzedUrl.attr('directory') + url.substring(2, url.length);
						} else if (fChar2 === '.') {
							var urlPageFragments = urlPage.attr('pathname').split('/');
							var urlPageLength = urlPageFragments.length - 2;
							if (url.substring(2, 3) !== undefined && url.substring(2, 3) === '/') {
								var urlFragments = url.split('../');
								var urlLength = urlFragments.length - 1;
								if (urlLength >= urlPageLength) {
									return urlPage.attr('protocol') + '//' + urlPage.attr('host') + '/' + urlFragments[urlFragments.length - 1];
								} else {
									var cade = '';
									for (var i = urlPageLength - urlLength; i > 0; i--) {
										cade = urlPageFragments[i] + '/' + cade;
									}
									return urlPage.attr('protocol') + '//' + urlPage.attr('host') + '/' + cade + urlFragments[urlFragments.length - 1];
								}
							} else {
								var urlFragments = url.split('..');
								var urlLength = urlFragments.length - 1;
								if (urlLength >= urlPageLength) {
									return urlPage.attr('protocol') + '//' + urlPage.attr('host') + urlFragments[urlFragments.length - 1];
								} else {
									var cade = '';
									for (var i = urlPageLength - urlLength; i > 0; i--) {
										cade = urlPageFragments[i] + '/' + cade;
									}
									return urlPage.attr('protocol') + '//' + urlPage.attr('host') + '/' + cade + urlFragments[urlFragments.length - 1];
								}
							}
						} else {
							$.rup.errorGestor($.rup.i18nParse($.rup.i18n.base, 'rup_utils.relToAbsUrlParamError') + url + $.rup.i18nParse($.rup.i18n.base, 'rup_utils.relToAbsUrlParamErrorEnd'));
							return undefined;
						}
					} else {
						var analyzedUrl = $.url(urlPage.attr('href'), true);
						return analyzedUrl.attr('base') + analyzedUrl.attr('directory') + url;
					}
				} else {
					return url;
				}
			} else {
				$.rup.errorGestor($.rup.i18nParse($.rup.i18n.base, 'rup_utils.relToAbsUrlParamFormatError'));
				return undefined;
			}
		},
		printMsg: function printMsg(msg) {
			var ret = '';
			if (typeof msg === 'string') {
				return msg + '<br/>';
			} else if ((typeof msg === 'undefined' ? 'undefined' : _typeof(msg)) === 'object') {
				if (jQuery.isArray(msg)) {
					for (var i = 0; i < msg.length; i++) {
						ret += $.rup_utils.printMsgAux(msg[i], 1);
					}
					return ret;
				} else {
					ret += $.rup_utils.printMsgAux(msg, 1);
				}
			}
			return ret;
		},
		printMsgAux: function printMsgAux(msg, nivel) {
			var ret = '';
			if (typeof msg === 'string') {
				return $('<span>').append(msg)[0].outerHTML + '<br/>';
			} else if ((typeof msg === 'undefined' ? 'undefined' : _typeof(msg)) === 'object') {
				if (jQuery.isArray(msg)) {
					var ul = $('<ul>').addClass('rup-maint_feedbackUL');
					for (var i = 0; i < msg.length; i++) {
						//						if (typeof msg[i]==="string" || (typeof msg[i]==="object" && !jQuery.isArray(msg))){
						if (nivel === 1) {
							ul.append($('<li>').append($.rup_utils.printMsgAux(msg[i], nivel + 1)));
						} else {
							ul.append($.rup_utils.printMsgAux(msg[i], nivel + 1));
						}
					}
					return ret += ul[0].outerHTML;
				} else {
					var span = $('<span>');

					if (msg.style !== undefined) {
						span.addClass(msg.style);
					}

					if (msg.label !== undefined) {
						span.append(msg.label);
					}

					return span[0].outerHTML + '<br/>';
				}
			}
		},
		//Función encargada de recuperar todas las variables pasadas por QueryString (en la url)
		getUrlVars: function getUrlVars() {
			if ($.rup.getParams === undefined) {
				var vars = {},
				    hash;
				var hashes = window.location.href.slice(window.location.href.indexOf('?') + 1).split('&');
				for (var i = 0; i < hashes.length; i++) {
					hash = decodeURIComponent(hashes[i]).split('=');
					vars[hash[0]] = hash[1];
				}
				$.rup.getParams = vars;
			}
			return $.rup.getParams;
		},
		//Función encargada de recuperar una variable especifica de las pasadas por QueryString (en la url)
		getUrlVar: function getUrlVar(name) {
			return $.rup_utils.getUrlVars()[name];
		},
		sortArray: function sortArray(array, sortFnc) {

			function defaultSortFnc(obj1, obj2) {
				return obj1 - obj2;
			}

			function bubbleSort(a, fnc) {
				var swapped;
				do {
					swapped = false;
					for (var i = 0; i < a.length - 1; i++) {
						if (fnc(a[i], a[i + 1]) < 0) {
							var temp = a[i];
							a[i] = a[i + 1];
							a[i + 1] = temp;
							swapped = true;
						}
					}
				} while (swapped);
			}

			if (!$.isArray(array)) {
				return undefined;
			}

			if ($.isFunction(sortFnc)) {
				bubbleSort(array, sortFnc);
			} else {
				bubbleSort(array, defaultSortFnc);
			}
		},
		insertSorted: function insertSorted(array, elem, sortFnc) {

			function defaultSortFnc(obj1, obj2) {
				return obj2 - obj1;
			}

			if (!$.isArray(array)) {
				return undefined;
			}

			array.push(elem);

			if ($.isFunction(sortFnc)) {
				$.rup_utils.sortArray(array, sortFnc);
			} else {
				$.rup_utils.sortArray(array, defaultSortFnc);
			}

			return $.inArray(elem, array);
		},
		getRupValueAsJson: function getRupValueAsJson(name, value) {
			var arrTmp,
			    returnArray,
			    dotNotation = false,
			    dotProperty,
			    tmpJson,
			    returnArray = [];

			if (name) {
				// Miramos si el name contiene notación dot
				arrTmp = name.split('.');
				if (arrTmp.length > 1) {
					dotNotation = true;
					dotProperty = arrTmp[arrTmp.length - 1];
				} else {
					dotProperty = arrTmp[0];
				}

				if (jQuery.isArray(value)) {

					//issue [utils] getRupValueAsJson provoca error con los arrays vacíos #24
					//https://github.com/UDA-EJIE/udaRUP/issues/24
					if (value.length !== 0) {
						// Devolvemos un array de resultados.
						for (var i = 0; i < value.length; i++) {
							tmpJson = {};
							if (dotNotation) {
								tmpJson[dotProperty] = value[i];
								returnArray.push(tmpJson);
							} else {
								tmpJson[dotProperty] = value[i];
								returnArray.push(tmpJson);
							}
						}

						return returnArray;
					}
				} else {
					// Devolvemos un único valor.
					tmpJson = {};
					tmpJson[dotProperty] = value;

					return tmpJson;
				}
			}

			return null;
		},
		getRupValueWrapped: function getRupValueWrapped(name, value) {
			var arrTmp,
			    dotNotation = false,
			    dotProperty,
			    wrapObj = {};
			if (name) {
				// Miramos si el name contiene notación dot
				arrTmp = name.split('.');
				if (arrTmp.length > 1) {
					dotNotation = true;
					dotProperty = arrTmp[arrTmp.length - 1];
				} else {
					return value;
				}

				wrapObj[dotProperty] = value;

				return wrapObj;
			}

			return null;
		},
		swing2Top: function swing2Top() {
			if (!$.rup_utils.swinging) {
				$.rup_utils.swinging = true;
				$('html, body').animate({
					scrollTop: 0
				}, '1000', 'swing', function () {
					$.rup_utils.swinging = false;
				});
			}
		}

	});

	//Utilidades de los formularios
	$.fn.serializeToObject = function () {
		//Para enviar los campos que contienen valor (!= "")
		var o = {},
		    a = this.serializeArrayWithoutNulls();
		$.each(a, function () {
			if (o[this.name]) {
				if (!o[this.name].push) {
					o[this.name] = [o[this.name]];
				}
				o[this.name].push(this.value || '');
			} else {
				o[this.name] = this.value;
			}
		});
		return o;
	};

	$.fn.serializeArrayWithoutNulls = function () {
		//crea un array con campos de un formulario que tienen valor !=""
		return this.map(function () {
			return this.elements ? jQuery.makeArray(this.elements) : this;
		}).filter(function () {
			return this.name && !this.disabled && (this.checked || /select|textarea/i.test(this.nodeName) || /color|date|datetime|email|hidden|month|number|password|range|search|tel|text|time|url|week/i.test(this.type));
		}).map(function (i, elem) {
			var val = jQuery(this).val();
			if (jQuery(this).hasClass('numeric') || jQuery(this).hasClass('datepicker')) /*&& val === ""*/{
					return {
						name: elem.name,
						value: null
					};
				}
			return val === null || val === '' ? null : jQuery.isArray(val) ? jQuery.map(val, function (val, i) {
				return {
					name: elem.name,
					value: val
				};
			}) : {
				name: elem.name,
				value: val
			};
		}).get();
	};

	$.fn.serializeObject = function () {
		//Para enviar los campos nulos con null en vez de en blanco
		var o = {},
		    a = this.serializeArrayNull();
		$.each(a, function () {
			if (o[this.name]) {
				if (!o[this.name].push) {
					o[this.name] = [o[this.name]];
				}
				o[this.name].push(this.value || '');
			} else {
				o[this.name] = this.value;
			}
		});
		return o;
	};

	$.fn.serializeArrayNull = function () {
		return this.map(function () {
			return this.elements ? jQuery.makeArray(this.elements) : this;
		}).filter(function () {
			return this.name && !this.disabled && (this.checked || /select|textarea/i.test(this.nodeName) || /color|date|datetime|email|hidden|month|number|password|range|search|tel|text|time|url|week/i.test(this.type));
		}).map(function (i, elem) {
			var val = jQuery(this).val();
			if ((jQuery(this).hasClass('numeric') || jQuery(this).hasClass('datepicker')) && val === '') {
				return {
					name: elem.name,
					value: null
				};
			}
			return val === null ? null : jQuery.isArray(val) ? jQuery.map(val, function (val, i) {
				return {
					name: elem.name,
					value: val
				};
			}) : {
				name: elem.name,
				value: val
			};
		}).get();
	};

	jQuery.rup_utils.base64 = {
		// private property
		_keyStr: 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/=',
		// public method for encoding
		encode: function encode(input) {
			var output = '';
			var chr1, chr2, chr3, enc1, enc2, enc3, enc4;
			var i = 0;
			input = jQuery.rup_utils.base64._utf8_encode(input);
			while (i < input.length) {
				chr1 = input.charCodeAt(i++);
				chr2 = input.charCodeAt(i++);
				chr3 = input.charCodeAt(i++);
				enc1 = chr1 >> 2;
				enc2 = (chr1 & 3) << 4 | chr2 >> 4;
				enc3 = (chr2 & 15) << 2 | chr3 >> 6;
				enc4 = chr3 & 63;
				if (isNaN(chr2)) {
					enc3 = enc4 = 64;
				} else if (isNaN(chr3)) {
					enc4 = 64;
				}
				output = output + this._keyStr.charAt(enc1) + this._keyStr.charAt(enc2) + this._keyStr.charAt(enc3) + this._keyStr.charAt(enc4);
			}
			return output;
		},
		// public method for decoding
		decode: function decode(input) {
			var output = '';
			var chr1, chr2, chr3;
			var enc1, enc2, enc3, enc4;
			var i = 0;
			input = input.replace(/[^A-Za-z0-9\+\/\=]/g, '');
			while (i < input.length) {
				enc1 = this._keyStr.indexOf(input.charAt(i++));
				enc2 = this._keyStr.indexOf(input.charAt(i++));
				enc3 = this._keyStr.indexOf(input.charAt(i++));
				enc4 = this._keyStr.indexOf(input.charAt(i++));
				chr1 = enc1 << 2 | enc2 >> 4;
				chr2 = (enc2 & 15) << 4 | enc3 >> 2;
				chr3 = (enc3 & 3) << 6 | enc4;
				output = output + String.fromCharCode(chr1);
				if (enc3 != 64) {
					output = output + String.fromCharCode(chr2);
				}
				if (enc4 != 64) {
					output = output + String.fromCharCode(chr3);
				}
			}
			output = jQuery.rup_utils.base64._utf8_decode(output);
			return output;
		},
		// private method for UTF-8 encoding
		_utf8_encode: function _utf8_encode(string) {
			string = string.replace(/\r\n/g, '\n');
			var utftext = '';
			for (var n = 0; n < string.length; n++) {
				var c = string.charCodeAt(n);
				if (c < 128) {
					utftext += String.fromCharCode(c);
				} else if (c > 127 && c < 2048) {
					utftext += String.fromCharCode(c >> 6 | 192);
					utftext += String.fromCharCode(c & 63 | 128);
				} else {
					utftext += String.fromCharCode(c >> 12 | 224);
					utftext += String.fromCharCode(c >> 6 & 63 | 128);
					utftext += String.fromCharCode(c & 63 | 128);
				}
			}
			return utftext;
		},
		// private method for UTF-8 decoding
		_utf8_decode: function _utf8_decode(utftext) {
			var string = '';
			var i = 0;
			var c = c1 = c2 = 0;
			while (i < utftext.length) {
				c = utftext.charCodeAt(i);
				if (c < 128) {
					string += String.fromCharCode(c);
					i++;
				} else if (c > 191 && c < 224) {
					c2 = utftext.charCodeAt(i + 1);
					string += String.fromCharCode((c & 31) << 6 | c2 & 63);
					i += 2;
				} else {
					c2 = utftext.charCodeAt(i + 1);
					c3 = utftext.charCodeAt(i + 2);
					string += String.fromCharCode((c & 15) << 12 | (c2 & 63) << 6 | c3 & 63);
					i += 3;
				}
			}
			return string;
		}
	};
});
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))

/***/ }),
/* 18 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function($) {var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;var _typeof = typeof Symbol === "function" && typeof Symbol.iterator === "symbol" ? function (obj) { return typeof obj; } : function (obj) { return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj; };

/*!
 * Copyright 2016 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 */

/**
 * Permite al usuario validar los datos introducidos en los campos que se presentan en la aplicación.
 *
 * @summary Componente RUP Validate.
 * @module rup_validate
 * @see El componente está basado en el plugin {@link http://jqueryvalidation.org/|jQuery Validation Plugin}. Para mas información acerca de las funcionalidades y opciones de configuración pinche {@link http://jqueryvalidation.org/|aquí}.
 * @example
 * var properties={
 *   rules:{
 *       "campoObligatorio":{required:true},
 *       "dni":{required:true,dni:true}
 *   }
 * };
 * $("#formValidaciones").rup_validate(properties);
 */

/*global define */
/*global jQuery */
/*global $ */

(function (factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(2), __webpack_require__(27), __webpack_require__(268)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		factory(jQuery);
	}
})(function (jQuery) {

	//*********************************************
	// ESPECIFICACÍON DE LOS TIPOS BASE DEL PATRÓN
	//*********************************************

	//*****************************************************************************************************************
	// DEFINICIÓN BASE DEL PATRÓN (definición de la variable privada que contendrá los métodos y la función de jQuery)
	//*****************************************************************************************************************


	var rup_validate = {};
	$.rup_validate = {};

	//Se configura el arranque de UDA para que alberge el nuevo patrón
	$.extend($.rup.iniRup, $.rup.rupSelectorObjectConstructor('rup_validate', rup_validate));

	// Se configuran los mensajes idiomaticos.
	var messages = {};

	// Es necesario identificar los mensajes parametrizables. Para ello se buscan los fragmentos de tipo {i} para ser tratados por la funcion format del validador.
	var regularExpr = new RegExp('\\{\\d\\}');
	$.each($.rup.i18n.base.rup_validate.messages, function (key, value) {

		if (value.match(regularExpr) !== null) {
			messages[key] = jQuery.validator.format(value);
		} else {
			messages[key] = value;
		}
	});

	// Inicializacion de las expresiones regulares
	var rup_validate_number_regexpr = new RegExp($.rup.i18n.base.rup_validate.regexp.decimal);

	// Se configruran los mensajes de las reglas de validacion a partir de los definidos en los ficheros idiomaticos.
	$.extend($.validator.messages, messages);

	/*
   * VALIDACIONES
   */
	//sobreescritura
	//

	//
	jQuery.validator.addMethod('dni', function (value, element) {
		return this.optional(element) || euroNif(value);
	});

	function nif(dni) {
		if (dni.length === 9) {
			var numero = dni.substr(0, 8);
			var ss = typeof numero === 'undefined' ? 'undefined' : _typeof(numero);
			var ss2 = _typeof(dni.substr(dni.length - 1, dni.length));
			numero = numero % 23;
			var letra = 'TRWAGMYFPDXBNJZSQVHLCKET';
			letra = letra.substring(numero, numero + 1);
			if (letra != dni.substr(dni.length - 1, dni.length).toUpperCase()) {
				return false;
			} else {
				return true;
			}
		} else {
			return false;
		}
	}

	function stripHtml(value) {
		// remove html tags and space chars
		return value.replace(/<.[^<>]*?>/g, ' ').replace(/&nbsp;|&#160;/gi, ' ')
		// remove numbers and punctuation
		.replace(/[0-9.(),;:!?%#$'"_+=\/-]*/g, '');
	}

	// Dni
	jQuery.validator.addMethod('dni', function (value, element) {
		return this.optional(element) || nif(value);
	});

	// Numero maximo de palabras
	jQuery.validator.addMethod('maxWords', function (value, element, params) {
		return this.optional(element) || stripHtml(value).match(/\b\w+\b/g).length < params;
	});

	// Numero minimo de palabras
	jQuery.validator.addMethod('minWords', function (value, element, params) {
		return this.optional(element) || stripHtml(value).match(/\b\w+\b/g).length >= params;
	});

	// Intervalo de palabras
	jQuery.validator.addMethod('rangeWords', function (value, element, params) {
		return this.optional(element) || stripHtml(value).match(/\b\w+\b/g).length >= params[0] && value.match(/bw+b/g).length < params[1];
	});

	// Letras y caracteres de puntuacion
	jQuery.validator.addMethod('letterswithbasicpunc', function (value, element) {
		return this.optional(element) || /^[a-z-.,()'\"\s]+$/i.test(value);
	});

	// Letras, numeros, espacios o guiones bajos
	jQuery.validator.addMethod('alphanumeric', function (value, element) {
		return this.optional(element) || /^\w+$/i.test(value);
	});

	// Solo letras
	jQuery.validator.addMethod('lettersonly', function (value, element) {
		return this.optional(element) || /^[a-z]+$/i.test(value);
	});

	// Espacios no permitidos
	jQuery.validator.addMethod('nowhitespace', function (value, element) {
		return this.optional(element) || /^\S+$/i.test(value);
	});

	// Entero positivo o negativo
	jQuery.validator.addMethod('integer', function (value, element) {
		return this.optional(element) || /^-?\d+$/.test(value);
	});

	// Patron
	jQuery.validator.addMethod('pattern', function (value, element, param) {
		return this.optional(element) || param.test(value);
	});

	// Validacion de campo numerico. Tiene en cuenta el formato dependiendo de la locale
	jQuery.validator.addMethod('number', function (value, element) {
		var expr = new RegExp($.rup.i18n.base.rup_validate.regexp.decimal);
		return this.optional(element) || expr.test(value);
	});

	// Validacion de fecha. Tiene en cuanta el formato dependiendo de la locale
	jQuery.validator.addMethod('date', function (value, element, param) {
		var format;
		if (typeof param === 'boolean') {
			if (param === true) {
				format = $.rup.i18n.base.rup_validate.format.date;
			} else {
				return true;
			}
		} else {
			format = param;
		}

		return this.optional(element) || $.rup_validate.checkDate(format, value);
	});

	// Validacion email.De acuerdo a la oficial RFC 5322 http://www.ietf.org/rfc/rfc5322.txt
	jQuery.validator.addMethod('email', function (value, element) {
		var expr = /^(([^<>()\[\]\\.,;:\s@"]+(\.[^<>()\[\]\\.,;:\s@"]+)*)|(".+"))@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}])|(([a-zA-Z\-0-9]+\.)+[a-zA-Z]{2,}))$/;
		return this.optional(element) || expr.test(value);
	});

	//********************************
	// DEFINICIÓN DE MÉTODOS PÚBLICOS
	//********************************

	$.extend($.rup_validate, {
		// Metodo que valida una fecha de acuerdo al formato indicado
		checkDate: function checkDate(format, date) {
			var daysInFebruary = function daysInFebruary(year) {
				return year % 4 === 0 && (year % 100 !== 0 || year % 400 === 0) ? 29 : 28;
			},
			    DaysArray = function DaysArray(n) {
				for (var i = 1; i <= n; i++) {
					this[i] = 31;
					if (i == 4 || i == 6 || i == 9 || i == 11) {
						this[i] = 30;
					}
					if (i == 2) {
						this[i] = 29;
					}
				}
				return this;
			};

			var tsp = {},
			    sep;
			format = format.toLowerCase();
			// Se busca el separador de fecha entre los caracteres "/","-","."
			if (format.indexOf('/') != -1) {
				sep = '/';
			} else if (format.indexOf('-') != -1) {
				sep = '-';
			} else if (format.indexOf('.') != -1) {
				sep = '.';
			} else {
				sep = '/';
			}
			format = format.split(sep);
			date = date.split(sep);
			if (date.length != 3) {
				return false;
			}
			var j = -1,
			    yln,
			    dln = -1,
			    mln = -1;
			for (var i = 0; i < format.length; i++) {
				var dv = date[i] === null || date[i] === '' || isNaN(date[i]) ? 0 : parseInt(date[i], 10);
				tsp[format[i]] = dv;
				yln = format[i];
				if (yln.indexOf('y') != -1) {
					j = i;
				}
				if (yln.indexOf('m') != -1) {
					mln = i;
				}
				if (yln.indexOf('d') != -1) {
					dln = i;
				}
			}
			if (format[j] == 'y' || format[j] == 'yyyy') {
				yln = 4;
			} else if (format[j] == 'yy') {
				yln = 2;
			} else {
				yln = -1;
			}
			var daysInMonth = DaysArray(12),
			    strDate;
			if (j === -1) {
				return false;
			} else {
				strDate = tsp[format[j]].toString();
				if (yln == 2 && strDate.length == 1) {
					yln = 1;
				}
				if (strDate.length != yln || tsp[format[j]] === 0 && date[j] != '00') {
					return false;
				}
			}
			if (mln === -1) {
				return false;
			} else {
				strDate = tsp[format[mln]].toString();
				if (strDate.length < 1 || tsp[format[mln]] < 1 || tsp[format[mln]] > 12) {
					return false;
				}
			}
			if (dln === -1) {
				return false;
			} else {
				strDate = tsp[format[dln]].toString();
				if (strDate.length < 1 || tsp[format[dln]] < 1 || tsp[format[dln]] > 31 || tsp[format[mln]] == 2 && tsp[format[dln]] > daysInFebruary(tsp[format[j]]) || tsp[format[dln]] > daysInMonth[tsp[format[mln]]]) {
					return false;
				}
			}
			return true;
		}
	});

	$.fn.rup_validate('extend', {
		/**
     * Se eliminan todos los objetos y eventos credos por el componente.
     *
     * @function destroy
     * @example
     * $("#formValidaciones").rup_validate("destroy");
     */
		destroy: function destroy() {
			var self = this;

			// Se eliminan los mensajes de error.
			self.rup_validate('resetForm');
			// Se elimina la informacion almacenada en el objeto.
			$.removeData(self[0]);
			// Se eliminan los eventos asociados al objeto.
			self.unbind();
		},
		/**
     * Se realiza un reset del formulario y se eliminan los menssajes de error de las reglas de validacion.
     *
     * @function resetForm
     * @example
     * $("#formValidaciones").rup_validate("resetForm");
     */
		resetForm: function resetForm() {
			var self = this,
			    settings = self.data('settings');

			// En caso de mostrarse el feedback de error se oculta.
			if (settings != null && settings.feedback !== undefined && settings.showErrorsInFeedback) {
				settings.feedback.rup_feedback('hide');
			}

			// Se reinician los mensajes de error.
			self.validate().resetForm();
		},
		/**
     * Se eliminan los menssajes de error de las reglas de validacion.
     *
     * @function resetForm
     * @example
     * $("#formValidaciones").rup_validate("resetElements");
     */
		resetElements: function resetElements() {
			var self = this,
			    validator = self.validate();

			validator.resetElements(validator.elements());
		}
	});

	//********************************
	// DEFINICIÓN DE MÉTODOS PRIVADOS
	//********************************
	$.fn.rup_validate('extend', {});

	//*****************************
	// INICIALIZACION DE VARIABLES
	//*****************************

	// Propiedades de configuracion predeterminadas para cada una de las posibles parametrizaciones de los errores.
	var presetSettings = {
		// Configruacion del componente por defecto
		defaultPresetSettings: {
			showErrors: function showErrors(errors) {
				var self = this,
				    invalid,
				    errorText,
				    feedback,
				    field,
				    errorKey,
				    fieldError,
				    fieldErrorMsg,
				    error,
				    label;

				// Se comprueba si el parametro que contiene los errores está vacío. En este caso se
				if (self.currentElements.length === 1) {
					if ($.isEmptyObject(errors)) {
						delete self.invalid[self.currentElements.attr('name')];
					}
				}

				/*
         * Mostrar mensaje de error de validaciones en el feedback
         */
				feedback = self.settings.feedback;
				if (self.settings.showErrorsInFeedback && feedback !== undefined && feedback !== null) {
					errorText = $('<ul>').addClass('rup-maint_feedbackUL').prepend(self.settings.feedbackErrorConfig.errorMsg);

					if (jQuery.isEmptyObject(self.invalid)) {
						feedback.rup_feedback('close');
					} else {

						if (self.settings.showFieldErrorsInFeedback) {
							$.each(!jQuery.isEmptyObject(self.submitted) ? self.submitted : self.invalid, function (key, value) {

								if (self.invalid[key] !== undefined) {
									field = self.settings.feedbackErrorConfig.getField(self, self.currentForm, key);
									errorKey = self.settings.feedbackErrorConfig.getFieldName(self, self.currentForm, field);
									fieldError = self.settings.feedbackErrorConfig.getFieldErrorLabel(self, self.currentForm, field, errorKey);

									fieldErrorMsg = self.settings.feedbackErrorConfig.getFieldErrorMsg(self, self.currentForm, field, value);
									fieldError.append(fieldErrorMsg);
									errorText.append(fieldError);
								}
							});
						}
						feedback.rup_feedback('option', self.settings.feedbackOptions);
						feedback.rup_feedback('set', errorText, 'error');
					}
				}

				/*
         * Mostrar detalle de errores en el feedback
         */
				if (self.settings.showFieldErrorAsDefault) {
					for (var i = 0; self.errorList[i]; i++) {

						error = self.errorList[i];

						if (error.element !== undefined) {

							label = self.errorsFor(error.element);
							if (label.length) {
								label.remove();
							}
						}
					}
				}

				/* En caso de utilizar el tratamiento por defecto del componente de jquery.validate,
         * no es posible indicarle varios mensajes de error para un campo.
         * Por ello deberemos concatenar estos mensajes de error en caso de que se de el caso.
         */
				for (var i = 0; i < self.errorList.length; i++) {
					//					if (self.settings.showFieldErrorAsDefault){
					//						self.errorList[i].message="";
					//					}else
					if (self.errorList[i].element === undefined) {
						alert('El campo validado no existe en el formulario');
					}
					if ($.isArray(self.errorList[i].message)) {
						// En caso de que el mensaje de error sea un array de mensajes, se debera de recorrer y concatenar
						var newMessage = '';
						for (var j = 0; j < self.errorList[i].message.length; j++) {
							newMessage += self.errorList[i].message[j];
							if (j !== self.errorList[i].message.length - 1) {
								newMessage += ', ';
							}
						}
						self.errorList[i].message = newMessage;
					}
				}
				// Se eliminan los etilos de error previos
				$('.' + self.settings.errorClass + ':not(.rup-maint_validateIcon)', self.currentForm).removeClass(self.settings.errorClass);
				//Se eliminan los iconos duplicados
				var elements = self.currentForm.getElementsByClassName('rup-validate-error-icon');
				while (elements !== undefined && elements.length > 0) {
					elements[0].parentNode.removeChild(elements[0]);
				}
				// Se invoca al metodo por defecto del plugin subyacente
				self.defaultShowErrors();
			},
			showErrorsInFeedback: function showErrorsInFeedback(errors) {},
			errorPlacement: function errorPlacement(label, element) {

				if (element.attr('ruptype') === 'combo') {
					var comboElem = $('#' + element.attr('id') + '-button');
					if (comboElem) {
						label.insertAfter(comboElem);
					}
				} else {
					label.insertAfter(element);
				}
			}
		},
		// Configuracion de las propiedades a aplicar en caso de que se deban mostrar los errores mediante la visualizacion por defecto.
		showFieldErrorAsDefault: {
			errorElement: 'img',
			errorPlacement: function errorPlacement(error, element) {
				var errorElem = error.attr('src', this.errorImage).addClass('rup-maint_validateIcon').html('').rup_tooltip({
					'applyToPortal': true
				});

				if (element.attr('ruptype') === 'combo') {
					var comboElem = $('#' + element.attr('id') + '-button');
					if (comboElem) {
						errorElem.insertAfter(comboElem);
					}
				} else {
					errorElem.insertAfter(element);
				}
			}
		}
	};

	$.fn.rup_validate('extend', {
		_init: function _init(args) {

			var self = this,
			    settingsAdapter,
			    defaultPresetSettings,
			    settings;

			settingsAdapter = $.extend(true, {}, {
				adapter: $.fn.rup_validate.defaults.adapter
			}, {
				adapter: presetSettings.defaultPresetSettings.adapter
			}, {
				adapter: args[0].adapter
			});
			self[0]._ADAPTER = $.rup.adapter[settingsAdapter.adapter];

			defaultPresetSettings = $.extend(true, {}, presetSettings.defaultPresetSettings, {
				showFieldErrorAsDefault: {
					highlight: self[0]._ADAPTER.highlight,
					unhighlight: self[0]._ADAPTER.unhighlight,
					errorElement: self[0]._ADAPTER.errorElement,
					errorPlacement: self[0]._ADAPTER.errorPlacement
				}
			});
			// settings = $.extend(true,{},$.fn.rup_validate.defaults, presetSettings.defaultPresetSettings, args[0]);

			settings = $.extend(true, {}, $.fn.rup_validate.defaults, defaultPresetSettings, args[0]);

			// settings = $.extend(true, {}, defaultSettings, args[0]);


			// Anadimos al formulario el class rup_validate para identificarlo como componente formulario.
			self.addClass('rup_validate');
			// Anadimos el ruptype validate
			self.attr('ruptype', 'validate');

			/*
       * Configuracion del componente de validaciones.
       */

			// En caso de que se deban mostrar los errores mediante la visualizacion predeterminada se configuran los presets correspondientes.
			if (settings.showFieldErrorAsDefault) {
				settings = $.extend(true, settings, defaultPresetSettings.showFieldErrorAsDefault);
			}
			settings = $.extend(true, {}, settings, args[0]);
			// Se realiza la invocacion al plugin jquery.validate
			self.validate(settings);

			if (settings.showFieldErrorAsDefault) {
				self.validate().showLabel = self[0]._ADAPTER.showLabel;
			}

			// Si se ha configurado el componente para que no se realicen validaciones al vuelo de los campos, se eliminan los eventos correspondientes.
			if (!settings.liveCheckingErrors) {
				self.unbind('click').unbind('focusin').unbind('focusout').unbind('keyup');
			}

			// Se captura el evento invalid-form del plugin subyacente para generar un evento propio
			self.on('invalid-form.rupValidate_formValidationError', function (event) {
				self.off('invalid-form.rupValidate_formValidationError');
				self.triggerHandler('rupValidate_formValidationError', [this]);
			});

			// Se almacena la configuracion del componente en el objeto dom para poder recuperarla en sucesivas invocaciones a los metodos del componente.
			self.data('settings', settings);
		}
	});

	//*******************************************************
	// DEFINICIÓN DE LA CONFIGURACION POR DEFECTO DEL PATRON
	//*******************************************************

	$.fn.rup_validate.defaults = {
		adapter: 'validate_bootstrap',
		ignore: ':hidden[ruptype!=\'autocomplete\'][ruptype!=\'combo\']',
		feedbackOptions: {
			gotoTop: false,
			fadeSpeed: null,
			delay: null
		},
		feedbackErrorConfig: {
			errorMsg: $.rup.i18nParse($.rup.i18n.base, 'rup_table.validateError'),
			getField: function getField(self, form, fieldName) {
				return $('[name=\'' + fieldName + '\']', form);
			},
			getFieldName: function getFieldName(self, form, field) {
				var fieldTmp, labelAttributes, labelElem;

				fieldTmp = jQuery(field.length > 1 ? field[0] : field);

				labelAttributes = {
					labelForId: fieldTmp.attr('id'),
					labelForName: fieldTmp.attr('name'),
					labelForTitle: fieldTmp.attr('oldtitle')
				};

				labelElem = $.rup.adapter[$.fn.rup_validate.defaults.adapter];

				if ($.fn.rup_validate.defaults.adapter === 'validate_bootstrap') {
					labelElem = labelElem.forLabelElement(form, labelAttributes);
				} else {
					if (labelAttributes.labelForTitle === undefined || labelAttributes.labelForTitle === '') {
						labelElem = labelElem.forLabelElement(form, labelAttributes);
					} else {
						return labelElem.forLabelElement(fieldTmp, labelAttributes);
					}
				}

				if (labelElem !== undefined && labelElem !== '') {
					return labelElem.replace(':', '');
				} else {
					labelElem = $.rup.adapter[$.fn.rup_validate.defaults.adapter].forInputIdElement(form, labelAttributes);

					if (labelElem !== undefined && labelElem !== '') {
						return labelElem.id;
					}

					labelElem = $.rup.adapter[$.fn.rup_validate.defaults.adapter].forInputNameElement(form, labelAttributes);

					if (labelElem !== undefined && labelElem !== '') {
						return labelElem.name;
					}
				}

				return fieldTmp.attr('title');
			},
			getFieldErrorLabel: function getFieldErrorLabel(self, form, field, errorLabel) {
				return $('<li>').append('<b>' + errorLabel + ':</b>');
			},
			getFieldErrorMsg: function getFieldErrorMsg(self, form, field, errorMsg) {
				/* En caso de utilizar el tratamiento por defecto del componente de jquery.validate,
         * no es posible indicarle varios mensajes de error para un campo.
         * Por ello deberemos concatenar estos mensajes de error en caso de que se de el caso.
         */
				if ($.isArray(errorMsg)) {
					// En caso de que el mensaje de error sea un array de mensajes, se debera de recorrer y concatenar
					var baseUl = $('<ul>');
					for (var i = 0; i < errorMsg.length; i++) {
						baseUl.append($('<li>').append(errorMsg[i]));
					}
					return baseUl;
				} else {
					return $('<ul>').append($('<li>').append(errorMsg));
				}
			}
		},
		liveCheckingErrors: false,
		showErrorsInFeedback: true,
		showFieldErrorAsDefault: true,
		showFieldErrorsInFeedback: true,
		errorImage: $.rup.STATICS + '/rup/css/images/exclamation.png'
	};

	/**
  * Función de callback que se ejecutará cuando el formulario sea válido.
  *
  * @callback module:rup_validate~onSubmitHandler
  * @param {Element} form - Referencia al objeto DOM del formulario que está siendo validado.
  * @example <caption>Envia el formulario cuando este es válido.</caption>
  * $("#idFormulario").rup_tooltip({
  *   onSubmitHandler: function(form){
  *       $(form).ajaxSubmit();
  *   }
  * });
  * @example <caption>Realizar otras operaciones cuando el formulario es válido.</caption>
  * $("#idFormulario").rup_tooltip({
  *   onSubmitHandler: function(form){
          // Operaciones extra
  *       $(form).ajaxSubmit();
  *   }
  * });
  */

	/**
   * Función que se ejecutará cuando el formulario presente errores de validación.
   *
   * @callback module:rup_validate~onInvalidHandler
   * @param {Event} event - Objeto event asociado al evento lanzado.
   * @param {object} validator - Instancia del validador asociada al formulario actual.
   * @example
   * $(".selector").validate({
   *   invalidHandler: function(event, validator) {
   *    // 'this' refers to the form
   *    var errors = validator.numberOfInvalids();
   *    if (errors) {
   *      var message = errors == 1
   *        ? 'You missed 1 field. It has been highlighted'
   *        : 'You missed ' + errors + ' fields. They have been highlighted';
   *      $("div.error span").html(message);
   *      $("div.error").show();
   *    } else {
   *      $("div.error").hide();
   *    }
   *  }
   * });
   */

	/**
   * Función que se ejecutará cuando se produzca la validación de los datos permitiendo personalizar los errores de validación.
   *
   * @callback module:rup_validate~onShowErrors
   * @param {Object} errorMap - Pares de clave/valor, donde el key se corresponde con el name del campo del formulario y el value con el mensaje que se va a mostrar para ese campo.
   * @param {Object[]} errorList - Array de objetos correspondientes a los campos validados.
   * @param {String} errorList.message - Mensaje que va mostrarse para ese campo.
   * @param {Element} errorList.element - Objeto del DOM correspondiente a ese campo.
   * @example
   * $(".selector").validate({
   *  showErrors: function(errorMap, errorList) {
   *    $("#summary").html("Your form contains "
   *      + this.numberOfInvalids()
   *      + " errors, see details below.");
   *    this.defaultShowErrors();
   *  }
   * });
   */

	/**
   * Función de callback que permite personalizar el lugar en el que se posicionarán los mensajes de error.
   *
   * @callback module:rup_validate~onErrorPlacement
   * @param {jQuery} error - Referencia al objeto label que va a ser insertado en el DOM para visualizar los errores.
   * @param {jQuery} element - Referencia al campo validado.
   * @example
   * $("#myform").validate({
   *   errorPlacement: function(error, element) {
   *       error.appendTo( element.parent("td").next("td") );
   *   }
   * });
   */

	/**
   * Función de callback para determinar como se debe resaltar los campos inválidos.
   *
   * @callback module:rup_validate~onHighlight
   * @param {jQuery} element - Referencia al campo validado.
   * @param {String} errorClass - Valor actual del parámetro errorClass.
   * @param {String} validClass - Valor actual del parámetro validClass.
   * @example
   * $(".selector").validate({
   *   highlight: function(element, errorClass, validClass) {
   *        $(element).fadeOut(function() {
   *            $(element).fadeIn();
   *        });
   *   }
   * });
   */

	/**
   * Función de callback para determinar como se debe resaltar los campos inválidos.
   *
   * @callback module:rup_validate~onUnhighlight
   * @param {jQuery} element - Referencia al campo validado.
   * @param {String} errorClass - Valor actual del parámetro errorClass.
   * @param {String} validClass - Valor actual del parámetro validClass.
   * @example
   * $(".selector").validate({
   *  highlight: function(element, errorClass, validClass) {
   *    $(element).addClass(errorClass).removeClass(validClass);
   *    $(element.form).find("label[for=" + element.id + "]")
   *      .addClass(errorClass);
   *  },
   *  unhighlight: function(element, errorClass, validClass) {
   *    $(element).removeClass(errorClass).addClass(validClass);
   *    $(element.form).find("label[for=" + element.id + "]")
   *      .removeClass(errorClass);
   *  }
   * });
   */

	/**
   * @description Propiedades de configuración del componente.
   * @see Para mas información consulte la documentación acerca de las opciones de configuración del plugin {@link http://jqueryvalidation.org/validate/|jQuery Validation Plugin}.
   *
   * @name options
   * @property {boolean} [debug=false] - Activa el modo debug. En caso de estar activado el formulario no se envía el formulario y los errores de ejecución que se hayan producido se visualizan en la consola. Requiere Firebug o Firebug lite.
   * @property {module:rup_validate~onSubmitHandler} [submitHandler] - Método callback utilizado para capturar el evento submit cuando el formulario es válido. Reemplaza el submit por defecto. Es el método utilizado para realizar un submit mediante AJAX después de ser validado.
   * @property {module:rup_validate~onInvalidHandler} [invalidHandler] - Método callback que se ejecuta cuando un formulario presenta errores de validación.
   * @property {Selector} [ignore] - Selector jQuery que identifica los elementos del formulario que van a ser ignorados al realizarse las validaciones.
   * @property {object} [messages] - Utilizado para indicar mensajes propios para las validaciones. Estos se especifican mediante pares de clave/valor. La clave es el nombre del elemento mientras que el valor es el texto que se ha de mostrar en caso de producirse un error en la validación.
   * @property {object} [groups] - Se utiliza para realizar agrupamientos de mensajes de error.
   * @property {boolean} [onsubmit=true] - Determina si se valida el formulario al realizarse el submit. Marcar como false para realizar las validaciones mediante el resto de eventos.
   * @property {boolean} [ofocusout=true] - Determina si se realiza la validación de los campos (excepto los checkbox y radio) al lanzarse los eventos blur. Estas validaciones se realizan únicamente una vez que un campo ha sido marcado como inválido.
   * @property {boolean} [okeyup=true] - Determina si se realiza la validación de los campos (excepto los checkbox y radio) al lanzarse los eventos keyup. Las validaciones se realizan únicamente una vez que un campo ha sido marcado como inválido.
   * @property {boolean} [onclick=true] - Determina si se realizan las validaciones de los checkbox y radio al realizar un click sobre los mismos.
   * @property {boolean} [focusInvalid=true] - Posiciona el foco en el último campo activo o en el primer campo inválido la realizarse la validación de los campos. En caso de encontrarse el foco en un campo al realizarse la validación se mantiene en dicho campo. En caso de no encontrarse el foco en un campo, se posicionará en el primer campo inválido existente.
   * @property {boolean} [focusCleanup=false] - En caso de activarse, elimina el errorClass correspondiente y oculta los mensajes de error de los campos que reciben el foco. Evitar utilizar esta propiedad en conjunción con focusInvalid.
   * @property {Selector} [meta] - En caso de utilizar metainformación en los campos que sea utilizada por otros plugins, es posible indicar un identificador para envolver la metadata correspondiente al el componente validate dentro de un objeto propio.
   * @property {String} [errorClass=error] - Determina el nombre del class que va a aplicarse a los campos que presenten errores de validación.
   * @property {String} [validClass=valid] - Determina el nombre del class que va a aplicarse a los campos que han sido validados y no presenten errores.
   * @property {String} [errorElement=label] - Determina el tipo del elemento que va a utilizarse para generar los mensajes de error.
   * @property {String} [wrapper=window] - Recubre los mensajes de error con el elemento especificado. Util en conjunción la propiedad errorLabelContainer para crear listado de errores.
   * @property {Selector} [errorLabelContainer] - Determina el objeto contenedor en el que se van a mostrar los mensajes de error.
   * @property {Selector} [errorContainer] - Determina un contenedor adicional para los mensajes de error.
   * @property {boolean} [ignoreTitle=false] - Determina si se evita el obtener los mensajes a partir del atributo title.
   * @property {module:rup_validate~onShowErrors} [showErrors] - Función callback para realizar un tratamiento  personalizado de los errores de validación.
   * @property {module:rup_validate~onErrorPlacement} [errorPlacement] - Función de callback que permite personalizar el lugar en el que se posicionarán los mensajes de error.
   * @property {module:rup_validate~onHighlight} [highlight] - Función de callback para determinar como se debe resaltar los campos inválidos.
   * @property {module:rup_validate~onUnhighlight} [unhighlight] - Función de callback para restaurar los cambios realizados por la función indicada en la propiedad highlight.
   */

	/* **********/
	/* EVENTOS */
	/* **********/

	/**
   * Este evento es lanzado cuando se produce alguna violación entre las reglas de validación especificadas para ser aplicadas sobre los campos del formulario.
   *
   * @event module:rup_validate#rupValidate_formValidationError
   * @property {Event} e - Objeto Event correspondiente al evento disparado.
   * @example
   * $("#idFormulario").on("rupValidate_formValidationError", function(event){
   * });
   */
});
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))

/***/ }),
/* 19 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function(jQuery) {var _typeof = typeof Symbol === "function" && typeof Symbol.iterator === "symbol" ? function (obj) { return typeof obj; } : function (obj) { return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj; };

/*
* jQuery timepicker addon
* By: Trent Richardson [http://trentrichardson.com]
* Version 1.0.1
* Last Modified: 07/01/2012
*
* Copyright 2012 Trent Richardson
* You may use this project under MIT or GPL licenses.
* http://trentrichardson.com/Impromptu/GPL-LICENSE.txt
* http://trentrichardson.com/Impromptu/MIT-LICENSE.txt
*
* HERES THE CSS:
* .ui-timepicker-div .ui-widget-header { margin-bottom: 8px; }
* .ui-timepicker-div dl { text-align: left; }
* .ui-timepicker-div dl dt { height: 25px; margin-bottom: -25px; }
* .ui-timepicker-div dl dd { margin: 0 10px 10px 65px; }
* .ui-timepicker-div td { font-size: 90%; }
* .ui-tpicker-grid-label { background: none; border: none; margin: 0; padding: 0; }
*/

/*jslint evil: true, maxlen: 300, white: false, undef: false, nomen: false, onevar: false */

(function ($) {

	// Prevent "Uncaught RangeError: Maximum call stack size exceeded"
	$.ui.timepicker = $.ui.timepicker || {};
	if ($.ui.timepicker.version) {
		return;
	}

	$.extend($.ui, { timepicker: { version: "1.0.1" } });

	/* Time picker manager.
    Use the singleton instance of this class, $.timepicker, to interact with the time picker.
    Settings for (groups of) time pickers are maintained in an instance object,
    allowing multiple different settings on the same page. */

	function Timepicker() {
		this.regional = []; // Available regional settings, indexed by language code
		this.regional[''] = { // Default regional settings
			currentText: 'Now',
			closeText: 'Done',
			ampm: false,
			amNames: ['AM', 'A'],
			pmNames: ['PM', 'P'],
			timeFormat: 'hh:mm tt',
			timeSuffix: '',
			timeOnlyTitle: 'Choose Time',
			timeText: 'Time',
			hourText: 'Hour',
			minuteText: 'Minute',
			secondText: 'Second',
			millisecText: 'Millisecond',
			timezoneText: 'Time Zone'
		};
		this._defaults = { // Global defaults for all the datetime picker instances
			showButtonPanel: true,
			timeOnly: false,
			showHour: true,
			showMinute: true,
			showSecond: false,
			showMillisec: false,
			showTimezone: false,
			showTime: true,
			stepHour: 1,
			stepMinute: 1,
			stepSecond: 1,
			stepMillisec: 1,
			hour: 0,
			minute: 0,
			second: 0,
			millisec: 0,
			timezone: null,
			useLocalTimezone: false,
			defaultTimezone: "+0000",
			hourMin: 0,
			minuteMin: 0,
			secondMin: 0,
			millisecMin: 0,
			hourMax: 23,
			minuteMax: 59,
			secondMax: 59,
			millisecMax: 999,
			minDateTime: null,
			maxDateTime: null,
			onSelect: null,
			hourGrid: 0,
			minuteGrid: 0,
			secondGrid: 0,
			millisecGrid: 0,
			alwaysSetTime: true,
			separator: ' ',
			altFieldTimeOnly: true,
			showTimepicker: true,
			timezoneIso8601: false,
			timezoneList: null,
			addSliderAccess: false,
			sliderAccessArgs: null
		};
		$.extend(this._defaults, this.regional['']);
	}

	$.extend(Timepicker.prototype, {
		$input: null,
		$altInput: null,
		$timeObj: null,
		inst: null,
		hour_slider: null,
		minute_slider: null,
		second_slider: null,
		millisec_slider: null,
		timezone_select: null,
		hour: 0,
		minute: 0,
		second: 0,
		millisec: 0,
		timezone: null,
		defaultTimezone: "+0000",
		hourMinOriginal: null,
		minuteMinOriginal: null,
		secondMinOriginal: null,
		millisecMinOriginal: null,
		hourMaxOriginal: null,
		minuteMaxOriginal: null,
		secondMaxOriginal: null,
		millisecMaxOriginal: null,
		ampm: '',
		formattedDate: '',
		formattedTime: '',
		formattedDateTime: '',
		timezoneList: null,

		/* Override the default settings for all instances of the time picker.
     @param  settings  object - the new settings to use as defaults (anonymous object)
     @return the manager object */
		setDefaults: function setDefaults(settings) {
			extendRemove(this._defaults, settings || {});
			return this;
		},

		//########################################################################
		// Create a new Timepicker instance
		//########################################################################
		_newInst: function _newInst($input, o) {
			var tp_inst = new Timepicker(),
			    inlineSettings = {};

			for (var attrName in this._defaults) {
				var attrValue = $input.attr('time:' + attrName);
				if (attrValue) {
					try {
						inlineSettings[attrName] = eval(attrValue);
					} catch (err) {
						inlineSettings[attrName] = attrValue;
					}
				}
			}
			tp_inst._defaults = $.extend({}, this._defaults, inlineSettings, o, {
				beforeShow: function beforeShow(input, dp_inst) {
					if ($.isFunction(o.beforeShow)) {
						return o.beforeShow(input, dp_inst, tp_inst);
					}
				},
				onChangeMonthYear: function onChangeMonthYear(year, month, dp_inst) {
					// Update the time as well : this prevents the time from disappearing from the $input field.
					tp_inst._updateDateTime(dp_inst);
					if ($.isFunction(o.onChangeMonthYear)) {
						o.onChangeMonthYear.call($input[0], year, month, dp_inst, tp_inst);
					}
				},
				onClose: function onClose(dateText, dp_inst) {
					if (tp_inst.timeDefined === true && $input.val() !== '') {
						tp_inst._updateDateTime(dp_inst);
					}
					if ($.isFunction(o.onClose)) {
						o.onClose.call($input[0], dateText, dp_inst, tp_inst);
					}
				},
				timepicker: tp_inst // add timepicker as a property of datepicker: $.datepicker._get(dp_inst, 'timepicker');
			});
			tp_inst.amNames = $.map(tp_inst._defaults.amNames, function (val) {
				return val.toUpperCase();
			});
			tp_inst.pmNames = $.map(tp_inst._defaults.pmNames, function (val) {
				return val.toUpperCase();
			});

			if (tp_inst._defaults.timezoneList === null) {
				var timezoneList = [];
				for (var i = -11; i <= 12; i++) {
					timezoneList.push((i >= 0 ? '+' : '-') + ('0' + Math.abs(i).toString()).slice(-2) + '00');
				}
				if (tp_inst._defaults.timezoneIso8601) {
					timezoneList = $.map(timezoneList, function (val) {
						return val == '+0000' ? 'Z' : val.substring(0, 3) + ':' + val.substring(3);
					});
				}
				tp_inst._defaults.timezoneList = timezoneList;
			}

			tp_inst.timezone = tp_inst._defaults.timezone;
			tp_inst.hour = tp_inst._defaults.hour;
			tp_inst.minute = tp_inst._defaults.minute;
			tp_inst.second = tp_inst._defaults.second;
			tp_inst.millisec = tp_inst._defaults.millisec;
			tp_inst.ampm = '';
			tp_inst.$input = $input;

			if (o.altField) {
				tp_inst.$altInput = $(o.altField).css({ cursor: 'pointer' }).focus(function () {
					$input.trigger("focus");
				});
			}

			if (tp_inst._defaults.minDate === 0 || tp_inst._defaults.minDateTime === 0) {
				tp_inst._defaults.minDate = new Date();
			}
			if (tp_inst._defaults.maxDate === 0 || tp_inst._defaults.maxDateTime === 0) {
				tp_inst._defaults.maxDate = new Date();
			}

			// datepicker needs minDate/maxDate, timepicker needs minDateTime/maxDateTime..
			if (tp_inst._defaults.minDate !== undefined && tp_inst._defaults.minDate instanceof Date) {
				tp_inst._defaults.minDateTime = new Date(tp_inst._defaults.minDate.getTime());
			}
			if (tp_inst._defaults.minDateTime !== undefined && tp_inst._defaults.minDateTime instanceof Date) {
				tp_inst._defaults.minDate = new Date(tp_inst._defaults.minDateTime.getTime());
			}
			if (tp_inst._defaults.maxDate !== undefined && tp_inst._defaults.maxDate instanceof Date) {
				tp_inst._defaults.maxDateTime = new Date(tp_inst._defaults.maxDate.getTime());
			}
			if (tp_inst._defaults.maxDateTime !== undefined && tp_inst._defaults.maxDateTime instanceof Date) {
				tp_inst._defaults.maxDate = new Date(tp_inst._defaults.maxDateTime.getTime());
			}
			return tp_inst;
		},

		//########################################################################
		// add our sliders to the calendar
		//########################################################################
		_addTimePicker: function _addTimePicker(dp_inst) {
			var currDT = this.$altInput && this._defaults.altFieldTimeOnly ? this.$input.val() + ' ' + this.$altInput.val() : this.$input.val();

			this.timeDefined = this._parseTime(currDT);
			this._limitMinMaxDateTime(dp_inst, false);
			this._injectTimePicker();
		},

		//########################################################################
		// parse the time string from input value or _setTime
		//########################################################################
		_parseTime: function _parseTime(timeString, withDate) {
			if (!this.inst) {
				this.inst = $.datepicker._getInst(this.$input[0]);
			}

			if (withDate || !this._defaults.timeOnly) {
				var dp_dateFormat = $.datepicker._get(this.inst, 'dateFormat');
				try {
					var parseRes = parseDateTimeInternal(dp_dateFormat, this._defaults.timeFormat, timeString, $.datepicker._getFormatConfig(this.inst), this._defaults);
					if (!parseRes.timeObj) {
						return false;
					}
					$.extend(this, parseRes.timeObj);
				} catch (err) {
					return false;
				}
				return true;
			} else {
				var timeObj = $.datepicker.parseTime(this._defaults.timeFormat, timeString, this._defaults);
				if (!timeObj) {
					return false;
				}
				$.extend(this, timeObj);
				return true;
			}
		},

		//########################################################################
		// generate and inject html for timepicker into ui datepicker
		//########################################################################
		_injectTimePicker: function _injectTimePicker() {
			var $dp = this.inst.dpDiv,
			    o = this._defaults,
			    tp_inst = this,

			// Added by Peter Medeiros:
			// - Figure out what the hour/minute/second max should be based on the step values.
			// - Example: if stepMinute is 15, then minMax is 45.
			hourMax = parseInt(o.hourMax - (o.hourMax - o.hourMin) % o.stepHour, 10),
			    minMax = parseInt(o.minuteMax - (o.minuteMax - o.minuteMin) % o.stepMinute, 10),
			    secMax = parseInt(o.secondMax - (o.secondMax - o.secondMin) % o.stepSecond, 10),
			    millisecMax = parseInt(o.millisecMax - (o.millisecMax - o.millisecMin) % o.stepMillisec, 10),
			    dp_id = this.inst.id.toString().replace(/([^A-Za-z0-9_])/g, '');

			// Prevent displaying twice
			//if ($dp.find("div#ui-timepicker-div-"+ dp_id).length === 0) {
			if ($dp.find("div#ui-timepicker-div-" + dp_id).length === 0 && o.showTimepicker) {
				var noDisplay = ' style="display:none;"',
				    html = '<div class="ui-timepicker-div" id="ui-timepicker-div-' + dp_id + '"><dl>' + '<dt class="ui_tpicker_time_label" id="ui_tpicker_time_label_' + dp_id + '"' + (o.showTime ? '' : noDisplay) + '>' + o.timeText + '</dt>' + '<dd class="ui_tpicker_time" id="ui_tpicker_time_' + dp_id + '"' + (o.showTime ? '' : noDisplay) + '></dd>' + '<dt class="ui_tpicker_hour_label" id="ui_tpicker_hour_label_' + dp_id + '"' + (o.showHour ? '' : noDisplay) + '>' + o.hourText + '</dt>',
				    hourGridSize = 0,
				    minuteGridSize = 0,
				    secondGridSize = 0,
				    millisecGridSize = 0,
				    size = null;

				// Hours
				html += '<dd class="ui_tpicker_hour"><div id="ui_tpicker_hour_' + dp_id + '"' + (o.showHour ? '' : noDisplay) + '></div>';
				if (o.showHour && o.hourGrid > 0) {
					html += '<div style="padding-left: 1px"><table class="ui-tpicker-grid-label"><tr>';

					for (var h = o.hourMin; h <= hourMax; h += parseInt(o.hourGrid, 10)) {
						hourGridSize++;
						var tmph = o.ampm && h > 12 ? h - 12 : h;
						if (tmph < 10) {
							tmph = '0' + tmph;
						}
						if (o.ampm) {
							if (h === 0) {
								tmph = 12 + 'a';
							} else {
								if (h < 12) {
									tmph += 'a';
								} else {
									tmph += 'p';
								}
							}
						}
						html += '<td>' + tmph + '</td>';
					}

					html += '</tr></table></div>';
				}
				html += '</dd>';

				// Minutes
				html += '<dt class="ui_tpicker_minute_label" id="ui_tpicker_minute_label_' + dp_id + '"' + (o.showMinute ? '' : noDisplay) + '>' + o.minuteText + '</dt>' + '<dd class="ui_tpicker_minute"><div id="ui_tpicker_minute_' + dp_id + '"' + (o.showMinute ? '' : noDisplay) + '></div>';

				if (o.showMinute && o.minuteGrid > 0) {
					html += '<div style="padding-left: 1px"><table class="ui-tpicker-grid-label"><tr>';

					for (var m = o.minuteMin; m <= minMax; m += parseInt(o.minuteGrid, 10)) {
						minuteGridSize++;
						html += '<td>' + (m < 10 ? '0' : '') + m + '</td>';
					}

					html += '</tr></table></div>';
				}
				html += '</dd>';

				// Seconds
				html += '<dt class="ui_tpicker_second_label" id="ui_tpicker_second_label_' + dp_id + '"' + (o.showSecond ? '' : noDisplay) + '>' + o.secondText + '</dt>' + '<dd class="ui_tpicker_second"><div id="ui_tpicker_second_' + dp_id + '"' + (o.showSecond ? '' : noDisplay) + '></div>';

				if (o.showSecond && o.secondGrid > 0) {
					html += '<div style="padding-left: 1px"><table><tr>';

					for (var s = o.secondMin; s <= secMax; s += parseInt(o.secondGrid, 10)) {
						secondGridSize++;
						html += '<td>' + (s < 10 ? '0' : '') + s + '</td>';
					}

					html += '</tr></table></div>';
				}
				html += '</dd>';

				// Milliseconds
				html += '<dt class="ui_tpicker_millisec_label" id="ui_tpicker_millisec_label_' + dp_id + '"' + (o.showMillisec ? '' : noDisplay) + '>' + o.millisecText + '</dt>' + '<dd class="ui_tpicker_millisec"><div id="ui_tpicker_millisec_' + dp_id + '"' + (o.showMillisec ? '' : noDisplay) + '></div>';

				if (o.showMillisec && o.millisecGrid > 0) {
					html += '<div style="padding-left: 1px"><table><tr>';

					for (var l = o.millisecMin; l <= millisecMax; l += parseInt(o.millisecGrid, 10)) {
						millisecGridSize++;
						html += '<td>' + (l < 10 ? '0' : '') + l + '</td>';
					}

					html += '</tr></table></div>';
				}
				html += '</dd>';

				// Timezone
				html += '<dt class="ui_tpicker_timezone_label" id="ui_tpicker_timezone_label_' + dp_id + '"' + (o.showTimezone ? '' : noDisplay) + '>' + o.timezoneText + '</dt>';
				html += '<dd class="ui_tpicker_timezone" id="ui_tpicker_timezone_' + dp_id + '"' + (o.showTimezone ? '' : noDisplay) + '></dd>';

				html += '</dl></div>';
				var $tp = $(html);

				// if we only want time picker...
				if (o.timeOnly === true) {
					$tp.prepend('<div class="ui-widget-header ui-helper-clearfix ui-corner-all">' + '<div class="ui-datepicker-title">' + o.timeOnlyTitle + '</div>' + '</div>');
					$dp.find('.ui-datepicker-header, .ui-datepicker-calendar').hide();
				}

				this.hour_slider = $tp.find('#ui_tpicker_hour_' + dp_id).slider({
					orientation: "horizontal",
					value: this.hour,
					min: o.hourMin,
					max: hourMax,
					step: o.stepHour,
					slide: function slide(event, ui) {
						tp_inst.hour_slider.slider("option", "value", ui.value);
						tp_inst._onTimeChange();
					}
				});

				// Updated by Peter Medeiros:
				// - Pass in Event and UI instance into slide function
				this.minute_slider = $tp.find('#ui_tpicker_minute_' + dp_id).slider({
					orientation: "horizontal",
					value: this.minute,
					min: o.minuteMin,
					max: minMax,
					step: o.stepMinute,
					slide: function slide(event, ui) {
						tp_inst.minute_slider.slider("option", "value", ui.value);
						tp_inst._onTimeChange();
					}
				});

				this.second_slider = $tp.find('#ui_tpicker_second_' + dp_id).slider({
					orientation: "horizontal",
					value: this.second,
					min: o.secondMin,
					max: secMax,
					step: o.stepSecond,
					slide: function slide(event, ui) {
						tp_inst.second_slider.slider("option", "value", ui.value);
						tp_inst._onTimeChange();
					}
				});

				this.millisec_slider = $tp.find('#ui_tpicker_millisec_' + dp_id).slider({
					orientation: "horizontal",
					value: this.millisec,
					min: o.millisecMin,
					max: millisecMax,
					step: o.stepMillisec,
					slide: function slide(event, ui) {
						tp_inst.millisec_slider.slider("option", "value", ui.value);
						tp_inst._onTimeChange();
					}
				});

				this.timezone_select = $tp.find('#ui_tpicker_timezone_' + dp_id).append('<select></select>').find("select");
				$.fn.append.apply(this.timezone_select, $.map(o.timezoneList, function (val, idx) {
					return $("<option />").val((typeof val === 'undefined' ? 'undefined' : _typeof(val)) == "object" ? val.value : val).text((typeof val === 'undefined' ? 'undefined' : _typeof(val)) == "object" ? val.label : val);
				}));
				if (typeof this.timezone != "undefined" && this.timezone !== null && this.timezone !== "") {
					var local_date = new Date(this.inst.selectedYear, this.inst.selectedMonth, this.inst.selectedDay, 12);
					var local_timezone = timeZoneString(local_date);
					if (local_timezone == this.timezone) {
						selectLocalTimeZone(tp_inst);
					} else {
						this.timezone_select.val(this.timezone);
					}
				} else {
					if (typeof this.hour != "undefined" && this.hour !== null && this.hour !== "") {
						this.timezone_select.val(o.defaultTimezone);
					} else {
						selectLocalTimeZone(tp_inst);
					}
				}
				this.timezone_select.change(function () {
					tp_inst._defaults.useLocalTimezone = false;
					tp_inst._onTimeChange();
				});

				// Add grid functionality
				if (o.showHour && o.hourGrid > 0) {
					size = 100 * hourGridSize * o.hourGrid / (hourMax - o.hourMin);

					$tp.find(".ui_tpicker_hour table").css({
						width: size + "%",
						marginLeft: size / (-2 * hourGridSize) + "%",
						borderCollapse: 'collapse'
					}).find("td").each(function (index) {
						$(this).click(function () {
							var h = $(this).html();
							if (o.ampm) {
								var ap = h.substring(2).toLowerCase(),
								    aph = parseInt(h.substring(0, 2), 10);
								if (ap == 'a') {
									if (aph == 12) {
										h = 0;
									} else {
										h = aph;
									}
								} else if (aph == 12) {
									h = 12;
								} else {
									h = aph + 12;
								}
							}
							tp_inst.hour_slider.slider("option", "value", h);
							tp_inst._onTimeChange();
							tp_inst._onSelectHandler();
						}).css({
							cursor: 'pointer',
							width: 100 / hourGridSize + '%',
							textAlign: 'center',
							overflow: 'hidden'
						});
					});
				}

				if (o.showMinute && o.minuteGrid > 0) {
					size = 100 * minuteGridSize * o.minuteGrid / (minMax - o.minuteMin);
					$tp.find(".ui_tpicker_minute table").css({
						width: size + "%",
						marginLeft: size / (-2 * minuteGridSize) + "%",
						borderCollapse: 'collapse'
					}).find("td").each(function (index) {
						$(this).click(function () {
							tp_inst.minute_slider.slider("option", "value", $(this).html());
							tp_inst._onTimeChange();
							tp_inst._onSelectHandler();
						}).css({
							cursor: 'pointer',
							width: 100 / minuteGridSize + '%',
							textAlign: 'center',
							overflow: 'hidden'
						});
					});
				}

				if (o.showSecond && o.secondGrid > 0) {
					$tp.find(".ui_tpicker_second table").css({
						width: size + "%",
						marginLeft: size / (-2 * secondGridSize) + "%",
						borderCollapse: 'collapse'
					}).find("td").each(function (index) {
						$(this).click(function () {
							tp_inst.second_slider.slider("option", "value", $(this).html());
							tp_inst._onTimeChange();
							tp_inst._onSelectHandler();
						}).css({
							cursor: 'pointer',
							width: 100 / secondGridSize + '%',
							textAlign: 'center',
							overflow: 'hidden'
						});
					});
				}

				if (o.showMillisec && o.millisecGrid > 0) {
					$tp.find(".ui_tpicker_millisec table").css({
						width: size + "%",
						marginLeft: size / (-2 * millisecGridSize) + "%",
						borderCollapse: 'collapse'
					}).find("td").each(function (index) {
						$(this).click(function () {
							tp_inst.millisec_slider.slider("option", "value", $(this).html());
							tp_inst._onTimeChange();
							tp_inst._onSelectHandler();
						}).css({
							cursor: 'pointer',
							width: 100 / millisecGridSize + '%',
							textAlign: 'center',
							overflow: 'hidden'
						});
					});
				}

				var $buttonPanel = $dp.find('.ui-datepicker-buttonpane');
				if ($buttonPanel.length) {
					$buttonPanel.before($tp);
				} else {
					$dp.append($tp);
				}

				this.$timeObj = $tp.find('#ui_tpicker_time_' + dp_id);

				if (this.inst !== null) {
					var timeDefined = this.timeDefined;
					this._onTimeChange();
					this.timeDefined = timeDefined;
				}

				//Emulate datepicker onSelect behavior. Call on slidestop.
				var onSelectDelegate = function onSelectDelegate() {
					tp_inst._onSelectHandler();
				};
				this.hour_slider.bind('slidestop', onSelectDelegate);
				this.minute_slider.bind('slidestop', onSelectDelegate);
				this.second_slider.bind('slidestop', onSelectDelegate);
				this.millisec_slider.bind('slidestop', onSelectDelegate);

				// slideAccess integration: http://trentrichardson.com/2011/11/11/jquery-ui-sliders-and-touch-accessibility/
				if (this._defaults.addSliderAccess) {
					var sliderAccessArgs = this._defaults.sliderAccessArgs;
					setTimeout(function () {
						// fix for inline mode
						if ($tp.find('.ui-slider-access').length === 0) {
							$tp.find('.ui-slider:visible').sliderAccess(sliderAccessArgs);

							// fix any grids since sliders are shorter
							var sliderAccessWidth = $tp.find('.ui-slider-access:eq(0)').outerWidth(true);
							if (sliderAccessWidth) {
								$tp.find('table:visible').each(function () {
									var $g = $(this),
									    oldWidth = $g.outerWidth(),
									    oldMarginLeft = $g.css('marginLeft').toString().replace('%', ''),
									    newWidth = oldWidth - sliderAccessWidth,
									    newMarginLeft = oldMarginLeft * newWidth / oldWidth + '%';

									$g.css({ width: newWidth, marginLeft: newMarginLeft });
								});
							}
						}
					}, 0);
				}
				// end slideAccess integration
			}
		},

		//########################################################################
		// This function tries to limit the ability to go outside the
		// min/max date range
		//########################################################################
		_limitMinMaxDateTime: function _limitMinMaxDateTime(dp_inst, adjustSliders) {
			var o = this._defaults,
			    dp_date = new Date(dp_inst.selectedYear, dp_inst.selectedMonth, dp_inst.selectedDay);

			if (!this._defaults.showTimepicker) {
				return;
			} // No time so nothing to check here

			if ($.datepicker._get(dp_inst, 'minDateTime') !== null && $.datepicker._get(dp_inst, 'minDateTime') !== undefined && dp_date) {
				var minDateTime = $.datepicker._get(dp_inst, 'minDateTime'),
				    minDateTimeDate = new Date(minDateTime.getFullYear(), minDateTime.getMonth(), minDateTime.getDate(), 0, 0, 0, 0);

				if (this.hourMinOriginal === null || this.minuteMinOriginal === null || this.secondMinOriginal === null || this.millisecMinOriginal === null) {
					this.hourMinOriginal = o.hourMin;
					this.minuteMinOriginal = o.minuteMin;
					this.secondMinOriginal = o.secondMin;
					this.millisecMinOriginal = o.millisecMin;
				}

				if (dp_inst.settings.timeOnly || minDateTimeDate.getTime() == dp_date.getTime()) {
					this._defaults.hourMin = minDateTime.getHours();
					if (this.hour <= this._defaults.hourMin) {
						this.hour = this._defaults.hourMin;
						this._defaults.minuteMin = minDateTime.getMinutes();
						if (this.minute <= this._defaults.minuteMin) {
							this.minute = this._defaults.minuteMin;
							this._defaults.secondMin = minDateTime.getSeconds();
						} else if (this.second <= this._defaults.secondMin) {
							this.second = this._defaults.secondMin;
							this._defaults.millisecMin = minDateTime.getMilliseconds();
						} else {
							if (this.millisec < this._defaults.millisecMin) {
								this.millisec = this._defaults.millisecMin;
							}
							this._defaults.millisecMin = this.millisecMinOriginal;
						}
					} else {
						this._defaults.minuteMin = this.minuteMinOriginal;
						this._defaults.secondMin = this.secondMinOriginal;
						this._defaults.millisecMin = this.millisecMinOriginal;
					}
				} else {
					this._defaults.hourMin = this.hourMinOriginal;
					this._defaults.minuteMin = this.minuteMinOriginal;
					this._defaults.secondMin = this.secondMinOriginal;
					this._defaults.millisecMin = this.millisecMinOriginal;
				}
			}

			if ($.datepicker._get(dp_inst, 'maxDateTime') !== null && $.datepicker._get(dp_inst, 'maxDateTime') !== undefined && dp_date) {
				var maxDateTime = $.datepicker._get(dp_inst, 'maxDateTime'),
				    maxDateTimeDate = new Date(maxDateTime.getFullYear(), maxDateTime.getMonth(), maxDateTime.getDate(), 0, 0, 0, 0);

				if (this.hourMaxOriginal === null || this.minuteMaxOriginal === null || this.secondMaxOriginal === null) {
					this.hourMaxOriginal = o.hourMax;
					this.minuteMaxOriginal = o.minuteMax;
					this.secondMaxOriginal = o.secondMax;
					this.millisecMaxOriginal = o.millisecMax;
				}

				if (dp_inst.settings.timeOnly || maxDateTimeDate.getTime() == dp_date.getTime()) {
					this._defaults.hourMax = maxDateTime.getHours();
					if (this.hour >= this._defaults.hourMax) {
						this.hour = this._defaults.hourMax;
						this._defaults.minuteMax = maxDateTime.getMinutes();
						if (this.minute >= this._defaults.minuteMax) {
							this.minute = this._defaults.minuteMax;
							this._defaults.secondMax = maxDateTime.getSeconds();
						} else if (this.second >= this._defaults.secondMax) {
							this.second = this._defaults.secondMax;
							this._defaults.millisecMax = maxDateTime.getMilliseconds();
						} else {
							if (this.millisec > this._defaults.millisecMax) {
								this.millisec = this._defaults.millisecMax;
							}
							this._defaults.millisecMax = this.millisecMaxOriginal;
						}
					} else {
						this._defaults.minuteMax = this.minuteMaxOriginal;
						this._defaults.secondMax = this.secondMaxOriginal;
						this._defaults.millisecMax = this.millisecMaxOriginal;
					}
				} else {
					this._defaults.hourMax = this.hourMaxOriginal;
					this._defaults.minuteMax = this.minuteMaxOriginal;
					this._defaults.secondMax = this.secondMaxOriginal;
					this._defaults.millisecMax = this.millisecMaxOriginal;
				}
			}

			if (adjustSliders !== undefined && adjustSliders === true) {
				var hourMax = parseInt(this._defaults.hourMax - (this._defaults.hourMax - this._defaults.hourMin) % this._defaults.stepHour, 10),
				    minMax = parseInt(this._defaults.minuteMax - (this._defaults.minuteMax - this._defaults.minuteMin) % this._defaults.stepMinute, 10),
				    secMax = parseInt(this._defaults.secondMax - (this._defaults.secondMax - this._defaults.secondMin) % this._defaults.stepSecond, 10),
				    millisecMax = parseInt(this._defaults.millisecMax - (this._defaults.millisecMax - this._defaults.millisecMin) % this._defaults.stepMillisec, 10);

				if (this.hour_slider) {
					this.hour_slider.slider("option", { min: this._defaults.hourMin, max: hourMax }).slider('value', this.hour);
				}
				if (this.minute_slider) {
					this.minute_slider.slider("option", { min: this._defaults.minuteMin, max: minMax }).slider('value', this.minute);
				}
				if (this.second_slider) {
					this.second_slider.slider("option", { min: this._defaults.secondMin, max: secMax }).slider('value', this.second);
				}
				if (this.millisec_slider) {
					this.millisec_slider.slider("option", { min: this._defaults.millisecMin, max: millisecMax }).slider('value', this.millisec);
				}
			}
		},

		//########################################################################
		// when a slider moves, set the internal time...
		// on time change is also called when the time is updated in the text field
		//########################################################################
		_onTimeChange: function _onTimeChange() {
			var hour = this.hour_slider ? this.hour_slider.slider('value') : false,
			    minute = this.minute_slider ? this.minute_slider.slider('value') : false,
			    second = this.second_slider ? this.second_slider.slider('value') : false,
			    millisec = this.millisec_slider ? this.millisec_slider.slider('value') : false,
			    timezone = this.timezone_select ? this.timezone_select.val() : false,
			    o = this._defaults;

			if ((typeof hour === 'undefined' ? 'undefined' : _typeof(hour)) == 'object') {
				hour = false;
			}
			if ((typeof minute === 'undefined' ? 'undefined' : _typeof(minute)) == 'object') {
				minute = false;
			}
			if ((typeof second === 'undefined' ? 'undefined' : _typeof(second)) == 'object') {
				second = false;
			}
			if ((typeof millisec === 'undefined' ? 'undefined' : _typeof(millisec)) == 'object') {
				millisec = false;
			}
			if ((typeof timezone === 'undefined' ? 'undefined' : _typeof(timezone)) == 'object') {
				timezone = false;
			}

			if (hour !== false) {
				hour = parseInt(hour, 10);
			}
			if (minute !== false) {
				minute = parseInt(minute, 10);
			}
			if (second !== false) {
				second = parseInt(second, 10);
			}
			if (millisec !== false) {
				millisec = parseInt(millisec, 10);
			}

			var ampm = o[hour < 12 ? 'amNames' : 'pmNames'][0];

			// If the update was done in the input field, the input field should not be updated.
			// If the update was done using the sliders, update the input field.
			var hasChanged = hour != this.hour || minute != this.minute || second != this.second || millisec != this.millisec || this.ampm.length > 0 && hour < 12 != ($.inArray(this.ampm.toUpperCase(), this.amNames) !== -1) || timezone != this.timezone;

			if (hasChanged) {

				if (hour !== false) {
					this.hour = hour;
				}
				if (minute !== false) {
					this.minute = minute;
				}
				if (second !== false) {
					this.second = second;
				}
				if (millisec !== false) {
					this.millisec = millisec;
				}
				if (timezone !== false) {
					this.timezone = timezone;
				}

				if (!this.inst) {
					this.inst = $.datepicker._getInst(this.$input[0]);
				}

				this._limitMinMaxDateTime(this.inst, true);
			}
			if (o.ampm) {
				this.ampm = ampm;
			}

			//this._formatTime();
			this.formattedTime = $.datepicker.formatTime(this._defaults.timeFormat, this, this._defaults);
			if (this.$timeObj) {
				this.$timeObj.text(this.formattedTime + o.timeSuffix);
			}
			this.timeDefined = true;
			if (hasChanged) {
				this._updateDateTime();
			}
		},

		//########################################################################
		// call custom onSelect.
		// bind to sliders slidestop, and grid click.
		//########################################################################
		_onSelectHandler: function _onSelectHandler() {
			var onSelect = this._defaults.onSelect;
			var inputEl = this.$input ? this.$input[0] : null;
			if (onSelect && inputEl) {
				onSelect.apply(inputEl, [this.formattedDateTime, this]);
			}
		},

		//########################################################################
		// left for any backwards compatibility
		//########################################################################
		_formatTime: function _formatTime(time, format) {
			time = time || { hour: this.hour, minute: this.minute, second: this.second, millisec: this.millisec, ampm: this.ampm, timezone: this.timezone };
			var tmptime = (format || this._defaults.timeFormat).toString();

			tmptime = $.datepicker.formatTime(tmptime, time, this._defaults);

			if (arguments.length) {
				return tmptime;
			} else {
				this.formattedTime = tmptime;
			}
		},

		//########################################################################
		// update our input with the new date time..
		//########################################################################
		_updateDateTime: function _updateDateTime(dp_inst) {
			dp_inst = this.inst || dp_inst;
			var dt = $.datepicker._daylightSavingAdjust(new Date(dp_inst.selectedYear, dp_inst.selectedMonth, dp_inst.selectedDay)),
			    dateFmt = $.datepicker._get(dp_inst, 'dateFormat'),
			    formatCfg = $.datepicker._getFormatConfig(dp_inst),
			    timeAvailable = dt !== null && this.timeDefined;
			this.formattedDate = $.datepicker.formatDate(dateFmt, dt === null ? new Date() : dt, formatCfg);
			var formattedDateTime = this.formattedDate;
			// remove following lines to force every changes in date picker to change the input value
			// Bug descriptions: when an input field has a default value, and click on the field to pop up the date picker. 
			// If the user manually empty the value in the input field, the date picker will never change selected value.
			//if (dp_inst.lastVal !== undefined && (dp_inst.lastVal.length > 0 && this.$input.val().length === 0)) {
			//	return;
			//}

			if (this._defaults.timeOnly === true) {
				formattedDateTime = this.formattedTime;
			} else if (this._defaults.timeOnly !== true && (this._defaults.alwaysSetTime || timeAvailable)) {
				formattedDateTime += this._defaults.separator + this.formattedTime + this._defaults.timeSuffix;
			}

			this.formattedDateTime = formattedDateTime;

			if (!this._defaults.showTimepicker) {
				this.$input.val(this.formattedDate);
			} else if (this.$altInput && this._defaults.altFieldTimeOnly === true) {
				this.$altInput.val(this.formattedTime);
				this.$input.val(this.formattedDate);
			} else if (this.$altInput) {
				this.$altInput.val(formattedDateTime);
				this.$input.val(formattedDateTime);
			} else {
				this.$input.val(formattedDateTime);
			}

			this.$input.trigger("change");
		}

	});

	$.fn.extend({
		//########################################################################
		// shorthand just to use timepicker..
		//########################################################################
		timepicker: function timepicker(o) {
			o = o || {};
			var tmp_args = arguments;

			if ((typeof o === 'undefined' ? 'undefined' : _typeof(o)) == 'object') {
				tmp_args[0] = $.extend(o, { timeOnly: true });
			}

			return $(this).each(function () {
				$.fn.datetimepicker.apply($(this), tmp_args);
			});
		},

		//########################################################################
		// extend timepicker to datepicker
		//########################################################################
		datetimepicker: function datetimepicker(o) {
			o = o || {};
			var tmp_args = arguments;

			if (typeof o == 'string') {
				if (o == 'getDate') {
					return $.fn.datepicker.apply($(this[0]), tmp_args);
				} else {
					return this.each(function () {
						var $t = $(this);
						$t.datepicker.apply($t, tmp_args);
					});
				}
			} else {
				return this.each(function () {
					var $t = $(this);
					$t.datepicker($.timepicker._newInst($t, o)._defaults);
				});
			}
		}
	});

	$.datepicker.parseDateTime = function (dateFormat, timeFormat, dateTimeString, dateSettings, timeSettings) {
		var parseRes = parseDateTimeInternal(dateFormat, timeFormat, dateTimeString, dateSettings, timeSettings);
		if (parseRes.timeObj) {
			var t = parseRes.timeObj;
			parseRes.date.setHours(t.hour, t.minute, t.second, t.millisec);
		}

		return parseRes.date;
	};

	$.datepicker.parseTime = function (timeFormat, timeString, options) {

		//########################################################################
		// pattern for standard and localized AM/PM markers
		//########################################################################
		var getPatternAmpm = function getPatternAmpm(amNames, pmNames) {
			var markers = [];
			if (amNames) {
				$.merge(markers, amNames);
			}
			if (pmNames) {
				$.merge(markers, pmNames);
			}
			markers = $.map(markers, function (val) {
				return val.replace(/[.*+?|()\[\]{}\\]/g, '\\$&');
			});
			return '(' + markers.join('|') + ')?';
		};

		//########################################################################
		// figure out position of time elements.. cause js cant do named captures
		//########################################################################
		var getFormatPositions = function getFormatPositions(timeFormat) {
			var finds = timeFormat.toLowerCase().match(/(h{1,2}|m{1,2}|s{1,2}|l{1}|t{1,2}|z)/g),
			    orders = { h: -1, m: -1, s: -1, l: -1, t: -1, z: -1 };

			if (finds) {
				for (var i = 0; i < finds.length; i++) {
					if (orders[finds[i].toString().charAt(0)] == -1) {
						orders[finds[i].toString().charAt(0)] = i + 1;
					}
				}
			}
			return orders;
		};

		var o = extendRemove(extendRemove({}, $.timepicker._defaults), options || {});

		var regstr = '^' + timeFormat.toString().replace(/h{1,2}/ig, '(\\d?\\d)').replace(/m{1,2}/ig, '(\\d?\\d)').replace(/s{1,2}/ig, '(\\d?\\d)').replace(/l{1}/ig, '(\\d?\\d?\\d)').replace(/t{1,2}/ig, getPatternAmpm(o.amNames, o.pmNames)).replace(/z{1}/ig, '(z|[-+]\\d\\d:?\\d\\d)?').replace(/\s/g, '\\s?') + o.timeSuffix + '$',
		    order = getFormatPositions(timeFormat),
		    ampm = '',
		    treg;

		treg = timeString.match(new RegExp(regstr, 'i'));

		var resTime = { hour: 0, minute: 0, second: 0, millisec: 0 };

		if (treg) {
			if (order.t !== -1) {
				if (treg[order.t] === undefined || treg[order.t].length === 0) {
					ampm = '';
					resTime.ampm = '';
				} else {
					ampm = $.inArray(treg[order.t], o.amNames) !== -1 ? 'AM' : 'PM';
					resTime.ampm = o[ampm == 'AM' ? 'amNames' : 'pmNames'][0];
				}
			}

			if (order.h !== -1) {
				if (ampm == 'AM' && treg[order.h] == '12') {
					resTime.hour = 0; // 12am = 0 hour
				} else {
					if (ampm == 'PM' && treg[order.h] != '12') {
						resTime.hour = parseInt(treg[order.h], 10) + 12; // 12pm = 12 hour, any other pm = hour + 12
					} else {
						resTime.hour = Number(treg[order.h]);
					}
				}
			}

			if (order.m !== -1) {
				resTime.minute = Number(treg[order.m]);
			}
			if (order.s !== -1) {
				resTime.second = Number(treg[order.s]);
			}
			if (order.l !== -1) {
				resTime.millisec = Number(treg[order.l]);
			}
			if (order.z !== -1 && treg[order.z] !== undefined) {
				var tz = treg[order.z].toUpperCase();
				switch (tz.length) {
					case 1:
						// Z
						tz = o.timezoneIso8601 ? 'Z' : '+0000';
						break;
					case 5:
						// +hhmm
						if (o.timezoneIso8601) {
							tz = tz.substring(1) == '0000' ? 'Z' : tz.substring(0, 3) + ':' + tz.substring(3);
						}
						break;
					case 6:
						// +hh:mm
						if (!o.timezoneIso8601) {
							tz = tz == 'Z' || tz.substring(1) == '00:00' ? '+0000' : tz.replace(/:/, '');
						} else {
							if (tz.substring(1) == '00:00') {
								tz = 'Z';
							}
						}
						break;
				}
				resTime.timezone = tz;
			}

			return resTime;
		}

		return false;
	};

	//########################################################################
	// format the time all pretty...
	// format = string format of the time
	// time = a {}, not a Date() for timezones
	// options = essentially the regional[].. amNames, pmNames, ampm
	//########################################################################
	$.datepicker.formatTime = function (format, time, options) {
		options = options || {};
		options = $.extend($.timepicker._defaults, options);
		time = $.extend({ hour: 0, minute: 0, second: 0, millisec: 0, timezone: '+0000' }, time);

		var tmptime = format;
		var ampmName = options.amNames[0];

		var hour = parseInt(time.hour, 10);
		if (options.ampm) {
			if (hour > 11) {
				ampmName = options.pmNames[0];
				if (hour > 12) {
					hour = hour % 12;
				}
			}
			if (hour === 0) {
				hour = 12;
			}
		}
		tmptime = tmptime.replace(/(?:hh?|mm?|ss?|[tT]{1,2}|[lz])/g, function (match) {
			switch (match.toLowerCase()) {
				case 'hh':
					return ('0' + hour).slice(-2);
				case 'h':
					return hour;
				case 'mm':
					return ('0' + time.minute).slice(-2);
				case 'm':
					return time.minute;
				case 'ss':
					return ('0' + time.second).slice(-2);
				case 's':
					return time.second;
				case 'l':
					return ('00' + time.millisec).slice(-3);
				case 'z':
					return time.timezone;
				case 't':case 'tt':
					if (options.ampm) {
						if (match.length == 1) {
							ampmName = ampmName.charAt(0);
						}
						return match.charAt(0) == 'T' ? ampmName.toUpperCase() : ampmName.toLowerCase();
					}
					return '';
			}
		});

		tmptime = $.trim(tmptime);
		return tmptime;
	};

	//########################################################################
	// the bad hack :/ override datepicker so it doesnt close on select
	// inspired: http://stackoverflow.com/questions/1252512/jquery-datepicker-prevent-closing-picker-when-clicking-a-date/1762378#1762378
	//########################################################################
	$.datepicker._base_selectDate = $.datepicker._selectDate;
	$.datepicker._selectDate = function (id, dateStr) {
		var inst = this._getInst($(id)[0]),
		    tp_inst = this._get(inst, 'timepicker');

		if (tp_inst) {
			tp_inst._limitMinMaxDateTime(inst, true);
			inst.inline = inst.stay_open = true;
			//This way the onSelect handler called from calendarpicker get the full dateTime
			this._base_selectDate(id, dateStr);
			inst.inline = inst.stay_open = false;
			this._notifyChange(inst);
			this._updateDatepicker(inst);
		} else {
			this._base_selectDate(id, dateStr);
		}
	};

	//#############################################################################################
	// second bad hack :/ override datepicker so it triggers an event when changing the input field
	// and does not redraw the datepicker on every selectDate event
	//#############################################################################################
	$.datepicker._base_updateDatepicker = $.datepicker._updateDatepicker;
	$.datepicker._updateDatepicker = function (inst) {

		// don't popup the datepicker if there is another instance already opened
		var input = inst.input[0];
		if ($.datepicker._curInst && $.datepicker._curInst != inst && $.datepicker._datepickerShowing && $.datepicker._lastInput != input) {
			return;
		}

		if (typeof inst.stay_open !== 'boolean' || inst.stay_open === false) {

			this._base_updateDatepicker(inst);

			// Reload the time control when changing something in the input text field.
			var tp_inst = this._get(inst, 'timepicker');
			if (tp_inst) {
				tp_inst._addTimePicker(inst);

				if (tp_inst._defaults.useLocalTimezone) {
					//checks daylight saving with the new date.
					var date = new Date(inst.selectedYear, inst.selectedMonth, inst.selectedDay, 12);
					selectLocalTimeZone(tp_inst, date);
					tp_inst._onTimeChange();
				}
			}
		}
	};

	//#######################################################################################
	// third bad hack :/ override datepicker so it allows spaces and colon in the input field
	//#######################################################################################
	$.datepicker._base_doKeyPress = $.datepicker._doKeyPress;
	$.datepicker._doKeyPress = function (event) {
		var inst = $.datepicker._getInst(event.target),
		    tp_inst = $.datepicker._get(inst, 'timepicker');

		if (tp_inst) {
			if ($.datepicker._get(inst, 'constrainInput')) {
				var ampm = tp_inst._defaults.ampm,
				    dateChars = $.datepicker._possibleChars($.datepicker._get(inst, 'dateFormat')),
				    datetimeChars = tp_inst._defaults.timeFormat.toString().replace(/[hms]/g, '').replace(/TT/g, ampm ? 'APM' : '').replace(/Tt/g, ampm ? 'AaPpMm' : '').replace(/tT/g, ampm ? 'AaPpMm' : '').replace(/T/g, ampm ? 'AP' : '').replace(/tt/g, ampm ? 'apm' : '').replace(/t/g, ampm ? 'ap' : '') + " " + tp_inst._defaults.separator + tp_inst._defaults.timeSuffix + (tp_inst._defaults.showTimezone ? tp_inst._defaults.timezoneList.join('') : '') + tp_inst._defaults.amNames.join('') + tp_inst._defaults.pmNames.join('') + dateChars,
				    chr = String.fromCharCode(event.charCode === undefined ? event.keyCode : event.charCode);
				return event.ctrlKey || chr < ' ' || !dateChars || datetimeChars.indexOf(chr) > -1;
			}
		}

		return $.datepicker._base_doKeyPress(event);
	};

	//#######################################################################################
	// Override key up event to sync manual input changes.
	//#######################################################################################
	$.datepicker._base_doKeyUp = $.datepicker._doKeyUp;
	$.datepicker._doKeyUp = function (event) {
		var inst = $.datepicker._getInst(event.target),
		    tp_inst = $.datepicker._get(inst, 'timepicker');

		if (tp_inst) {
			if (tp_inst._defaults.timeOnly && inst.input.val() != inst.lastVal) {
				try {
					$.datepicker._updateDatepicker(inst);
				} catch (err) {
					$.datepicker.log(err);
				}
			}
		}

		return $.datepicker._base_doKeyUp(event);
	};

	//#######################################################################################
	// override "Today" button to also grab the time.
	//#######################################################################################
	$.datepicker._base_gotoToday = $.datepicker._gotoToday;
	$.datepicker._gotoToday = function (id) {
		var inst = this._getInst($(id)[0]),
		    $dp = inst.dpDiv;
		this._base_gotoToday(id);
		var tp_inst = this._get(inst, 'timepicker');
		selectLocalTimeZone(tp_inst);
		var now = new Date();
		this._setTime(inst, now);
		$('.ui-datepicker-today', $dp).click();
	};

	//#######################################################################################
	// Disable & enable the Time in the datetimepicker
	//#######################################################################################
	$.datepicker._disableTimepickerDatepicker = function (target) {
		var inst = this._getInst(target);
		if (!inst) {
			return;
		}

		var tp_inst = this._get(inst, 'timepicker');
		$(target).datepicker('getDate'); // Init selected[Year|Month|Day]
		if (tp_inst) {
			tp_inst._defaults.showTimepicker = false;
			tp_inst._updateDateTime(inst);
		}
	};

	$.datepicker._enableTimepickerDatepicker = function (target) {
		var inst = this._getInst(target);
		if (!inst) {
			return;
		}

		var tp_inst = this._get(inst, 'timepicker');
		$(target).datepicker('getDate'); // Init selected[Year|Month|Day]
		if (tp_inst) {
			tp_inst._defaults.showTimepicker = true;
			tp_inst._addTimePicker(inst); // Could be disabled on page load
			tp_inst._updateDateTime(inst);
		}
	};

	//#######################################################################################
	// Create our own set time function
	//#######################################################################################
	$.datepicker._setTime = function (inst, date) {
		var tp_inst = this._get(inst, 'timepicker');
		if (tp_inst) {
			var defaults = tp_inst._defaults,

			// calling _setTime with no date sets time to defaults
			hour = date ? date.getHours() : defaults.hour,
			    minute = date ? date.getMinutes() : defaults.minute,
			    second = date ? date.getSeconds() : defaults.second,
			    millisec = date ? date.getMilliseconds() : defaults.millisec;
			//check if within min/max times..
			// correct check if within min/max times. 	
			// Rewritten by Scott A. Woodward
			var hourEq = hour === defaults.hourMin,
			    minuteEq = minute === defaults.minuteMin,
			    secondEq = second === defaults.secondMin;
			var reset = false;
			if (hour < defaults.hourMin || hour > defaults.hourMax) reset = true;else if ((minute < defaults.minuteMin || minute > defaults.minuteMax) && hourEq) reset = true;else if ((second < defaults.secondMin || second > defaults.secondMax) && hourEq && minuteEq) reset = true;else if ((millisec < defaults.millisecMin || millisec > defaults.millisecMax) && hourEq && minuteEq && secondEq) reset = true;
			if (reset) {
				hour = defaults.hourMin;
				minute = defaults.minuteMin;
				second = defaults.secondMin;
				millisec = defaults.millisecMin;
			}
			tp_inst.hour = hour;
			tp_inst.minute = minute;
			tp_inst.second = second;
			tp_inst.millisec = millisec;
			if (tp_inst.hour_slider) tp_inst.hour_slider.slider('value', hour);
			if (tp_inst.minute_slider) tp_inst.minute_slider.slider('value', minute);
			if (tp_inst.second_slider) tp_inst.second_slider.slider('value', second);
			if (tp_inst.millisec_slider) tp_inst.millisec_slider.slider('value', millisec);

			tp_inst._onTimeChange();
			tp_inst._updateDateTime(inst);
		}
	};

	//#######################################################################################
	// Create new public method to set only time, callable as $().datepicker('setTime', date)
	//#######################################################################################
	$.datepicker._setTimeDatepicker = function (target, date, withDate) {
		var inst = this._getInst(target);
		if (!inst) {
			return;
		}

		var tp_inst = this._get(inst, 'timepicker');

		if (tp_inst) {
			this._setDateFromField(inst);
			var tp_date;
			if (date) {
				if (typeof date == "string") {
					tp_inst._parseTime(date, withDate);
					tp_date = new Date();
					tp_date.setHours(tp_inst.hour, tp_inst.minute, tp_inst.second, tp_inst.millisec);
				} else {
					tp_date = new Date(date.getTime());
				}
				if (tp_date.toString() == 'Invalid Date') {
					tp_date = undefined;
				}
				this._setTime(inst, tp_date);
			}
		}
	};

	//#######################################################################################
	// override setDate() to allow setting time too within Date object
	//#######################################################################################
	$.datepicker._base_setDateDatepicker = $.datepicker._setDateDatepicker;
	$.datepicker._setDateDatepicker = function (target, date) {
		var inst = this._getInst(target);
		if (!inst) {
			return;
		}

		var tp_date = date instanceof Date ? new Date(date.getTime()) : date;

		this._updateDatepicker(inst);
		this._base_setDateDatepicker.apply(this, arguments);
		this._setTimeDatepicker(target, tp_date, true);
	};

	//#######################################################################################
	// override getDate() to allow getting time too within Date object
	//#######################################################################################
	$.datepicker._base_getDateDatepicker = $.datepicker._getDateDatepicker;
	$.datepicker._getDateDatepicker = function (target, noDefault) {
		var inst = this._getInst(target);
		if (!inst) {
			return;
		}

		var tp_inst = this._get(inst, 'timepicker');

		if (tp_inst) {
			this._setDateFromField(inst, noDefault);
			var date = this._getDate(inst);
			if (date && tp_inst._parseTime($(target).val(), tp_inst.timeOnly)) {
				date.setHours(tp_inst.hour, tp_inst.minute, tp_inst.second, tp_inst.millisec);
			}
			return date;
		}
		return this._base_getDateDatepicker(target, noDefault);
	};

	//#######################################################################################
	// override parseDate() because UI 1.8.14 throws an error about "Extra characters"
	// An option in datapicker to ignore extra format characters would be nicer.
	//#######################################################################################
	$.datepicker._base_parseDate = $.datepicker.parseDate;
	$.datepicker.parseDate = function (format, value, settings) {
		var splitRes = splitDateTime(format, value, settings);
		return $.datepicker._base_parseDate(format, splitRes[0], settings);
	};

	//#######################################################################################
	// override formatDate to set date with time to the input
	//#######################################################################################
	$.datepicker._base_formatDate = $.datepicker._formatDate;
	$.datepicker._formatDate = function (inst, day, month, year) {
		var tp_inst = this._get(inst, 'timepicker');
		if (tp_inst) {
			tp_inst._updateDateTime(inst);
			return tp_inst.$input.val();
		}
		return this._base_formatDate(inst);
	};

	//#######################################################################################
	// override options setter to add time to maxDate(Time) and minDate(Time). MaxDate
	//#######################################################################################
	$.datepicker._base_optionDatepicker = $.datepicker._optionDatepicker;
	$.datepicker._optionDatepicker = function (target, name, value) {
		var inst = this._getInst(target);
		if (!inst) {
			return null;
		}

		var tp_inst = this._get(inst, 'timepicker');
		if (tp_inst) {
			var min = null,
			    max = null,
			    onselect = null;
			if (typeof name == 'string') {
				// if min/max was set with the string
				if (name === 'minDate' || name === 'minDateTime') {
					min = value;
				} else {
					if (name === 'maxDate' || name === 'maxDateTime') {
						max = value;
					} else {
						if (name === 'onSelect') {
							onselect = value;
						}
					}
				}
			} else {
				if ((typeof name === 'undefined' ? 'undefined' : _typeof(name)) == 'object') {
					//if min/max was set with the JSON
					if (name.minDate) {
						min = name.minDate;
					} else {
						if (name.minDateTime) {
							min = name.minDateTime;
						} else {
							if (name.maxDate) {
								max = name.maxDate;
							} else {
								if (name.maxDateTime) {
									max = name.maxDateTime;
								}
							}
						}
					}
				}
			}
			if (min) {
				//if min was set
				if (min === 0) {
					min = new Date();
				} else {
					min = new Date(min);
				}

				tp_inst._defaults.minDate = min;
				tp_inst._defaults.minDateTime = min;
			} else if (max) {
				//if max was set
				if (max === 0) {
					max = new Date();
				} else {
					max = new Date(max);
				}
				tp_inst._defaults.maxDate = max;
				tp_inst._defaults.maxDateTime = max;
			} else if (onselect) {
				tp_inst._defaults.onSelect = onselect;
			}
		}
		if (value === undefined) {
			return this._base_optionDatepicker(target, name);
		}
		return this._base_optionDatepicker(target, name, value);
	};

	//#######################################################################################
	// jQuery extend now ignores nulls!
	//#######################################################################################
	function extendRemove(target, props) {
		$.extend(target, props);
		for (var name in props) {
			if (props[name] === null || props[name] === undefined) {
				target[name] = props[name];
			}
		}
		return target;
	}

	//#######################################################################################
	// Splits datetime string into date ans time substrings.
	// Throws exception when date can't be parsed
	// If only date is present, time substring eill be '' 
	//#######################################################################################
	var splitDateTime = function splitDateTime(dateFormat, dateTimeString, dateSettings) {
		try {
			var date = $.datepicker._base_parseDate(dateFormat, dateTimeString, dateSettings);
		} catch (err) {
			if (err.indexOf(":") >= 0) {
				// Hack!  The error message ends with a colon, a space, and
				// the "extra" characters.  We rely on that instead of
				// attempting to perfectly reproduce the parsing algorithm.
				var dateStringLength = dateTimeString.length - (err.length - err.indexOf(':') - 2);
				var timeString = dateTimeString.substring(dateStringLength);

				return [dateTimeString.substring(0, dateStringLength), dateTimeString.substring(dateStringLength)];
			} else {
				throw err;
			}
		}
		return [dateTimeString, ''];
	};

	//#######################################################################################
	// Internal function to parse datetime interval
	// Returns: {date: Date, timeObj: Object}, where
	//   date - parsed date without time (type Date)
	//   timeObj = {hour: , minute: , second: , millisec: } - parsed time. Optional
	//#######################################################################################
	var parseDateTimeInternal = function parseDateTimeInternal(dateFormat, timeFormat, dateTimeString, dateSettings, timeSettings) {
		var date;
		var splitRes = splitDateTime(dateFormat, dateTimeString, dateSettings);
		date = $.datepicker._base_parseDate(dateFormat, splitRes[0], dateSettings);
		if (splitRes[1] !== '') {
			var timeString = splitRes[1];
			var separator = timeSettings && timeSettings.separator ? timeSettings.separator : $.timepicker._defaults.separator;
			if (timeString.indexOf(separator) !== 0) {
				throw 'Missing time separator';
			}
			timeString = timeString.substring(separator.length);
			var parsedTime = $.datepicker.parseTime(timeFormat, timeString, timeSettings);
			if (parsedTime === null) {
				throw 'Wrong time format';
			}
			return { date: date, timeObj: parsedTime };
		} else {
			return { date: date };
		}
	};

	//#######################################################################################
	// Internal function to set timezone_select to the local timezone
	//#######################################################################################
	var selectLocalTimeZone = function selectLocalTimeZone(tp_inst, date) {
		if (tp_inst && tp_inst.timezone_select) {
			tp_inst._defaults.useLocalTimezone = true;
			var now = typeof date !== 'undefined' ? date : new Date();
			var tzoffset = timeZoneString(now);
			if (tp_inst._defaults.timezoneIso8601) {
				tzoffset = tzoffset.substring(0, 3) + ':' + tzoffset.substring(3);
			}
			tp_inst.timezone_select.val(tzoffset);
		}
	};

	// Input: Date Object
	// Output: String with timezone offset, e.g. '+0100'
	var timeZoneString = function timeZoneString(date) {
		var off = date.getTimezoneOffset() * -10100 / 60;
		var timezone = (off >= 0 ? '+' : '-') + Math.abs(off).toString().substr(1);
		return timezone;
	};

	$.timepicker = new Timepicker(); // singleton instance
	$.timepicker.version = "1.0.1";
})(jQuery);
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))

/***/ }),
/* 20 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*
 * jQuery UI Selectmenu version 1.5.0pre
 *
 * Copyright (c) 2009-2010 filament group, http://filamentgroup.com
 * Copyright (c) 2010-2014 Felix Nagel, http://www.felixnagel.com
 * Licensed under the MIT (MIT-LICENSE.txt)
 *
 * https://github.com/fnagel/jquery-ui/wiki/Selectmenu
 */

/* global define */
/* global jQuery */

(function (factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(11)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		factory(jQuery);
	}
})(function ($) {

	$.widget('ui.selectmenu', {
		options: {
			appendTo: 'body',
			typeAhead: 1000,
			style: 'dropdown',
			positionOptions: null,
			width: null,
			menuWidth: null,
			handleWidth: 26,
			maxHeight: null,
			icons: null,
			format: null,
			escapeHtml: false,
			bgImage: function bgImage() {}
		},

		_create: function _create() {
			var self = this,
			    o = this.options;

			// make / set unique id
			var selectmenuId = this.element.uniqueId().attr('id');

			// quick array of button and menu id's
			this.ids = [selectmenuId, selectmenuId + '-button', selectmenuId + '-menu'];

			// define safe mouseup for future toggling
			this._safemouseup = true;
			this.isOpen = false;

			// create menu button wrapper
			this.newelement = $('<a />', {
				'class': 'ui-selectmenu ui-widget ui-state-default ui-corner-all',
				'id': this.ids[1],
				'role': 'button',
				'href': '#nogo',
				'tabindex': this.element.attr('disabled') ? 1 : 0,
				'aria-haspopup': true,
				'aria-owns': this.ids[2]
			});
			this.newelementWrap = $('<span />').append(this.newelement).insertAfter(this.element);

			// transfer tabindex
			var tabindex = this.element.attr('tabindex');
			if (tabindex) {
				this.newelement.attr('tabindex', tabindex);
			}

			// save reference to select in data for ease in calling methods
			this.newelement.data('selectelement', this.element);

			// menu icon
			this.selectmenuIcon = $('<span class="ui-selectmenu-icon ui-icon"></span>').prependTo(this.newelement);

			// append status span to button
			this.newelement.prepend('<span class="ui-selectmenu-status" />');

			// make associated form label trigger focus
			this.element.bind({
				'click.selectmenu': function clickSelectmenu(event) {
					self.newelement.focus();
					event.preventDefault();
				}
			});

			// click toggle for menu visibility
			this.newelement.bind('mousedown.selectmenu', function (event) {
				self._toggle(event, true);
				// make sure a click won't open/close instantly
				if (o.style == 'popup') {
					self._safemouseup = false;
					setTimeout(function () {
						self._safemouseup = true;
					}, 300);
				}

				event.preventDefault();
			}).bind('click.selectmenu', function (event) {
				event.preventDefault();
			}).bind('keydown.selectmenu', function (event) {
				var ret = false;
				switch (event.keyCode) {
					case $.ui.keyCode.ENTER:
						ret = true;
						break;
					case $.ui.keyCode.SPACE:
						self._toggle(event);
						break;
					case $.ui.keyCode.UP:
						if (event.altKey) {
							self.open(event);
						} else {
							self._moveSelection(-1);
						}
						break;
					case $.ui.keyCode.DOWN:
						if (event.altKey) {
							self.open(event);
						} else {
							self._moveSelection(1);
						}
						break;
					case $.ui.keyCode.LEFT:
						self._moveSelection(-1);
						break;
					case $.ui.keyCode.RIGHT:
						self._moveSelection(1);
						break;
					case $.ui.keyCode.TAB:
						ret = true;
						break;
					case $.ui.keyCode.PAGE_UP:
					case $.ui.keyCode.HOME:
						self.index(0);
						break;
					case $.ui.keyCode.PAGE_DOWN:
					case $.ui.keyCode.END:
						self.index(self._optionLis.length);
						break;
					default:
						ret = true;
				}
				return ret;
			}).bind('keypress.selectmenu', function (event) {
				if (event.which > 0) {
					self._typeAhead(event.which, 'mouseup');
				}
				return true;
			}).bind('mouseover.selectmenu', function () {
				if (!o.disabled) $(this).addClass('ui-state-hover');
			}).bind('mouseout.selectmenu', function () {
				if (!o.disabled) $(this).removeClass('ui-state-hover');
			}).bind('focus.selectmenu', function () {
				if (!o.disabled) $(this).addClass('ui-state-focus');
			}).bind('blur.selectmenu', function () {
				if (!o.disabled) $(this).removeClass('ui-state-focus');
			});

			// document click closes menu
			$(document).bind('mousedown.selectmenu-' + this.ids[0], function (event) {
				//check if open and if the clicket targes parent is the same
				if (self.isOpen && !$(event.target).closest('#' + self.ids[1]).length) {
					self.close(event);
				}
			});

			// change event on original selectmenu
			this.element.bind('click.selectmenu', function () {
				self._refreshValue();
			})
			// FIXME: newelement can be null under unclear circumstances in IE8
			// TODO not sure if this is still a problem (fnagel 20.03.11)
			.bind('focus.selectmenu', function () {
				if (self.newelement) {
					self.newelement[0].focus();
				}
			});

			// set width when not set via options
			if (!o.width) {
				o.width = this.element.outerWidth();
			}
			// set menu button width
			this.newelement.width(o.width);

			// hide original selectmenu element
			this.element.hide();

			// create menu portion, append to body
			this.list = $('<ul />', {
				'class': 'ui-widget ui-widget-content',
				'aria-hidden': true,
				'role': 'listbox',
				'aria-labelledby': this.ids[1],
				'id': this.ids[2]
			});
			this.listWrap = $('<div />', {
				'class': 'ui-selectmenu-menu'
			}).append(this.list).appendTo(o.appendTo);

			// transfer menu click to menu button
			this.list.bind('keydown.selectmenu', function (event) {
				var ret = false;
				switch (event.keyCode) {
					case $.ui.keyCode.UP:
						if (event.altKey) {
							self.close(event, true);
						} else {
							self._moveFocus(-1);
						}
						break;
					case $.ui.keyCode.DOWN:
						if (event.altKey) {
							self.close(event, true);
						} else {
							self._moveFocus(1);
						}
						break;
					case $.ui.keyCode.LEFT:
						self._moveFocus(-1);
						break;
					case $.ui.keyCode.RIGHT:
						self._moveFocus(1);
						break;
					case $.ui.keyCode.HOME:
						self._moveFocus(':first');
						break;
					case $.ui.keyCode.PAGE_UP:
						self._scrollPage('up');
						break;
					case $.ui.keyCode.PAGE_DOWN:
						self._scrollPage('down');
						break;
					case $.ui.keyCode.END:
						self._moveFocus(':last');
						break;
					case $.ui.keyCode.ENTER:
					case $.ui.keyCode.SPACE:
						self.close(event, true);
						$(event.target).parents('li:eq(0)').trigger('mouseup');
						break;
					case $.ui.keyCode.TAB:
						ret = true;
						self.close(event, true);
						$(event.target).parents('li:eq(0)').trigger('mouseup');
						break;
					case $.ui.keyCode.ESCAPE:
						self.close(event, true);
						break;
					default:
						ret = true;
				}
				return ret;
			}).bind('keypress.selectmenu', function (event) {
				if (event.which > 0) {
					self._typeAhead(event.which, 'focus');
				}
				return true;
			})
			// this allows for using the scrollbar in an overflowed list
			.bind('mousedown.selectmenu mouseup.selectmenu', function () {
				return false;
			});

			// needed when window is resized
			$(window).bind('resize.selectmenu-' + this.ids[0], $.proxy(self.close, this));
		},

		_init: function _init() {
			var self = this,
			    o = this.options;

			// serialize selectmenu element options
			var selectOptionData = [];
			this.element.find('option').each(function () {
				var opt = $(this);
				selectOptionData.push({
					value: opt.attr('value'),
					text: self._formatText(opt.text(), opt),
					selected: opt.attr('selected'),
					disabled: opt.attr('disabled'),
					classes: opt.attr('class'),
					typeahead: opt.attr('typeahead'),
					parentOptGroup: opt.parent('optgroup'),
					bgImage: o.bgImage.call(opt)
				});
			});

			// active state class is only used in popup style
			var activeClass = self.options.style == 'popup' ? ' ui-state-active' : '';

			// empty list so we can refresh the selectmenu via selectmenu()
			this.list.html('');

			// write li's
			if (selectOptionData.length) {
				for (var i = 0; i < selectOptionData.length; i++) {
					var thisLiAttr = { role: 'presentation' };
					if (selectOptionData[i].disabled) {
						thisLiAttr['class'] = 'ui-state-disabled';
					}
					var thisAAttr = {
						html: selectOptionData[i].text || '&nbsp;',
						href: '#nogo',
						tabindex: -1,
						role: 'option',
						'aria-selected': false
					};
					if (selectOptionData[i].disabled) {
						thisAAttr['aria-disabled'] = true;
					}
					if (selectOptionData[i].typeahead) {
						thisAAttr['typeahead'] = selectOptionData[i].typeahead;
					}
					var thisA = $('<a/>', thisAAttr).bind('focus.selectmenu', function () {
						$(this).parent().mouseover();
					}).bind('blur.selectmenu', function () {
						$(this).parent().mouseout();
					});
					var thisLi = $('<li/>', thisLiAttr).append(thisA).data('index', i).addClass(selectOptionData[i].classes).data('optionClasses', selectOptionData[i].classes || '').bind('mouseup.selectmenu', function (event) {
						if (self._safemouseup && !self._disabled(event.currentTarget) && !self._disabled($(event.currentTarget).parents('ul > li.ui-selectmenu-group '))) {
							self.index($(this).data('index'));
							self.select(event);
							self.close(event, true);
						}
						return false;
					}).bind('click.selectmenu', function () {
						return false;
					}).bind('mouseover.selectmenu', function (e) {
						// no hover if disabled
						if (!$(this).hasClass('ui-state-disabled') && !$(this).parent('ul').parent('li').hasClass('ui-state-disabled')) {
							if (self._typeAhead_timer === undefined) {
								e.optionValue = self.element[0].options[$(this).data('index')].value;
								self._trigger('hover', e, self._uiHash());
								self._selectedOptionLi().addClass(activeClass);
								self._focusedOptionLi().removeClass('ui-selectmenu-item-focus ui-state-hover');
								$(this).removeClass('ui-state-active').addClass('ui-selectmenu-item-focus ui-state-hover');
							}
						}
					}).bind('mouseout.selectmenu', function (e) {
						if ($(this).is(self._selectedOptionLi())) {
							$(this).addClass(activeClass);
						}
						e.optionValue = self.element[0].options[$(this).data('index')].value;
						self._trigger('blur', e, self._uiHash());
						$(this).removeClass('ui-selectmenu-item-focus ui-state-hover');
					});

					// optgroup or not...
					if (selectOptionData[i].parentOptGroup.length) {
						var optGroupName = 'ui-selectmenu-group-' + this.element.find('optgroup').index(selectOptionData[i].parentOptGroup);
						if (this.list.find('li.' + optGroupName).length) {
							this.list.find('li.' + optGroupName + ':last ul').append(thisLi);
						} else {
							$('<li role="presentation" class="ui-selectmenu-group ' + optGroupName + (selectOptionData[i].parentOptGroup.attr('disabled') ? ' ' + 'ui-state-disabled" aria-disabled="true"' : '"') + '><span class="ui-selectmenu-group-label">' + selectOptionData[i].parentOptGroup.attr('label') + '</span><ul></ul></li>').appendTo(this.list).find('ul').append(thisLi);
						}
					} else {
						thisLi.appendTo(this.list);
					}

					// append icon if option is specified
					if (o.icons) {
						for (var j in o.icons) {
							if (thisLi.is(o.icons[j].find)) {
								thisLi.data('optionClasses', selectOptionData[i].classes + ' ui-selectmenu-hasIcon').addClass('ui-selectmenu-hasIcon');
								var iconClass = o.icons[j].icon || '';
								thisLi.find('a:eq(0)').prepend('<span class="ui-selectmenu-item-icon ui-icon ' + iconClass + '"></span>');
								if (selectOptionData[i].bgImage) {
									thisLi.find('span').css('background-image', selectOptionData[i].bgImage);
								}
							}
						}
					}
				}
			} else {
				$('<li role="presentation"><a href="#nogo" tabindex="-1" role="option"></a></li>').appendTo(this.list);
			}
			// we need to set and unset the CSS classes for dropdown and popup style
			var isDropDown = o.style == 'dropdown';
			this.newelement.toggleClass('ui-selectmenu-dropdown', isDropDown).toggleClass('ui-selectmenu-popup', !isDropDown);
			this.list.toggleClass('ui-selectmenu-menu-dropdown ui-corner-bottom', isDropDown).toggleClass('ui-selectmenu-menu-popup ui-corner-all', !isDropDown)
			// add corners to top and bottom menu items
			.find('li:first').toggleClass('ui-corner-top', !isDropDown).end().find('li:last').addClass('ui-corner-bottom');
			this.selectmenuIcon.toggleClass('ui-icon-triangle-1-s', isDropDown).toggleClass('ui-icon-triangle-2-n-s', !isDropDown);

			// set menu width to either menuWidth option value, width option value, or select width
			if (o.style == 'dropdown') {
				this.list.width(o.menuWidth ? o.menuWidth : o.width);
			} else {
				this.list.width(o.menuWidth ? o.menuWidth : o.width - o.handleWidth);
			}

			// Android 2 (Gingerbread) doesn't support internal scrollable divs.
			// Don't limit the menu height for that browser.
			if (!navigator.userAgent.match(/Android 2/)) {
				var listH = this.listWrap.height();
				var winH = $(window).height();
				// calculate default max height
				var maxH = o.maxHeight ? Math.min(o.maxHeight, winH) : winH / 3;
				if (listH > maxH) this.list.height(maxH);
			}

			// save reference to actionable li's (not group label li's)
			this._optionLis = this.list.find('li:not(.ui-selectmenu-group)');

			// transfer disabled state
			if (this.element.attr('disabled')) {
				this.disable();
			} else {
				this.enable();
			}

			// update value
			this._refreshValue();

			// set selected item so movefocus has intial state
			this._selectedOptionLi().addClass('ui-selectmenu-item-focus');

			// needed when selectmenu is placed at the very bottom / top of the page
			clearTimeout(this.refreshTimeout);
			this.refreshTimeout = window.setTimeout(function () {
				self._refreshPosition();
			}, 200);
		},

		destroy: function destroy() {
			this.element.removeData(this.widgetName).removeClass('ui-selectmenu-disabled' + ' ' + 'ui-state-disabled').removeAttr('aria-disabled').unbind('.selectmenu');

			$(window).unbind('.selectmenu-' + this.ids[0]);
			$(document).unbind('.selectmenu-' + this.ids[0]);

			this.newelementWrap.remove();
			this.listWrap.remove();

			// unbind click event and show original select
			this.element.unbind('.selectmenu').show();

			// call widget destroy function
			$.Widget.prototype.destroy.apply(this, arguments);
		},

		_typeAhead: function _typeAhead(code, eventType) {
			var self = this,
			    c = String.fromCharCode(code).toLowerCase(),
			    matchee = null,
			    nextIndex = null;

			// Clear any previous timer if present
			if (self._typeAhead_timer) {
				window.clearTimeout(self._typeAhead_timer);
				self._typeAhead_timer = undefined;
			}
			// Store the character typed
			self._typeAhead_chars = (self._typeAhead_chars === undefined ? '' : self._typeAhead_chars).concat(c);
			// Detect if we are in cyciling mode or direct selection mode
			if (self._typeAhead_chars.length < 2 || self._typeAhead_chars.substr(-2, 1) === c && self._typeAhead_cycling) {
				self._typeAhead_cycling = true;
				// Match only the first character and loop
				matchee = c;
			} else {
				// We won't be cycling anymore until the timer expires
				self._typeAhead_cycling = false;
				// Match all the characters typed
				matchee = self._typeAhead_chars;
			}

			// We need to determine the currently active index, but it depends on
			// the used context: if it's in the element, we want the actual
			// selected index, if it's in the menu, just the focused one
			var selectedIndex = (eventType !== 'focus' ? this._selectedOptionLi().data('index') : this._focusedOptionLi().data('index')) || 0;
			for (var i = 0; i < this._optionLis.length; i++) {
				var thisText = this._optionLis.eq(i).text().substr(0, matchee.length).toLowerCase();
				if (thisText === matchee) {
					if (self._typeAhead_cycling) {
						if (nextIndex === null) nextIndex = i;
						if (i > selectedIndex) {
							nextIndex = i;
							break;
						}
					} else {
						nextIndex = i;
						break;
					}
				}
			}

			if (nextIndex !== null) {
				// Why using trigger() instead of a direct method to select the index? Because we don't what is the exact action to do,
				// it depends if the user is typing on the element or on the popped up menu
				this._optionLis.eq(nextIndex).find('a').trigger(eventType);
			}

			self._typeAhead_timer = window.setTimeout(function () {
				self._typeAhead_timer = undefined;
				self._typeAhead_chars = undefined;
				self._typeAhead_cycling = undefined;
			}, self.options.typeAhead);
		},

		// returns some usefull information, called by callbacks only
		_uiHash: function _uiHash() {
			var index = this.index();
			return {
				index: index,
				option: $('option', this.element).get(index),
				value: this.element[0].value
			};
		},

		open: function open(event) {
			if (this.newelement.attr('aria-disabled') != 'true') {
				var self = this,
				    o = this.options,
				    selected = this._selectedOptionLi(),
				    link = selected.find('a');

				self._closeOthers(event);
				self.newelement.addClass('ui-state-active');
				self.list.attr('aria-hidden', false);
				self.listWrap.addClass('ui-selectmenu-open');

				if (o.style == 'dropdown') {
					self.newelement.removeClass('ui-corner-all').addClass('ui-corner-top');
				} else {
					// center overflow and avoid flickering
					this.list.css('left', -5000).scrollTop(this.list.scrollTop() + selected.position().top - this.list.outerHeight() / 2 + selected.outerHeight() / 2).css('left', 'auto');
				}

				self._refreshPosition();

				if (link.length) {
					link[0].focus();
				}

				self.isOpen = true;
				self._trigger('open', event, self._uiHash());
			}
		},

		close: function close(event, retainFocus) {
			if (this.newelement.is('.ui-state-active')) {
				this.newelement.removeClass('ui-state-active');
				this.listWrap.removeClass('ui-selectmenu-open');
				this.list.attr('aria-hidden', true);
				if (this.options.style == 'dropdown') {
					this.newelement.removeClass('ui-corner-top').addClass('ui-corner-all');
				}
				if (retainFocus) {
					this.newelement.focus();
				}
				this.isOpen = false;
				this._trigger('close', event, this._uiHash());
			}
		},

		change: function change(event) {
			this.element.trigger('change');
			this._trigger('change', event, this._uiHash());
		},

		select: function select(event) {
			if (this._disabled(event.currentTarget)) {
				return false;
			}
			this._trigger('select', event, this._uiHash());
		},

		widget: function widget() {
			return this.listWrap.add(this.newelementWrap);
		},

		_closeOthers: function _closeOthers(event) {
			$('.ui-selectmenu.ui-state-active').not(this.newelement).each(function () {
				$(this).data('selectelement').selectmenu('close', event);
			});
			$('.ui-selectmenu.ui-state-hover').trigger('mouseout');
		},

		_toggle: function _toggle(event, retainFocus) {
			if (this.isOpen) {
				this.close(event, retainFocus);
			} else {
				this.open(event);
			}
		},

		_formatText: function _formatText(text, opt) {
			if (this.options.format) {
				text = this.options.format(text, opt);
			} else if (this.options.escapeHtml) {
				text = $('<div />').text(text).html();
			}
			return text;
		},

		_selectedIndex: function _selectedIndex() {
			return this.element[0].selectedIndex;
		},

		_selectedOptionLi: function _selectedOptionLi() {
			return this._optionLis.eq(this._selectedIndex());
		},

		_focusedOptionLi: function _focusedOptionLi() {
			return this.list.find('.ui-selectmenu-item-focus');
		},

		_moveSelection: function _moveSelection(amt, recIndex) {
			// do nothing if disabled
			if (!this.options.disabled) {
				var currIndex = parseInt(this._selectedOptionLi().data('index') || 0, 10);
				var newIndex = currIndex + amt;
				// do not loop when using up key
				if (newIndex < 0) {
					newIndex = 0;
				}
				if (newIndex > this._optionLis.size() - 1) {
					newIndex = this._optionLis.size() - 1;
				}
				// Occurs when a full loop has been made
				if (newIndex === recIndex) {
					return false;
				}

				if (this._optionLis.eq(newIndex).hasClass('ui-state-disabled')) {
					// if option at newIndex is disabled, call _moveFocus, incrementing amt by one
					amt > 0 ? ++amt : --amt;
					this._moveSelection(amt, newIndex);
				} else {
					this._optionLis.eq(newIndex).trigger('mouseover').trigger('mouseup');
				}
			}
		},

		_moveFocus: function _moveFocus(amt, recIndex) {
			if (!isNaN(amt)) {
				var currIndex = parseInt(this._focusedOptionLi().data('index') || 0, 10);
				var newIndex = currIndex + amt;
			} else {
				var newIndex = parseInt(this._optionLis.filter(amt).data('index'), 10);
			}

			if (newIndex < 0) {
				newIndex = 0;
			}
			if (newIndex > this._optionLis.size() - 1) {
				newIndex = this._optionLis.size() - 1;
			}

			//Occurs when a full loop has been made
			if (newIndex === recIndex) {
				return false;
			}

			var activeID = 'ui-selectmenu-item-' + Math.round(Math.random() * 1000);

			this._focusedOptionLi().find('a:eq(0)').attr('id', '');

			if (this._optionLis.eq(newIndex).hasClass('ui-state-disabled')) {
				// if option at newIndex is disabled, call _moveFocus, incrementing amt by one
				amt > 0 ? ++amt : --amt;
				this._moveFocus(amt, newIndex);
			} else {
				this._optionLis.eq(newIndex).find('a:eq(0)').attr('id', activeID).focus();
			}

			this.list.attr('aria-activedescendant', activeID);
		},

		_scrollPage: function _scrollPage(direction) {
			var numPerPage = Math.floor(this.list.outerHeight() / this._optionLis.first().outerHeight());
			numPerPage = direction == 'up' ? -numPerPage : numPerPage;
			this._moveFocus(numPerPage);
		},

		_setOption: function _setOption(key, value) {
			this.options[key] = value;
			if (key == 'disabled') {
				if (value) this.close();
				this.element.add(this.newelement).add(this.list)[value ? 'addClass' : 'removeClass']('ui-selectmenu-disabled ' + 'ui-state-disabled').attr('aria-disabled', value).attr('tabindex', value ? 1 : 0);
			}
		},

		disable: function disable(index, type) {
			// if options is not provided, call the parents disable function
			if (typeof index == 'undefined') {
				this._setOption('disabled', true);
			} else {
				this._toggleEnabled(type || 'option', index, false);
			}
		},

		enable: function enable(index, type) {
			// if options is not provided, call the parents enable function
			if (typeof index == 'undefined') {
				this._setOption('disabled', false);
			} else {
				this._toggleEnabled(type || 'option', index, true);
			}
		},

		_disabled: function _disabled(elem) {
			return $(elem).hasClass('ui-state-disabled');
		},

		// true = enabled, false = disabled
		_toggleEnabled: function _toggleEnabled(type, index, flag) {
			var element = this.element.find(type).eq(index),
			    elements = type === 'optgroup' ? this.list.find('li.ui-selectmenu-group-' + index) : this._optionLis.eq(index);

			if (elements) {
				elements.toggleClass('ui-state-disabled', !flag).attr('aria-disabled', !flag);

				if (flag) {
					element.removeAttr('disabled');
				} else {
					element.attr('disabled', 'disabled');
				}
			}
		},

		index: function index(newIndex) {
			if (arguments.length) {
				if (!this._disabled($(this._optionLis[newIndex])) && newIndex != this._selectedIndex()) {
					this.element[0].selectedIndex = newIndex;
					this._refreshValue();
					this.change();
				} else {
					return false;
				}
			} else {
				return this._selectedIndex();
			}
		},

		value: function value(newValue) {
			if (arguments.length && newValue != this.element[0].value) {
				this.element[0].value = newValue;
				this._refreshValue();
				this.change();
			} else {
				return this.element[0].value;
			}
		},

		_refreshValue: function _refreshValue() {
			var activeClass = this.options.style == 'popup' ? ' ui-state-active' : '';
			var activeID = 'ui-selectmenu-item-' + Math.round(Math.random() * 1000);
			// deselect previous
			this.list.find('.ui-selectmenu-item-selected').removeClass('ui-selectmenu-item-selected' + activeClass).find('a').attr('aria-selected', 'false').attr('id', '');
			// select new
			this._selectedOptionLi().addClass('ui-selectmenu-item-selected' + activeClass).find('a').attr('aria-selected', 'true').attr('id', activeID);

			// toggle any class brought in from option
			var currentOptionClasses = this.newelement.data('optionClasses') ? this.newelement.data('optionClasses') : '';
			var newOptionClasses = this._selectedOptionLi().data('optionClasses') ? this._selectedOptionLi().data('optionClasses') : '';
			this.newelement.removeClass(currentOptionClasses).data('optionClasses', newOptionClasses).addClass(newOptionClasses).find('.ui-selectmenu-status').html(this._selectedOptionLi().find('a:eq(0)').html());

			this.list.attr('aria-activedescendant', activeID);
		},

		_refreshPosition: function _refreshPosition() {
			var o = this.options,
			    positionDefault = {
				of: this.newelement,
				my: 'left top',
				at: 'left bottom',
				collision: 'flip'
			};

			// if its a pop-up we need to calculate the position of the selected li
			if (o.style == 'popup') {
				var selected = this._selectedOptionLi();
				positionDefault.my = 'left top' + (this.list.offset().top - selected.offset().top - (this.newelement.outerHeight() + selected.outerHeight()) / 2);
				positionDefault.collision = 'fit';
			}

			this.listWrap.removeAttr('style').css('z-index', this.element.css('z-index') + 2)
			//.zIndex( this.element.zIndex() + 2 )
			.position($.extend(positionDefault, o.positionOptions));
		}
	});
});

/***/ }),
/* 21 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function(jQuery) {var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/**
 * Copyright (c) 2010 Maxim Vasiliev
 *
 * Permission is hereby granted, free of charge, to any person obtaining a copy
 * of this software and associated documentation files (the "Software"), to deal
 * in the Software without restriction, including without limitation the rights
 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
 * copies of the Software, and to permit persons to whom the Software is
 * furnished to do so, subject to the following conditions:
 *
 * The above copyright notice and this permission notice shall be included in
 * all copies or substantial portions of the Software.
 *
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
 * THE SOFTWARE.
 *
 *  
 * Date: 09.09.2010
 * Time: 19:02:33
 */

(function (factory) {
  if (true) {

    // AMD. Register as an anonymous module.
    !(__WEBPACK_AMD_DEFINE_ARRAY__ = [], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
  } else {

    // Browser globals
    factory(jQuery);
  }
})(function ($) {
  /**
   * Returns form values represented as Javascript object
   * "name" attribute defines structure of resulting object
   *
   * @param rootNode {Element|String} root form element (or it's id)
   * @param delimiter {String} structure parts delimiter defaults to '.'
   * @param skipEmpty {Boolean} should skip empty text values, defaults to true
   */
  window.form2object = function (rootNode, delimiter, skipEmpty) {
    if (typeof skipEmpty == 'undefined' || skipEmpty == null) skipEmpty = true;
    if (typeof delimiter == 'undefined' || delimiter == null) delimiter = '.';
    rootNode = typeof rootNode == 'string' ? document.getElementById(rootNode) : rootNode;

    var formValues = getFormValues(rootNode);
    var result = {};
    var arrays = {};

    for (var i = 0; i < formValues.length; i++) {
      var value = formValues[i].value;
      if (skipEmpty && value === '') continue;

      var name = formValues[i].name;

      if (name) {

        var nameParts = name.split(delimiter);

        var currResult = result;

        for (var j = 0; j < nameParts.length; j++) {
          var namePart = nameParts[j];

          var arrName;

          if (namePart.indexOf('[]') > -1 && j == nameParts.length - 1) {
            arrName = namePart.substr(0, namePart.indexOf('['));

            if (!currResult[arrName]) currResult[arrName] = [];
            currResult[arrName].push(value);
          } else {
            if (namePart.indexOf('[') > -1) {
              arrName = namePart.substr(0, namePart.indexOf('['));
              var arrIdx = namePart.replace(/^[a-z]+\[|\]$/gi, '');

              /*
               * Because arrIdx in field name can be not zero-based and step can be
               * other than 1, we can't use them in target array directly.
               * Instead we're making a hash where key is arrIdx and value is a reference to
               * added array element
               */

              if (!arrays[arrName]) arrays[arrName] = {};
              if (!currResult[arrName]) currResult[arrName] = [];

              if (j == nameParts.length - 1) {
                currResult[arrName].push(value);
              } else {
                if (!arrays[arrName][arrIdx]) {
                  currResult[arrName].push({});
                  arrays[arrName][arrIdx] = currResult[arrName][currResult[arrName].length - 1];
                }
              }

              currResult = arrays[arrName][arrIdx];
            } else {
              if (j < nameParts.length - 1) /* Not the last part of name - means object */
                {
                  if (!currResult[namePart]) currResult[namePart] = {};
                  currResult = currResult[namePart];
                } else {
                currResult[namePart] = value;
              }
            }
          }
        }
      }
    }

    return result;
  };

  function getFormValues(rootNode) {
    var result = [],
        name;
    var currentNode = rootNode.firstChild;

    while (currentNode) {
      if (currentNode.nodeName.match(/INPUT|SELECT|TEXTAREA|HIDDEN/i) || jQuery(currentNode).is("[ruptype='tree']")) {
        var fieldValue = getFieldValue(currentNode);

        if (jQuery(currentNode).is("select") && currentNode.multiple || jQuery(currentNode).is("[ruptype='tree']")) {
          var nameParts = jQuery(currentNode).attr("name").split(".");
          name = nameParts.length > 1 ? nameParts.slice(0, nameParts.length - 1).join('.') : nameParts[0];
        } else {
          name = jQuery(currentNode).attr("name");
        }
        if (fieldValue !== null) {
          result.push({ name: name, value: fieldValue });
        }
      } else {
        var subresult = getFormValues(currentNode);
        result = result.concat(subresult);
      }

      currentNode = currentNode.nextSibling;
    }

    return result;
  }

  function getFieldValue(fieldNode) {
    var ruptype = jQuery(fieldNode).attr("ruptype");
    if (ruptype) {
      return jQuery(fieldNode)["rup_" + ruptype]("getRupValue");
    } else {
      switch (fieldNode.nodeName) {
        case 'HIDDEN':
        case 'INPUT':
        case 'TEXTAREA':
          switch (fieldNode.type.toLowerCase()) {
            case 'radio':
            case 'checkbox':
              if (fieldNode.checked) return fieldNode.value;
              break;

            case 'button':
            case 'reset':
            case 'submit':
            case 'image':
              return '';
              break;

            default:
              return fieldNode.value;
              break;
          }
          break;

        case 'SELECT':
          return getSelectedOptionValue(fieldNode);
          break;

        default:
          break;
      }
    }

    return null;
  }

  function getSelectedOptionValue(selectNode) {
    var multiple = selectNode.multiple;
    if (!multiple) return selectNode.value;

    var result = [];
    for (var options = selectNode.getElementsByTagName("option"), i = 0, l = options.length; i < l; i++) {
      var nameParts = selectNode.name.split(".");
      nameParts[nameParts.length - 1];
      //                        if (options[i].selected) result.push(options[i].value);
      if (options[i].selected) {
        var jsonObj = {};
        jsonObj[nameParts[nameParts.length - 1]] = options[i].value;
        result.push(jsonObj);
      }
    }

    return result;
  }

  /**
   * @deprecated Use form2object() instead
   * @param rootNode
   * @param delimiter
   */
  window.form2json = window.form2object;
});
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))

/***/ }),
/* 22 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function(jQuery) {Object.defineProperty(exports, "__esModule", {
  value: true
});
/**
 * --------------------------------------------------------------------------
 * Bootstrap (v4.0.0-alpha.5): util.js
 * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)
 * --------------------------------------------------------------------------
 */

var Util = function ($) {

  /**
   * ------------------------------------------------------------------------
   * Private TransitionEnd Helpers
   * ------------------------------------------------------------------------
   */

  var transition = false;

  var MAX_UID = 1000000;

  var TransitionEndEvent = {
    WebkitTransition: 'webkitTransitionEnd',
    MozTransition: 'transitionend',
    OTransition: 'oTransitionEnd otransitionend',
    transition: 'transitionend'

    // shoutout AngusCroll (https://goo.gl/pxwQGp)
  };function toType(obj) {
    return {}.toString.call(obj).match(/\s([a-zA-Z]+)/)[1].toLowerCase();
  }

  function isElement(obj) {
    return (obj[0] || obj).nodeType;
  }

  function getSpecialTransitionEndEvent() {
    return {
      bindType: transition.end,
      delegateType: transition.end,
      handle: function handle(event) {
        if ($(event.target).is(this)) {
          return event.handleObj.handler.apply(this, arguments); // eslint-disable-line prefer-rest-params
        }
        return undefined;
      }
    };
  }

  function transitionEndTest() {
    if (window.QUnit) {
      return false;
    }

    var el = document.createElement('bootstrap');

    for (var name in TransitionEndEvent) {
      if (el.style[name] !== undefined) {
        return { end: TransitionEndEvent[name] };
      }
    }

    return false;
  }

  function transitionEndEmulator(duration) {
    var _this = this;

    var called = false;

    $(this).one(Util.TRANSITION_END, function () {
      called = true;
    });

    setTimeout(function () {
      if (!called) {
        Util.triggerTransitionEnd(_this);
      }
    }, duration);

    return this;
  }

  function setTransitionEndSupport() {
    transition = transitionEndTest();

    $.fn.emulateTransitionEnd = transitionEndEmulator;

    if (Util.supportsTransitionEnd()) {
      $.event.special[Util.TRANSITION_END] = getSpecialTransitionEndEvent();
    }
  }

  /**
   * --------------------------------------------------------------------------
   * Public Util Api
   * --------------------------------------------------------------------------
   */

  var Util = {

    TRANSITION_END: 'bsTransitionEnd',

    getUID: function getUID(prefix) {
      do {
        /* eslint-disable no-bitwise */
        prefix += ~~(Math.random() * MAX_UID); // "~~" acts like a faster Math.floor() here
        /* eslint-enable no-bitwise */
      } while (document.getElementById(prefix));
      return prefix;
    },
    getSelectorFromElement: function getSelectorFromElement(element) {
      var selector = element.getAttribute('data-target');

      if (!selector) {
        selector = element.getAttribute('href') || '';
        selector = /^#[a-z]/i.test(selector) ? selector : null;
      }

      return selector;
    },
    reflow: function reflow(element) {
      new Function('bs', 'return bs')(element.offsetHeight);
    },
    triggerTransitionEnd: function triggerTransitionEnd(element) {
      $(element).trigger(transition.end);
    },
    supportsTransitionEnd: function supportsTransitionEnd() {
      return Boolean(transition);
    },
    typeCheckConfig: function typeCheckConfig(componentName, config, configTypes) {
      for (var property in configTypes) {
        if (configTypes.hasOwnProperty(property)) {
          var expectedTypes = configTypes[property];
          var value = config[property];
          var valueType = void 0;

          if (value && isElement(value)) {
            valueType = 'element';
          } else {
            valueType = toType(value);
          }

          if (!new RegExp(expectedTypes).test(valueType)) {
            throw new Error(componentName.toUpperCase() + ': ' + ('Option "' + property + '" provided type "' + valueType + '" ') + ('but expected type "' + expectedTypes + '".'));
          }
        }
      }
    }
  };

  setTransitionEndSupport();

  return Util;
}(jQuery);

exports.default = Util;
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))

/***/ }),
/* 23 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*!
 * jQuery blockUI plugin
 * Version 2.70.0-2014.11.23
 * Requires jQuery v1.7 or later
 *
 * Examples at: http://malsup.com/jquery/block/
 * Copyright (c) 2007-2013 M. Alsup
 * Dual licensed under the MIT and GPL licenses:
 * http://www.opensource.org/licenses/mit-license.php
 * http://www.gnu.org/licenses/gpl.html
 *
 * Thanks to Amir-Hossein Sobhi for some excellent contributions!
 */

;(function() {
/*jshint eqeqeq:false curly:false latedef:false */
"use strict";

	function setup($) {
		$.fn._fadeIn = $.fn.fadeIn;

		var noOp = $.noop || function() {};

		// this bit is to ensure we don't call setExpression when we shouldn't (with extra muscle to handle
		// confusing userAgent strings on Vista)
		var msie = /MSIE/.test(navigator.userAgent);
		var ie6  = /MSIE 6.0/.test(navigator.userAgent) && ! /MSIE 8.0/.test(navigator.userAgent);
		var mode = document.documentMode || 0;
		var setExpr = $.isFunction( document.createElement('div').style.setExpression );

		// global $ methods for blocking/unblocking the entire page
		$.blockUI   = function(opts) { install(window, opts); };
		$.unblockUI = function(opts) { remove(window, opts); };

		// convenience method for quick growl-like notifications  (http://www.google.com/search?q=growl)
		$.growlUI = function(title, message, timeout, onClose) {
			var $m = $('<div class="growlUI"></div>');
			if (title) $m.append('<h1>'+title+'</h1>');
			if (message) $m.append('<h2>'+message+'</h2>');
			if (timeout === undefined) timeout = 3000;

			// Added by konapun: Set timeout to 30 seconds if this growl is moused over, like normal toast notifications
			var callBlock = function(opts) {
				opts = opts || {};

				$.blockUI({
					message: $m,
					fadeIn : typeof opts.fadeIn  !== 'undefined' ? opts.fadeIn  : 700,
					fadeOut: typeof opts.fadeOut !== 'undefined' ? opts.fadeOut : 1000,
					timeout: typeof opts.timeout !== 'undefined' ? opts.timeout : timeout,
					centerY: false,
					showOverlay: false,
					onUnblock: onClose,
					css: $.blockUI.defaults.growlCSS
				});
			};

			callBlock();
			var nonmousedOpacity = $m.css('opacity');
			$m.mouseover(function() {
				callBlock({
					fadeIn: 0,
					timeout: 30000
				});

				var displayBlock = $('.blockMsg');
				displayBlock.stop(); // cancel fadeout if it has started
				displayBlock.fadeTo(300, 1); // make it easier to read the message by removing transparency
			}).mouseout(function() {
				$('.blockMsg').fadeOut(1000);
			});
			// End konapun additions
		};

		// plugin method for blocking element content
		$.fn.block = function(opts) {
			if ( this[0] === window ) {
				$.blockUI( opts );
				return this;
			}
			var fullOpts = $.extend({}, $.blockUI.defaults, opts || {});
			this.each(function() {
				var $el = $(this);
				if (fullOpts.ignoreIfBlocked && $el.data('blockUI.isBlocked'))
					return;
				$el.unblock({ fadeOut: 0 });
			});

			return this.each(function() {
				if ($.css(this,'position') == 'static') {
					this.style.position = 'relative';
					$(this).data('blockUI.static', true);
				}
				this.style.zoom = 1; // force 'hasLayout' in ie
				install(this, opts);
			});
		};

		// plugin method for unblocking element content
		$.fn.unblock = function(opts) {
			if ( this[0] === window ) {
				$.unblockUI( opts );
				return this;
			}
			return this.each(function() {
				remove(this, opts);
			});
		};

		$.blockUI.version = 2.70; // 2nd generation blocking at no extra cost!

		// override these in your code to change the default behavior and style
		$.blockUI.defaults = {
			// message displayed when blocking (use null for no message)
			message:  '<h1>Please wait...</h1>',

			title: null,		// title string; only used when theme == true
			draggable: true,	// only used when theme == true (requires jquery-ui.js to be loaded)

			theme: false, // set to true to use with jQuery UI themes

			// styles for the message when blocking; if you wish to disable
			// these and use an external stylesheet then do this in your code:
			// $.blockUI.defaults.css = {};
			css: {
				padding:	0,
				margin:		0,
				width:		'30%',
				top:		'40%',
				left:		'35%',
				textAlign:	'center',
				color:		'#000',
				border:		'3px solid #aaa',
				backgroundColor:'#fff',
				cursor:		'wait'
			},

			// minimal style set used when themes are used
			themedCSS: {
				width:	'30%',
				top:	'40%',
				left:	'35%'
			},

			// styles for the overlay
			overlayCSS:  {
				backgroundColor:	'#000',
				opacity:			0.6,
				cursor:				'wait'
			},

			// style to replace wait cursor before unblocking to correct issue
			// of lingering wait cursor
			cursorReset: 'default',

			// styles applied when using $.growlUI
			growlCSS: {
				width:		'350px',
				top:		'10px',
				left:		'',
				right:		'10px',
				border:		'none',
				padding:	'5px',
				opacity:	0.6,
				cursor:		'default',
				color:		'#fff',
				backgroundColor: '#000',
				'-webkit-border-radius':'10px',
				'-moz-border-radius':	'10px',
				'border-radius':		'10px'
			},

			// IE issues: 'about:blank' fails on HTTPS and javascript:false is s-l-o-w
			// (hat tip to Jorge H. N. de Vasconcelos)
			/*jshint scripturl:true */
			iframeSrc: /^https/i.test(window.location.href || '') ? 'javascript:false' : 'about:blank',

			// force usage of iframe in non-IE browsers (handy for blocking applets)
			forceIframe: false,

			// z-index for the blocking overlay
			baseZ: 1000,

			// set these to true to have the message automatically centered
			centerX: true, // <-- only effects element blocking (page block controlled via css above)
			centerY: true,

			// allow body element to be stetched in ie6; this makes blocking look better
			// on "short" pages.  disable if you wish to prevent changes to the body height
			allowBodyStretch: true,

			// enable if you want key and mouse events to be disabled for content that is blocked
			bindEvents: true,

			// be default blockUI will supress tab navigation from leaving blocking content
			// (if bindEvents is true)
			constrainTabKey: true,

			// fadeIn time in millis; set to 0 to disable fadeIn on block
			fadeIn:  200,

			// fadeOut time in millis; set to 0 to disable fadeOut on unblock
			fadeOut:  400,

			// time in millis to wait before auto-unblocking; set to 0 to disable auto-unblock
			timeout: 0,

			// disable if you don't want to show the overlay
			showOverlay: true,

			// if true, focus will be placed in the first available input field when
			// page blocking
			focusInput: true,

            // elements that can receive focus
            focusableElements: ':input:enabled:visible',

			// suppresses the use of overlay styles on FF/Linux (due to performance issues with opacity)
			// no longer needed in 2012
			// applyPlatformOpacityRules: true,

			// callback method invoked when fadeIn has completed and blocking message is visible
			onBlock: null,

			// callback method invoked when unblocking has completed; the callback is
			// passed the element that has been unblocked (which is the window object for page
			// blocks) and the options that were passed to the unblock call:
			//	onUnblock(element, options)
			onUnblock: null,

			// callback method invoked when the overlay area is clicked.
			// setting this will turn the cursor to a pointer, otherwise cursor defined in overlayCss will be used.
			onOverlayClick: null,

			// don't ask; if you really must know: http://groups.google.com/group/jquery-en/browse_thread/thread/36640a8730503595/2f6a79a77a78e493#2f6a79a77a78e493
			quirksmodeOffsetHack: 4,

			// class name of the message block
			blockMsgClass: 'blockMsg',

			// if it is already blocked, then ignore it (don't unblock and reblock)
			ignoreIfBlocked: false
		};

		// private data and functions follow...

		var pageBlock = null;
		var pageBlockEls = [];

		function install(el, opts) {
			var css, themedCSS;
			var full = (el == window);
			var msg = (opts && opts.message !== undefined ? opts.message : undefined);
			opts = $.extend({}, $.blockUI.defaults, opts || {});

			if (opts.ignoreIfBlocked && $(el).data('blockUI.isBlocked'))
				return;

			opts.overlayCSS = $.extend({}, $.blockUI.defaults.overlayCSS, opts.overlayCSS || {});
			css = $.extend({}, $.blockUI.defaults.css, opts.css || {});
			if (opts.onOverlayClick)
				opts.overlayCSS.cursor = 'pointer';

			themedCSS = $.extend({}, $.blockUI.defaults.themedCSS, opts.themedCSS || {});
			msg = msg === undefined ? opts.message : msg;

			// remove the current block (if there is one)
			if (full && pageBlock)
				remove(window, {fadeOut:0});

			// if an existing element is being used as the blocking content then we capture
			// its current place in the DOM (and current display style) so we can restore
			// it when we unblock
			if (msg && typeof msg != 'string' && (msg.parentNode || msg.jquery)) {
				var node = msg.jquery ? msg[0] : msg;
				var data = {};
				$(el).data('blockUI.history', data);
				data.el = node;
				data.parent = node.parentNode;
				data.display = node.style.display;
				data.position = node.style.position;
				if (data.parent)
					data.parent.removeChild(node);
			}

			$(el).data('blockUI.onUnblock', opts.onUnblock);
			var z = opts.baseZ;

			// blockUI uses 3 layers for blocking, for simplicity they are all used on every platform;
			// layer1 is the iframe layer which is used to supress bleed through of underlying content
			// layer2 is the overlay layer which has opacity and a wait cursor (by default)
			// layer3 is the message content that is displayed while blocking
			var lyr1, lyr2, lyr3, s;
			if (msie || opts.forceIframe)
				lyr1 = $('<iframe class="blockUI" style="z-index:'+ (z++) +';display:none;border:none;margin:0;padding:0;position:absolute;width:100%;height:100%;top:0;left:0" src="'+opts.iframeSrc+'"></iframe>');
			else
				lyr1 = $('<div class="blockUI" style="display:none"></div>');

			if (opts.theme)
				lyr2 = $('<div class="blockUI blockOverlay ui-widget-overlay" style="z-index:'+ (z++) +';display:none"></div>');
			else
				lyr2 = $('<div class="blockUI blockOverlay" style="z-index:'+ (z++) +';display:none;border:none;margin:0;padding:0;width:100%;height:100%;top:0;left:0"></div>');

			if (opts.theme && full) {
				s = '<div class="blockUI ' + opts.blockMsgClass + ' blockPage ui-dialog ui-widget ui-corner-all" style="z-index:'+(z+10)+';display:none;position:fixed">';
				if ( opts.title ) {
					s += '<div class="ui-widget-header ui-dialog-titlebar ui-corner-all blockTitle">'+(opts.title || '&nbsp;')+'</div>';
				}
				s += '<div class="ui-widget-content ui-dialog-content"></div>';
				s += '</div>';
			}
			else if (opts.theme) {
				s = '<div class="blockUI ' + opts.blockMsgClass + ' blockElement ui-dialog ui-widget ui-corner-all" style="z-index:'+(z+10)+';display:none;position:absolute">';
				if ( opts.title ) {
					s += '<div class="ui-widget-header ui-dialog-titlebar ui-corner-all blockTitle">'+(opts.title || '&nbsp;')+'</div>';
				}
				s += '<div class="ui-widget-content ui-dialog-content"></div>';
				s += '</div>';
			}
			else if (full) {
				s = '<div class="blockUI ' + opts.blockMsgClass + ' blockPage" style="z-index:'+(z+10)+';display:none;position:fixed"></div>';
			}
			else {
				s = '<div class="blockUI ' + opts.blockMsgClass + ' blockElement" style="z-index:'+(z+10)+';display:none;position:absolute"></div>';
			}
			lyr3 = $(s);

			// if we have a message, style it
			if (msg) {
				if (opts.theme) {
					lyr3.css(themedCSS);
					lyr3.addClass('ui-widget-content');
				}
				else
					lyr3.css(css);
			}

			// style the overlay
			if (!opts.theme /*&& (!opts.applyPlatformOpacityRules)*/)
				lyr2.css(opts.overlayCSS);
			lyr2.css('position', full ? 'fixed' : 'absolute');

			// make iframe layer transparent in IE
			if (msie || opts.forceIframe)
				lyr1.css('opacity',0.0);

			//$([lyr1[0],lyr2[0],lyr3[0]]).appendTo(full ? 'body' : el);
			var layers = [lyr1,lyr2,lyr3], $par = full ? $('body') : $(el);
			$.each(layers, function() {
				this.appendTo($par);
			});

			if (opts.theme && opts.draggable && $.fn.draggable) {
				lyr3.draggable({
					handle: '.ui-dialog-titlebar',
					cancel: 'li'
				});
			}

			// ie7 must use absolute positioning in quirks mode and to account for activex issues (when scrolling)
			var expr = setExpr && (!$.support.boxModel || $('object,embed', full ? null : el).length > 0);
			if (ie6 || expr) {
				// give body 100% height
				if (full && opts.allowBodyStretch && $.support.boxModel)
					$('html,body').css('height','100%');

				// fix ie6 issue when blocked element has a border width
				if ((ie6 || !$.support.boxModel) && !full) {
					var t = sz(el,'borderTopWidth'), l = sz(el,'borderLeftWidth');
					var fixT = t ? '(0 - '+t+')' : 0;
					var fixL = l ? '(0 - '+l+')' : 0;
				}

				// simulate fixed position
				$.each(layers, function(i,o) {
					var s = o[0].style;
					s.position = 'absolute';
					if (i < 2) {
						if (full)
							s.setExpression('height','Math.max(document.body.scrollHeight, document.body.offsetHeight) - (jQuery.support.boxModel?0:'+opts.quirksmodeOffsetHack+') + "px"');
						else
							s.setExpression('height','this.parentNode.offsetHeight + "px"');
						if (full)
							s.setExpression('width','jQuery.support.boxModel && document.documentElement.clientWidth || document.body.clientWidth + "px"');
						else
							s.setExpression('width','this.parentNode.offsetWidth + "px"');
						if (fixL) s.setExpression('left', fixL);
						if (fixT) s.setExpression('top', fixT);
					}
					else if (opts.centerY) {
						if (full) s.setExpression('top','(document.documentElement.clientHeight || document.body.clientHeight) / 2 - (this.offsetHeight / 2) + (blah = document.documentElement.scrollTop ? document.documentElement.scrollTop : document.body.scrollTop) + "px"');
						s.marginTop = 0;
					}
					else if (!opts.centerY && full) {
						var top = (opts.css && opts.css.top) ? parseInt(opts.css.top, 10) : 0;
						var expression = '((document.documentElement.scrollTop ? document.documentElement.scrollTop : document.body.scrollTop) + '+top+') + "px"';
						s.setExpression('top',expression);
					}
				});
			}

			// show the message
			if (msg) {
				if (opts.theme)
					lyr3.find('.ui-widget-content').append(msg);
				else
					lyr3.append(msg);
				if (msg.jquery || msg.nodeType)
					$(msg).show();
			}

			if ((msie || opts.forceIframe) && opts.showOverlay)
				lyr1.show(); // opacity is zero
			if (opts.fadeIn) {
				var cb = opts.onBlock ? opts.onBlock : noOp;
				var cb1 = (opts.showOverlay && !msg) ? cb : noOp;
				var cb2 = msg ? cb : noOp;
				if (opts.showOverlay)
					lyr2._fadeIn(opts.fadeIn, cb1);
				if (msg)
					lyr3._fadeIn(opts.fadeIn, cb2);
			}
			else {
				if (opts.showOverlay)
					lyr2.show();
				if (msg)
					lyr3.show();
				if (opts.onBlock)
					opts.onBlock.bind(lyr3)();
			}

			// bind key and mouse events
			bind(1, el, opts);

			if (full) {
				pageBlock = lyr3[0];
				pageBlockEls = $(opts.focusableElements,pageBlock);
				if (opts.focusInput)
					setTimeout(focus, 20);
			}
			else
				center(lyr3[0], opts.centerX, opts.centerY);

			if (opts.timeout) {
				// auto-unblock
				var to = setTimeout(function() {
					if (full)
						$.unblockUI(opts);
					else
						$(el).unblock(opts);
				}, opts.timeout);
				$(el).data('blockUI.timeout', to);
			}
		}

		// remove the block
		function remove(el, opts) {
			var count;
			var full = (el == window);
			var $el = $(el);
			var data = $el.data('blockUI.history');
			var to = $el.data('blockUI.timeout');
			if (to) {
				clearTimeout(to);
				$el.removeData('blockUI.timeout');
			}
			opts = $.extend({}, $.blockUI.defaults, opts || {});
			bind(0, el, opts); // unbind events

			if (opts.onUnblock === null) {
				opts.onUnblock = $el.data('blockUI.onUnblock');
				$el.removeData('blockUI.onUnblock');
			}

			var els;
			if (full) // crazy selector to handle odd field errors in ie6/7
				els = $('body').children().filter('.blockUI').add('body > .blockUI');
			else
				els = $el.find('>.blockUI');

			// fix cursor issue
			if ( opts.cursorReset ) {
				if ( els.length > 1 )
					els[1].style.cursor = opts.cursorReset;
				if ( els.length > 2 )
					els[2].style.cursor = opts.cursorReset;
			}

			if (full)
				pageBlock = pageBlockEls = null;

			if (opts.fadeOut) {
				count = els.length;
				els.stop().fadeOut(opts.fadeOut, function() {
					if ( --count === 0)
						reset(els,data,opts,el);
				});
			}
			else
				reset(els, data, opts, el);
		}

		// move blocking element back into the DOM where it started
		function reset(els,data,opts,el) {
			var $el = $(el);
			if ( $el.data('blockUI.isBlocked') )
				return;

			els.each(function(i,o) {
				// remove via DOM calls so we don't lose event handlers
				if (this.parentNode)
					this.parentNode.removeChild(this);
			});

			if (data && data.el) {
				data.el.style.display = data.display;
				data.el.style.position = data.position;
				data.el.style.cursor = 'default'; // #59
				if (data.parent)
					data.parent.appendChild(data.el);
				$el.removeData('blockUI.history');
			}

			if ($el.data('blockUI.static')) {
				$el.css('position', 'static'); // #22
			}

			if (typeof opts.onUnblock == 'function')
				opts.onUnblock(el,opts);

			// fix issue in Safari 6 where block artifacts remain until reflow
			var body = $(document.body), w = body.width(), cssW = body[0].style.width;
			body.width(w-1).width(w);
			body[0].style.width = cssW;
		}

		// bind/unbind the handler
		function bind(b, el, opts) {
			var full = el == window, $el = $(el);

			// don't bother unbinding if there is nothing to unbind
			if (!b && (full && !pageBlock || !full && !$el.data('blockUI.isBlocked')))
				return;

			$el.data('blockUI.isBlocked', b);

			// don't bind events when overlay is not in use or if bindEvents is false
			if (!full || !opts.bindEvents || (b && !opts.showOverlay))
				return;

			// bind anchors and inputs for mouse and key events
			var events = 'mousedown mouseup keydown keypress keyup touchstart touchend touchmove';
			if (b)
				$(document).bind(events, opts, handler);
			else
				$(document).unbind(events, handler);

		// former impl...
		//		var $e = $('a,:input');
		//		b ? $e.bind(events, opts, handler) : $e.unbind(events, handler);
		}

		// event handler to suppress keyboard/mouse events when blocking
		function handler(e) {
			// allow tab navigation (conditionally)
			if (e.type === 'keydown' && e.keyCode && e.keyCode == 9) {
				if (pageBlock && e.data.constrainTabKey) {
					var els = pageBlockEls;
					var fwd = !e.shiftKey && e.target === els[els.length-1];
					var back = e.shiftKey && e.target === els[0];
					if (fwd || back) {
						setTimeout(function(){focus(back);},10);
						return false;
					}
				}
			}
			var opts = e.data;
			var target = $(e.target);
			if (target.hasClass('blockOverlay') && opts.onOverlayClick)
				opts.onOverlayClick(e);

			// allow events within the message content
			if (target.parents('div.' + opts.blockMsgClass).length > 0)
				return true;

			// allow events for content that is not being blocked
			return target.parents().children().filter('div.blockUI').length === 0;
		}

		function focus(back) {
			if (!pageBlockEls)
				return;
			var e = pageBlockEls[back===true ? pageBlockEls.length-1 : 0];
			if (e)
				e.focus();
		}

		function center(el, x, y) {
			var p = el.parentNode, s = el.style;
			var l = ((p.offsetWidth - el.offsetWidth)/2) - sz(p,'borderLeftWidth');
			var t = ((p.offsetHeight - el.offsetHeight)/2) - sz(p,'borderTopWidth');
			if (x) s.left = l > 0 ? (l+'px') : '0';
			if (y) s.top  = t > 0 ? (t+'px') : '0';
		}

		function sz(el, p) {
			return parseInt($.css(el,p),10)||0;
		}

	}


	/*global define:true */
	if (true) {
		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0)], __WEBPACK_AMD_DEFINE_FACTORY__ = (setup),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else if (typeof exports === 'object') {
		// Node/CommonJS
		setup(require('jquery'));
	} else {
		// Browser globals
		setup(jQuery);
	}

})();


/***/ }),
/* 24 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*
 * JavaScript Load Image Meta
 * https://github.com/blueimp/JavaScript-Load-Image
 *
 * Copyright 2013, Sebastian Tschan
 * https://blueimp.net
 *
 * Image meta data handling implementation
 * based on the help and contribution of
 * Achim Stöhr.
 *
 * Licensed under the MIT license:
 * http://www.opensource.org/licenses/MIT
 */

/*global define, module, require, window, DataView, Blob, Uint8Array, console */

;(function (factory) {
  'use strict'
  if (true) {
    // Register as an anonymous AMD module:
    !(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(5)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__))
  } else if (typeof module === 'object' && module.exports) {
    factory(require('./load-image'))
  } else {
    // Browser globals:
    factory(window.loadImage)
  }
}(function (loadImage) {
  'use strict'

  var hasblobSlice = window.Blob && (Blob.prototype.slice ||
  Blob.prototype.webkitSlice || Blob.prototype.mozSlice)

  loadImage.blobSlice = hasblobSlice && function () {
    var slice = this.slice || this.webkitSlice || this.mozSlice
    return slice.apply(this, arguments)
  }

  loadImage.metaDataParsers = {
    jpeg: {
      0xffe1: [] // APP1 marker
    }
  }

  // Parses image meta data and calls the callback with an object argument
  // with the following properties:
  // * imageHead: The complete image head as ArrayBuffer (Uint8Array for IE10)
  // The options arguments accepts an object and supports the following properties:
  // * maxMetaDataSize: Defines the maximum number of bytes to parse.
  // * disableImageHead: Disables creating the imageHead property.
  loadImage.parseMetaData = function (file, callback, options) {
    options = options || {}
    var that = this
    // 256 KiB should contain all EXIF/ICC/IPTC segments:
    var maxMetaDataSize = options.maxMetaDataSize || 262144
    var data = {}
    var noMetaData = !(window.DataView && file && file.size >= 12 &&
                      file.type === 'image/jpeg' && loadImage.blobSlice)
    if (noMetaData || !loadImage.readFile(
        loadImage.blobSlice.call(file, 0, maxMetaDataSize),
        function (e) {
          if (e.target.error) {
            // FileReader error
            console.log(e.target.error)
            callback(data)
            return
          }
          // Note on endianness:
          // Since the marker and length bytes in JPEG files are always
          // stored in big endian order, we can leave the endian parameter
          // of the DataView methods undefined, defaulting to big endian.
          var buffer = e.target.result
          var dataView = new DataView(buffer)
          var offset = 2
          var maxOffset = dataView.byteLength - 4
          var headLength = offset
          var markerBytes
          var markerLength
          var parsers
          var i
          // Check for the JPEG marker (0xffd8):
          if (dataView.getUint16(0) === 0xffd8) {
            while (offset < maxOffset) {
              markerBytes = dataView.getUint16(offset)
              // Search for APPn (0xffeN) and COM (0xfffe) markers,
              // which contain application-specific meta-data like
              // Exif, ICC and IPTC data and text comments:
              if ((markerBytes >= 0xffe0 && markerBytes <= 0xffef) ||
                markerBytes === 0xfffe) {
                // The marker bytes (2) are always followed by
                // the length bytes (2), indicating the length of the
                // marker segment, which includes the length bytes,
                // but not the marker bytes, so we add 2:
                markerLength = dataView.getUint16(offset + 2) + 2
                if (offset + markerLength > dataView.byteLength) {
                  console.log('Invalid meta data: Invalid segment size.')
                  break
                }
                parsers = loadImage.metaDataParsers.jpeg[markerBytes]
                if (parsers) {
                  for (i = 0; i < parsers.length; i += 1) {
                    parsers[i].call(
                      that,
                      dataView,
                      offset,
                      markerLength,
                      data,
                      options
                    )
                  }
                }
                offset += markerLength
                headLength = offset
              } else {
                // Not an APPn or COM marker, probably safe to
                // assume that this is the end of the meta data
                break
              }
            }
            // Meta length must be longer than JPEG marker (2)
            // plus APPn marker (2), followed by length bytes (2):
            if (!options.disableImageHead && headLength > 6) {
              if (buffer.slice) {
                data.imageHead = buffer.slice(0, headLength)
              } else {
                // Workaround for IE10, which does not yet
                // support ArrayBuffer.slice:
                data.imageHead = new Uint8Array(buffer)
                  .subarray(0, headLength)
              }
            }
          } else {
            console.log('Invalid JPEG file: Missing JPEG marker.')
          }
          callback(data)
        },
        'readAsArrayBuffer'
      )) {
      callback(data)
    }
  }
}))


/***/ }),
/* 25 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*! DataTables Bootstrap 3 integration
 * ©2011-2015 SpryMedia Ltd - datatables.net/license
 */

/**
 * DataTables integration for Bootstrap 3. This requires Bootstrap 3 and
 * DataTables 1.10 or newer.
 *
 * This file sets the defaults and adds options to DataTables to style its
 * controls using Bootstrap. See http://datatables.net/manual/styling/bootstrap
 * for further information.
 */
(function( factory ){
	if ( true ) {
		// AMD
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(4)], __WEBPACK_AMD_DEFINE_RESULT__ = function ( $ ) {
			return factory( $, window, document );
		}.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	}
	else if ( typeof exports === 'object' ) {
		// CommonJS
		module.exports = function (root, $) {
			if ( ! root ) {
				root = window;
			}

			if ( ! $ || ! $.fn.dataTable ) {
				// Require DataTables, which attaches to jQuery, including
				// jQuery if needed and have a $ property so we can access the
				// jQuery object that is used
				$ = require('datatables.net')(root, $).$;
			}

			return factory( $, root, root.document );
		};
	}
	else {
		// Browser
		factory( jQuery, window, document );
	}
}(function( $, window, document, undefined ) {
'use strict';
var DataTable = $.fn.dataTable;


/* Set the defaults for DataTables initialisation */
$.extend( true, DataTable.defaults, {
	dom:
		"<'row'<'col-sm-12 col-md-6'l><'col-sm-12 col-md-6'f>>" +
		"<'row'<'col-sm-12'tr>>" +
		"<'row'<'col-sm-12 col-md-5'i><'col-sm-12 col-md-7'p>>",
	renderer: 'bootstrap'
} );


/* Default class modification */
$.extend( DataTable.ext.classes, {
	sWrapper:      "dataTables_wrapper container-fluid dt-bootstrap4",
	sFilterInput:  "form-control form-control-sm",
	sLengthSelect: "form-control form-control-sm",
	sProcessing:   "dataTables_processing card",
	sPageButton:   "paginate_button page-item"
} );


/* Bootstrap paging button renderer */
DataTable.ext.renderer.pageButton.bootstrap = function ( settings, host, idx, buttons, page, pages ) {
	var api     = new DataTable.Api( settings );
	var classes = settings.oClasses;
	var lang    = settings.oLanguage.oPaginate;
	var aria = settings.oLanguage.oAria.paginate || {};
	var btnDisplay, btnClass, counter=0;

	var attach = function( container, buttons ) {
		var i, ien, node, button;
		var clickHandler = function ( e ) {
			e.preventDefault();
			if ( !$(e.currentTarget).hasClass('disabled') && api.page() != e.data.action ) {
				api.page( e.data.action ).draw( 'page' );
			}
		};

		for ( i=0, ien=buttons.length ; i<ien ; i++ ) {
			button = buttons[i];

			if ( $.isArray( button ) ) {
				attach( container, button );
			}
			else {
				btnDisplay = '';
				btnClass = '';

				switch ( button ) {
					case 'ellipsis':
						btnDisplay = '&#x2026;';
						btnClass = 'disabled';
						break;

					case 'first':
						btnDisplay = lang.sFirst;
						btnClass = button + (page > 0 ?
							'' : ' disabled');
						break;

					case 'previous':
						btnDisplay = lang.sPrevious;
						btnClass = button + (page > 0 ?
							'' : ' disabled');
						break;

					case 'next':
						btnDisplay = lang.sNext;
						btnClass = button + (page < pages-1 ?
							'' : ' disabled');
						break;

					case 'last':
						btnDisplay = lang.sLast;
						btnClass = button + (page < pages-1 ?
							'' : ' disabled');
						break;

					default:
						btnDisplay = button + 1;
						btnClass = page === button ?
							'active' : '';
						break;
				}

				if ( btnDisplay ) {
					node = $('<li>', {
							'class': classes.sPageButton+' '+btnClass,
							'id': idx === 0 && typeof button === 'string' ?
								settings.sTableId +'_'+ button :
								null
						} )
						.append( $('<a>', {
								'href': '#',
								'aria-controls': settings.sTableId,
								'aria-label': aria[ button ],
								'data-dt-idx': counter,
								'tabindex': settings.iTabIndex,
								'class': 'page-link'
							} )
							.html( btnDisplay )
						)
						.appendTo( container );

					settings.oApi._fnBindAction(
						node, {action: button}, clickHandler
					);

					counter++;
				}
			}
		}
	};

	// IE9 throws an 'unknown error' if document.activeElement is used
	// inside an iframe or frame. 
	var activeEl;

	try {
		// Because this approach is destroying and recreating the paging
		// elements, focus is lost on the select button which is bad for
		// accessibility. So we want to restore focus once the draw has
		// completed
		activeEl = $(host).find(document.activeElement).data('dt-idx');
	}
	catch (e) {}

	attach(
		$(host).empty().html('<ul class="pagination"/>').children('ul'),
		buttons
	);

	if ( activeEl !== undefined ) {
		$(host).find( '[data-dt-idx='+activeEl+']' ).focus();
	}
};


return DataTable;
}));


/***/ }),
/* 26 */
/***/ (function(module, exports, __webpack_require__) {

/*!

 handlebars v4.0.5

Copyright (C) 2011-2015 by Yehuda Katz

Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:

The above copyright notice and this permission notice shall be included in
all copies or substantial portions of the Software.

THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
THE SOFTWARE.

@license
*/
(function webpackUniversalModuleDefinition(root, factory) {
	if(true)
		module.exports = factory();
	else if(typeof define === 'function' && define.amd)
		define([], factory);
	else if(typeof exports === 'object')
		exports["Handlebars"] = factory();
	else
		root["Handlebars"] = factory();
})(this, function() {
return /******/ (function(modules) { // webpackBootstrap
/******/ 	// The module cache
/******/ 	var installedModules = {};

/******/ 	// The require function
/******/ 	function __webpack_require__(moduleId) {

/******/ 		// Check if module is in cache
/******/ 		if(installedModules[moduleId])
/******/ 			return installedModules[moduleId].exports;

/******/ 		// Create a new module (and put it into the cache)
/******/ 		var module = installedModules[moduleId] = {
/******/ 			exports: {},
/******/ 			id: moduleId,
/******/ 			loaded: false
/******/ 		};

/******/ 		// Execute the module function
/******/ 		modules[moduleId].call(module.exports, module, module.exports, __webpack_require__);

/******/ 		// Flag the module as loaded
/******/ 		module.loaded = true;

/******/ 		// Return the exports of the module
/******/ 		return module.exports;
/******/ 	}


/******/ 	// expose the modules object (__webpack_modules__)
/******/ 	__webpack_require__.m = modules;

/******/ 	// expose the module cache
/******/ 	__webpack_require__.c = installedModules;

/******/ 	// __webpack_public_path__
/******/ 	__webpack_require__.p = "";

/******/ 	// Load entry module and return exports
/******/ 	return __webpack_require__(0);
/******/ })
/************************************************************************/
/******/ ([
/* 0 */
/***/ function(module, exports, __webpack_require__) {

	'use strict';

	var _interopRequireDefault = __webpack_require__(1)['default'];

	exports.__esModule = true;

	var _handlebarsRuntime = __webpack_require__(2);

	var _handlebarsRuntime2 = _interopRequireDefault(_handlebarsRuntime);

	// Compiler imports

	var _handlebarsCompilerAst = __webpack_require__(21);

	var _handlebarsCompilerAst2 = _interopRequireDefault(_handlebarsCompilerAst);

	var _handlebarsCompilerBase = __webpack_require__(22);

	var _handlebarsCompilerCompiler = __webpack_require__(27);

	var _handlebarsCompilerJavascriptCompiler = __webpack_require__(28);

	var _handlebarsCompilerJavascriptCompiler2 = _interopRequireDefault(_handlebarsCompilerJavascriptCompiler);

	var _handlebarsCompilerVisitor = __webpack_require__(25);

	var _handlebarsCompilerVisitor2 = _interopRequireDefault(_handlebarsCompilerVisitor);

	var _handlebarsNoConflict = __webpack_require__(20);

	var _handlebarsNoConflict2 = _interopRequireDefault(_handlebarsNoConflict);

	var _create = _handlebarsRuntime2['default'].create;
	function create() {
	  var hb = _create();

	  hb.compile = function (input, options) {
	    return _handlebarsCompilerCompiler.compile(input, options, hb);
	  };
	  hb.precompile = function (input, options) {
	    return _handlebarsCompilerCompiler.precompile(input, options, hb);
	  };

	  hb.AST = _handlebarsCompilerAst2['default'];
	  hb.Compiler = _handlebarsCompilerCompiler.Compiler;
	  hb.JavaScriptCompiler = _handlebarsCompilerJavascriptCompiler2['default'];
	  hb.Parser = _handlebarsCompilerBase.parser;
	  hb.parse = _handlebarsCompilerBase.parse;

	  return hb;
	}

	var inst = create();
	inst.create = create;

	_handlebarsNoConflict2['default'](inst);

	inst.Visitor = _handlebarsCompilerVisitor2['default'];

	inst['default'] = inst;

	exports['default'] = inst;
	module.exports = exports['default'];

/***/ },
/* 1 */
/***/ function(module, exports) {

	"use strict";

	exports["default"] = function (obj) {
	  return obj && obj.__esModule ? obj : {
	    "default": obj
	  };
	};

	exports.__esModule = true;

/***/ },
/* 2 */
/***/ function(module, exports, __webpack_require__) {

	'use strict';

	var _interopRequireWildcard = __webpack_require__(3)['default'];

	var _interopRequireDefault = __webpack_require__(1)['default'];

	exports.__esModule = true;

	var _handlebarsBase = __webpack_require__(4);

	var base = _interopRequireWildcard(_handlebarsBase);

	// Each of these augment the Handlebars object. No need to setup here.
	// (This is done to easily share code between commonjs and browse envs)

	var _handlebarsSafeString = __webpack_require__(18);

	var _handlebarsSafeString2 = _interopRequireDefault(_handlebarsSafeString);

	var _handlebarsException = __webpack_require__(6);

	var _handlebarsException2 = _interopRequireDefault(_handlebarsException);

	var _handlebarsUtils = __webpack_require__(5);

	var Utils = _interopRequireWildcard(_handlebarsUtils);

	var _handlebarsRuntime = __webpack_require__(19);

	var runtime = _interopRequireWildcard(_handlebarsRuntime);

	var _handlebarsNoConflict = __webpack_require__(20);

	var _handlebarsNoConflict2 = _interopRequireDefault(_handlebarsNoConflict);

	// For compatibility and usage outside of module systems, make the Handlebars object a namespace
	function create() {
	  var hb = new base.HandlebarsEnvironment();

	  Utils.extend(hb, base);
	  hb.SafeString = _handlebarsSafeString2['default'];
	  hb.Exception = _handlebarsException2['default'];
	  hb.Utils = Utils;
	  hb.escapeExpression = Utils.escapeExpression;

	  hb.VM = runtime;
	  hb.template = function (spec) {
	    return runtime.template(spec, hb);
	  };

	  return hb;
	}

	var inst = create();
	inst.create = create;

	_handlebarsNoConflict2['default'](inst);

	inst['default'] = inst;

	exports['default'] = inst;
	module.exports = exports['default'];

/***/ },
/* 3 */
/***/ function(module, exports) {

	"use strict";

	exports["default"] = function (obj) {
	  if (obj && obj.__esModule) {
	    return obj;
	  } else {
	    var newObj = {};

	    if (obj != null) {
	      for (var key in obj) {
	        if (Object.prototype.hasOwnProperty.call(obj, key)) newObj[key] = obj[key];
	      }
	    }

	    newObj["default"] = obj;
	    return newObj;
	  }
	};

	exports.__esModule = true;

/***/ },
/* 4 */
/***/ function(module, exports, __webpack_require__) {

	'use strict';

	var _interopRequireDefault = __webpack_require__(1)['default'];

	exports.__esModule = true;
	exports.HandlebarsEnvironment = HandlebarsEnvironment;

	var _utils = __webpack_require__(5);

	var _exception = __webpack_require__(6);

	var _exception2 = _interopRequireDefault(_exception);

	var _helpers = __webpack_require__(7);

	var _decorators = __webpack_require__(15);

	var _logger = __webpack_require__(17);

	var _logger2 = _interopRequireDefault(_logger);

	var VERSION = '4.0.5';
	exports.VERSION = VERSION;
	var COMPILER_REVISION = 7;

	exports.COMPILER_REVISION = COMPILER_REVISION;
	var REVISION_CHANGES = {
	  1: '<= 1.0.rc.2', // 1.0.rc.2 is actually rev2 but doesn't report it
	  2: '== 1.0.0-rc.3',
	  3: '== 1.0.0-rc.4',
	  4: '== 1.x.x',
	  5: '== 2.0.0-alpha.x',
	  6: '>= 2.0.0-beta.1',
	  7: '>= 4.0.0'
	};

	exports.REVISION_CHANGES = REVISION_CHANGES;
	var objectType = '[object Object]';

	function HandlebarsEnvironment(helpers, partials, decorators) {
	  this.helpers = helpers || {};
	  this.partials = partials || {};
	  this.decorators = decorators || {};

	  _helpers.registerDefaultHelpers(this);
	  _decorators.registerDefaultDecorators(this);
	}

	HandlebarsEnvironment.prototype = {
	  constructor: HandlebarsEnvironment,

	  logger: _logger2['default'],
	  log: _logger2['default'].log,

	  registerHelper: function registerHelper(name, fn) {
	    if (_utils.toString.call(name) === objectType) {
	      if (fn) {
	        throw new _exception2['default']('Arg not supported with multiple helpers');
	      }
	      _utils.extend(this.helpers, name);
	    } else {
	      this.helpers[name] = fn;
	    }
	  },
	  unregisterHelper: function unregisterHelper(name) {
	    delete this.helpers[name];
	  },

	  registerPartial: function registerPartial(name, partial) {
	    if (_utils.toString.call(name) === objectType) {
	      _utils.extend(this.partials, name);
	    } else {
	      if (typeof partial === 'undefined') {
	        throw new _exception2['default']('Attempting to register a partial called "' + name + '" as undefined');
	      }
	      this.partials[name] = partial;
	    }
	  },
	  unregisterPartial: function unregisterPartial(name) {
	    delete this.partials[name];
	  },

	  registerDecorator: function registerDecorator(name, fn) {
	    if (_utils.toString.call(name) === objectType) {
	      if (fn) {
	        throw new _exception2['default']('Arg not supported with multiple decorators');
	      }
	      _utils.extend(this.decorators, name);
	    } else {
	      this.decorators[name] = fn;
	    }
	  },
	  unregisterDecorator: function unregisterDecorator(name) {
	    delete this.decorators[name];
	  }
	};

	var log = _logger2['default'].log;

	exports.log = log;
	exports.createFrame = _utils.createFrame;
	exports.logger = _logger2['default'];

/***/ },
/* 5 */
/***/ function(module, exports) {

	'use strict';

	exports.__esModule = true;
	exports.extend = extend;
	exports.indexOf = indexOf;
	exports.escapeExpression = escapeExpression;
	exports.isEmpty = isEmpty;
	exports.createFrame = createFrame;
	exports.blockParams = blockParams;
	exports.appendContextPath = appendContextPath;
	var escape = {
	  '&': '&amp;',
	  '<': '&lt;',
	  '>': '&gt;',
	  '"': '&quot;',
	  "'": '&#x27;',
	  '`': '&#x60;',
	  '=': '&#x3D;'
	};

	var badChars = /[&<>"'`=]/g,
	    possible = /[&<>"'`=]/;

	function escapeChar(chr) {
	  return escape[chr];
	}

	function extend(obj /* , ...source */) {
	  for (var i = 1; i < arguments.length; i++) {
	    for (var key in arguments[i]) {
	      if (Object.prototype.hasOwnProperty.call(arguments[i], key)) {
	        obj[key] = arguments[i][key];
	      }
	    }
	  }

	  return obj;
	}

	var toString = Object.prototype.toString;

	exports.toString = toString;
	// Sourced from lodash
	// https://github.com/bestiejs/lodash/blob/master/LICENSE.txt
	/* eslint-disable func-style */
	var isFunction = function isFunction(value) {
	  return typeof value === 'function';
	};
	// fallback for older versions of Chrome and Safari
	/* istanbul ignore next */
	if (isFunction(/x/)) {
	  exports.isFunction = isFunction = function (value) {
	    return typeof value === 'function' && toString.call(value) === '[object Function]';
	  };
	}
	exports.isFunction = isFunction;

	/* eslint-enable func-style */

	/* istanbul ignore next */
	var isArray = Array.isArray || function (value) {
	  return value && typeof value === 'object' ? toString.call(value) === '[object Array]' : false;
	};

	exports.isArray = isArray;
	// Older IE versions do not directly support indexOf so we must implement our own, sadly.

	function indexOf(array, value) {
	  for (var i = 0, len = array.length; i < len; i++) {
	    if (array[i] === value) {
	      return i;
	    }
	  }
	  return -1;
	}

	function escapeExpression(string) {
	  if (typeof string !== 'string') {
	    // don't escape SafeStrings, since they're already safe
	    if (string && string.toHTML) {
	      return string.toHTML();
	    } else if (string == null) {
	      return '';
	    } else if (!string) {
	      return string + '';
	    }

	    // Force a string conversion as this will be done by the append regardless and
	    // the regex test will do this transparently behind the scenes, causing issues if
	    // an object's to string has escaped characters in it.
	    string = '' + string;
	  }

	  if (!possible.test(string)) {
	    return string;
	  }
	  return string.replace(badChars, escapeChar);
	}

	function isEmpty(value) {
	  if (!value && value !== 0) {
	    return true;
	  } else if (isArray(value) && value.length === 0) {
	    return true;
	  } else {
	    return false;
	  }
	}

	function createFrame(object) {
	  var frame = extend({}, object);
	  frame._parent = object;
	  return frame;
	}

	function blockParams(params, ids) {
	  params.path = ids;
	  return params;
	}

	function appendContextPath(contextPath, id) {
	  return (contextPath ? contextPath + '.' : '') + id;
	}

/***/ },
/* 6 */
/***/ function(module, exports) {

	'use strict';

	exports.__esModule = true;

	var errorProps = ['description', 'fileName', 'lineNumber', 'message', 'name', 'number', 'stack'];

	function Exception(message, node) {
	  var loc = node && node.loc,
	      line = undefined,
	      column = undefined;
	  if (loc) {
	    line = loc.start.line;
	    column = loc.start.column;

	    message += ' - ' + line + ':' + column;
	  }

	  var tmp = Error.prototype.constructor.call(this, message);

	  // Unfortunately errors are not enumerable in Chrome (at least), so `for prop in tmp` doesn't work.
	  for (var idx = 0; idx < errorProps.length; idx++) {
	    this[errorProps[idx]] = tmp[errorProps[idx]];
	  }

	  /* istanbul ignore else */
	  if (Error.captureStackTrace) {
	    Error.captureStackTrace(this, Exception);
	  }

	  if (loc) {
	    this.lineNumber = line;
	    this.column = column;
	  }
	}

	Exception.prototype = new Error();

	exports['default'] = Exception;
	module.exports = exports['default'];

/***/ },
/* 7 */
/***/ function(module, exports, __webpack_require__) {

	'use strict';

	var _interopRequireDefault = __webpack_require__(1)['default'];

	exports.__esModule = true;
	exports.registerDefaultHelpers = registerDefaultHelpers;

	var _helpersBlockHelperMissing = __webpack_require__(8);

	var _helpersBlockHelperMissing2 = _interopRequireDefault(_helpersBlockHelperMissing);

	var _helpersEach = __webpack_require__(9);

	var _helpersEach2 = _interopRequireDefault(_helpersEach);

	var _helpersHelperMissing = __webpack_require__(10);

	var _helpersHelperMissing2 = _interopRequireDefault(_helpersHelperMissing);

	var _helpersIf = __webpack_require__(11);

	var _helpersIf2 = _interopRequireDefault(_helpersIf);

	var _helpersLog = __webpack_require__(12);

	var _helpersLog2 = _interopRequireDefault(_helpersLog);

	var _helpersLookup = __webpack_require__(13);

	var _helpersLookup2 = _interopRequireDefault(_helpersLookup);

	var _helpersWith = __webpack_require__(14);

	var _helpersWith2 = _interopRequireDefault(_helpersWith);

	function registerDefaultHelpers(instance) {
	  _helpersBlockHelperMissing2['default'](instance);
	  _helpersEach2['default'](instance);
	  _helpersHelperMissing2['default'](instance);
	  _helpersIf2['default'](instance);
	  _helpersLog2['default'](instance);
	  _helpersLookup2['default'](instance);
	  _helpersWith2['default'](instance);
	}

/***/ },
/* 8 */
/***/ function(module, exports, __webpack_require__) {

	'use strict';

	exports.__esModule = true;

	var _utils = __webpack_require__(5);

	exports['default'] = function (instance) {
	  instance.registerHelper('blockHelperMissing', function (context, options) {
	    var inverse = options.inverse,
	        fn = options.fn;

	    if (context === true) {
	      return fn(this);
	    } else if (context === false || context == null) {
	      return inverse(this);
	    } else if (_utils.isArray(context)) {
	      if (context.length > 0) {
	        if (options.ids) {
	          options.ids = [options.name];
	        }

	        return instance.helpers.each(context, options);
	      } else {
	        return inverse(this);
	      }
	    } else {
	      if (options.data && options.ids) {
	        var data = _utils.createFrame(options.data);
	        data.contextPath = _utils.appendContextPath(options.data.contextPath, options.name);
	        options = { data: data };
	      }

	      return fn(context, options);
	    }
	  });
	};

	module.exports = exports['default'];

/***/ },
/* 9 */
/***/ function(module, exports, __webpack_require__) {

	'use strict';

	var _interopRequireDefault = __webpack_require__(1)['default'];

	exports.__esModule = true;

	var _utils = __webpack_require__(5);

	var _exception = __webpack_require__(6);

	var _exception2 = _interopRequireDefault(_exception);

	exports['default'] = function (instance) {
	  instance.registerHelper('each', function (context, options) {
	    if (!options) {
	      throw new _exception2['default']('Must pass iterator to #each');
	    }

	    var fn = options.fn,
	        inverse = options.inverse,
	        i = 0,
	        ret = '',
	        data = undefined,
	        contextPath = undefined;

	    if (options.data && options.ids) {
	      contextPath = _utils.appendContextPath(options.data.contextPath, options.ids[0]) + '.';
	    }

	    if (_utils.isFunction(context)) {
	      context = context.call(this);
	    }

	    if (options.data) {
	      data = _utils.createFrame(options.data);
	    }

	    function execIteration(field, index, last) {
	      if (data) {
	        data.key = field;
	        data.index = index;
	        data.first = index === 0;
	        data.last = !!last;

	        if (contextPath) {
	          data.contextPath = contextPath + field;
	        }
	      }

	      ret = ret + fn(context[field], {
	        data: data,
	        blockParams: _utils.blockParams([context[field], field], [contextPath + field, null])
	      });
	    }

	    if (context && typeof context === 'object') {
	      if (_utils.isArray(context)) {
	        for (var j = context.length; i < j; i++) {
	          if (i in context) {
	            execIteration(i, i, i === context.length - 1);
	          }
	        }
	      } else {
	        var priorKey = undefined;

	        for (var key in context) {
	          if (context.hasOwnProperty(key)) {
	            // We're running the iterations one step out of sync so we can detect
	            // the last iteration without have to scan the object twice and create
	            // an itermediate keys array.
	            if (priorKey !== undefined) {
	              execIteration(priorKey, i - 1);
	            }
	            priorKey = key;
	            i++;
	          }
	        }
	        if (priorKey !== undefined) {
	          execIteration(priorKey, i - 1, true);
	        }
	      }
	    }

	    if (i === 0) {
	      ret = inverse(this);
	    }

	    return ret;
	  });
	};

	module.exports = exports['default'];

/***/ },
/* 10 */
/***/ function(module, exports, __webpack_require__) {

	'use strict';

	var _interopRequireDefault = __webpack_require__(1)['default'];

	exports.__esModule = true;

	var _exception = __webpack_require__(6);

	var _exception2 = _interopRequireDefault(_exception);

	exports['default'] = function (instance) {
	  instance.registerHelper('helperMissing', function () /* [args, ]options */{
	    if (arguments.length === 1) {
	      // A missing field in a {{foo}} construct.
	      return undefined;
	    } else {
	      // Someone is actually trying to call something, blow up.
	      throw new _exception2['default']('Missing helper: "' + arguments[arguments.length - 1].name + '"');
	    }
	  });
	};

	module.exports = exports['default'];

/***/ },
/* 11 */
/***/ function(module, exports, __webpack_require__) {

	'use strict';

	exports.__esModule = true;

	var _utils = __webpack_require__(5);

	exports['default'] = function (instance) {
	  instance.registerHelper('if', function (conditional, options) {
	    if (_utils.isFunction(conditional)) {
	      conditional = conditional.call(this);
	    }

	    // Default behavior is to render the positive path if the value is truthy and not empty.
	    // The `includeZero` option may be set to treat the condtional as purely not empty based on the
	    // behavior of isEmpty. Effectively this determines if 0 is handled by the positive path or negative.
	    if (!options.hash.includeZero && !conditional || _utils.isEmpty(conditional)) {
	      return options.inverse(this);
	    } else {
	      return options.fn(this);
	    }
	  });

	  instance.registerHelper('unless', function (conditional, options) {
	    return instance.helpers['if'].call(this, conditional, { fn: options.inverse, inverse: options.fn, hash: options.hash });
	  });
	};

	module.exports = exports['default'];

/***/ },
/* 12 */
/***/ function(module, exports) {

	'use strict';

	exports.__esModule = true;

	exports['default'] = function (instance) {
	  instance.registerHelper('log', function () /* message, options */{
	    var args = [undefined],
	        options = arguments[arguments.length - 1];
	    for (var i = 0; i < arguments.length - 1; i++) {
	      args.push(arguments[i]);
	    }

	    var level = 1;
	    if (options.hash.level != null) {
	      level = options.hash.level;
	    } else if (options.data && options.data.level != null) {
	      level = options.data.level;
	    }
	    args[0] = level;

	    instance.log.apply(instance, args);
	  });
	};

	module.exports = exports['default'];

/***/ },
/* 13 */
/***/ function(module, exports) {

	'use strict';

	exports.__esModule = true;

	exports['default'] = function (instance) {
	  instance.registerHelper('lookup', function (obj, field) {
	    return obj && obj[field];
	  });
	};

	module.exports = exports['default'];

/***/ },
/* 14 */
/***/ function(module, exports, __webpack_require__) {

	'use strict';

	exports.__esModule = true;

	var _utils = __webpack_require__(5);

	exports['default'] = function (instance) {
	  instance.registerHelper('with', function (context, options) {
	    if (_utils.isFunction(context)) {
	      context = context.call(this);
	    }

	    var fn = options.fn;

	    if (!_utils.isEmpty(context)) {
	      var data = options.data;
	      if (options.data && options.ids) {
	        data = _utils.createFrame(options.data);
	        data.contextPath = _utils.appendContextPath(options.data.contextPath, options.ids[0]);
	      }

	      return fn(context, {
	        data: data,
	        blockParams: _utils.blockParams([context], [data && data.contextPath])
	      });
	    } else {
	      return options.inverse(this);
	    }
	  });
	};

	module.exports = exports['default'];

/***/ },
/* 15 */
/***/ function(module, exports, __webpack_require__) {

	'use strict';

	var _interopRequireDefault = __webpack_require__(1)['default'];

	exports.__esModule = true;
	exports.registerDefaultDecorators = registerDefaultDecorators;

	var _decoratorsInline = __webpack_require__(16);

	var _decoratorsInline2 = _interopRequireDefault(_decoratorsInline);

	function registerDefaultDecorators(instance) {
	  _decoratorsInline2['default'](instance);
	}

/***/ },
/* 16 */
/***/ function(module, exports, __webpack_require__) {

	'use strict';

	exports.__esModule = true;

	var _utils = __webpack_require__(5);

	exports['default'] = function (instance) {
	  instance.registerDecorator('inline', function (fn, props, container, options) {
	    var ret = fn;
	    if (!props.partials) {
	      props.partials = {};
	      ret = function (context, options) {
	        // Create a new partials stack frame prior to exec.
	        var original = container.partials;
	        container.partials = _utils.extend({}, original, props.partials);
	        var ret = fn(context, options);
	        container.partials = original;
	        return ret;
	      };
	    }

	    props.partials[options.args[0]] = options.fn;

	    return ret;
	  });
	};

	module.exports = exports['default'];

/***/ },
/* 17 */
/***/ function(module, exports, __webpack_require__) {

	'use strict';

	exports.__esModule = true;

	var _utils = __webpack_require__(5);

	var logger = {
	  methodMap: ['debug', 'info', 'warn', 'error'],
	  level: 'info',

	  // Maps a given level value to the `methodMap` indexes above.
	  lookupLevel: function lookupLevel(level) {
	    if (typeof level === 'string') {
	      var levelMap = _utils.indexOf(logger.methodMap, level.toLowerCase());
	      if (levelMap >= 0) {
	        level = levelMap;
	      } else {
	        level = parseInt(level, 10);
	      }
	    }

	    return level;
	  },

	  // Can be overridden in the host environment
	  log: function log(level) {
	    level = logger.lookupLevel(level);

	    if (typeof console !== 'undefined' && logger.lookupLevel(logger.level) <= level) {
	      var method = logger.methodMap[level];
	      if (!console[method]) {
	        // eslint-disable-line no-console
	        method = 'log';
	      }

	      for (var _len = arguments.length, message = Array(_len > 1 ? _len - 1 : 0), _key = 1; _key < _len; _key++) {
	        message[_key - 1] = arguments[_key];
	      }

	      console[method].apply(console, message); // eslint-disable-line no-console
	    }
	  }
	};

	exports['default'] = logger;
	module.exports = exports['default'];

/***/ },
/* 18 */
/***/ function(module, exports) {

	// Build out our basic SafeString type
	'use strict';

	exports.__esModule = true;
	function SafeString(string) {
	  this.string = string;
	}

	SafeString.prototype.toString = SafeString.prototype.toHTML = function () {
	  return '' + this.string;
	};

	exports['default'] = SafeString;
	module.exports = exports['default'];

/***/ },
/* 19 */
/***/ function(module, exports, __webpack_require__) {

	'use strict';

	var _interopRequireWildcard = __webpack_require__(3)['default'];

	var _interopRequireDefault = __webpack_require__(1)['default'];

	exports.__esModule = true;
	exports.checkRevision = checkRevision;
	exports.template = template;
	exports.wrapProgram = wrapProgram;
	exports.resolvePartial = resolvePartial;
	exports.invokePartial = invokePartial;
	exports.noop = noop;

	var _utils = __webpack_require__(5);

	var Utils = _interopRequireWildcard(_utils);

	var _exception = __webpack_require__(6);

	var _exception2 = _interopRequireDefault(_exception);

	var _base = __webpack_require__(4);

	function checkRevision(compilerInfo) {
	  var compilerRevision = compilerInfo && compilerInfo[0] || 1,
	      currentRevision = _base.COMPILER_REVISION;

	  if (compilerRevision !== currentRevision) {
	    if (compilerRevision < currentRevision) {
	      var runtimeVersions = _base.REVISION_CHANGES[currentRevision],
	          compilerVersions = _base.REVISION_CHANGES[compilerRevision];
	      throw new _exception2['default']('Template was precompiled with an older version of Handlebars than the current runtime. ' + 'Please update your precompiler to a newer version (' + runtimeVersions + ') or downgrade your runtime to an older version (' + compilerVersions + ').');
	    } else {
	      // Use the embedded version info since the runtime doesn't know about this revision yet
	      throw new _exception2['default']('Template was precompiled with a newer version of Handlebars than the current runtime. ' + 'Please update your runtime to a newer version (' + compilerInfo[1] + ').');
	    }
	  }
	}

	function template(templateSpec, env) {
	  /* istanbul ignore next */
	  if (!env) {
	    throw new _exception2['default']('No environment passed to template');
	  }
	  if (!templateSpec || !templateSpec.main) {
	    throw new _exception2['default']('Unknown template object: ' + typeof templateSpec);
	  }

	  templateSpec.main.decorator = templateSpec.main_d;

	  // Note: Using env.VM references rather than local var references throughout this section to allow
	  // for external users to override these as psuedo-supported APIs.
	  env.VM.checkRevision(templateSpec.compiler);

	  function invokePartialWrapper(partial, context, options) {
	    if (options.hash) {
	      context = Utils.extend({}, context, options.hash);
	      if (options.ids) {
	        options.ids[0] = true;
	      }
	    }

	    partial = env.VM.resolvePartial.call(this, partial, context, options);
	    var result = env.VM.invokePartial.call(this, partial, context, options);

	    if (result == null && env.compile) {
	      options.partials[options.name] = env.compile(partial, templateSpec.compilerOptions, env);
	      result = options.partials[options.name](context, options);
	    }
	    if (result != null) {
	      if (options.indent) {
	        var lines = result.split('\n');
	        for (var i = 0, l = lines.length; i < l; i++) {
	          if (!lines[i] && i + 1 === l) {
	            break;
	          }

	          lines[i] = options.indent + lines[i];
	        }
	        result = lines.join('\n');
	      }
	      return result;
	    } else {
	      throw new _exception2['default']('The partial ' + options.name + ' could not be compiled when running in runtime-only mode');
	    }
	  }

	  // Just add water
	  var container = {
	    strict: function strict(obj, name) {
	      if (!(name in obj)) {
	        throw new _exception2['default']('"' + name + '" not defined in ' + obj);
	      }
	      return obj[name];
	    },
	    lookup: function lookup(depths, name) {
	      var len = depths.length;
	      for (var i = 0; i < len; i++) {
	        if (depths[i] && depths[i][name] != null) {
	          return depths[i][name];
	        }
	      }
	    },
	    lambda: function lambda(current, context) {
	      return typeof current === 'function' ? current.call(context) : current;
	    },

	    escapeExpression: Utils.escapeExpression,
	    invokePartial: invokePartialWrapper,

	    fn: function fn(i) {
	      var ret = templateSpec[i];
	      ret.decorator = templateSpec[i + '_d'];
	      return ret;
	    },

	    programs: [],
	    program: function program(i, data, declaredBlockParams, blockParams, depths) {
	      var programWrapper = this.programs[i],
	          fn = this.fn(i);
	      if (data || depths || blockParams || declaredBlockParams) {
	        programWrapper = wrapProgram(this, i, fn, data, declaredBlockParams, blockParams, depths);
	      } else if (!programWrapper) {
	        programWrapper = this.programs[i] = wrapProgram(this, i, fn);
	      }
	      return programWrapper;
	    },

	    data: function data(value, depth) {
	      while (value && depth--) {
	        value = value._parent;
	      }
	      return value;
	    },
	    merge: function merge(param, common) {
	      var obj = param || common;

	      if (param && common && param !== common) {
	        obj = Utils.extend({}, common, param);
	      }

	      return obj;
	    },

	    noop: env.VM.noop,
	    compilerInfo: templateSpec.compiler
	  };

	  function ret(context) {
	    var options = arguments.length <= 1 || arguments[1] === undefined ? {} : arguments[1];

	    var data = options.data;

	    ret._setup(options);
	    if (!options.partial && templateSpec.useData) {
	      data = initData(context, data);
	    }
	    var depths = undefined,
	        blockParams = templateSpec.useBlockParams ? [] : undefined;
	    if (templateSpec.useDepths) {
	      if (options.depths) {
	        depths = context !== options.depths[0] ? [context].concat(options.depths) : options.depths;
	      } else {
	        depths = [context];
	      }
	    }

	    function main(context /*, options*/) {
	      return '' + templateSpec.main(container, context, container.helpers, container.partials, data, blockParams, depths);
	    }
	    main = executeDecorators(templateSpec.main, main, container, options.depths || [], data, blockParams);
	    return main(context, options);
	  }
	  ret.isTop = true;

	  ret._setup = function (options) {
	    if (!options.partial) {
	      container.helpers = container.merge(options.helpers, env.helpers);

	      if (templateSpec.usePartial) {
	        container.partials = container.merge(options.partials, env.partials);
	      }
	      if (templateSpec.usePartial || templateSpec.useDecorators) {
	        container.decorators = container.merge(options.decorators, env.decorators);
	      }
	    } else {
	      container.helpers = options.helpers;
	      container.partials = options.partials;
	      container.decorators = options.decorators;
	    }
	  };

	  ret._child = function (i, data, blockParams, depths) {
	    if (templateSpec.useBlockParams && !blockParams) {
	      throw new _exception2['default']('must pass block params');
	    }
	    if (templateSpec.useDepths && !depths) {
	      throw new _exception2['default']('must pass parent depths');
	    }

	    return wrapProgram(container, i, templateSpec[i], data, 0, blockParams, depths);
	  };
	  return ret;
	}

	function wrapProgram(container, i, fn, data, declaredBlockParams, blockParams, depths) {
	  function prog(context) {
	    var options = arguments.length <= 1 || arguments[1] === undefined ? {} : arguments[1];

	    var currentDepths = depths;
	    if (depths && context !== depths[0]) {
	      currentDepths = [context].concat(depths);
	    }

	    return fn(container, context, container.helpers, container.partials, options.data || data, blockParams && [options.blockParams].concat(blockParams), currentDepths);
	  }

	  prog = executeDecorators(fn, prog, container, depths, data, blockParams);

	  prog.program = i;
	  prog.depth = depths ? depths.length : 0;
	  prog.blockParams = declaredBlockParams || 0;
	  return prog;
	}

	function resolvePartial(partial, context, options) {
	  if (!partial) {
	    if (options.name === '@partial-block') {
	      partial = options.data['partial-block'];
	    } else {
	      partial = options.partials[options.name];
	    }
	  } else if (!partial.call && !options.name) {
	    // This is a dynamic partial that returned a string
	    options.name = partial;
	    partial = options.partials[partial];
	  }
	  return partial;
	}

	function invokePartial(partial, context, options) {
	  options.partial = true;
	  if (options.ids) {
	    options.data.contextPath = options.ids[0] || options.data.contextPath;
	  }

	  var partialBlock = undefined;
	  if (options.fn && options.fn !== noop) {
	    options.data = _base.createFrame(options.data);
	    partialBlock = options.data['partial-block'] = options.fn;

	    if (partialBlock.partials) {
	      options.partials = Utils.extend({}, options.partials, partialBlock.partials);
	    }
	  }

	  if (partial === undefined && partialBlock) {
	    partial = partialBlock;
	  }

	  if (partial === undefined) {
	    throw new _exception2['default']('The partial ' + options.name + ' could not be found');
	  } else if (partial instanceof Function) {
	    return partial(context, options);
	  }
	}

	function noop() {
	  return '';
	}

	function initData(context, data) {
	  if (!data || !('root' in data)) {
	    data = data ? _base.createFrame(data) : {};
	    data.root = context;
	  }
	  return data;
	}

	function executeDecorators(fn, prog, container, depths, data, blockParams) {
	  if (fn.decorator) {
	    var props = {};
	    prog = fn.decorator(prog, props, container, depths && depths[0], data, blockParams, depths);
	    Utils.extend(prog, props);
	  }
	  return prog;
	}

/***/ },
/* 20 */
/***/ function(module, exports) {

	/* WEBPACK VAR INJECTION */(function(global) {/* global window */
	'use strict';

	exports.__esModule = true;

	exports['default'] = function (Handlebars) {
	  /* istanbul ignore next */
	  var root = typeof global !== 'undefined' ? global : window,
	      $Handlebars = root.Handlebars;
	  /* istanbul ignore next */
	  Handlebars.noConflict = function () {
	    if (root.Handlebars === Handlebars) {
	      root.Handlebars = $Handlebars;
	    }
	    return Handlebars;
	  };
	};

	module.exports = exports['default'];
	/* WEBPACK VAR INJECTION */}.call(exports, (function() { return this; }())))

/***/ },
/* 21 */
/***/ function(module, exports) {

	'use strict';

	exports.__esModule = true;
	var AST = {
	  // Public API used to evaluate derived attributes regarding AST nodes
	  helpers: {
	    // a mustache is definitely a helper if:
	    // * it is an eligible helper, and
	    // * it has at least one parameter or hash segment
	    helperExpression: function helperExpression(node) {
	      return node.type === 'SubExpression' || (node.type === 'MustacheStatement' || node.type === 'BlockStatement') && !!(node.params && node.params.length || node.hash);
	    },

	    scopedId: function scopedId(path) {
	      return (/^\.|this\b/.test(path.original)
	      );
	    },

	    // an ID is simple if it only has one part, and that part is not
	    // `..` or `this`.
	    simpleId: function simpleId(path) {
	      return path.parts.length === 1 && !AST.helpers.scopedId(path) && !path.depth;
	    }
	  }
	};

	// Must be exported as an object rather than the root of the module as the jison lexer
	// must modify the object to operate properly.
	exports['default'] = AST;
	module.exports = exports['default'];

/***/ },
/* 22 */
/***/ function(module, exports, __webpack_require__) {

	'use strict';

	var _interopRequireDefault = __webpack_require__(1)['default'];

	var _interopRequireWildcard = __webpack_require__(3)['default'];

	exports.__esModule = true;
	exports.parse = parse;

	var _parser = __webpack_require__(23);

	var _parser2 = _interopRequireDefault(_parser);

	var _whitespaceControl = __webpack_require__(24);

	var _whitespaceControl2 = _interopRequireDefault(_whitespaceControl);

	var _helpers = __webpack_require__(26);

	var Helpers = _interopRequireWildcard(_helpers);

	var _utils = __webpack_require__(5);

	exports.parser = _parser2['default'];

	var yy = {};
	_utils.extend(yy, Helpers);

	function parse(input, options) {
	  // Just return if an already-compiled AST was passed in.
	  if (input.type === 'Program') {
	    return input;
	  }

	  _parser2['default'].yy = yy;

	  // Altering the shared object here, but this is ok as parser is a sync operation
	  yy.locInfo = function (locInfo) {
	    return new yy.SourceLocation(options && options.srcName, locInfo);
	  };

	  var strip = new _whitespaceControl2['default'](options);
	  return strip.accept(_parser2['default'].parse(input));
	}

/***/ },
/* 23 */
/***/ function(module, exports) {

	/* istanbul ignore next */
	/* Jison generated parser */
	"use strict";

	var handlebars = (function () {
	    var parser = { trace: function trace() {},
	        yy: {},
	        symbols_: { "error": 2, "root": 3, "program": 4, "EOF": 5, "program_repetition0": 6, "statement": 7, "mustache": 8, "block": 9, "rawBlock": 10, "partial": 11, "partialBlock": 12, "content": 13, "COMMENT": 14, "CONTENT": 15, "openRawBlock": 16, "rawBlock_repetition_plus0": 17, "END_RAW_BLOCK": 18, "OPEN_RAW_BLOCK": 19, "helperName": 20, "openRawBlock_repetition0": 21, "openRawBlock_option0": 22, "CLOSE_RAW_BLOCK": 23, "openBlock": 24, "block_option0": 25, "closeBlock": 26, "openInverse": 27, "block_option1": 28, "OPEN_BLOCK": 29, "openBlock_repetition0": 30, "openBlock_option0": 31, "openBlock_option1": 32, "CLOSE": 33, "OPEN_INVERSE": 34, "openInverse_repetition0": 35, "openInverse_option0": 36, "openInverse_option1": 37, "openInverseChain": 38, "OPEN_INVERSE_CHAIN": 39, "openInverseChain_repetition0": 40, "openInverseChain_option0": 41, "openInverseChain_option1": 42, "inverseAndProgram": 43, "INVERSE": 44, "inverseChain": 45, "inverseChain_option0": 46, "OPEN_ENDBLOCK": 47, "OPEN": 48, "mustache_repetition0": 49, "mustache_option0": 50, "OPEN_UNESCAPED": 51, "mustache_repetition1": 52, "mustache_option1": 53, "CLOSE_UNESCAPED": 54, "OPEN_PARTIAL": 55, "partialName": 56, "partial_repetition0": 57, "partial_option0": 58, "openPartialBlock": 59, "OPEN_PARTIAL_BLOCK": 60, "openPartialBlock_repetition0": 61, "openPartialBlock_option0": 62, "param": 63, "sexpr": 64, "OPEN_SEXPR": 65, "sexpr_repetition0": 66, "sexpr_option0": 67, "CLOSE_SEXPR": 68, "hash": 69, "hash_repetition_plus0": 70, "hashSegment": 71, "ID": 72, "EQUALS": 73, "blockParams": 74, "OPEN_BLOCK_PARAMS": 75, "blockParams_repetition_plus0": 76, "CLOSE_BLOCK_PARAMS": 77, "path": 78, "dataName": 79, "STRING": 80, "NUMBER": 81, "BOOLEAN": 82, "UNDEFINED": 83, "NULL": 84, "DATA": 85, "pathSegments": 86, "SEP": 87, "$accept": 0, "$end": 1 },
	        terminals_: { 2: "error", 5: "EOF", 14: "COMMENT", 15: "CONTENT", 18: "END_RAW_BLOCK", 19: "OPEN_RAW_BLOCK", 23: "CLOSE_RAW_BLOCK", 29: "OPEN_BLOCK", 33: "CLOSE", 34: "OPEN_INVERSE", 39: "OPEN_INVERSE_CHAIN", 44: "INVERSE", 47: "OPEN_ENDBLOCK", 48: "OPEN", 51: "OPEN_UNESCAPED", 54: "CLOSE_UNESCAPED", 55: "OPEN_PARTIAL", 60: "OPEN_PARTIAL_BLOCK", 65: "OPEN_SEXPR", 68: "CLOSE_SEXPR", 72: "ID", 73: "EQUALS", 75: "OPEN_BLOCK_PARAMS", 77: "CLOSE_BLOCK_PARAMS", 80: "STRING", 81: "NUMBER", 82: "BOOLEAN", 83: "UNDEFINED", 84: "NULL", 85: "DATA", 87: "SEP" },
	        productions_: [0, [3, 2], [4, 1], [7, 1], [7, 1], [7, 1], [7, 1], [7, 1], [7, 1], [7, 1], [13, 1], [10, 3], [16, 5], [9, 4], [9, 4], [24, 6], [27, 6], [38, 6], [43, 2], [45, 3], [45, 1], [26, 3], [8, 5], [8, 5], [11, 5], [12, 3], [59, 5], [63, 1], [63, 1], [64, 5], [69, 1], [71, 3], [74, 3], [20, 1], [20, 1], [20, 1], [20, 1], [20, 1], [20, 1], [20, 1], [56, 1], [56, 1], [79, 2], [78, 1], [86, 3], [86, 1], [6, 0], [6, 2], [17, 1], [17, 2], [21, 0], [21, 2], [22, 0], [22, 1], [25, 0], [25, 1], [28, 0], [28, 1], [30, 0], [30, 2], [31, 0], [31, 1], [32, 0], [32, 1], [35, 0], [35, 2], [36, 0], [36, 1], [37, 0], [37, 1], [40, 0], [40, 2], [41, 0], [41, 1], [42, 0], [42, 1], [46, 0], [46, 1], [49, 0], [49, 2], [50, 0], [50, 1], [52, 0], [52, 2], [53, 0], [53, 1], [57, 0], [57, 2], [58, 0], [58, 1], [61, 0], [61, 2], [62, 0], [62, 1], [66, 0], [66, 2], [67, 0], [67, 1], [70, 1], [70, 2], [76, 1], [76, 2]],
	        performAction: function anonymous(yytext, yyleng, yylineno, yy, yystate, $$, _$
	        /**/) {

	            var $0 = $$.length - 1;
	            switch (yystate) {
	                case 1:
	                    return $$[$0 - 1];
	                    break;
	                case 2:
	                    this.$ = yy.prepareProgram($$[$0]);
	                    break;
	                case 3:
	                    this.$ = $$[$0];
	                    break;
	                case 4:
	                    this.$ = $$[$0];
	                    break;
	                case 5:
	                    this.$ = $$[$0];
	                    break;
	                case 6:
	                    this.$ = $$[$0];
	                    break;
	                case 7:
	                    this.$ = $$[$0];
	                    break;
	                case 8:
	                    this.$ = $$[$0];
	                    break;
	                case 9:
	                    this.$ = {
	                        type: 'CommentStatement',
	                        value: yy.stripComment($$[$0]),
	                        strip: yy.stripFlags($$[$0], $$[$0]),
	                        loc: yy.locInfo(this._$)
	                    };

	                    break;
	                case 10:
	                    this.$ = {
	                        type: 'ContentStatement',
	                        original: $$[$0],
	                        value: $$[$0],
	                        loc: yy.locInfo(this._$)
	                    };

	                    break;
	                case 11:
	                    this.$ = yy.prepareRawBlock($$[$0 - 2], $$[$0 - 1], $$[$0], this._$);
	                    break;
	                case 12:
	                    this.$ = { path: $$[$0 - 3], params: $$[$0 - 2], hash: $$[$0 - 1] };
	                    break;
	                case 13:
	                    this.$ = yy.prepareBlock($$[$0 - 3], $$[$0 - 2], $$[$0 - 1], $$[$0], false, this._$);
	                    break;
	                case 14:
	                    this.$ = yy.prepareBlock($$[$0 - 3], $$[$0 - 2], $$[$0 - 1], $$[$0], true, this._$);
	                    break;
	                case 15:
	                    this.$ = { open: $$[$0 - 5], path: $$[$0 - 4], params: $$[$0 - 3], hash: $$[$0 - 2], blockParams: $$[$0 - 1], strip: yy.stripFlags($$[$0 - 5], $$[$0]) };
	                    break;
	                case 16:
	                    this.$ = { path: $$[$0 - 4], params: $$[$0 - 3], hash: $$[$0 - 2], blockParams: $$[$0 - 1], strip: yy.stripFlags($$[$0 - 5], $$[$0]) };
	                    break;
	                case 17:
	                    this.$ = { path: $$[$0 - 4], params: $$[$0 - 3], hash: $$[$0 - 2], blockParams: $$[$0 - 1], strip: yy.stripFlags($$[$0 - 5], $$[$0]) };
	                    break;
	                case 18:
	                    this.$ = { strip: yy.stripFlags($$[$0 - 1], $$[$0 - 1]), program: $$[$0] };
	                    break;
	                case 19:
	                    var inverse = yy.prepareBlock($$[$0 - 2], $$[$0 - 1], $$[$0], $$[$0], false, this._$),
	                        program = yy.prepareProgram([inverse], $$[$0 - 1].loc);
	                    program.chained = true;

	                    this.$ = { strip: $$[$0 - 2].strip, program: program, chain: true };

	                    break;
	                case 20:
	                    this.$ = $$[$0];
	                    break;
	                case 21:
	                    this.$ = { path: $$[$0 - 1], strip: yy.stripFlags($$[$0 - 2], $$[$0]) };
	                    break;
	                case 22:
	                    this.$ = yy.prepareMustache($$[$0 - 3], $$[$0 - 2], $$[$0 - 1], $$[$0 - 4], yy.stripFlags($$[$0 - 4], $$[$0]), this._$);
	                    break;
	                case 23:
	                    this.$ = yy.prepareMustache($$[$0 - 3], $$[$0 - 2], $$[$0 - 1], $$[$0 - 4], yy.stripFlags($$[$0 - 4], $$[$0]), this._$);
	                    break;
	                case 24:
	                    this.$ = {
	                        type: 'PartialStatement',
	                        name: $$[$0 - 3],
	                        params: $$[$0 - 2],
	                        hash: $$[$0 - 1],
	                        indent: '',
	                        strip: yy.stripFlags($$[$0 - 4], $$[$0]),
	                        loc: yy.locInfo(this._$)
	                    };

	                    break;
	                case 25:
	                    this.$ = yy.preparePartialBlock($$[$0 - 2], $$[$0 - 1], $$[$0], this._$);
	                    break;
	                case 26:
	                    this.$ = { path: $$[$0 - 3], params: $$[$0 - 2], hash: $$[$0 - 1], strip: yy.stripFlags($$[$0 - 4], $$[$0]) };
	                    break;
	                case 27:
	                    this.$ = $$[$0];
	                    break;
	                case 28:
	                    this.$ = $$[$0];
	                    break;
	                case 29:
	                    this.$ = {
	                        type: 'SubExpression',
	                        path: $$[$0 - 3],
	                        params: $$[$0 - 2],
	                        hash: $$[$0 - 1],
	                        loc: yy.locInfo(this._$)
	                    };

	                    break;
	                case 30:
	                    this.$ = { type: 'Hash', pairs: $$[$0], loc: yy.locInfo(this._$) };
	                    break;
	                case 31:
	                    this.$ = { type: 'HashPair', key: yy.id($$[$0 - 2]), value: $$[$0], loc: yy.locInfo(this._$) };
	                    break;
	                case 32:
	                    this.$ = yy.id($$[$0 - 1]);
	                    break;
	                case 33:
	                    this.$ = $$[$0];
	                    break;
	                case 34:
	                    this.$ = $$[$0];
	                    break;
	                case 35:
	                    this.$ = { type: 'StringLiteral', value: $$[$0], original: $$[$0], loc: yy.locInfo(this._$) };
	                    break;
	                case 36:
	                    this.$ = { type: 'NumberLiteral', value: Number($$[$0]), original: Number($$[$0]), loc: yy.locInfo(this._$) };
	                    break;
	                case 37:
	                    this.$ = { type: 'BooleanLiteral', value: $$[$0] === 'true', original: $$[$0] === 'true', loc: yy.locInfo(this._$) };
	                    break;
	                case 38:
	                    this.$ = { type: 'UndefinedLiteral', original: undefined, value: undefined, loc: yy.locInfo(this._$) };
	                    break;
	                case 39:
	                    this.$ = { type: 'NullLiteral', original: null, value: null, loc: yy.locInfo(this._$) };
	                    break;
	                case 40:
	                    this.$ = $$[$0];
	                    break;
	                case 41:
	                    this.$ = $$[$0];
	                    break;
	                case 42:
	                    this.$ = yy.preparePath(true, $$[$0], this._$);
	                    break;
	                case 43:
	                    this.$ = yy.preparePath(false, $$[$0], this._$);
	                    break;
	                case 44:
	                    $$[$0 - 2].push({ part: yy.id($$[$0]), original: $$[$0], separator: $$[$0 - 1] });this.$ = $$[$0 - 2];
	                    break;
	                case 45:
	                    this.$ = [{ part: yy.id($$[$0]), original: $$[$0] }];
	                    break;
	                case 46:
	                    this.$ = [];
	                    break;
	                case 47:
	                    $$[$0 - 1].push($$[$0]);
	                    break;
	                case 48:
	                    this.$ = [$$[$0]];
	                    break;
	                case 49:
	                    $$[$0 - 1].push($$[$0]);
	                    break;
	                case 50:
	                    this.$ = [];
	                    break;
	                case 51:
	                    $$[$0 - 1].push($$[$0]);
	                    break;
	                case 58:
	                    this.$ = [];
	                    break;
	                case 59:
	                    $$[$0 - 1].push($$[$0]);
	                    break;
	                case 64:
	                    this.$ = [];
	                    break;
	                case 65:
	                    $$[$0 - 1].push($$[$0]);
	                    break;
	                case 70:
	                    this.$ = [];
	                    break;
	                case 71:
	                    $$[$0 - 1].push($$[$0]);
	                    break;
	                case 78:
	                    this.$ = [];
	                    break;
	                case 79:
	                    $$[$0 - 1].push($$[$0]);
	                    break;
	                case 82:
	                    this.$ = [];
	                    break;
	                case 83:
	                    $$[$0 - 1].push($$[$0]);
	                    break;
	                case 86:
	                    this.$ = [];
	                    break;
	                case 87:
	                    $$[$0 - 1].push($$[$0]);
	                    break;
	                case 90:
	                    this.$ = [];
	                    break;
	                case 91:
	                    $$[$0 - 1].push($$[$0]);
	                    break;
	                case 94:
	                    this.$ = [];
	                    break;
	                case 95:
	                    $$[$0 - 1].push($$[$0]);
	                    break;
	                case 98:
	                    this.$ = [$$[$0]];
	                    break;
	                case 99:
	                    $$[$0 - 1].push($$[$0]);
	                    break;
	                case 100:
	                    this.$ = [$$[$0]];
	                    break;
	                case 101:
	                    $$[$0 - 1].push($$[$0]);
	                    break;
	            }
	        },
	        table: [{ 3: 1, 4: 2, 5: [2, 46], 6: 3, 14: [2, 46], 15: [2, 46], 19: [2, 46], 29: [2, 46], 34: [2, 46], 48: [2, 46], 51: [2, 46], 55: [2, 46], 60: [2, 46] }, { 1: [3] }, { 5: [1, 4] }, { 5: [2, 2], 7: 5, 8: 6, 9: 7, 10: 8, 11: 9, 12: 10, 13: 11, 14: [1, 12], 15: [1, 20], 16: 17, 19: [1, 23], 24: 15, 27: 16, 29: [1, 21], 34: [1, 22], 39: [2, 2], 44: [2, 2], 47: [2, 2], 48: [1, 13], 51: [1, 14], 55: [1, 18], 59: 19, 60: [1, 24] }, { 1: [2, 1] }, { 5: [2, 47], 14: [2, 47], 15: [2, 47], 19: [2, 47], 29: [2, 47], 34: [2, 47], 39: [2, 47], 44: [2, 47], 47: [2, 47], 48: [2, 47], 51: [2, 47], 55: [2, 47], 60: [2, 47] }, { 5: [2, 3], 14: [2, 3], 15: [2, 3], 19: [2, 3], 29: [2, 3], 34: [2, 3], 39: [2, 3], 44: [2, 3], 47: [2, 3], 48: [2, 3], 51: [2, 3], 55: [2, 3], 60: [2, 3] }, { 5: [2, 4], 14: [2, 4], 15: [2, 4], 19: [2, 4], 29: [2, 4], 34: [2, 4], 39: [2, 4], 44: [2, 4], 47: [2, 4], 48: [2, 4], 51: [2, 4], 55: [2, 4], 60: [2, 4] }, { 5: [2, 5], 14: [2, 5], 15: [2, 5], 19: [2, 5], 29: [2, 5], 34: [2, 5], 39: [2, 5], 44: [2, 5], 47: [2, 5], 48: [2, 5], 51: [2, 5], 55: [2, 5], 60: [2, 5] }, { 5: [2, 6], 14: [2, 6], 15: [2, 6], 19: [2, 6], 29: [2, 6], 34: [2, 6], 39: [2, 6], 44: [2, 6], 47: [2, 6], 48: [2, 6], 51: [2, 6], 55: [2, 6], 60: [2, 6] }, { 5: [2, 7], 14: [2, 7], 15: [2, 7], 19: [2, 7], 29: [2, 7], 34: [2, 7], 39: [2, 7], 44: [2, 7], 47: [2, 7], 48: [2, 7], 51: [2, 7], 55: [2, 7], 60: [2, 7] }, { 5: [2, 8], 14: [2, 8], 15: [2, 8], 19: [2, 8], 29: [2, 8], 34: [2, 8], 39: [2, 8], 44: [2, 8], 47: [2, 8], 48: [2, 8], 51: [2, 8], 55: [2, 8], 60: [2, 8] }, { 5: [2, 9], 14: [2, 9], 15: [2, 9], 19: [2, 9], 29: [2, 9], 34: [2, 9], 39: [2, 9], 44: [2, 9], 47: [2, 9], 48: [2, 9], 51: [2, 9], 55: [2, 9], 60: [2, 9] }, { 20: 25, 72: [1, 35], 78: 26, 79: 27, 80: [1, 28], 81: [1, 29], 82: [1, 30], 83: [1, 31], 84: [1, 32], 85: [1, 34], 86: 33 }, { 20: 36, 72: [1, 35], 78: 26, 79: 27, 80: [1, 28], 81: [1, 29], 82: [1, 30], 83: [1, 31], 84: [1, 32], 85: [1, 34], 86: 33 }, { 4: 37, 6: 3, 14: [2, 46], 15: [2, 46], 19: [2, 46], 29: [2, 46], 34: [2, 46], 39: [2, 46], 44: [2, 46], 47: [2, 46], 48: [2, 46], 51: [2, 46], 55: [2, 46], 60: [2, 46] }, { 4: 38, 6: 3, 14: [2, 46], 15: [2, 46], 19: [2, 46], 29: [2, 46], 34: [2, 46], 44: [2, 46], 47: [2, 46], 48: [2, 46], 51: [2, 46], 55: [2, 46], 60: [2, 46] }, { 13: 40, 15: [1, 20], 17: 39 }, { 20: 42, 56: 41, 64: 43, 65: [1, 44], 72: [1, 35], 78: 26, 79: 27, 80: [1, 28], 81: [1, 29], 82: [1, 30], 83: [1, 31], 84: [1, 32], 85: [1, 34], 86: 33 }, { 4: 45, 6: 3, 14: [2, 46], 15: [2, 46], 19: [2, 46], 29: [2, 46], 34: [2, 46], 47: [2, 46], 48: [2, 46], 51: [2, 46], 55: [2, 46], 60: [2, 46] }, { 5: [2, 10], 14: [2, 10], 15: [2, 10], 18: [2, 10], 19: [2, 10], 29: [2, 10], 34: [2, 10], 39: [2, 10], 44: [2, 10], 47: [2, 10], 48: [2, 10], 51: [2, 10], 55: [2, 10], 60: [2, 10] }, { 20: 46, 72: [1, 35], 78: 26, 79: 27, 80: [1, 28], 81: [1, 29], 82: [1, 30], 83: [1, 31], 84: [1, 32], 85: [1, 34], 86: 33 }, { 20: 47, 72: [1, 35], 78: 26, 79: 27, 80: [1, 28], 81: [1, 29], 82: [1, 30], 83: [1, 31], 84: [1, 32], 85: [1, 34], 86: 33 }, { 20: 48, 72: [1, 35], 78: 26, 79: 27, 80: [1, 28], 81: [1, 29], 82: [1, 30], 83: [1, 31], 84: [1, 32], 85: [1, 34], 86: 33 }, { 20: 42, 56: 49, 64: 43, 65: [1, 44], 72: [1, 35], 78: 26, 79: 27, 80: [1, 28], 81: [1, 29], 82: [1, 30], 83: [1, 31], 84: [1, 32], 85: [1, 34], 86: 33 }, { 33: [2, 78], 49: 50, 65: [2, 78], 72: [2, 78], 80: [2, 78], 81: [2, 78], 82: [2, 78], 83: [2, 78], 84: [2, 78], 85: [2, 78] }, { 23: [2, 33], 33: [2, 33], 54: [2, 33], 65: [2, 33], 68: [2, 33], 72: [2, 33], 75: [2, 33], 80: [2, 33], 81: [2, 33], 82: [2, 33], 83: [2, 33], 84: [2, 33], 85: [2, 33] }, { 23: [2, 34], 33: [2, 34], 54: [2, 34], 65: [2, 34], 68: [2, 34], 72: [2, 34], 75: [2, 34], 80: [2, 34], 81: [2, 34], 82: [2, 34], 83: [2, 34], 84: [2, 34], 85: [2, 34] }, { 23: [2, 35], 33: [2, 35], 54: [2, 35], 65: [2, 35], 68: [2, 35], 72: [2, 35], 75: [2, 35], 80: [2, 35], 81: [2, 35], 82: [2, 35], 83: [2, 35], 84: [2, 35], 85: [2, 35] }, { 23: [2, 36], 33: [2, 36], 54: [2, 36], 65: [2, 36], 68: [2, 36], 72: [2, 36], 75: [2, 36], 80: [2, 36], 81: [2, 36], 82: [2, 36], 83: [2, 36], 84: [2, 36], 85: [2, 36] }, { 23: [2, 37], 33: [2, 37], 54: [2, 37], 65: [2, 37], 68: [2, 37], 72: [2, 37], 75: [2, 37], 80: [2, 37], 81: [2, 37], 82: [2, 37], 83: [2, 37], 84: [2, 37], 85: [2, 37] }, { 23: [2, 38], 33: [2, 38], 54: [2, 38], 65: [2, 38], 68: [2, 38], 72: [2, 38], 75: [2, 38], 80: [2, 38], 81: [2, 38], 82: [2, 38], 83: [2, 38], 84: [2, 38], 85: [2, 38] }, { 23: [2, 39], 33: [2, 39], 54: [2, 39], 65: [2, 39], 68: [2, 39], 72: [2, 39], 75: [2, 39], 80: [2, 39], 81: [2, 39], 82: [2, 39], 83: [2, 39], 84: [2, 39], 85: [2, 39] }, { 23: [2, 43], 33: [2, 43], 54: [2, 43], 65: [2, 43], 68: [2, 43], 72: [2, 43], 75: [2, 43], 80: [2, 43], 81: [2, 43], 82: [2, 43], 83: [2, 43], 84: [2, 43], 85: [2, 43], 87: [1, 51] }, { 72: [1, 35], 86: 52 }, { 23: [2, 45], 33: [2, 45], 54: [2, 45], 65: [2, 45], 68: [2, 45], 72: [2, 45], 75: [2, 45], 80: [2, 45], 81: [2, 45], 82: [2, 45], 83: [2, 45], 84: [2, 45], 85: [2, 45], 87: [2, 45] }, { 52: 53, 54: [2, 82], 65: [2, 82], 72: [2, 82], 80: [2, 82], 81: [2, 82], 82: [2, 82], 83: [2, 82], 84: [2, 82], 85: [2, 82] }, { 25: 54, 38: 56, 39: [1, 58], 43: 57, 44: [1, 59], 45: 55, 47: [2, 54] }, { 28: 60, 43: 61, 44: [1, 59], 47: [2, 56] }, { 13: 63, 15: [1, 20], 18: [1, 62] }, { 15: [2, 48], 18: [2, 48] }, { 33: [2, 86], 57: 64, 65: [2, 86], 72: [2, 86], 80: [2, 86], 81: [2, 86], 82: [2, 86], 83: [2, 86], 84: [2, 86], 85: [2, 86] }, { 33: [2, 40], 65: [2, 40], 72: [2, 40], 80: [2, 40], 81: [2, 40], 82: [2, 40], 83: [2, 40], 84: [2, 40], 85: [2, 40] }, { 33: [2, 41], 65: [2, 41], 72: [2, 41], 80: [2, 41], 81: [2, 41], 82: [2, 41], 83: [2, 41], 84: [2, 41], 85: [2, 41] }, { 20: 65, 72: [1, 35], 78: 26, 79: 27, 80: [1, 28], 81: [1, 29], 82: [1, 30], 83: [1, 31], 84: [1, 32], 85: [1, 34], 86: 33 }, { 26: 66, 47: [1, 67] }, { 30: 68, 33: [2, 58], 65: [2, 58], 72: [2, 58], 75: [2, 58], 80: [2, 58], 81: [2, 58], 82: [2, 58], 83: [2, 58], 84: [2, 58], 85: [2, 58] }, { 33: [2, 64], 35: 69, 65: [2, 64], 72: [2, 64], 75: [2, 64], 80: [2, 64], 81: [2, 64], 82: [2, 64], 83: [2, 64], 84: [2, 64], 85: [2, 64] }, { 21: 70, 23: [2, 50], 65: [2, 50], 72: [2, 50], 80: [2, 50], 81: [2, 50], 82: [2, 50], 83: [2, 50], 84: [2, 50], 85: [2, 50] }, { 33: [2, 90], 61: 71, 65: [2, 90], 72: [2, 90], 80: [2, 90], 81: [2, 90], 82: [2, 90], 83: [2, 90], 84: [2, 90], 85: [2, 90] }, { 20: 75, 33: [2, 80], 50: 72, 63: 73, 64: 76, 65: [1, 44], 69: 74, 70: 77, 71: 78, 72: [1, 79], 78: 26, 79: 27, 80: [1, 28], 81: [1, 29], 82: [1, 30], 83: [1, 31], 84: [1, 32], 85: [1, 34], 86: 33 }, { 72: [1, 80] }, { 23: [2, 42], 33: [2, 42], 54: [2, 42], 65: [2, 42], 68: [2, 42], 72: [2, 42], 75: [2, 42], 80: [2, 42], 81: [2, 42], 82: [2, 42], 83: [2, 42], 84: [2, 42], 85: [2, 42], 87: [1, 51] }, { 20: 75, 53: 81, 54: [2, 84], 63: 82, 64: 76, 65: [1, 44], 69: 83, 70: 77, 71: 78, 72: [1, 79], 78: 26, 79: 27, 80: [1, 28], 81: [1, 29], 82: [1, 30], 83: [1, 31], 84: [1, 32], 85: [1, 34], 86: 33 }, { 26: 84, 47: [1, 67] }, { 47: [2, 55] }, { 4: 85, 6: 3, 14: [2, 46], 15: [2, 46], 19: [2, 46], 29: [2, 46], 34: [2, 46], 39: [2, 46], 44: [2, 46], 47: [2, 46], 48: [2, 46], 51: [2, 46], 55: [2, 46], 60: [2, 46] }, { 47: [2, 20] }, { 20: 86, 72: [1, 35], 78: 26, 79: 27, 80: [1, 28], 81: [1, 29], 82: [1, 30], 83: [1, 31], 84: [1, 32], 85: [1, 34], 86: 33 }, { 4: 87, 6: 3, 14: [2, 46], 15: [2, 46], 19: [2, 46], 29: [2, 46], 34: [2, 46], 47: [2, 46], 48: [2, 46], 51: [2, 46], 55: [2, 46], 60: [2, 46] }, { 26: 88, 47: [1, 67] }, { 47: [2, 57] }, { 5: [2, 11], 14: [2, 11], 15: [2, 11], 19: [2, 11], 29: [2, 11], 34: [2, 11], 39: [2, 11], 44: [2, 11], 47: [2, 11], 48: [2, 11], 51: [2, 11], 55: [2, 11], 60: [2, 11] }, { 15: [2, 49], 18: [2, 49] }, { 20: 75, 33: [2, 88], 58: 89, 63: 90, 64: 76, 65: [1, 44], 69: 91, 70: 77, 71: 78, 72: [1, 79], 78: 26, 79: 27, 80: [1, 28], 81: [1, 29], 82: [1, 30], 83: [1, 31], 84: [1, 32], 85: [1, 34], 86: 33 }, { 65: [2, 94], 66: 92, 68: [2, 94], 72: [2, 94], 80: [2, 94], 81: [2, 94], 82: [2, 94], 83: [2, 94], 84: [2, 94], 85: [2, 94] }, { 5: [2, 25], 14: [2, 25], 15: [2, 25], 19: [2, 25], 29: [2, 25], 34: [2, 25], 39: [2, 25], 44: [2, 25], 47: [2, 25], 48: [2, 25], 51: [2, 25], 55: [2, 25], 60: [2, 25] }, { 20: 93, 72: [1, 35], 78: 26, 79: 27, 80: [1, 28], 81: [1, 29], 82: [1, 30], 83: [1, 31], 84: [1, 32], 85: [1, 34], 86: 33 }, { 20: 75, 31: 94, 33: [2, 60], 63: 95, 64: 76, 65: [1, 44], 69: 96, 70: 77, 71: 78, 72: [1, 79], 75: [2, 60], 78: 26, 79: 27, 80: [1, 28], 81: [1, 29], 82: [1, 30], 83: [1, 31], 84: [1, 32], 85: [1, 34], 86: 33 }, { 20: 75, 33: [2, 66], 36: 97, 63: 98, 64: 76, 65: [1, 44], 69: 99, 70: 77, 71: 78, 72: [1, 79], 75: [2, 66], 78: 26, 79: 27, 80: [1, 28], 81: [1, 29], 82: [1, 30], 83: [1, 31], 84: [1, 32], 85: [1, 34], 86: 33 }, { 20: 75, 22: 100, 23: [2, 52], 63: 101, 64: 76, 65: [1, 44], 69: 102, 70: 77, 71: 78, 72: [1, 79], 78: 26, 79: 27, 80: [1, 28], 81: [1, 29], 82: [1, 30], 83: [1, 31], 84: [1, 32], 85: [1, 34], 86: 33 }, { 20: 75, 33: [2, 92], 62: 103, 63: 104, 64: 76, 65: [1, 44], 69: 105, 70: 77, 71: 78, 72: [1, 79], 78: 26, 79: 27, 80: [1, 28], 81: [1, 29], 82: [1, 30], 83: [1, 31], 84: [1, 32], 85: [1, 34], 86: 33 }, { 33: [1, 106] }, { 33: [2, 79], 65: [2, 79], 72: [2, 79], 80: [2, 79], 81: [2, 79], 82: [2, 79], 83: [2, 79], 84: [2, 79], 85: [2, 79] }, { 33: [2, 81] }, { 23: [2, 27], 33: [2, 27], 54: [2, 27], 65: [2, 27], 68: [2, 27], 72: [2, 27], 75: [2, 27], 80: [2, 27], 81: [2, 27], 82: [2, 27], 83: [2, 27], 84: [2, 27], 85: [2, 27] }, { 23: [2, 28], 33: [2, 28], 54: [2, 28], 65: [2, 28], 68: [2, 28], 72: [2, 28], 75: [2, 28], 80: [2, 28], 81: [2, 28], 82: [2, 28], 83: [2, 28], 84: [2, 28], 85: [2, 28] }, { 23: [2, 30], 33: [2, 30], 54: [2, 30], 68: [2, 30], 71: 107, 72: [1, 108], 75: [2, 30] }, { 23: [2, 98], 33: [2, 98], 54: [2, 98], 68: [2, 98], 72: [2, 98], 75: [2, 98] }, { 23: [2, 45], 33: [2, 45], 54: [2, 45], 65: [2, 45], 68: [2, 45], 72: [2, 45], 73: [1, 109], 75: [2, 45], 80: [2, 45], 81: [2, 45], 82: [2, 45], 83: [2, 45], 84: [2, 45], 85: [2, 45], 87: [2, 45] }, { 23: [2, 44], 33: [2, 44], 54: [2, 44], 65: [2, 44], 68: [2, 44], 72: [2, 44], 75: [2, 44], 80: [2, 44], 81: [2, 44], 82: [2, 44], 83: [2, 44], 84: [2, 44], 85: [2, 44], 87: [2, 44] }, { 54: [1, 110] }, { 54: [2, 83], 65: [2, 83], 72: [2, 83], 80: [2, 83], 81: [2, 83], 82: [2, 83], 83: [2, 83], 84: [2, 83], 85: [2, 83] }, { 54: [2, 85] }, { 5: [2, 13], 14: [2, 13], 15: [2, 13], 19: [2, 13], 29: [2, 13], 34: [2, 13], 39: [2, 13], 44: [2, 13], 47: [2, 13], 48: [2, 13], 51: [2, 13], 55: [2, 13], 60: [2, 13] }, { 38: 56, 39: [1, 58], 43: 57, 44: [1, 59], 45: 112, 46: 111, 47: [2, 76] }, { 33: [2, 70], 40: 113, 65: [2, 70], 72: [2, 70], 75: [2, 70], 80: [2, 70], 81: [2, 70], 82: [2, 70], 83: [2, 70], 84: [2, 70], 85: [2, 70] }, { 47: [2, 18] }, { 5: [2, 14], 14: [2, 14], 15: [2, 14], 19: [2, 14], 29: [2, 14], 34: [2, 14], 39: [2, 14], 44: [2, 14], 47: [2, 14], 48: [2, 14], 51: [2, 14], 55: [2, 14], 60: [2, 14] }, { 33: [1, 114] }, { 33: [2, 87], 65: [2, 87], 72: [2, 87], 80: [2, 87], 81: [2, 87], 82: [2, 87], 83: [2, 87], 84: [2, 87], 85: [2, 87] }, { 33: [2, 89] }, { 20: 75, 63: 116, 64: 76, 65: [1, 44], 67: 115, 68: [2, 96], 69: 117, 70: 77, 71: 78, 72: [1, 79], 78: 26, 79: 27, 80: [1, 28], 81: [1, 29], 82: [1, 30], 83: [1, 31], 84: [1, 32], 85: [1, 34], 86: 33 }, { 33: [1, 118] }, { 32: 119, 33: [2, 62], 74: 120, 75: [1, 121] }, { 33: [2, 59], 65: [2, 59], 72: [2, 59], 75: [2, 59], 80: [2, 59], 81: [2, 59], 82: [2, 59], 83: [2, 59], 84: [2, 59], 85: [2, 59] }, { 33: [2, 61], 75: [2, 61] }, { 33: [2, 68], 37: 122, 74: 123, 75: [1, 121] }, { 33: [2, 65], 65: [2, 65], 72: [2, 65], 75: [2, 65], 80: [2, 65], 81: [2, 65], 82: [2, 65], 83: [2, 65], 84: [2, 65], 85: [2, 65] }, { 33: [2, 67], 75: [2, 67] }, { 23: [1, 124] }, { 23: [2, 51], 65: [2, 51], 72: [2, 51], 80: [2, 51], 81: [2, 51], 82: [2, 51], 83: [2, 51], 84: [2, 51], 85: [2, 51] }, { 23: [2, 53] }, { 33: [1, 125] }, { 33: [2, 91], 65: [2, 91], 72: [2, 91], 80: [2, 91], 81: [2, 91], 82: [2, 91], 83: [2, 91], 84: [2, 91], 85: [2, 91] }, { 33: [2, 93] }, { 5: [2, 22], 14: [2, 22], 15: [2, 22], 19: [2, 22], 29: [2, 22], 34: [2, 22], 39: [2, 22], 44: [2, 22], 47: [2, 22], 48: [2, 22], 51: [2, 22], 55: [2, 22], 60: [2, 22] }, { 23: [2, 99], 33: [2, 99], 54: [2, 99], 68: [2, 99], 72: [2, 99], 75: [2, 99] }, { 73: [1, 109] }, { 20: 75, 63: 126, 64: 76, 65: [1, 44], 72: [1, 35], 78: 26, 79: 27, 80: [1, 28], 81: [1, 29], 82: [1, 30], 83: [1, 31], 84: [1, 32], 85: [1, 34], 86: 33 }, { 5: [2, 23], 14: [2, 23], 15: [2, 23], 19: [2, 23], 29: [2, 23], 34: [2, 23], 39: [2, 23], 44: [2, 23], 47: [2, 23], 48: [2, 23], 51: [2, 23], 55: [2, 23], 60: [2, 23] }, { 47: [2, 19] }, { 47: [2, 77] }, { 20: 75, 33: [2, 72], 41: 127, 63: 128, 64: 76, 65: [1, 44], 69: 129, 70: 77, 71: 78, 72: [1, 79], 75: [2, 72], 78: 26, 79: 27, 80: [1, 28], 81: [1, 29], 82: [1, 30], 83: [1, 31], 84: [1, 32], 85: [1, 34], 86: 33 }, { 5: [2, 24], 14: [2, 24], 15: [2, 24], 19: [2, 24], 29: [2, 24], 34: [2, 24], 39: [2, 24], 44: [2, 24], 47: [2, 24], 48: [2, 24], 51: [2, 24], 55: [2, 24], 60: [2, 24] }, { 68: [1, 130] }, { 65: [2, 95], 68: [2, 95], 72: [2, 95], 80: [2, 95], 81: [2, 95], 82: [2, 95], 83: [2, 95], 84: [2, 95], 85: [2, 95] }, { 68: [2, 97] }, { 5: [2, 21], 14: [2, 21], 15: [2, 21], 19: [2, 21], 29: [2, 21], 34: [2, 21], 39: [2, 21], 44: [2, 21], 47: [2, 21], 48: [2, 21], 51: [2, 21], 55: [2, 21], 60: [2, 21] }, { 33: [1, 131] }, { 33: [2, 63] }, { 72: [1, 133], 76: 132 }, { 33: [1, 134] }, { 33: [2, 69] }, { 15: [2, 12] }, { 14: [2, 26], 15: [2, 26], 19: [2, 26], 29: [2, 26], 34: [2, 26], 47: [2, 26], 48: [2, 26], 51: [2, 26], 55: [2, 26], 60: [2, 26] }, { 23: [2, 31], 33: [2, 31], 54: [2, 31], 68: [2, 31], 72: [2, 31], 75: [2, 31] }, { 33: [2, 74], 42: 135, 74: 136, 75: [1, 121] }, { 33: [2, 71], 65: [2, 71], 72: [2, 71], 75: [2, 71], 80: [2, 71], 81: [2, 71], 82: [2, 71], 83: [2, 71], 84: [2, 71], 85: [2, 71] }, { 33: [2, 73], 75: [2, 73] }, { 23: [2, 29], 33: [2, 29], 54: [2, 29], 65: [2, 29], 68: [2, 29], 72: [2, 29], 75: [2, 29], 80: [2, 29], 81: [2, 29], 82: [2, 29], 83: [2, 29], 84: [2, 29], 85: [2, 29] }, { 14: [2, 15], 15: [2, 15], 19: [2, 15], 29: [2, 15], 34: [2, 15], 39: [2, 15], 44: [2, 15], 47: [2, 15], 48: [2, 15], 51: [2, 15], 55: [2, 15], 60: [2, 15] }, { 72: [1, 138], 77: [1, 137] }, { 72: [2, 100], 77: [2, 100] }, { 14: [2, 16], 15: [2, 16], 19: [2, 16], 29: [2, 16], 34: [2, 16], 44: [2, 16], 47: [2, 16], 48: [2, 16], 51: [2, 16], 55: [2, 16], 60: [2, 16] }, { 33: [1, 139] }, { 33: [2, 75] }, { 33: [2, 32] }, { 72: [2, 101], 77: [2, 101] }, { 14: [2, 17], 15: [2, 17], 19: [2, 17], 29: [2, 17], 34: [2, 17], 39: [2, 17], 44: [2, 17], 47: [2, 17], 48: [2, 17], 51: [2, 17], 55: [2, 17], 60: [2, 17] }],
	        defaultActions: { 4: [2, 1], 55: [2, 55], 57: [2, 20], 61: [2, 57], 74: [2, 81], 83: [2, 85], 87: [2, 18], 91: [2, 89], 102: [2, 53], 105: [2, 93], 111: [2, 19], 112: [2, 77], 117: [2, 97], 120: [2, 63], 123: [2, 69], 124: [2, 12], 136: [2, 75], 137: [2, 32] },
	        parseError: function parseError(str, hash) {
	            throw new Error(str);
	        },
	        parse: function parse(input) {
	            var self = this,
	                stack = [0],
	                vstack = [null],
	                lstack = [],
	                table = this.table,
	                yytext = "",
	                yylineno = 0,
	                yyleng = 0,
	                recovering = 0,
	                TERROR = 2,
	                EOF = 1;
	            this.lexer.setInput(input);
	            this.lexer.yy = this.yy;
	            this.yy.lexer = this.lexer;
	            this.yy.parser = this;
	            if (typeof this.lexer.yylloc == "undefined") this.lexer.yylloc = {};
	            var yyloc = this.lexer.yylloc;
	            lstack.push(yyloc);
	            var ranges = this.lexer.options && this.lexer.options.ranges;
	            if (typeof this.yy.parseError === "function") this.parseError = this.yy.parseError;
	            function popStack(n) {
	                stack.length = stack.length - 2 * n;
	                vstack.length = vstack.length - n;
	                lstack.length = lstack.length - n;
	            }
	            function lex() {
	                var token;
	                token = self.lexer.lex() || 1;
	                if (typeof token !== "number") {
	                    token = self.symbols_[token] || token;
	                }
	                return token;
	            }
	            var symbol,
	                preErrorSymbol,
	                state,
	                action,
	                a,
	                r,
	                yyval = {},
	                p,
	                len,
	                newState,
	                expected;
	            while (true) {
	                state = stack[stack.length - 1];
	                if (this.defaultActions[state]) {
	                    action = this.defaultActions[state];
	                } else {
	                    if (symbol === null || typeof symbol == "undefined") {
	                        symbol = lex();
	                    }
	                    action = table[state] && table[state][symbol];
	                }
	                if (typeof action === "undefined" || !action.length || !action[0]) {
	                    var errStr = "";
	                    if (!recovering) {
	                        expected = [];
	                        for (p in table[state]) if (this.terminals_[p] && p > 2) {
	                            expected.push("'" + this.terminals_[p] + "'");
	                        }
	                        if (this.lexer.showPosition) {
	                            errStr = "Parse error on line " + (yylineno + 1) + ":\n" + this.lexer.showPosition() + "\nExpecting " + expected.join(", ") + ", got '" + (this.terminals_[symbol] || symbol) + "'";
	                        } else {
	                            errStr = "Parse error on line " + (yylineno + 1) + ": Unexpected " + (symbol == 1 ? "end of input" : "'" + (this.terminals_[symbol] || symbol) + "'");
	                        }
	                        this.parseError(errStr, { text: this.lexer.match, token: this.terminals_[symbol] || symbol, line: this.lexer.yylineno, loc: yyloc, expected: expected });
	                    }
	                }
	                if (action[0] instanceof Array && action.length > 1) {
	                    throw new Error("Parse Error: multiple actions possible at state: " + state + ", token: " + symbol);
	                }
	                switch (action[0]) {
	                    case 1:
	                        stack.push(symbol);
	                        vstack.push(this.lexer.yytext);
	                        lstack.push(this.lexer.yylloc);
	                        stack.push(action[1]);
	                        symbol = null;
	                        if (!preErrorSymbol) {
	                            yyleng = this.lexer.yyleng;
	                            yytext = this.lexer.yytext;
	                            yylineno = this.lexer.yylineno;
	                            yyloc = this.lexer.yylloc;
	                            if (recovering > 0) recovering--;
	                        } else {
	                            symbol = preErrorSymbol;
	                            preErrorSymbol = null;
	                        }
	                        break;
	                    case 2:
	                        len = this.productions_[action[1]][1];
	                        yyval.$ = vstack[vstack.length - len];
	                        yyval._$ = { first_line: lstack[lstack.length - (len || 1)].first_line, last_line: lstack[lstack.length - 1].last_line, first_column: lstack[lstack.length - (len || 1)].first_column, last_column: lstack[lstack.length - 1].last_column };
	                        if (ranges) {
	                            yyval._$.range = [lstack[lstack.length - (len || 1)].range[0], lstack[lstack.length - 1].range[1]];
	                        }
	                        r = this.performAction.call(yyval, yytext, yyleng, yylineno, this.yy, action[1], vstack, lstack);
	                        if (typeof r !== "undefined") {
	                            return r;
	                        }
	                        if (len) {
	                            stack = stack.slice(0, -1 * len * 2);
	                            vstack = vstack.slice(0, -1 * len);
	                            lstack = lstack.slice(0, -1 * len);
	                        }
	                        stack.push(this.productions_[action[1]][0]);
	                        vstack.push(yyval.$);
	                        lstack.push(yyval._$);
	                        newState = table[stack[stack.length - 2]][stack[stack.length - 1]];
	                        stack.push(newState);
	                        break;
	                    case 3:
	                        return true;
	                }
	            }
	            return true;
	        }
	    };
	    /* Jison generated lexer */
	    var lexer = (function () {
	        var lexer = { EOF: 1,
	            parseError: function parseError(str, hash) {
	                if (this.yy.parser) {
	                    this.yy.parser.parseError(str, hash);
	                } else {
	                    throw new Error(str);
	                }
	            },
	            setInput: function setInput(input) {
	                this._input = input;
	                this._more = this._less = this.done = false;
	                this.yylineno = this.yyleng = 0;
	                this.yytext = this.matched = this.match = '';
	                this.conditionStack = ['INITIAL'];
	                this.yylloc = { first_line: 1, first_column: 0, last_line: 1, last_column: 0 };
	                if (this.options.ranges) this.yylloc.range = [0, 0];
	                this.offset = 0;
	                return this;
	            },
	            input: function input() {
	                var ch = this._input[0];
	                this.yytext += ch;
	                this.yyleng++;
	                this.offset++;
	                this.match += ch;
	                this.matched += ch;
	                var lines = ch.match(/(?:\r\n?|\n).*/g);
	                if (lines) {
	                    this.yylineno++;
	                    this.yylloc.last_line++;
	                } else {
	                    this.yylloc.last_column++;
	                }
	                if (this.options.ranges) this.yylloc.range[1]++;

	                this._input = this._input.slice(1);
	                return ch;
	            },
	            unput: function unput(ch) {
	                var len = ch.length;
	                var lines = ch.split(/(?:\r\n?|\n)/g);

	                this._input = ch + this._input;
	                this.yytext = this.yytext.substr(0, this.yytext.length - len - 1);
	                //this.yyleng -= len;
	                this.offset -= len;
	                var oldLines = this.match.split(/(?:\r\n?|\n)/g);
	                this.match = this.match.substr(0, this.match.length - 1);
	                this.matched = this.matched.substr(0, this.matched.length - 1);

	                if (lines.length - 1) this.yylineno -= lines.length - 1;
	                var r = this.yylloc.range;

	                this.yylloc = { first_line: this.yylloc.first_line,
	                    last_line: this.yylineno + 1,
	                    first_column: this.yylloc.first_column,
	                    last_column: lines ? (lines.length === oldLines.length ? this.yylloc.first_column : 0) + oldLines[oldLines.length - lines.length].length - lines[0].length : this.yylloc.first_column - len
	                };

	                if (this.options.ranges) {
	                    this.yylloc.range = [r[0], r[0] + this.yyleng - len];
	                }
	                return this;
	            },
	            more: function more() {
	                this._more = true;
	                return this;
	            },
	            less: function less(n) {
	                this.unput(this.match.slice(n));
	            },
	            pastInput: function pastInput() {
	                var past = this.matched.substr(0, this.matched.length - this.match.length);
	                return (past.length > 20 ? '...' : '') + past.substr(-20).replace(/\n/g, "");
	            },
	            upcomingInput: function upcomingInput() {
	                var next = this.match;
	                if (next.length < 20) {
	                    next += this._input.substr(0, 20 - next.length);
	                }
	                return (next.substr(0, 20) + (next.length > 20 ? '...' : '')).replace(/\n/g, "");
	            },
	            showPosition: function showPosition() {
	                var pre = this.pastInput();
	                var c = new Array(pre.length + 1).join("-");
	                return pre + this.upcomingInput() + "\n" + c + "^";
	            },
	            next: function next() {
	                if (this.done) {
	                    return this.EOF;
	                }
	                if (!this._input) this.done = true;

	                var token, match, tempMatch, index, col, lines;
	                if (!this._more) {
	                    this.yytext = '';
	                    this.match = '';
	                }
	                var rules = this._currentRules();
	                for (var i = 0; i < rules.length; i++) {
	                    tempMatch = this._input.match(this.rules[rules[i]]);
	                    if (tempMatch && (!match || tempMatch[0].length > match[0].length)) {
	                        match = tempMatch;
	                        index = i;
	                        if (!this.options.flex) break;
	                    }
	                }
	                if (match) {
	                    lines = match[0].match(/(?:\r\n?|\n).*/g);
	                    if (lines) this.yylineno += lines.length;
	                    this.yylloc = { first_line: this.yylloc.last_line,
	                        last_line: this.yylineno + 1,
	                        first_column: this.yylloc.last_column,
	                        last_column: lines ? lines[lines.length - 1].length - lines[lines.length - 1].match(/\r?\n?/)[0].length : this.yylloc.last_column + match[0].length };
	                    this.yytext += match[0];
	                    this.match += match[0];
	                    this.matches = match;
	                    this.yyleng = this.yytext.length;
	                    if (this.options.ranges) {
	                        this.yylloc.range = [this.offset, this.offset += this.yyleng];
	                    }
	                    this._more = false;
	                    this._input = this._input.slice(match[0].length);
	                    this.matched += match[0];
	                    token = this.performAction.call(this, this.yy, this, rules[index], this.conditionStack[this.conditionStack.length - 1]);
	                    if (this.done && this._input) this.done = false;
	                    if (token) return token;else return;
	                }
	                if (this._input === "") {
	                    return this.EOF;
	                } else {
	                    return this.parseError('Lexical error on line ' + (this.yylineno + 1) + '. Unrecognized text.\n' + this.showPosition(), { text: "", token: null, line: this.yylineno });
	                }
	            },
	            lex: function lex() {
	                var r = this.next();
	                if (typeof r !== 'undefined') {
	                    return r;
	                } else {
	                    return this.lex();
	                }
	            },
	            begin: function begin(condition) {
	                this.conditionStack.push(condition);
	            },
	            popState: function popState() {
	                return this.conditionStack.pop();
	            },
	            _currentRules: function _currentRules() {
	                return this.conditions[this.conditionStack[this.conditionStack.length - 1]].rules;
	            },
	            topState: function topState() {
	                return this.conditionStack[this.conditionStack.length - 2];
	            },
	            pushState: function begin(condition) {
	                this.begin(condition);
	            } };
	        lexer.options = {};
	        lexer.performAction = function anonymous(yy, yy_, $avoiding_name_collisions, YY_START
	        /**/) {

	            function strip(start, end) {
	                return yy_.yytext = yy_.yytext.substr(start, yy_.yyleng - end);
	            }

	            var YYSTATE = YY_START;
	            switch ($avoiding_name_collisions) {
	                case 0:
	                    if (yy_.yytext.slice(-2) === "\\\\") {
	                        strip(0, 1);
	                        this.begin("mu");
	                    } else if (yy_.yytext.slice(-1) === "\\") {
	                        strip(0, 1);
	                        this.begin("emu");
	                    } else {
	                        this.begin("mu");
	                    }
	                    if (yy_.yytext) return 15;

	                    break;
	                case 1:
	                    return 15;
	                    break;
	                case 2:
	                    this.popState();
	                    return 15;

	                    break;
	                case 3:
	                    this.begin('raw');return 15;
	                    break;
	                case 4:
	                    this.popState();
	                    // Should be using `this.topState()` below, but it currently
	                    // returns the second top instead of the first top. Opened an
	                    // issue about it at https://github.com/zaach/jison/issues/291
	                    if (this.conditionStack[this.conditionStack.length - 1] === 'raw') {
	                        return 15;
	                    } else {
	                        yy_.yytext = yy_.yytext.substr(5, yy_.yyleng - 9);
	                        return 'END_RAW_BLOCK';
	                    }

	                    break;
	                case 5:
	                    return 15;
	                    break;
	                case 6:
	                    this.popState();
	                    return 14;

	                    break;
	                case 7:
	                    return 65;
	                    break;
	                case 8:
	                    return 68;
	                    break;
	                case 9:
	                    return 19;
	                    break;
	                case 10:
	                    this.popState();
	                    this.begin('raw');
	                    return 23;

	                    break;
	                case 11:
	                    return 55;
	                    break;
	                case 12:
	                    return 60;
	                    break;
	                case 13:
	                    return 29;
	                    break;
	                case 14:
	                    return 47;
	                    break;
	                case 15:
	                    this.popState();return 44;
	                    break;
	                case 16:
	                    this.popState();return 44;
	                    break;
	                case 17:
	                    return 34;
	                    break;
	                case 18:
	                    return 39;
	                    break;
	                case 19:
	                    return 51;
	                    break;
	                case 20:
	                    return 48;
	                    break;
	                case 21:
	                    this.unput(yy_.yytext);
	                    this.popState();
	                    this.begin('com');

	                    break;
	                case 22:
	                    this.popState();
	                    return 14;

	                    break;
	                case 23:
	                    return 48;
	                    break;
	                case 24:
	                    return 73;
	                    break;
	                case 25:
	                    return 72;
	                    break;
	                case 26:
	                    return 72;
	                    break;
	                case 27:
	                    return 87;
	                    break;
	                case 28:
	                    // ignore whitespace
	                    break;
	                case 29:
	                    this.popState();return 54;
	                    break;
	                case 30:
	                    this.popState();return 33;
	                    break;
	                case 31:
	                    yy_.yytext = strip(1, 2).replace(/\\"/g, '"');return 80;
	                    break;
	                case 32:
	                    yy_.yytext = strip(1, 2).replace(/\\'/g, "'");return 80;
	                    break;
	                case 33:
	                    return 85;
	                    break;
	                case 34:
	                    return 82;
	                    break;
	                case 35:
	                    return 82;
	                    break;
	                case 36:
	                    return 83;
	                    break;
	                case 37:
	                    return 84;
	                    break;
	                case 38:
	                    return 81;
	                    break;
	                case 39:
	                    return 75;
	                    break;
	                case 40:
	                    return 77;
	                    break;
	                case 41:
	                    return 72;
	                    break;
	                case 42:
	                    yy_.yytext = yy_.yytext.replace(/\\([\\\]])/g, '$1');return 72;
	                    break;
	                case 43:
	                    return 'INVALID';
	                    break;
	                case 44:
	                    return 5;
	                    break;
	            }
	        };
	        lexer.rules = [/^(?:[^\x00]*?(?=(\{\{)))/, /^(?:[^\x00]+)/, /^(?:[^\x00]{2,}?(?=(\{\{|\\\{\{|\\\\\{\{|$)))/, /^(?:\{\{\{\{(?=[^\/]))/, /^(?:\{\{\{\{\/[^\s!"#%-,\.\/;->@\[-\^`\{-~]+(?=[=}\s\/.])\}\}\}\})/, /^(?:[^\x00]*?(?=(\{\{\{\{)))/, /^(?:[\s\S]*?--(~)?\}\})/, /^(?:\()/, /^(?:\))/, /^(?:\{\{\{\{)/, /^(?:\}\}\}\})/, /^(?:\{\{(~)?>)/, /^(?:\{\{(~)?#>)/, /^(?:\{\{(~)?#\*?)/, /^(?:\{\{(~)?\/)/, /^(?:\{\{(~)?\^\s*(~)?\}\})/, /^(?:\{\{(~)?\s*else\s*(~)?\}\})/, /^(?:\{\{(~)?\^)/, /^(?:\{\{(~)?\s*else\b)/, /^(?:\{\{(~)?\{)/, /^(?:\{\{(~)?&)/, /^(?:\{\{(~)?!--)/, /^(?:\{\{(~)?![\s\S]*?\}\})/, /^(?:\{\{(~)?\*?)/, /^(?:=)/, /^(?:\.\.)/, /^(?:\.(?=([=~}\s\/.)|])))/, /^(?:[\/.])/, /^(?:\s+)/, /^(?:\}(~)?\}\})/, /^(?:(~)?\}\})/, /^(?:"(\\["]|[^"])*")/, /^(?:'(\\[']|[^'])*')/, /^(?:@)/, /^(?:true(?=([~}\s)])))/, /^(?:false(?=([~}\s)])))/, /^(?:undefined(?=([~}\s)])))/, /^(?:null(?=([~}\s)])))/, /^(?:-?[0-9]+(?:\.[0-9]+)?(?=([~}\s)])))/, /^(?:as\s+\|)/, /^(?:\|)/, /^(?:([^\s!"#%-,\.\/;->@\[-\^`\{-~]+(?=([=~}\s\/.)|]))))/, /^(?:\[(\\\]|[^\]])*\])/, /^(?:.)/, /^(?:$)/];
	        lexer.conditions = { "mu": { "rules": [7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44], "inclusive": false }, "emu": { "rules": [2], "inclusive": false }, "com": { "rules": [6], "inclusive": false }, "raw": { "rules": [3, 4, 5], "inclusive": false }, "INITIAL": { "rules": [0, 1, 44], "inclusive": true } };
	        return lexer;
	    })();
	    parser.lexer = lexer;
	    function Parser() {
	        this.yy = {};
	    }Parser.prototype = parser;parser.Parser = Parser;
	    return new Parser();
	})();exports.__esModule = true;
	exports['default'] = handlebars;

/***/ },
/* 24 */
/***/ function(module, exports, __webpack_require__) {

	'use strict';

	var _interopRequireDefault = __webpack_require__(1)['default'];

	exports.__esModule = true;

	var _visitor = __webpack_require__(25);

	var _visitor2 = _interopRequireDefault(_visitor);

	function WhitespaceControl() {
	  var options = arguments.length <= 0 || arguments[0] === undefined ? {} : arguments[0];

	  this.options = options;
	}
	WhitespaceControl.prototype = new _visitor2['default']();

	WhitespaceControl.prototype.Program = function (program) {
	  var doStandalone = !this.options.ignoreStandalone;

	  var isRoot = !this.isRootSeen;
	  this.isRootSeen = true;

	  var body = program.body;
	  for (var i = 0, l = body.length; i < l; i++) {
	    var current = body[i],
	        strip = this.accept(current);

	    if (!strip) {
	      continue;
	    }

	    var _isPrevWhitespace = isPrevWhitespace(body, i, isRoot),
	        _isNextWhitespace = isNextWhitespace(body, i, isRoot),
	        openStandalone = strip.openStandalone && _isPrevWhitespace,
	        closeStandalone = strip.closeStandalone && _isNextWhitespace,
	        inlineStandalone = strip.inlineStandalone && _isPrevWhitespace && _isNextWhitespace;

	    if (strip.close) {
	      omitRight(body, i, true);
	    }
	    if (strip.open) {
	      omitLeft(body, i, true);
	    }

	    if (doStandalone && inlineStandalone) {
	      omitRight(body, i);

	      if (omitLeft(body, i)) {
	        // If we are on a standalone node, save the indent info for partials
	        if (current.type === 'PartialStatement') {
	          // Pull out the whitespace from the final line
	          current.indent = /([ \t]+$)/.exec(body[i - 1].original)[1];
	        }
	      }
	    }
	    if (doStandalone && openStandalone) {
	      omitRight((current.program || current.inverse).body);

	      // Strip out the previous content node if it's whitespace only
	      omitLeft(body, i);
	    }
	    if (doStandalone && closeStandalone) {
	      // Always strip the next node
	      omitRight(body, i);

	      omitLeft((current.inverse || current.program).body);
	    }
	  }

	  return program;
	};

	WhitespaceControl.prototype.BlockStatement = WhitespaceControl.prototype.DecoratorBlock = WhitespaceControl.prototype.PartialBlockStatement = function (block) {
	  this.accept(block.program);
	  this.accept(block.inverse);

	  // Find the inverse program that is involed with whitespace stripping.
	  var program = block.program || block.inverse,
	      inverse = block.program && block.inverse,
	      firstInverse = inverse,
	      lastInverse = inverse;

	  if (inverse && inverse.chained) {
	    firstInverse = inverse.body[0].program;

	    // Walk the inverse chain to find the last inverse that is actually in the chain.
	    while (lastInverse.chained) {
	      lastInverse = lastInverse.body[lastInverse.body.length - 1].program;
	    }
	  }

	  var strip = {
	    open: block.openStrip.open,
	    close: block.closeStrip.close,

	    // Determine the standalone candiacy. Basically flag our content as being possibly standalone
	    // so our parent can determine if we actually are standalone
	    openStandalone: isNextWhitespace(program.body),
	    closeStandalone: isPrevWhitespace((firstInverse || program).body)
	  };

	  if (block.openStrip.close) {
	    omitRight(program.body, null, true);
	  }

	  if (inverse) {
	    var inverseStrip = block.inverseStrip;

	    if (inverseStrip.open) {
	      omitLeft(program.body, null, true);
	    }

	    if (inverseStrip.close) {
	      omitRight(firstInverse.body, null, true);
	    }
	    if (block.closeStrip.open) {
	      omitLeft(lastInverse.body, null, true);
	    }

	    // Find standalone else statments
	    if (!this.options.ignoreStandalone && isPrevWhitespace(program.body) && isNextWhitespace(firstInverse.body)) {
	      omitLeft(program.body);
	      omitRight(firstInverse.body);
	    }
	  } else if (block.closeStrip.open) {
	    omitLeft(program.body, null, true);
	  }

	  return strip;
	};

	WhitespaceControl.prototype.Decorator = WhitespaceControl.prototype.MustacheStatement = function (mustache) {
	  return mustache.strip;
	};

	WhitespaceControl.prototype.PartialStatement = WhitespaceControl.prototype.CommentStatement = function (node) {
	  /* istanbul ignore next */
	  var strip = node.strip || {};
	  return {
	    inlineStandalone: true,
	    open: strip.open,
	    close: strip.close
	  };
	};

	function isPrevWhitespace(body, i, isRoot) {
	  if (i === undefined) {
	    i = body.length;
	  }

	  // Nodes that end with newlines are considered whitespace (but are special
	  // cased for strip operations)
	  var prev = body[i - 1],
	      sibling = body[i - 2];
	  if (!prev) {
	    return isRoot;
	  }

	  if (prev.type === 'ContentStatement') {
	    return (sibling || !isRoot ? /\r?\n\s*?$/ : /(^|\r?\n)\s*?$/).test(prev.original);
	  }
	}
	function isNextWhitespace(body, i, isRoot) {
	  if (i === undefined) {
	    i = -1;
	  }

	  var next = body[i + 1],
	      sibling = body[i + 2];
	  if (!next) {
	    return isRoot;
	  }

	  if (next.type === 'ContentStatement') {
	    return (sibling || !isRoot ? /^\s*?\r?\n/ : /^\s*?(\r?\n|$)/).test(next.original);
	  }
	}

	// Marks the node to the right of the position as omitted.
	// I.e. {{foo}}' ' will mark the ' ' node as omitted.
	//
	// If i is undefined, then the first child will be marked as such.
	//
	// If mulitple is truthy then all whitespace will be stripped out until non-whitespace
	// content is met.
	function omitRight(body, i, multiple) {
	  var current = body[i == null ? 0 : i + 1];
	  if (!current || current.type !== 'ContentStatement' || !multiple && current.rightStripped) {
	    return;
	  }

	  var original = current.value;
	  current.value = current.value.replace(multiple ? /^\s+/ : /^[ \t]*\r?\n?/, '');
	  current.rightStripped = current.value !== original;
	}

	// Marks the node to the left of the position as omitted.
	// I.e. ' '{{foo}} will mark the ' ' node as omitted.
	//
	// If i is undefined then the last child will be marked as such.
	//
	// If mulitple is truthy then all whitespace will be stripped out until non-whitespace
	// content is met.
	function omitLeft(body, i, multiple) {
	  var current = body[i == null ? body.length - 1 : i - 1];
	  if (!current || current.type !== 'ContentStatement' || !multiple && current.leftStripped) {
	    return;
	  }

	  // We omit the last node if it's whitespace only and not preceeded by a non-content node.
	  var original = current.value;
	  current.value = current.value.replace(multiple ? /\s+$/ : /[ \t]+$/, '');
	  current.leftStripped = current.value !== original;
	  return current.leftStripped;
	}

	exports['default'] = WhitespaceControl;
	module.exports = exports['default'];

/***/ },
/* 25 */
/***/ function(module, exports, __webpack_require__) {

	'use strict';

	var _interopRequireDefault = __webpack_require__(1)['default'];

	exports.__esModule = true;

	var _exception = __webpack_require__(6);

	var _exception2 = _interopRequireDefault(_exception);

	function Visitor() {
	  this.parents = [];
	}

	Visitor.prototype = {
	  constructor: Visitor,
	  mutating: false,

	  // Visits a given value. If mutating, will replace the value if necessary.
	  acceptKey: function acceptKey(node, name) {
	    var value = this.accept(node[name]);
	    if (this.mutating) {
	      // Hacky sanity check: This may have a few false positives for type for the helper
	      // methods but will generally do the right thing without a lot of overhead.
	      if (value && !Visitor.prototype[value.type]) {
	        throw new _exception2['default']('Unexpected node type "' + value.type + '" found when accepting ' + name + ' on ' + node.type);
	      }
	      node[name] = value;
	    }
	  },

	  // Performs an accept operation with added sanity check to ensure
	  // required keys are not removed.
	  acceptRequired: function acceptRequired(node, name) {
	    this.acceptKey(node, name);

	    if (!node[name]) {
	      throw new _exception2['default'](node.type + ' requires ' + name);
	    }
	  },

	  // Traverses a given array. If mutating, empty respnses will be removed
	  // for child elements.
	  acceptArray: function acceptArray(array) {
	    for (var i = 0, l = array.length; i < l; i++) {
	      this.acceptKey(array, i);

	      if (!array[i]) {
	        array.splice(i, 1);
	        i--;
	        l--;
	      }
	    }
	  },

	  accept: function accept(object) {
	    if (!object) {
	      return;
	    }

	    /* istanbul ignore next: Sanity code */
	    if (!this[object.type]) {
	      throw new _exception2['default']('Unknown type: ' + object.type, object);
	    }

	    if (this.current) {
	      this.parents.unshift(this.current);
	    }
	    this.current = object;

	    var ret = this[object.type](object);

	    this.current = this.parents.shift();

	    if (!this.mutating || ret) {
	      return ret;
	    } else if (ret !== false) {
	      return object;
	    }
	  },

	  Program: function Program(program) {
	    this.acceptArray(program.body);
	  },

	  MustacheStatement: visitSubExpression,
	  Decorator: visitSubExpression,

	  BlockStatement: visitBlock,
	  DecoratorBlock: visitBlock,

	  PartialStatement: visitPartial,
	  PartialBlockStatement: function PartialBlockStatement(partial) {
	    visitPartial.call(this, partial);

	    this.acceptKey(partial, 'program');
	  },

	  ContentStatement: function ContentStatement() /* content */{},
	  CommentStatement: function CommentStatement() /* comment */{},

	  SubExpression: visitSubExpression,

	  PathExpression: function PathExpression() /* path */{},

	  StringLiteral: function StringLiteral() /* string */{},
	  NumberLiteral: function NumberLiteral() /* number */{},
	  BooleanLiteral: function BooleanLiteral() /* bool */{},
	  UndefinedLiteral: function UndefinedLiteral() /* literal */{},
	  NullLiteral: function NullLiteral() /* literal */{},

	  Hash: function Hash(hash) {
	    this.acceptArray(hash.pairs);
	  },
	  HashPair: function HashPair(pair) {
	    this.acceptRequired(pair, 'value');
	  }
	};

	function visitSubExpression(mustache) {
	  this.acceptRequired(mustache, 'path');
	  this.acceptArray(mustache.params);
	  this.acceptKey(mustache, 'hash');
	}
	function visitBlock(block) {
	  visitSubExpression.call(this, block);

	  this.acceptKey(block, 'program');
	  this.acceptKey(block, 'inverse');
	}
	function visitPartial(partial) {
	  this.acceptRequired(partial, 'name');
	  this.acceptArray(partial.params);
	  this.acceptKey(partial, 'hash');
	}

	exports['default'] = Visitor;
	module.exports = exports['default'];

/***/ },
/* 26 */
/***/ function(module, exports, __webpack_require__) {

	'use strict';

	var _interopRequireDefault = __webpack_require__(1)['default'];

	exports.__esModule = true;
	exports.SourceLocation = SourceLocation;
	exports.id = id;
	exports.stripFlags = stripFlags;
	exports.stripComment = stripComment;
	exports.preparePath = preparePath;
	exports.prepareMustache = prepareMustache;
	exports.prepareRawBlock = prepareRawBlock;
	exports.prepareBlock = prepareBlock;
	exports.prepareProgram = prepareProgram;
	exports.preparePartialBlock = preparePartialBlock;

	var _exception = __webpack_require__(6);

	var _exception2 = _interopRequireDefault(_exception);

	function validateClose(open, close) {
	  close = close.path ? close.path.original : close;

	  if (open.path.original !== close) {
	    var errorNode = { loc: open.path.loc };

	    throw new _exception2['default'](open.path.original + " doesn't match " + close, errorNode);
	  }
	}

	function SourceLocation(source, locInfo) {
	  this.source = source;
	  this.start = {
	    line: locInfo.first_line,
	    column: locInfo.first_column
	  };
	  this.end = {
	    line: locInfo.last_line,
	    column: locInfo.last_column
	  };
	}

	function id(token) {
	  if (/^\[.*\]$/.test(token)) {
	    return token.substr(1, token.length - 2);
	  } else {
	    return token;
	  }
	}

	function stripFlags(open, close) {
	  return {
	    open: open.charAt(2) === '~',
	    close: close.charAt(close.length - 3) === '~'
	  };
	}

	function stripComment(comment) {
	  return comment.replace(/^\{\{~?\!-?-?/, '').replace(/-?-?~?\}\}$/, '');
	}

	function preparePath(data, parts, loc) {
	  loc = this.locInfo(loc);

	  var original = data ? '@' : '',
	      dig = [],
	      depth = 0,
	      depthString = '';

	  for (var i = 0, l = parts.length; i < l; i++) {
	    var part = parts[i].part,

	    // If we have [] syntax then we do not treat path references as operators,
	    // i.e. foo.[this] resolves to approximately context.foo['this']
	    isLiteral = parts[i].original !== part;
	    original += (parts[i].separator || '') + part;

	    if (!isLiteral && (part === '..' || part === '.' || part === 'this')) {
	      if (dig.length > 0) {
	        throw new _exception2['default']('Invalid path: ' + original, { loc: loc });
	      } else if (part === '..') {
	        depth++;
	        depthString += '../';
	      }
	    } else {
	      dig.push(part);
	    }
	  }

	  return {
	    type: 'PathExpression',
	    data: data,
	    depth: depth,
	    parts: dig,
	    original: original,
	    loc: loc
	  };
	}

	function prepareMustache(path, params, hash, open, strip, locInfo) {
	  // Must use charAt to support IE pre-10
	  var escapeFlag = open.charAt(3) || open.charAt(2),
	      escaped = escapeFlag !== '{' && escapeFlag !== '&';

	  var decorator = /\*/.test(open);
	  return {
	    type: decorator ? 'Decorator' : 'MustacheStatement',
	    path: path,
	    params: params,
	    hash: hash,
	    escaped: escaped,
	    strip: strip,
	    loc: this.locInfo(locInfo)
	  };
	}

	function prepareRawBlock(openRawBlock, contents, close, locInfo) {
	  validateClose(openRawBlock, close);

	  locInfo = this.locInfo(locInfo);
	  var program = {
	    type: 'Program',
	    body: contents,
	    strip: {},
	    loc: locInfo
	  };

	  return {
	    type: 'BlockStatement',
	    path: openRawBlock.path,
	    params: openRawBlock.params,
	    hash: openRawBlock.hash,
	    program: program,
	    openStrip: {},
	    inverseStrip: {},
	    closeStrip: {},
	    loc: locInfo
	  };
	}

	function prepareBlock(openBlock, program, inverseAndProgram, close, inverted, locInfo) {
	  if (close && close.path) {
	    validateClose(openBlock, close);
	  }

	  var decorator = /\*/.test(openBlock.open);

	  program.blockParams = openBlock.blockParams;

	  var inverse = undefined,
	      inverseStrip = undefined;

	  if (inverseAndProgram) {
	    if (decorator) {
	      throw new _exception2['default']('Unexpected inverse block on decorator', inverseAndProgram);
	    }

	    if (inverseAndProgram.chain) {
	      inverseAndProgram.program.body[0].closeStrip = close.strip;
	    }

	    inverseStrip = inverseAndProgram.strip;
	    inverse = inverseAndProgram.program;
	  }

	  if (inverted) {
	    inverted = inverse;
	    inverse = program;
	    program = inverted;
	  }

	  return {
	    type: decorator ? 'DecoratorBlock' : 'BlockStatement',
	    path: openBlock.path,
	    params: openBlock.params,
	    hash: openBlock.hash,
	    program: program,
	    inverse: inverse,
	    openStrip: openBlock.strip,
	    inverseStrip: inverseStrip,
	    closeStrip: close && close.strip,
	    loc: this.locInfo(locInfo)
	  };
	}

	function prepareProgram(statements, loc) {
	  if (!loc && statements.length) {
	    var firstLoc = statements[0].loc,
	        lastLoc = statements[statements.length - 1].loc;

	    /* istanbul ignore else */
	    if (firstLoc && lastLoc) {
	      loc = {
	        source: firstLoc.source,
	        start: {
	          line: firstLoc.start.line,
	          column: firstLoc.start.column
	        },
	        end: {
	          line: lastLoc.end.line,
	          column: lastLoc.end.column
	        }
	      };
	    }
	  }

	  return {
	    type: 'Program',
	    body: statements,
	    strip: {},
	    loc: loc
	  };
	}

	function preparePartialBlock(open, program, close, locInfo) {
	  validateClose(open, close);

	  return {
	    type: 'PartialBlockStatement',
	    name: open.path,
	    params: open.params,
	    hash: open.hash,
	    program: program,
	    openStrip: open.strip,
	    closeStrip: close && close.strip,
	    loc: this.locInfo(locInfo)
	  };
	}

/***/ },
/* 27 */
/***/ function(module, exports, __webpack_require__) {

	/* eslint-disable new-cap */

	'use strict';

	var _interopRequireDefault = __webpack_require__(1)['default'];

	exports.__esModule = true;
	exports.Compiler = Compiler;
	exports.precompile = precompile;
	exports.compile = compile;

	var _exception = __webpack_require__(6);

	var _exception2 = _interopRequireDefault(_exception);

	var _utils = __webpack_require__(5);

	var _ast = __webpack_require__(21);

	var _ast2 = _interopRequireDefault(_ast);

	var slice = [].slice;

	function Compiler() {}

	// the foundHelper register will disambiguate helper lookup from finding a
	// function in a context. This is necessary for mustache compatibility, which
	// requires that context functions in blocks are evaluated by blockHelperMissing,
	// and then proceed as if the resulting value was provided to blockHelperMissing.

	Compiler.prototype = {
	  compiler: Compiler,

	  equals: function equals(other) {
	    var len = this.opcodes.length;
	    if (other.opcodes.length !== len) {
	      return false;
	    }

	    for (var i = 0; i < len; i++) {
	      var opcode = this.opcodes[i],
	          otherOpcode = other.opcodes[i];
	      if (opcode.opcode !== otherOpcode.opcode || !argEquals(opcode.args, otherOpcode.args)) {
	        return false;
	      }
	    }

	    // We know that length is the same between the two arrays because they are directly tied
	    // to the opcode behavior above.
	    len = this.children.length;
	    for (var i = 0; i < len; i++) {
	      if (!this.children[i].equals(other.children[i])) {
	        return false;
	      }
	    }

	    return true;
	  },

	  guid: 0,

	  compile: function compile(program, options) {
	    this.sourceNode = [];
	    this.opcodes = [];
	    this.children = [];
	    this.options = options;
	    this.stringParams = options.stringParams;
	    this.trackIds = options.trackIds;

	    options.blockParams = options.blockParams || [];

	    // These changes will propagate to the other compiler components
	    var knownHelpers = options.knownHelpers;
	    options.knownHelpers = {
	      'helperMissing': true,
	      'blockHelperMissing': true,
	      'each': true,
	      'if': true,
	      'unless': true,
	      'with': true,
	      'log': true,
	      'lookup': true
	    };
	    if (knownHelpers) {
	      for (var _name in knownHelpers) {
	        /* istanbul ignore else */
	        if (_name in knownHelpers) {
	          options.knownHelpers[_name] = knownHelpers[_name];
	        }
	      }
	    }

	    return this.accept(program);
	  },

	  compileProgram: function compileProgram(program) {
	    var childCompiler = new this.compiler(),
	        // eslint-disable-line new-cap
	    result = childCompiler.compile(program, this.options),
	        guid = this.guid++;

	    this.usePartial = this.usePartial || result.usePartial;

	    this.children[guid] = result;
	    this.useDepths = this.useDepths || result.useDepths;

	    return guid;
	  },

	  accept: function accept(node) {
	    /* istanbul ignore next: Sanity code */
	    if (!this[node.type]) {
	      throw new _exception2['default']('Unknown type: ' + node.type, node);
	    }

	    this.sourceNode.unshift(node);
	    var ret = this[node.type](node);
	    this.sourceNode.shift();
	    return ret;
	  },

	  Program: function Program(program) {
	    this.options.blockParams.unshift(program.blockParams);

	    var body = program.body,
	        bodyLength = body.length;
	    for (var i = 0; i < bodyLength; i++) {
	      this.accept(body[i]);
	    }

	    this.options.blockParams.shift();

	    this.isSimple = bodyLength === 1;
	    this.blockParams = program.blockParams ? program.blockParams.length : 0;

	    return this;
	  },

	  BlockStatement: function BlockStatement(block) {
	    transformLiteralToPath(block);

	    var program = block.program,
	        inverse = block.inverse;

	    program = program && this.compileProgram(program);
	    inverse = inverse && this.compileProgram(inverse);

	    var type = this.classifySexpr(block);

	    if (type === 'helper') {
	      this.helperSexpr(block, program, inverse);
	    } else if (type === 'simple') {
	      this.simpleSexpr(block);

	      // now that the simple mustache is resolved, we need to
	      // evaluate it by executing `blockHelperMissing`
	      this.opcode('pushProgram', program);
	      this.opcode('pushProgram', inverse);
	      this.opcode('emptyHash');
	      this.opcode('blockValue', block.path.original);
	    } else {
	      this.ambiguousSexpr(block, program, inverse);

	      // now that the simple mustache is resolved, we need to
	      // evaluate it by executing `blockHelperMissing`
	      this.opcode('pushProgram', program);
	      this.opcode('pushProgram', inverse);
	      this.opcode('emptyHash');
	      this.opcode('ambiguousBlockValue');
	    }

	    this.opcode('append');
	  },

	  DecoratorBlock: function DecoratorBlock(decorator) {
	    var program = decorator.program && this.compileProgram(decorator.program);
	    var params = this.setupFullMustacheParams(decorator, program, undefined),
	        path = decorator.path;

	    this.useDecorators = true;
	    this.opcode('registerDecorator', params.length, path.original);
	  },

	  PartialStatement: function PartialStatement(partial) {
	    this.usePartial = true;

	    var program = partial.program;
	    if (program) {
	      program = this.compileProgram(partial.program);
	    }

	    var params = partial.params;
	    if (params.length > 1) {
	      throw new _exception2['default']('Unsupported number of partial arguments: ' + params.length, partial);
	    } else if (!params.length) {
	      if (this.options.explicitPartialContext) {
	        this.opcode('pushLiteral', 'undefined');
	      } else {
	        params.push({ type: 'PathExpression', parts: [], depth: 0 });
	      }
	    }

	    var partialName = partial.name.original,
	        isDynamic = partial.name.type === 'SubExpression';
	    if (isDynamic) {
	      this.accept(partial.name);
	    }

	    this.setupFullMustacheParams(partial, program, undefined, true);

	    var indent = partial.indent || '';
	    if (this.options.preventIndent && indent) {
	      this.opcode('appendContent', indent);
	      indent = '';
	    }

	    this.opcode('invokePartial', isDynamic, partialName, indent);
	    this.opcode('append');
	  },
	  PartialBlockStatement: function PartialBlockStatement(partialBlock) {
	    this.PartialStatement(partialBlock);
	  },

	  MustacheStatement: function MustacheStatement(mustache) {
	    this.SubExpression(mustache);

	    if (mustache.escaped && !this.options.noEscape) {
	      this.opcode('appendEscaped');
	    } else {
	      this.opcode('append');
	    }
	  },
	  Decorator: function Decorator(decorator) {
	    this.DecoratorBlock(decorator);
	  },

	  ContentStatement: function ContentStatement(content) {
	    if (content.value) {
	      this.opcode('appendContent', content.value);
	    }
	  },

	  CommentStatement: function CommentStatement() {},

	  SubExpression: function SubExpression(sexpr) {
	    transformLiteralToPath(sexpr);
	    var type = this.classifySexpr(sexpr);

	    if (type === 'simple') {
	      this.simpleSexpr(sexpr);
	    } else if (type === 'helper') {
	      this.helperSexpr(sexpr);
	    } else {
	      this.ambiguousSexpr(sexpr);
	    }
	  },
	  ambiguousSexpr: function ambiguousSexpr(sexpr, program, inverse) {
	    var path = sexpr.path,
	        name = path.parts[0],
	        isBlock = program != null || inverse != null;

	    this.opcode('getContext', path.depth);

	    this.opcode('pushProgram', program);
	    this.opcode('pushProgram', inverse);

	    path.strict = true;
	    this.accept(path);

	    this.opcode('invokeAmbiguous', name, isBlock);
	  },

	  simpleSexpr: function simpleSexpr(sexpr) {
	    var path = sexpr.path;
	    path.strict = true;
	    this.accept(path);
	    this.opcode('resolvePossibleLambda');
	  },

	  helperSexpr: function helperSexpr(sexpr, program, inverse) {
	    var params = this.setupFullMustacheParams(sexpr, program, inverse),
	        path = sexpr.path,
	        name = path.parts[0];

	    if (this.options.knownHelpers[name]) {
	      this.opcode('invokeKnownHelper', params.length, name);
	    } else if (this.options.knownHelpersOnly) {
	      throw new _exception2['default']('You specified knownHelpersOnly, but used the unknown helper ' + name, sexpr);
	    } else {
	      path.strict = true;
	      path.falsy = true;

	      this.accept(path);
	      this.opcode('invokeHelper', params.length, path.original, _ast2['default'].helpers.simpleId(path));
	    }
	  },

	  PathExpression: function PathExpression(path) {
	    this.addDepth(path.depth);
	    this.opcode('getContext', path.depth);

	    var name = path.parts[0],
	        scoped = _ast2['default'].helpers.scopedId(path),
	        blockParamId = !path.depth && !scoped && this.blockParamIndex(name);

	    if (blockParamId) {
	      this.opcode('lookupBlockParam', blockParamId, path.parts);
	    } else if (!name) {
	      // Context reference, i.e. `{{foo .}}` or `{{foo ..}}`
	      this.opcode('pushContext');
	    } else if (path.data) {
	      this.options.data = true;
	      this.opcode('lookupData', path.depth, path.parts, path.strict);
	    } else {
	      this.opcode('lookupOnContext', path.parts, path.falsy, path.strict, scoped);
	    }
	  },

	  StringLiteral: function StringLiteral(string) {
	    this.opcode('pushString', string.value);
	  },

	  NumberLiteral: function NumberLiteral(number) {
	    this.opcode('pushLiteral', number.value);
	  },

	  BooleanLiteral: function BooleanLiteral(bool) {
	    this.opcode('pushLiteral', bool.value);
	  },

	  UndefinedLiteral: function UndefinedLiteral() {
	    this.opcode('pushLiteral', 'undefined');
	  },

	  NullLiteral: function NullLiteral() {
	    this.opcode('pushLiteral', 'null');
	  },

	  Hash: function Hash(hash) {
	    var pairs = hash.pairs,
	        i = 0,
	        l = pairs.length;

	    this.opcode('pushHash');

	    for (; i < l; i++) {
	      this.pushParam(pairs[i].value);
	    }
	    while (i--) {
	      this.opcode('assignToHash', pairs[i].key);
	    }
	    this.opcode('popHash');
	  },

	  // HELPERS
	  opcode: function opcode(name) {
	    this.opcodes.push({ opcode: name, args: slice.call(arguments, 1), loc: this.sourceNode[0].loc });
	  },

	  addDepth: function addDepth(depth) {
	    if (!depth) {
	      return;
	    }

	    this.useDepths = true;
	  },

	  classifySexpr: function classifySexpr(sexpr) {
	    var isSimple = _ast2['default'].helpers.simpleId(sexpr.path);

	    var isBlockParam = isSimple && !!this.blockParamIndex(sexpr.path.parts[0]);

	    // a mustache is an eligible helper if:
	    // * its id is simple (a single part, not `this` or `..`)
	    var isHelper = !isBlockParam && _ast2['default'].helpers.helperExpression(sexpr);

	    // if a mustache is an eligible helper but not a definite
	    // helper, it is ambiguous, and will be resolved in a later
	    // pass or at runtime.
	    var isEligible = !isBlockParam && (isHelper || isSimple);

	    // if ambiguous, we can possibly resolve the ambiguity now
	    // An eligible helper is one that does not have a complex path, i.e. `this.foo`, `../foo` etc.
	    if (isEligible && !isHelper) {
	      var _name2 = sexpr.path.parts[0],
	          options = this.options;

	      if (options.knownHelpers[_name2]) {
	        isHelper = true;
	      } else if (options.knownHelpersOnly) {
	        isEligible = false;
	      }
	    }

	    if (isHelper) {
	      return 'helper';
	    } else if (isEligible) {
	      return 'ambiguous';
	    } else {
	      return 'simple';
	    }
	  },

	  pushParams: function pushParams(params) {
	    for (var i = 0, l = params.length; i < l; i++) {
	      this.pushParam(params[i]);
	    }
	  },

	  pushParam: function pushParam(val) {
	    var value = val.value != null ? val.value : val.original || '';

	    if (this.stringParams) {
	      if (value.replace) {
	        value = value.replace(/^(\.?\.\/)*/g, '').replace(/\//g, '.');
	      }

	      if (val.depth) {
	        this.addDepth(val.depth);
	      }
	      this.opcode('getContext', val.depth || 0);
	      this.opcode('pushStringParam', value, val.type);

	      if (val.type === 'SubExpression') {
	        // SubExpressions get evaluated and passed in
	        // in string params mode.
	        this.accept(val);
	      }
	    } else {
	      if (this.trackIds) {
	        var blockParamIndex = undefined;
	        if (val.parts && !_ast2['default'].helpers.scopedId(val) && !val.depth) {
	          blockParamIndex = this.blockParamIndex(val.parts[0]);
	        }
	        if (blockParamIndex) {
	          var blockParamChild = val.parts.slice(1).join('.');
	          this.opcode('pushId', 'BlockParam', blockParamIndex, blockParamChild);
	        } else {
	          value = val.original || value;
	          if (value.replace) {
	            value = value.replace(/^this(?:\.|$)/, '').replace(/^\.\//, '').replace(/^\.$/, '');
	          }

	          this.opcode('pushId', val.type, value);
	        }
	      }
	      this.accept(val);
	    }
	  },

	  setupFullMustacheParams: function setupFullMustacheParams(sexpr, program, inverse, omitEmpty) {
	    var params = sexpr.params;
	    this.pushParams(params);

	    this.opcode('pushProgram', program);
	    this.opcode('pushProgram', inverse);

	    if (sexpr.hash) {
	      this.accept(sexpr.hash);
	    } else {
	      this.opcode('emptyHash', omitEmpty);
	    }

	    return params;
	  },

	  blockParamIndex: function blockParamIndex(name) {
	    for (var depth = 0, len = this.options.blockParams.length; depth < len; depth++) {
	      var blockParams = this.options.blockParams[depth],
	          param = blockParams && _utils.indexOf(blockParams, name);
	      if (blockParams && param >= 0) {
	        return [depth, param];
	      }
	    }
	  }
	};

	function precompile(input, options, env) {
	  if (input == null || typeof input !== 'string' && input.type !== 'Program') {
	    throw new _exception2['default']('You must pass a string or Handlebars AST to Handlebars.precompile. You passed ' + input);
	  }

	  options = options || {};
	  if (!('data' in options)) {
	    options.data = true;
	  }
	  if (options.compat) {
	    options.useDepths = true;
	  }

	  var ast = env.parse(input, options),
	      environment = new env.Compiler().compile(ast, options);
	  return new env.JavaScriptCompiler().compile(environment, options);
	}

	function compile(input, options, env) {
	  if (options === undefined) options = {};

	  if (input == null || typeof input !== 'string' && input.type !== 'Program') {
	    throw new _exception2['default']('You must pass a string or Handlebars AST to Handlebars.compile. You passed ' + input);
	  }

	  if (!('data' in options)) {
	    options.data = true;
	  }
	  if (options.compat) {
	    options.useDepths = true;
	  }

	  var compiled = undefined;

	  function compileInput() {
	    var ast = env.parse(input, options),
	        environment = new env.Compiler().compile(ast, options),
	        templateSpec = new env.JavaScriptCompiler().compile(environment, options, undefined, true);
	    return env.template(templateSpec);
	  }

	  // Template is only compiled on first use and cached after that point.
	  function ret(context, execOptions) {
	    if (!compiled) {
	      compiled = compileInput();
	    }
	    return compiled.call(this, context, execOptions);
	  }
	  ret._setup = function (setupOptions) {
	    if (!compiled) {
	      compiled = compileInput();
	    }
	    return compiled._setup(setupOptions);
	  };
	  ret._child = function (i, data, blockParams, depths) {
	    if (!compiled) {
	      compiled = compileInput();
	    }
	    return compiled._child(i, data, blockParams, depths);
	  };
	  return ret;
	}

	function argEquals(a, b) {
	  if (a === b) {
	    return true;
	  }

	  if (_utils.isArray(a) && _utils.isArray(b) && a.length === b.length) {
	    for (var i = 0; i < a.length; i++) {
	      if (!argEquals(a[i], b[i])) {
	        return false;
	      }
	    }
	    return true;
	  }
	}

	function transformLiteralToPath(sexpr) {
	  if (!sexpr.path.parts) {
	    var literal = sexpr.path;
	    // Casting to string here to make false and 0 literal values play nicely with the rest
	    // of the system.
	    sexpr.path = {
	      type: 'PathExpression',
	      data: false,
	      depth: 0,
	      parts: [literal.original + ''],
	      original: literal.original + '',
	      loc: literal.loc
	    };
	  }
	}

/***/ },
/* 28 */
/***/ function(module, exports, __webpack_require__) {

	'use strict';

	var _interopRequireDefault = __webpack_require__(1)['default'];

	exports.__esModule = true;

	var _base = __webpack_require__(4);

	var _exception = __webpack_require__(6);

	var _exception2 = _interopRequireDefault(_exception);

	var _utils = __webpack_require__(5);

	var _codeGen = __webpack_require__(29);

	var _codeGen2 = _interopRequireDefault(_codeGen);

	function Literal(value) {
	  this.value = value;
	}

	function JavaScriptCompiler() {}

	JavaScriptCompiler.prototype = {
	  // PUBLIC API: You can override these methods in a subclass to provide
	  // alternative compiled forms for name lookup and buffering semantics
	  nameLookup: function nameLookup(parent, name /* , type*/) {
	    if (JavaScriptCompiler.isValidJavaScriptVariableName(name)) {
	      return [parent, '.', name];
	    } else {
	      return [parent, '[', JSON.stringify(name), ']'];
	    }
	  },
	  depthedLookup: function depthedLookup(name) {
	    return [this.aliasable('container.lookup'), '(depths, "', name, '")'];
	  },

	  compilerInfo: function compilerInfo() {
	    var revision = _base.COMPILER_REVISION,
	        versions = _base.REVISION_CHANGES[revision];
	    return [revision, versions];
	  },

	  appendToBuffer: function appendToBuffer(source, location, explicit) {
	    // Force a source as this simplifies the merge logic.
	    if (!_utils.isArray(source)) {
	      source = [source];
	    }
	    source = this.source.wrap(source, location);

	    if (this.environment.isSimple) {
	      return ['return ', source, ';'];
	    } else if (explicit) {
	      // This is a case where the buffer operation occurs as a child of another
	      // construct, generally braces. We have to explicitly output these buffer
	      // operations to ensure that the emitted code goes in the correct location.
	      return ['buffer += ', source, ';'];
	    } else {
	      source.appendToBuffer = true;
	      return source;
	    }
	  },

	  initializeBuffer: function initializeBuffer() {
	    return this.quotedString('');
	  },
	  // END PUBLIC API

	  compile: function compile(environment, options, context, asObject) {
	    this.environment = environment;
	    this.options = options;
	    this.stringParams = this.options.stringParams;
	    this.trackIds = this.options.trackIds;
	    this.precompile = !asObject;

	    this.name = this.environment.name;
	    this.isChild = !!context;
	    this.context = context || {
	      decorators: [],
	      programs: [],
	      environments: []
	    };

	    this.preamble();

	    this.stackSlot = 0;
	    this.stackVars = [];
	    this.aliases = {};
	    this.registers = { list: [] };
	    this.hashes = [];
	    this.compileStack = [];
	    this.inlineStack = [];
	    this.blockParams = [];

	    this.compileChildren(environment, options);

	    this.useDepths = this.useDepths || environment.useDepths || environment.useDecorators || this.options.compat;
	    this.useBlockParams = this.useBlockParams || environment.useBlockParams;

	    var opcodes = environment.opcodes,
	        opcode = undefined,
	        firstLoc = undefined,
	        i = undefined,
	        l = undefined;

	    for (i = 0, l = opcodes.length; i < l; i++) {
	      opcode = opcodes[i];

	      this.source.currentLocation = opcode.loc;
	      firstLoc = firstLoc || opcode.loc;
	      this[opcode.opcode].apply(this, opcode.args);
	    }

	    // Flush any trailing content that might be pending.
	    this.source.currentLocation = firstLoc;
	    this.pushSource('');

	    /* istanbul ignore next */
	    if (this.stackSlot || this.inlineStack.length || this.compileStack.length) {
	      throw new _exception2['default']('Compile completed with content left on stack');
	    }

	    if (!this.decorators.isEmpty()) {
	      this.useDecorators = true;

	      this.decorators.prepend('var decorators = container.decorators;\n');
	      this.decorators.push('return fn;');

	      if (asObject) {
	        this.decorators = Function.apply(this, ['fn', 'props', 'container', 'depth0', 'data', 'blockParams', 'depths', this.decorators.merge()]);
	      } else {
	        this.decorators.prepend('function(fn, props, container, depth0, data, blockParams, depths) {\n');
	        this.decorators.push('}\n');
	        this.decorators = this.decorators.merge();
	      }
	    } else {
	      this.decorators = undefined;
	    }

	    var fn = this.createFunctionContext(asObject);
	    if (!this.isChild) {
	      var ret = {
	        compiler: this.compilerInfo(),
	        main: fn
	      };

	      if (this.decorators) {
	        ret.main_d = this.decorators; // eslint-disable-line camelcase
	        ret.useDecorators = true;
	      }

	      var _context = this.context;
	      var programs = _context.programs;
	      var decorators = _context.decorators;

	      for (i = 0, l = programs.length; i < l; i++) {
	        if (programs[i]) {
	          ret[i] = programs[i];
	          if (decorators[i]) {
	            ret[i + '_d'] = decorators[i];
	            ret.useDecorators = true;
	          }
	        }
	      }

	      if (this.environment.usePartial) {
	        ret.usePartial = true;
	      }
	      if (this.options.data) {
	        ret.useData = true;
	      }
	      if (this.useDepths) {
	        ret.useDepths = true;
	      }
	      if (this.useBlockParams) {
	        ret.useBlockParams = true;
	      }
	      if (this.options.compat) {
	        ret.compat = true;
	      }

	      if (!asObject) {
	        ret.compiler = JSON.stringify(ret.compiler);

	        this.source.currentLocation = { start: { line: 1, column: 0 } };
	        ret = this.objectLiteral(ret);

	        if (options.srcName) {
	          ret = ret.toStringWithSourceMap({ file: options.destName });
	          ret.map = ret.map && ret.map.toString();
	        } else {
	          ret = ret.toString();
	        }
	      } else {
	        ret.compilerOptions = this.options;
	      }

	      return ret;
	    } else {
	      return fn;
	    }
	  },

	  preamble: function preamble() {
	    // track the last context pushed into place to allow skipping the
	    // getContext opcode when it would be a noop
	    this.lastContext = 0;
	    this.source = new _codeGen2['default'](this.options.srcName);
	    this.decorators = new _codeGen2['default'](this.options.srcName);
	  },

	  createFunctionContext: function createFunctionContext(asObject) {
	    var varDeclarations = '';

	    var locals = this.stackVars.concat(this.registers.list);
	    if (locals.length > 0) {
	      varDeclarations += ', ' + locals.join(', ');
	    }

	    // Generate minimizer alias mappings
	    //
	    // When using true SourceNodes, this will update all references to the given alias
	    // as the source nodes are reused in situ. For the non-source node compilation mode,
	    // aliases will not be used, but this case is already being run on the client and
	    // we aren't concern about minimizing the template size.
	    var aliasCount = 0;
	    for (var alias in this.aliases) {
	      // eslint-disable-line guard-for-in
	      var node = this.aliases[alias];

	      if (this.aliases.hasOwnProperty(alias) && node.children && node.referenceCount > 1) {
	        varDeclarations += ', alias' + ++aliasCount + '=' + alias;
	        node.children[0] = 'alias' + aliasCount;
	      }
	    }

	    var params = ['container', 'depth0', 'helpers', 'partials', 'data'];

	    if (this.useBlockParams || this.useDepths) {
	      params.push('blockParams');
	    }
	    if (this.useDepths) {
	      params.push('depths');
	    }

	    // Perform a second pass over the output to merge content when possible
	    var source = this.mergeSource(varDeclarations);

	    if (asObject) {
	      params.push(source);

	      return Function.apply(this, params);
	    } else {
	      return this.source.wrap(['function(', params.join(','), ') {\n  ', source, '}']);
	    }
	  },
	  mergeSource: function mergeSource(varDeclarations) {
	    var isSimple = this.environment.isSimple,
	        appendOnly = !this.forceBuffer,
	        appendFirst = undefined,
	        sourceSeen = undefined,
	        bufferStart = undefined,
	        bufferEnd = undefined;
	    this.source.each(function (line) {
	      if (line.appendToBuffer) {
	        if (bufferStart) {
	          line.prepend('  + ');
	        } else {
	          bufferStart = line;
	        }
	        bufferEnd = line;
	      } else {
	        if (bufferStart) {
	          if (!sourceSeen) {
	            appendFirst = true;
	          } else {
	            bufferStart.prepend('buffer += ');
	          }
	          bufferEnd.add(';');
	          bufferStart = bufferEnd = undefined;
	        }

	        sourceSeen = true;
	        if (!isSimple) {
	          appendOnly = false;
	        }
	      }
	    });

	    if (appendOnly) {
	      if (bufferStart) {
	        bufferStart.prepend('return ');
	        bufferEnd.add(';');
	      } else if (!sourceSeen) {
	        this.source.push('return "";');
	      }
	    } else {
	      varDeclarations += ', buffer = ' + (appendFirst ? '' : this.initializeBuffer());

	      if (bufferStart) {
	        bufferStart.prepend('return buffer + ');
	        bufferEnd.add(';');
	      } else {
	        this.source.push('return buffer;');
	      }
	    }

	    if (varDeclarations) {
	      this.source.prepend('var ' + varDeclarations.substring(2) + (appendFirst ? '' : ';\n'));
	    }

	    return this.source.merge();
	  },

	  // [blockValue]
	  //
	  // On stack, before: hash, inverse, program, value
	  // On stack, after: return value of blockHelperMissing
	  //
	  // The purpose of this opcode is to take a block of the form
	  // `{{#this.foo}}...{{/this.foo}}`, resolve the value of `foo`, and
	  // replace it on the stack with the result of properly
	  // invoking blockHelperMissing.
	  blockValue: function blockValue(name) {
	    var blockHelperMissing = this.aliasable('helpers.blockHelperMissing'),
	        params = [this.contextName(0)];
	    this.setupHelperArgs(name, 0, params);

	    var blockName = this.popStack();
	    params.splice(1, 0, blockName);

	    this.push(this.source.functionCall(blockHelperMissing, 'call', params));
	  },

	  // [ambiguousBlockValue]
	  //
	  // On stack, before: hash, inverse, program, value
	  // Compiler value, before: lastHelper=value of last found helper, if any
	  // On stack, after, if no lastHelper: same as [blockValue]
	  // On stack, after, if lastHelper: value
	  ambiguousBlockValue: function ambiguousBlockValue() {
	    // We're being a bit cheeky and reusing the options value from the prior exec
	    var blockHelperMissing = this.aliasable('helpers.blockHelperMissing'),
	        params = [this.contextName(0)];
	    this.setupHelperArgs('', 0, params, true);

	    this.flushInline();

	    var current = this.topStack();
	    params.splice(1, 0, current);

	    this.pushSource(['if (!', this.lastHelper, ') { ', current, ' = ', this.source.functionCall(blockHelperMissing, 'call', params), '}']);
	  },

	  // [appendContent]
	  //
	  // On stack, before: ...
	  // On stack, after: ...
	  //
	  // Appends the string value of `content` to the current buffer
	  appendContent: function appendContent(content) {
	    if (this.pendingContent) {
	      content = this.pendingContent + content;
	    } else {
	      this.pendingLocation = this.source.currentLocation;
	    }

	    this.pendingContent = content;
	  },

	  // [append]
	  //
	  // On stack, before: value, ...
	  // On stack, after: ...
	  //
	  // Coerces `value` to a String and appends it to the current buffer.
	  //
	  // If `value` is truthy, or 0, it is coerced into a string and appended
	  // Otherwise, the empty string is appended
	  append: function append() {
	    if (this.isInline()) {
	      this.replaceStack(function (current) {
	        return [' != null ? ', current, ' : ""'];
	      });

	      this.pushSource(this.appendToBuffer(this.popStack()));
	    } else {
	      var local = this.popStack();
	      this.pushSource(['if (', local, ' != null) { ', this.appendToBuffer(local, undefined, true), ' }']);
	      if (this.environment.isSimple) {
	        this.pushSource(['else { ', this.appendToBuffer("''", undefined, true), ' }']);
	      }
	    }
	  },

	  // [appendEscaped]
	  //
	  // On stack, before: value, ...
	  // On stack, after: ...
	  //
	  // Escape `value` and append it to the buffer
	  appendEscaped: function appendEscaped() {
	    this.pushSource(this.appendToBuffer([this.aliasable('container.escapeExpression'), '(', this.popStack(), ')']));
	  },

	  // [getContext]
	  //
	  // On stack, before: ...
	  // On stack, after: ...
	  // Compiler value, after: lastContext=depth
	  //
	  // Set the value of the `lastContext` compiler value to the depth
	  getContext: function getContext(depth) {
	    this.lastContext = depth;
	  },

	  // [pushContext]
	  //
	  // On stack, before: ...
	  // On stack, after: currentContext, ...
	  //
	  // Pushes the value of the current context onto the stack.
	  pushContext: function pushContext() {
	    this.pushStackLiteral(this.contextName(this.lastContext));
	  },

	  // [lookupOnContext]
	  //
	  // On stack, before: ...
	  // On stack, after: currentContext[name], ...
	  //
	  // Looks up the value of `name` on the current context and pushes
	  // it onto the stack.
	  lookupOnContext: function lookupOnContext(parts, falsy, strict, scoped) {
	    var i = 0;

	    if (!scoped && this.options.compat && !this.lastContext) {
	      // The depthed query is expected to handle the undefined logic for the root level that
	      // is implemented below, so we evaluate that directly in compat mode
	      this.push(this.depthedLookup(parts[i++]));
	    } else {
	      this.pushContext();
	    }

	    this.resolvePath('context', parts, i, falsy, strict);
	  },

	  // [lookupBlockParam]
	  //
	  // On stack, before: ...
	  // On stack, after: blockParam[name], ...
	  //
	  // Looks up the value of `parts` on the given block param and pushes
	  // it onto the stack.
	  lookupBlockParam: function lookupBlockParam(blockParamId, parts) {
	    this.useBlockParams = true;

	    this.push(['blockParams[', blockParamId[0], '][', blockParamId[1], ']']);
	    this.resolvePath('context', parts, 1);
	  },

	  // [lookupData]
	  //
	  // On stack, before: ...
	  // On stack, after: data, ...
	  //
	  // Push the data lookup operator
	  lookupData: function lookupData(depth, parts, strict) {
	    if (!depth) {
	      this.pushStackLiteral('data');
	    } else {
	      this.pushStackLiteral('container.data(data, ' + depth + ')');
	    }

	    this.resolvePath('data', parts, 0, true, strict);
	  },

	  resolvePath: function resolvePath(type, parts, i, falsy, strict) {
	    // istanbul ignore next

	    var _this = this;

	    if (this.options.strict || this.options.assumeObjects) {
	      this.push(strictLookup(this.options.strict && strict, this, parts, type));
	      return;
	    }

	    var len = parts.length;
	    for (; i < len; i++) {
	      /* eslint-disable no-loop-func */
	      this.replaceStack(function (current) {
	        var lookup = _this.nameLookup(current, parts[i], type);
	        // We want to ensure that zero and false are handled properly if the context (falsy flag)
	        // needs to have the special handling for these values.
	        if (!falsy) {
	          return [' != null ? ', lookup, ' : ', current];
	        } else {
	          // Otherwise we can use generic falsy handling
	          return [' && ', lookup];
	        }
	      });
	      /* eslint-enable no-loop-func */
	    }
	  },

	  // [resolvePossibleLambda]
	  //
	  // On stack, before: value, ...
	  // On stack, after: resolved value, ...
	  //
	  // If the `value` is a lambda, replace it on the stack by
	  // the return value of the lambda
	  resolvePossibleLambda: function resolvePossibleLambda() {
	    this.push([this.aliasable('container.lambda'), '(', this.popStack(), ', ', this.contextName(0), ')']);
	  },

	  // [pushStringParam]
	  //
	  // On stack, before: ...
	  // On stack, after: string, currentContext, ...
	  //
	  // This opcode is designed for use in string mode, which
	  // provides the string value of a parameter along with its
	  // depth rather than resolving it immediately.
	  pushStringParam: function pushStringParam(string, type) {
	    this.pushContext();
	    this.pushString(type);

	    // If it's a subexpression, the string result
	    // will be pushed after this opcode.
	    if (type !== 'SubExpression') {
	      if (typeof string === 'string') {
	        this.pushString(string);
	      } else {
	        this.pushStackLiteral(string);
	      }
	    }
	  },

	  emptyHash: function emptyHash(omitEmpty) {
	    if (this.trackIds) {
	      this.push('{}'); // hashIds
	    }
	    if (this.stringParams) {
	      this.push('{}'); // hashContexts
	      this.push('{}'); // hashTypes
	    }
	    this.pushStackLiteral(omitEmpty ? 'undefined' : '{}');
	  },
	  pushHash: function pushHash() {
	    if (this.hash) {
	      this.hashes.push(this.hash);
	    }
	    this.hash = { values: [], types: [], contexts: [], ids: [] };
	  },
	  popHash: function popHash() {
	    var hash = this.hash;
	    this.hash = this.hashes.pop();

	    if (this.trackIds) {
	      this.push(this.objectLiteral(hash.ids));
	    }
	    if (this.stringParams) {
	      this.push(this.objectLiteral(hash.contexts));
	      this.push(this.objectLiteral(hash.types));
	    }

	    this.push(this.objectLiteral(hash.values));
	  },

	  // [pushString]
	  //
	  // On stack, before: ...
	  // On stack, after: quotedString(string), ...
	  //
	  // Push a quoted version of `string` onto the stack
	  pushString: function pushString(string) {
	    this.pushStackLiteral(this.quotedString(string));
	  },

	  // [pushLiteral]
	  //
	  // On stack, before: ...
	  // On stack, after: value, ...
	  //
	  // Pushes a value onto the stack. This operation prevents
	  // the compiler from creating a temporary variable to hold
	  // it.
	  pushLiteral: function pushLiteral(value) {
	    this.pushStackLiteral(value);
	  },

	  // [pushProgram]
	  //
	  // On stack, before: ...
	  // On stack, after: program(guid), ...
	  //
	  // Push a program expression onto the stack. This takes
	  // a compile-time guid and converts it into a runtime-accessible
	  // expression.
	  pushProgram: function pushProgram(guid) {
	    if (guid != null) {
	      this.pushStackLiteral(this.programExpression(guid));
	    } else {
	      this.pushStackLiteral(null);
	    }
	  },

	  // [registerDecorator]
	  //
	  // On stack, before: hash, program, params..., ...
	  // On stack, after: ...
	  //
	  // Pops off the decorator's parameters, invokes the decorator,
	  // and inserts the decorator into the decorators list.
	  registerDecorator: function registerDecorator(paramSize, name) {
	    var foundDecorator = this.nameLookup('decorators', name, 'decorator'),
	        options = this.setupHelperArgs(name, paramSize);

	    this.decorators.push(['fn = ', this.decorators.functionCall(foundDecorator, '', ['fn', 'props', 'container', options]), ' || fn;']);
	  },

	  // [invokeHelper]
	  //
	  // On stack, before: hash, inverse, program, params..., ...
	  // On stack, after: result of helper invocation
	  //
	  // Pops off the helper's parameters, invokes the helper,
	  // and pushes the helper's return value onto the stack.
	  //
	  // If the helper is not found, `helperMissing` is called.
	  invokeHelper: function invokeHelper(paramSize, name, isSimple) {
	    var nonHelper = this.popStack(),
	        helper = this.setupHelper(paramSize, name),
	        simple = isSimple ? [helper.name, ' || '] : '';

	    var lookup = ['('].concat(simple, nonHelper);
	    if (!this.options.strict) {
	      lookup.push(' || ', this.aliasable('helpers.helperMissing'));
	    }
	    lookup.push(')');

	    this.push(this.source.functionCall(lookup, 'call', helper.callParams));
	  },

	  // [invokeKnownHelper]
	  //
	  // On stack, before: hash, inverse, program, params..., ...
	  // On stack, after: result of helper invocation
	  //
	  // This operation is used when the helper is known to exist,
	  // so a `helperMissing` fallback is not required.
	  invokeKnownHelper: function invokeKnownHelper(paramSize, name) {
	    var helper = this.setupHelper(paramSize, name);
	    this.push(this.source.functionCall(helper.name, 'call', helper.callParams));
	  },

	  // [invokeAmbiguous]
	  //
	  // On stack, before: hash, inverse, program, params..., ...
	  // On stack, after: result of disambiguation
	  //
	  // This operation is used when an expression like `{{foo}}`
	  // is provided, but we don't know at compile-time whether it
	  // is a helper or a path.
	  //
	  // This operation emits more code than the other options,
	  // and can be avoided by passing the `knownHelpers` and
	  // `knownHelpersOnly` flags at compile-time.
	  invokeAmbiguous: function invokeAmbiguous(name, helperCall) {
	    this.useRegister('helper');

	    var nonHelper = this.popStack();

	    this.emptyHash();
	    var helper = this.setupHelper(0, name, helperCall);

	    var helperName = this.lastHelper = this.nameLookup('helpers', name, 'helper');

	    var lookup = ['(', '(helper = ', helperName, ' || ', nonHelper, ')'];
	    if (!this.options.strict) {
	      lookup[0] = '(helper = ';
	      lookup.push(' != null ? helper : ', this.aliasable('helpers.helperMissing'));
	    }

	    this.push(['(', lookup, helper.paramsInit ? ['),(', helper.paramsInit] : [], '),', '(typeof helper === ', this.aliasable('"function"'), ' ? ', this.source.functionCall('helper', 'call', helper.callParams), ' : helper))']);
	  },

	  // [invokePartial]
	  //
	  // On stack, before: context, ...
	  // On stack after: result of partial invocation
	  //
	  // This operation pops off a context, invokes a partial with that context,
	  // and pushes the result of the invocation back.
	  invokePartial: function invokePartial(isDynamic, name, indent) {
	    var params = [],
	        options = this.setupParams(name, 1, params);

	    if (isDynamic) {
	      name = this.popStack();
	      delete options.name;
	    }

	    if (indent) {
	      options.indent = JSON.stringify(indent);
	    }
	    options.helpers = 'helpers';
	    options.partials = 'partials';
	    options.decorators = 'container.decorators';

	    if (!isDynamic) {
	      params.unshift(this.nameLookup('partials', name, 'partial'));
	    } else {
	      params.unshift(name);
	    }

	    if (this.options.compat) {
	      options.depths = 'depths';
	    }
	    options = this.objectLiteral(options);
	    params.push(options);

	    this.push(this.source.functionCall('container.invokePartial', '', params));
	  },

	  // [assignToHash]
	  //
	  // On stack, before: value, ..., hash, ...
	  // On stack, after: ..., hash, ...
	  //
	  // Pops a value off the stack and assigns it to the current hash
	  assignToHash: function assignToHash(key) {
	    var value = this.popStack(),
	        context = undefined,
	        type = undefined,
	        id = undefined;

	    if (this.trackIds) {
	      id = this.popStack();
	    }
	    if (this.stringParams) {
	      type = this.popStack();
	      context = this.popStack();
	    }

	    var hash = this.hash;
	    if (context) {
	      hash.contexts[key] = context;
	    }
	    if (type) {
	      hash.types[key] = type;
	    }
	    if (id) {
	      hash.ids[key] = id;
	    }
	    hash.values[key] = value;
	  },

	  pushId: function pushId(type, name, child) {
	    if (type === 'BlockParam') {
	      this.pushStackLiteral('blockParams[' + name[0] + '].path[' + name[1] + ']' + (child ? ' + ' + JSON.stringify('.' + child) : ''));
	    } else if (type === 'PathExpression') {
	      this.pushString(name);
	    } else if (type === 'SubExpression') {
	      this.pushStackLiteral('true');
	    } else {
	      this.pushStackLiteral('null');
	    }
	  },

	  // HELPERS

	  compiler: JavaScriptCompiler,

	  compileChildren: function compileChildren(environment, options) {
	    var children = environment.children,
	        child = undefined,
	        compiler = undefined;

	    for (var i = 0, l = children.length; i < l; i++) {
	      child = children[i];
	      compiler = new this.compiler(); // eslint-disable-line new-cap

	      var index = this.matchExistingProgram(child);

	      if (index == null) {
	        this.context.programs.push(''); // Placeholder to prevent name conflicts for nested children
	        index = this.context.programs.length;
	        child.index = index;
	        child.name = 'program' + index;
	        this.context.programs[index] = compiler.compile(child, options, this.context, !this.precompile);
	        this.context.decorators[index] = compiler.decorators;
	        this.context.environments[index] = child;

	        this.useDepths = this.useDepths || compiler.useDepths;
	        this.useBlockParams = this.useBlockParams || compiler.useBlockParams;
	      } else {
	        child.index = index;
	        child.name = 'program' + index;

	        this.useDepths = this.useDepths || child.useDepths;
	        this.useBlockParams = this.useBlockParams || child.useBlockParams;
	      }
	    }
	  },
	  matchExistingProgram: function matchExistingProgram(child) {
	    for (var i = 0, len = this.context.environments.length; i < len; i++) {
	      var environment = this.context.environments[i];
	      if (environment && environment.equals(child)) {
	        return i;
	      }
	    }
	  },

	  programExpression: function programExpression(guid) {
	    var child = this.environment.children[guid],
	        programParams = [child.index, 'data', child.blockParams];

	    if (this.useBlockParams || this.useDepths) {
	      programParams.push('blockParams');
	    }
	    if (this.useDepths) {
	      programParams.push('depths');
	    }

	    return 'container.program(' + programParams.join(', ') + ')';
	  },

	  useRegister: function useRegister(name) {
	    if (!this.registers[name]) {
	      this.registers[name] = true;
	      this.registers.list.push(name);
	    }
	  },

	  push: function push(expr) {
	    if (!(expr instanceof Literal)) {
	      expr = this.source.wrap(expr);
	    }

	    this.inlineStack.push(expr);
	    return expr;
	  },

	  pushStackLiteral: function pushStackLiteral(item) {
	    this.push(new Literal(item));
	  },

	  pushSource: function pushSource(source) {
	    if (this.pendingContent) {
	      this.source.push(this.appendToBuffer(this.source.quotedString(this.pendingContent), this.pendingLocation));
	      this.pendingContent = undefined;
	    }

	    if (source) {
	      this.source.push(source);
	    }
	  },

	  replaceStack: function replaceStack(callback) {
	    var prefix = ['('],
	        stack = undefined,
	        createdStack = undefined,
	        usedLiteral = undefined;

	    /* istanbul ignore next */
	    if (!this.isInline()) {
	      throw new _exception2['default']('replaceStack on non-inline');
	    }

	    // We want to merge the inline statement into the replacement statement via ','
	    var top = this.popStack(true);

	    if (top instanceof Literal) {
	      // Literals do not need to be inlined
	      stack = [top.value];
	      prefix = ['(', stack];
	      usedLiteral = true;
	    } else {
	      // Get or create the current stack name for use by the inline
	      createdStack = true;
	      var _name = this.incrStack();

	      prefix = ['((', this.push(_name), ' = ', top, ')'];
	      stack = this.topStack();
	    }

	    var item = callback.call(this, stack);

	    if (!usedLiteral) {
	      this.popStack();
	    }
	    if (createdStack) {
	      this.stackSlot--;
	    }
	    this.push(prefix.concat(item, ')'));
	  },

	  incrStack: function incrStack() {
	    this.stackSlot++;
	    if (this.stackSlot > this.stackVars.length) {
	      this.stackVars.push('stack' + this.stackSlot);
	    }
	    return this.topStackName();
	  },
	  topStackName: function topStackName() {
	    return 'stack' + this.stackSlot;
	  },
	  flushInline: function flushInline() {
	    var inlineStack = this.inlineStack;
	    this.inlineStack = [];
	    for (var i = 0, len = inlineStack.length; i < len; i++) {
	      var entry = inlineStack[i];
	      /* istanbul ignore if */
	      if (entry instanceof Literal) {
	        this.compileStack.push(entry);
	      } else {
	        var stack = this.incrStack();
	        this.pushSource([stack, ' = ', entry, ';']);
	        this.compileStack.push(stack);
	      }
	    }
	  },
	  isInline: function isInline() {
	    return this.inlineStack.length;
	  },

	  popStack: function popStack(wrapped) {
	    var inline = this.isInline(),
	        item = (inline ? this.inlineStack : this.compileStack).pop();

	    if (!wrapped && item instanceof Literal) {
	      return item.value;
	    } else {
	      if (!inline) {
	        /* istanbul ignore next */
	        if (!this.stackSlot) {
	          throw new _exception2['default']('Invalid stack pop');
	        }
	        this.stackSlot--;
	      }
	      return item;
	    }
	  },

	  topStack: function topStack() {
	    var stack = this.isInline() ? this.inlineStack : this.compileStack,
	        item = stack[stack.length - 1];

	    /* istanbul ignore if */
	    if (item instanceof Literal) {
	      return item.value;
	    } else {
	      return item;
	    }
	  },

	  contextName: function contextName(context) {
	    if (this.useDepths && context) {
	      return 'depths[' + context + ']';
	    } else {
	      return 'depth' + context;
	    }
	  },

	  quotedString: function quotedString(str) {
	    return this.source.quotedString(str);
	  },

	  objectLiteral: function objectLiteral(obj) {
	    return this.source.objectLiteral(obj);
	  },

	  aliasable: function aliasable(name) {
	    var ret = this.aliases[name];
	    if (ret) {
	      ret.referenceCount++;
	      return ret;
	    }

	    ret = this.aliases[name] = this.source.wrap(name);
	    ret.aliasable = true;
	    ret.referenceCount = 1;

	    return ret;
	  },

	  setupHelper: function setupHelper(paramSize, name, blockHelper) {
	    var params = [],
	        paramsInit = this.setupHelperArgs(name, paramSize, params, blockHelper);
	    var foundHelper = this.nameLookup('helpers', name, 'helper'),
	        callContext = this.aliasable(this.contextName(0) + ' != null ? ' + this.contextName(0) + ' : {}');

	    return {
	      params: params,
	      paramsInit: paramsInit,
	      name: foundHelper,
	      callParams: [callContext].concat(params)
	    };
	  },

	  setupParams: function setupParams(helper, paramSize, params) {
	    var options = {},
	        contexts = [],
	        types = [],
	        ids = [],
	        objectArgs = !params,
	        param = undefined;

	    if (objectArgs) {
	      params = [];
	    }

	    options.name = this.quotedString(helper);
	    options.hash = this.popStack();

	    if (this.trackIds) {
	      options.hashIds = this.popStack();
	    }
	    if (this.stringParams) {
	      options.hashTypes = this.popStack();
	      options.hashContexts = this.popStack();
	    }

	    var inverse = this.popStack(),
	        program = this.popStack();

	    // Avoid setting fn and inverse if neither are set. This allows
	    // helpers to do a check for `if (options.fn)`
	    if (program || inverse) {
	      options.fn = program || 'container.noop';
	      options.inverse = inverse || 'container.noop';
	    }

	    // The parameters go on to the stack in order (making sure that they are evaluated in order)
	    // so we need to pop them off the stack in reverse order
	    var i = paramSize;
	    while (i--) {
	      param = this.popStack();
	      params[i] = param;

	      if (this.trackIds) {
	        ids[i] = this.popStack();
	      }
	      if (this.stringParams) {
	        types[i] = this.popStack();
	        contexts[i] = this.popStack();
	      }
	    }

	    if (objectArgs) {
	      options.args = this.source.generateArray(params);
	    }

	    if (this.trackIds) {
	      options.ids = this.source.generateArray(ids);
	    }
	    if (this.stringParams) {
	      options.types = this.source.generateArray(types);
	      options.contexts = this.source.generateArray(contexts);
	    }

	    if (this.options.data) {
	      options.data = 'data';
	    }
	    if (this.useBlockParams) {
	      options.blockParams = 'blockParams';
	    }
	    return options;
	  },

	  setupHelperArgs: function setupHelperArgs(helper, paramSize, params, useRegister) {
	    var options = this.setupParams(helper, paramSize, params);
	    options = this.objectLiteral(options);
	    if (useRegister) {
	      this.useRegister('options');
	      params.push('options');
	      return ['options=', options];
	    } else if (params) {
	      params.push(options);
	      return '';
	    } else {
	      return options;
	    }
	  }
	};

	(function () {
	  var reservedWords = ('break else new var' + ' case finally return void' + ' catch for switch while' + ' continue function this with' + ' default if throw' + ' delete in try' + ' do instanceof typeof' + ' abstract enum int short' + ' boolean export interface static' + ' byte extends long super' + ' char final native synchronized' + ' class float package throws' + ' const goto private transient' + ' debugger implements protected volatile' + ' double import public let yield await' + ' null true false').split(' ');

	  var compilerWords = JavaScriptCompiler.RESERVED_WORDS = {};

	  for (var i = 0, l = reservedWords.length; i < l; i++) {
	    compilerWords[reservedWords[i]] = true;
	  }
	})();

	JavaScriptCompiler.isValidJavaScriptVariableName = function (name) {
	  return !JavaScriptCompiler.RESERVED_WORDS[name] && /^[a-zA-Z_$][0-9a-zA-Z_$]*$/.test(name);
	};

	function strictLookup(requireTerminal, compiler, parts, type) {
	  var stack = compiler.popStack(),
	      i = 0,
	      len = parts.length;
	  if (requireTerminal) {
	    len--;
	  }

	  for (; i < len; i++) {
	    stack = compiler.nameLookup(stack, parts[i], type);
	  }

	  if (requireTerminal) {
	    return [compiler.aliasable('container.strict'), '(', stack, ', ', compiler.quotedString(parts[i]), ')'];
	  } else {
	    return stack;
	  }
	}

	exports['default'] = JavaScriptCompiler;
	module.exports = exports['default'];

/***/ },
/* 29 */
/***/ function(module, exports, __webpack_require__) {

	/* global define */
	'use strict';

	exports.__esModule = true;

	var _utils = __webpack_require__(5);

	var SourceNode = undefined;

	try {
	  /* istanbul ignore next */
	  if (false) {
	    // We don't support this in AMD environments. For these environments, we asusme that
	    // they are running on the browser and thus have no need for the source-map library.
	    var SourceMap = require('source-map');
	    SourceNode = SourceMap.SourceNode;
	  }
	} catch (err) {}
	/* NOP */

	/* istanbul ignore if: tested but not covered in istanbul due to dist build  */
	if (!SourceNode) {
	  SourceNode = function (line, column, srcFile, chunks) {
	    this.src = '';
	    if (chunks) {
	      this.add(chunks);
	    }
	  };
	  /* istanbul ignore next */
	  SourceNode.prototype = {
	    add: function add(chunks) {
	      if (_utils.isArray(chunks)) {
	        chunks = chunks.join('');
	      }
	      this.src += chunks;
	    },
	    prepend: function prepend(chunks) {
	      if (_utils.isArray(chunks)) {
	        chunks = chunks.join('');
	      }
	      this.src = chunks + this.src;
	    },
	    toStringWithSourceMap: function toStringWithSourceMap() {
	      return { code: this.toString() };
	    },
	    toString: function toString() {
	      return this.src;
	    }
	  };
	}

	function castChunk(chunk, codeGen, loc) {
	  if (_utils.isArray(chunk)) {
	    var ret = [];

	    for (var i = 0, len = chunk.length; i < len; i++) {
	      ret.push(codeGen.wrap(chunk[i], loc));
	    }
	    return ret;
	  } else if (typeof chunk === 'boolean' || typeof chunk === 'number') {
	    // Handle primitives that the SourceNode will throw up on
	    return chunk + '';
	  }
	  return chunk;
	}

	function CodeGen(srcFile) {
	  this.srcFile = srcFile;
	  this.source = [];
	}

	CodeGen.prototype = {
	  isEmpty: function isEmpty() {
	    return !this.source.length;
	  },
	  prepend: function prepend(source, loc) {
	    this.source.unshift(this.wrap(source, loc));
	  },
	  push: function push(source, loc) {
	    this.source.push(this.wrap(source, loc));
	  },

	  merge: function merge() {
	    var source = this.empty();
	    this.each(function (line) {
	      source.add(['  ', line, '\n']);
	    });
	    return source;
	  },

	  each: function each(iter) {
	    for (var i = 0, len = this.source.length; i < len; i++) {
	      iter(this.source[i]);
	    }
	  },

	  empty: function empty() {
	    var loc = this.currentLocation || { start: {} };
	    return new SourceNode(loc.start.line, loc.start.column, this.srcFile);
	  },
	  wrap: function wrap(chunk) {
	    var loc = arguments.length <= 1 || arguments[1] === undefined ? this.currentLocation || { start: {} } : arguments[1];

	    if (chunk instanceof SourceNode) {
	      return chunk;
	    }

	    chunk = castChunk(chunk, this, loc);

	    return new SourceNode(loc.start.line, loc.start.column, this.srcFile, chunk);
	  },

	  functionCall: function functionCall(fn, type, params) {
	    params = this.generateList(params);
	    return this.wrap([fn, type ? '.' + type + '(' : '(', params, ')']);
	  },

	  quotedString: function quotedString(str) {
	    return '"' + (str + '').replace(/\\/g, '\\\\').replace(/"/g, '\\"').replace(/\n/g, '\\n').replace(/\r/g, '\\r').replace(/\u2028/g, '\\u2028') // Per Ecma-262 7.3 + 7.8.4
	    .replace(/\u2029/g, '\\u2029') + '"';
	  },

	  objectLiteral: function objectLiteral(obj) {
	    var pairs = [];

	    for (var key in obj) {
	      if (obj.hasOwnProperty(key)) {
	        var value = castChunk(obj[key], this);
	        if (value !== 'undefined') {
	          pairs.push([this.quotedString(key), ':', value]);
	        }
	      }
	    }

	    var ret = this.generateList(pairs);
	    ret.prepend('{');
	    ret.add('}');
	    return ret;
	  },

	  generateList: function generateList(entries) {
	    var ret = this.empty();

	    for (var i = 0, len = entries.length; i < len; i++) {
	      if (i) {
	        ret.add(',');
	      }

	      ret.add(castChunk(entries[i], this));
	    }

	    return ret;
	  },

	  generateArray: function generateArray(entries) {
	    var ret = this.generateList(entries);
	    ret.prepend('[');
	    ret.add(']');

	    return ret;
	  }
	};

	exports['default'] = CodeGen;
	module.exports = exports['default'];

/***/ }
/******/ ])
});
;

/***/ }),
/* 27 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*!
 * jQuery Validation Plugin v1.15.1
 *
 * http://jqueryvalidation.org/
 *
 * Copyright (c) 2016 Jörn Zaefferer
 * Released under the MIT license
 */
(function( factory ) {
	if ( true ) {
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else if (typeof module === "object" && module.exports) {
		module.exports = factory( require( "jquery" ) );
	} else {
		factory( jQuery );
	}
}(function( $ ) {

$.extend( $.fn, {

	// http://jqueryvalidation.org/validate/
	validate: function( options ) {

		// If nothing is selected, return nothing; can't chain anyway
		if ( !this.length ) {
			if ( options && options.debug && window.console ) {
				console.warn( "Nothing selected, can't validate, returning nothing." );
			}
			return;
		}

		// Check if a validator for this form was already created
		var validator = $.data( this[ 0 ], "validator" );
		if ( validator ) {
			return validator;
		}

		// Add novalidate tag if HTML5.
		this.attr( "novalidate", "novalidate" );

		validator = new $.validator( options, this[ 0 ] );
		$.data( this[ 0 ], "validator", validator );

		if ( validator.settings.onsubmit ) {

			this.on( "click.validate", ":submit", function( event ) {
				if ( validator.settings.submitHandler ) {
					validator.submitButton = event.target;
				}

				// Allow suppressing validation by adding a cancel class to the submit button
				if ( $( this ).hasClass( "cancel" ) ) {
					validator.cancelSubmit = true;
				}

				// Allow suppressing validation by adding the html5 formnovalidate attribute to the submit button
				if ( $( this ).attr( "formnovalidate" ) !== undefined ) {
					validator.cancelSubmit = true;
				}
			} );

			// Validate the form on submit
			this.on( "submit.validate", function( event ) {
				if ( validator.settings.debug ) {

					// Prevent form submit to be able to see console output
					event.preventDefault();
				}
				function handle() {
					var hidden, result;
					if ( validator.settings.submitHandler ) {
						if ( validator.submitButton ) {

							// Insert a hidden input as a replacement for the missing submit button
							hidden = $( "<input type='hidden'/>" )
								.attr( "name", validator.submitButton.name )
								.val( $( validator.submitButton ).val() )
								.appendTo( validator.currentForm );
						}
						result = validator.settings.submitHandler.call( validator, validator.currentForm, event );
						if ( validator.submitButton ) {

							// And clean up afterwards; thanks to no-block-scope, hidden can be referenced
							hidden.remove();
						}
						if ( result !== undefined ) {
							return result;
						}
						return false;
					}
					return true;
				}

				// Prevent submit for invalid forms or custom submit handlers
				if ( validator.cancelSubmit ) {
					validator.cancelSubmit = false;
					return handle();
				}
				if ( validator.form() ) {
					if ( validator.pendingRequest ) {
						validator.formSubmitted = true;
						return false;
					}
					return handle();
				} else {
					validator.focusInvalid();
					return false;
				}
			} );
		}

		return validator;
	},

	// http://jqueryvalidation.org/valid/
	valid: function() {
		var valid, validator, errorList;

		if ( $( this[ 0 ] ).is( "form" ) ) {
			valid = this.validate().form();
		} else {
			errorList = [];
			valid = true;
			validator = $( this[ 0 ].form ).validate();
			this.each( function() {
				valid = validator.element( this ) && valid;
				if ( !valid ) {
					errorList = errorList.concat( validator.errorList );
				}
			} );
			validator.errorList = errorList;
		}
		return valid;
	},

	// http://jqueryvalidation.org/rules/
	rules: function( command, argument ) {
		var element = this[ 0 ],
			settings, staticRules, existingRules, data, param, filtered;

		// If nothing is selected, return empty object; can't chain anyway
		if ( element == null || element.form == null ) {
			return;
		}

		if ( command ) {
			settings = $.data( element.form, "validator" ).settings;
			staticRules = settings.rules;
			existingRules = $.validator.staticRules( element );
			switch ( command ) {
			case "add":
				$.extend( existingRules, $.validator.normalizeRule( argument ) );

				// Remove messages from rules, but allow them to be set separately
				delete existingRules.messages;
				staticRules[ element.name ] = existingRules;
				if ( argument.messages ) {
					settings.messages[ element.name ] = $.extend( settings.messages[ element.name ], argument.messages );
				}
				break;
			case "remove":
				if ( !argument ) {
					delete staticRules[ element.name ];
					return existingRules;
				}
				filtered = {};
				$.each( argument.split( /\s/ ), function( index, method ) {
					filtered[ method ] = existingRules[ method ];
					delete existingRules[ method ];
					if ( method === "required" ) {
						$( element ).removeAttr( "aria-required" );
					}
				} );
				return filtered;
			}
		}

		data = $.validator.normalizeRules(
		$.extend(
			{},
			$.validator.classRules( element ),
			$.validator.attributeRules( element ),
			$.validator.dataRules( element ),
			$.validator.staticRules( element )
		), element );

		// Make sure required is at front
		if ( data.required ) {
			param = data.required;
			delete data.required;
			data = $.extend( { required: param }, data );
			$( element ).attr( "aria-required", "true" );
		}

		// Make sure remote is at back
		if ( data.remote ) {
			param = data.remote;
			delete data.remote;
			data = $.extend( data, { remote: param } );
		}

		return data;
	}
} );

// Custom selectors
$.extend( $.expr[ ":" ], {

	// http://jqueryvalidation.org/blank-selector/
	blank: function( a ) {
		return !$.trim( "" + $( a ).val() );
	},

	// http://jqueryvalidation.org/filled-selector/
	filled: function( a ) {
		var val = $( a ).val();
		return val !== null && !!$.trim( "" + val );
	},

	// http://jqueryvalidation.org/unchecked-selector/
	unchecked: function( a ) {
		return !$( a ).prop( "checked" );
	}
} );

// Constructor for validator
$.validator = function( options, form ) {
	this.settings = $.extend( true, {}, $.validator.defaults, options );
	this.currentForm = form;
	this.init();
};

// http://jqueryvalidation.org/jQuery.validator.format/
$.validator.format = function( source, params ) {
	if ( arguments.length === 1 ) {
		return function() {
			var args = $.makeArray( arguments );
			args.unshift( source );
			return $.validator.format.apply( this, args );
		};
	}
	if ( params === undefined ) {
		return source;
	}
	if ( arguments.length > 2 && params.constructor !== Array  ) {
		params = $.makeArray( arguments ).slice( 1 );
	}
	if ( params.constructor !== Array ) {
		params = [ params ];
	}
	$.each( params, function( i, n ) {
		source = source.replace( new RegExp( "\\{" + i + "\\}", "g" ), function() {
			return n;
		} );
	} );
	return source;
};

$.extend( $.validator, {

	defaults: {
		messages: {},
		groups: {},
		rules: {},
		errorClass: "error",
		pendingClass: "pending",
		validClass: "valid",
		errorElement: "label",
		focusCleanup: false,
		focusInvalid: true,
		errorContainer: $( [] ),
		errorLabelContainer: $( [] ),
		onsubmit: true,
		ignore: ":hidden",
		ignoreTitle: false,
		onfocusin: function( element ) {
			this.lastActive = element;

			// Hide error label and remove error class on focus if enabled
			if ( this.settings.focusCleanup ) {
				if ( this.settings.unhighlight ) {
					this.settings.unhighlight.call( this, element, this.settings.errorClass, this.settings.validClass );
				}
				this.hideThese( this.errorsFor( element ) );
			}
		},
		onfocusout: function( element ) {
			if ( !this.checkable( element ) && ( element.name in this.submitted || !this.optional( element ) ) ) {
				this.element( element );
			}
		},
		onkeyup: function( element, event ) {

			// Avoid revalidate the field when pressing one of the following keys
			// Shift       => 16
			// Ctrl        => 17
			// Alt         => 18
			// Caps lock   => 20
			// End         => 35
			// Home        => 36
			// Left arrow  => 37
			// Up arrow    => 38
			// Right arrow => 39
			// Down arrow  => 40
			// Insert      => 45
			// Num lock    => 144
			// AltGr key   => 225
			var excludedKeys = [
				16, 17, 18, 20, 35, 36, 37,
				38, 39, 40, 45, 144, 225
			];

			if ( event.which === 9 && this.elementValue( element ) === "" || $.inArray( event.keyCode, excludedKeys ) !== -1 ) {
				return;
			} else if ( element.name in this.submitted || element.name in this.invalid ) {
				this.element( element );
			}
		},
		onclick: function( element ) {

			// Click on selects, radiobuttons and checkboxes
			if ( element.name in this.submitted ) {
				this.element( element );

			// Or option elements, check parent select in that case
			} else if ( element.parentNode.name in this.submitted ) {
				this.element( element.parentNode );
			}
		},
		highlight: function( element, errorClass, validClass ) {
			if ( element.type === "radio" ) {
				this.findByName( element.name ).addClass( errorClass ).removeClass( validClass );
			} else {
				$( element ).addClass( errorClass ).removeClass( validClass );
			}
		},
		unhighlight: function( element, errorClass, validClass ) {
			if ( element.type === "radio" ) {
				this.findByName( element.name ).removeClass( errorClass ).addClass( validClass );
			} else {
				$( element ).removeClass( errorClass ).addClass( validClass );
			}
		}
	},

	// http://jqueryvalidation.org/jQuery.validator.setDefaults/
	setDefaults: function( settings ) {
		$.extend( $.validator.defaults, settings );
	},

	messages: {
		required: "This field is required.",
		remote: "Please fix this field.",
		email: "Please enter a valid email address.",
		url: "Please enter a valid URL.",
		date: "Please enter a valid date.",
		dateISO: "Please enter a valid date (ISO).",
		number: "Please enter a valid number.",
		digits: "Please enter only digits.",
		equalTo: "Please enter the same value again.",
		maxlength: $.validator.format( "Please enter no more than {0} characters." ),
		minlength: $.validator.format( "Please enter at least {0} characters." ),
		rangelength: $.validator.format( "Please enter a value between {0} and {1} characters long." ),
		range: $.validator.format( "Please enter a value between {0} and {1}." ),
		max: $.validator.format( "Please enter a value less than or equal to {0}." ),
		min: $.validator.format( "Please enter a value greater than or equal to {0}." ),
		step: $.validator.format( "Please enter a multiple of {0}." )
	},

	autoCreateRanges: false,

	prototype: {

		init: function() {
			this.labelContainer = $( this.settings.errorLabelContainer );
			this.errorContext = this.labelContainer.length && this.labelContainer || $( this.currentForm );
			this.containers = $( this.settings.errorContainer ).add( this.settings.errorLabelContainer );
			this.submitted = {};
			this.valueCache = {};
			this.pendingRequest = 0;
			this.pending = {};
			this.invalid = {};
			this.reset();

			var groups = ( this.groups = {} ),
				rules;
			$.each( this.settings.groups, function( key, value ) {
				if ( typeof value === "string" ) {
					value = value.split( /\s/ );
				}
				$.each( value, function( index, name ) {
					groups[ name ] = key;
				} );
			} );
			rules = this.settings.rules;
			$.each( rules, function( key, value ) {
				rules[ key ] = $.validator.normalizeRule( value );
			} );

			function delegate( event ) {

				// Set form expando on contenteditable
				if ( !this.form && this.hasAttribute( "contenteditable" ) ) {
					this.form = $( this ).closest( "form" )[ 0 ];
				}

				var validator = $.data( this.form, "validator" ),
					eventType = "on" + event.type.replace( /^validate/, "" ),
					settings = validator.settings;
				if ( settings[ eventType ] && !$( this ).is( settings.ignore ) ) {
					settings[ eventType ].call( validator, this, event );
				}
			}

			$( this.currentForm )
				.on( "focusin.validate focusout.validate keyup.validate",
					":text, [type='password'], [type='file'], select, textarea, [type='number'], [type='search'], " +
					"[type='tel'], [type='url'], [type='email'], [type='datetime'], [type='date'], [type='month'], " +
					"[type='week'], [type='time'], [type='datetime-local'], [type='range'], [type='color'], " +
					"[type='radio'], [type='checkbox'], [contenteditable]", delegate )

				// Support: Chrome, oldIE
				// "select" is provided as event.target when clicking a option
				.on( "click.validate", "select, option, [type='radio'], [type='checkbox']", delegate );

			if ( this.settings.invalidHandler ) {
				$( this.currentForm ).on( "invalid-form.validate", this.settings.invalidHandler );
			}

			// Add aria-required to any Static/Data/Class required fields before first validation
			// Screen readers require this attribute to be present before the initial submission http://www.w3.org/TR/WCAG-TECHS/ARIA2.html
			$( this.currentForm ).find( "[required], [data-rule-required], .required" ).attr( "aria-required", "true" );
		},

		// http://jqueryvalidation.org/Validator.form/
		form: function() {
			this.checkForm();
			$.extend( this.submitted, this.errorMap );
			this.invalid = $.extend( {}, this.errorMap );
			if ( !this.valid() ) {
				$( this.currentForm ).triggerHandler( "invalid-form", [ this ] );
			}
			this.showErrors();
			return this.valid();
		},

		checkForm: function() {
			this.prepareForm();
			for ( var i = 0, elements = ( this.currentElements = this.elements() ); elements[ i ]; i++ ) {
				this.check( elements[ i ] );
			}
			return this.valid();
		},

		// http://jqueryvalidation.org/Validator.element/
		element: function( element ) {
			var cleanElement = this.clean( element ),
				checkElement = this.validationTargetFor( cleanElement ),
				v = this,
				result = true,
				rs, group;

			if ( checkElement === undefined ) {
				delete this.invalid[ cleanElement.name ];
			} else {
				this.prepareElement( checkElement );
				this.currentElements = $( checkElement );

				// If this element is grouped, then validate all group elements already
				// containing a value
				group = this.groups[ checkElement.name ];
				if ( group ) {
					$.each( this.groups, function( name, testgroup ) {
						if ( testgroup === group && name !== checkElement.name ) {
							cleanElement = v.validationTargetFor( v.clean( v.findByName( name ) ) );
							if ( cleanElement && cleanElement.name in v.invalid ) {
								v.currentElements.push( cleanElement );
								result = v.check( cleanElement ) && result;
							}
						}
					} );
				}

				rs = this.check( checkElement ) !== false;
				result = result && rs;
				if ( rs ) {
					this.invalid[ checkElement.name ] = false;
				} else {
					this.invalid[ checkElement.name ] = true;
				}

				if ( !this.numberOfInvalids() ) {

					// Hide error containers on last error
					this.toHide = this.toHide.add( this.containers );
				}
				this.showErrors();

				// Add aria-invalid status for screen readers
				$( element ).attr( "aria-invalid", !rs );
			}

			return result;
		},

		// http://jqueryvalidation.org/Validator.showErrors/
		showErrors: function( errors ) {
			if ( errors ) {
				var validator = this;

				// Add items to error list and map
				$.extend( this.errorMap, errors );
				this.errorList = $.map( this.errorMap, function( message, name ) {
					return {
						message: message,
						element: validator.findByName( name )[ 0 ]
					};
				} );

				// Remove items from success list
				this.successList = $.grep( this.successList, function( element ) {
					return !( element.name in errors );
				} );
			}
			if ( this.settings.showErrors ) {
				this.settings.showErrors.call( this, this.errorMap, this.errorList );
			} else {
				this.defaultShowErrors();
			}
		},

		// http://jqueryvalidation.org/Validator.resetForm/
		resetForm: function() {
			if ( $.fn.resetForm ) {
				$( this.currentForm ).resetForm();
			}
			this.invalid = {};
			this.submitted = {};
			this.prepareForm();
			this.hideErrors();
			var elements = this.elements()
				.removeData( "previousValue" )
				.removeAttr( "aria-invalid" );

			this.resetElements( elements );
		},

		resetElements: function( elements ) {
			var i;

			if ( this.settings.unhighlight ) {
				for ( i = 0; elements[ i ]; i++ ) {
					this.settings.unhighlight.call( this, elements[ i ],
						this.settings.errorClass, "" );
					this.findByName( elements[ i ].name ).removeClass( this.settings.validClass );
				}
			} else {
				elements
					.removeClass( this.settings.errorClass )
					.removeClass( this.settings.validClass );
			}
		},

		numberOfInvalids: function() {
			return this.objectLength( this.invalid );
		},

		objectLength: function( obj ) {
			/* jshint unused: false */
			var count = 0,
				i;
			for ( i in obj ) {
				if ( obj[ i ] ) {
					count++;
				}
			}
			return count;
		},

		hideErrors: function() {
			this.hideThese( this.toHide );
		},

		hideThese: function( errors ) {
			errors.not( this.containers ).text( "" );
			this.addWrapper( errors ).hide();
		},

		valid: function() {
			return this.size() === 0;
		},

		size: function() {
			return this.errorList.length;
		},

		focusInvalid: function() {
			if ( this.settings.focusInvalid ) {
				try {
					$( this.findLastActive() || this.errorList.length && this.errorList[ 0 ].element || [] )
					.filter( ":visible" )
					.focus()

					// Manually trigger focusin event; without it, focusin handler isn't called, findLastActive won't have anything to find
					.trigger( "focusin" );
				} catch ( e ) {

					// Ignore IE throwing errors when focusing hidden elements
				}
			}
		},

		findLastActive: function() {
			var lastActive = this.lastActive;
			return lastActive && $.grep( this.errorList, function( n ) {
				return n.element.name === lastActive.name;
			} ).length === 1 && lastActive;
		},

		elements: function() {
			var validator = this,
				rulesCache = {};

			// Select all valid inputs inside the form (no submit or reset buttons)
			return $( this.currentForm )
			.find( "input, select, textarea, [contenteditable]" )
			.not( ":submit, :reset, :image, :disabled" )
			.not( this.settings.ignore )
			.filter( function() {
				var name = this.name || $( this ).attr( "name" ); // For contenteditable
				if ( !name && validator.settings.debug && window.console ) {
					console.error( "%o has no name assigned", this );
				}

				// Set form expando on contenteditable
				if ( this.hasAttribute( "contenteditable" ) ) {
					this.form = $( this ).closest( "form" )[ 0 ];
				}

				// Select only the first element for each name, and only those with rules specified
				if ( name in rulesCache || !validator.objectLength( $( this ).rules() ) ) {
					return false;
				}

				rulesCache[ name ] = true;
				return true;
			} );
		},

		clean: function( selector ) {
			return $( selector )[ 0 ];
		},

		errors: function() {
			var errorClass = this.settings.errorClass.split( " " ).join( "." );
			return $( this.settings.errorElement + "." + errorClass, this.errorContext );
		},

		resetInternals: function() {
			this.successList = [];
			this.errorList = [];
			this.errorMap = {};
			this.toShow = $( [] );
			this.toHide = $( [] );
		},

		reset: function() {
			this.resetInternals();
			this.currentElements = $( [] );
		},

		prepareForm: function() {
			this.reset();
			this.toHide = this.errors().add( this.containers );
		},

		prepareElement: function( element ) {
			this.reset();
			this.toHide = this.errorsFor( element );
		},

		elementValue: function( element ) {
			var $element = $( element ),
				type = element.type,
				val, idx;

			if ( type === "radio" || type === "checkbox" ) {
				return this.findByName( element.name ).filter( ":checked" ).val();
			} else if ( type === "number" && typeof element.validity !== "undefined" ) {
				return element.validity.badInput ? "NaN" : $element.val();
			}

			if ( element.hasAttribute( "contenteditable" ) ) {
				val = $element.text();
			} else {
				val = $element.val();
			}

			if ( type === "file" ) {

				// Modern browser (chrome & safari)
				if ( val.substr( 0, 12 ) === "C:\\fakepath\\" ) {
					return val.substr( 12 );
				}

				// Legacy browsers
				// Unix-based path
				idx = val.lastIndexOf( "/" );
				if ( idx >= 0 ) {
					return val.substr( idx + 1 );
				}

				// Windows-based path
				idx = val.lastIndexOf( "\\" );
				if ( idx >= 0 ) {
					return val.substr( idx + 1 );
				}

				// Just the file name
				return val;
			}

			if ( typeof val === "string" ) {
				return val.replace( /\r/g, "" );
			}
			return val;
		},

		check: function( element ) {
			element = this.validationTargetFor( this.clean( element ) );

			var rules = $( element ).rules(),
				rulesCount = $.map( rules, function( n, i ) {
					return i;
				} ).length,
				dependencyMismatch = false,
				val = this.elementValue( element ),
				result, method, rule;

			// If a normalizer is defined for this element, then
			// call it to retreive the changed value instead
			// of using the real one.
			// Note that `this` in the normalizer is `element`.
			if ( typeof rules.normalizer === "function" ) {
				val = rules.normalizer.call( element, val );

				if ( typeof val !== "string" ) {
					throw new TypeError( "The normalizer should return a string value." );
				}

				// Delete the normalizer from rules to avoid treating
				// it as a pre-defined method.
				delete rules.normalizer;
			}

			for ( method in rules ) {
				rule = { method: method, parameters: rules[ method ] };
				try {
					result = $.validator.methods[ method ].call( this, val, element, rule.parameters );

					// If a method indicates that the field is optional and therefore valid,
					// don't mark it as valid when there are no other rules
					if ( result === "dependency-mismatch" && rulesCount === 1 ) {
						dependencyMismatch = true;
						continue;
					}
					dependencyMismatch = false;

					if ( result === "pending" ) {
						this.toHide = this.toHide.not( this.errorsFor( element ) );
						return;
					}

					if ( !result ) {
						this.formatAndAdd( element, rule );
						return false;
					}
				} catch ( e ) {
					if ( this.settings.debug && window.console ) {
						console.log( "Exception occurred when checking element " + element.id + ", check the '" + rule.method + "' method.", e );
					}
					if ( e instanceof TypeError ) {
						e.message += ".  Exception occurred when checking element " + element.id + ", check the '" + rule.method + "' method.";
					}

					throw e;
				}
			}
			if ( dependencyMismatch ) {
				return;
			}
			if ( this.objectLength( rules ) ) {
				this.successList.push( element );
			}
			return true;
		},

		// Return the custom message for the given element and validation method
		// specified in the element's HTML5 data attribute
		// return the generic message if present and no method specific message is present
		customDataMessage: function( element, method ) {
			return $( element ).data( "msg" + method.charAt( 0 ).toUpperCase() +
				method.substring( 1 ).toLowerCase() ) || $( element ).data( "msg" );
		},

		// Return the custom message for the given element name and validation method
		customMessage: function( name, method ) {
			var m = this.settings.messages[ name ];
			return m && ( m.constructor === String ? m : m[ method ] );
		},

		// Return the first defined argument, allowing empty strings
		findDefined: function() {
			for ( var i = 0; i < arguments.length; i++ ) {
				if ( arguments[ i ] !== undefined ) {
					return arguments[ i ];
				}
			}
			return undefined;
		},

		// The second parameter 'rule' used to be a string, and extended to an object literal
		// of the following form:
		// rule = {
		//     method: "method name",
		//     parameters: "the given method parameters"
		// }
		//
		// The old behavior still supported, kept to maintain backward compatibility with
		// old code, and will be removed in the next major release.
		defaultMessage: function( element, rule ) {
			if ( typeof rule === "string" ) {
				rule = { method: rule };
			}

			var message = this.findDefined(
					this.customMessage( element.name, rule.method ),
					this.customDataMessage( element, rule.method ),

					// 'title' is never undefined, so handle empty string as undefined
					!this.settings.ignoreTitle && element.title || undefined,
					$.validator.messages[ rule.method ],
					"<strong>Warning: No message defined for " + element.name + "</strong>"
				),
				theregex = /\$?\{(\d+)\}/g;
			if ( typeof message === "function" ) {
				message = message.call( this, rule.parameters, element );
			} else if ( theregex.test( message ) ) {
				message = $.validator.format( message.replace( theregex, "{$1}" ), rule.parameters );
			}

			return message;
		},

		formatAndAdd: function( element, rule ) {
			var message = this.defaultMessage( element, rule );

			this.errorList.push( {
				message: message,
				element: element,
				method: rule.method
			} );

			this.errorMap[ element.name ] = message;
			this.submitted[ element.name ] = message;
		},

		addWrapper: function( toToggle ) {
			if ( this.settings.wrapper ) {
				toToggle = toToggle.add( toToggle.parent( this.settings.wrapper ) );
			}
			return toToggle;
		},

		defaultShowErrors: function() {
			var i, elements, error;
			for ( i = 0; this.errorList[ i ]; i++ ) {
				error = this.errorList[ i ];
				if ( this.settings.highlight ) {
					this.settings.highlight.call( this, error.element, this.settings.errorClass, this.settings.validClass );
				}
				this.showLabel( error.element, error.message );
			}
			if ( this.errorList.length ) {
				this.toShow = this.toShow.add( this.containers );
			}
			if ( this.settings.success ) {
				for ( i = 0; this.successList[ i ]; i++ ) {
					this.showLabel( this.successList[ i ] );
				}
			}
			if ( this.settings.unhighlight ) {
				for ( i = 0, elements = this.validElements(); elements[ i ]; i++ ) {
					this.settings.unhighlight.call( this, elements[ i ], this.settings.errorClass, this.settings.validClass );
				}
			}
			this.toHide = this.toHide.not( this.toShow );
			this.hideErrors();
			this.addWrapper( this.toShow ).show();
		},

		validElements: function() {
			return this.currentElements.not( this.invalidElements() );
		},

		invalidElements: function() {
			return $( this.errorList ).map( function() {
				return this.element;
			} );
		},

		showLabel: function( element, message ) {
			var place, group, errorID, v,
				error = this.errorsFor( element ),
				elementID = this.idOrName( element ),
				describedBy = $( element ).attr( "aria-describedby" );

			if ( error.length ) {

				// Refresh error/success class
				error.removeClass( this.settings.validClass ).addClass( this.settings.errorClass );

				// Replace message on existing label
				error.html( message );
			} else {

				// Create error element
				error = $( "<" + this.settings.errorElement + ">" )
					.attr( "id", elementID + "-error" )
					.addClass( this.settings.errorClass )
					.html( message || "" );

				// Maintain reference to the element to be placed into the DOM
				place = error;
				if ( this.settings.wrapper ) {

					// Make sure the element is visible, even in IE
					// actually showing the wrapped element is handled elsewhere
					place = error.hide().show().wrap( "<" + this.settings.wrapper + "/>" ).parent();
				}
				if ( this.labelContainer.length ) {
					this.labelContainer.append( place );
				} else if ( this.settings.errorPlacement ) {
					this.settings.errorPlacement.call( this, place, $( element ) );
				} else {
					place.insertAfter( element );
				}

				// Link error back to the element
				if ( error.is( "label" ) ) {

					// If the error is a label, then associate using 'for'
					error.attr( "for", elementID );

					// If the element is not a child of an associated label, then it's necessary
					// to explicitly apply aria-describedby
				} else if ( error.parents( "label[for='" + this.escapeCssMeta( elementID ) + "']" ).length === 0 ) {
					errorID = error.attr( "id" );

					// Respect existing non-error aria-describedby
					if ( !describedBy ) {
						describedBy = errorID;
					} else if ( !describedBy.match( new RegExp( "\\b" + this.escapeCssMeta( errorID ) + "\\b" ) ) ) {

						// Add to end of list if not already present
						describedBy += " " + errorID;
					}
					$( element ).attr( "aria-describedby", describedBy );

					// If this element is grouped, then assign to all elements in the same group
					group = this.groups[ element.name ];
					if ( group ) {
						v = this;
						$.each( v.groups, function( name, testgroup ) {
							if ( testgroup === group ) {
								$( "[name='" + v.escapeCssMeta( name ) + "']", v.currentForm )
									.attr( "aria-describedby", error.attr( "id" ) );
							}
						} );
					}
				}
			}
			if ( !message && this.settings.success ) {
				error.text( "" );
				if ( typeof this.settings.success === "string" ) {
					error.addClass( this.settings.success );
				} else {
					this.settings.success( error, element );
				}
			}
			this.toShow = this.toShow.add( error );
		},

		errorsFor: function( element ) {
			var name = this.escapeCssMeta( this.idOrName( element ) ),
				describer = $( element ).attr( "aria-describedby" ),
				selector = "label[for='" + name + "'], label[for='" + name + "'] *";

			// 'aria-describedby' should directly reference the error element
			if ( describer ) {
				selector = selector + ", #" + this.escapeCssMeta( describer )
					.replace( /\s+/g, ", #" );
			}

			return this
				.errors()
				.filter( selector );
		},

		// See https://api.jquery.com/category/selectors/, for CSS
		// meta-characters that should be escaped in order to be used with JQuery
		// as a literal part of a name/id or any selector.
		escapeCssMeta: function( string ) {
			return string.replace( /([\\!"#$%&'()*+,./:;<=>?@\[\]^`{|}~])/g, "\\$1" );
		},

		idOrName: function( element ) {
			return this.groups[ element.name ] || ( this.checkable( element ) ? element.name : element.id || element.name );
		},

		validationTargetFor: function( element ) {

			// If radio/checkbox, validate first element in group instead
			if ( this.checkable( element ) ) {
				element = this.findByName( element.name );
			}

			// Always apply ignore filter
			return $( element ).not( this.settings.ignore )[ 0 ];
		},

		checkable: function( element ) {
			return ( /radio|checkbox/i ).test( element.type );
		},

		findByName: function( name ) {
			return $( this.currentForm ).find( "[name='" + this.escapeCssMeta( name ) + "']" );
		},

		getLength: function( value, element ) {
			switch ( element.nodeName.toLowerCase() ) {
			case "select":
				return $( "option:selected", element ).length;
			case "input":
				if ( this.checkable( element ) ) {
					return this.findByName( element.name ).filter( ":checked" ).length;
				}
			}
			return value.length;
		},

		depend: function( param, element ) {
			return this.dependTypes[ typeof param ] ? this.dependTypes[ typeof param ]( param, element ) : true;
		},

		dependTypes: {
			"boolean": function( param ) {
				return param;
			},
			"string": function( param, element ) {
				return !!$( param, element.form ).length;
			},
			"function": function( param, element ) {
				return param( element );
			}
		},

		optional: function( element ) {
			var val = this.elementValue( element );
			return !$.validator.methods.required.call( this, val, element ) && "dependency-mismatch";
		},

		startRequest: function( element ) {
			if ( !this.pending[ element.name ] ) {
				this.pendingRequest++;
				$( element ).addClass( this.settings.pendingClass );
				this.pending[ element.name ] = true;
			}
		},

		stopRequest: function( element, valid ) {
			this.pendingRequest--;

			// Sometimes synchronization fails, make sure pendingRequest is never < 0
			if ( this.pendingRequest < 0 ) {
				this.pendingRequest = 0;
			}
			delete this.pending[ element.name ];
			$( element ).removeClass( this.settings.pendingClass );
			if ( valid && this.pendingRequest === 0 && this.formSubmitted && this.form() ) {
				$( this.currentForm ).submit();
				this.formSubmitted = false;
			} else if ( !valid && this.pendingRequest === 0 && this.formSubmitted ) {
				$( this.currentForm ).triggerHandler( "invalid-form", [ this ] );
				this.formSubmitted = false;
			}
		},

		previousValue: function( element, method ) {
			method = typeof method === "string" && method || "remote";

			return $.data( element, "previousValue" ) || $.data( element, "previousValue", {
				old: null,
				valid: true,
				message: this.defaultMessage( element, { method: method } )
			} );
		},

		// Cleans up all forms and elements, removes validator-specific events
		destroy: function() {
			this.resetForm();

			$( this.currentForm )
				.off( ".validate" )
				.removeData( "validator" )
				.find( ".validate-equalTo-blur" )
					.off( ".validate-equalTo" )
					.removeClass( "validate-equalTo-blur" );
		}

	},

	classRuleSettings: {
		required: { required: true },
		email: { email: true },
		url: { url: true },
		date: { date: true },
		dateISO: { dateISO: true },
		number: { number: true },
		digits: { digits: true },
		creditcard: { creditcard: true }
	},

	addClassRules: function( className, rules ) {
		if ( className.constructor === String ) {
			this.classRuleSettings[ className ] = rules;
		} else {
			$.extend( this.classRuleSettings, className );
		}
	},

	classRules: function( element ) {
		var rules = {},
			classes = $( element ).attr( "class" );

		if ( classes ) {
			$.each( classes.split( " " ), function() {
				if ( this in $.validator.classRuleSettings ) {
					$.extend( rules, $.validator.classRuleSettings[ this ] );
				}
			} );
		}
		return rules;
	},

	normalizeAttributeRule: function( rules, type, method, value ) {

		// Convert the value to a number for number inputs, and for text for backwards compability
		// allows type="date" and others to be compared as strings
		if ( /min|max|step/.test( method ) && ( type === null || /number|range|text/.test( type ) ) ) {
			value = Number( value );

			// Support Opera Mini, which returns NaN for undefined minlength
			if ( isNaN( value ) ) {
				value = undefined;
			}
		}

		if ( value || value === 0 ) {
			rules[ method ] = value;
		} else if ( type === method && type !== "range" ) {

			// Exception: the jquery validate 'range' method
			// does not test for the html5 'range' type
			rules[ method ] = true;
		}
	},

	attributeRules: function( element ) {
		var rules = {},
			$element = $( element ),
			type = element.getAttribute( "type" ),
			method, value;

		for ( method in $.validator.methods ) {

			// Support for <input required> in both html5 and older browsers
			if ( method === "required" ) {
				value = element.getAttribute( method );

				// Some browsers return an empty string for the required attribute
				// and non-HTML5 browsers might have required="" markup
				if ( value === "" ) {
					value = true;
				}

				// Force non-HTML5 browsers to return bool
				value = !!value;
			} else {
				value = $element.attr( method );
			}

			this.normalizeAttributeRule( rules, type, method, value );
		}

		// 'maxlength' may be returned as -1, 2147483647 ( IE ) and 524288 ( safari ) for text inputs
		if ( rules.maxlength && /-1|2147483647|524288/.test( rules.maxlength ) ) {
			delete rules.maxlength;
		}

		return rules;
	},

	dataRules: function( element ) {
		var rules = {},
			$element = $( element ),
			type = element.getAttribute( "type" ),
			method, value;

		for ( method in $.validator.methods ) {
			value = $element.data( "rule" + method.charAt( 0 ).toUpperCase() + method.substring( 1 ).toLowerCase() );
			this.normalizeAttributeRule( rules, type, method, value );
		}
		return rules;
	},

	staticRules: function( element ) {
		var rules = {},
			validator = $.data( element.form, "validator" );

		if ( validator.settings.rules ) {
			rules = $.validator.normalizeRule( validator.settings.rules[ element.name ] ) || {};
		}
		return rules;
	},

	normalizeRules: function( rules, element ) {

		// Handle dependency check
		$.each( rules, function( prop, val ) {

			// Ignore rule when param is explicitly false, eg. required:false
			if ( val === false ) {
				delete rules[ prop ];
				return;
			}
			if ( val.param || val.depends ) {
				var keepRule = true;
				switch ( typeof val.depends ) {
				case "string":
					keepRule = !!$( val.depends, element.form ).length;
					break;
				case "function":
					keepRule = val.depends.call( element, element );
					break;
				}
				if ( keepRule ) {
					rules[ prop ] = val.param !== undefined ? val.param : true;
				} else {
					$.data( element.form, "validator" ).resetElements( $( element ) );
					delete rules[ prop ];
				}
			}
		} );

		// Evaluate parameters
		$.each( rules, function( rule, parameter ) {
			rules[ rule ] = $.isFunction( parameter ) && rule !== "normalizer" ? parameter( element ) : parameter;
		} );

		// Clean number parameters
		$.each( [ "minlength", "maxlength" ], function() {
			if ( rules[ this ] ) {
				rules[ this ] = Number( rules[ this ] );
			}
		} );
		$.each( [ "rangelength", "range" ], function() {
			var parts;
			if ( rules[ this ] ) {
				if ( $.isArray( rules[ this ] ) ) {
					rules[ this ] = [ Number( rules[ this ][ 0 ] ), Number( rules[ this ][ 1 ] ) ];
				} else if ( typeof rules[ this ] === "string" ) {
					parts = rules[ this ].replace( /[\[\]]/g, "" ).split( /[\s,]+/ );
					rules[ this ] = [ Number( parts[ 0 ] ), Number( parts[ 1 ] ) ];
				}
			}
		} );

		if ( $.validator.autoCreateRanges ) {

			// Auto-create ranges
			if ( rules.min != null && rules.max != null ) {
				rules.range = [ rules.min, rules.max ];
				delete rules.min;
				delete rules.max;
			}
			if ( rules.minlength != null && rules.maxlength != null ) {
				rules.rangelength = [ rules.minlength, rules.maxlength ];
				delete rules.minlength;
				delete rules.maxlength;
			}
		}

		return rules;
	},

	// Converts a simple string to a {string: true} rule, e.g., "required" to {required:true}
	normalizeRule: function( data ) {
		if ( typeof data === "string" ) {
			var transformed = {};
			$.each( data.split( /\s/ ), function() {
				transformed[ this ] = true;
			} );
			data = transformed;
		}
		return data;
	},

	// http://jqueryvalidation.org/jQuery.validator.addMethod/
	addMethod: function( name, method, message ) {
		$.validator.methods[ name ] = method;
		$.validator.messages[ name ] = message !== undefined ? message : $.validator.messages[ name ];
		if ( method.length < 3 ) {
			$.validator.addClassRules( name, $.validator.normalizeRule( name ) );
		}
	},

	// http://jqueryvalidation.org/jQuery.validator.methods/
	methods: {

		// http://jqueryvalidation.org/required-method/
		required: function( value, element, param ) {

			// Check if dependency is met
			if ( !this.depend( param, element ) ) {
				return "dependency-mismatch";
			}
			if ( element.nodeName.toLowerCase() === "select" ) {

				// Could be an array for select-multiple or a string, both are fine this way
				var val = $( element ).val();
				return val && val.length > 0;
			}
			if ( this.checkable( element ) ) {
				return this.getLength( value, element ) > 0;
			}
			return value.length > 0;
		},

		// http://jqueryvalidation.org/email-method/
		email: function( value, element ) {

			// From https://html.spec.whatwg.org/multipage/forms.html#valid-e-mail-address
			// Retrieved 2014-01-14
			// If you have a problem with this implementation, report a bug against the above spec
			// Or use custom methods to implement your own email validation
			return this.optional( element ) || /^[a-zA-Z0-9.!#$%&'*+\/=?^_`{|}~-]+@[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?(?:\.[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?)*$/.test( value );
		},

		// http://jqueryvalidation.org/url-method/
		url: function( value, element ) {

			// Copyright (c) 2010-2013 Diego Perini, MIT licensed
			// https://gist.github.com/dperini/729294
			// see also https://mathiasbynens.be/demo/url-regex
			// modified to allow protocol-relative URLs
			return this.optional( element ) || /^(?:(?:(?:https?|ftp):)?\/\/)(?:\S+(?::\S*)?@)?(?:(?!(?:10|127)(?:\.\d{1,3}){3})(?!(?:169\.254|192\.168)(?:\.\d{1,3}){2})(?!172\.(?:1[6-9]|2\d|3[0-1])(?:\.\d{1,3}){2})(?:[1-9]\d?|1\d\d|2[01]\d|22[0-3])(?:\.(?:1?\d{1,2}|2[0-4]\d|25[0-5])){2}(?:\.(?:[1-9]\d?|1\d\d|2[0-4]\d|25[0-4]))|(?:(?:[a-z\u00a1-\uffff0-9]-*)*[a-z\u00a1-\uffff0-9]+)(?:\.(?:[a-z\u00a1-\uffff0-9]-*)*[a-z\u00a1-\uffff0-9]+)*(?:\.(?:[a-z\u00a1-\uffff]{2,})).?)(?::\d{2,5})?(?:[/?#]\S*)?$/i.test( value );
		},

		// http://jqueryvalidation.org/date-method/
		date: function( value, element ) {
			return this.optional( element ) || !/Invalid|NaN/.test( new Date( value ).toString() );
		},

		// http://jqueryvalidation.org/dateISO-method/
		dateISO: function( value, element ) {
			return this.optional( element ) || /^\d{4}[\/\-](0?[1-9]|1[012])[\/\-](0?[1-9]|[12][0-9]|3[01])$/.test( value );
		},

		// http://jqueryvalidation.org/number-method/
		number: function( value, element ) {
			return this.optional( element ) || /^(?:-?\d+|-?\d{1,3}(?:,\d{3})+)?(?:\.\d+)?$/.test( value );
		},

		// http://jqueryvalidation.org/digits-method/
		digits: function( value, element ) {
			return this.optional( element ) || /^\d+$/.test( value );
		},

		// http://jqueryvalidation.org/minlength-method/
		minlength: function( value, element, param ) {
			var length = $.isArray( value ) ? value.length : this.getLength( value, element );
			return this.optional( element ) || length >= param;
		},

		// http://jqueryvalidation.org/maxlength-method/
		maxlength: function( value, element, param ) {
			var length = $.isArray( value ) ? value.length : this.getLength( value, element );
			return this.optional( element ) || length <= param;
		},

		// http://jqueryvalidation.org/rangelength-method/
		rangelength: function( value, element, param ) {
			var length = $.isArray( value ) ? value.length : this.getLength( value, element );
			return this.optional( element ) || ( length >= param[ 0 ] && length <= param[ 1 ] );
		},

		// http://jqueryvalidation.org/min-method/
		min: function( value, element, param ) {
			return this.optional( element ) || value >= param;
		},

		// http://jqueryvalidation.org/max-method/
		max: function( value, element, param ) {
			return this.optional( element ) || value <= param;
		},

		// http://jqueryvalidation.org/range-method/
		range: function( value, element, param ) {
			return this.optional( element ) || ( value >= param[ 0 ] && value <= param[ 1 ] );
		},

		// http://jqueryvalidation.org/step-method/
		step: function( value, element, param ) {
			var type = $( element ).attr( "type" ),
				errorMessage = "Step attribute on input type " + type + " is not supported.",
				supportedTypes = [ "text", "number", "range" ],
				re = new RegExp( "\\b" + type + "\\b" ),
				notSupported = type && !re.test( supportedTypes.join() ),
				decimalPlaces = function( num ) {
					var match = ( "" + num ).match( /(?:\.(\d+))?$/ );
					if ( !match ) {
						return 0;
					}

					// Number of digits right of decimal point.
					return match[ 1 ] ? match[ 1 ].length : 0;
				},
				toInt = function( num ) {
					return Math.round( num * Math.pow( 10, decimals ) );
				},
				valid = true,
				decimals;

			// Works only for text, number and range input types
			// TODO find a way to support input types date, datetime, datetime-local, month, time and week
			if ( notSupported ) {
				throw new Error( errorMessage );
			}

			decimals = decimalPlaces( param );

			// Value can't have too many decimals
			if ( decimalPlaces( value ) > decimals || toInt( value ) % toInt( param ) !== 0 ) {
				valid = false;
			}

			return this.optional( element ) || valid;
		},

		// http://jqueryvalidation.org/equalTo-method/
		equalTo: function( value, element, param ) {

			// Bind to the blur event of the target in order to revalidate whenever the target field is updated
			var target = $( param );
			if ( this.settings.onfocusout && target.not( ".validate-equalTo-blur" ).length ) {
				target.addClass( "validate-equalTo-blur" ).on( "blur.validate-equalTo", function() {
					$( element ).valid();
				} );
			}
			return value === target.val();
		},

		// http://jqueryvalidation.org/remote-method/
		remote: function( value, element, param, method ) {
			if ( this.optional( element ) ) {
				return "dependency-mismatch";
			}

			method = typeof method === "string" && method || "remote";

			var previous = this.previousValue( element, method ),
				validator, data, optionDataString;

			if ( !this.settings.messages[ element.name ] ) {
				this.settings.messages[ element.name ] = {};
			}
			previous.originalMessage = previous.originalMessage || this.settings.messages[ element.name ][ method ];
			this.settings.messages[ element.name ][ method ] = previous.message;

			param = typeof param === "string" && { url: param } || param;
			optionDataString = $.param( $.extend( { data: value }, param.data ) );
			if ( previous.old === optionDataString ) {
				return previous.valid;
			}

			previous.old = optionDataString;
			validator = this;
			this.startRequest( element );
			data = {};
			data[ element.name ] = value;
			$.ajax( $.extend( true, {
				mode: "abort",
				port: "validate" + element.name,
				dataType: "json",
				data: data,
				context: validator.currentForm,
				success: function( response ) {
					var valid = response === true || response === "true",
						errors, message, submitted;

					validator.settings.messages[ element.name ][ method ] = previous.originalMessage;
					if ( valid ) {
						submitted = validator.formSubmitted;
						validator.resetInternals();
						validator.toHide = validator.errorsFor( element );
						validator.formSubmitted = submitted;
						validator.successList.push( element );
						validator.invalid[ element.name ] = false;
						validator.showErrors();
					} else {
						errors = {};
						message = response || validator.defaultMessage( element, { method: method, parameters: value } );
						errors[ element.name ] = previous.message = message;
						validator.invalid[ element.name ] = true;
						validator.showErrors( errors );
					}
					previous.valid = valid;
					validator.stopRequest( element, valid );
				}
			}, param ) );
			return "pending";
		}
	}

} );

// Ajax mode: abort
// usage: $.ajax({ mode: "abort"[, port: "uniqueport"]});
// if mode:"abort" is used, the previous request on that port (port can be undefined) is aborted via XMLHttpRequest.abort()

var pendingRequests = {},
	ajax;

// Use a prefilter if available (1.5+)
if ( $.ajaxPrefilter ) {
	$.ajaxPrefilter( function( settings, _, xhr ) {
		var port = settings.port;
		if ( settings.mode === "abort" ) {
			if ( pendingRequests[ port ] ) {
				pendingRequests[ port ].abort();
			}
			pendingRequests[ port ] = xhr;
		}
	} );
} else {

	// Proxy ajax
	ajax = $.ajax;
	$.ajax = function( settings ) {
		var mode = ( "mode" in settings ? settings : $.ajaxSettings ).mode,
			port = ( "port" in settings ? settings : $.ajaxSettings ).port;
		if ( mode === "abort" ) {
			if ( pendingRequests[ port ] ) {
				pendingRequests[ port ].abort();
			}
			pendingRequests[ port ] = ajax.apply( this, arguments );
			return pendingRequests[ port ];
		}
		return ajax.apply( this, arguments );
	};
}

}));

/***/ }),
/* 28 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Afrikaans [af]
//! author : Werner Mollentze : https://github.com/wernerm

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var af = moment.defineLocale('af', {
    months : 'Januarie_Februarie_Maart_April_Mei_Junie_Julie_Augustus_September_Oktober_November_Desember'.split('_'),
    monthsShort : 'Jan_Feb_Mrt_Apr_Mei_Jun_Jul_Aug_Sep_Okt_Nov_Des'.split('_'),
    weekdays : 'Sondag_Maandag_Dinsdag_Woensdag_Donderdag_Vrydag_Saterdag'.split('_'),
    weekdaysShort : 'Son_Maa_Din_Woe_Don_Vry_Sat'.split('_'),
    weekdaysMin : 'So_Ma_Di_Wo_Do_Vr_Sa'.split('_'),
    meridiemParse: /vm|nm/i,
    isPM : function (input) {
        return /^nm$/i.test(input);
    },
    meridiem : function (hours, minutes, isLower) {
        if (hours < 12) {
            return isLower ? 'vm' : 'VM';
        } else {
            return isLower ? 'nm' : 'NM';
        }
    },
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY HH:mm',
        LLLL : 'dddd, D MMMM YYYY HH:mm'
    },
    calendar : {
        sameDay : '[Vandag om] LT',
        nextDay : '[Môre om] LT',
        nextWeek : 'dddd [om] LT',
        lastDay : '[Gister om] LT',
        lastWeek : '[Laas] dddd [om] LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : 'oor %s',
        past : '%s gelede',
        s : '\'n paar sekondes',
        ss : '%d sekondes',
        m : '\'n minuut',
        mm : '%d minute',
        h : '\'n uur',
        hh : '%d ure',
        d : '\'n dag',
        dd : '%d dae',
        M : '\'n maand',
        MM : '%d maande',
        y : '\'n jaar',
        yy : '%d jaar'
    },
    dayOfMonthOrdinalParse: /\d{1,2}(ste|de)/,
    ordinal : function (number) {
        return number + ((number === 1 || number === 8 || number >= 20) ? 'ste' : 'de'); // Thanks to Joris Röling : https://github.com/jjupiter
    },
    week : {
        dow : 1, // Maandag is die eerste dag van die week.
        doy : 4  // Die week wat die 4de Januarie bevat is die eerste week van die jaar.
    }
});

return af;

})));


/***/ }),
/* 29 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Arabic (Algeria) [ar-dz]
//! author : Noureddine LOUAHEDJ : https://github.com/noureddineme

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var arDz = moment.defineLocale('ar-dz', {
    months : 'جانفي_فيفري_مارس_أفريل_ماي_جوان_جويلية_أوت_سبتمبر_أكتوبر_نوفمبر_ديسمبر'.split('_'),
    monthsShort : 'جانفي_فيفري_مارس_أفريل_ماي_جوان_جويلية_أوت_سبتمبر_أكتوبر_نوفمبر_ديسمبر'.split('_'),
    weekdays : 'الأحد_الإثنين_الثلاثاء_الأربعاء_الخميس_الجمعة_السبت'.split('_'),
    weekdaysShort : 'احد_اثنين_ثلاثاء_اربعاء_خميس_جمعة_سبت'.split('_'),
    weekdaysMin : 'أح_إث_ثلا_أر_خم_جم_سب'.split('_'),
    weekdaysParseExact : true,
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY HH:mm',
        LLLL : 'dddd D MMMM YYYY HH:mm'
    },
    calendar : {
        sameDay: '[اليوم على الساعة] LT',
        nextDay: '[غدا على الساعة] LT',
        nextWeek: 'dddd [على الساعة] LT',
        lastDay: '[أمس على الساعة] LT',
        lastWeek: 'dddd [على الساعة] LT',
        sameElse: 'L'
    },
    relativeTime : {
        future : 'في %s',
        past : 'منذ %s',
        s : 'ثوان',
        ss : '%d ثانية',
        m : 'دقيقة',
        mm : '%d دقائق',
        h : 'ساعة',
        hh : '%d ساعات',
        d : 'يوم',
        dd : '%d أيام',
        M : 'شهر',
        MM : '%d أشهر',
        y : 'سنة',
        yy : '%d سنوات'
    },
    week : {
        dow : 0, // Sunday is the first day of the week.
        doy : 4  // The week that contains Jan 1st is the first week of the year.
    }
});

return arDz;

})));


/***/ }),
/* 30 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Arabic (Kuwait) [ar-kw]
//! author : Nusret Parlak: https://github.com/nusretparlak

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var arKw = moment.defineLocale('ar-kw', {
    months : 'يناير_فبراير_مارس_أبريل_ماي_يونيو_يوليوز_غشت_شتنبر_أكتوبر_نونبر_دجنبر'.split('_'),
    monthsShort : 'يناير_فبراير_مارس_أبريل_ماي_يونيو_يوليوز_غشت_شتنبر_أكتوبر_نونبر_دجنبر'.split('_'),
    weekdays : 'الأحد_الإتنين_الثلاثاء_الأربعاء_الخميس_الجمعة_السبت'.split('_'),
    weekdaysShort : 'احد_اتنين_ثلاثاء_اربعاء_خميس_جمعة_سبت'.split('_'),
    weekdaysMin : 'ح_ن_ث_ر_خ_ج_س'.split('_'),
    weekdaysParseExact : true,
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY HH:mm',
        LLLL : 'dddd D MMMM YYYY HH:mm'
    },
    calendar : {
        sameDay: '[اليوم على الساعة] LT',
        nextDay: '[غدا على الساعة] LT',
        nextWeek: 'dddd [على الساعة] LT',
        lastDay: '[أمس على الساعة] LT',
        lastWeek: 'dddd [على الساعة] LT',
        sameElse: 'L'
    },
    relativeTime : {
        future : 'في %s',
        past : 'منذ %s',
        s : 'ثوان',
        ss : '%d ثانية',
        m : 'دقيقة',
        mm : '%d دقائق',
        h : 'ساعة',
        hh : '%d ساعات',
        d : 'يوم',
        dd : '%d أيام',
        M : 'شهر',
        MM : '%d أشهر',
        y : 'سنة',
        yy : '%d سنوات'
    },
    week : {
        dow : 0, // Sunday is the first day of the week.
        doy : 12  // The week that contains Jan 1st is the first week of the year.
    }
});

return arKw;

})));


/***/ }),
/* 31 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Arabic (Lybia) [ar-ly]
//! author : Ali Hmer: https://github.com/kikoanis

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var symbolMap = {
    '1': '1',
    '2': '2',
    '3': '3',
    '4': '4',
    '5': '5',
    '6': '6',
    '7': '7',
    '8': '8',
    '9': '9',
    '0': '0'
};
var pluralForm = function (n) {
    return n === 0 ? 0 : n === 1 ? 1 : n === 2 ? 2 : n % 100 >= 3 && n % 100 <= 10 ? 3 : n % 100 >= 11 ? 4 : 5;
};
var plurals = {
    s : ['أقل من ثانية', 'ثانية واحدة', ['ثانيتان', 'ثانيتين'], '%d ثوان', '%d ثانية', '%d ثانية'],
    m : ['أقل من دقيقة', 'دقيقة واحدة', ['دقيقتان', 'دقيقتين'], '%d دقائق', '%d دقيقة', '%d دقيقة'],
    h : ['أقل من ساعة', 'ساعة واحدة', ['ساعتان', 'ساعتين'], '%d ساعات', '%d ساعة', '%d ساعة'],
    d : ['أقل من يوم', 'يوم واحد', ['يومان', 'يومين'], '%d أيام', '%d يومًا', '%d يوم'],
    M : ['أقل من شهر', 'شهر واحد', ['شهران', 'شهرين'], '%d أشهر', '%d شهرا', '%d شهر'],
    y : ['أقل من عام', 'عام واحد', ['عامان', 'عامين'], '%d أعوام', '%d عامًا', '%d عام']
};
var pluralize = function (u) {
    return function (number, withoutSuffix, string, isFuture) {
        var f = pluralForm(number),
            str = plurals[u][pluralForm(number)];
        if (f === 2) {
            str = str[withoutSuffix ? 0 : 1];
        }
        return str.replace(/%d/i, number);
    };
};
var months = [
    'يناير',
    'فبراير',
    'مارس',
    'أبريل',
    'مايو',
    'يونيو',
    'يوليو',
    'أغسطس',
    'سبتمبر',
    'أكتوبر',
    'نوفمبر',
    'ديسمبر'
];

var arLy = moment.defineLocale('ar-ly', {
    months : months,
    monthsShort : months,
    weekdays : 'الأحد_الإثنين_الثلاثاء_الأربعاء_الخميس_الجمعة_السبت'.split('_'),
    weekdaysShort : 'أحد_إثنين_ثلاثاء_أربعاء_خميس_جمعة_سبت'.split('_'),
    weekdaysMin : 'ح_ن_ث_ر_خ_ج_س'.split('_'),
    weekdaysParseExact : true,
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'D/\u200FM/\u200FYYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY HH:mm',
        LLLL : 'dddd D MMMM YYYY HH:mm'
    },
    meridiemParse: /ص|م/,
    isPM : function (input) {
        return 'م' === input;
    },
    meridiem : function (hour, minute, isLower) {
        if (hour < 12) {
            return 'ص';
        } else {
            return 'م';
        }
    },
    calendar : {
        sameDay: '[اليوم عند الساعة] LT',
        nextDay: '[غدًا عند الساعة] LT',
        nextWeek: 'dddd [عند الساعة] LT',
        lastDay: '[أمس عند الساعة] LT',
        lastWeek: 'dddd [عند الساعة] LT',
        sameElse: 'L'
    },
    relativeTime : {
        future : 'بعد %s',
        past : 'منذ %s',
        s : pluralize('s'),
        ss : pluralize('s'),
        m : pluralize('m'),
        mm : pluralize('m'),
        h : pluralize('h'),
        hh : pluralize('h'),
        d : pluralize('d'),
        dd : pluralize('d'),
        M : pluralize('M'),
        MM : pluralize('M'),
        y : pluralize('y'),
        yy : pluralize('y')
    },
    preparse: function (string) {
        return string.replace(/،/g, ',');
    },
    postformat: function (string) {
        return string.replace(/\d/g, function (match) {
            return symbolMap[match];
        }).replace(/,/g, '،');
    },
    week : {
        dow : 6, // Saturday is the first day of the week.
        doy : 12  // The week that contains Jan 1st is the first week of the year.
    }
});

return arLy;

})));


/***/ }),
/* 32 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Arabic (Morocco) [ar-ma]
//! author : ElFadili Yassine : https://github.com/ElFadiliY
//! author : Abdel Said : https://github.com/abdelsaid

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var arMa = moment.defineLocale('ar-ma', {
    months : 'يناير_فبراير_مارس_أبريل_ماي_يونيو_يوليوز_غشت_شتنبر_أكتوبر_نونبر_دجنبر'.split('_'),
    monthsShort : 'يناير_فبراير_مارس_أبريل_ماي_يونيو_يوليوز_غشت_شتنبر_أكتوبر_نونبر_دجنبر'.split('_'),
    weekdays : 'الأحد_الإتنين_الثلاثاء_الأربعاء_الخميس_الجمعة_السبت'.split('_'),
    weekdaysShort : 'احد_اتنين_ثلاثاء_اربعاء_خميس_جمعة_سبت'.split('_'),
    weekdaysMin : 'ح_ن_ث_ر_خ_ج_س'.split('_'),
    weekdaysParseExact : true,
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY HH:mm',
        LLLL : 'dddd D MMMM YYYY HH:mm'
    },
    calendar : {
        sameDay: '[اليوم على الساعة] LT',
        nextDay: '[غدا على الساعة] LT',
        nextWeek: 'dddd [على الساعة] LT',
        lastDay: '[أمس على الساعة] LT',
        lastWeek: 'dddd [على الساعة] LT',
        sameElse: 'L'
    },
    relativeTime : {
        future : 'في %s',
        past : 'منذ %s',
        s : 'ثوان',
        ss : '%d ثانية',
        m : 'دقيقة',
        mm : '%d دقائق',
        h : 'ساعة',
        hh : '%d ساعات',
        d : 'يوم',
        dd : '%d أيام',
        M : 'شهر',
        MM : '%d أشهر',
        y : 'سنة',
        yy : '%d سنوات'
    },
    week : {
        dow : 6, // Saturday is the first day of the week.
        doy : 12  // The week that contains Jan 1st is the first week of the year.
    }
});

return arMa;

})));


/***/ }),
/* 33 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Arabic (Saudi Arabia) [ar-sa]
//! author : Suhail Alkowaileet : https://github.com/xsoh

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var symbolMap = {
    '1': '١',
    '2': '٢',
    '3': '٣',
    '4': '٤',
    '5': '٥',
    '6': '٦',
    '7': '٧',
    '8': '٨',
    '9': '٩',
    '0': '٠'
};
var numberMap = {
    '١': '1',
    '٢': '2',
    '٣': '3',
    '٤': '4',
    '٥': '5',
    '٦': '6',
    '٧': '7',
    '٨': '8',
    '٩': '9',
    '٠': '0'
};

var arSa = moment.defineLocale('ar-sa', {
    months : 'يناير_فبراير_مارس_أبريل_مايو_يونيو_يوليو_أغسطس_سبتمبر_أكتوبر_نوفمبر_ديسمبر'.split('_'),
    monthsShort : 'يناير_فبراير_مارس_أبريل_مايو_يونيو_يوليو_أغسطس_سبتمبر_أكتوبر_نوفمبر_ديسمبر'.split('_'),
    weekdays : 'الأحد_الإثنين_الثلاثاء_الأربعاء_الخميس_الجمعة_السبت'.split('_'),
    weekdaysShort : 'أحد_إثنين_ثلاثاء_أربعاء_خميس_جمعة_سبت'.split('_'),
    weekdaysMin : 'ح_ن_ث_ر_خ_ج_س'.split('_'),
    weekdaysParseExact : true,
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY HH:mm',
        LLLL : 'dddd D MMMM YYYY HH:mm'
    },
    meridiemParse: /ص|م/,
    isPM : function (input) {
        return 'م' === input;
    },
    meridiem : function (hour, minute, isLower) {
        if (hour < 12) {
            return 'ص';
        } else {
            return 'م';
        }
    },
    calendar : {
        sameDay: '[اليوم على الساعة] LT',
        nextDay: '[غدا على الساعة] LT',
        nextWeek: 'dddd [على الساعة] LT',
        lastDay: '[أمس على الساعة] LT',
        lastWeek: 'dddd [على الساعة] LT',
        sameElse: 'L'
    },
    relativeTime : {
        future : 'في %s',
        past : 'منذ %s',
        s : 'ثوان',
        ss : '%d ثانية',
        m : 'دقيقة',
        mm : '%d دقائق',
        h : 'ساعة',
        hh : '%d ساعات',
        d : 'يوم',
        dd : '%d أيام',
        M : 'شهر',
        MM : '%d أشهر',
        y : 'سنة',
        yy : '%d سنوات'
    },
    preparse: function (string) {
        return string.replace(/[١٢٣٤٥٦٧٨٩٠]/g, function (match) {
            return numberMap[match];
        }).replace(/،/g, ',');
    },
    postformat: function (string) {
        return string.replace(/\d/g, function (match) {
            return symbolMap[match];
        }).replace(/,/g, '،');
    },
    week : {
        dow : 0, // Sunday is the first day of the week.
        doy : 6  // The week that contains Jan 1st is the first week of the year.
    }
});

return arSa;

})));


/***/ }),
/* 34 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale  :  Arabic (Tunisia) [ar-tn]
//! author : Nader Toukabri : https://github.com/naderio

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var arTn = moment.defineLocale('ar-tn', {
    months: 'جانفي_فيفري_مارس_أفريل_ماي_جوان_جويلية_أوت_سبتمبر_أكتوبر_نوفمبر_ديسمبر'.split('_'),
    monthsShort: 'جانفي_فيفري_مارس_أفريل_ماي_جوان_جويلية_أوت_سبتمبر_أكتوبر_نوفمبر_ديسمبر'.split('_'),
    weekdays: 'الأحد_الإثنين_الثلاثاء_الأربعاء_الخميس_الجمعة_السبت'.split('_'),
    weekdaysShort: 'أحد_إثنين_ثلاثاء_أربعاء_خميس_جمعة_سبت'.split('_'),
    weekdaysMin: 'ح_ن_ث_ر_خ_ج_س'.split('_'),
    weekdaysParseExact : true,
    longDateFormat: {
        LT: 'HH:mm',
        LTS: 'HH:mm:ss',
        L: 'DD/MM/YYYY',
        LL: 'D MMMM YYYY',
        LLL: 'D MMMM YYYY HH:mm',
        LLLL: 'dddd D MMMM YYYY HH:mm'
    },
    calendar: {
        sameDay: '[اليوم على الساعة] LT',
        nextDay: '[غدا على الساعة] LT',
        nextWeek: 'dddd [على الساعة] LT',
        lastDay: '[أمس على الساعة] LT',
        lastWeek: 'dddd [على الساعة] LT',
        sameElse: 'L'
    },
    relativeTime: {
        future: 'في %s',
        past: 'منذ %s',
        s: 'ثوان',
        ss : '%d ثانية',
        m: 'دقيقة',
        mm: '%d دقائق',
        h: 'ساعة',
        hh: '%d ساعات',
        d: 'يوم',
        dd: '%d أيام',
        M: 'شهر',
        MM: '%d أشهر',
        y: 'سنة',
        yy: '%d سنوات'
    },
    week: {
        dow: 1, // Monday is the first day of the week.
        doy: 4 // The week that contains Jan 4th is the first week of the year.
    }
});

return arTn;

})));


/***/ }),
/* 35 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Arabic [ar]
//! author : Abdel Said: https://github.com/abdelsaid
//! author : Ahmed Elkhatib
//! author : forabi https://github.com/forabi

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var symbolMap = {
    '1': '١',
    '2': '٢',
    '3': '٣',
    '4': '٤',
    '5': '٥',
    '6': '٦',
    '7': '٧',
    '8': '٨',
    '9': '٩',
    '0': '٠'
};
var numberMap = {
    '١': '1',
    '٢': '2',
    '٣': '3',
    '٤': '4',
    '٥': '5',
    '٦': '6',
    '٧': '7',
    '٨': '8',
    '٩': '9',
    '٠': '0'
};
var pluralForm = function (n) {
    return n === 0 ? 0 : n === 1 ? 1 : n === 2 ? 2 : n % 100 >= 3 && n % 100 <= 10 ? 3 : n % 100 >= 11 ? 4 : 5;
};
var plurals = {
    s : ['أقل من ثانية', 'ثانية واحدة', ['ثانيتان', 'ثانيتين'], '%d ثوان', '%d ثانية', '%d ثانية'],
    m : ['أقل من دقيقة', 'دقيقة واحدة', ['دقيقتان', 'دقيقتين'], '%d دقائق', '%d دقيقة', '%d دقيقة'],
    h : ['أقل من ساعة', 'ساعة واحدة', ['ساعتان', 'ساعتين'], '%d ساعات', '%d ساعة', '%d ساعة'],
    d : ['أقل من يوم', 'يوم واحد', ['يومان', 'يومين'], '%d أيام', '%d يومًا', '%d يوم'],
    M : ['أقل من شهر', 'شهر واحد', ['شهران', 'شهرين'], '%d أشهر', '%d شهرا', '%d شهر'],
    y : ['أقل من عام', 'عام واحد', ['عامان', 'عامين'], '%d أعوام', '%d عامًا', '%d عام']
};
var pluralize = function (u) {
    return function (number, withoutSuffix, string, isFuture) {
        var f = pluralForm(number),
            str = plurals[u][pluralForm(number)];
        if (f === 2) {
            str = str[withoutSuffix ? 0 : 1];
        }
        return str.replace(/%d/i, number);
    };
};
var months = [
    'يناير',
    'فبراير',
    'مارس',
    'أبريل',
    'مايو',
    'يونيو',
    'يوليو',
    'أغسطس',
    'سبتمبر',
    'أكتوبر',
    'نوفمبر',
    'ديسمبر'
];

var ar = moment.defineLocale('ar', {
    months : months,
    monthsShort : months,
    weekdays : 'الأحد_الإثنين_الثلاثاء_الأربعاء_الخميس_الجمعة_السبت'.split('_'),
    weekdaysShort : 'أحد_إثنين_ثلاثاء_أربعاء_خميس_جمعة_سبت'.split('_'),
    weekdaysMin : 'ح_ن_ث_ر_خ_ج_س'.split('_'),
    weekdaysParseExact : true,
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'D/\u200FM/\u200FYYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY HH:mm',
        LLLL : 'dddd D MMMM YYYY HH:mm'
    },
    meridiemParse: /ص|م/,
    isPM : function (input) {
        return 'م' === input;
    },
    meridiem : function (hour, minute, isLower) {
        if (hour < 12) {
            return 'ص';
        } else {
            return 'م';
        }
    },
    calendar : {
        sameDay: '[اليوم عند الساعة] LT',
        nextDay: '[غدًا عند الساعة] LT',
        nextWeek: 'dddd [عند الساعة] LT',
        lastDay: '[أمس عند الساعة] LT',
        lastWeek: 'dddd [عند الساعة] LT',
        sameElse: 'L'
    },
    relativeTime : {
        future : 'بعد %s',
        past : 'منذ %s',
        s : pluralize('s'),
        ss : pluralize('s'),
        m : pluralize('m'),
        mm : pluralize('m'),
        h : pluralize('h'),
        hh : pluralize('h'),
        d : pluralize('d'),
        dd : pluralize('d'),
        M : pluralize('M'),
        MM : pluralize('M'),
        y : pluralize('y'),
        yy : pluralize('y')
    },
    preparse: function (string) {
        return string.replace(/[١٢٣٤٥٦٧٨٩٠]/g, function (match) {
            return numberMap[match];
        }).replace(/،/g, ',');
    },
    postformat: function (string) {
        return string.replace(/\d/g, function (match) {
            return symbolMap[match];
        }).replace(/,/g, '،');
    },
    week : {
        dow : 6, // Saturday is the first day of the week.
        doy : 12  // The week that contains Jan 1st is the first week of the year.
    }
});

return ar;

})));


/***/ }),
/* 36 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Azerbaijani [az]
//! author : topchiyev : https://github.com/topchiyev

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var suffixes = {
    1: '-inci',
    5: '-inci',
    8: '-inci',
    70: '-inci',
    80: '-inci',
    2: '-nci',
    7: '-nci',
    20: '-nci',
    50: '-nci',
    3: '-üncü',
    4: '-üncü',
    100: '-üncü',
    6: '-ncı',
    9: '-uncu',
    10: '-uncu',
    30: '-uncu',
    60: '-ıncı',
    90: '-ıncı'
};

var az = moment.defineLocale('az', {
    months : 'yanvar_fevral_mart_aprel_may_iyun_iyul_avqust_sentyabr_oktyabr_noyabr_dekabr'.split('_'),
    monthsShort : 'yan_fev_mar_apr_may_iyn_iyl_avq_sen_okt_noy_dek'.split('_'),
    weekdays : 'Bazar_Bazar ertəsi_Çərşənbə axşamı_Çərşənbə_Cümə axşamı_Cümə_Şənbə'.split('_'),
    weekdaysShort : 'Baz_BzE_ÇAx_Çər_CAx_Cüm_Şən'.split('_'),
    weekdaysMin : 'Bz_BE_ÇA_Çə_CA_Cü_Şə'.split('_'),
    weekdaysParseExact : true,
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD.MM.YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY HH:mm',
        LLLL : 'dddd, D MMMM YYYY HH:mm'
    },
    calendar : {
        sameDay : '[bugün saat] LT',
        nextDay : '[sabah saat] LT',
        nextWeek : '[gələn həftə] dddd [saat] LT',
        lastDay : '[dünən] LT',
        lastWeek : '[keçən həftə] dddd [saat] LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : '%s sonra',
        past : '%s əvvəl',
        s : 'birneçə saniyyə',
        ss : '%d saniyə',
        m : 'bir dəqiqə',
        mm : '%d dəqiqə',
        h : 'bir saat',
        hh : '%d saat',
        d : 'bir gün',
        dd : '%d gün',
        M : 'bir ay',
        MM : '%d ay',
        y : 'bir il',
        yy : '%d il'
    },
    meridiemParse: /gecə|səhər|gündüz|axşam/,
    isPM : function (input) {
        return /^(gündüz|axşam)$/.test(input);
    },
    meridiem : function (hour, minute, isLower) {
        if (hour < 4) {
            return 'gecə';
        } else if (hour < 12) {
            return 'səhər';
        } else if (hour < 17) {
            return 'gündüz';
        } else {
            return 'axşam';
        }
    },
    dayOfMonthOrdinalParse: /\d{1,2}-(ıncı|inci|nci|üncü|ncı|uncu)/,
    ordinal : function (number) {
        if (number === 0) {  // special case for zero
            return number + '-ıncı';
        }
        var a = number % 10,
            b = number % 100 - a,
            c = number >= 100 ? 100 : null;
        return number + (suffixes[a] || suffixes[b] || suffixes[c]);
    },
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 7  // The week that contains Jan 1st is the first week of the year.
    }
});

return az;

})));


/***/ }),
/* 37 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Belarusian [be]
//! author : Dmitry Demidov : https://github.com/demidov91
//! author: Praleska: http://praleska.pro/
//! Author : Menelion Elensúle : https://github.com/Oire

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


function plural(word, num) {
    var forms = word.split('_');
    return num % 10 === 1 && num % 100 !== 11 ? forms[0] : (num % 10 >= 2 && num % 10 <= 4 && (num % 100 < 10 || num % 100 >= 20) ? forms[1] : forms[2]);
}
function relativeTimeWithPlural(number, withoutSuffix, key) {
    var format = {
        'ss': withoutSuffix ? 'секунда_секунды_секунд' : 'секунду_секунды_секунд',
        'mm': withoutSuffix ? 'хвіліна_хвіліны_хвілін' : 'хвіліну_хвіліны_хвілін',
        'hh': withoutSuffix ? 'гадзіна_гадзіны_гадзін' : 'гадзіну_гадзіны_гадзін',
        'dd': 'дзень_дні_дзён',
        'MM': 'месяц_месяцы_месяцаў',
        'yy': 'год_гады_гадоў'
    };
    if (key === 'm') {
        return withoutSuffix ? 'хвіліна' : 'хвіліну';
    }
    else if (key === 'h') {
        return withoutSuffix ? 'гадзіна' : 'гадзіну';
    }
    else {
        return number + ' ' + plural(format[key], +number);
    }
}

var be = moment.defineLocale('be', {
    months : {
        format: 'студзеня_лютага_сакавіка_красавіка_траўня_чэрвеня_ліпеня_жніўня_верасня_кастрычніка_лістапада_снежня'.split('_'),
        standalone: 'студзень_люты_сакавік_красавік_травень_чэрвень_ліпень_жнівень_верасень_кастрычнік_лістапад_снежань'.split('_')
    },
    monthsShort : 'студ_лют_сак_крас_трав_чэрв_ліп_жнів_вер_каст_ліст_снеж'.split('_'),
    weekdays : {
        format: 'нядзелю_панядзелак_аўторак_сераду_чацвер_пятніцу_суботу'.split('_'),
        standalone: 'нядзеля_панядзелак_аўторак_серада_чацвер_пятніца_субота'.split('_'),
        isFormat: /\[ ?[Вв] ?(?:мінулую|наступную)? ?\] ?dddd/
    },
    weekdaysShort : 'нд_пн_ат_ср_чц_пт_сб'.split('_'),
    weekdaysMin : 'нд_пн_ат_ср_чц_пт_сб'.split('_'),
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD.MM.YYYY',
        LL : 'D MMMM YYYY г.',
        LLL : 'D MMMM YYYY г., HH:mm',
        LLLL : 'dddd, D MMMM YYYY г., HH:mm'
    },
    calendar : {
        sameDay: '[Сёння ў] LT',
        nextDay: '[Заўтра ў] LT',
        lastDay: '[Учора ў] LT',
        nextWeek: function () {
            return '[У] dddd [ў] LT';
        },
        lastWeek: function () {
            switch (this.day()) {
                case 0:
                case 3:
                case 5:
                case 6:
                    return '[У мінулую] dddd [ў] LT';
                case 1:
                case 2:
                case 4:
                    return '[У мінулы] dddd [ў] LT';
            }
        },
        sameElse: 'L'
    },
    relativeTime : {
        future : 'праз %s',
        past : '%s таму',
        s : 'некалькі секунд',
        m : relativeTimeWithPlural,
        mm : relativeTimeWithPlural,
        h : relativeTimeWithPlural,
        hh : relativeTimeWithPlural,
        d : 'дзень',
        dd : relativeTimeWithPlural,
        M : 'месяц',
        MM : relativeTimeWithPlural,
        y : 'год',
        yy : relativeTimeWithPlural
    },
    meridiemParse: /ночы|раніцы|дня|вечара/,
    isPM : function (input) {
        return /^(дня|вечара)$/.test(input);
    },
    meridiem : function (hour, minute, isLower) {
        if (hour < 4) {
            return 'ночы';
        } else if (hour < 12) {
            return 'раніцы';
        } else if (hour < 17) {
            return 'дня';
        } else {
            return 'вечара';
        }
    },
    dayOfMonthOrdinalParse: /\d{1,2}-(і|ы|га)/,
    ordinal: function (number, period) {
        switch (period) {
            case 'M':
            case 'd':
            case 'DDD':
            case 'w':
            case 'W':
                return (number % 10 === 2 || number % 10 === 3) && (number % 100 !== 12 && number % 100 !== 13) ? number + '-і' : number + '-ы';
            case 'D':
                return number + '-га';
            default:
                return number;
        }
    },
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 7  // The week that contains Jan 1st is the first week of the year.
    }
});

return be;

})));


/***/ }),
/* 38 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Bulgarian [bg]
//! author : Krasen Borisov : https://github.com/kraz

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var bg = moment.defineLocale('bg', {
    months : 'януари_февруари_март_април_май_юни_юли_август_септември_октомври_ноември_декември'.split('_'),
    monthsShort : 'янр_фев_мар_апр_май_юни_юли_авг_сеп_окт_ное_дек'.split('_'),
    weekdays : 'неделя_понеделник_вторник_сряда_четвъртък_петък_събота'.split('_'),
    weekdaysShort : 'нед_пон_вто_сря_чет_пет_съб'.split('_'),
    weekdaysMin : 'нд_пн_вт_ср_чт_пт_сб'.split('_'),
    longDateFormat : {
        LT : 'H:mm',
        LTS : 'H:mm:ss',
        L : 'D.MM.YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY H:mm',
        LLLL : 'dddd, D MMMM YYYY H:mm'
    },
    calendar : {
        sameDay : '[Днес в] LT',
        nextDay : '[Утре в] LT',
        nextWeek : 'dddd [в] LT',
        lastDay : '[Вчера в] LT',
        lastWeek : function () {
            switch (this.day()) {
                case 0:
                case 3:
                case 6:
                    return '[В изминалата] dddd [в] LT';
                case 1:
                case 2:
                case 4:
                case 5:
                    return '[В изминалия] dddd [в] LT';
            }
        },
        sameElse : 'L'
    },
    relativeTime : {
        future : 'след %s',
        past : 'преди %s',
        s : 'няколко секунди',
        ss : '%d секунди',
        m : 'минута',
        mm : '%d минути',
        h : 'час',
        hh : '%d часа',
        d : 'ден',
        dd : '%d дни',
        M : 'месец',
        MM : '%d месеца',
        y : 'година',
        yy : '%d години'
    },
    dayOfMonthOrdinalParse: /\d{1,2}-(ев|ен|ти|ви|ри|ми)/,
    ordinal : function (number) {
        var lastDigit = number % 10,
            last2Digits = number % 100;
        if (number === 0) {
            return number + '-ев';
        } else if (last2Digits === 0) {
            return number + '-ен';
        } else if (last2Digits > 10 && last2Digits < 20) {
            return number + '-ти';
        } else if (lastDigit === 1) {
            return number + '-ви';
        } else if (lastDigit === 2) {
            return number + '-ри';
        } else if (lastDigit === 7 || lastDigit === 8) {
            return number + '-ми';
        } else {
            return number + '-ти';
        }
    },
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 7  // The week that contains Jan 1st is the first week of the year.
    }
});

return bg;

})));


/***/ }),
/* 39 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Bambara [bm]
//! author : Estelle Comment : https://github.com/estellecomment

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';

// Language contact person : Abdoufata Kane : https://github.com/abdoufata

var bm = moment.defineLocale('bm', {
    months : 'Zanwuyekalo_Fewuruyekalo_Marisikalo_Awirilikalo_Mɛkalo_Zuwɛnkalo_Zuluyekalo_Utikalo_Sɛtanburukalo_ɔkutɔburukalo_Nowanburukalo_Desanburukalo'.split('_'),
    monthsShort : 'Zan_Few_Mar_Awi_Mɛ_Zuw_Zul_Uti_Sɛt_ɔku_Now_Des'.split('_'),
    weekdays : 'Kari_Ntɛnɛn_Tarata_Araba_Alamisa_Juma_Sibiri'.split('_'),
    weekdaysShort : 'Kar_Ntɛ_Tar_Ara_Ala_Jum_Sib'.split('_'),
    weekdaysMin : 'Ka_Nt_Ta_Ar_Al_Ju_Si'.split('_'),
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD/MM/YYYY',
        LL : 'MMMM [tile] D [san] YYYY',
        LLL : 'MMMM [tile] D [san] YYYY [lɛrɛ] HH:mm',
        LLLL : 'dddd MMMM [tile] D [san] YYYY [lɛrɛ] HH:mm'
    },
    calendar : {
        sameDay : '[Bi lɛrɛ] LT',
        nextDay : '[Sini lɛrɛ] LT',
        nextWeek : 'dddd [don lɛrɛ] LT',
        lastDay : '[Kunu lɛrɛ] LT',
        lastWeek : 'dddd [tɛmɛnen lɛrɛ] LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : '%s kɔnɔ',
        past : 'a bɛ %s bɔ',
        s : 'sanga dama dama',
        ss : 'sekondi %d',
        m : 'miniti kelen',
        mm : 'miniti %d',
        h : 'lɛrɛ kelen',
        hh : 'lɛrɛ %d',
        d : 'tile kelen',
        dd : 'tile %d',
        M : 'kalo kelen',
        MM : 'kalo %d',
        y : 'san kelen',
        yy : 'san %d'
    },
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return bm;

})));


/***/ }),
/* 40 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Bengali [bn]
//! author : Kaushik Gandhi : https://github.com/kaushikgandhi

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var symbolMap = {
    '1': '১',
    '2': '২',
    '3': '৩',
    '4': '৪',
    '5': '৫',
    '6': '৬',
    '7': '৭',
    '8': '৮',
    '9': '৯',
    '0': '০'
};
var numberMap = {
    '১': '1',
    '২': '2',
    '৩': '3',
    '৪': '4',
    '৫': '5',
    '৬': '6',
    '৭': '7',
    '৮': '8',
    '৯': '9',
    '০': '0'
};

var bn = moment.defineLocale('bn', {
    months : 'জানুয়ারী_ফেব্রুয়ারি_মার্চ_এপ্রিল_মে_জুন_জুলাই_আগস্ট_সেপ্টেম্বর_অক্টোবর_নভেম্বর_ডিসেম্বর'.split('_'),
    monthsShort : 'জানু_ফেব_মার্চ_এপ্র_মে_জুন_জুল_আগ_সেপ্ট_অক্টো_নভে_ডিসে'.split('_'),
    weekdays : 'রবিবার_সোমবার_মঙ্গলবার_বুধবার_বৃহস্পতিবার_শুক্রবার_শনিবার'.split('_'),
    weekdaysShort : 'রবি_সোম_মঙ্গল_বুধ_বৃহস্পতি_শুক্র_শনি'.split('_'),
    weekdaysMin : 'রবি_সোম_মঙ্গ_বুধ_বৃহঃ_শুক্র_শনি'.split('_'),
    longDateFormat : {
        LT : 'A h:mm সময়',
        LTS : 'A h:mm:ss সময়',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY, A h:mm সময়',
        LLLL : 'dddd, D MMMM YYYY, A h:mm সময়'
    },
    calendar : {
        sameDay : '[আজ] LT',
        nextDay : '[আগামীকাল] LT',
        nextWeek : 'dddd, LT',
        lastDay : '[গতকাল] LT',
        lastWeek : '[গত] dddd, LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : '%s পরে',
        past : '%s আগে',
        s : 'কয়েক সেকেন্ড',
        ss : '%d সেকেন্ড',
        m : 'এক মিনিট',
        mm : '%d মিনিট',
        h : 'এক ঘন্টা',
        hh : '%d ঘন্টা',
        d : 'এক দিন',
        dd : '%d দিন',
        M : 'এক মাস',
        MM : '%d মাস',
        y : 'এক বছর',
        yy : '%d বছর'
    },
    preparse: function (string) {
        return string.replace(/[১২৩৪৫৬৭৮৯০]/g, function (match) {
            return numberMap[match];
        });
    },
    postformat: function (string) {
        return string.replace(/\d/g, function (match) {
            return symbolMap[match];
        });
    },
    meridiemParse: /রাত|সকাল|দুপুর|বিকাল|রাত/,
    meridiemHour : function (hour, meridiem) {
        if (hour === 12) {
            hour = 0;
        }
        if ((meridiem === 'রাত' && hour >= 4) ||
                (meridiem === 'দুপুর' && hour < 5) ||
                meridiem === 'বিকাল') {
            return hour + 12;
        } else {
            return hour;
        }
    },
    meridiem : function (hour, minute, isLower) {
        if (hour < 4) {
            return 'রাত';
        } else if (hour < 10) {
            return 'সকাল';
        } else if (hour < 17) {
            return 'দুপুর';
        } else if (hour < 20) {
            return 'বিকাল';
        } else {
            return 'রাত';
        }
    },
    week : {
        dow : 0, // Sunday is the first day of the week.
        doy : 6  // The week that contains Jan 1st is the first week of the year.
    }
});

return bn;

})));


/***/ }),
/* 41 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Tibetan [bo]
//! author : Thupten N. Chakrishar : https://github.com/vajradog

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var symbolMap = {
    '1': '༡',
    '2': '༢',
    '3': '༣',
    '4': '༤',
    '5': '༥',
    '6': '༦',
    '7': '༧',
    '8': '༨',
    '9': '༩',
    '0': '༠'
};
var numberMap = {
    '༡': '1',
    '༢': '2',
    '༣': '3',
    '༤': '4',
    '༥': '5',
    '༦': '6',
    '༧': '7',
    '༨': '8',
    '༩': '9',
    '༠': '0'
};

var bo = moment.defineLocale('bo', {
    months : 'ཟླ་བ་དང་པོ_ཟླ་བ་གཉིས་པ_ཟླ་བ་གསུམ་པ_ཟླ་བ་བཞི་པ_ཟླ་བ་ལྔ་པ_ཟླ་བ་དྲུག་པ_ཟླ་བ་བདུན་པ_ཟླ་བ་བརྒྱད་པ_ཟླ་བ་དགུ་པ_ཟླ་བ་བཅུ་པ_ཟླ་བ་བཅུ་གཅིག་པ_ཟླ་བ་བཅུ་གཉིས་པ'.split('_'),
    monthsShort : 'ཟླ་བ་དང་པོ_ཟླ་བ་གཉིས་པ_ཟླ་བ་གསུམ་པ_ཟླ་བ་བཞི་པ_ཟླ་བ་ལྔ་པ_ཟླ་བ་དྲུག་པ_ཟླ་བ་བདུན་པ_ཟླ་བ་བརྒྱད་པ_ཟླ་བ་དགུ་པ_ཟླ་བ་བཅུ་པ_ཟླ་བ་བཅུ་གཅིག་པ_ཟླ་བ་བཅུ་གཉིས་པ'.split('_'),
    weekdays : 'གཟའ་ཉི་མ་_གཟའ་ཟླ་བ་_གཟའ་མིག་དམར་_གཟའ་ལྷག་པ་_གཟའ་ཕུར་བུ_གཟའ་པ་སངས་_གཟའ་སྤེན་པ་'.split('_'),
    weekdaysShort : 'ཉི་མ་_ཟླ་བ་_མིག་དམར་_ལྷག་པ་_ཕུར་བུ_པ་སངས་_སྤེན་པ་'.split('_'),
    weekdaysMin : 'ཉི་མ་_ཟླ་བ་_མིག་དམར་_ལྷག་པ་_ཕུར་བུ_པ་སངས་_སྤེན་པ་'.split('_'),
    longDateFormat : {
        LT : 'A h:mm',
        LTS : 'A h:mm:ss',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY, A h:mm',
        LLLL : 'dddd, D MMMM YYYY, A h:mm'
    },
    calendar : {
        sameDay : '[དི་རིང] LT',
        nextDay : '[སང་ཉིན] LT',
        nextWeek : '[བདུན་ཕྲག་རྗེས་མ], LT',
        lastDay : '[ཁ་སང] LT',
        lastWeek : '[བདུན་ཕྲག་མཐའ་མ] dddd, LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : '%s ལ་',
        past : '%s སྔན་ལ',
        s : 'ལམ་སང',
        ss : '%d སྐར་ཆ།',
        m : 'སྐར་མ་གཅིག',
        mm : '%d སྐར་མ',
        h : 'ཆུ་ཚོད་གཅིག',
        hh : '%d ཆུ་ཚོད',
        d : 'ཉིན་གཅིག',
        dd : '%d ཉིན་',
        M : 'ཟླ་བ་གཅིག',
        MM : '%d ཟླ་བ',
        y : 'ལོ་གཅིག',
        yy : '%d ལོ'
    },
    preparse: function (string) {
        return string.replace(/[༡༢༣༤༥༦༧༨༩༠]/g, function (match) {
            return numberMap[match];
        });
    },
    postformat: function (string) {
        return string.replace(/\d/g, function (match) {
            return symbolMap[match];
        });
    },
    meridiemParse: /མཚན་མོ|ཞོགས་ཀས|ཉིན་གུང|དགོང་དག|མཚན་མོ/,
    meridiemHour : function (hour, meridiem) {
        if (hour === 12) {
            hour = 0;
        }
        if ((meridiem === 'མཚན་མོ' && hour >= 4) ||
                (meridiem === 'ཉིན་གུང' && hour < 5) ||
                meridiem === 'དགོང་དག') {
            return hour + 12;
        } else {
            return hour;
        }
    },
    meridiem : function (hour, minute, isLower) {
        if (hour < 4) {
            return 'མཚན་མོ';
        } else if (hour < 10) {
            return 'ཞོགས་ཀས';
        } else if (hour < 17) {
            return 'ཉིན་གུང';
        } else if (hour < 20) {
            return 'དགོང་དག';
        } else {
            return 'མཚན་མོ';
        }
    },
    week : {
        dow : 0, // Sunday is the first day of the week.
        doy : 6  // The week that contains Jan 1st is the first week of the year.
    }
});

return bo;

})));


/***/ }),
/* 42 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Breton [br]
//! author : Jean-Baptiste Le Duigou : https://github.com/jbleduigou

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


function relativeTimeWithMutation(number, withoutSuffix, key) {
    var format = {
        'mm': 'munutenn',
        'MM': 'miz',
        'dd': 'devezh'
    };
    return number + ' ' + mutation(format[key], number);
}
function specialMutationForYears(number) {
    switch (lastNumber(number)) {
        case 1:
        case 3:
        case 4:
        case 5:
        case 9:
            return number + ' bloaz';
        default:
            return number + ' vloaz';
    }
}
function lastNumber(number) {
    if (number > 9) {
        return lastNumber(number % 10);
    }
    return number;
}
function mutation(text, number) {
    if (number === 2) {
        return softMutation(text);
    }
    return text;
}
function softMutation(text) {
    var mutationTable = {
        'm': 'v',
        'b': 'v',
        'd': 'z'
    };
    if (mutationTable[text.charAt(0)] === undefined) {
        return text;
    }
    return mutationTable[text.charAt(0)] + text.substring(1);
}

var br = moment.defineLocale('br', {
    months : 'Genver_C\'hwevrer_Meurzh_Ebrel_Mae_Mezheven_Gouere_Eost_Gwengolo_Here_Du_Kerzu'.split('_'),
    monthsShort : 'Gen_C\'hwe_Meu_Ebr_Mae_Eve_Gou_Eos_Gwe_Her_Du_Ker'.split('_'),
    weekdays : 'Sul_Lun_Meurzh_Merc\'her_Yaou_Gwener_Sadorn'.split('_'),
    weekdaysShort : 'Sul_Lun_Meu_Mer_Yao_Gwe_Sad'.split('_'),
    weekdaysMin : 'Su_Lu_Me_Mer_Ya_Gw_Sa'.split('_'),
    weekdaysParseExact : true,
    longDateFormat : {
        LT : 'h[e]mm A',
        LTS : 'h[e]mm:ss A',
        L : 'DD/MM/YYYY',
        LL : 'D [a viz] MMMM YYYY',
        LLL : 'D [a viz] MMMM YYYY h[e]mm A',
        LLLL : 'dddd, D [a viz] MMMM YYYY h[e]mm A'
    },
    calendar : {
        sameDay : '[Hiziv da] LT',
        nextDay : '[Warc\'hoazh da] LT',
        nextWeek : 'dddd [da] LT',
        lastDay : '[Dec\'h da] LT',
        lastWeek : 'dddd [paset da] LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : 'a-benn %s',
        past : '%s \'zo',
        s : 'un nebeud segondennoù',
        ss : '%d eilenn',
        m : 'ur vunutenn',
        mm : relativeTimeWithMutation,
        h : 'un eur',
        hh : '%d eur',
        d : 'un devezh',
        dd : relativeTimeWithMutation,
        M : 'ur miz',
        MM : relativeTimeWithMutation,
        y : 'ur bloaz',
        yy : specialMutationForYears
    },
    dayOfMonthOrdinalParse: /\d{1,2}(añ|vet)/,
    ordinal : function (number) {
        var output = (number === 1) ? 'añ' : 'vet';
        return number + output;
    },
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return br;

})));


/***/ }),
/* 43 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Bosnian [bs]
//! author : Nedim Cholich : https://github.com/frontyard
//! based on (hr) translation by Bojan Marković

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


function translate(number, withoutSuffix, key) {
    var result = number + ' ';
    switch (key) {
        case 'ss':
            if (number === 1) {
                result += 'sekunda';
            } else if (number === 2 || number === 3 || number === 4) {
                result += 'sekunde';
            } else {
                result += 'sekundi';
            }
            return result;
        case 'm':
            return withoutSuffix ? 'jedna minuta' : 'jedne minute';
        case 'mm':
            if (number === 1) {
                result += 'minuta';
            } else if (number === 2 || number === 3 || number === 4) {
                result += 'minute';
            } else {
                result += 'minuta';
            }
            return result;
        case 'h':
            return withoutSuffix ? 'jedan sat' : 'jednog sata';
        case 'hh':
            if (number === 1) {
                result += 'sat';
            } else if (number === 2 || number === 3 || number === 4) {
                result += 'sata';
            } else {
                result += 'sati';
            }
            return result;
        case 'dd':
            if (number === 1) {
                result += 'dan';
            } else {
                result += 'dana';
            }
            return result;
        case 'MM':
            if (number === 1) {
                result += 'mjesec';
            } else if (number === 2 || number === 3 || number === 4) {
                result += 'mjeseca';
            } else {
                result += 'mjeseci';
            }
            return result;
        case 'yy':
            if (number === 1) {
                result += 'godina';
            } else if (number === 2 || number === 3 || number === 4) {
                result += 'godine';
            } else {
                result += 'godina';
            }
            return result;
    }
}

var bs = moment.defineLocale('bs', {
    months : 'januar_februar_mart_april_maj_juni_juli_august_septembar_oktobar_novembar_decembar'.split('_'),
    monthsShort : 'jan._feb._mar._apr._maj._jun._jul._aug._sep._okt._nov._dec.'.split('_'),
    monthsParseExact: true,
    weekdays : 'nedjelja_ponedjeljak_utorak_srijeda_četvrtak_petak_subota'.split('_'),
    weekdaysShort : 'ned._pon._uto._sri._čet._pet._sub.'.split('_'),
    weekdaysMin : 'ne_po_ut_sr_če_pe_su'.split('_'),
    weekdaysParseExact : true,
    longDateFormat : {
        LT : 'H:mm',
        LTS : 'H:mm:ss',
        L : 'DD.MM.YYYY',
        LL : 'D. MMMM YYYY',
        LLL : 'D. MMMM YYYY H:mm',
        LLLL : 'dddd, D. MMMM YYYY H:mm'
    },
    calendar : {
        sameDay  : '[danas u] LT',
        nextDay  : '[sutra u] LT',
        nextWeek : function () {
            switch (this.day()) {
                case 0:
                    return '[u] [nedjelju] [u] LT';
                case 3:
                    return '[u] [srijedu] [u] LT';
                case 6:
                    return '[u] [subotu] [u] LT';
                case 1:
                case 2:
                case 4:
                case 5:
                    return '[u] dddd [u] LT';
            }
        },
        lastDay  : '[jučer u] LT',
        lastWeek : function () {
            switch (this.day()) {
                case 0:
                case 3:
                    return '[prošlu] dddd [u] LT';
                case 6:
                    return '[prošle] [subote] [u] LT';
                case 1:
                case 2:
                case 4:
                case 5:
                    return '[prošli] dddd [u] LT';
            }
        },
        sameElse : 'L'
    },
    relativeTime : {
        future : 'za %s',
        past   : 'prije %s',
        s      : 'par sekundi',
        ss     : translate,
        m      : translate,
        mm     : translate,
        h      : translate,
        hh     : translate,
        d      : 'dan',
        dd     : translate,
        M      : 'mjesec',
        MM     : translate,
        y      : 'godinu',
        yy     : translate
    },
    dayOfMonthOrdinalParse: /\d{1,2}\./,
    ordinal : '%d.',
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 7  // The week that contains Jan 1st is the first week of the year.
    }
});

return bs;

})));


/***/ }),
/* 44 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Catalan [ca]
//! author : Juan G. Hurtado : https://github.com/juanghurtado

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var ca = moment.defineLocale('ca', {
    months : {
        standalone: 'gener_febrer_març_abril_maig_juny_juliol_agost_setembre_octubre_novembre_desembre'.split('_'),
        format: 'de gener_de febrer_de març_d\'abril_de maig_de juny_de juliol_d\'agost_de setembre_d\'octubre_de novembre_de desembre'.split('_'),
        isFormat: /D[oD]?(\s)+MMMM/
    },
    monthsShort : 'gen._febr._març_abr._maig_juny_jul._ag._set._oct._nov._des.'.split('_'),
    monthsParseExact : true,
    weekdays : 'diumenge_dilluns_dimarts_dimecres_dijous_divendres_dissabte'.split('_'),
    weekdaysShort : 'dg._dl._dt._dc._dj._dv._ds.'.split('_'),
    weekdaysMin : 'dg_dl_dt_dc_dj_dv_ds'.split('_'),
    weekdaysParseExact : true,
    longDateFormat : {
        LT : 'H:mm',
        LTS : 'H:mm:ss',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM [de] YYYY',
        ll : 'D MMM YYYY',
        LLL : 'D MMMM [de] YYYY [a les] H:mm',
        lll : 'D MMM YYYY, H:mm',
        LLLL : 'dddd D MMMM [de] YYYY [a les] H:mm',
        llll : 'ddd D MMM YYYY, H:mm'
    },
    calendar : {
        sameDay : function () {
            return '[avui a ' + ((this.hours() !== 1) ? 'les' : 'la') + '] LT';
        },
        nextDay : function () {
            return '[demà a ' + ((this.hours() !== 1) ? 'les' : 'la') + '] LT';
        },
        nextWeek : function () {
            return 'dddd [a ' + ((this.hours() !== 1) ? 'les' : 'la') + '] LT';
        },
        lastDay : function () {
            return '[ahir a ' + ((this.hours() !== 1) ? 'les' : 'la') + '] LT';
        },
        lastWeek : function () {
            return '[el] dddd [passat a ' + ((this.hours() !== 1) ? 'les' : 'la') + '] LT';
        },
        sameElse : 'L'
    },
    relativeTime : {
        future : 'd\'aquí %s',
        past : 'fa %s',
        s : 'uns segons',
        ss : '%d segons',
        m : 'un minut',
        mm : '%d minuts',
        h : 'una hora',
        hh : '%d hores',
        d : 'un dia',
        dd : '%d dies',
        M : 'un mes',
        MM : '%d mesos',
        y : 'un any',
        yy : '%d anys'
    },
    dayOfMonthOrdinalParse: /\d{1,2}(r|n|t|è|a)/,
    ordinal : function (number, period) {
        var output = (number === 1) ? 'r' :
            (number === 2) ? 'n' :
            (number === 3) ? 'r' :
            (number === 4) ? 't' : 'è';
        if (period === 'w' || period === 'W') {
            output = 'a';
        }
        return number + output;
    },
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return ca;

})));


/***/ }),
/* 45 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Czech [cs]
//! author : petrbela : https://github.com/petrbela

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var months = 'leden_únor_březen_duben_květen_červen_červenec_srpen_září_říjen_listopad_prosinec'.split('_');
var monthsShort = 'led_úno_bře_dub_kvě_čvn_čvc_srp_zář_říj_lis_pro'.split('_');
function plural(n) {
    return (n > 1) && (n < 5) && (~~(n / 10) !== 1);
}
function translate(number, withoutSuffix, key, isFuture) {
    var result = number + ' ';
    switch (key) {
        case 's':  // a few seconds / in a few seconds / a few seconds ago
            return (withoutSuffix || isFuture) ? 'pár sekund' : 'pár sekundami';
        case 'ss': // 9 seconds / in 9 seconds / 9 seconds ago
            if (withoutSuffix || isFuture) {
                return result + (plural(number) ? 'sekundy' : 'sekund');
            } else {
                return result + 'sekundami';
            }
            break;
        case 'm':  // a minute / in a minute / a minute ago
            return withoutSuffix ? 'minuta' : (isFuture ? 'minutu' : 'minutou');
        case 'mm': // 9 minutes / in 9 minutes / 9 minutes ago
            if (withoutSuffix || isFuture) {
                return result + (plural(number) ? 'minuty' : 'minut');
            } else {
                return result + 'minutami';
            }
            break;
        case 'h':  // an hour / in an hour / an hour ago
            return withoutSuffix ? 'hodina' : (isFuture ? 'hodinu' : 'hodinou');
        case 'hh': // 9 hours / in 9 hours / 9 hours ago
            if (withoutSuffix || isFuture) {
                return result + (plural(number) ? 'hodiny' : 'hodin');
            } else {
                return result + 'hodinami';
            }
            break;
        case 'd':  // a day / in a day / a day ago
            return (withoutSuffix || isFuture) ? 'den' : 'dnem';
        case 'dd': // 9 days / in 9 days / 9 days ago
            if (withoutSuffix || isFuture) {
                return result + (plural(number) ? 'dny' : 'dní');
            } else {
                return result + 'dny';
            }
            break;
        case 'M':  // a month / in a month / a month ago
            return (withoutSuffix || isFuture) ? 'měsíc' : 'měsícem';
        case 'MM': // 9 months / in 9 months / 9 months ago
            if (withoutSuffix || isFuture) {
                return result + (plural(number) ? 'měsíce' : 'měsíců');
            } else {
                return result + 'měsíci';
            }
            break;
        case 'y':  // a year / in a year / a year ago
            return (withoutSuffix || isFuture) ? 'rok' : 'rokem';
        case 'yy': // 9 years / in 9 years / 9 years ago
            if (withoutSuffix || isFuture) {
                return result + (plural(number) ? 'roky' : 'let');
            } else {
                return result + 'lety';
            }
            break;
    }
}

var cs = moment.defineLocale('cs', {
    months : months,
    monthsShort : monthsShort,
    monthsParse : (function (months, monthsShort) {
        var i, _monthsParse = [];
        for (i = 0; i < 12; i++) {
            // use custom parser to solve problem with July (červenec)
            _monthsParse[i] = new RegExp('^' + months[i] + '$|^' + monthsShort[i] + '$', 'i');
        }
        return _monthsParse;
    }(months, monthsShort)),
    shortMonthsParse : (function (monthsShort) {
        var i, _shortMonthsParse = [];
        for (i = 0; i < 12; i++) {
            _shortMonthsParse[i] = new RegExp('^' + monthsShort[i] + '$', 'i');
        }
        return _shortMonthsParse;
    }(monthsShort)),
    longMonthsParse : (function (months) {
        var i, _longMonthsParse = [];
        for (i = 0; i < 12; i++) {
            _longMonthsParse[i] = new RegExp('^' + months[i] + '$', 'i');
        }
        return _longMonthsParse;
    }(months)),
    weekdays : 'neděle_pondělí_úterý_středa_čtvrtek_pátek_sobota'.split('_'),
    weekdaysShort : 'ne_po_út_st_čt_pá_so'.split('_'),
    weekdaysMin : 'ne_po_út_st_čt_pá_so'.split('_'),
    longDateFormat : {
        LT: 'H:mm',
        LTS : 'H:mm:ss',
        L : 'DD.MM.YYYY',
        LL : 'D. MMMM YYYY',
        LLL : 'D. MMMM YYYY H:mm',
        LLLL : 'dddd D. MMMM YYYY H:mm',
        l : 'D. M. YYYY'
    },
    calendar : {
        sameDay: '[dnes v] LT',
        nextDay: '[zítra v] LT',
        nextWeek: function () {
            switch (this.day()) {
                case 0:
                    return '[v neděli v] LT';
                case 1:
                case 2:
                    return '[v] dddd [v] LT';
                case 3:
                    return '[ve středu v] LT';
                case 4:
                    return '[ve čtvrtek v] LT';
                case 5:
                    return '[v pátek v] LT';
                case 6:
                    return '[v sobotu v] LT';
            }
        },
        lastDay: '[včera v] LT',
        lastWeek: function () {
            switch (this.day()) {
                case 0:
                    return '[minulou neděli v] LT';
                case 1:
                case 2:
                    return '[minulé] dddd [v] LT';
                case 3:
                    return '[minulou středu v] LT';
                case 4:
                case 5:
                    return '[minulý] dddd [v] LT';
                case 6:
                    return '[minulou sobotu v] LT';
            }
        },
        sameElse: 'L'
    },
    relativeTime : {
        future : 'za %s',
        past : 'před %s',
        s : translate,
        ss : translate,
        m : translate,
        mm : translate,
        h : translate,
        hh : translate,
        d : translate,
        dd : translate,
        M : translate,
        MM : translate,
        y : translate,
        yy : translate
    },
    dayOfMonthOrdinalParse : /\d{1,2}\./,
    ordinal : '%d.',
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return cs;

})));


/***/ }),
/* 46 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Chuvash [cv]
//! author : Anatoly Mironov : https://github.com/mirontoli

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var cv = moment.defineLocale('cv', {
    months : 'кӑрлач_нарӑс_пуш_ака_май_ҫӗртме_утӑ_ҫурла_авӑн_юпа_чӳк_раштав'.split('_'),
    monthsShort : 'кӑр_нар_пуш_ака_май_ҫӗр_утӑ_ҫур_авн_юпа_чӳк_раш'.split('_'),
    weekdays : 'вырсарникун_тунтикун_ытларикун_юнкун_кӗҫнерникун_эрнекун_шӑматкун'.split('_'),
    weekdaysShort : 'выр_тун_ытл_юн_кӗҫ_эрн_шӑм'.split('_'),
    weekdaysMin : 'вр_тн_ыт_юн_кҫ_эр_шм'.split('_'),
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD-MM-YYYY',
        LL : 'YYYY [ҫулхи] MMMM [уйӑхӗн] D[-мӗшӗ]',
        LLL : 'YYYY [ҫулхи] MMMM [уйӑхӗн] D[-мӗшӗ], HH:mm',
        LLLL : 'dddd, YYYY [ҫулхи] MMMM [уйӑхӗн] D[-мӗшӗ], HH:mm'
    },
    calendar : {
        sameDay: '[Паян] LT [сехетре]',
        nextDay: '[Ыран] LT [сехетре]',
        lastDay: '[Ӗнер] LT [сехетре]',
        nextWeek: '[Ҫитес] dddd LT [сехетре]',
        lastWeek: '[Иртнӗ] dddd LT [сехетре]',
        sameElse: 'L'
    },
    relativeTime : {
        future : function (output) {
            var affix = /сехет$/i.exec(output) ? 'рен' : /ҫул$/i.exec(output) ? 'тан' : 'ран';
            return output + affix;
        },
        past : '%s каялла',
        s : 'пӗр-ик ҫеккунт',
        ss : '%d ҫеккунт',
        m : 'пӗр минут',
        mm : '%d минут',
        h : 'пӗр сехет',
        hh : '%d сехет',
        d : 'пӗр кун',
        dd : '%d кун',
        M : 'пӗр уйӑх',
        MM : '%d уйӑх',
        y : 'пӗр ҫул',
        yy : '%d ҫул'
    },
    dayOfMonthOrdinalParse: /\d{1,2}-мӗш/,
    ordinal : '%d-мӗш',
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 7  // The week that contains Jan 1st is the first week of the year.
    }
});

return cv;

})));


/***/ }),
/* 47 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Welsh [cy]
//! author : Robert Allen : https://github.com/robgallen
//! author : https://github.com/ryangreaves

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var cy = moment.defineLocale('cy', {
    months: 'Ionawr_Chwefror_Mawrth_Ebrill_Mai_Mehefin_Gorffennaf_Awst_Medi_Hydref_Tachwedd_Rhagfyr'.split('_'),
    monthsShort: 'Ion_Chwe_Maw_Ebr_Mai_Meh_Gor_Aws_Med_Hyd_Tach_Rhag'.split('_'),
    weekdays: 'Dydd Sul_Dydd Llun_Dydd Mawrth_Dydd Mercher_Dydd Iau_Dydd Gwener_Dydd Sadwrn'.split('_'),
    weekdaysShort: 'Sul_Llun_Maw_Mer_Iau_Gwe_Sad'.split('_'),
    weekdaysMin: 'Su_Ll_Ma_Me_Ia_Gw_Sa'.split('_'),
    weekdaysParseExact : true,
    // time formats are the same as en-gb
    longDateFormat: {
        LT: 'HH:mm',
        LTS : 'HH:mm:ss',
        L: 'DD/MM/YYYY',
        LL: 'D MMMM YYYY',
        LLL: 'D MMMM YYYY HH:mm',
        LLLL: 'dddd, D MMMM YYYY HH:mm'
    },
    calendar: {
        sameDay: '[Heddiw am] LT',
        nextDay: '[Yfory am] LT',
        nextWeek: 'dddd [am] LT',
        lastDay: '[Ddoe am] LT',
        lastWeek: 'dddd [diwethaf am] LT',
        sameElse: 'L'
    },
    relativeTime: {
        future: 'mewn %s',
        past: '%s yn ôl',
        s: 'ychydig eiliadau',
        ss: '%d eiliad',
        m: 'munud',
        mm: '%d munud',
        h: 'awr',
        hh: '%d awr',
        d: 'diwrnod',
        dd: '%d diwrnod',
        M: 'mis',
        MM: '%d mis',
        y: 'blwyddyn',
        yy: '%d flynedd'
    },
    dayOfMonthOrdinalParse: /\d{1,2}(fed|ain|af|il|ydd|ed|eg)/,
    // traditional ordinal numbers above 31 are not commonly used in colloquial Welsh
    ordinal: function (number) {
        var b = number,
            output = '',
            lookup = [
                '', 'af', 'il', 'ydd', 'ydd', 'ed', 'ed', 'ed', 'fed', 'fed', 'fed', // 1af to 10fed
                'eg', 'fed', 'eg', 'eg', 'fed', 'eg', 'eg', 'fed', 'eg', 'fed' // 11eg to 20fed
            ];
        if (b > 20) {
            if (b === 40 || b === 50 || b === 60 || b === 80 || b === 100) {
                output = 'fed'; // not 30ain, 70ain or 90ain
            } else {
                output = 'ain';
            }
        } else if (b > 0) {
            output = lookup[b];
        }
        return number + output;
    },
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return cy;

})));


/***/ }),
/* 48 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Danish [da]
//! author : Ulrik Nielsen : https://github.com/mrbase

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var da = moment.defineLocale('da', {
    months : 'januar_februar_marts_april_maj_juni_juli_august_september_oktober_november_december'.split('_'),
    monthsShort : 'jan_feb_mar_apr_maj_jun_jul_aug_sep_okt_nov_dec'.split('_'),
    weekdays : 'søndag_mandag_tirsdag_onsdag_torsdag_fredag_lørdag'.split('_'),
    weekdaysShort : 'søn_man_tir_ons_tor_fre_lør'.split('_'),
    weekdaysMin : 'sø_ma_ti_on_to_fr_lø'.split('_'),
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD.MM.YYYY',
        LL : 'D. MMMM YYYY',
        LLL : 'D. MMMM YYYY HH:mm',
        LLLL : 'dddd [d.] D. MMMM YYYY [kl.] HH:mm'
    },
    calendar : {
        sameDay : '[i dag kl.] LT',
        nextDay : '[i morgen kl.] LT',
        nextWeek : 'på dddd [kl.] LT',
        lastDay : '[i går kl.] LT',
        lastWeek : '[i] dddd[s kl.] LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : 'om %s',
        past : '%s siden',
        s : 'få sekunder',
        ss : '%d sekunder',
        m : 'et minut',
        mm : '%d minutter',
        h : 'en time',
        hh : '%d timer',
        d : 'en dag',
        dd : '%d dage',
        M : 'en måned',
        MM : '%d måneder',
        y : 'et år',
        yy : '%d år'
    },
    dayOfMonthOrdinalParse: /\d{1,2}\./,
    ordinal : '%d.',
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return da;

})));


/***/ }),
/* 49 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : German (Austria) [de-at]
//! author : lluchs : https://github.com/lluchs
//! author: Menelion Elensúle: https://github.com/Oire
//! author : Martin Groller : https://github.com/MadMG
//! author : Mikolaj Dadela : https://github.com/mik01aj

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


function processRelativeTime(number, withoutSuffix, key, isFuture) {
    var format = {
        'm': ['eine Minute', 'einer Minute'],
        'h': ['eine Stunde', 'einer Stunde'],
        'd': ['ein Tag', 'einem Tag'],
        'dd': [number + ' Tage', number + ' Tagen'],
        'M': ['ein Monat', 'einem Monat'],
        'MM': [number + ' Monate', number + ' Monaten'],
        'y': ['ein Jahr', 'einem Jahr'],
        'yy': [number + ' Jahre', number + ' Jahren']
    };
    return withoutSuffix ? format[key][0] : format[key][1];
}

var deAt = moment.defineLocale('de-at', {
    months : 'Jänner_Februar_März_April_Mai_Juni_Juli_August_September_Oktober_November_Dezember'.split('_'),
    monthsShort : 'Jän._Feb._März_Apr._Mai_Juni_Juli_Aug._Sep._Okt._Nov._Dez.'.split('_'),
    monthsParseExact : true,
    weekdays : 'Sonntag_Montag_Dienstag_Mittwoch_Donnerstag_Freitag_Samstag'.split('_'),
    weekdaysShort : 'So._Mo._Di._Mi._Do._Fr._Sa.'.split('_'),
    weekdaysMin : 'So_Mo_Di_Mi_Do_Fr_Sa'.split('_'),
    weekdaysParseExact : true,
    longDateFormat : {
        LT: 'HH:mm',
        LTS: 'HH:mm:ss',
        L : 'DD.MM.YYYY',
        LL : 'D. MMMM YYYY',
        LLL : 'D. MMMM YYYY HH:mm',
        LLLL : 'dddd, D. MMMM YYYY HH:mm'
    },
    calendar : {
        sameDay: '[heute um] LT [Uhr]',
        sameElse: 'L',
        nextDay: '[morgen um] LT [Uhr]',
        nextWeek: 'dddd [um] LT [Uhr]',
        lastDay: '[gestern um] LT [Uhr]',
        lastWeek: '[letzten] dddd [um] LT [Uhr]'
    },
    relativeTime : {
        future : 'in %s',
        past : 'vor %s',
        s : 'ein paar Sekunden',
        ss : '%d Sekunden',
        m : processRelativeTime,
        mm : '%d Minuten',
        h : processRelativeTime,
        hh : '%d Stunden',
        d : processRelativeTime,
        dd : processRelativeTime,
        M : processRelativeTime,
        MM : processRelativeTime,
        y : processRelativeTime,
        yy : processRelativeTime
    },
    dayOfMonthOrdinalParse: /\d{1,2}\./,
    ordinal : '%d.',
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return deAt;

})));


/***/ }),
/* 50 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : German (Switzerland) [de-ch]
//! author : sschueller : https://github.com/sschueller

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


// based on: https://www.bk.admin.ch/dokumentation/sprachen/04915/05016/index.html?lang=de#

function processRelativeTime(number, withoutSuffix, key, isFuture) {
    var format = {
        'm': ['eine Minute', 'einer Minute'],
        'h': ['eine Stunde', 'einer Stunde'],
        'd': ['ein Tag', 'einem Tag'],
        'dd': [number + ' Tage', number + ' Tagen'],
        'M': ['ein Monat', 'einem Monat'],
        'MM': [number + ' Monate', number + ' Monaten'],
        'y': ['ein Jahr', 'einem Jahr'],
        'yy': [number + ' Jahre', number + ' Jahren']
    };
    return withoutSuffix ? format[key][0] : format[key][1];
}

var deCh = moment.defineLocale('de-ch', {
    months : 'Januar_Februar_März_April_Mai_Juni_Juli_August_September_Oktober_November_Dezember'.split('_'),
    monthsShort : 'Jan._Feb._März_Apr._Mai_Juni_Juli_Aug._Sep._Okt._Nov._Dez.'.split('_'),
    monthsParseExact : true,
    weekdays : 'Sonntag_Montag_Dienstag_Mittwoch_Donnerstag_Freitag_Samstag'.split('_'),
    weekdaysShort : 'So_Mo_Di_Mi_Do_Fr_Sa'.split('_'),
    weekdaysMin : 'So_Mo_Di_Mi_Do_Fr_Sa'.split('_'),
    weekdaysParseExact : true,
    longDateFormat : {
        LT: 'HH:mm',
        LTS: 'HH:mm:ss',
        L : 'DD.MM.YYYY',
        LL : 'D. MMMM YYYY',
        LLL : 'D. MMMM YYYY HH:mm',
        LLLL : 'dddd, D. MMMM YYYY HH:mm'
    },
    calendar : {
        sameDay: '[heute um] LT [Uhr]',
        sameElse: 'L',
        nextDay: '[morgen um] LT [Uhr]',
        nextWeek: 'dddd [um] LT [Uhr]',
        lastDay: '[gestern um] LT [Uhr]',
        lastWeek: '[letzten] dddd [um] LT [Uhr]'
    },
    relativeTime : {
        future : 'in %s',
        past : 'vor %s',
        s : 'ein paar Sekunden',
        ss : '%d Sekunden',
        m : processRelativeTime,
        mm : '%d Minuten',
        h : processRelativeTime,
        hh : '%d Stunden',
        d : processRelativeTime,
        dd : processRelativeTime,
        M : processRelativeTime,
        MM : processRelativeTime,
        y : processRelativeTime,
        yy : processRelativeTime
    },
    dayOfMonthOrdinalParse: /\d{1,2}\./,
    ordinal : '%d.',
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return deCh;

})));


/***/ }),
/* 51 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : German [de]
//! author : lluchs : https://github.com/lluchs
//! author: Menelion Elensúle: https://github.com/Oire
//! author : Mikolaj Dadela : https://github.com/mik01aj

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


function processRelativeTime(number, withoutSuffix, key, isFuture) {
    var format = {
        'm': ['eine Minute', 'einer Minute'],
        'h': ['eine Stunde', 'einer Stunde'],
        'd': ['ein Tag', 'einem Tag'],
        'dd': [number + ' Tage', number + ' Tagen'],
        'M': ['ein Monat', 'einem Monat'],
        'MM': [number + ' Monate', number + ' Monaten'],
        'y': ['ein Jahr', 'einem Jahr'],
        'yy': [number + ' Jahre', number + ' Jahren']
    };
    return withoutSuffix ? format[key][0] : format[key][1];
}

var de = moment.defineLocale('de', {
    months : 'Januar_Februar_März_April_Mai_Juni_Juli_August_September_Oktober_November_Dezember'.split('_'),
    monthsShort : 'Jan._Feb._März_Apr._Mai_Juni_Juli_Aug._Sep._Okt._Nov._Dez.'.split('_'),
    monthsParseExact : true,
    weekdays : 'Sonntag_Montag_Dienstag_Mittwoch_Donnerstag_Freitag_Samstag'.split('_'),
    weekdaysShort : 'So._Mo._Di._Mi._Do._Fr._Sa.'.split('_'),
    weekdaysMin : 'So_Mo_Di_Mi_Do_Fr_Sa'.split('_'),
    weekdaysParseExact : true,
    longDateFormat : {
        LT: 'HH:mm',
        LTS: 'HH:mm:ss',
        L : 'DD.MM.YYYY',
        LL : 'D. MMMM YYYY',
        LLL : 'D. MMMM YYYY HH:mm',
        LLLL : 'dddd, D. MMMM YYYY HH:mm'
    },
    calendar : {
        sameDay: '[heute um] LT [Uhr]',
        sameElse: 'L',
        nextDay: '[morgen um] LT [Uhr]',
        nextWeek: 'dddd [um] LT [Uhr]',
        lastDay: '[gestern um] LT [Uhr]',
        lastWeek: '[letzten] dddd [um] LT [Uhr]'
    },
    relativeTime : {
        future : 'in %s',
        past : 'vor %s',
        s : 'ein paar Sekunden',
        ss : '%d Sekunden',
        m : processRelativeTime,
        mm : '%d Minuten',
        h : processRelativeTime,
        hh : '%d Stunden',
        d : processRelativeTime,
        dd : processRelativeTime,
        M : processRelativeTime,
        MM : processRelativeTime,
        y : processRelativeTime,
        yy : processRelativeTime
    },
    dayOfMonthOrdinalParse: /\d{1,2}\./,
    ordinal : '%d.',
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return de;

})));


/***/ }),
/* 52 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Maldivian [dv]
//! author : Jawish Hameed : https://github.com/jawish

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var months = [
    'ޖެނުއަރީ',
    'ފެބްރުއަރީ',
    'މާރިޗު',
    'އޭޕްރީލު',
    'މޭ',
    'ޖޫން',
    'ޖުލައި',
    'އޯގަސްޓު',
    'ސެޕްޓެމްބަރު',
    'އޮކްޓޯބަރު',
    'ނޮވެމްބަރު',
    'ޑިސެމްބަރު'
];
var weekdays = [
    'އާދިއްތަ',
    'ހޯމަ',
    'އަންގާރަ',
    'ބުދަ',
    'ބުރާސްފަތި',
    'ހުކުރު',
    'ހޮނިހިރު'
];

var dv = moment.defineLocale('dv', {
    months : months,
    monthsShort : months,
    weekdays : weekdays,
    weekdaysShort : weekdays,
    weekdaysMin : 'އާދި_ހޯމަ_އަން_ބުދަ_ބުރާ_ހުކު_ހޮނި'.split('_'),
    longDateFormat : {

        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'D/M/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY HH:mm',
        LLLL : 'dddd D MMMM YYYY HH:mm'
    },
    meridiemParse: /މކ|މފ/,
    isPM : function (input) {
        return 'މފ' === input;
    },
    meridiem : function (hour, minute, isLower) {
        if (hour < 12) {
            return 'މކ';
        } else {
            return 'މފ';
        }
    },
    calendar : {
        sameDay : '[މިއަދު] LT',
        nextDay : '[މާދަމާ] LT',
        nextWeek : 'dddd LT',
        lastDay : '[އިއްޔެ] LT',
        lastWeek : '[ފާއިތުވި] dddd LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : 'ތެރޭގައި %s',
        past : 'ކުރިން %s',
        s : 'ސިކުންތުކޮޅެއް',
        ss : 'd% ސިކުންތު',
        m : 'މިނިޓެއް',
        mm : 'މިނިޓު %d',
        h : 'ގަޑިއިރެއް',
        hh : 'ގަޑިއިރު %d',
        d : 'ދުވަހެއް',
        dd : 'ދުވަސް %d',
        M : 'މަހެއް',
        MM : 'މަސް %d',
        y : 'އަހަރެއް',
        yy : 'އަހަރު %d'
    },
    preparse: function (string) {
        return string.replace(/،/g, ',');
    },
    postformat: function (string) {
        return string.replace(/,/g, '،');
    },
    week : {
        dow : 7,  // Sunday is the first day of the week.
        doy : 12  // The week that contains Jan 1st is the first week of the year.
    }
});

return dv;

})));


/***/ }),
/* 53 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Greek [el]
//! author : Aggelos Karalias : https://github.com/mehiel

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';

function isFunction(input) {
    return input instanceof Function || Object.prototype.toString.call(input) === '[object Function]';
}


var el = moment.defineLocale('el', {
    monthsNominativeEl : 'Ιανουάριος_Φεβρουάριος_Μάρτιος_Απρίλιος_Μάιος_Ιούνιος_Ιούλιος_Αύγουστος_Σεπτέμβριος_Οκτώβριος_Νοέμβριος_Δεκέμβριος'.split('_'),
    monthsGenitiveEl : 'Ιανουαρίου_Φεβρουαρίου_Μαρτίου_Απριλίου_Μαΐου_Ιουνίου_Ιουλίου_Αυγούστου_Σεπτεμβρίου_Οκτωβρίου_Νοεμβρίου_Δεκεμβρίου'.split('_'),
    months : function (momentToFormat, format) {
        if (!momentToFormat) {
            return this._monthsNominativeEl;
        } else if (typeof format === 'string' && /D/.test(format.substring(0, format.indexOf('MMMM')))) { // if there is a day number before 'MMMM'
            return this._monthsGenitiveEl[momentToFormat.month()];
        } else {
            return this._monthsNominativeEl[momentToFormat.month()];
        }
    },
    monthsShort : 'Ιαν_Φεβ_Μαρ_Απρ_Μαϊ_Ιουν_Ιουλ_Αυγ_Σεπ_Οκτ_Νοε_Δεκ'.split('_'),
    weekdays : 'Κυριακή_Δευτέρα_Τρίτη_Τετάρτη_Πέμπτη_Παρασκευή_Σάββατο'.split('_'),
    weekdaysShort : 'Κυρ_Δευ_Τρι_Τετ_Πεμ_Παρ_Σαβ'.split('_'),
    weekdaysMin : 'Κυ_Δε_Τρ_Τε_Πε_Πα_Σα'.split('_'),
    meridiem : function (hours, minutes, isLower) {
        if (hours > 11) {
            return isLower ? 'μμ' : 'ΜΜ';
        } else {
            return isLower ? 'πμ' : 'ΠΜ';
        }
    },
    isPM : function (input) {
        return ((input + '').toLowerCase()[0] === 'μ');
    },
    meridiemParse : /[ΠΜ]\.?Μ?\.?/i,
    longDateFormat : {
        LT : 'h:mm A',
        LTS : 'h:mm:ss A',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY h:mm A',
        LLLL : 'dddd, D MMMM YYYY h:mm A'
    },
    calendarEl : {
        sameDay : '[Σήμερα {}] LT',
        nextDay : '[Αύριο {}] LT',
        nextWeek : 'dddd [{}] LT',
        lastDay : '[Χθες {}] LT',
        lastWeek : function () {
            switch (this.day()) {
                case 6:
                    return '[το προηγούμενο] dddd [{}] LT';
                default:
                    return '[την προηγούμενη] dddd [{}] LT';
            }
        },
        sameElse : 'L'
    },
    calendar : function (key, mom) {
        var output = this._calendarEl[key],
            hours = mom && mom.hours();
        if (isFunction(output)) {
            output = output.apply(mom);
        }
        return output.replace('{}', (hours % 12 === 1 ? 'στη' : 'στις'));
    },
    relativeTime : {
        future : 'σε %s',
        past : '%s πριν',
        s : 'λίγα δευτερόλεπτα',
        ss : '%d δευτερόλεπτα',
        m : 'ένα λεπτό',
        mm : '%d λεπτά',
        h : 'μία ώρα',
        hh : '%d ώρες',
        d : 'μία μέρα',
        dd : '%d μέρες',
        M : 'ένας μήνας',
        MM : '%d μήνες',
        y : 'ένας χρόνος',
        yy : '%d χρόνια'
    },
    dayOfMonthOrdinalParse: /\d{1,2}η/,
    ordinal: '%dη',
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4st is the first week of the year.
    }
});

return el;

})));


/***/ }),
/* 54 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : English (Australia) [en-au]
//! author : Jared Morse : https://github.com/jarcoal

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var enAu = moment.defineLocale('en-au', {
    months : 'January_February_March_April_May_June_July_August_September_October_November_December'.split('_'),
    monthsShort : 'Jan_Feb_Mar_Apr_May_Jun_Jul_Aug_Sep_Oct_Nov_Dec'.split('_'),
    weekdays : 'Sunday_Monday_Tuesday_Wednesday_Thursday_Friday_Saturday'.split('_'),
    weekdaysShort : 'Sun_Mon_Tue_Wed_Thu_Fri_Sat'.split('_'),
    weekdaysMin : 'Su_Mo_Tu_We_Th_Fr_Sa'.split('_'),
    longDateFormat : {
        LT : 'h:mm A',
        LTS : 'h:mm:ss A',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY h:mm A',
        LLLL : 'dddd, D MMMM YYYY h:mm A'
    },
    calendar : {
        sameDay : '[Today at] LT',
        nextDay : '[Tomorrow at] LT',
        nextWeek : 'dddd [at] LT',
        lastDay : '[Yesterday at] LT',
        lastWeek : '[Last] dddd [at] LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : 'in %s',
        past : '%s ago',
        s : 'a few seconds',
        ss : '%d seconds',
        m : 'a minute',
        mm : '%d minutes',
        h : 'an hour',
        hh : '%d hours',
        d : 'a day',
        dd : '%d days',
        M : 'a month',
        MM : '%d months',
        y : 'a year',
        yy : '%d years'
    },
    dayOfMonthOrdinalParse: /\d{1,2}(st|nd|rd|th)/,
    ordinal : function (number) {
        var b = number % 10,
            output = (~~(number % 100 / 10) === 1) ? 'th' :
            (b === 1) ? 'st' :
            (b === 2) ? 'nd' :
            (b === 3) ? 'rd' : 'th';
        return number + output;
    },
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return enAu;

})));


/***/ }),
/* 55 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : English (Canada) [en-ca]
//! author : Jonathan Abourbih : https://github.com/jonbca

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var enCa = moment.defineLocale('en-ca', {
    months : 'January_February_March_April_May_June_July_August_September_October_November_December'.split('_'),
    monthsShort : 'Jan_Feb_Mar_Apr_May_Jun_Jul_Aug_Sep_Oct_Nov_Dec'.split('_'),
    weekdays : 'Sunday_Monday_Tuesday_Wednesday_Thursday_Friday_Saturday'.split('_'),
    weekdaysShort : 'Sun_Mon_Tue_Wed_Thu_Fri_Sat'.split('_'),
    weekdaysMin : 'Su_Mo_Tu_We_Th_Fr_Sa'.split('_'),
    longDateFormat : {
        LT : 'h:mm A',
        LTS : 'h:mm:ss A',
        L : 'YYYY-MM-DD',
        LL : 'MMMM D, YYYY',
        LLL : 'MMMM D, YYYY h:mm A',
        LLLL : 'dddd, MMMM D, YYYY h:mm A'
    },
    calendar : {
        sameDay : '[Today at] LT',
        nextDay : '[Tomorrow at] LT',
        nextWeek : 'dddd [at] LT',
        lastDay : '[Yesterday at] LT',
        lastWeek : '[Last] dddd [at] LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : 'in %s',
        past : '%s ago',
        s : 'a few seconds',
        ss : '%d seconds',
        m : 'a minute',
        mm : '%d minutes',
        h : 'an hour',
        hh : '%d hours',
        d : 'a day',
        dd : '%d days',
        M : 'a month',
        MM : '%d months',
        y : 'a year',
        yy : '%d years'
    },
    dayOfMonthOrdinalParse: /\d{1,2}(st|nd|rd|th)/,
    ordinal : function (number) {
        var b = number % 10,
            output = (~~(number % 100 / 10) === 1) ? 'th' :
            (b === 1) ? 'st' :
            (b === 2) ? 'nd' :
            (b === 3) ? 'rd' : 'th';
        return number + output;
    }
});

return enCa;

})));


/***/ }),
/* 56 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : English (United Kingdom) [en-gb]
//! author : Chris Gedrim : https://github.com/chrisgedrim

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var enGb = moment.defineLocale('en-gb', {
    months : 'January_February_March_April_May_June_July_August_September_October_November_December'.split('_'),
    monthsShort : 'Jan_Feb_Mar_Apr_May_Jun_Jul_Aug_Sep_Oct_Nov_Dec'.split('_'),
    weekdays : 'Sunday_Monday_Tuesday_Wednesday_Thursday_Friday_Saturday'.split('_'),
    weekdaysShort : 'Sun_Mon_Tue_Wed_Thu_Fri_Sat'.split('_'),
    weekdaysMin : 'Su_Mo_Tu_We_Th_Fr_Sa'.split('_'),
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY HH:mm',
        LLLL : 'dddd, D MMMM YYYY HH:mm'
    },
    calendar : {
        sameDay : '[Today at] LT',
        nextDay : '[Tomorrow at] LT',
        nextWeek : 'dddd [at] LT',
        lastDay : '[Yesterday at] LT',
        lastWeek : '[Last] dddd [at] LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : 'in %s',
        past : '%s ago',
        s : 'a few seconds',
        ss : '%d seconds',
        m : 'a minute',
        mm : '%d minutes',
        h : 'an hour',
        hh : '%d hours',
        d : 'a day',
        dd : '%d days',
        M : 'a month',
        MM : '%d months',
        y : 'a year',
        yy : '%d years'
    },
    dayOfMonthOrdinalParse: /\d{1,2}(st|nd|rd|th)/,
    ordinal : function (number) {
        var b = number % 10,
            output = (~~(number % 100 / 10) === 1) ? 'th' :
            (b === 1) ? 'st' :
            (b === 2) ? 'nd' :
            (b === 3) ? 'rd' : 'th';
        return number + output;
    },
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return enGb;

})));


/***/ }),
/* 57 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : English (Ireland) [en-ie]
//! author : Chris Cartlidge : https://github.com/chriscartlidge

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var enIe = moment.defineLocale('en-ie', {
    months : 'January_February_March_April_May_June_July_August_September_October_November_December'.split('_'),
    monthsShort : 'Jan_Feb_Mar_Apr_May_Jun_Jul_Aug_Sep_Oct_Nov_Dec'.split('_'),
    weekdays : 'Sunday_Monday_Tuesday_Wednesday_Thursday_Friday_Saturday'.split('_'),
    weekdaysShort : 'Sun_Mon_Tue_Wed_Thu_Fri_Sat'.split('_'),
    weekdaysMin : 'Su_Mo_Tu_We_Th_Fr_Sa'.split('_'),
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD-MM-YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY HH:mm',
        LLLL : 'dddd D MMMM YYYY HH:mm'
    },
    calendar : {
        sameDay : '[Today at] LT',
        nextDay : '[Tomorrow at] LT',
        nextWeek : 'dddd [at] LT',
        lastDay : '[Yesterday at] LT',
        lastWeek : '[Last] dddd [at] LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : 'in %s',
        past : '%s ago',
        s : 'a few seconds',
        ss : '%d seconds',
        m : 'a minute',
        mm : '%d minutes',
        h : 'an hour',
        hh : '%d hours',
        d : 'a day',
        dd : '%d days',
        M : 'a month',
        MM : '%d months',
        y : 'a year',
        yy : '%d years'
    },
    dayOfMonthOrdinalParse: /\d{1,2}(st|nd|rd|th)/,
    ordinal : function (number) {
        var b = number % 10,
            output = (~~(number % 100 / 10) === 1) ? 'th' :
            (b === 1) ? 'st' :
            (b === 2) ? 'nd' :
            (b === 3) ? 'rd' : 'th';
        return number + output;
    },
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return enIe;

})));


/***/ }),
/* 58 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : English (New Zealand) [en-nz]
//! author : Luke McGregor : https://github.com/lukemcgregor

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var enNz = moment.defineLocale('en-nz', {
    months : 'January_February_March_April_May_June_July_August_September_October_November_December'.split('_'),
    monthsShort : 'Jan_Feb_Mar_Apr_May_Jun_Jul_Aug_Sep_Oct_Nov_Dec'.split('_'),
    weekdays : 'Sunday_Monday_Tuesday_Wednesday_Thursday_Friday_Saturday'.split('_'),
    weekdaysShort : 'Sun_Mon_Tue_Wed_Thu_Fri_Sat'.split('_'),
    weekdaysMin : 'Su_Mo_Tu_We_Th_Fr_Sa'.split('_'),
    longDateFormat : {
        LT : 'h:mm A',
        LTS : 'h:mm:ss A',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY h:mm A',
        LLLL : 'dddd, D MMMM YYYY h:mm A'
    },
    calendar : {
        sameDay : '[Today at] LT',
        nextDay : '[Tomorrow at] LT',
        nextWeek : 'dddd [at] LT',
        lastDay : '[Yesterday at] LT',
        lastWeek : '[Last] dddd [at] LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : 'in %s',
        past : '%s ago',
        s : 'a few seconds',
        ss : '%d seconds',
        m : 'a minute',
        mm : '%d minutes',
        h : 'an hour',
        hh : '%d hours',
        d : 'a day',
        dd : '%d days',
        M : 'a month',
        MM : '%d months',
        y : 'a year',
        yy : '%d years'
    },
    dayOfMonthOrdinalParse: /\d{1,2}(st|nd|rd|th)/,
    ordinal : function (number) {
        var b = number % 10,
            output = (~~(number % 100 / 10) === 1) ? 'th' :
            (b === 1) ? 'st' :
            (b === 2) ? 'nd' :
            (b === 3) ? 'rd' : 'th';
        return number + output;
    },
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return enNz;

})));


/***/ }),
/* 59 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Esperanto [eo]
//! author : Colin Dean : https://github.com/colindean
//! author : Mia Nordentoft Imperatori : https://github.com/miestasmia
//! comment : miestasmia corrected the translation by colindean

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var eo = moment.defineLocale('eo', {
    months : 'januaro_februaro_marto_aprilo_majo_junio_julio_aŭgusto_septembro_oktobro_novembro_decembro'.split('_'),
    monthsShort : 'jan_feb_mar_apr_maj_jun_jul_aŭg_sep_okt_nov_dec'.split('_'),
    weekdays : 'dimanĉo_lundo_mardo_merkredo_ĵaŭdo_vendredo_sabato'.split('_'),
    weekdaysShort : 'dim_lun_mard_merk_ĵaŭ_ven_sab'.split('_'),
    weekdaysMin : 'di_lu_ma_me_ĵa_ve_sa'.split('_'),
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'YYYY-MM-DD',
        LL : 'D[-a de] MMMM, YYYY',
        LLL : 'D[-a de] MMMM, YYYY HH:mm',
        LLLL : 'dddd, [la] D[-a de] MMMM, YYYY HH:mm'
    },
    meridiemParse: /[ap]\.t\.m/i,
    isPM: function (input) {
        return input.charAt(0).toLowerCase() === 'p';
    },
    meridiem : function (hours, minutes, isLower) {
        if (hours > 11) {
            return isLower ? 'p.t.m.' : 'P.T.M.';
        } else {
            return isLower ? 'a.t.m.' : 'A.T.M.';
        }
    },
    calendar : {
        sameDay : '[Hodiaŭ je] LT',
        nextDay : '[Morgaŭ je] LT',
        nextWeek : 'dddd [je] LT',
        lastDay : '[Hieraŭ je] LT',
        lastWeek : '[pasinta] dddd [je] LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : 'post %s',
        past : 'antaŭ %s',
        s : 'sekundoj',
        ss : '%d sekundoj',
        m : 'minuto',
        mm : '%d minutoj',
        h : 'horo',
        hh : '%d horoj',
        d : 'tago',//ne 'diurno', ĉar estas uzita por proksimumo
        dd : '%d tagoj',
        M : 'monato',
        MM : '%d monatoj',
        y : 'jaro',
        yy : '%d jaroj'
    },
    dayOfMonthOrdinalParse: /\d{1,2}a/,
    ordinal : '%da',
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 7  // The week that contains Jan 1st is the first week of the year.
    }
});

return eo;

})));


/***/ }),
/* 60 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Spanish (Dominican Republic) [es-do]

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var monthsShortDot = 'ene._feb._mar._abr._may._jun._jul._ago._sep._oct._nov._dic.'.split('_');
var monthsShort = 'ene_feb_mar_abr_may_jun_jul_ago_sep_oct_nov_dic'.split('_');

var monthsParse = [/^ene/i, /^feb/i, /^mar/i, /^abr/i, /^may/i, /^jun/i, /^jul/i, /^ago/i, /^sep/i, /^oct/i, /^nov/i, /^dic/i];
var monthsRegex = /^(enero|febrero|marzo|abril|mayo|junio|julio|agosto|septiembre|octubre|noviembre|diciembre|ene\.?|feb\.?|mar\.?|abr\.?|may\.?|jun\.?|jul\.?|ago\.?|sep\.?|oct\.?|nov\.?|dic\.?)/i;

var esDo = moment.defineLocale('es-do', {
    months : 'enero_febrero_marzo_abril_mayo_junio_julio_agosto_septiembre_octubre_noviembre_diciembre'.split('_'),
    monthsShort : function (m, format) {
        if (!m) {
            return monthsShortDot;
        } else if (/-MMM-/.test(format)) {
            return monthsShort[m.month()];
        } else {
            return monthsShortDot[m.month()];
        }
    },
    monthsRegex: monthsRegex,
    monthsShortRegex: monthsRegex,
    monthsStrictRegex: /^(enero|febrero|marzo|abril|mayo|junio|julio|agosto|septiembre|octubre|noviembre|diciembre)/i,
    monthsShortStrictRegex: /^(ene\.?|feb\.?|mar\.?|abr\.?|may\.?|jun\.?|jul\.?|ago\.?|sep\.?|oct\.?|nov\.?|dic\.?)/i,
    monthsParse: monthsParse,
    longMonthsParse: monthsParse,
    shortMonthsParse: monthsParse,
    weekdays : 'domingo_lunes_martes_miércoles_jueves_viernes_sábado'.split('_'),
    weekdaysShort : 'dom._lun._mar._mié._jue._vie._sáb.'.split('_'),
    weekdaysMin : 'do_lu_ma_mi_ju_vi_sá'.split('_'),
    weekdaysParseExact : true,
    longDateFormat : {
        LT : 'h:mm A',
        LTS : 'h:mm:ss A',
        L : 'DD/MM/YYYY',
        LL : 'D [de] MMMM [de] YYYY',
        LLL : 'D [de] MMMM [de] YYYY h:mm A',
        LLLL : 'dddd, D [de] MMMM [de] YYYY h:mm A'
    },
    calendar : {
        sameDay : function () {
            return '[hoy a la' + ((this.hours() !== 1) ? 's' : '') + '] LT';
        },
        nextDay : function () {
            return '[mañana a la' + ((this.hours() !== 1) ? 's' : '') + '] LT';
        },
        nextWeek : function () {
            return 'dddd [a la' + ((this.hours() !== 1) ? 's' : '') + '] LT';
        },
        lastDay : function () {
            return '[ayer a la' + ((this.hours() !== 1) ? 's' : '') + '] LT';
        },
        lastWeek : function () {
            return '[el] dddd [pasado a la' + ((this.hours() !== 1) ? 's' : '') + '] LT';
        },
        sameElse : 'L'
    },
    relativeTime : {
        future : 'en %s',
        past : 'hace %s',
        s : 'unos segundos',
        ss : '%d segundos',
        m : 'un minuto',
        mm : '%d minutos',
        h : 'una hora',
        hh : '%d horas',
        d : 'un día',
        dd : '%d días',
        M : 'un mes',
        MM : '%d meses',
        y : 'un año',
        yy : '%d años'
    },
    dayOfMonthOrdinalParse : /\d{1,2}º/,
    ordinal : '%dº',
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return esDo;

})));


/***/ }),
/* 61 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Spanish (United States) [es-us]
//! author : bustta : https://github.com/bustta

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var monthsShortDot = 'ene._feb._mar._abr._may._jun._jul._ago._sep._oct._nov._dic.'.split('_');
var monthsShort = 'ene_feb_mar_abr_may_jun_jul_ago_sep_oct_nov_dic'.split('_');

var esUs = moment.defineLocale('es-us', {
    months : 'enero_febrero_marzo_abril_mayo_junio_julio_agosto_septiembre_octubre_noviembre_diciembre'.split('_'),
    monthsShort : function (m, format) {
        if (!m) {
            return monthsShortDot;
        } else if (/-MMM-/.test(format)) {
            return monthsShort[m.month()];
        } else {
            return monthsShortDot[m.month()];
        }
    },
    monthsParseExact : true,
    weekdays : 'domingo_lunes_martes_miércoles_jueves_viernes_sábado'.split('_'),
    weekdaysShort : 'dom._lun._mar._mié._jue._vie._sáb.'.split('_'),
    weekdaysMin : 'do_lu_ma_mi_ju_vi_sá'.split('_'),
    weekdaysParseExact : true,
    longDateFormat : {
        LT : 'h:mm A',
        LTS : 'h:mm:ss A',
        L : 'MM/DD/YYYY',
        LL : 'MMMM [de] D [de] YYYY',
        LLL : 'MMMM [de] D [de] YYYY h:mm A',
        LLLL : 'dddd, MMMM [de] D [de] YYYY h:mm A'
    },
    calendar : {
        sameDay : function () {
            return '[hoy a la' + ((this.hours() !== 1) ? 's' : '') + '] LT';
        },
        nextDay : function () {
            return '[mañana a la' + ((this.hours() !== 1) ? 's' : '') + '] LT';
        },
        nextWeek : function () {
            return 'dddd [a la' + ((this.hours() !== 1) ? 's' : '') + '] LT';
        },
        lastDay : function () {
            return '[ayer a la' + ((this.hours() !== 1) ? 's' : '') + '] LT';
        },
        lastWeek : function () {
            return '[el] dddd [pasado a la' + ((this.hours() !== 1) ? 's' : '') + '] LT';
        },
        sameElse : 'L'
    },
    relativeTime : {
        future : 'en %s',
        past : 'hace %s',
        s : 'unos segundos',
        ss : '%d segundos',
        m : 'un minuto',
        mm : '%d minutos',
        h : 'una hora',
        hh : '%d horas',
        d : 'un día',
        dd : '%d días',
        M : 'un mes',
        MM : '%d meses',
        y : 'un año',
        yy : '%d años'
    },
    dayOfMonthOrdinalParse : /\d{1,2}º/,
    ordinal : '%dº',
    week : {
        dow : 0, // Sunday is the first day of the week.
        doy : 6  // The week that contains Jan 1st is the first week of the year.
    }
});

return esUs;

})));


/***/ }),
/* 62 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Spanish [es]
//! author : Julio Napurí : https://github.com/julionc

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var monthsShortDot = 'ene._feb._mar._abr._may._jun._jul._ago._sep._oct._nov._dic.'.split('_');
var monthsShort = 'ene_feb_mar_abr_may_jun_jul_ago_sep_oct_nov_dic'.split('_');

var monthsParse = [/^ene/i, /^feb/i, /^mar/i, /^abr/i, /^may/i, /^jun/i, /^jul/i, /^ago/i, /^sep/i, /^oct/i, /^nov/i, /^dic/i];
var monthsRegex = /^(enero|febrero|marzo|abril|mayo|junio|julio|agosto|septiembre|octubre|noviembre|diciembre|ene\.?|feb\.?|mar\.?|abr\.?|may\.?|jun\.?|jul\.?|ago\.?|sep\.?|oct\.?|nov\.?|dic\.?)/i;

var es = moment.defineLocale('es', {
    months : 'enero_febrero_marzo_abril_mayo_junio_julio_agosto_septiembre_octubre_noviembre_diciembre'.split('_'),
    monthsShort : function (m, format) {
        if (!m) {
            return monthsShortDot;
        } else if (/-MMM-/.test(format)) {
            return monthsShort[m.month()];
        } else {
            return monthsShortDot[m.month()];
        }
    },
    monthsRegex : monthsRegex,
    monthsShortRegex : monthsRegex,
    monthsStrictRegex : /^(enero|febrero|marzo|abril|mayo|junio|julio|agosto|septiembre|octubre|noviembre|diciembre)/i,
    monthsShortStrictRegex : /^(ene\.?|feb\.?|mar\.?|abr\.?|may\.?|jun\.?|jul\.?|ago\.?|sep\.?|oct\.?|nov\.?|dic\.?)/i,
    monthsParse : monthsParse,
    longMonthsParse : monthsParse,
    shortMonthsParse : monthsParse,
    weekdays : 'domingo_lunes_martes_miércoles_jueves_viernes_sábado'.split('_'),
    weekdaysShort : 'dom._lun._mar._mié._jue._vie._sáb.'.split('_'),
    weekdaysMin : 'do_lu_ma_mi_ju_vi_sá'.split('_'),
    weekdaysParseExact : true,
    longDateFormat : {
        LT : 'H:mm',
        LTS : 'H:mm:ss',
        L : 'DD/MM/YYYY',
        LL : 'D [de] MMMM [de] YYYY',
        LLL : 'D [de] MMMM [de] YYYY H:mm',
        LLLL : 'dddd, D [de] MMMM [de] YYYY H:mm'
    },
    calendar : {
        sameDay : function () {
            return '[hoy a la' + ((this.hours() !== 1) ? 's' : '') + '] LT';
        },
        nextDay : function () {
            return '[mañana a la' + ((this.hours() !== 1) ? 's' : '') + '] LT';
        },
        nextWeek : function () {
            return 'dddd [a la' + ((this.hours() !== 1) ? 's' : '') + '] LT';
        },
        lastDay : function () {
            return '[ayer a la' + ((this.hours() !== 1) ? 's' : '') + '] LT';
        },
        lastWeek : function () {
            return '[el] dddd [pasado a la' + ((this.hours() !== 1) ? 's' : '') + '] LT';
        },
        sameElse : 'L'
    },
    relativeTime : {
        future : 'en %s',
        past : 'hace %s',
        s : 'unos segundos',
        ss : '%d segundos',
        m : 'un minuto',
        mm : '%d minutos',
        h : 'una hora',
        hh : '%d horas',
        d : 'un día',
        dd : '%d días',
        M : 'un mes',
        MM : '%d meses',
        y : 'un año',
        yy : '%d años'
    },
    dayOfMonthOrdinalParse : /\d{1,2}º/,
    ordinal : '%dº',
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return es;

})));


/***/ }),
/* 63 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Estonian [et]
//! author : Henry Kehlmann : https://github.com/madhenry
//! improvements : Illimar Tambek : https://github.com/ragulka

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


function processRelativeTime(number, withoutSuffix, key, isFuture) {
    var format = {
        's' : ['mõne sekundi', 'mõni sekund', 'paar sekundit'],
        'ss': [number + 'sekundi', number + 'sekundit'],
        'm' : ['ühe minuti', 'üks minut'],
        'mm': [number + ' minuti', number + ' minutit'],
        'h' : ['ühe tunni', 'tund aega', 'üks tund'],
        'hh': [number + ' tunni', number + ' tundi'],
        'd' : ['ühe päeva', 'üks päev'],
        'M' : ['kuu aja', 'kuu aega', 'üks kuu'],
        'MM': [number + ' kuu', number + ' kuud'],
        'y' : ['ühe aasta', 'aasta', 'üks aasta'],
        'yy': [number + ' aasta', number + ' aastat']
    };
    if (withoutSuffix) {
        return format[key][2] ? format[key][2] : format[key][1];
    }
    return isFuture ? format[key][0] : format[key][1];
}

var et = moment.defineLocale('et', {
    months        : 'jaanuar_veebruar_märts_aprill_mai_juuni_juuli_august_september_oktoober_november_detsember'.split('_'),
    monthsShort   : 'jaan_veebr_märts_apr_mai_juuni_juuli_aug_sept_okt_nov_dets'.split('_'),
    weekdays      : 'pühapäev_esmaspäev_teisipäev_kolmapäev_neljapäev_reede_laupäev'.split('_'),
    weekdaysShort : 'P_E_T_K_N_R_L'.split('_'),
    weekdaysMin   : 'P_E_T_K_N_R_L'.split('_'),
    longDateFormat : {
        LT   : 'H:mm',
        LTS : 'H:mm:ss',
        L    : 'DD.MM.YYYY',
        LL   : 'D. MMMM YYYY',
        LLL  : 'D. MMMM YYYY H:mm',
        LLLL : 'dddd, D. MMMM YYYY H:mm'
    },
    calendar : {
        sameDay  : '[Täna,] LT',
        nextDay  : '[Homme,] LT',
        nextWeek : '[Järgmine] dddd LT',
        lastDay  : '[Eile,] LT',
        lastWeek : '[Eelmine] dddd LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : '%s pärast',
        past   : '%s tagasi',
        s      : processRelativeTime,
        ss     : processRelativeTime,
        m      : processRelativeTime,
        mm     : processRelativeTime,
        h      : processRelativeTime,
        hh     : processRelativeTime,
        d      : processRelativeTime,
        dd     : '%d päeva',
        M      : processRelativeTime,
        MM     : processRelativeTime,
        y      : processRelativeTime,
        yy     : processRelativeTime
    },
    dayOfMonthOrdinalParse: /\d{1,2}\./,
    ordinal : '%d.',
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return et;

})));


/***/ }),
/* 64 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Basque [eu]
//! author : Eneko Illarramendi : https://github.com/eillarra

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var eu = moment.defineLocale('eu', {
    months : 'urtarrila_otsaila_martxoa_apirila_maiatza_ekaina_uztaila_abuztua_iraila_urria_azaroa_abendua'.split('_'),
    monthsShort : 'urt._ots._mar._api._mai._eka._uzt._abu._ira._urr._aza._abe.'.split('_'),
    monthsParseExact : true,
    weekdays : 'igandea_astelehena_asteartea_asteazkena_osteguna_ostirala_larunbata'.split('_'),
    weekdaysShort : 'ig._al._ar._az._og._ol._lr.'.split('_'),
    weekdaysMin : 'ig_al_ar_az_og_ol_lr'.split('_'),
    weekdaysParseExact : true,
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'YYYY-MM-DD',
        LL : 'YYYY[ko] MMMM[ren] D[a]',
        LLL : 'YYYY[ko] MMMM[ren] D[a] HH:mm',
        LLLL : 'dddd, YYYY[ko] MMMM[ren] D[a] HH:mm',
        l : 'YYYY-M-D',
        ll : 'YYYY[ko] MMM D[a]',
        lll : 'YYYY[ko] MMM D[a] HH:mm',
        llll : 'ddd, YYYY[ko] MMM D[a] HH:mm'
    },
    calendar : {
        sameDay : '[gaur] LT[etan]',
        nextDay : '[bihar] LT[etan]',
        nextWeek : 'dddd LT[etan]',
        lastDay : '[atzo] LT[etan]',
        lastWeek : '[aurreko] dddd LT[etan]',
        sameElse : 'L'
    },
    relativeTime : {
        future : '%s barru',
        past : 'duela %s',
        s : 'segundo batzuk',
        ss : '%d segundo',
        m : 'minutu bat',
        mm : '%d minutu',
        h : 'ordu bat',
        hh : '%d ordu',
        d : 'egun bat',
        dd : '%d egun',
        M : 'hilabete bat',
        MM : '%d hilabete',
        y : 'urte bat',
        yy : '%d urte'
    },
    dayOfMonthOrdinalParse: /\d{1,2}\./,
    ordinal : '%d.',
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 7  // The week that contains Jan 1st is the first week of the year.
    }
});

return eu;

})));


/***/ }),
/* 65 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Persian [fa]
//! author : Ebrahim Byagowi : https://github.com/ebraminio

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var symbolMap = {
    '1': '۱',
    '2': '۲',
    '3': '۳',
    '4': '۴',
    '5': '۵',
    '6': '۶',
    '7': '۷',
    '8': '۸',
    '9': '۹',
    '0': '۰'
};
var numberMap = {
    '۱': '1',
    '۲': '2',
    '۳': '3',
    '۴': '4',
    '۵': '5',
    '۶': '6',
    '۷': '7',
    '۸': '8',
    '۹': '9',
    '۰': '0'
};

var fa = moment.defineLocale('fa', {
    months : 'ژانویه_فوریه_مارس_آوریل_مه_ژوئن_ژوئیه_اوت_سپتامبر_اکتبر_نوامبر_دسامبر'.split('_'),
    monthsShort : 'ژانویه_فوریه_مارس_آوریل_مه_ژوئن_ژوئیه_اوت_سپتامبر_اکتبر_نوامبر_دسامبر'.split('_'),
    weekdays : 'یک\u200cشنبه_دوشنبه_سه\u200cشنبه_چهارشنبه_پنج\u200cشنبه_جمعه_شنبه'.split('_'),
    weekdaysShort : 'یک\u200cشنبه_دوشنبه_سه\u200cشنبه_چهارشنبه_پنج\u200cشنبه_جمعه_شنبه'.split('_'),
    weekdaysMin : 'ی_د_س_چ_پ_ج_ش'.split('_'),
    weekdaysParseExact : true,
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY HH:mm',
        LLLL : 'dddd, D MMMM YYYY HH:mm'
    },
    meridiemParse: /قبل از ظهر|بعد از ظهر/,
    isPM: function (input) {
        return /بعد از ظهر/.test(input);
    },
    meridiem : function (hour, minute, isLower) {
        if (hour < 12) {
            return 'قبل از ظهر';
        } else {
            return 'بعد از ظهر';
        }
    },
    calendar : {
        sameDay : '[امروز ساعت] LT',
        nextDay : '[فردا ساعت] LT',
        nextWeek : 'dddd [ساعت] LT',
        lastDay : '[دیروز ساعت] LT',
        lastWeek : 'dddd [پیش] [ساعت] LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : 'در %s',
        past : '%s پیش',
        s : 'چند ثانیه',
        ss : 'ثانیه d%',
        m : 'یک دقیقه',
        mm : '%d دقیقه',
        h : 'یک ساعت',
        hh : '%d ساعت',
        d : 'یک روز',
        dd : '%d روز',
        M : 'یک ماه',
        MM : '%d ماه',
        y : 'یک سال',
        yy : '%d سال'
    },
    preparse: function (string) {
        return string.replace(/[۰-۹]/g, function (match) {
            return numberMap[match];
        }).replace(/،/g, ',');
    },
    postformat: function (string) {
        return string.replace(/\d/g, function (match) {
            return symbolMap[match];
        }).replace(/,/g, '،');
    },
    dayOfMonthOrdinalParse: /\d{1,2}م/,
    ordinal : '%dم',
    week : {
        dow : 6, // Saturday is the first day of the week.
        doy : 12 // The week that contains Jan 1st is the first week of the year.
    }
});

return fa;

})));


/***/ }),
/* 66 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Finnish [fi]
//! author : Tarmo Aidantausta : https://github.com/bleadof

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var numbersPast = 'nolla yksi kaksi kolme neljä viisi kuusi seitsemän kahdeksan yhdeksän'.split(' ');
var numbersFuture = [
        'nolla', 'yhden', 'kahden', 'kolmen', 'neljän', 'viiden', 'kuuden',
        numbersPast[7], numbersPast[8], numbersPast[9]
    ];
function translate(number, withoutSuffix, key, isFuture) {
    var result = '';
    switch (key) {
        case 's':
            return isFuture ? 'muutaman sekunnin' : 'muutama sekunti';
        case 'ss':
            return isFuture ? 'sekunnin' : 'sekuntia';
        case 'm':
            return isFuture ? 'minuutin' : 'minuutti';
        case 'mm':
            result = isFuture ? 'minuutin' : 'minuuttia';
            break;
        case 'h':
            return isFuture ? 'tunnin' : 'tunti';
        case 'hh':
            result = isFuture ? 'tunnin' : 'tuntia';
            break;
        case 'd':
            return isFuture ? 'päivän' : 'päivä';
        case 'dd':
            result = isFuture ? 'päivän' : 'päivää';
            break;
        case 'M':
            return isFuture ? 'kuukauden' : 'kuukausi';
        case 'MM':
            result = isFuture ? 'kuukauden' : 'kuukautta';
            break;
        case 'y':
            return isFuture ? 'vuoden' : 'vuosi';
        case 'yy':
            result = isFuture ? 'vuoden' : 'vuotta';
            break;
    }
    result = verbalNumber(number, isFuture) + ' ' + result;
    return result;
}
function verbalNumber(number, isFuture) {
    return number < 10 ? (isFuture ? numbersFuture[number] : numbersPast[number]) : number;
}

var fi = moment.defineLocale('fi', {
    months : 'tammikuu_helmikuu_maaliskuu_huhtikuu_toukokuu_kesäkuu_heinäkuu_elokuu_syyskuu_lokakuu_marraskuu_joulukuu'.split('_'),
    monthsShort : 'tammi_helmi_maalis_huhti_touko_kesä_heinä_elo_syys_loka_marras_joulu'.split('_'),
    weekdays : 'sunnuntai_maanantai_tiistai_keskiviikko_torstai_perjantai_lauantai'.split('_'),
    weekdaysShort : 'su_ma_ti_ke_to_pe_la'.split('_'),
    weekdaysMin : 'su_ma_ti_ke_to_pe_la'.split('_'),
    longDateFormat : {
        LT : 'HH.mm',
        LTS : 'HH.mm.ss',
        L : 'DD.MM.YYYY',
        LL : 'Do MMMM[ta] YYYY',
        LLL : 'Do MMMM[ta] YYYY, [klo] HH.mm',
        LLLL : 'dddd, Do MMMM[ta] YYYY, [klo] HH.mm',
        l : 'D.M.YYYY',
        ll : 'Do MMM YYYY',
        lll : 'Do MMM YYYY, [klo] HH.mm',
        llll : 'ddd, Do MMM YYYY, [klo] HH.mm'
    },
    calendar : {
        sameDay : '[tänään] [klo] LT',
        nextDay : '[huomenna] [klo] LT',
        nextWeek : 'dddd [klo] LT',
        lastDay : '[eilen] [klo] LT',
        lastWeek : '[viime] dddd[na] [klo] LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : '%s päästä',
        past : '%s sitten',
        s : translate,
        ss : translate,
        m : translate,
        mm : translate,
        h : translate,
        hh : translate,
        d : translate,
        dd : translate,
        M : translate,
        MM : translate,
        y : translate,
        yy : translate
    },
    dayOfMonthOrdinalParse: /\d{1,2}\./,
    ordinal : '%d.',
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return fi;

})));


/***/ }),
/* 67 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Faroese [fo]
//! author : Ragnar Johannesen : https://github.com/ragnar123

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var fo = moment.defineLocale('fo', {
    months : 'januar_februar_mars_apríl_mai_juni_juli_august_september_oktober_november_desember'.split('_'),
    monthsShort : 'jan_feb_mar_apr_mai_jun_jul_aug_sep_okt_nov_des'.split('_'),
    weekdays : 'sunnudagur_mánadagur_týsdagur_mikudagur_hósdagur_fríggjadagur_leygardagur'.split('_'),
    weekdaysShort : 'sun_mán_týs_mik_hós_frí_ley'.split('_'),
    weekdaysMin : 'su_má_tý_mi_hó_fr_le'.split('_'),
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY HH:mm',
        LLLL : 'dddd D. MMMM, YYYY HH:mm'
    },
    calendar : {
        sameDay : '[Í dag kl.] LT',
        nextDay : '[Í morgin kl.] LT',
        nextWeek : 'dddd [kl.] LT',
        lastDay : '[Í gjár kl.] LT',
        lastWeek : '[síðstu] dddd [kl] LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : 'um %s',
        past : '%s síðani',
        s : 'fá sekund',
        ss : '%d sekundir',
        m : 'ein minutt',
        mm : '%d minuttir',
        h : 'ein tími',
        hh : '%d tímar',
        d : 'ein dagur',
        dd : '%d dagar',
        M : 'ein mánaði',
        MM : '%d mánaðir',
        y : 'eitt ár',
        yy : '%d ár'
    },
    dayOfMonthOrdinalParse: /\d{1,2}\./,
    ordinal : '%d.',
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return fo;

})));


/***/ }),
/* 68 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : French (Canada) [fr-ca]
//! author : Jonathan Abourbih : https://github.com/jonbca

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var frCa = moment.defineLocale('fr-ca', {
    months : 'janvier_février_mars_avril_mai_juin_juillet_août_septembre_octobre_novembre_décembre'.split('_'),
    monthsShort : 'janv._févr._mars_avr._mai_juin_juil._août_sept._oct._nov._déc.'.split('_'),
    monthsParseExact : true,
    weekdays : 'dimanche_lundi_mardi_mercredi_jeudi_vendredi_samedi'.split('_'),
    weekdaysShort : 'dim._lun._mar._mer._jeu._ven._sam.'.split('_'),
    weekdaysMin : 'di_lu_ma_me_je_ve_sa'.split('_'),
    weekdaysParseExact : true,
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'YYYY-MM-DD',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY HH:mm',
        LLLL : 'dddd D MMMM YYYY HH:mm'
    },
    calendar : {
        sameDay : '[Aujourd’hui à] LT',
        nextDay : '[Demain à] LT',
        nextWeek : 'dddd [à] LT',
        lastDay : '[Hier à] LT',
        lastWeek : 'dddd [dernier à] LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : 'dans %s',
        past : 'il y a %s',
        s : 'quelques secondes',
        ss : '%d secondes',
        m : 'une minute',
        mm : '%d minutes',
        h : 'une heure',
        hh : '%d heures',
        d : 'un jour',
        dd : '%d jours',
        M : 'un mois',
        MM : '%d mois',
        y : 'un an',
        yy : '%d ans'
    },
    dayOfMonthOrdinalParse: /\d{1,2}(er|e)/,
    ordinal : function (number, period) {
        switch (period) {
            // Words with masculine grammatical gender: mois, trimestre, jour
            default:
            case 'M':
            case 'Q':
            case 'D':
            case 'DDD':
            case 'd':
                return number + (number === 1 ? 'er' : 'e');

            // Words with feminine grammatical gender: semaine
            case 'w':
            case 'W':
                return number + (number === 1 ? 're' : 'e');
        }
    }
});

return frCa;

})));


/***/ }),
/* 69 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : French (Switzerland) [fr-ch]
//! author : Gaspard Bucher : https://github.com/gaspard

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var frCh = moment.defineLocale('fr-ch', {
    months : 'janvier_février_mars_avril_mai_juin_juillet_août_septembre_octobre_novembre_décembre'.split('_'),
    monthsShort : 'janv._févr._mars_avr._mai_juin_juil._août_sept._oct._nov._déc.'.split('_'),
    monthsParseExact : true,
    weekdays : 'dimanche_lundi_mardi_mercredi_jeudi_vendredi_samedi'.split('_'),
    weekdaysShort : 'dim._lun._mar._mer._jeu._ven._sam.'.split('_'),
    weekdaysMin : 'di_lu_ma_me_je_ve_sa'.split('_'),
    weekdaysParseExact : true,
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD.MM.YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY HH:mm',
        LLLL : 'dddd D MMMM YYYY HH:mm'
    },
    calendar : {
        sameDay : '[Aujourd’hui à] LT',
        nextDay : '[Demain à] LT',
        nextWeek : 'dddd [à] LT',
        lastDay : '[Hier à] LT',
        lastWeek : 'dddd [dernier à] LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : 'dans %s',
        past : 'il y a %s',
        s : 'quelques secondes',
        ss : '%d secondes',
        m : 'une minute',
        mm : '%d minutes',
        h : 'une heure',
        hh : '%d heures',
        d : 'un jour',
        dd : '%d jours',
        M : 'un mois',
        MM : '%d mois',
        y : 'un an',
        yy : '%d ans'
    },
    dayOfMonthOrdinalParse: /\d{1,2}(er|e)/,
    ordinal : function (number, period) {
        switch (period) {
            // Words with masculine grammatical gender: mois, trimestre, jour
            default:
            case 'M':
            case 'Q':
            case 'D':
            case 'DDD':
            case 'd':
                return number + (number === 1 ? 'er' : 'e');

            // Words with feminine grammatical gender: semaine
            case 'w':
            case 'W':
                return number + (number === 1 ? 're' : 'e');
        }
    },
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return frCh;

})));


/***/ }),
/* 70 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : French [fr]
//! author : John Fischer : https://github.com/jfroffice

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var fr = moment.defineLocale('fr', {
    months : 'janvier_février_mars_avril_mai_juin_juillet_août_septembre_octobre_novembre_décembre'.split('_'),
    monthsShort : 'janv._févr._mars_avr._mai_juin_juil._août_sept._oct._nov._déc.'.split('_'),
    monthsParseExact : true,
    weekdays : 'dimanche_lundi_mardi_mercredi_jeudi_vendredi_samedi'.split('_'),
    weekdaysShort : 'dim._lun._mar._mer._jeu._ven._sam.'.split('_'),
    weekdaysMin : 'di_lu_ma_me_je_ve_sa'.split('_'),
    weekdaysParseExact : true,
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY HH:mm',
        LLLL : 'dddd D MMMM YYYY HH:mm'
    },
    calendar : {
        sameDay : '[Aujourd’hui à] LT',
        nextDay : '[Demain à] LT',
        nextWeek : 'dddd [à] LT',
        lastDay : '[Hier à] LT',
        lastWeek : 'dddd [dernier à] LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : 'dans %s',
        past : 'il y a %s',
        s : 'quelques secondes',
        ss : '%d secondes',
        m : 'une minute',
        mm : '%d minutes',
        h : 'une heure',
        hh : '%d heures',
        d : 'un jour',
        dd : '%d jours',
        M : 'un mois',
        MM : '%d mois',
        y : 'un an',
        yy : '%d ans'
    },
    dayOfMonthOrdinalParse: /\d{1,2}(er|)/,
    ordinal : function (number, period) {
        switch (period) {
            // TODO: Return 'e' when day of month > 1. Move this case inside
            // block for masculine words below.
            // See https://github.com/moment/moment/issues/3375
            case 'D':
                return number + (number === 1 ? 'er' : '');

            // Words with masculine grammatical gender: mois, trimestre, jour
            default:
            case 'M':
            case 'Q':
            case 'DDD':
            case 'd':
                return number + (number === 1 ? 'er' : 'e');

            // Words with feminine grammatical gender: semaine
            case 'w':
            case 'W':
                return number + (number === 1 ? 're' : 'e');
        }
    },
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return fr;

})));


/***/ }),
/* 71 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Frisian [fy]
//! author : Robin van der Vliet : https://github.com/robin0van0der0v

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var monthsShortWithDots = 'jan._feb._mrt._apr._mai_jun._jul._aug._sep._okt._nov._des.'.split('_');
var monthsShortWithoutDots = 'jan_feb_mrt_apr_mai_jun_jul_aug_sep_okt_nov_des'.split('_');

var fy = moment.defineLocale('fy', {
    months : 'jannewaris_febrewaris_maart_april_maaie_juny_july_augustus_septimber_oktober_novimber_desimber'.split('_'),
    monthsShort : function (m, format) {
        if (!m) {
            return monthsShortWithDots;
        } else if (/-MMM-/.test(format)) {
            return monthsShortWithoutDots[m.month()];
        } else {
            return monthsShortWithDots[m.month()];
        }
    },
    monthsParseExact : true,
    weekdays : 'snein_moandei_tiisdei_woansdei_tongersdei_freed_sneon'.split('_'),
    weekdaysShort : 'si._mo._ti._wo._to._fr._so.'.split('_'),
    weekdaysMin : 'Si_Mo_Ti_Wo_To_Fr_So'.split('_'),
    weekdaysParseExact : true,
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD-MM-YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY HH:mm',
        LLLL : 'dddd D MMMM YYYY HH:mm'
    },
    calendar : {
        sameDay: '[hjoed om] LT',
        nextDay: '[moarn om] LT',
        nextWeek: 'dddd [om] LT',
        lastDay: '[juster om] LT',
        lastWeek: '[ôfrûne] dddd [om] LT',
        sameElse: 'L'
    },
    relativeTime : {
        future : 'oer %s',
        past : '%s lyn',
        s : 'in pear sekonden',
        ss : '%d sekonden',
        m : 'ien minút',
        mm : '%d minuten',
        h : 'ien oere',
        hh : '%d oeren',
        d : 'ien dei',
        dd : '%d dagen',
        M : 'ien moanne',
        MM : '%d moannen',
        y : 'ien jier',
        yy : '%d jierren'
    },
    dayOfMonthOrdinalParse: /\d{1,2}(ste|de)/,
    ordinal : function (number) {
        return number + ((number === 1 || number === 8 || number >= 20) ? 'ste' : 'de');
    },
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return fy;

})));


/***/ }),
/* 72 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Scottish Gaelic [gd]
//! author : Jon Ashdown : https://github.com/jonashdown

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var months = [
    'Am Faoilleach', 'An Gearran', 'Am Màrt', 'An Giblean', 'An Cèitean', 'An t-Ògmhios', 'An t-Iuchar', 'An Lùnastal', 'An t-Sultain', 'An Dàmhair', 'An t-Samhain', 'An Dùbhlachd'
];

var monthsShort = ['Faoi', 'Gear', 'Màrt', 'Gibl', 'Cèit', 'Ògmh', 'Iuch', 'Lùn', 'Sult', 'Dàmh', 'Samh', 'Dùbh'];

var weekdays = ['Didòmhnaich', 'Diluain', 'Dimàirt', 'Diciadain', 'Diardaoin', 'Dihaoine', 'Disathairne'];

var weekdaysShort = ['Did', 'Dil', 'Dim', 'Dic', 'Dia', 'Dih', 'Dis'];

var weekdaysMin = ['Dò', 'Lu', 'Mà', 'Ci', 'Ar', 'Ha', 'Sa'];

var gd = moment.defineLocale('gd', {
    months : months,
    monthsShort : monthsShort,
    monthsParseExact : true,
    weekdays : weekdays,
    weekdaysShort : weekdaysShort,
    weekdaysMin : weekdaysMin,
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY HH:mm',
        LLLL : 'dddd, D MMMM YYYY HH:mm'
    },
    calendar : {
        sameDay : '[An-diugh aig] LT',
        nextDay : '[A-màireach aig] LT',
        nextWeek : 'dddd [aig] LT',
        lastDay : '[An-dè aig] LT',
        lastWeek : 'dddd [seo chaidh] [aig] LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : 'ann an %s',
        past : 'bho chionn %s',
        s : 'beagan diogan',
        ss : '%d diogan',
        m : 'mionaid',
        mm : '%d mionaidean',
        h : 'uair',
        hh : '%d uairean',
        d : 'latha',
        dd : '%d latha',
        M : 'mìos',
        MM : '%d mìosan',
        y : 'bliadhna',
        yy : '%d bliadhna'
    },
    dayOfMonthOrdinalParse : /\d{1,2}(d|na|mh)/,
    ordinal : function (number) {
        var output = number === 1 ? 'd' : number % 10 === 2 ? 'na' : 'mh';
        return number + output;
    },
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return gd;

})));


/***/ }),
/* 73 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Galician [gl]
//! author : Juan G. Hurtado : https://github.com/juanghurtado

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var gl = moment.defineLocale('gl', {
    months : 'xaneiro_febreiro_marzo_abril_maio_xuño_xullo_agosto_setembro_outubro_novembro_decembro'.split('_'),
    monthsShort : 'xan._feb._mar._abr._mai._xuñ._xul._ago._set._out._nov._dec.'.split('_'),
    monthsParseExact: true,
    weekdays : 'domingo_luns_martes_mércores_xoves_venres_sábado'.split('_'),
    weekdaysShort : 'dom._lun._mar._mér._xov._ven._sáb.'.split('_'),
    weekdaysMin : 'do_lu_ma_mé_xo_ve_sá'.split('_'),
    weekdaysParseExact : true,
    longDateFormat : {
        LT : 'H:mm',
        LTS : 'H:mm:ss',
        L : 'DD/MM/YYYY',
        LL : 'D [de] MMMM [de] YYYY',
        LLL : 'D [de] MMMM [de] YYYY H:mm',
        LLLL : 'dddd, D [de] MMMM [de] YYYY H:mm'
    },
    calendar : {
        sameDay : function () {
            return '[hoxe ' + ((this.hours() !== 1) ? 'ás' : 'á') + '] LT';
        },
        nextDay : function () {
            return '[mañá ' + ((this.hours() !== 1) ? 'ás' : 'á') + '] LT';
        },
        nextWeek : function () {
            return 'dddd [' + ((this.hours() !== 1) ? 'ás' : 'a') + '] LT';
        },
        lastDay : function () {
            return '[onte ' + ((this.hours() !== 1) ? 'á' : 'a') + '] LT';
        },
        lastWeek : function () {
            return '[o] dddd [pasado ' + ((this.hours() !== 1) ? 'ás' : 'a') + '] LT';
        },
        sameElse : 'L'
    },
    relativeTime : {
        future : function (str) {
            if (str.indexOf('un') === 0) {
                return 'n' + str;
            }
            return 'en ' + str;
        },
        past : 'hai %s',
        s : 'uns segundos',
        ss : '%d segundos',
        m : 'un minuto',
        mm : '%d minutos',
        h : 'unha hora',
        hh : '%d horas',
        d : 'un día',
        dd : '%d días',
        M : 'un mes',
        MM : '%d meses',
        y : 'un ano',
        yy : '%d anos'
    },
    dayOfMonthOrdinalParse : /\d{1,2}º/,
    ordinal : '%dº',
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return gl;

})));


/***/ }),
/* 74 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Konkani Latin script [gom-latn]
//! author : The Discoverer : https://github.com/WikiDiscoverer

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


function processRelativeTime(number, withoutSuffix, key, isFuture) {
    var format = {
        's': ['thodde secondanim', 'thodde second'],
        'ss': [number + ' secondanim', number + ' second'],
        'm': ['eka mintan', 'ek minute'],
        'mm': [number + ' mintanim', number + ' mintam'],
        'h': ['eka horan', 'ek hor'],
        'hh': [number + ' horanim', number + ' hor'],
        'd': ['eka disan', 'ek dis'],
        'dd': [number + ' disanim', number + ' dis'],
        'M': ['eka mhoinean', 'ek mhoino'],
        'MM': [number + ' mhoineanim', number + ' mhoine'],
        'y': ['eka vorsan', 'ek voros'],
        'yy': [number + ' vorsanim', number + ' vorsam']
    };
    return withoutSuffix ? format[key][0] : format[key][1];
}

var gomLatn = moment.defineLocale('gom-latn', {
    months : 'Janer_Febrer_Mars_Abril_Mai_Jun_Julai_Agost_Setembr_Otubr_Novembr_Dezembr'.split('_'),
    monthsShort : 'Jan._Feb._Mars_Abr._Mai_Jun_Jul._Ago._Set._Otu._Nov._Dez.'.split('_'),
    monthsParseExact : true,
    weekdays : 'Aitar_Somar_Mongllar_Budvar_Brestar_Sukrar_Son\'var'.split('_'),
    weekdaysShort : 'Ait._Som._Mon._Bud._Bre._Suk._Son.'.split('_'),
    weekdaysMin : 'Ai_Sm_Mo_Bu_Br_Su_Sn'.split('_'),
    weekdaysParseExact : true,
    longDateFormat : {
        LT : 'A h:mm [vazta]',
        LTS : 'A h:mm:ss [vazta]',
        L : 'DD-MM-YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY A h:mm [vazta]',
        LLLL : 'dddd, MMMM[achea] Do, YYYY, A h:mm [vazta]',
        llll: 'ddd, D MMM YYYY, A h:mm [vazta]'
    },
    calendar : {
        sameDay: '[Aiz] LT',
        nextDay: '[Faleam] LT',
        nextWeek: '[Ieta to] dddd[,] LT',
        lastDay: '[Kal] LT',
        lastWeek: '[Fatlo] dddd[,] LT',
        sameElse: 'L'
    },
    relativeTime : {
        future : '%s',
        past : '%s adim',
        s : processRelativeTime,
        ss : processRelativeTime,
        m : processRelativeTime,
        mm : processRelativeTime,
        h : processRelativeTime,
        hh : processRelativeTime,
        d : processRelativeTime,
        dd : processRelativeTime,
        M : processRelativeTime,
        MM : processRelativeTime,
        y : processRelativeTime,
        yy : processRelativeTime
    },
    dayOfMonthOrdinalParse : /\d{1,2}(er)/,
    ordinal : function (number, period) {
        switch (period) {
            // the ordinal 'er' only applies to day of the month
            case 'D':
                return number + 'er';
            default:
            case 'M':
            case 'Q':
            case 'DDD':
            case 'd':
            case 'w':
            case 'W':
                return number;
        }
    },
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    },
    meridiemParse: /rati|sokalli|donparam|sanje/,
    meridiemHour : function (hour, meridiem) {
        if (hour === 12) {
            hour = 0;
        }
        if (meridiem === 'rati') {
            return hour < 4 ? hour : hour + 12;
        } else if (meridiem === 'sokalli') {
            return hour;
        } else if (meridiem === 'donparam') {
            return hour > 12 ? hour : hour + 12;
        } else if (meridiem === 'sanje') {
            return hour + 12;
        }
    },
    meridiem : function (hour, minute, isLower) {
        if (hour < 4) {
            return 'rati';
        } else if (hour < 12) {
            return 'sokalli';
        } else if (hour < 16) {
            return 'donparam';
        } else if (hour < 20) {
            return 'sanje';
        } else {
            return 'rati';
        }
    }
});

return gomLatn;

})));


/***/ }),
/* 75 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Gujarati [gu]
//! author : Kaushik Thanki : https://github.com/Kaushik1987

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var symbolMap = {
        '1': '૧',
        '2': '૨',
        '3': '૩',
        '4': '૪',
        '5': '૫',
        '6': '૬',
        '7': '૭',
        '8': '૮',
        '9': '૯',
        '0': '૦'
    };
var numberMap = {
        '૧': '1',
        '૨': '2',
        '૩': '3',
        '૪': '4',
        '૫': '5',
        '૬': '6',
        '૭': '7',
        '૮': '8',
        '૯': '9',
        '૦': '0'
    };

var gu = moment.defineLocale('gu', {
    months: 'જાન્યુઆરી_ફેબ્રુઆરી_માર્ચ_એપ્રિલ_મે_જૂન_જુલાઈ_ઑગસ્ટ_સપ્ટેમ્બર_ઑક્ટ્બર_નવેમ્બર_ડિસેમ્બર'.split('_'),
    monthsShort: 'જાન્યુ._ફેબ્રુ._માર્ચ_એપ્રિ._મે_જૂન_જુલા._ઑગ._સપ્ટે._ઑક્ટ્._નવે._ડિસે.'.split('_'),
    monthsParseExact: true,
    weekdays: 'રવિવાર_સોમવાર_મંગળવાર_બુધ્વાર_ગુરુવાર_શુક્રવાર_શનિવાર'.split('_'),
    weekdaysShort: 'રવિ_સોમ_મંગળ_બુધ્_ગુરુ_શુક્ર_શનિ'.split('_'),
    weekdaysMin: 'ર_સો_મં_બુ_ગુ_શુ_શ'.split('_'),
    longDateFormat: {
        LT: 'A h:mm વાગ્યે',
        LTS: 'A h:mm:ss વાગ્યે',
        L: 'DD/MM/YYYY',
        LL: 'D MMMM YYYY',
        LLL: 'D MMMM YYYY, A h:mm વાગ્યે',
        LLLL: 'dddd, D MMMM YYYY, A h:mm વાગ્યે'
    },
    calendar: {
        sameDay: '[આજ] LT',
        nextDay: '[કાલે] LT',
        nextWeek: 'dddd, LT',
        lastDay: '[ગઇકાલે] LT',
        lastWeek: '[પાછલા] dddd, LT',
        sameElse: 'L'
    },
    relativeTime: {
        future: '%s મા',
        past: '%s પેહલા',
        s: 'અમુક પળો',
        ss: '%d સેકંડ',
        m: 'એક મિનિટ',
        mm: '%d મિનિટ',
        h: 'એક કલાક',
        hh: '%d કલાક',
        d: 'એક દિવસ',
        dd: '%d દિવસ',
        M: 'એક મહિનો',
        MM: '%d મહિનો',
        y: 'એક વર્ષ',
        yy: '%d વર્ષ'
    },
    preparse: function (string) {
        return string.replace(/[૧૨૩૪૫૬૭૮૯૦]/g, function (match) {
            return numberMap[match];
        });
    },
    postformat: function (string) {
        return string.replace(/\d/g, function (match) {
            return symbolMap[match];
        });
    },
    // Gujarati notation for meridiems are quite fuzzy in practice. While there exists
    // a rigid notion of a 'Pahar' it is not used as rigidly in modern Gujarati.
    meridiemParse: /રાત|બપોર|સવાર|સાંજ/,
    meridiemHour: function (hour, meridiem) {
        if (hour === 12) {
            hour = 0;
        }
        if (meridiem === 'રાત') {
            return hour < 4 ? hour : hour + 12;
        } else if (meridiem === 'સવાર') {
            return hour;
        } else if (meridiem === 'બપોર') {
            return hour >= 10 ? hour : hour + 12;
        } else if (meridiem === 'સાંજ') {
            return hour + 12;
        }
    },
    meridiem: function (hour, minute, isLower) {
        if (hour < 4) {
            return 'રાત';
        } else if (hour < 10) {
            return 'સવાર';
        } else if (hour < 17) {
            return 'બપોર';
        } else if (hour < 20) {
            return 'સાંજ';
        } else {
            return 'રાત';
        }
    },
    week: {
        dow: 0, // Sunday is the first day of the week.
        doy: 6 // The week that contains Jan 1st is the first week of the year.
    }
});

return gu;

})));


/***/ }),
/* 76 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Hebrew [he]
//! author : Tomer Cohen : https://github.com/tomer
//! author : Moshe Simantov : https://github.com/DevelopmentIL
//! author : Tal Ater : https://github.com/TalAter

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var he = moment.defineLocale('he', {
    months : 'ינואר_פברואר_מרץ_אפריל_מאי_יוני_יולי_אוגוסט_ספטמבר_אוקטובר_נובמבר_דצמבר'.split('_'),
    monthsShort : 'ינו׳_פבר׳_מרץ_אפר׳_מאי_יוני_יולי_אוג׳_ספט׳_אוק׳_נוב׳_דצמ׳'.split('_'),
    weekdays : 'ראשון_שני_שלישי_רביעי_חמישי_שישי_שבת'.split('_'),
    weekdaysShort : 'א׳_ב׳_ג׳_ד׳_ה׳_ו׳_ש׳'.split('_'),
    weekdaysMin : 'א_ב_ג_ד_ה_ו_ש'.split('_'),
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD/MM/YYYY',
        LL : 'D [ב]MMMM YYYY',
        LLL : 'D [ב]MMMM YYYY HH:mm',
        LLLL : 'dddd, D [ב]MMMM YYYY HH:mm',
        l : 'D/M/YYYY',
        ll : 'D MMM YYYY',
        lll : 'D MMM YYYY HH:mm',
        llll : 'ddd, D MMM YYYY HH:mm'
    },
    calendar : {
        sameDay : '[היום ב־]LT',
        nextDay : '[מחר ב־]LT',
        nextWeek : 'dddd [בשעה] LT',
        lastDay : '[אתמול ב־]LT',
        lastWeek : '[ביום] dddd [האחרון בשעה] LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : 'בעוד %s',
        past : 'לפני %s',
        s : 'מספר שניות',
        ss : '%d שניות',
        m : 'דקה',
        mm : '%d דקות',
        h : 'שעה',
        hh : function (number) {
            if (number === 2) {
                return 'שעתיים';
            }
            return number + ' שעות';
        },
        d : 'יום',
        dd : function (number) {
            if (number === 2) {
                return 'יומיים';
            }
            return number + ' ימים';
        },
        M : 'חודש',
        MM : function (number) {
            if (number === 2) {
                return 'חודשיים';
            }
            return number + ' חודשים';
        },
        y : 'שנה',
        yy : function (number) {
            if (number === 2) {
                return 'שנתיים';
            } else if (number % 10 === 0 && number !== 10) {
                return number + ' שנה';
            }
            return number + ' שנים';
        }
    },
    meridiemParse: /אחה"צ|לפנה"צ|אחרי הצהריים|לפני הצהריים|לפנות בוקר|בבוקר|בערב/i,
    isPM : function (input) {
        return /^(אחה"צ|אחרי הצהריים|בערב)$/.test(input);
    },
    meridiem : function (hour, minute, isLower) {
        if (hour < 5) {
            return 'לפנות בוקר';
        } else if (hour < 10) {
            return 'בבוקר';
        } else if (hour < 12) {
            return isLower ? 'לפנה"צ' : 'לפני הצהריים';
        } else if (hour < 18) {
            return isLower ? 'אחה"צ' : 'אחרי הצהריים';
        } else {
            return 'בערב';
        }
    }
});

return he;

})));


/***/ }),
/* 77 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Hindi [hi]
//! author : Mayank Singhal : https://github.com/mayanksinghal

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var symbolMap = {
    '1': '१',
    '2': '२',
    '3': '३',
    '4': '४',
    '5': '५',
    '6': '६',
    '7': '७',
    '8': '८',
    '9': '९',
    '0': '०'
};
var numberMap = {
    '१': '1',
    '२': '2',
    '३': '3',
    '४': '4',
    '५': '5',
    '६': '6',
    '७': '7',
    '८': '8',
    '९': '9',
    '०': '0'
};

var hi = moment.defineLocale('hi', {
    months : 'जनवरी_फ़रवरी_मार्च_अप्रैल_मई_जून_जुलाई_अगस्त_सितम्बर_अक्टूबर_नवम्बर_दिसम्बर'.split('_'),
    monthsShort : 'जन._फ़र._मार्च_अप्रै._मई_जून_जुल._अग._सित._अक्टू._नव._दिस.'.split('_'),
    monthsParseExact: true,
    weekdays : 'रविवार_सोमवार_मंगलवार_बुधवार_गुरूवार_शुक्रवार_शनिवार'.split('_'),
    weekdaysShort : 'रवि_सोम_मंगल_बुध_गुरू_शुक्र_शनि'.split('_'),
    weekdaysMin : 'र_सो_मं_बु_गु_शु_श'.split('_'),
    longDateFormat : {
        LT : 'A h:mm बजे',
        LTS : 'A h:mm:ss बजे',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY, A h:mm बजे',
        LLLL : 'dddd, D MMMM YYYY, A h:mm बजे'
    },
    calendar : {
        sameDay : '[आज] LT',
        nextDay : '[कल] LT',
        nextWeek : 'dddd, LT',
        lastDay : '[कल] LT',
        lastWeek : '[पिछले] dddd, LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : '%s में',
        past : '%s पहले',
        s : 'कुछ ही क्षण',
        ss : '%d सेकंड',
        m : 'एक मिनट',
        mm : '%d मिनट',
        h : 'एक घंटा',
        hh : '%d घंटे',
        d : 'एक दिन',
        dd : '%d दिन',
        M : 'एक महीने',
        MM : '%d महीने',
        y : 'एक वर्ष',
        yy : '%d वर्ष'
    },
    preparse: function (string) {
        return string.replace(/[१२३४५६७८९०]/g, function (match) {
            return numberMap[match];
        });
    },
    postformat: function (string) {
        return string.replace(/\d/g, function (match) {
            return symbolMap[match];
        });
    },
    // Hindi notation for meridiems are quite fuzzy in practice. While there exists
    // a rigid notion of a 'Pahar' it is not used as rigidly in modern Hindi.
    meridiemParse: /रात|सुबह|दोपहर|शाम/,
    meridiemHour : function (hour, meridiem) {
        if (hour === 12) {
            hour = 0;
        }
        if (meridiem === 'रात') {
            return hour < 4 ? hour : hour + 12;
        } else if (meridiem === 'सुबह') {
            return hour;
        } else if (meridiem === 'दोपहर') {
            return hour >= 10 ? hour : hour + 12;
        } else if (meridiem === 'शाम') {
            return hour + 12;
        }
    },
    meridiem : function (hour, minute, isLower) {
        if (hour < 4) {
            return 'रात';
        } else if (hour < 10) {
            return 'सुबह';
        } else if (hour < 17) {
            return 'दोपहर';
        } else if (hour < 20) {
            return 'शाम';
        } else {
            return 'रात';
        }
    },
    week : {
        dow : 0, // Sunday is the first day of the week.
        doy : 6  // The week that contains Jan 1st is the first week of the year.
    }
});

return hi;

})));


/***/ }),
/* 78 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Croatian [hr]
//! author : Bojan Marković : https://github.com/bmarkovic

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


function translate(number, withoutSuffix, key) {
    var result = number + ' ';
    switch (key) {
        case 'ss':
            if (number === 1) {
                result += 'sekunda';
            } else if (number === 2 || number === 3 || number === 4) {
                result += 'sekunde';
            } else {
                result += 'sekundi';
            }
            return result;
        case 'm':
            return withoutSuffix ? 'jedna minuta' : 'jedne minute';
        case 'mm':
            if (number === 1) {
                result += 'minuta';
            } else if (number === 2 || number === 3 || number === 4) {
                result += 'minute';
            } else {
                result += 'minuta';
            }
            return result;
        case 'h':
            return withoutSuffix ? 'jedan sat' : 'jednog sata';
        case 'hh':
            if (number === 1) {
                result += 'sat';
            } else if (number === 2 || number === 3 || number === 4) {
                result += 'sata';
            } else {
                result += 'sati';
            }
            return result;
        case 'dd':
            if (number === 1) {
                result += 'dan';
            } else {
                result += 'dana';
            }
            return result;
        case 'MM':
            if (number === 1) {
                result += 'mjesec';
            } else if (number === 2 || number === 3 || number === 4) {
                result += 'mjeseca';
            } else {
                result += 'mjeseci';
            }
            return result;
        case 'yy':
            if (number === 1) {
                result += 'godina';
            } else if (number === 2 || number === 3 || number === 4) {
                result += 'godine';
            } else {
                result += 'godina';
            }
            return result;
    }
}

var hr = moment.defineLocale('hr', {
    months : {
        format: 'siječnja_veljače_ožujka_travnja_svibnja_lipnja_srpnja_kolovoza_rujna_listopada_studenoga_prosinca'.split('_'),
        standalone: 'siječanj_veljača_ožujak_travanj_svibanj_lipanj_srpanj_kolovoz_rujan_listopad_studeni_prosinac'.split('_')
    },
    monthsShort : 'sij._velj._ožu._tra._svi._lip._srp._kol._ruj._lis._stu._pro.'.split('_'),
    monthsParseExact: true,
    weekdays : 'nedjelja_ponedjeljak_utorak_srijeda_četvrtak_petak_subota'.split('_'),
    weekdaysShort : 'ned._pon._uto._sri._čet._pet._sub.'.split('_'),
    weekdaysMin : 'ne_po_ut_sr_če_pe_su'.split('_'),
    weekdaysParseExact : true,
    longDateFormat : {
        LT : 'H:mm',
        LTS : 'H:mm:ss',
        L : 'DD.MM.YYYY',
        LL : 'D. MMMM YYYY',
        LLL : 'D. MMMM YYYY H:mm',
        LLLL : 'dddd, D. MMMM YYYY H:mm'
    },
    calendar : {
        sameDay  : '[danas u] LT',
        nextDay  : '[sutra u] LT',
        nextWeek : function () {
            switch (this.day()) {
                case 0:
                    return '[u] [nedjelju] [u] LT';
                case 3:
                    return '[u] [srijedu] [u] LT';
                case 6:
                    return '[u] [subotu] [u] LT';
                case 1:
                case 2:
                case 4:
                case 5:
                    return '[u] dddd [u] LT';
            }
        },
        lastDay  : '[jučer u] LT',
        lastWeek : function () {
            switch (this.day()) {
                case 0:
                case 3:
                    return '[prošlu] dddd [u] LT';
                case 6:
                    return '[prošle] [subote] [u] LT';
                case 1:
                case 2:
                case 4:
                case 5:
                    return '[prošli] dddd [u] LT';
            }
        },
        sameElse : 'L'
    },
    relativeTime : {
        future : 'za %s',
        past   : 'prije %s',
        s      : 'par sekundi',
        ss     : translate,
        m      : translate,
        mm     : translate,
        h      : translate,
        hh     : translate,
        d      : 'dan',
        dd     : translate,
        M      : 'mjesec',
        MM     : translate,
        y      : 'godinu',
        yy     : translate
    },
    dayOfMonthOrdinalParse: /\d{1,2}\./,
    ordinal : '%d.',
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 7  // The week that contains Jan 1st is the first week of the year.
    }
});

return hr;

})));


/***/ }),
/* 79 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Hungarian [hu]
//! author : Adam Brunner : https://github.com/adambrunner

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var weekEndings = 'vasárnap hétfőn kedden szerdán csütörtökön pénteken szombaton'.split(' ');
function translate(number, withoutSuffix, key, isFuture) {
    var num = number;
    switch (key) {
        case 's':
            return (isFuture || withoutSuffix) ? 'néhány másodperc' : 'néhány másodperce';
        case 'ss':
            return num + (isFuture || withoutSuffix) ? ' másodperc' : ' másodperce';
        case 'm':
            return 'egy' + (isFuture || withoutSuffix ? ' perc' : ' perce');
        case 'mm':
            return num + (isFuture || withoutSuffix ? ' perc' : ' perce');
        case 'h':
            return 'egy' + (isFuture || withoutSuffix ? ' óra' : ' órája');
        case 'hh':
            return num + (isFuture || withoutSuffix ? ' óra' : ' órája');
        case 'd':
            return 'egy' + (isFuture || withoutSuffix ? ' nap' : ' napja');
        case 'dd':
            return num + (isFuture || withoutSuffix ? ' nap' : ' napja');
        case 'M':
            return 'egy' + (isFuture || withoutSuffix ? ' hónap' : ' hónapja');
        case 'MM':
            return num + (isFuture || withoutSuffix ? ' hónap' : ' hónapja');
        case 'y':
            return 'egy' + (isFuture || withoutSuffix ? ' év' : ' éve');
        case 'yy':
            return num + (isFuture || withoutSuffix ? ' év' : ' éve');
    }
    return '';
}
function week(isFuture) {
    return (isFuture ? '' : '[múlt] ') + '[' + weekEndings[this.day()] + '] LT[-kor]';
}

var hu = moment.defineLocale('hu', {
    months : 'január_február_március_április_május_június_július_augusztus_szeptember_október_november_december'.split('_'),
    monthsShort : 'jan_feb_márc_ápr_máj_jún_júl_aug_szept_okt_nov_dec'.split('_'),
    weekdays : 'vasárnap_hétfő_kedd_szerda_csütörtök_péntek_szombat'.split('_'),
    weekdaysShort : 'vas_hét_kedd_sze_csüt_pén_szo'.split('_'),
    weekdaysMin : 'v_h_k_sze_cs_p_szo'.split('_'),
    longDateFormat : {
        LT : 'H:mm',
        LTS : 'H:mm:ss',
        L : 'YYYY.MM.DD.',
        LL : 'YYYY. MMMM D.',
        LLL : 'YYYY. MMMM D. H:mm',
        LLLL : 'YYYY. MMMM D., dddd H:mm'
    },
    meridiemParse: /de|du/i,
    isPM: function (input) {
        return input.charAt(1).toLowerCase() === 'u';
    },
    meridiem : function (hours, minutes, isLower) {
        if (hours < 12) {
            return isLower === true ? 'de' : 'DE';
        } else {
            return isLower === true ? 'du' : 'DU';
        }
    },
    calendar : {
        sameDay : '[ma] LT[-kor]',
        nextDay : '[holnap] LT[-kor]',
        nextWeek : function () {
            return week.call(this, true);
        },
        lastDay : '[tegnap] LT[-kor]',
        lastWeek : function () {
            return week.call(this, false);
        },
        sameElse : 'L'
    },
    relativeTime : {
        future : '%s múlva',
        past : '%s',
        s : translate,
        ss : translate,
        m : translate,
        mm : translate,
        h : translate,
        hh : translate,
        d : translate,
        dd : translate,
        M : translate,
        MM : translate,
        y : translate,
        yy : translate
    },
    dayOfMonthOrdinalParse: /\d{1,2}\./,
    ordinal : '%d.',
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return hu;

})));


/***/ }),
/* 80 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Armenian [hy-am]
//! author : Armendarabyan : https://github.com/armendarabyan

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var hyAm = moment.defineLocale('hy-am', {
    months : {
        format: 'հունվարի_փետրվարի_մարտի_ապրիլի_մայիսի_հունիսի_հուլիսի_օգոստոսի_սեպտեմբերի_հոկտեմբերի_նոյեմբերի_դեկտեմբերի'.split('_'),
        standalone: 'հունվար_փետրվար_մարտ_ապրիլ_մայիս_հունիս_հուլիս_օգոստոս_սեպտեմբեր_հոկտեմբեր_նոյեմբեր_դեկտեմբեր'.split('_')
    },
    monthsShort : 'հնվ_փտր_մրտ_ապր_մյս_հնս_հլս_օգս_սպտ_հկտ_նմբ_դկտ'.split('_'),
    weekdays : 'կիրակի_երկուշաբթի_երեքշաբթի_չորեքշաբթի_հինգշաբթի_ուրբաթ_շաբաթ'.split('_'),
    weekdaysShort : 'կրկ_երկ_երք_չրք_հնգ_ուրբ_շբթ'.split('_'),
    weekdaysMin : 'կրկ_երկ_երք_չրք_հնգ_ուրբ_շբթ'.split('_'),
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD.MM.YYYY',
        LL : 'D MMMM YYYY թ.',
        LLL : 'D MMMM YYYY թ., HH:mm',
        LLLL : 'dddd, D MMMM YYYY թ., HH:mm'
    },
    calendar : {
        sameDay: '[այսօր] LT',
        nextDay: '[վաղը] LT',
        lastDay: '[երեկ] LT',
        nextWeek: function () {
            return 'dddd [օրը ժամը] LT';
        },
        lastWeek: function () {
            return '[անցած] dddd [օրը ժամը] LT';
        },
        sameElse: 'L'
    },
    relativeTime : {
        future : '%s հետո',
        past : '%s առաջ',
        s : 'մի քանի վայրկյան',
        ss : '%d վայրկյան',
        m : 'րոպե',
        mm : '%d րոպե',
        h : 'ժամ',
        hh : '%d ժամ',
        d : 'օր',
        dd : '%d օր',
        M : 'ամիս',
        MM : '%d ամիս',
        y : 'տարի',
        yy : '%d տարի'
    },
    meridiemParse: /գիշերվա|առավոտվա|ցերեկվա|երեկոյան/,
    isPM: function (input) {
        return /^(ցերեկվա|երեկոյան)$/.test(input);
    },
    meridiem : function (hour) {
        if (hour < 4) {
            return 'գիշերվա';
        } else if (hour < 12) {
            return 'առավոտվա';
        } else if (hour < 17) {
            return 'ցերեկվա';
        } else {
            return 'երեկոյան';
        }
    },
    dayOfMonthOrdinalParse: /\d{1,2}|\d{1,2}-(ին|րդ)/,
    ordinal: function (number, period) {
        switch (period) {
            case 'DDD':
            case 'w':
            case 'W':
            case 'DDDo':
                if (number === 1) {
                    return number + '-ին';
                }
                return number + '-րդ';
            default:
                return number;
        }
    },
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 7  // The week that contains Jan 1st is the first week of the year.
    }
});

return hyAm;

})));


/***/ }),
/* 81 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Indonesian [id]
//! author : Mohammad Satrio Utomo : https://github.com/tyok
//! reference: http://id.wikisource.org/wiki/Pedoman_Umum_Ejaan_Bahasa_Indonesia_yang_Disempurnakan

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var id = moment.defineLocale('id', {
    months : 'Januari_Februari_Maret_April_Mei_Juni_Juli_Agustus_September_Oktober_November_Desember'.split('_'),
    monthsShort : 'Jan_Feb_Mar_Apr_Mei_Jun_Jul_Ags_Sep_Okt_Nov_Des'.split('_'),
    weekdays : 'Minggu_Senin_Selasa_Rabu_Kamis_Jumat_Sabtu'.split('_'),
    weekdaysShort : 'Min_Sen_Sel_Rab_Kam_Jum_Sab'.split('_'),
    weekdaysMin : 'Mg_Sn_Sl_Rb_Km_Jm_Sb'.split('_'),
    longDateFormat : {
        LT : 'HH.mm',
        LTS : 'HH.mm.ss',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY [pukul] HH.mm',
        LLLL : 'dddd, D MMMM YYYY [pukul] HH.mm'
    },
    meridiemParse: /pagi|siang|sore|malam/,
    meridiemHour : function (hour, meridiem) {
        if (hour === 12) {
            hour = 0;
        }
        if (meridiem === 'pagi') {
            return hour;
        } else if (meridiem === 'siang') {
            return hour >= 11 ? hour : hour + 12;
        } else if (meridiem === 'sore' || meridiem === 'malam') {
            return hour + 12;
        }
    },
    meridiem : function (hours, minutes, isLower) {
        if (hours < 11) {
            return 'pagi';
        } else if (hours < 15) {
            return 'siang';
        } else if (hours < 19) {
            return 'sore';
        } else {
            return 'malam';
        }
    },
    calendar : {
        sameDay : '[Hari ini pukul] LT',
        nextDay : '[Besok pukul] LT',
        nextWeek : 'dddd [pukul] LT',
        lastDay : '[Kemarin pukul] LT',
        lastWeek : 'dddd [lalu pukul] LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : 'dalam %s',
        past : '%s yang lalu',
        s : 'beberapa detik',
        ss : '%d detik',
        m : 'semenit',
        mm : '%d menit',
        h : 'sejam',
        hh : '%d jam',
        d : 'sehari',
        dd : '%d hari',
        M : 'sebulan',
        MM : '%d bulan',
        y : 'setahun',
        yy : '%d tahun'
    },
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 7  // The week that contains Jan 1st is the first week of the year.
    }
});

return id;

})));


/***/ }),
/* 82 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Icelandic [is]
//! author : Hinrik Örn Sigurðsson : https://github.com/hinrik

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


function plural(n) {
    if (n % 100 === 11) {
        return true;
    } else if (n % 10 === 1) {
        return false;
    }
    return true;
}
function translate(number, withoutSuffix, key, isFuture) {
    var result = number + ' ';
    switch (key) {
        case 's':
            return withoutSuffix || isFuture ? 'nokkrar sekúndur' : 'nokkrum sekúndum';
        case 'ss':
            if (plural(number)) {
                return result + (withoutSuffix || isFuture ? 'sekúndur' : 'sekúndum');
            }
            return result + 'sekúnda';
        case 'm':
            return withoutSuffix ? 'mínúta' : 'mínútu';
        case 'mm':
            if (plural(number)) {
                return result + (withoutSuffix || isFuture ? 'mínútur' : 'mínútum');
            } else if (withoutSuffix) {
                return result + 'mínúta';
            }
            return result + 'mínútu';
        case 'hh':
            if (plural(number)) {
                return result + (withoutSuffix || isFuture ? 'klukkustundir' : 'klukkustundum');
            }
            return result + 'klukkustund';
        case 'd':
            if (withoutSuffix) {
                return 'dagur';
            }
            return isFuture ? 'dag' : 'degi';
        case 'dd':
            if (plural(number)) {
                if (withoutSuffix) {
                    return result + 'dagar';
                }
                return result + (isFuture ? 'daga' : 'dögum');
            } else if (withoutSuffix) {
                return result + 'dagur';
            }
            return result + (isFuture ? 'dag' : 'degi');
        case 'M':
            if (withoutSuffix) {
                return 'mánuður';
            }
            return isFuture ? 'mánuð' : 'mánuði';
        case 'MM':
            if (plural(number)) {
                if (withoutSuffix) {
                    return result + 'mánuðir';
                }
                return result + (isFuture ? 'mánuði' : 'mánuðum');
            } else if (withoutSuffix) {
                return result + 'mánuður';
            }
            return result + (isFuture ? 'mánuð' : 'mánuði');
        case 'y':
            return withoutSuffix || isFuture ? 'ár' : 'ári';
        case 'yy':
            if (plural(number)) {
                return result + (withoutSuffix || isFuture ? 'ár' : 'árum');
            }
            return result + (withoutSuffix || isFuture ? 'ár' : 'ári');
    }
}

var is = moment.defineLocale('is', {
    months : 'janúar_febrúar_mars_apríl_maí_júní_júlí_ágúst_september_október_nóvember_desember'.split('_'),
    monthsShort : 'jan_feb_mar_apr_maí_jún_júl_ágú_sep_okt_nóv_des'.split('_'),
    weekdays : 'sunnudagur_mánudagur_þriðjudagur_miðvikudagur_fimmtudagur_föstudagur_laugardagur'.split('_'),
    weekdaysShort : 'sun_mán_þri_mið_fim_fös_lau'.split('_'),
    weekdaysMin : 'Su_Má_Þr_Mi_Fi_Fö_La'.split('_'),
    longDateFormat : {
        LT : 'H:mm',
        LTS : 'H:mm:ss',
        L : 'DD.MM.YYYY',
        LL : 'D. MMMM YYYY',
        LLL : 'D. MMMM YYYY [kl.] H:mm',
        LLLL : 'dddd, D. MMMM YYYY [kl.] H:mm'
    },
    calendar : {
        sameDay : '[í dag kl.] LT',
        nextDay : '[á morgun kl.] LT',
        nextWeek : 'dddd [kl.] LT',
        lastDay : '[í gær kl.] LT',
        lastWeek : '[síðasta] dddd [kl.] LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : 'eftir %s',
        past : 'fyrir %s síðan',
        s : translate,
        ss : translate,
        m : translate,
        mm : translate,
        h : 'klukkustund',
        hh : translate,
        d : translate,
        dd : translate,
        M : translate,
        MM : translate,
        y : translate,
        yy : translate
    },
    dayOfMonthOrdinalParse: /\d{1,2}\./,
    ordinal : '%d.',
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return is;

})));


/***/ }),
/* 83 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Italian [it]
//! author : Lorenzo : https://github.com/aliem
//! author: Mattia Larentis: https://github.com/nostalgiaz

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var it = moment.defineLocale('it', {
    months : 'gennaio_febbraio_marzo_aprile_maggio_giugno_luglio_agosto_settembre_ottobre_novembre_dicembre'.split('_'),
    monthsShort : 'gen_feb_mar_apr_mag_giu_lug_ago_set_ott_nov_dic'.split('_'),
    weekdays : 'domenica_lunedì_martedì_mercoledì_giovedì_venerdì_sabato'.split('_'),
    weekdaysShort : 'dom_lun_mar_mer_gio_ven_sab'.split('_'),
    weekdaysMin : 'do_lu_ma_me_gi_ve_sa'.split('_'),
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY HH:mm',
        LLLL : 'dddd D MMMM YYYY HH:mm'
    },
    calendar : {
        sameDay: '[Oggi alle] LT',
        nextDay: '[Domani alle] LT',
        nextWeek: 'dddd [alle] LT',
        lastDay: '[Ieri alle] LT',
        lastWeek: function () {
            switch (this.day()) {
                case 0:
                    return '[la scorsa] dddd [alle] LT';
                default:
                    return '[lo scorso] dddd [alle] LT';
            }
        },
        sameElse: 'L'
    },
    relativeTime : {
        future : function (s) {
            return ((/^[0-9].+$/).test(s) ? 'tra' : 'in') + ' ' + s;
        },
        past : '%s fa',
        s : 'alcuni secondi',
        ss : '%d secondi',
        m : 'un minuto',
        mm : '%d minuti',
        h : 'un\'ora',
        hh : '%d ore',
        d : 'un giorno',
        dd : '%d giorni',
        M : 'un mese',
        MM : '%d mesi',
        y : 'un anno',
        yy : '%d anni'
    },
    dayOfMonthOrdinalParse : /\d{1,2}º/,
    ordinal: '%dº',
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return it;

})));


/***/ }),
/* 84 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Japanese [ja]
//! author : LI Long : https://github.com/baryon

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var ja = moment.defineLocale('ja', {
    months : '1月_2月_3月_4月_5月_6月_7月_8月_9月_10月_11月_12月'.split('_'),
    monthsShort : '1月_2月_3月_4月_5月_6月_7月_8月_9月_10月_11月_12月'.split('_'),
    weekdays : '日曜日_月曜日_火曜日_水曜日_木曜日_金曜日_土曜日'.split('_'),
    weekdaysShort : '日_月_火_水_木_金_土'.split('_'),
    weekdaysMin : '日_月_火_水_木_金_土'.split('_'),
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'YYYY/MM/DD',
        LL : 'YYYY年M月D日',
        LLL : 'YYYY年M月D日 HH:mm',
        LLLL : 'YYYY年M月D日 HH:mm dddd',
        l : 'YYYY/MM/DD',
        ll : 'YYYY年M月D日',
        lll : 'YYYY年M月D日 HH:mm',
        llll : 'YYYY年M月D日 HH:mm dddd'
    },
    meridiemParse: /午前|午後/i,
    isPM : function (input) {
        return input === '午後';
    },
    meridiem : function (hour, minute, isLower) {
        if (hour < 12) {
            return '午前';
        } else {
            return '午後';
        }
    },
    calendar : {
        sameDay : '[今日] LT',
        nextDay : '[明日] LT',
        nextWeek : '[来週]dddd LT',
        lastDay : '[昨日] LT',
        lastWeek : '[前週]dddd LT',
        sameElse : 'L'
    },
    dayOfMonthOrdinalParse : /\d{1,2}日/,
    ordinal : function (number, period) {
        switch (period) {
            case 'd':
            case 'D':
            case 'DDD':
                return number + '日';
            default:
                return number;
        }
    },
    relativeTime : {
        future : '%s後',
        past : '%s前',
        s : '数秒',
        ss : '%d秒',
        m : '1分',
        mm : '%d分',
        h : '1時間',
        hh : '%d時間',
        d : '1日',
        dd : '%d日',
        M : '1ヶ月',
        MM : '%dヶ月',
        y : '1年',
        yy : '%d年'
    }
});

return ja;

})));


/***/ }),
/* 85 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Javanese [jv]
//! author : Rony Lantip : https://github.com/lantip
//! reference: http://jv.wikipedia.org/wiki/Basa_Jawa

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var jv = moment.defineLocale('jv', {
    months : 'Januari_Februari_Maret_April_Mei_Juni_Juli_Agustus_September_Oktober_Nopember_Desember'.split('_'),
    monthsShort : 'Jan_Feb_Mar_Apr_Mei_Jun_Jul_Ags_Sep_Okt_Nop_Des'.split('_'),
    weekdays : 'Minggu_Senen_Seloso_Rebu_Kemis_Jemuwah_Septu'.split('_'),
    weekdaysShort : 'Min_Sen_Sel_Reb_Kem_Jem_Sep'.split('_'),
    weekdaysMin : 'Mg_Sn_Sl_Rb_Km_Jm_Sp'.split('_'),
    longDateFormat : {
        LT : 'HH.mm',
        LTS : 'HH.mm.ss',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY [pukul] HH.mm',
        LLLL : 'dddd, D MMMM YYYY [pukul] HH.mm'
    },
    meridiemParse: /enjing|siyang|sonten|ndalu/,
    meridiemHour : function (hour, meridiem) {
        if (hour === 12) {
            hour = 0;
        }
        if (meridiem === 'enjing') {
            return hour;
        } else if (meridiem === 'siyang') {
            return hour >= 11 ? hour : hour + 12;
        } else if (meridiem === 'sonten' || meridiem === 'ndalu') {
            return hour + 12;
        }
    },
    meridiem : function (hours, minutes, isLower) {
        if (hours < 11) {
            return 'enjing';
        } else if (hours < 15) {
            return 'siyang';
        } else if (hours < 19) {
            return 'sonten';
        } else {
            return 'ndalu';
        }
    },
    calendar : {
        sameDay : '[Dinten puniko pukul] LT',
        nextDay : '[Mbenjang pukul] LT',
        nextWeek : 'dddd [pukul] LT',
        lastDay : '[Kala wingi pukul] LT',
        lastWeek : 'dddd [kepengker pukul] LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : 'wonten ing %s',
        past : '%s ingkang kepengker',
        s : 'sawetawis detik',
        ss : '%d detik',
        m : 'setunggal menit',
        mm : '%d menit',
        h : 'setunggal jam',
        hh : '%d jam',
        d : 'sedinten',
        dd : '%d dinten',
        M : 'sewulan',
        MM : '%d wulan',
        y : 'setaun',
        yy : '%d taun'
    },
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 7  // The week that contains Jan 1st is the first week of the year.
    }
});

return jv;

})));


/***/ }),
/* 86 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Georgian [ka]
//! author : Irakli Janiashvili : https://github.com/irakli-janiashvili

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var ka = moment.defineLocale('ka', {
    months : {
        standalone: 'იანვარი_თებერვალი_მარტი_აპრილი_მაისი_ივნისი_ივლისი_აგვისტო_სექტემბერი_ოქტომბერი_ნოემბერი_დეკემბერი'.split('_'),
        format: 'იანვარს_თებერვალს_მარტს_აპრილის_მაისს_ივნისს_ივლისს_აგვისტს_სექტემბერს_ოქტომბერს_ნოემბერს_დეკემბერს'.split('_')
    },
    monthsShort : 'იან_თებ_მარ_აპრ_მაი_ივნ_ივლ_აგვ_სექ_ოქტ_ნოე_დეკ'.split('_'),
    weekdays : {
        standalone: 'კვირა_ორშაბათი_სამშაბათი_ოთხშაბათი_ხუთშაბათი_პარასკევი_შაბათი'.split('_'),
        format: 'კვირას_ორშაბათს_სამშაბათს_ოთხშაბათს_ხუთშაბათს_პარასკევს_შაბათს'.split('_'),
        isFormat: /(წინა|შემდეგ)/
    },
    weekdaysShort : 'კვი_ორშ_სამ_ოთხ_ხუთ_პარ_შაბ'.split('_'),
    weekdaysMin : 'კვ_ორ_სა_ოთ_ხუ_პა_შა'.split('_'),
    longDateFormat : {
        LT : 'h:mm A',
        LTS : 'h:mm:ss A',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY h:mm A',
        LLLL : 'dddd, D MMMM YYYY h:mm A'
    },
    calendar : {
        sameDay : '[დღეს] LT[-ზე]',
        nextDay : '[ხვალ] LT[-ზე]',
        lastDay : '[გუშინ] LT[-ზე]',
        nextWeek : '[შემდეგ] dddd LT[-ზე]',
        lastWeek : '[წინა] dddd LT-ზე',
        sameElse : 'L'
    },
    relativeTime : {
        future : function (s) {
            return (/(წამი|წუთი|საათი|წელი)/).test(s) ?
                s.replace(/ი$/, 'ში') :
                s + 'ში';
        },
        past : function (s) {
            if ((/(წამი|წუთი|საათი|დღე|თვე)/).test(s)) {
                return s.replace(/(ი|ე)$/, 'ის უკან');
            }
            if ((/წელი/).test(s)) {
                return s.replace(/წელი$/, 'წლის უკან');
            }
        },
        s : 'რამდენიმე წამი',
        ss : '%d წამი',
        m : 'წუთი',
        mm : '%d წუთი',
        h : 'საათი',
        hh : '%d საათი',
        d : 'დღე',
        dd : '%d დღე',
        M : 'თვე',
        MM : '%d თვე',
        y : 'წელი',
        yy : '%d წელი'
    },
    dayOfMonthOrdinalParse: /0|1-ლი|მე-\d{1,2}|\d{1,2}-ე/,
    ordinal : function (number) {
        if (number === 0) {
            return number;
        }
        if (number === 1) {
            return number + '-ლი';
        }
        if ((number < 20) || (number <= 100 && (number % 20 === 0)) || (number % 100 === 0)) {
            return 'მე-' + number;
        }
        return number + '-ე';
    },
    week : {
        dow : 1,
        doy : 7
    }
});

return ka;

})));


/***/ }),
/* 87 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Kazakh [kk]
//! authors : Nurlan Rakhimzhanov : https://github.com/nurlan

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var suffixes = {
    0: '-ші',
    1: '-ші',
    2: '-ші',
    3: '-ші',
    4: '-ші',
    5: '-ші',
    6: '-шы',
    7: '-ші',
    8: '-ші',
    9: '-шы',
    10: '-шы',
    20: '-шы',
    30: '-шы',
    40: '-шы',
    50: '-ші',
    60: '-шы',
    70: '-ші',
    80: '-ші',
    90: '-шы',
    100: '-ші'
};

var kk = moment.defineLocale('kk', {
    months : 'қаңтар_ақпан_наурыз_сәуір_мамыр_маусым_шілде_тамыз_қыркүйек_қазан_қараша_желтоқсан'.split('_'),
    monthsShort : 'қаң_ақп_нау_сәу_мам_мау_шіл_там_қыр_қаз_қар_жел'.split('_'),
    weekdays : 'жексенбі_дүйсенбі_сейсенбі_сәрсенбі_бейсенбі_жұма_сенбі'.split('_'),
    weekdaysShort : 'жек_дүй_сей_сәр_бей_жұм_сен'.split('_'),
    weekdaysMin : 'жк_дй_сй_ср_бй_жм_сн'.split('_'),
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD.MM.YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY HH:mm',
        LLLL : 'dddd, D MMMM YYYY HH:mm'
    },
    calendar : {
        sameDay : '[Бүгін сағат] LT',
        nextDay : '[Ертең сағат] LT',
        nextWeek : 'dddd [сағат] LT',
        lastDay : '[Кеше сағат] LT',
        lastWeek : '[Өткен аптаның] dddd [сағат] LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : '%s ішінде',
        past : '%s бұрын',
        s : 'бірнеше секунд',
        ss : '%d секунд',
        m : 'бір минут',
        mm : '%d минут',
        h : 'бір сағат',
        hh : '%d сағат',
        d : 'бір күн',
        dd : '%d күн',
        M : 'бір ай',
        MM : '%d ай',
        y : 'бір жыл',
        yy : '%d жыл'
    },
    dayOfMonthOrdinalParse: /\d{1,2}-(ші|шы)/,
    ordinal : function (number) {
        var a = number % 10,
            b = number >= 100 ? 100 : null;
        return number + (suffixes[number] || suffixes[a] || suffixes[b]);
    },
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 7  // The week that contains Jan 1st is the first week of the year.
    }
});

return kk;

})));


/***/ }),
/* 88 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Cambodian [km]
//! author : Kruy Vanna : https://github.com/kruyvanna

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var km = moment.defineLocale('km', {
    months: 'មករា_កុម្ភៈ_មីនា_មេសា_ឧសភា_មិថុនា_កក្កដា_សីហា_កញ្ញា_តុលា_វិច្ឆិកា_ធ្នូ'.split('_'),
    monthsShort: 'មករា_កុម្ភៈ_មីនា_មេសា_ឧសភា_មិថុនា_កក្កដា_សីហា_កញ្ញា_តុលា_វិច្ឆិកា_ធ្នូ'.split('_'),
    weekdays: 'អាទិត្យ_ច័ន្ទ_អង្គារ_ពុធ_ព្រហស្បតិ៍_សុក្រ_សៅរ៍'.split('_'),
    weekdaysShort: 'អាទិត្យ_ច័ន្ទ_អង្គារ_ពុធ_ព្រហស្បតិ៍_សុក្រ_សៅរ៍'.split('_'),
    weekdaysMin: 'អាទិត្យ_ច័ន្ទ_អង្គារ_ពុធ_ព្រហស្បតិ៍_សុក្រ_សៅរ៍'.split('_'),
    longDateFormat: {
        LT: 'HH:mm',
        LTS : 'HH:mm:ss',
        L: 'DD/MM/YYYY',
        LL: 'D MMMM YYYY',
        LLL: 'D MMMM YYYY HH:mm',
        LLLL: 'dddd, D MMMM YYYY HH:mm'
    },
    calendar: {
        sameDay: '[ថ្ងៃនេះ ម៉ោង] LT',
        nextDay: '[ស្អែក ម៉ោង] LT',
        nextWeek: 'dddd [ម៉ោង] LT',
        lastDay: '[ម្សិលមិញ ម៉ោង] LT',
        lastWeek: 'dddd [សប្តាហ៍មុន] [ម៉ោង] LT',
        sameElse: 'L'
    },
    relativeTime: {
        future: '%sទៀត',
        past: '%sមុន',
        s: 'ប៉ុន្មានវិនាទី',
        ss: '%d វិនាទី',
        m: 'មួយនាទី',
        mm: '%d នាទី',
        h: 'មួយម៉ោង',
        hh: '%d ម៉ោង',
        d: 'មួយថ្ងៃ',
        dd: '%d ថ្ងៃ',
        M: 'មួយខែ',
        MM: '%d ខែ',
        y: 'មួយឆ្នាំ',
        yy: '%d ឆ្នាំ'
    },
    week: {
        dow: 1, // Monday is the first day of the week.
        doy: 4 // The week that contains Jan 4th is the first week of the year.
    }
});

return km;

})));


/***/ }),
/* 89 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Kannada [kn]
//! author : Rajeev Naik : https://github.com/rajeevnaikte

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var symbolMap = {
    '1': '೧',
    '2': '೨',
    '3': '೩',
    '4': '೪',
    '5': '೫',
    '6': '೬',
    '7': '೭',
    '8': '೮',
    '9': '೯',
    '0': '೦'
};
var numberMap = {
    '೧': '1',
    '೨': '2',
    '೩': '3',
    '೪': '4',
    '೫': '5',
    '೬': '6',
    '೭': '7',
    '೮': '8',
    '೯': '9',
    '೦': '0'
};

var kn = moment.defineLocale('kn', {
    months : 'ಜನವರಿ_ಫೆಬ್ರವರಿ_ಮಾರ್ಚ್_ಏಪ್ರಿಲ್_ಮೇ_ಜೂನ್_ಜುಲೈ_ಆಗಸ್ಟ್_ಸೆಪ್ಟೆಂಬರ್_ಅಕ್ಟೋಬರ್_ನವೆಂಬರ್_ಡಿಸೆಂಬರ್'.split('_'),
    monthsShort : 'ಜನ_ಫೆಬ್ರ_ಮಾರ್ಚ್_ಏಪ್ರಿಲ್_ಮೇ_ಜೂನ್_ಜುಲೈ_ಆಗಸ್ಟ್_ಸೆಪ್ಟೆಂಬ_ಅಕ್ಟೋಬ_ನವೆಂಬ_ಡಿಸೆಂಬ'.split('_'),
    monthsParseExact: true,
    weekdays : 'ಭಾನುವಾರ_ಸೋಮವಾರ_ಮಂಗಳವಾರ_ಬುಧವಾರ_ಗುರುವಾರ_ಶುಕ್ರವಾರ_ಶನಿವಾರ'.split('_'),
    weekdaysShort : 'ಭಾನು_ಸೋಮ_ಮಂಗಳ_ಬುಧ_ಗುರು_ಶುಕ್ರ_ಶನಿ'.split('_'),
    weekdaysMin : 'ಭಾ_ಸೋ_ಮಂ_ಬು_ಗು_ಶು_ಶ'.split('_'),
    longDateFormat : {
        LT : 'A h:mm',
        LTS : 'A h:mm:ss',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY, A h:mm',
        LLLL : 'dddd, D MMMM YYYY, A h:mm'
    },
    calendar : {
        sameDay : '[ಇಂದು] LT',
        nextDay : '[ನಾಳೆ] LT',
        nextWeek : 'dddd, LT',
        lastDay : '[ನಿನ್ನೆ] LT',
        lastWeek : '[ಕೊನೆಯ] dddd, LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : '%s ನಂತರ',
        past : '%s ಹಿಂದೆ',
        s : 'ಕೆಲವು ಕ್ಷಣಗಳು',
        ss : '%d ಸೆಕೆಂಡುಗಳು',
        m : 'ಒಂದು ನಿಮಿಷ',
        mm : '%d ನಿಮಿಷ',
        h : 'ಒಂದು ಗಂಟೆ',
        hh : '%d ಗಂಟೆ',
        d : 'ಒಂದು ದಿನ',
        dd : '%d ದಿನ',
        M : 'ಒಂದು ತಿಂಗಳು',
        MM : '%d ತಿಂಗಳು',
        y : 'ಒಂದು ವರ್ಷ',
        yy : '%d ವರ್ಷ'
    },
    preparse: function (string) {
        return string.replace(/[೧೨೩೪೫೬೭೮೯೦]/g, function (match) {
            return numberMap[match];
        });
    },
    postformat: function (string) {
        return string.replace(/\d/g, function (match) {
            return symbolMap[match];
        });
    },
    meridiemParse: /ರಾತ್ರಿ|ಬೆಳಿಗ್ಗೆ|ಮಧ್ಯಾಹ್ನ|ಸಂಜೆ/,
    meridiemHour : function (hour, meridiem) {
        if (hour === 12) {
            hour = 0;
        }
        if (meridiem === 'ರಾತ್ರಿ') {
            return hour < 4 ? hour : hour + 12;
        } else if (meridiem === 'ಬೆಳಿಗ್ಗೆ') {
            return hour;
        } else if (meridiem === 'ಮಧ್ಯಾಹ್ನ') {
            return hour >= 10 ? hour : hour + 12;
        } else if (meridiem === 'ಸಂಜೆ') {
            return hour + 12;
        }
    },
    meridiem : function (hour, minute, isLower) {
        if (hour < 4) {
            return 'ರಾತ್ರಿ';
        } else if (hour < 10) {
            return 'ಬೆಳಿಗ್ಗೆ';
        } else if (hour < 17) {
            return 'ಮಧ್ಯಾಹ್ನ';
        } else if (hour < 20) {
            return 'ಸಂಜೆ';
        } else {
            return 'ರಾತ್ರಿ';
        }
    },
    dayOfMonthOrdinalParse: /\d{1,2}(ನೇ)/,
    ordinal : function (number) {
        return number + 'ನೇ';
    },
    week : {
        dow : 0, // Sunday is the first day of the week.
        doy : 6  // The week that contains Jan 1st is the first week of the year.
    }
});

return kn;

})));


/***/ }),
/* 90 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Korean [ko]
//! author : Kyungwook, Park : https://github.com/kyungw00k
//! author : Jeeeyul Lee <jeeeyul@gmail.com>

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var ko = moment.defineLocale('ko', {
    months : '1월_2월_3월_4월_5월_6월_7월_8월_9월_10월_11월_12월'.split('_'),
    monthsShort : '1월_2월_3월_4월_5월_6월_7월_8월_9월_10월_11월_12월'.split('_'),
    weekdays : '일요일_월요일_화요일_수요일_목요일_금요일_토요일'.split('_'),
    weekdaysShort : '일_월_화_수_목_금_토'.split('_'),
    weekdaysMin : '일_월_화_수_목_금_토'.split('_'),
    longDateFormat : {
        LT : 'A h:mm',
        LTS : 'A h:mm:ss',
        L : 'YYYY.MM.DD',
        LL : 'YYYY년 MMMM D일',
        LLL : 'YYYY년 MMMM D일 A h:mm',
        LLLL : 'YYYY년 MMMM D일 dddd A h:mm',
        l : 'YYYY.MM.DD',
        ll : 'YYYY년 MMMM D일',
        lll : 'YYYY년 MMMM D일 A h:mm',
        llll : 'YYYY년 MMMM D일 dddd A h:mm'
    },
    calendar : {
        sameDay : '오늘 LT',
        nextDay : '내일 LT',
        nextWeek : 'dddd LT',
        lastDay : '어제 LT',
        lastWeek : '지난주 dddd LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : '%s 후',
        past : '%s 전',
        s : '몇 초',
        ss : '%d초',
        m : '1분',
        mm : '%d분',
        h : '한 시간',
        hh : '%d시간',
        d : '하루',
        dd : '%d일',
        M : '한 달',
        MM : '%d달',
        y : '일 년',
        yy : '%d년'
    },
    dayOfMonthOrdinalParse : /\d{1,2}(일|월|주)/,
    ordinal : function (number, period) {
        switch (period) {
            case 'd':
            case 'D':
            case 'DDD':
                return number + '일';
            case 'M':
                return number + '월';
            case 'w':
            case 'W':
                return number + '주';
            default:
                return number;
        }
    },
    meridiemParse : /오전|오후/,
    isPM : function (token) {
        return token === '오후';
    },
    meridiem : function (hour, minute, isUpper) {
        return hour < 12 ? '오전' : '오후';
    }
});

return ko;

})));


/***/ }),
/* 91 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Kyrgyz [ky]
//! author : Chyngyz Arystan uulu : https://github.com/chyngyz

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';



var suffixes = {
    0: '-чү',
    1: '-чи',
    2: '-чи',
    3: '-чү',
    4: '-чү',
    5: '-чи',
    6: '-чы',
    7: '-чи',
    8: '-чи',
    9: '-чу',
    10: '-чу',
    20: '-чы',
    30: '-чу',
    40: '-чы',
    50: '-чү',
    60: '-чы',
    70: '-чи',
    80: '-чи',
    90: '-чу',
    100: '-чү'
};

var ky = moment.defineLocale('ky', {
    months : 'январь_февраль_март_апрель_май_июнь_июль_август_сентябрь_октябрь_ноябрь_декабрь'.split('_'),
    monthsShort : 'янв_фев_март_апр_май_июнь_июль_авг_сен_окт_ноя_дек'.split('_'),
    weekdays : 'Жекшемби_Дүйшөмбү_Шейшемби_Шаршемби_Бейшемби_Жума_Ишемби'.split('_'),
    weekdaysShort : 'Жек_Дүй_Шей_Шар_Бей_Жум_Ише'.split('_'),
    weekdaysMin : 'Жк_Дй_Шй_Шр_Бй_Жм_Иш'.split('_'),
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD.MM.YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY HH:mm',
        LLLL : 'dddd, D MMMM YYYY HH:mm'
    },
    calendar : {
        sameDay : '[Бүгүн саат] LT',
        nextDay : '[Эртең саат] LT',
        nextWeek : 'dddd [саат] LT',
        lastDay : '[Кече саат] LT',
        lastWeek : '[Өткен аптанын] dddd [күнү] [саат] LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : '%s ичинде',
        past : '%s мурун',
        s : 'бирнече секунд',
        ss : '%d секунд',
        m : 'бир мүнөт',
        mm : '%d мүнөт',
        h : 'бир саат',
        hh : '%d саат',
        d : 'бир күн',
        dd : '%d күн',
        M : 'бир ай',
        MM : '%d ай',
        y : 'бир жыл',
        yy : '%d жыл'
    },
    dayOfMonthOrdinalParse: /\d{1,2}-(чи|чы|чү|чу)/,
    ordinal : function (number) {
        var a = number % 10,
            b = number >= 100 ? 100 : null;
        return number + (suffixes[number] || suffixes[a] || suffixes[b]);
    },
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 7  // The week that contains Jan 1st is the first week of the year.
    }
});

return ky;

})));


/***/ }),
/* 92 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Luxembourgish [lb]
//! author : mweimerskirch : https://github.com/mweimerskirch
//! author : David Raison : https://github.com/kwisatz

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


function processRelativeTime(number, withoutSuffix, key, isFuture) {
    var format = {
        'm': ['eng Minutt', 'enger Minutt'],
        'h': ['eng Stonn', 'enger Stonn'],
        'd': ['een Dag', 'engem Dag'],
        'M': ['ee Mount', 'engem Mount'],
        'y': ['ee Joer', 'engem Joer']
    };
    return withoutSuffix ? format[key][0] : format[key][1];
}
function processFutureTime(string) {
    var number = string.substr(0, string.indexOf(' '));
    if (eifelerRegelAppliesToNumber(number)) {
        return 'a ' + string;
    }
    return 'an ' + string;
}
function processPastTime(string) {
    var number = string.substr(0, string.indexOf(' '));
    if (eifelerRegelAppliesToNumber(number)) {
        return 'viru ' + string;
    }
    return 'virun ' + string;
}
/**
 * Returns true if the word before the given number loses the '-n' ending.
 * e.g. 'an 10 Deeg' but 'a 5 Deeg'
 *
 * @param number {integer}
 * @returns {boolean}
 */
function eifelerRegelAppliesToNumber(number) {
    number = parseInt(number, 10);
    if (isNaN(number)) {
        return false;
    }
    if (number < 0) {
        // Negative Number --> always true
        return true;
    } else if (number < 10) {
        // Only 1 digit
        if (4 <= number && number <= 7) {
            return true;
        }
        return false;
    } else if (number < 100) {
        // 2 digits
        var lastDigit = number % 10, firstDigit = number / 10;
        if (lastDigit === 0) {
            return eifelerRegelAppliesToNumber(firstDigit);
        }
        return eifelerRegelAppliesToNumber(lastDigit);
    } else if (number < 10000) {
        // 3 or 4 digits --> recursively check first digit
        while (number >= 10) {
            number = number / 10;
        }
        return eifelerRegelAppliesToNumber(number);
    } else {
        // Anything larger than 4 digits: recursively check first n-3 digits
        number = number / 1000;
        return eifelerRegelAppliesToNumber(number);
    }
}

var lb = moment.defineLocale('lb', {
    months: 'Januar_Februar_Mäerz_Abrëll_Mee_Juni_Juli_August_September_Oktober_November_Dezember'.split('_'),
    monthsShort: 'Jan._Febr._Mrz._Abr._Mee_Jun._Jul._Aug._Sept._Okt._Nov._Dez.'.split('_'),
    monthsParseExact : true,
    weekdays: 'Sonndeg_Méindeg_Dënschdeg_Mëttwoch_Donneschdeg_Freideg_Samschdeg'.split('_'),
    weekdaysShort: 'So._Mé._Dë._Më._Do._Fr._Sa.'.split('_'),
    weekdaysMin: 'So_Mé_Dë_Më_Do_Fr_Sa'.split('_'),
    weekdaysParseExact : true,
    longDateFormat: {
        LT: 'H:mm [Auer]',
        LTS: 'H:mm:ss [Auer]',
        L: 'DD.MM.YYYY',
        LL: 'D. MMMM YYYY',
        LLL: 'D. MMMM YYYY H:mm [Auer]',
        LLLL: 'dddd, D. MMMM YYYY H:mm [Auer]'
    },
    calendar: {
        sameDay: '[Haut um] LT',
        sameElse: 'L',
        nextDay: '[Muer um] LT',
        nextWeek: 'dddd [um] LT',
        lastDay: '[Gëschter um] LT',
        lastWeek: function () {
            // Different date string for 'Dënschdeg' (Tuesday) and 'Donneschdeg' (Thursday) due to phonological rule
            switch (this.day()) {
                case 2:
                case 4:
                    return '[Leschten] dddd [um] LT';
                default:
                    return '[Leschte] dddd [um] LT';
            }
        }
    },
    relativeTime : {
        future : processFutureTime,
        past : processPastTime,
        s : 'e puer Sekonnen',
        ss : '%d Sekonnen',
        m : processRelativeTime,
        mm : '%d Minutten',
        h : processRelativeTime,
        hh : '%d Stonnen',
        d : processRelativeTime,
        dd : '%d Deeg',
        M : processRelativeTime,
        MM : '%d Méint',
        y : processRelativeTime,
        yy : '%d Joer'
    },
    dayOfMonthOrdinalParse: /\d{1,2}\./,
    ordinal: '%d.',
    week: {
        dow: 1, // Monday is the first day of the week.
        doy: 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return lb;

})));


/***/ }),
/* 93 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Lao [lo]
//! author : Ryan Hart : https://github.com/ryanhart2

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var lo = moment.defineLocale('lo', {
    months : 'ມັງກອນ_ກຸມພາ_ມີນາ_ເມສາ_ພຶດສະພາ_ມິຖຸນາ_ກໍລະກົດ_ສິງຫາ_ກັນຍາ_ຕຸລາ_ພະຈິກ_ທັນວາ'.split('_'),
    monthsShort : 'ມັງກອນ_ກຸມພາ_ມີນາ_ເມສາ_ພຶດສະພາ_ມິຖຸນາ_ກໍລະກົດ_ສິງຫາ_ກັນຍາ_ຕຸລາ_ພະຈິກ_ທັນວາ'.split('_'),
    weekdays : 'ອາທິດ_ຈັນ_ອັງຄານ_ພຸດ_ພະຫັດ_ສຸກ_ເສົາ'.split('_'),
    weekdaysShort : 'ທິດ_ຈັນ_ອັງຄານ_ພຸດ_ພະຫັດ_ສຸກ_ເສົາ'.split('_'),
    weekdaysMin : 'ທ_ຈ_ອຄ_ພ_ພຫ_ສກ_ສ'.split('_'),
    weekdaysParseExact : true,
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY HH:mm',
        LLLL : 'ວັນdddd D MMMM YYYY HH:mm'
    },
    meridiemParse: /ຕອນເຊົ້າ|ຕອນແລງ/,
    isPM: function (input) {
        return input === 'ຕອນແລງ';
    },
    meridiem : function (hour, minute, isLower) {
        if (hour < 12) {
            return 'ຕອນເຊົ້າ';
        } else {
            return 'ຕອນແລງ';
        }
    },
    calendar : {
        sameDay : '[ມື້ນີ້ເວລາ] LT',
        nextDay : '[ມື້ອື່ນເວລາ] LT',
        nextWeek : '[ວັນ]dddd[ໜ້າເວລາ] LT',
        lastDay : '[ມື້ວານນີ້ເວລາ] LT',
        lastWeek : '[ວັນ]dddd[ແລ້ວນີ້ເວລາ] LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : 'ອີກ %s',
        past : '%sຜ່ານມາ',
        s : 'ບໍ່ເທົ່າໃດວິນາທີ',
        ss : '%d ວິນາທີ' ,
        m : '1 ນາທີ',
        mm : '%d ນາທີ',
        h : '1 ຊົ່ວໂມງ',
        hh : '%d ຊົ່ວໂມງ',
        d : '1 ມື້',
        dd : '%d ມື້',
        M : '1 ເດືອນ',
        MM : '%d ເດືອນ',
        y : '1 ປີ',
        yy : '%d ປີ'
    },
    dayOfMonthOrdinalParse: /(ທີ່)\d{1,2}/,
    ordinal : function (number) {
        return 'ທີ່' + number;
    }
});

return lo;

})));


/***/ }),
/* 94 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Lithuanian [lt]
//! author : Mindaugas Mozūras : https://github.com/mmozuras

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var units = {
    'ss' : 'sekundė_sekundžių_sekundes',
    'm' : 'minutė_minutės_minutę',
    'mm': 'minutės_minučių_minutes',
    'h' : 'valanda_valandos_valandą',
    'hh': 'valandos_valandų_valandas',
    'd' : 'diena_dienos_dieną',
    'dd': 'dienos_dienų_dienas',
    'M' : 'mėnuo_mėnesio_mėnesį',
    'MM': 'mėnesiai_mėnesių_mėnesius',
    'y' : 'metai_metų_metus',
    'yy': 'metai_metų_metus'
};
function translateSeconds(number, withoutSuffix, key, isFuture) {
    if (withoutSuffix) {
        return 'kelios sekundės';
    } else {
        return isFuture ? 'kelių sekundžių' : 'kelias sekundes';
    }
}
function translateSingular(number, withoutSuffix, key, isFuture) {
    return withoutSuffix ? forms(key)[0] : (isFuture ? forms(key)[1] : forms(key)[2]);
}
function special(number) {
    return number % 10 === 0 || (number > 10 && number < 20);
}
function forms(key) {
    return units[key].split('_');
}
function translate(number, withoutSuffix, key, isFuture) {
    var result = number + ' ';
    if (number === 1) {
        return result + translateSingular(number, withoutSuffix, key[0], isFuture);
    } else if (withoutSuffix) {
        return result + (special(number) ? forms(key)[1] : forms(key)[0]);
    } else {
        if (isFuture) {
            return result + forms(key)[1];
        } else {
            return result + (special(number) ? forms(key)[1] : forms(key)[2]);
        }
    }
}
var lt = moment.defineLocale('lt', {
    months : {
        format: 'sausio_vasario_kovo_balandžio_gegužės_birželio_liepos_rugpjūčio_rugsėjo_spalio_lapkričio_gruodžio'.split('_'),
        standalone: 'sausis_vasaris_kovas_balandis_gegužė_birželis_liepa_rugpjūtis_rugsėjis_spalis_lapkritis_gruodis'.split('_'),
        isFormat: /D[oD]?(\[[^\[\]]*\]|\s)+MMMM?|MMMM?(\[[^\[\]]*\]|\s)+D[oD]?/
    },
    monthsShort : 'sau_vas_kov_bal_geg_bir_lie_rgp_rgs_spa_lap_grd'.split('_'),
    weekdays : {
        format: 'sekmadienį_pirmadienį_antradienį_trečiadienį_ketvirtadienį_penktadienį_šeštadienį'.split('_'),
        standalone: 'sekmadienis_pirmadienis_antradienis_trečiadienis_ketvirtadienis_penktadienis_šeštadienis'.split('_'),
        isFormat: /dddd HH:mm/
    },
    weekdaysShort : 'Sek_Pir_Ant_Tre_Ket_Pen_Šeš'.split('_'),
    weekdaysMin : 'S_P_A_T_K_Pn_Š'.split('_'),
    weekdaysParseExact : true,
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'YYYY-MM-DD',
        LL : 'YYYY [m.] MMMM D [d.]',
        LLL : 'YYYY [m.] MMMM D [d.], HH:mm [val.]',
        LLLL : 'YYYY [m.] MMMM D [d.], dddd, HH:mm [val.]',
        l : 'YYYY-MM-DD',
        ll : 'YYYY [m.] MMMM D [d.]',
        lll : 'YYYY [m.] MMMM D [d.], HH:mm [val.]',
        llll : 'YYYY [m.] MMMM D [d.], ddd, HH:mm [val.]'
    },
    calendar : {
        sameDay : '[Šiandien] LT',
        nextDay : '[Rytoj] LT',
        nextWeek : 'dddd LT',
        lastDay : '[Vakar] LT',
        lastWeek : '[Praėjusį] dddd LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : 'po %s',
        past : 'prieš %s',
        s : translateSeconds,
        ss : translate,
        m : translateSingular,
        mm : translate,
        h : translateSingular,
        hh : translate,
        d : translateSingular,
        dd : translate,
        M : translateSingular,
        MM : translate,
        y : translateSingular,
        yy : translate
    },
    dayOfMonthOrdinalParse: /\d{1,2}-oji/,
    ordinal : function (number) {
        return number + '-oji';
    },
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return lt;

})));


/***/ }),
/* 95 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Latvian [lv]
//! author : Kristaps Karlsons : https://github.com/skakri
//! author : Jānis Elmeris : https://github.com/JanisE

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var units = {
    'ss': 'sekundes_sekundēm_sekunde_sekundes'.split('_'),
    'm': 'minūtes_minūtēm_minūte_minūtes'.split('_'),
    'mm': 'minūtes_minūtēm_minūte_minūtes'.split('_'),
    'h': 'stundas_stundām_stunda_stundas'.split('_'),
    'hh': 'stundas_stundām_stunda_stundas'.split('_'),
    'd': 'dienas_dienām_diena_dienas'.split('_'),
    'dd': 'dienas_dienām_diena_dienas'.split('_'),
    'M': 'mēneša_mēnešiem_mēnesis_mēneši'.split('_'),
    'MM': 'mēneša_mēnešiem_mēnesis_mēneši'.split('_'),
    'y': 'gada_gadiem_gads_gadi'.split('_'),
    'yy': 'gada_gadiem_gads_gadi'.split('_')
};
/**
 * @param withoutSuffix boolean true = a length of time; false = before/after a period of time.
 */
function format(forms, number, withoutSuffix) {
    if (withoutSuffix) {
        // E.g. "21 minūte", "3 minūtes".
        return number % 10 === 1 && number % 100 !== 11 ? forms[2] : forms[3];
    } else {
        // E.g. "21 minūtes" as in "pēc 21 minūtes".
        // E.g. "3 minūtēm" as in "pēc 3 minūtēm".
        return number % 10 === 1 && number % 100 !== 11 ? forms[0] : forms[1];
    }
}
function relativeTimeWithPlural(number, withoutSuffix, key) {
    return number + ' ' + format(units[key], number, withoutSuffix);
}
function relativeTimeWithSingular(number, withoutSuffix, key) {
    return format(units[key], number, withoutSuffix);
}
function relativeSeconds(number, withoutSuffix) {
    return withoutSuffix ? 'dažas sekundes' : 'dažām sekundēm';
}

var lv = moment.defineLocale('lv', {
    months : 'janvāris_februāris_marts_aprīlis_maijs_jūnijs_jūlijs_augusts_septembris_oktobris_novembris_decembris'.split('_'),
    monthsShort : 'jan_feb_mar_apr_mai_jūn_jūl_aug_sep_okt_nov_dec'.split('_'),
    weekdays : 'svētdiena_pirmdiena_otrdiena_trešdiena_ceturtdiena_piektdiena_sestdiena'.split('_'),
    weekdaysShort : 'Sv_P_O_T_C_Pk_S'.split('_'),
    weekdaysMin : 'Sv_P_O_T_C_Pk_S'.split('_'),
    weekdaysParseExact : true,
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD.MM.YYYY.',
        LL : 'YYYY. [gada] D. MMMM',
        LLL : 'YYYY. [gada] D. MMMM, HH:mm',
        LLLL : 'YYYY. [gada] D. MMMM, dddd, HH:mm'
    },
    calendar : {
        sameDay : '[Šodien pulksten] LT',
        nextDay : '[Rīt pulksten] LT',
        nextWeek : 'dddd [pulksten] LT',
        lastDay : '[Vakar pulksten] LT',
        lastWeek : '[Pagājušā] dddd [pulksten] LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : 'pēc %s',
        past : 'pirms %s',
        s : relativeSeconds,
        ss : relativeTimeWithPlural,
        m : relativeTimeWithSingular,
        mm : relativeTimeWithPlural,
        h : relativeTimeWithSingular,
        hh : relativeTimeWithPlural,
        d : relativeTimeWithSingular,
        dd : relativeTimeWithPlural,
        M : relativeTimeWithSingular,
        MM : relativeTimeWithPlural,
        y : relativeTimeWithSingular,
        yy : relativeTimeWithPlural
    },
    dayOfMonthOrdinalParse: /\d{1,2}\./,
    ordinal : '%d.',
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return lv;

})));


/***/ }),
/* 96 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Montenegrin [me]
//! author : Miodrag Nikač <miodrag@restartit.me> : https://github.com/miodragnikac

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var translator = {
    words: { //Different grammatical cases
        ss: ['sekund', 'sekunda', 'sekundi'],
        m: ['jedan minut', 'jednog minuta'],
        mm: ['minut', 'minuta', 'minuta'],
        h: ['jedan sat', 'jednog sata'],
        hh: ['sat', 'sata', 'sati'],
        dd: ['dan', 'dana', 'dana'],
        MM: ['mjesec', 'mjeseca', 'mjeseci'],
        yy: ['godina', 'godine', 'godina']
    },
    correctGrammaticalCase: function (number, wordKey) {
        return number === 1 ? wordKey[0] : (number >= 2 && number <= 4 ? wordKey[1] : wordKey[2]);
    },
    translate: function (number, withoutSuffix, key) {
        var wordKey = translator.words[key];
        if (key.length === 1) {
            return withoutSuffix ? wordKey[0] : wordKey[1];
        } else {
            return number + ' ' + translator.correctGrammaticalCase(number, wordKey);
        }
    }
};

var me = moment.defineLocale('me', {
    months: 'januar_februar_mart_april_maj_jun_jul_avgust_septembar_oktobar_novembar_decembar'.split('_'),
    monthsShort: 'jan._feb._mar._apr._maj_jun_jul_avg._sep._okt._nov._dec.'.split('_'),
    monthsParseExact : true,
    weekdays: 'nedjelja_ponedjeljak_utorak_srijeda_četvrtak_petak_subota'.split('_'),
    weekdaysShort: 'ned._pon._uto._sri._čet._pet._sub.'.split('_'),
    weekdaysMin: 'ne_po_ut_sr_če_pe_su'.split('_'),
    weekdaysParseExact : true,
    longDateFormat: {
        LT: 'H:mm',
        LTS : 'H:mm:ss',
        L: 'DD.MM.YYYY',
        LL: 'D. MMMM YYYY',
        LLL: 'D. MMMM YYYY H:mm',
        LLLL: 'dddd, D. MMMM YYYY H:mm'
    },
    calendar: {
        sameDay: '[danas u] LT',
        nextDay: '[sjutra u] LT',

        nextWeek: function () {
            switch (this.day()) {
                case 0:
                    return '[u] [nedjelju] [u] LT';
                case 3:
                    return '[u] [srijedu] [u] LT';
                case 6:
                    return '[u] [subotu] [u] LT';
                case 1:
                case 2:
                case 4:
                case 5:
                    return '[u] dddd [u] LT';
            }
        },
        lastDay  : '[juče u] LT',
        lastWeek : function () {
            var lastWeekDays = [
                '[prošle] [nedjelje] [u] LT',
                '[prošlog] [ponedjeljka] [u] LT',
                '[prošlog] [utorka] [u] LT',
                '[prošle] [srijede] [u] LT',
                '[prošlog] [četvrtka] [u] LT',
                '[prošlog] [petka] [u] LT',
                '[prošle] [subote] [u] LT'
            ];
            return lastWeekDays[this.day()];
        },
        sameElse : 'L'
    },
    relativeTime : {
        future : 'za %s',
        past   : 'prije %s',
        s      : 'nekoliko sekundi',
        ss     : translator.translate,
        m      : translator.translate,
        mm     : translator.translate,
        h      : translator.translate,
        hh     : translator.translate,
        d      : 'dan',
        dd     : translator.translate,
        M      : 'mjesec',
        MM     : translator.translate,
        y      : 'godinu',
        yy     : translator.translate
    },
    dayOfMonthOrdinalParse: /\d{1,2}\./,
    ordinal : '%d.',
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 7  // The week that contains Jan 1st is the first week of the year.
    }
});

return me;

})));


/***/ }),
/* 97 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Maori [mi]
//! author : John Corrigan <robbiecloset@gmail.com> : https://github.com/johnideal

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var mi = moment.defineLocale('mi', {
    months: 'Kohi-tāte_Hui-tanguru_Poutū-te-rangi_Paenga-whāwhā_Haratua_Pipiri_Hōngoingoi_Here-turi-kōkā_Mahuru_Whiringa-ā-nuku_Whiringa-ā-rangi_Hakihea'.split('_'),
    monthsShort: 'Kohi_Hui_Pou_Pae_Hara_Pipi_Hōngoi_Here_Mahu_Whi-nu_Whi-ra_Haki'.split('_'),
    monthsRegex: /(?:['a-z\u0101\u014D\u016B]+\-?){1,3}/i,
    monthsStrictRegex: /(?:['a-z\u0101\u014D\u016B]+\-?){1,3}/i,
    monthsShortRegex: /(?:['a-z\u0101\u014D\u016B]+\-?){1,3}/i,
    monthsShortStrictRegex: /(?:['a-z\u0101\u014D\u016B]+\-?){1,2}/i,
    weekdays: 'Rātapu_Mane_Tūrei_Wenerei_Tāite_Paraire_Hātarei'.split('_'),
    weekdaysShort: 'Ta_Ma_Tū_We_Tāi_Pa_Hā'.split('_'),
    weekdaysMin: 'Ta_Ma_Tū_We_Tāi_Pa_Hā'.split('_'),
    longDateFormat: {
        LT: 'HH:mm',
        LTS: 'HH:mm:ss',
        L: 'DD/MM/YYYY',
        LL: 'D MMMM YYYY',
        LLL: 'D MMMM YYYY [i] HH:mm',
        LLLL: 'dddd, D MMMM YYYY [i] HH:mm'
    },
    calendar: {
        sameDay: '[i teie mahana, i] LT',
        nextDay: '[apopo i] LT',
        nextWeek: 'dddd [i] LT',
        lastDay: '[inanahi i] LT',
        lastWeek: 'dddd [whakamutunga i] LT',
        sameElse: 'L'
    },
    relativeTime: {
        future: 'i roto i %s',
        past: '%s i mua',
        s: 'te hēkona ruarua',
        ss: '%d hēkona',
        m: 'he meneti',
        mm: '%d meneti',
        h: 'te haora',
        hh: '%d haora',
        d: 'he ra',
        dd: '%d ra',
        M: 'he marama',
        MM: '%d marama',
        y: 'he tau',
        yy: '%d tau'
    },
    dayOfMonthOrdinalParse: /\d{1,2}º/,
    ordinal: '%dº',
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return mi;

})));


/***/ }),
/* 98 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Macedonian [mk]
//! author : Borislav Mickov : https://github.com/B0k0

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var mk = moment.defineLocale('mk', {
    months : 'јануари_февруари_март_април_мај_јуни_јули_август_септември_октомври_ноември_декември'.split('_'),
    monthsShort : 'јан_фев_мар_апр_мај_јун_јул_авг_сеп_окт_ное_дек'.split('_'),
    weekdays : 'недела_понеделник_вторник_среда_четврток_петок_сабота'.split('_'),
    weekdaysShort : 'нед_пон_вто_сре_чет_пет_саб'.split('_'),
    weekdaysMin : 'нe_пo_вт_ср_че_пе_сa'.split('_'),
    longDateFormat : {
        LT : 'H:mm',
        LTS : 'H:mm:ss',
        L : 'D.MM.YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY H:mm',
        LLLL : 'dddd, D MMMM YYYY H:mm'
    },
    calendar : {
        sameDay : '[Денес во] LT',
        nextDay : '[Утре во] LT',
        nextWeek : '[Во] dddd [во] LT',
        lastDay : '[Вчера во] LT',
        lastWeek : function () {
            switch (this.day()) {
                case 0:
                case 3:
                case 6:
                    return '[Изминатата] dddd [во] LT';
                case 1:
                case 2:
                case 4:
                case 5:
                    return '[Изминатиот] dddd [во] LT';
            }
        },
        sameElse : 'L'
    },
    relativeTime : {
        future : 'после %s',
        past : 'пред %s',
        s : 'неколку секунди',
        ss : '%d секунди',
        m : 'минута',
        mm : '%d минути',
        h : 'час',
        hh : '%d часа',
        d : 'ден',
        dd : '%d дена',
        M : 'месец',
        MM : '%d месеци',
        y : 'година',
        yy : '%d години'
    },
    dayOfMonthOrdinalParse: /\d{1,2}-(ев|ен|ти|ви|ри|ми)/,
    ordinal : function (number) {
        var lastDigit = number % 10,
            last2Digits = number % 100;
        if (number === 0) {
            return number + '-ев';
        } else if (last2Digits === 0) {
            return number + '-ен';
        } else if (last2Digits > 10 && last2Digits < 20) {
            return number + '-ти';
        } else if (lastDigit === 1) {
            return number + '-ви';
        } else if (lastDigit === 2) {
            return number + '-ри';
        } else if (lastDigit === 7 || lastDigit === 8) {
            return number + '-ми';
        } else {
            return number + '-ти';
        }
    },
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 7  // The week that contains Jan 1st is the first week of the year.
    }
});

return mk;

})));


/***/ }),
/* 99 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Malayalam [ml]
//! author : Floyd Pink : https://github.com/floydpink

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var ml = moment.defineLocale('ml', {
    months : 'ജനുവരി_ഫെബ്രുവരി_മാർച്ച്_ഏപ്രിൽ_മേയ്_ജൂൺ_ജൂലൈ_ഓഗസ്റ്റ്_സെപ്റ്റംബർ_ഒക്ടോബർ_നവംബർ_ഡിസംബർ'.split('_'),
    monthsShort : 'ജനു._ഫെബ്രു._മാർ._ഏപ്രി._മേയ്_ജൂൺ_ജൂലൈ._ഓഗ._സെപ്റ്റ._ഒക്ടോ._നവം._ഡിസം.'.split('_'),
    monthsParseExact : true,
    weekdays : 'ഞായറാഴ്ച_തിങ്കളാഴ്ച_ചൊവ്വാഴ്ച_ബുധനാഴ്ച_വ്യാഴാഴ്ച_വെള്ളിയാഴ്ച_ശനിയാഴ്ച'.split('_'),
    weekdaysShort : 'ഞായർ_തിങ്കൾ_ചൊവ്വ_ബുധൻ_വ്യാഴം_വെള്ളി_ശനി'.split('_'),
    weekdaysMin : 'ഞാ_തി_ചൊ_ബു_വ്യാ_വെ_ശ'.split('_'),
    longDateFormat : {
        LT : 'A h:mm -നു',
        LTS : 'A h:mm:ss -നു',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY, A h:mm -നു',
        LLLL : 'dddd, D MMMM YYYY, A h:mm -നു'
    },
    calendar : {
        sameDay : '[ഇന്ന്] LT',
        nextDay : '[നാളെ] LT',
        nextWeek : 'dddd, LT',
        lastDay : '[ഇന്നലെ] LT',
        lastWeek : '[കഴിഞ്ഞ] dddd, LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : '%s കഴിഞ്ഞ്',
        past : '%s മുൻപ്',
        s : 'അൽപ നിമിഷങ്ങൾ',
        ss : '%d സെക്കൻഡ്',
        m : 'ഒരു മിനിറ്റ്',
        mm : '%d മിനിറ്റ്',
        h : 'ഒരു മണിക്കൂർ',
        hh : '%d മണിക്കൂർ',
        d : 'ഒരു ദിവസം',
        dd : '%d ദിവസം',
        M : 'ഒരു മാസം',
        MM : '%d മാസം',
        y : 'ഒരു വർഷം',
        yy : '%d വർഷം'
    },
    meridiemParse: /രാത്രി|രാവിലെ|ഉച്ച കഴിഞ്ഞ്|വൈകുന്നേരം|രാത്രി/i,
    meridiemHour : function (hour, meridiem) {
        if (hour === 12) {
            hour = 0;
        }
        if ((meridiem === 'രാത്രി' && hour >= 4) ||
                meridiem === 'ഉച്ച കഴിഞ്ഞ്' ||
                meridiem === 'വൈകുന്നേരം') {
            return hour + 12;
        } else {
            return hour;
        }
    },
    meridiem : function (hour, minute, isLower) {
        if (hour < 4) {
            return 'രാത്രി';
        } else if (hour < 12) {
            return 'രാവിലെ';
        } else if (hour < 17) {
            return 'ഉച്ച കഴിഞ്ഞ്';
        } else if (hour < 20) {
            return 'വൈകുന്നേരം';
        } else {
            return 'രാത്രി';
        }
    }
});

return ml;

})));


/***/ }),
/* 100 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Marathi [mr]
//! author : Harshad Kale : https://github.com/kalehv
//! author : Vivek Athalye : https://github.com/vnathalye

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var symbolMap = {
    '1': '१',
    '2': '२',
    '3': '३',
    '4': '४',
    '5': '५',
    '6': '६',
    '7': '७',
    '8': '८',
    '9': '९',
    '0': '०'
};
var numberMap = {
    '१': '1',
    '२': '2',
    '३': '3',
    '४': '4',
    '५': '5',
    '६': '6',
    '७': '7',
    '८': '8',
    '९': '9',
    '०': '0'
};

function relativeTimeMr(number, withoutSuffix, string, isFuture)
{
    var output = '';
    if (withoutSuffix) {
        switch (string) {
            case 's': output = 'काही सेकंद'; break;
            case 'ss': output = '%d सेकंद'; break;
            case 'm': output = 'एक मिनिट'; break;
            case 'mm': output = '%d मिनिटे'; break;
            case 'h': output = 'एक तास'; break;
            case 'hh': output = '%d तास'; break;
            case 'd': output = 'एक दिवस'; break;
            case 'dd': output = '%d दिवस'; break;
            case 'M': output = 'एक महिना'; break;
            case 'MM': output = '%d महिने'; break;
            case 'y': output = 'एक वर्ष'; break;
            case 'yy': output = '%d वर्षे'; break;
        }
    }
    else {
        switch (string) {
            case 's': output = 'काही सेकंदां'; break;
            case 'ss': output = '%d सेकंदां'; break;
            case 'm': output = 'एका मिनिटा'; break;
            case 'mm': output = '%d मिनिटां'; break;
            case 'h': output = 'एका तासा'; break;
            case 'hh': output = '%d तासां'; break;
            case 'd': output = 'एका दिवसा'; break;
            case 'dd': output = '%d दिवसां'; break;
            case 'M': output = 'एका महिन्या'; break;
            case 'MM': output = '%d महिन्यां'; break;
            case 'y': output = 'एका वर्षा'; break;
            case 'yy': output = '%d वर्षां'; break;
        }
    }
    return output.replace(/%d/i, number);
}

var mr = moment.defineLocale('mr', {
    months : 'जानेवारी_फेब्रुवारी_मार्च_एप्रिल_मे_जून_जुलै_ऑगस्ट_सप्टेंबर_ऑक्टोबर_नोव्हेंबर_डिसेंबर'.split('_'),
    monthsShort: 'जाने._फेब्रु._मार्च._एप्रि._मे._जून._जुलै._ऑग._सप्टें._ऑक्टो._नोव्हें._डिसें.'.split('_'),
    monthsParseExact : true,
    weekdays : 'रविवार_सोमवार_मंगळवार_बुधवार_गुरूवार_शुक्रवार_शनिवार'.split('_'),
    weekdaysShort : 'रवि_सोम_मंगळ_बुध_गुरू_शुक्र_शनि'.split('_'),
    weekdaysMin : 'र_सो_मं_बु_गु_शु_श'.split('_'),
    longDateFormat : {
        LT : 'A h:mm वाजता',
        LTS : 'A h:mm:ss वाजता',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY, A h:mm वाजता',
        LLLL : 'dddd, D MMMM YYYY, A h:mm वाजता'
    },
    calendar : {
        sameDay : '[आज] LT',
        nextDay : '[उद्या] LT',
        nextWeek : 'dddd, LT',
        lastDay : '[काल] LT',
        lastWeek: '[मागील] dddd, LT',
        sameElse : 'L'
    },
    relativeTime : {
        future: '%sमध्ये',
        past: '%sपूर्वी',
        s: relativeTimeMr,
        ss: relativeTimeMr,
        m: relativeTimeMr,
        mm: relativeTimeMr,
        h: relativeTimeMr,
        hh: relativeTimeMr,
        d: relativeTimeMr,
        dd: relativeTimeMr,
        M: relativeTimeMr,
        MM: relativeTimeMr,
        y: relativeTimeMr,
        yy: relativeTimeMr
    },
    preparse: function (string) {
        return string.replace(/[१२३४५६७८९०]/g, function (match) {
            return numberMap[match];
        });
    },
    postformat: function (string) {
        return string.replace(/\d/g, function (match) {
            return symbolMap[match];
        });
    },
    meridiemParse: /रात्री|सकाळी|दुपारी|सायंकाळी/,
    meridiemHour : function (hour, meridiem) {
        if (hour === 12) {
            hour = 0;
        }
        if (meridiem === 'रात्री') {
            return hour < 4 ? hour : hour + 12;
        } else if (meridiem === 'सकाळी') {
            return hour;
        } else if (meridiem === 'दुपारी') {
            return hour >= 10 ? hour : hour + 12;
        } else if (meridiem === 'सायंकाळी') {
            return hour + 12;
        }
    },
    meridiem: function (hour, minute, isLower) {
        if (hour < 4) {
            return 'रात्री';
        } else if (hour < 10) {
            return 'सकाळी';
        } else if (hour < 17) {
            return 'दुपारी';
        } else if (hour < 20) {
            return 'सायंकाळी';
        } else {
            return 'रात्री';
        }
    },
    week : {
        dow : 0, // Sunday is the first day of the week.
        doy : 6  // The week that contains Jan 1st is the first week of the year.
    }
});

return mr;

})));


/***/ }),
/* 101 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Malay [ms-my]
//! note : DEPRECATED, the correct one is [ms]
//! author : Weldan Jamili : https://github.com/weldan

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var msMy = moment.defineLocale('ms-my', {
    months : 'Januari_Februari_Mac_April_Mei_Jun_Julai_Ogos_September_Oktober_November_Disember'.split('_'),
    monthsShort : 'Jan_Feb_Mac_Apr_Mei_Jun_Jul_Ogs_Sep_Okt_Nov_Dis'.split('_'),
    weekdays : 'Ahad_Isnin_Selasa_Rabu_Khamis_Jumaat_Sabtu'.split('_'),
    weekdaysShort : 'Ahd_Isn_Sel_Rab_Kha_Jum_Sab'.split('_'),
    weekdaysMin : 'Ah_Is_Sl_Rb_Km_Jm_Sb'.split('_'),
    longDateFormat : {
        LT : 'HH.mm',
        LTS : 'HH.mm.ss',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY [pukul] HH.mm',
        LLLL : 'dddd, D MMMM YYYY [pukul] HH.mm'
    },
    meridiemParse: /pagi|tengahari|petang|malam/,
    meridiemHour: function (hour, meridiem) {
        if (hour === 12) {
            hour = 0;
        }
        if (meridiem === 'pagi') {
            return hour;
        } else if (meridiem === 'tengahari') {
            return hour >= 11 ? hour : hour + 12;
        } else if (meridiem === 'petang' || meridiem === 'malam') {
            return hour + 12;
        }
    },
    meridiem : function (hours, minutes, isLower) {
        if (hours < 11) {
            return 'pagi';
        } else if (hours < 15) {
            return 'tengahari';
        } else if (hours < 19) {
            return 'petang';
        } else {
            return 'malam';
        }
    },
    calendar : {
        sameDay : '[Hari ini pukul] LT',
        nextDay : '[Esok pukul] LT',
        nextWeek : 'dddd [pukul] LT',
        lastDay : '[Kelmarin pukul] LT',
        lastWeek : 'dddd [lepas pukul] LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : 'dalam %s',
        past : '%s yang lepas',
        s : 'beberapa saat',
        ss : '%d saat',
        m : 'seminit',
        mm : '%d minit',
        h : 'sejam',
        hh : '%d jam',
        d : 'sehari',
        dd : '%d hari',
        M : 'sebulan',
        MM : '%d bulan',
        y : 'setahun',
        yy : '%d tahun'
    },
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 7  // The week that contains Jan 1st is the first week of the year.
    }
});

return msMy;

})));


/***/ }),
/* 102 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Malay [ms]
//! author : Weldan Jamili : https://github.com/weldan

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var ms = moment.defineLocale('ms', {
    months : 'Januari_Februari_Mac_April_Mei_Jun_Julai_Ogos_September_Oktober_November_Disember'.split('_'),
    monthsShort : 'Jan_Feb_Mac_Apr_Mei_Jun_Jul_Ogs_Sep_Okt_Nov_Dis'.split('_'),
    weekdays : 'Ahad_Isnin_Selasa_Rabu_Khamis_Jumaat_Sabtu'.split('_'),
    weekdaysShort : 'Ahd_Isn_Sel_Rab_Kha_Jum_Sab'.split('_'),
    weekdaysMin : 'Ah_Is_Sl_Rb_Km_Jm_Sb'.split('_'),
    longDateFormat : {
        LT : 'HH.mm',
        LTS : 'HH.mm.ss',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY [pukul] HH.mm',
        LLLL : 'dddd, D MMMM YYYY [pukul] HH.mm'
    },
    meridiemParse: /pagi|tengahari|petang|malam/,
    meridiemHour: function (hour, meridiem) {
        if (hour === 12) {
            hour = 0;
        }
        if (meridiem === 'pagi') {
            return hour;
        } else if (meridiem === 'tengahari') {
            return hour >= 11 ? hour : hour + 12;
        } else if (meridiem === 'petang' || meridiem === 'malam') {
            return hour + 12;
        }
    },
    meridiem : function (hours, minutes, isLower) {
        if (hours < 11) {
            return 'pagi';
        } else if (hours < 15) {
            return 'tengahari';
        } else if (hours < 19) {
            return 'petang';
        } else {
            return 'malam';
        }
    },
    calendar : {
        sameDay : '[Hari ini pukul] LT',
        nextDay : '[Esok pukul] LT',
        nextWeek : 'dddd [pukul] LT',
        lastDay : '[Kelmarin pukul] LT',
        lastWeek : 'dddd [lepas pukul] LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : 'dalam %s',
        past : '%s yang lepas',
        s : 'beberapa saat',
        ss : '%d saat',
        m : 'seminit',
        mm : '%d minit',
        h : 'sejam',
        hh : '%d jam',
        d : 'sehari',
        dd : '%d hari',
        M : 'sebulan',
        MM : '%d bulan',
        y : 'setahun',
        yy : '%d tahun'
    },
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 7  // The week that contains Jan 1st is the first week of the year.
    }
});

return ms;

})));


/***/ }),
/* 103 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Maltese (Malta) [mt]
//! author : Alessandro Maruccia : https://github.com/alesma

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var mt = moment.defineLocale('mt', {
    months : 'Jannar_Frar_Marzu_April_Mejju_Ġunju_Lulju_Awwissu_Settembru_Ottubru_Novembru_Diċembru'.split('_'),
    monthsShort : 'Jan_Fra_Mar_Apr_Mej_Ġun_Lul_Aww_Set_Ott_Nov_Diċ'.split('_'),
    weekdays : 'Il-Ħadd_It-Tnejn_It-Tlieta_L-Erbgħa_Il-Ħamis_Il-Ġimgħa_Is-Sibt'.split('_'),
    weekdaysShort : 'Ħad_Tne_Tli_Erb_Ħam_Ġim_Sib'.split('_'),
    weekdaysMin : 'Ħa_Tn_Tl_Er_Ħa_Ġi_Si'.split('_'),
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY HH:mm',
        LLLL : 'dddd, D MMMM YYYY HH:mm'
    },
    calendar : {
        sameDay : '[Illum fil-]LT',
        nextDay : '[Għada fil-]LT',
        nextWeek : 'dddd [fil-]LT',
        lastDay : '[Il-bieraħ fil-]LT',
        lastWeek : 'dddd [li għadda] [fil-]LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : 'f’ %s',
        past : '%s ilu',
        s : 'ftit sekondi',
        ss : '%d sekondi',
        m : 'minuta',
        mm : '%d minuti',
        h : 'siegħa',
        hh : '%d siegħat',
        d : 'ġurnata',
        dd : '%d ġranet',
        M : 'xahar',
        MM : '%d xhur',
        y : 'sena',
        yy : '%d sni'
    },
    dayOfMonthOrdinalParse : /\d{1,2}º/,
    ordinal: '%dº',
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return mt;

})));


/***/ }),
/* 104 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Burmese [my]
//! author : Squar team, mysquar.com
//! author : David Rossellat : https://github.com/gholadr
//! author : Tin Aung Lin : https://github.com/thanyawzinmin

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var symbolMap = {
    '1': '၁',
    '2': '၂',
    '3': '၃',
    '4': '၄',
    '5': '၅',
    '6': '၆',
    '7': '၇',
    '8': '၈',
    '9': '၉',
    '0': '၀'
};
var numberMap = {
    '၁': '1',
    '၂': '2',
    '၃': '3',
    '၄': '4',
    '၅': '5',
    '၆': '6',
    '၇': '7',
    '၈': '8',
    '၉': '9',
    '၀': '0'
};

var my = moment.defineLocale('my', {
    months: 'ဇန်နဝါရီ_ဖေဖော်ဝါရီ_မတ်_ဧပြီ_မေ_ဇွန်_ဇူလိုင်_သြဂုတ်_စက်တင်ဘာ_အောက်တိုဘာ_နိုဝင်ဘာ_ဒီဇင်ဘာ'.split('_'),
    monthsShort: 'ဇန်_ဖေ_မတ်_ပြီ_မေ_ဇွန်_လိုင်_သြ_စက်_အောက်_နို_ဒီ'.split('_'),
    weekdays: 'တနင်္ဂနွေ_တနင်္လာ_အင်္ဂါ_ဗုဒ္ဓဟူး_ကြာသပတေး_သောကြာ_စနေ'.split('_'),
    weekdaysShort: 'နွေ_လာ_ဂါ_ဟူး_ကြာ_သော_နေ'.split('_'),
    weekdaysMin: 'နွေ_လာ_ဂါ_ဟူး_ကြာ_သော_နေ'.split('_'),

    longDateFormat: {
        LT: 'HH:mm',
        LTS: 'HH:mm:ss',
        L: 'DD/MM/YYYY',
        LL: 'D MMMM YYYY',
        LLL: 'D MMMM YYYY HH:mm',
        LLLL: 'dddd D MMMM YYYY HH:mm'
    },
    calendar: {
        sameDay: '[ယနေ.] LT [မှာ]',
        nextDay: '[မနက်ဖြန်] LT [မှာ]',
        nextWeek: 'dddd LT [မှာ]',
        lastDay: '[မနေ.က] LT [မှာ]',
        lastWeek: '[ပြီးခဲ့သော] dddd LT [မှာ]',
        sameElse: 'L'
    },
    relativeTime: {
        future: 'လာမည့် %s မှာ',
        past: 'လွန်ခဲ့သော %s က',
        s: 'စက္ကန်.အနည်းငယ်',
        ss : '%d စက္ကန့်',
        m: 'တစ်မိနစ်',
        mm: '%d မိနစ်',
        h: 'တစ်နာရီ',
        hh: '%d နာရီ',
        d: 'တစ်ရက်',
        dd: '%d ရက်',
        M: 'တစ်လ',
        MM: '%d လ',
        y: 'တစ်နှစ်',
        yy: '%d နှစ်'
    },
    preparse: function (string) {
        return string.replace(/[၁၂၃၄၅၆၇၈၉၀]/g, function (match) {
            return numberMap[match];
        });
    },
    postformat: function (string) {
        return string.replace(/\d/g, function (match) {
            return symbolMap[match];
        });
    },
    week: {
        dow: 1, // Monday is the first day of the week.
        doy: 4 // The week that contains Jan 1st is the first week of the year.
    }
});

return my;

})));


/***/ }),
/* 105 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Norwegian Bokmål [nb]
//! authors : Espen Hovlandsdal : https://github.com/rexxars
//!           Sigurd Gartmann : https://github.com/sigurdga

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var nb = moment.defineLocale('nb', {
    months : 'januar_februar_mars_april_mai_juni_juli_august_september_oktober_november_desember'.split('_'),
    monthsShort : 'jan._feb._mars_april_mai_juni_juli_aug._sep._okt._nov._des.'.split('_'),
    monthsParseExact : true,
    weekdays : 'søndag_mandag_tirsdag_onsdag_torsdag_fredag_lørdag'.split('_'),
    weekdaysShort : 'sø._ma._ti._on._to._fr._lø.'.split('_'),
    weekdaysMin : 'sø_ma_ti_on_to_fr_lø'.split('_'),
    weekdaysParseExact : true,
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD.MM.YYYY',
        LL : 'D. MMMM YYYY',
        LLL : 'D. MMMM YYYY [kl.] HH:mm',
        LLLL : 'dddd D. MMMM YYYY [kl.] HH:mm'
    },
    calendar : {
        sameDay: '[i dag kl.] LT',
        nextDay: '[i morgen kl.] LT',
        nextWeek: 'dddd [kl.] LT',
        lastDay: '[i går kl.] LT',
        lastWeek: '[forrige] dddd [kl.] LT',
        sameElse: 'L'
    },
    relativeTime : {
        future : 'om %s',
        past : '%s siden',
        s : 'noen sekunder',
        ss : '%d sekunder',
        m : 'ett minutt',
        mm : '%d minutter',
        h : 'en time',
        hh : '%d timer',
        d : 'en dag',
        dd : '%d dager',
        M : 'en måned',
        MM : '%d måneder',
        y : 'ett år',
        yy : '%d år'
    },
    dayOfMonthOrdinalParse: /\d{1,2}\./,
    ordinal : '%d.',
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return nb;

})));


/***/ }),
/* 106 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Nepalese [ne]
//! author : suvash : https://github.com/suvash

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var symbolMap = {
    '1': '१',
    '2': '२',
    '3': '३',
    '4': '४',
    '5': '५',
    '6': '६',
    '7': '७',
    '8': '८',
    '9': '९',
    '0': '०'
};
var numberMap = {
    '१': '1',
    '२': '2',
    '३': '3',
    '४': '4',
    '५': '5',
    '६': '6',
    '७': '7',
    '८': '8',
    '९': '9',
    '०': '0'
};

var ne = moment.defineLocale('ne', {
    months : 'जनवरी_फेब्रुवरी_मार्च_अप्रिल_मई_जुन_जुलाई_अगष्ट_सेप्टेम्बर_अक्टोबर_नोभेम्बर_डिसेम्बर'.split('_'),
    monthsShort : 'जन._फेब्रु._मार्च_अप्रि._मई_जुन_जुलाई._अग._सेप्ट._अक्टो._नोभे._डिसे.'.split('_'),
    monthsParseExact : true,
    weekdays : 'आइतबार_सोमबार_मङ्गलबार_बुधबार_बिहिबार_शुक्रबार_शनिबार'.split('_'),
    weekdaysShort : 'आइत._सोम._मङ्गल._बुध._बिहि._शुक्र._शनि.'.split('_'),
    weekdaysMin : 'आ._सो._मं._बु._बि._शु._श.'.split('_'),
    weekdaysParseExact : true,
    longDateFormat : {
        LT : 'Aको h:mm बजे',
        LTS : 'Aको h:mm:ss बजे',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY, Aको h:mm बजे',
        LLLL : 'dddd, D MMMM YYYY, Aको h:mm बजे'
    },
    preparse: function (string) {
        return string.replace(/[१२३४५६७८९०]/g, function (match) {
            return numberMap[match];
        });
    },
    postformat: function (string) {
        return string.replace(/\d/g, function (match) {
            return symbolMap[match];
        });
    },
    meridiemParse: /राति|बिहान|दिउँसो|साँझ/,
    meridiemHour : function (hour, meridiem) {
        if (hour === 12) {
            hour = 0;
        }
        if (meridiem === 'राति') {
            return hour < 4 ? hour : hour + 12;
        } else if (meridiem === 'बिहान') {
            return hour;
        } else if (meridiem === 'दिउँसो') {
            return hour >= 10 ? hour : hour + 12;
        } else if (meridiem === 'साँझ') {
            return hour + 12;
        }
    },
    meridiem : function (hour, minute, isLower) {
        if (hour < 3) {
            return 'राति';
        } else if (hour < 12) {
            return 'बिहान';
        } else if (hour < 16) {
            return 'दिउँसो';
        } else if (hour < 20) {
            return 'साँझ';
        } else {
            return 'राति';
        }
    },
    calendar : {
        sameDay : '[आज] LT',
        nextDay : '[भोलि] LT',
        nextWeek : '[आउँदो] dddd[,] LT',
        lastDay : '[हिजो] LT',
        lastWeek : '[गएको] dddd[,] LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : '%sमा',
        past : '%s अगाडि',
        s : 'केही क्षण',
        ss : '%d सेकेण्ड',
        m : 'एक मिनेट',
        mm : '%d मिनेट',
        h : 'एक घण्टा',
        hh : '%d घण्टा',
        d : 'एक दिन',
        dd : '%d दिन',
        M : 'एक महिना',
        MM : '%d महिना',
        y : 'एक बर्ष',
        yy : '%d बर्ष'
    },
    week : {
        dow : 0, // Sunday is the first day of the week.
        doy : 6  // The week that contains Jan 1st is the first week of the year.
    }
});

return ne;

})));


/***/ }),
/* 107 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Dutch (Belgium) [nl-be]
//! author : Joris Röling : https://github.com/jorisroling
//! author : Jacob Middag : https://github.com/middagj

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var monthsShortWithDots = 'jan._feb._mrt._apr._mei_jun._jul._aug._sep._okt._nov._dec.'.split('_');
var monthsShortWithoutDots = 'jan_feb_mrt_apr_mei_jun_jul_aug_sep_okt_nov_dec'.split('_');

var monthsParse = [/^jan/i, /^feb/i, /^maart|mrt.?$/i, /^apr/i, /^mei$/i, /^jun[i.]?$/i, /^jul[i.]?$/i, /^aug/i, /^sep/i, /^okt/i, /^nov/i, /^dec/i];
var monthsRegex = /^(januari|februari|maart|april|mei|april|ju[nl]i|augustus|september|oktober|november|december|jan\.?|feb\.?|mrt\.?|apr\.?|ju[nl]\.?|aug\.?|sep\.?|okt\.?|nov\.?|dec\.?)/i;

var nlBe = moment.defineLocale('nl-be', {
    months : 'januari_februari_maart_april_mei_juni_juli_augustus_september_oktober_november_december'.split('_'),
    monthsShort : function (m, format) {
        if (!m) {
            return monthsShortWithDots;
        } else if (/-MMM-/.test(format)) {
            return monthsShortWithoutDots[m.month()];
        } else {
            return monthsShortWithDots[m.month()];
        }
    },

    monthsRegex: monthsRegex,
    monthsShortRegex: monthsRegex,
    monthsStrictRegex: /^(januari|februari|maart|mei|ju[nl]i|april|augustus|september|oktober|november|december)/i,
    monthsShortStrictRegex: /^(jan\.?|feb\.?|mrt\.?|apr\.?|mei|ju[nl]\.?|aug\.?|sep\.?|okt\.?|nov\.?|dec\.?)/i,

    monthsParse : monthsParse,
    longMonthsParse : monthsParse,
    shortMonthsParse : monthsParse,

    weekdays : 'zondag_maandag_dinsdag_woensdag_donderdag_vrijdag_zaterdag'.split('_'),
    weekdaysShort : 'zo._ma._di._wo._do._vr._za.'.split('_'),
    weekdaysMin : 'zo_ma_di_wo_do_vr_za'.split('_'),
    weekdaysParseExact : true,
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY HH:mm',
        LLLL : 'dddd D MMMM YYYY HH:mm'
    },
    calendar : {
        sameDay: '[vandaag om] LT',
        nextDay: '[morgen om] LT',
        nextWeek: 'dddd [om] LT',
        lastDay: '[gisteren om] LT',
        lastWeek: '[afgelopen] dddd [om] LT',
        sameElse: 'L'
    },
    relativeTime : {
        future : 'over %s',
        past : '%s geleden',
        s : 'een paar seconden',
        ss : '%d seconden',
        m : 'één minuut',
        mm : '%d minuten',
        h : 'één uur',
        hh : '%d uur',
        d : 'één dag',
        dd : '%d dagen',
        M : 'één maand',
        MM : '%d maanden',
        y : 'één jaar',
        yy : '%d jaar'
    },
    dayOfMonthOrdinalParse: /\d{1,2}(ste|de)/,
    ordinal : function (number) {
        return number + ((number === 1 || number === 8 || number >= 20) ? 'ste' : 'de');
    },
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return nlBe;

})));


/***/ }),
/* 108 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Dutch [nl]
//! author : Joris Röling : https://github.com/jorisroling
//! author : Jacob Middag : https://github.com/middagj

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var monthsShortWithDots = 'jan._feb._mrt._apr._mei_jun._jul._aug._sep._okt._nov._dec.'.split('_');
var monthsShortWithoutDots = 'jan_feb_mrt_apr_mei_jun_jul_aug_sep_okt_nov_dec'.split('_');

var monthsParse = [/^jan/i, /^feb/i, /^maart|mrt.?$/i, /^apr/i, /^mei$/i, /^jun[i.]?$/i, /^jul[i.]?$/i, /^aug/i, /^sep/i, /^okt/i, /^nov/i, /^dec/i];
var monthsRegex = /^(januari|februari|maart|april|mei|april|ju[nl]i|augustus|september|oktober|november|december|jan\.?|feb\.?|mrt\.?|apr\.?|ju[nl]\.?|aug\.?|sep\.?|okt\.?|nov\.?|dec\.?)/i;

var nl = moment.defineLocale('nl', {
    months : 'januari_februari_maart_april_mei_juni_juli_augustus_september_oktober_november_december'.split('_'),
    monthsShort : function (m, format) {
        if (!m) {
            return monthsShortWithDots;
        } else if (/-MMM-/.test(format)) {
            return monthsShortWithoutDots[m.month()];
        } else {
            return monthsShortWithDots[m.month()];
        }
    },

    monthsRegex: monthsRegex,
    monthsShortRegex: monthsRegex,
    monthsStrictRegex: /^(januari|februari|maart|mei|ju[nl]i|april|augustus|september|oktober|november|december)/i,
    monthsShortStrictRegex: /^(jan\.?|feb\.?|mrt\.?|apr\.?|mei|ju[nl]\.?|aug\.?|sep\.?|okt\.?|nov\.?|dec\.?)/i,

    monthsParse : monthsParse,
    longMonthsParse : monthsParse,
    shortMonthsParse : monthsParse,

    weekdays : 'zondag_maandag_dinsdag_woensdag_donderdag_vrijdag_zaterdag'.split('_'),
    weekdaysShort : 'zo._ma._di._wo._do._vr._za.'.split('_'),
    weekdaysMin : 'zo_ma_di_wo_do_vr_za'.split('_'),
    weekdaysParseExact : true,
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD-MM-YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY HH:mm',
        LLLL : 'dddd D MMMM YYYY HH:mm'
    },
    calendar : {
        sameDay: '[vandaag om] LT',
        nextDay: '[morgen om] LT',
        nextWeek: 'dddd [om] LT',
        lastDay: '[gisteren om] LT',
        lastWeek: '[afgelopen] dddd [om] LT',
        sameElse: 'L'
    },
    relativeTime : {
        future : 'over %s',
        past : '%s geleden',
        s : 'een paar seconden',
        ss : '%d seconden',
        m : 'één minuut',
        mm : '%d minuten',
        h : 'één uur',
        hh : '%d uur',
        d : 'één dag',
        dd : '%d dagen',
        M : 'één maand',
        MM : '%d maanden',
        y : 'één jaar',
        yy : '%d jaar'
    },
    dayOfMonthOrdinalParse: /\d{1,2}(ste|de)/,
    ordinal : function (number) {
        return number + ((number === 1 || number === 8 || number >= 20) ? 'ste' : 'de');
    },
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return nl;

})));


/***/ }),
/* 109 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Nynorsk [nn]
//! author : https://github.com/mechuwind

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var nn = moment.defineLocale('nn', {
    months : 'januar_februar_mars_april_mai_juni_juli_august_september_oktober_november_desember'.split('_'),
    monthsShort : 'jan_feb_mar_apr_mai_jun_jul_aug_sep_okt_nov_des'.split('_'),
    weekdays : 'sundag_måndag_tysdag_onsdag_torsdag_fredag_laurdag'.split('_'),
    weekdaysShort : 'sun_mån_tys_ons_tor_fre_lau'.split('_'),
    weekdaysMin : 'su_må_ty_on_to_fr_lø'.split('_'),
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD.MM.YYYY',
        LL : 'D. MMMM YYYY',
        LLL : 'D. MMMM YYYY [kl.] H:mm',
        LLLL : 'dddd D. MMMM YYYY [kl.] HH:mm'
    },
    calendar : {
        sameDay: '[I dag klokka] LT',
        nextDay: '[I morgon klokka] LT',
        nextWeek: 'dddd [klokka] LT',
        lastDay: '[I går klokka] LT',
        lastWeek: '[Føregåande] dddd [klokka] LT',
        sameElse: 'L'
    },
    relativeTime : {
        future : 'om %s',
        past : '%s sidan',
        s : 'nokre sekund',
        ss : '%d sekund',
        m : 'eit minutt',
        mm : '%d minutt',
        h : 'ein time',
        hh : '%d timar',
        d : 'ein dag',
        dd : '%d dagar',
        M : 'ein månad',
        MM : '%d månader',
        y : 'eit år',
        yy : '%d år'
    },
    dayOfMonthOrdinalParse: /\d{1,2}\./,
    ordinal : '%d.',
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return nn;

})));


/***/ }),
/* 110 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Punjabi (India) [pa-in]
//! author : Harpreet Singh : https://github.com/harpreetkhalsagtbit

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var symbolMap = {
    '1': '੧',
    '2': '੨',
    '3': '੩',
    '4': '੪',
    '5': '੫',
    '6': '੬',
    '7': '੭',
    '8': '੮',
    '9': '੯',
    '0': '੦'
};
var numberMap = {
    '੧': '1',
    '੨': '2',
    '੩': '3',
    '੪': '4',
    '੫': '5',
    '੬': '6',
    '੭': '7',
    '੮': '8',
    '੯': '9',
    '੦': '0'
};

var paIn = moment.defineLocale('pa-in', {
    // There are months name as per Nanakshahi Calender but they are not used as rigidly in modern Punjabi.
    months : 'ਜਨਵਰੀ_ਫ਼ਰਵਰੀ_ਮਾਰਚ_ਅਪ੍ਰੈਲ_ਮਈ_ਜੂਨ_ਜੁਲਾਈ_ਅਗਸਤ_ਸਤੰਬਰ_ਅਕਤੂਬਰ_ਨਵੰਬਰ_ਦਸੰਬਰ'.split('_'),
    monthsShort : 'ਜਨਵਰੀ_ਫ਼ਰਵਰੀ_ਮਾਰਚ_ਅਪ੍ਰੈਲ_ਮਈ_ਜੂਨ_ਜੁਲਾਈ_ਅਗਸਤ_ਸਤੰਬਰ_ਅਕਤੂਬਰ_ਨਵੰਬਰ_ਦਸੰਬਰ'.split('_'),
    weekdays : 'ਐਤਵਾਰ_ਸੋਮਵਾਰ_ਮੰਗਲਵਾਰ_ਬੁਧਵਾਰ_ਵੀਰਵਾਰ_ਸ਼ੁੱਕਰਵਾਰ_ਸ਼ਨੀਚਰਵਾਰ'.split('_'),
    weekdaysShort : 'ਐਤ_ਸੋਮ_ਮੰਗਲ_ਬੁਧ_ਵੀਰ_ਸ਼ੁਕਰ_ਸ਼ਨੀ'.split('_'),
    weekdaysMin : 'ਐਤ_ਸੋਮ_ਮੰਗਲ_ਬੁਧ_ਵੀਰ_ਸ਼ੁਕਰ_ਸ਼ਨੀ'.split('_'),
    longDateFormat : {
        LT : 'A h:mm ਵਜੇ',
        LTS : 'A h:mm:ss ਵਜੇ',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY, A h:mm ਵਜੇ',
        LLLL : 'dddd, D MMMM YYYY, A h:mm ਵਜੇ'
    },
    calendar : {
        sameDay : '[ਅਜ] LT',
        nextDay : '[ਕਲ] LT',
        nextWeek : 'dddd, LT',
        lastDay : '[ਕਲ] LT',
        lastWeek : '[ਪਿਛਲੇ] dddd, LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : '%s ਵਿੱਚ',
        past : '%s ਪਿਛਲੇ',
        s : 'ਕੁਝ ਸਕਿੰਟ',
        ss : '%d ਸਕਿੰਟ',
        m : 'ਇਕ ਮਿੰਟ',
        mm : '%d ਮਿੰਟ',
        h : 'ਇੱਕ ਘੰਟਾ',
        hh : '%d ਘੰਟੇ',
        d : 'ਇੱਕ ਦਿਨ',
        dd : '%d ਦਿਨ',
        M : 'ਇੱਕ ਮਹੀਨਾ',
        MM : '%d ਮਹੀਨੇ',
        y : 'ਇੱਕ ਸਾਲ',
        yy : '%d ਸਾਲ'
    },
    preparse: function (string) {
        return string.replace(/[੧੨੩੪੫੬੭੮੯੦]/g, function (match) {
            return numberMap[match];
        });
    },
    postformat: function (string) {
        return string.replace(/\d/g, function (match) {
            return symbolMap[match];
        });
    },
    // Punjabi notation for meridiems are quite fuzzy in practice. While there exists
    // a rigid notion of a 'Pahar' it is not used as rigidly in modern Punjabi.
    meridiemParse: /ਰਾਤ|ਸਵੇਰ|ਦੁਪਹਿਰ|ਸ਼ਾਮ/,
    meridiemHour : function (hour, meridiem) {
        if (hour === 12) {
            hour = 0;
        }
        if (meridiem === 'ਰਾਤ') {
            return hour < 4 ? hour : hour + 12;
        } else if (meridiem === 'ਸਵੇਰ') {
            return hour;
        } else if (meridiem === 'ਦੁਪਹਿਰ') {
            return hour >= 10 ? hour : hour + 12;
        } else if (meridiem === 'ਸ਼ਾਮ') {
            return hour + 12;
        }
    },
    meridiem : function (hour, minute, isLower) {
        if (hour < 4) {
            return 'ਰਾਤ';
        } else if (hour < 10) {
            return 'ਸਵੇਰ';
        } else if (hour < 17) {
            return 'ਦੁਪਹਿਰ';
        } else if (hour < 20) {
            return 'ਸ਼ਾਮ';
        } else {
            return 'ਰਾਤ';
        }
    },
    week : {
        dow : 0, // Sunday is the first day of the week.
        doy : 6  // The week that contains Jan 1st is the first week of the year.
    }
});

return paIn;

})));


/***/ }),
/* 111 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Polish [pl]
//! author : Rafal Hirsz : https://github.com/evoL

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var monthsNominative = 'styczeń_luty_marzec_kwiecień_maj_czerwiec_lipiec_sierpień_wrzesień_październik_listopad_grudzień'.split('_');
var monthsSubjective = 'stycznia_lutego_marca_kwietnia_maja_czerwca_lipca_sierpnia_września_października_listopada_grudnia'.split('_');
function plural(n) {
    return (n % 10 < 5) && (n % 10 > 1) && ((~~(n / 10) % 10) !== 1);
}
function translate(number, withoutSuffix, key) {
    var result = number + ' ';
    switch (key) {
        case 'ss':
            return result + (plural(number) ? 'sekundy' : 'sekund');
        case 'm':
            return withoutSuffix ? 'minuta' : 'minutę';
        case 'mm':
            return result + (plural(number) ? 'minuty' : 'minut');
        case 'h':
            return withoutSuffix  ? 'godzina'  : 'godzinę';
        case 'hh':
            return result + (plural(number) ? 'godziny' : 'godzin');
        case 'MM':
            return result + (plural(number) ? 'miesiące' : 'miesięcy');
        case 'yy':
            return result + (plural(number) ? 'lata' : 'lat');
    }
}

var pl = moment.defineLocale('pl', {
    months : function (momentToFormat, format) {
        if (!momentToFormat) {
            return monthsNominative;
        } else if (format === '') {
            // Hack: if format empty we know this is used to generate
            // RegExp by moment. Give then back both valid forms of months
            // in RegExp ready format.
            return '(' + monthsSubjective[momentToFormat.month()] + '|' + monthsNominative[momentToFormat.month()] + ')';
        } else if (/D MMMM/.test(format)) {
            return monthsSubjective[momentToFormat.month()];
        } else {
            return monthsNominative[momentToFormat.month()];
        }
    },
    monthsShort : 'sty_lut_mar_kwi_maj_cze_lip_sie_wrz_paź_lis_gru'.split('_'),
    weekdays : 'niedziela_poniedziałek_wtorek_środa_czwartek_piątek_sobota'.split('_'),
    weekdaysShort : 'ndz_pon_wt_śr_czw_pt_sob'.split('_'),
    weekdaysMin : 'Nd_Pn_Wt_Śr_Cz_Pt_So'.split('_'),
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD.MM.YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY HH:mm',
        LLLL : 'dddd, D MMMM YYYY HH:mm'
    },
    calendar : {
        sameDay: '[Dziś o] LT',
        nextDay: '[Jutro o] LT',
        nextWeek: function () {
            switch (this.day()) {
                case 0:
                    return '[W niedzielę o] LT';

                case 2:
                    return '[We wtorek o] LT';

                case 3:
                    return '[W środę o] LT';

                case 6:
                    return '[W sobotę o] LT';

                default:
                    return '[W] dddd [o] LT';
            }
        },
        lastDay: '[Wczoraj o] LT',
        lastWeek: function () {
            switch (this.day()) {
                case 0:
                    return '[W zeszłą niedzielę o] LT';
                case 3:
                    return '[W zeszłą środę o] LT';
                case 6:
                    return '[W zeszłą sobotę o] LT';
                default:
                    return '[W zeszły] dddd [o] LT';
            }
        },
        sameElse: 'L'
    },
    relativeTime : {
        future : 'za %s',
        past : '%s temu',
        s : 'kilka sekund',
        ss : translate,
        m : translate,
        mm : translate,
        h : translate,
        hh : translate,
        d : '1 dzień',
        dd : '%d dni',
        M : 'miesiąc',
        MM : translate,
        y : 'rok',
        yy : translate
    },
    dayOfMonthOrdinalParse: /\d{1,2}\./,
    ordinal : '%d.',
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return pl;

})));


/***/ }),
/* 112 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Portuguese (Brazil) [pt-br]
//! author : Caio Ribeiro Pereira : https://github.com/caio-ribeiro-pereira

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var ptBr = moment.defineLocale('pt-br', {
    months : 'janeiro_fevereiro_março_abril_maio_junho_julho_agosto_setembro_outubro_novembro_dezembro'.split('_'),
    monthsShort : 'jan_fev_mar_abr_mai_jun_jul_ago_set_out_nov_dez'.split('_'),
    weekdays : 'Domingo_Segunda-feira_Terça-feira_Quarta-feira_Quinta-feira_Sexta-feira_Sábado'.split('_'),
    weekdaysShort : 'Dom_Seg_Ter_Qua_Qui_Sex_Sáb'.split('_'),
    weekdaysMin : 'Do_2ª_3ª_4ª_5ª_6ª_Sá'.split('_'),
    weekdaysParseExact : true,
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD/MM/YYYY',
        LL : 'D [de] MMMM [de] YYYY',
        LLL : 'D [de] MMMM [de] YYYY [às] HH:mm',
        LLLL : 'dddd, D [de] MMMM [de] YYYY [às] HH:mm'
    },
    calendar : {
        sameDay: '[Hoje às] LT',
        nextDay: '[Amanhã às] LT',
        nextWeek: 'dddd [às] LT',
        lastDay: '[Ontem às] LT',
        lastWeek: function () {
            return (this.day() === 0 || this.day() === 6) ?
                '[Último] dddd [às] LT' : // Saturday + Sunday
                '[Última] dddd [às] LT'; // Monday - Friday
        },
        sameElse: 'L'
    },
    relativeTime : {
        future : 'em %s',
        past : '%s atrás',
        s : 'poucos segundos',
        ss : '%d segundos',
        m : 'um minuto',
        mm : '%d minutos',
        h : 'uma hora',
        hh : '%d horas',
        d : 'um dia',
        dd : '%d dias',
        M : 'um mês',
        MM : '%d meses',
        y : 'um ano',
        yy : '%d anos'
    },
    dayOfMonthOrdinalParse: /\d{1,2}º/,
    ordinal : '%dº'
});

return ptBr;

})));


/***/ }),
/* 113 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Portuguese [pt]
//! author : Jefferson : https://github.com/jalex79

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var pt = moment.defineLocale('pt', {
    months : 'janeiro_fevereiro_março_abril_maio_junho_julho_agosto_setembro_outubro_novembro_dezembro'.split('_'),
    monthsShort : 'jan_fev_mar_abr_mai_jun_jul_ago_set_out_nov_dez'.split('_'),
    weekdays : 'Domingo_Segunda-feira_Terça-feira_Quarta-feira_Quinta-feira_Sexta-feira_Sábado'.split('_'),
    weekdaysShort : 'Dom_Seg_Ter_Qua_Qui_Sex_Sáb'.split('_'),
    weekdaysMin : 'Do_2ª_3ª_4ª_5ª_6ª_Sá'.split('_'),
    weekdaysParseExact : true,
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD/MM/YYYY',
        LL : 'D [de] MMMM [de] YYYY',
        LLL : 'D [de] MMMM [de] YYYY HH:mm',
        LLLL : 'dddd, D [de] MMMM [de] YYYY HH:mm'
    },
    calendar : {
        sameDay: '[Hoje às] LT',
        nextDay: '[Amanhã às] LT',
        nextWeek: 'dddd [às] LT',
        lastDay: '[Ontem às] LT',
        lastWeek: function () {
            return (this.day() === 0 || this.day() === 6) ?
                '[Último] dddd [às] LT' : // Saturday + Sunday
                '[Última] dddd [às] LT'; // Monday - Friday
        },
        sameElse: 'L'
    },
    relativeTime : {
        future : 'em %s',
        past : 'há %s',
        s : 'segundos',
        ss : '%d segundos',
        m : 'um minuto',
        mm : '%d minutos',
        h : 'uma hora',
        hh : '%d horas',
        d : 'um dia',
        dd : '%d dias',
        M : 'um mês',
        MM : '%d meses',
        y : 'um ano',
        yy : '%d anos'
    },
    dayOfMonthOrdinalParse: /\d{1,2}º/,
    ordinal : '%dº',
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return pt;

})));


/***/ }),
/* 114 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Romanian [ro]
//! author : Vlad Gurdiga : https://github.com/gurdiga
//! author : Valentin Agachi : https://github.com/avaly

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


function relativeTimeWithPlural(number, withoutSuffix, key) {
    var format = {
            'ss': 'secunde',
            'mm': 'minute',
            'hh': 'ore',
            'dd': 'zile',
            'MM': 'luni',
            'yy': 'ani'
        },
        separator = ' ';
    if (number % 100 >= 20 || (number >= 100 && number % 100 === 0)) {
        separator = ' de ';
    }
    return number + separator + format[key];
}

var ro = moment.defineLocale('ro', {
    months : 'ianuarie_februarie_martie_aprilie_mai_iunie_iulie_august_septembrie_octombrie_noiembrie_decembrie'.split('_'),
    monthsShort : 'ian._febr._mart._apr._mai_iun._iul._aug._sept._oct._nov._dec.'.split('_'),
    monthsParseExact: true,
    weekdays : 'duminică_luni_marți_miercuri_joi_vineri_sâmbătă'.split('_'),
    weekdaysShort : 'Dum_Lun_Mar_Mie_Joi_Vin_Sâm'.split('_'),
    weekdaysMin : 'Du_Lu_Ma_Mi_Jo_Vi_Sâ'.split('_'),
    longDateFormat : {
        LT : 'H:mm',
        LTS : 'H:mm:ss',
        L : 'DD.MM.YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY H:mm',
        LLLL : 'dddd, D MMMM YYYY H:mm'
    },
    calendar : {
        sameDay: '[azi la] LT',
        nextDay: '[mâine la] LT',
        nextWeek: 'dddd [la] LT',
        lastDay: '[ieri la] LT',
        lastWeek: '[fosta] dddd [la] LT',
        sameElse: 'L'
    },
    relativeTime : {
        future : 'peste %s',
        past : '%s în urmă',
        s : 'câteva secunde',
        ss : relativeTimeWithPlural,
        m : 'un minut',
        mm : relativeTimeWithPlural,
        h : 'o oră',
        hh : relativeTimeWithPlural,
        d : 'o zi',
        dd : relativeTimeWithPlural,
        M : 'o lună',
        MM : relativeTimeWithPlural,
        y : 'un an',
        yy : relativeTimeWithPlural
    },
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 7  // The week that contains Jan 1st is the first week of the year.
    }
});

return ro;

})));


/***/ }),
/* 115 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Russian [ru]
//! author : Viktorminator : https://github.com/Viktorminator
//! Author : Menelion Elensúle : https://github.com/Oire
//! author : Коренберг Марк : https://github.com/socketpair

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


function plural(word, num) {
    var forms = word.split('_');
    return num % 10 === 1 && num % 100 !== 11 ? forms[0] : (num % 10 >= 2 && num % 10 <= 4 && (num % 100 < 10 || num % 100 >= 20) ? forms[1] : forms[2]);
}
function relativeTimeWithPlural(number, withoutSuffix, key) {
    var format = {
        'ss': withoutSuffix ? 'секунда_секунды_секунд' : 'секунду_секунды_секунд',
        'mm': withoutSuffix ? 'минута_минуты_минут' : 'минуту_минуты_минут',
        'hh': 'час_часа_часов',
        'dd': 'день_дня_дней',
        'MM': 'месяц_месяца_месяцев',
        'yy': 'год_года_лет'
    };
    if (key === 'm') {
        return withoutSuffix ? 'минута' : 'минуту';
    }
    else {
        return number + ' ' + plural(format[key], +number);
    }
}
var monthsParse = [/^янв/i, /^фев/i, /^мар/i, /^апр/i, /^ма[йя]/i, /^июн/i, /^июл/i, /^авг/i, /^сен/i, /^окт/i, /^ноя/i, /^дек/i];

// http://new.gramota.ru/spravka/rules/139-prop : § 103
// Сокращения месяцев: http://new.gramota.ru/spravka/buro/search-answer?s=242637
// CLDR data:          http://www.unicode.org/cldr/charts/28/summary/ru.html#1753
var ru = moment.defineLocale('ru', {
    months : {
        format: 'января_февраля_марта_апреля_мая_июня_июля_августа_сентября_октября_ноября_декабря'.split('_'),
        standalone: 'январь_февраль_март_апрель_май_июнь_июль_август_сентябрь_октябрь_ноябрь_декабрь'.split('_')
    },
    monthsShort : {
        // по CLDR именно "июл." и "июн.", но какой смысл менять букву на точку ?
        format: 'янв._февр._мар._апр._мая_июня_июля_авг._сент._окт._нояб._дек.'.split('_'),
        standalone: 'янв._февр._март_апр._май_июнь_июль_авг._сент._окт._нояб._дек.'.split('_')
    },
    weekdays : {
        standalone: 'воскресенье_понедельник_вторник_среда_четверг_пятница_суббота'.split('_'),
        format: 'воскресенье_понедельник_вторник_среду_четверг_пятницу_субботу'.split('_'),
        isFormat: /\[ ?[Вв] ?(?:прошлую|следующую|эту)? ?\] ?dddd/
    },
    weekdaysShort : 'вс_пн_вт_ср_чт_пт_сб'.split('_'),
    weekdaysMin : 'вс_пн_вт_ср_чт_пт_сб'.split('_'),
    monthsParse : monthsParse,
    longMonthsParse : monthsParse,
    shortMonthsParse : monthsParse,

    // полные названия с падежами, по три буквы, для некоторых, по 4 буквы, сокращения с точкой и без точки
    monthsRegex: /^(январ[ья]|янв\.?|феврал[ья]|февр?\.?|марта?|мар\.?|апрел[ья]|апр\.?|ма[йя]|июн[ья]|июн\.?|июл[ья]|июл\.?|августа?|авг\.?|сентябр[ья]|сент?\.?|октябр[ья]|окт\.?|ноябр[ья]|нояб?\.?|декабр[ья]|дек\.?)/i,

    // копия предыдущего
    monthsShortRegex: /^(январ[ья]|янв\.?|феврал[ья]|февр?\.?|марта?|мар\.?|апрел[ья]|апр\.?|ма[йя]|июн[ья]|июн\.?|июл[ья]|июл\.?|августа?|авг\.?|сентябр[ья]|сент?\.?|октябр[ья]|окт\.?|ноябр[ья]|нояб?\.?|декабр[ья]|дек\.?)/i,

    // полные названия с падежами
    monthsStrictRegex: /^(январ[яь]|феврал[яь]|марта?|апрел[яь]|ма[яй]|июн[яь]|июл[яь]|августа?|сентябр[яь]|октябр[яь]|ноябр[яь]|декабр[яь])/i,

    // Выражение, которое соотвествует только сокращённым формам
    monthsShortStrictRegex: /^(янв\.|февр?\.|мар[т.]|апр\.|ма[яй]|июн[ья.]|июл[ья.]|авг\.|сент?\.|окт\.|нояб?\.|дек\.)/i,
    longDateFormat : {
        LT : 'H:mm',
        LTS : 'H:mm:ss',
        L : 'DD.MM.YYYY',
        LL : 'D MMMM YYYY г.',
        LLL : 'D MMMM YYYY г., H:mm',
        LLLL : 'dddd, D MMMM YYYY г., H:mm'
    },
    calendar : {
        sameDay: '[Сегодня в] LT',
        nextDay: '[Завтра в] LT',
        lastDay: '[Вчера в] LT',
        nextWeek: function (now) {
            if (now.week() !== this.week()) {
                switch (this.day()) {
                    case 0:
                        return '[В следующее] dddd [в] LT';
                    case 1:
                    case 2:
                    case 4:
                        return '[В следующий] dddd [в] LT';
                    case 3:
                    case 5:
                    case 6:
                        return '[В следующую] dddd [в] LT';
                }
            } else {
                if (this.day() === 2) {
                    return '[Во] dddd [в] LT';
                } else {
                    return '[В] dddd [в] LT';
                }
            }
        },
        lastWeek: function (now) {
            if (now.week() !== this.week()) {
                switch (this.day()) {
                    case 0:
                        return '[В прошлое] dddd [в] LT';
                    case 1:
                    case 2:
                    case 4:
                        return '[В прошлый] dddd [в] LT';
                    case 3:
                    case 5:
                    case 6:
                        return '[В прошлую] dddd [в] LT';
                }
            } else {
                if (this.day() === 2) {
                    return '[Во] dddd [в] LT';
                } else {
                    return '[В] dddd [в] LT';
                }
            }
        },
        sameElse: 'L'
    },
    relativeTime : {
        future : 'через %s',
        past : '%s назад',
        s : 'несколько секунд',
        ss : relativeTimeWithPlural,
        m : relativeTimeWithPlural,
        mm : relativeTimeWithPlural,
        h : 'час',
        hh : relativeTimeWithPlural,
        d : 'день',
        dd : relativeTimeWithPlural,
        M : 'месяц',
        MM : relativeTimeWithPlural,
        y : 'год',
        yy : relativeTimeWithPlural
    },
    meridiemParse: /ночи|утра|дня|вечера/i,
    isPM : function (input) {
        return /^(дня|вечера)$/.test(input);
    },
    meridiem : function (hour, minute, isLower) {
        if (hour < 4) {
            return 'ночи';
        } else if (hour < 12) {
            return 'утра';
        } else if (hour < 17) {
            return 'дня';
        } else {
            return 'вечера';
        }
    },
    dayOfMonthOrdinalParse: /\d{1,2}-(й|го|я)/,
    ordinal: function (number, period) {
        switch (period) {
            case 'M':
            case 'd':
            case 'DDD':
                return number + '-й';
            case 'D':
                return number + '-го';
            case 'w':
            case 'W':
                return number + '-я';
            default:
                return number;
        }
    },
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return ru;

})));


/***/ }),
/* 116 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Sindhi [sd]
//! author : Narain Sagar : https://github.com/narainsagar

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var months = [
    'جنوري',
    'فيبروري',
    'مارچ',
    'اپريل',
    'مئي',
    'جون',
    'جولاءِ',
    'آگسٽ',
    'سيپٽمبر',
    'آڪٽوبر',
    'نومبر',
    'ڊسمبر'
];
var days = [
    'آچر',
    'سومر',
    'اڱارو',
    'اربع',
    'خميس',
    'جمع',
    'ڇنڇر'
];

var sd = moment.defineLocale('sd', {
    months : months,
    monthsShort : months,
    weekdays : days,
    weekdaysShort : days,
    weekdaysMin : days,
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY HH:mm',
        LLLL : 'dddd، D MMMM YYYY HH:mm'
    },
    meridiemParse: /صبح|شام/,
    isPM : function (input) {
        return 'شام' === input;
    },
    meridiem : function (hour, minute, isLower) {
        if (hour < 12) {
            return 'صبح';
        }
        return 'شام';
    },
    calendar : {
        sameDay : '[اڄ] LT',
        nextDay : '[سڀاڻي] LT',
        nextWeek : 'dddd [اڳين هفتي تي] LT',
        lastDay : '[ڪالهه] LT',
        lastWeek : '[گزريل هفتي] dddd [تي] LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : '%s پوء',
        past : '%s اڳ',
        s : 'چند سيڪنڊ',
        ss : '%d سيڪنڊ',
        m : 'هڪ منٽ',
        mm : '%d منٽ',
        h : 'هڪ ڪلاڪ',
        hh : '%d ڪلاڪ',
        d : 'هڪ ڏينهن',
        dd : '%d ڏينهن',
        M : 'هڪ مهينو',
        MM : '%d مهينا',
        y : 'هڪ سال',
        yy : '%d سال'
    },
    preparse: function (string) {
        return string.replace(/،/g, ',');
    },
    postformat: function (string) {
        return string.replace(/,/g, '،');
    },
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return sd;

})));


/***/ }),
/* 117 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Northern Sami [se]
//! authors : Bård Rolstad Henriksen : https://github.com/karamell

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';



var se = moment.defineLocale('se', {
    months : 'ođđajagemánnu_guovvamánnu_njukčamánnu_cuoŋománnu_miessemánnu_geassemánnu_suoidnemánnu_borgemánnu_čakčamánnu_golggotmánnu_skábmamánnu_juovlamánnu'.split('_'),
    monthsShort : 'ođđj_guov_njuk_cuo_mies_geas_suoi_borg_čakč_golg_skáb_juov'.split('_'),
    weekdays : 'sotnabeaivi_vuossárga_maŋŋebárga_gaskavahkku_duorastat_bearjadat_lávvardat'.split('_'),
    weekdaysShort : 'sotn_vuos_maŋ_gask_duor_bear_láv'.split('_'),
    weekdaysMin : 's_v_m_g_d_b_L'.split('_'),
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD.MM.YYYY',
        LL : 'MMMM D. [b.] YYYY',
        LLL : 'MMMM D. [b.] YYYY [ti.] HH:mm',
        LLLL : 'dddd, MMMM D. [b.] YYYY [ti.] HH:mm'
    },
    calendar : {
        sameDay: '[otne ti] LT',
        nextDay: '[ihttin ti] LT',
        nextWeek: 'dddd [ti] LT',
        lastDay: '[ikte ti] LT',
        lastWeek: '[ovddit] dddd [ti] LT',
        sameElse: 'L'
    },
    relativeTime : {
        future : '%s geažes',
        past : 'maŋit %s',
        s : 'moadde sekunddat',
        ss: '%d sekunddat',
        m : 'okta minuhta',
        mm : '%d minuhtat',
        h : 'okta diimmu',
        hh : '%d diimmut',
        d : 'okta beaivi',
        dd : '%d beaivvit',
        M : 'okta mánnu',
        MM : '%d mánut',
        y : 'okta jahki',
        yy : '%d jagit'
    },
    dayOfMonthOrdinalParse: /\d{1,2}\./,
    ordinal : '%d.',
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return se;

})));


/***/ }),
/* 118 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Sinhalese [si]
//! author : Sampath Sitinamaluwa : https://github.com/sampathsris

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


/*jshint -W100*/
var si = moment.defineLocale('si', {
    months : 'ජනවාරි_පෙබරවාරි_මාර්තු_අප්‍රේල්_මැයි_ජූනි_ජූලි_අගෝස්තු_සැප්තැම්බර්_ඔක්තෝබර්_නොවැම්බර්_දෙසැම්බර්'.split('_'),
    monthsShort : 'ජන_පෙබ_මාර්_අප්_මැයි_ජූනි_ජූලි_අගෝ_සැප්_ඔක්_නොවැ_දෙසැ'.split('_'),
    weekdays : 'ඉරිදා_සඳුදා_අඟහරුවාදා_බදාදා_බ්‍රහස්පතින්දා_සිකුරාදා_සෙනසුරාදා'.split('_'),
    weekdaysShort : 'ඉරි_සඳු_අඟ_බදා_බ්‍රහ_සිකු_සෙන'.split('_'),
    weekdaysMin : 'ඉ_ස_අ_බ_බ්‍ර_සි_සෙ'.split('_'),
    weekdaysParseExact : true,
    longDateFormat : {
        LT : 'a h:mm',
        LTS : 'a h:mm:ss',
        L : 'YYYY/MM/DD',
        LL : 'YYYY MMMM D',
        LLL : 'YYYY MMMM D, a h:mm',
        LLLL : 'YYYY MMMM D [වැනි] dddd, a h:mm:ss'
    },
    calendar : {
        sameDay : '[අද] LT[ට]',
        nextDay : '[හෙට] LT[ට]',
        nextWeek : 'dddd LT[ට]',
        lastDay : '[ඊයේ] LT[ට]',
        lastWeek : '[පසුගිය] dddd LT[ට]',
        sameElse : 'L'
    },
    relativeTime : {
        future : '%sකින්',
        past : '%sකට පෙර',
        s : 'තත්පර කිහිපය',
        ss : 'තත්පර %d',
        m : 'මිනිත්තුව',
        mm : 'මිනිත්තු %d',
        h : 'පැය',
        hh : 'පැය %d',
        d : 'දිනය',
        dd : 'දින %d',
        M : 'මාසය',
        MM : 'මාස %d',
        y : 'වසර',
        yy : 'වසර %d'
    },
    dayOfMonthOrdinalParse: /\d{1,2} වැනි/,
    ordinal : function (number) {
        return number + ' වැනි';
    },
    meridiemParse : /පෙර වරු|පස් වරු|පෙ.ව|ප.ව./,
    isPM : function (input) {
        return input === 'ප.ව.' || input === 'පස් වරු';
    },
    meridiem : function (hours, minutes, isLower) {
        if (hours > 11) {
            return isLower ? 'ප.ව.' : 'පස් වරු';
        } else {
            return isLower ? 'පෙ.ව.' : 'පෙර වරු';
        }
    }
});

return si;

})));


/***/ }),
/* 119 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Slovak [sk]
//! author : Martin Minka : https://github.com/k2s
//! based on work of petrbela : https://github.com/petrbela

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var months = 'január_február_marec_apríl_máj_jún_júl_august_september_október_november_december'.split('_');
var monthsShort = 'jan_feb_mar_apr_máj_jún_júl_aug_sep_okt_nov_dec'.split('_');
function plural(n) {
    return (n > 1) && (n < 5);
}
function translate(number, withoutSuffix, key, isFuture) {
    var result = number + ' ';
    switch (key) {
        case 's':  // a few seconds / in a few seconds / a few seconds ago
            return (withoutSuffix || isFuture) ? 'pár sekúnd' : 'pár sekundami';
        case 'ss': // 9 seconds / in 9 seconds / 9 seconds ago
            if (withoutSuffix || isFuture) {
                return result + (plural(number) ? 'sekundy' : 'sekúnd');
            } else {
                return result + 'sekundami';
            }
            break;
        case 'm':  // a minute / in a minute / a minute ago
            return withoutSuffix ? 'minúta' : (isFuture ? 'minútu' : 'minútou');
        case 'mm': // 9 minutes / in 9 minutes / 9 minutes ago
            if (withoutSuffix || isFuture) {
                return result + (plural(number) ? 'minúty' : 'minút');
            } else {
                return result + 'minútami';
            }
            break;
        case 'h':  // an hour / in an hour / an hour ago
            return withoutSuffix ? 'hodina' : (isFuture ? 'hodinu' : 'hodinou');
        case 'hh': // 9 hours / in 9 hours / 9 hours ago
            if (withoutSuffix || isFuture) {
                return result + (plural(number) ? 'hodiny' : 'hodín');
            } else {
                return result + 'hodinami';
            }
            break;
        case 'd':  // a day / in a day / a day ago
            return (withoutSuffix || isFuture) ? 'deň' : 'dňom';
        case 'dd': // 9 days / in 9 days / 9 days ago
            if (withoutSuffix || isFuture) {
                return result + (plural(number) ? 'dni' : 'dní');
            } else {
                return result + 'dňami';
            }
            break;
        case 'M':  // a month / in a month / a month ago
            return (withoutSuffix || isFuture) ? 'mesiac' : 'mesiacom';
        case 'MM': // 9 months / in 9 months / 9 months ago
            if (withoutSuffix || isFuture) {
                return result + (plural(number) ? 'mesiace' : 'mesiacov');
            } else {
                return result + 'mesiacmi';
            }
            break;
        case 'y':  // a year / in a year / a year ago
            return (withoutSuffix || isFuture) ? 'rok' : 'rokom';
        case 'yy': // 9 years / in 9 years / 9 years ago
            if (withoutSuffix || isFuture) {
                return result + (plural(number) ? 'roky' : 'rokov');
            } else {
                return result + 'rokmi';
            }
            break;
    }
}

var sk = moment.defineLocale('sk', {
    months : months,
    monthsShort : monthsShort,
    weekdays : 'nedeľa_pondelok_utorok_streda_štvrtok_piatok_sobota'.split('_'),
    weekdaysShort : 'ne_po_ut_st_št_pi_so'.split('_'),
    weekdaysMin : 'ne_po_ut_st_št_pi_so'.split('_'),
    longDateFormat : {
        LT: 'H:mm',
        LTS : 'H:mm:ss',
        L : 'DD.MM.YYYY',
        LL : 'D. MMMM YYYY',
        LLL : 'D. MMMM YYYY H:mm',
        LLLL : 'dddd D. MMMM YYYY H:mm'
    },
    calendar : {
        sameDay: '[dnes o] LT',
        nextDay: '[zajtra o] LT',
        nextWeek: function () {
            switch (this.day()) {
                case 0:
                    return '[v nedeľu o] LT';
                case 1:
                case 2:
                    return '[v] dddd [o] LT';
                case 3:
                    return '[v stredu o] LT';
                case 4:
                    return '[vo štvrtok o] LT';
                case 5:
                    return '[v piatok o] LT';
                case 6:
                    return '[v sobotu o] LT';
            }
        },
        lastDay: '[včera o] LT',
        lastWeek: function () {
            switch (this.day()) {
                case 0:
                    return '[minulú nedeľu o] LT';
                case 1:
                case 2:
                    return '[minulý] dddd [o] LT';
                case 3:
                    return '[minulú stredu o] LT';
                case 4:
                case 5:
                    return '[minulý] dddd [o] LT';
                case 6:
                    return '[minulú sobotu o] LT';
            }
        },
        sameElse: 'L'
    },
    relativeTime : {
        future : 'za %s',
        past : 'pred %s',
        s : translate,
        ss : translate,
        m : translate,
        mm : translate,
        h : translate,
        hh : translate,
        d : translate,
        dd : translate,
        M : translate,
        MM : translate,
        y : translate,
        yy : translate
    },
    dayOfMonthOrdinalParse: /\d{1,2}\./,
    ordinal : '%d.',
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return sk;

})));


/***/ }),
/* 120 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Slovenian [sl]
//! author : Robert Sedovšek : https://github.com/sedovsek

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


function processRelativeTime(number, withoutSuffix, key, isFuture) {
    var result = number + ' ';
    switch (key) {
        case 's':
            return withoutSuffix || isFuture ? 'nekaj sekund' : 'nekaj sekundami';
        case 'ss':
            if (number === 1) {
                result += withoutSuffix ? 'sekundo' : 'sekundi';
            } else if (number === 2) {
                result += withoutSuffix || isFuture ? 'sekundi' : 'sekundah';
            } else if (number < 5) {
                result += withoutSuffix || isFuture ? 'sekunde' : 'sekundah';
            } else {
                result += withoutSuffix || isFuture ? 'sekund' : 'sekund';
            }
            return result;
        case 'm':
            return withoutSuffix ? 'ena minuta' : 'eno minuto';
        case 'mm':
            if (number === 1) {
                result += withoutSuffix ? 'minuta' : 'minuto';
            } else if (number === 2) {
                result += withoutSuffix || isFuture ? 'minuti' : 'minutama';
            } else if (number < 5) {
                result += withoutSuffix || isFuture ? 'minute' : 'minutami';
            } else {
                result += withoutSuffix || isFuture ? 'minut' : 'minutami';
            }
            return result;
        case 'h':
            return withoutSuffix ? 'ena ura' : 'eno uro';
        case 'hh':
            if (number === 1) {
                result += withoutSuffix ? 'ura' : 'uro';
            } else if (number === 2) {
                result += withoutSuffix || isFuture ? 'uri' : 'urama';
            } else if (number < 5) {
                result += withoutSuffix || isFuture ? 'ure' : 'urami';
            } else {
                result += withoutSuffix || isFuture ? 'ur' : 'urami';
            }
            return result;
        case 'd':
            return withoutSuffix || isFuture ? 'en dan' : 'enim dnem';
        case 'dd':
            if (number === 1) {
                result += withoutSuffix || isFuture ? 'dan' : 'dnem';
            } else if (number === 2) {
                result += withoutSuffix || isFuture ? 'dni' : 'dnevoma';
            } else {
                result += withoutSuffix || isFuture ? 'dni' : 'dnevi';
            }
            return result;
        case 'M':
            return withoutSuffix || isFuture ? 'en mesec' : 'enim mesecem';
        case 'MM':
            if (number === 1) {
                result += withoutSuffix || isFuture ? 'mesec' : 'mesecem';
            } else if (number === 2) {
                result += withoutSuffix || isFuture ? 'meseca' : 'mesecema';
            } else if (number < 5) {
                result += withoutSuffix || isFuture ? 'mesece' : 'meseci';
            } else {
                result += withoutSuffix || isFuture ? 'mesecev' : 'meseci';
            }
            return result;
        case 'y':
            return withoutSuffix || isFuture ? 'eno leto' : 'enim letom';
        case 'yy':
            if (number === 1) {
                result += withoutSuffix || isFuture ? 'leto' : 'letom';
            } else if (number === 2) {
                result += withoutSuffix || isFuture ? 'leti' : 'letoma';
            } else if (number < 5) {
                result += withoutSuffix || isFuture ? 'leta' : 'leti';
            } else {
                result += withoutSuffix || isFuture ? 'let' : 'leti';
            }
            return result;
    }
}

var sl = moment.defineLocale('sl', {
    months : 'januar_februar_marec_april_maj_junij_julij_avgust_september_oktober_november_december'.split('_'),
    monthsShort : 'jan._feb._mar._apr._maj._jun._jul._avg._sep._okt._nov._dec.'.split('_'),
    monthsParseExact: true,
    weekdays : 'nedelja_ponedeljek_torek_sreda_četrtek_petek_sobota'.split('_'),
    weekdaysShort : 'ned._pon._tor._sre._čet._pet._sob.'.split('_'),
    weekdaysMin : 'ne_po_to_sr_če_pe_so'.split('_'),
    weekdaysParseExact : true,
    longDateFormat : {
        LT : 'H:mm',
        LTS : 'H:mm:ss',
        L : 'DD.MM.YYYY',
        LL : 'D. MMMM YYYY',
        LLL : 'D. MMMM YYYY H:mm',
        LLLL : 'dddd, D. MMMM YYYY H:mm'
    },
    calendar : {
        sameDay  : '[danes ob] LT',
        nextDay  : '[jutri ob] LT',

        nextWeek : function () {
            switch (this.day()) {
                case 0:
                    return '[v] [nedeljo] [ob] LT';
                case 3:
                    return '[v] [sredo] [ob] LT';
                case 6:
                    return '[v] [soboto] [ob] LT';
                case 1:
                case 2:
                case 4:
                case 5:
                    return '[v] dddd [ob] LT';
            }
        },
        lastDay  : '[včeraj ob] LT',
        lastWeek : function () {
            switch (this.day()) {
                case 0:
                    return '[prejšnjo] [nedeljo] [ob] LT';
                case 3:
                    return '[prejšnjo] [sredo] [ob] LT';
                case 6:
                    return '[prejšnjo] [soboto] [ob] LT';
                case 1:
                case 2:
                case 4:
                case 5:
                    return '[prejšnji] dddd [ob] LT';
            }
        },
        sameElse : 'L'
    },
    relativeTime : {
        future : 'čez %s',
        past   : 'pred %s',
        s      : processRelativeTime,
        ss     : processRelativeTime,
        m      : processRelativeTime,
        mm     : processRelativeTime,
        h      : processRelativeTime,
        hh     : processRelativeTime,
        d      : processRelativeTime,
        dd     : processRelativeTime,
        M      : processRelativeTime,
        MM     : processRelativeTime,
        y      : processRelativeTime,
        yy     : processRelativeTime
    },
    dayOfMonthOrdinalParse: /\d{1,2}\./,
    ordinal : '%d.',
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 7  // The week that contains Jan 1st is the first week of the year.
    }
});

return sl;

})));


/***/ }),
/* 121 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Albanian [sq]
//! author : Flakërim Ismani : https://github.com/flakerimi
//! author : Menelion Elensúle : https://github.com/Oire
//! author : Oerd Cukalla : https://github.com/oerd

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var sq = moment.defineLocale('sq', {
    months : 'Janar_Shkurt_Mars_Prill_Maj_Qershor_Korrik_Gusht_Shtator_Tetor_Nëntor_Dhjetor'.split('_'),
    monthsShort : 'Jan_Shk_Mar_Pri_Maj_Qer_Kor_Gus_Sht_Tet_Nën_Dhj'.split('_'),
    weekdays : 'E Diel_E Hënë_E Martë_E Mërkurë_E Enjte_E Premte_E Shtunë'.split('_'),
    weekdaysShort : 'Die_Hën_Mar_Mër_Enj_Pre_Sht'.split('_'),
    weekdaysMin : 'D_H_Ma_Më_E_P_Sh'.split('_'),
    weekdaysParseExact : true,
    meridiemParse: /PD|MD/,
    isPM: function (input) {
        return input.charAt(0) === 'M';
    },
    meridiem : function (hours, minutes, isLower) {
        return hours < 12 ? 'PD' : 'MD';
    },
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY HH:mm',
        LLLL : 'dddd, D MMMM YYYY HH:mm'
    },
    calendar : {
        sameDay : '[Sot në] LT',
        nextDay : '[Nesër në] LT',
        nextWeek : 'dddd [në] LT',
        lastDay : '[Dje në] LT',
        lastWeek : 'dddd [e kaluar në] LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : 'në %s',
        past : '%s më parë',
        s : 'disa sekonda',
        ss : '%d sekonda',
        m : 'një minutë',
        mm : '%d minuta',
        h : 'një orë',
        hh : '%d orë',
        d : 'një ditë',
        dd : '%d ditë',
        M : 'një muaj',
        MM : '%d muaj',
        y : 'një vit',
        yy : '%d vite'
    },
    dayOfMonthOrdinalParse: /\d{1,2}\./,
    ordinal : '%d.',
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return sq;

})));


/***/ }),
/* 122 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Serbian Cyrillic [sr-cyrl]
//! author : Milan Janačković<milanjanackovic@gmail.com> : https://github.com/milan-j

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var translator = {
    words: { //Different grammatical cases
        ss: ['секунда', 'секунде', 'секунди'],
        m: ['један минут', 'једне минуте'],
        mm: ['минут', 'минуте', 'минута'],
        h: ['један сат', 'једног сата'],
        hh: ['сат', 'сата', 'сати'],
        dd: ['дан', 'дана', 'дана'],
        MM: ['месец', 'месеца', 'месеци'],
        yy: ['година', 'године', 'година']
    },
    correctGrammaticalCase: function (number, wordKey) {
        return number === 1 ? wordKey[0] : (number >= 2 && number <= 4 ? wordKey[1] : wordKey[2]);
    },
    translate: function (number, withoutSuffix, key) {
        var wordKey = translator.words[key];
        if (key.length === 1) {
            return withoutSuffix ? wordKey[0] : wordKey[1];
        } else {
            return number + ' ' + translator.correctGrammaticalCase(number, wordKey);
        }
    }
};

var srCyrl = moment.defineLocale('sr-cyrl', {
    months: 'јануар_фебруар_март_април_мај_јун_јул_август_септембар_октобар_новембар_децембар'.split('_'),
    monthsShort: 'јан._феб._мар._апр._мај_јун_јул_авг._сеп._окт._нов._дец.'.split('_'),
    monthsParseExact: true,
    weekdays: 'недеља_понедељак_уторак_среда_четвртак_петак_субота'.split('_'),
    weekdaysShort: 'нед._пон._уто._сре._чет._пет._суб.'.split('_'),
    weekdaysMin: 'не_по_ут_ср_че_пе_су'.split('_'),
    weekdaysParseExact : true,
    longDateFormat: {
        LT: 'H:mm',
        LTS : 'H:mm:ss',
        L: 'DD.MM.YYYY',
        LL: 'D. MMMM YYYY',
        LLL: 'D. MMMM YYYY H:mm',
        LLLL: 'dddd, D. MMMM YYYY H:mm'
    },
    calendar: {
        sameDay: '[данас у] LT',
        nextDay: '[сутра у] LT',
        nextWeek: function () {
            switch (this.day()) {
                case 0:
                    return '[у] [недељу] [у] LT';
                case 3:
                    return '[у] [среду] [у] LT';
                case 6:
                    return '[у] [суботу] [у] LT';
                case 1:
                case 2:
                case 4:
                case 5:
                    return '[у] dddd [у] LT';
            }
        },
        lastDay  : '[јуче у] LT',
        lastWeek : function () {
            var lastWeekDays = [
                '[прошле] [недеље] [у] LT',
                '[прошлог] [понедељка] [у] LT',
                '[прошлог] [уторка] [у] LT',
                '[прошле] [среде] [у] LT',
                '[прошлог] [четвртка] [у] LT',
                '[прошлог] [петка] [у] LT',
                '[прошле] [суботе] [у] LT'
            ];
            return lastWeekDays[this.day()];
        },
        sameElse : 'L'
    },
    relativeTime : {
        future : 'за %s',
        past   : 'пре %s',
        s      : 'неколико секунди',
        ss     : translator.translate,
        m      : translator.translate,
        mm     : translator.translate,
        h      : translator.translate,
        hh     : translator.translate,
        d      : 'дан',
        dd     : translator.translate,
        M      : 'месец',
        MM     : translator.translate,
        y      : 'годину',
        yy     : translator.translate
    },
    dayOfMonthOrdinalParse: /\d{1,2}\./,
    ordinal : '%d.',
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 7  // The week that contains Jan 1st is the first week of the year.
    }
});

return srCyrl;

})));


/***/ }),
/* 123 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Serbian [sr]
//! author : Milan Janačković<milanjanackovic@gmail.com> : https://github.com/milan-j

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var translator = {
    words: { //Different grammatical cases
        ss: ['sekunda', 'sekunde', 'sekundi'],
        m: ['jedan minut', 'jedne minute'],
        mm: ['minut', 'minute', 'minuta'],
        h: ['jedan sat', 'jednog sata'],
        hh: ['sat', 'sata', 'sati'],
        dd: ['dan', 'dana', 'dana'],
        MM: ['mesec', 'meseca', 'meseci'],
        yy: ['godina', 'godine', 'godina']
    },
    correctGrammaticalCase: function (number, wordKey) {
        return number === 1 ? wordKey[0] : (number >= 2 && number <= 4 ? wordKey[1] : wordKey[2]);
    },
    translate: function (number, withoutSuffix, key) {
        var wordKey = translator.words[key];
        if (key.length === 1) {
            return withoutSuffix ? wordKey[0] : wordKey[1];
        } else {
            return number + ' ' + translator.correctGrammaticalCase(number, wordKey);
        }
    }
};

var sr = moment.defineLocale('sr', {
    months: 'januar_februar_mart_april_maj_jun_jul_avgust_septembar_oktobar_novembar_decembar'.split('_'),
    monthsShort: 'jan._feb._mar._apr._maj_jun_jul_avg._sep._okt._nov._dec.'.split('_'),
    monthsParseExact: true,
    weekdays: 'nedelja_ponedeljak_utorak_sreda_četvrtak_petak_subota'.split('_'),
    weekdaysShort: 'ned._pon._uto._sre._čet._pet._sub.'.split('_'),
    weekdaysMin: 'ne_po_ut_sr_če_pe_su'.split('_'),
    weekdaysParseExact : true,
    longDateFormat: {
        LT: 'H:mm',
        LTS : 'H:mm:ss',
        L: 'DD.MM.YYYY',
        LL: 'D. MMMM YYYY',
        LLL: 'D. MMMM YYYY H:mm',
        LLLL: 'dddd, D. MMMM YYYY H:mm'
    },
    calendar: {
        sameDay: '[danas u] LT',
        nextDay: '[sutra u] LT',
        nextWeek: function () {
            switch (this.day()) {
                case 0:
                    return '[u] [nedelju] [u] LT';
                case 3:
                    return '[u] [sredu] [u] LT';
                case 6:
                    return '[u] [subotu] [u] LT';
                case 1:
                case 2:
                case 4:
                case 5:
                    return '[u] dddd [u] LT';
            }
        },
        lastDay  : '[juče u] LT',
        lastWeek : function () {
            var lastWeekDays = [
                '[prošle] [nedelje] [u] LT',
                '[prošlog] [ponedeljka] [u] LT',
                '[prošlog] [utorka] [u] LT',
                '[prošle] [srede] [u] LT',
                '[prošlog] [četvrtka] [u] LT',
                '[prošlog] [petka] [u] LT',
                '[prošle] [subote] [u] LT'
            ];
            return lastWeekDays[this.day()];
        },
        sameElse : 'L'
    },
    relativeTime : {
        future : 'za %s',
        past   : 'pre %s',
        s      : 'nekoliko sekundi',
        ss     : translator.translate,
        m      : translator.translate,
        mm     : translator.translate,
        h      : translator.translate,
        hh     : translator.translate,
        d      : 'dan',
        dd     : translator.translate,
        M      : 'mesec',
        MM     : translator.translate,
        y      : 'godinu',
        yy     : translator.translate
    },
    dayOfMonthOrdinalParse: /\d{1,2}\./,
    ordinal : '%d.',
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 7  // The week that contains Jan 1st is the first week of the year.
    }
});

return sr;

})));


/***/ }),
/* 124 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : siSwati [ss]
//! author : Nicolai Davies<mail@nicolai.io> : https://github.com/nicolaidavies

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';



var ss = moment.defineLocale('ss', {
    months : "Bhimbidvwane_Indlovana_Indlov'lenkhulu_Mabasa_Inkhwekhweti_Inhlaba_Kholwane_Ingci_Inyoni_Imphala_Lweti_Ingongoni".split('_'),
    monthsShort : 'Bhi_Ina_Inu_Mab_Ink_Inh_Kho_Igc_Iny_Imp_Lwe_Igo'.split('_'),
    weekdays : 'Lisontfo_Umsombuluko_Lesibili_Lesitsatfu_Lesine_Lesihlanu_Umgcibelo'.split('_'),
    weekdaysShort : 'Lis_Umb_Lsb_Les_Lsi_Lsh_Umg'.split('_'),
    weekdaysMin : 'Li_Us_Lb_Lt_Ls_Lh_Ug'.split('_'),
    weekdaysParseExact : true,
    longDateFormat : {
        LT : 'h:mm A',
        LTS : 'h:mm:ss A',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY h:mm A',
        LLLL : 'dddd, D MMMM YYYY h:mm A'
    },
    calendar : {
        sameDay : '[Namuhla nga] LT',
        nextDay : '[Kusasa nga] LT',
        nextWeek : 'dddd [nga] LT',
        lastDay : '[Itolo nga] LT',
        lastWeek : 'dddd [leliphelile] [nga] LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : 'nga %s',
        past : 'wenteka nga %s',
        s : 'emizuzwana lomcane',
        ss : '%d mzuzwana',
        m : 'umzuzu',
        mm : '%d emizuzu',
        h : 'lihora',
        hh : '%d emahora',
        d : 'lilanga',
        dd : '%d emalanga',
        M : 'inyanga',
        MM : '%d tinyanga',
        y : 'umnyaka',
        yy : '%d iminyaka'
    },
    meridiemParse: /ekuseni|emini|entsambama|ebusuku/,
    meridiem : function (hours, minutes, isLower) {
        if (hours < 11) {
            return 'ekuseni';
        } else if (hours < 15) {
            return 'emini';
        } else if (hours < 19) {
            return 'entsambama';
        } else {
            return 'ebusuku';
        }
    },
    meridiemHour : function (hour, meridiem) {
        if (hour === 12) {
            hour = 0;
        }
        if (meridiem === 'ekuseni') {
            return hour;
        } else if (meridiem === 'emini') {
            return hour >= 11 ? hour : hour + 12;
        } else if (meridiem === 'entsambama' || meridiem === 'ebusuku') {
            if (hour === 0) {
                return 0;
            }
            return hour + 12;
        }
    },
    dayOfMonthOrdinalParse: /\d{1,2}/,
    ordinal : '%d',
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return ss;

})));


/***/ }),
/* 125 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Swedish [sv]
//! author : Jens Alm : https://github.com/ulmus

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var sv = moment.defineLocale('sv', {
    months : 'januari_februari_mars_april_maj_juni_juli_augusti_september_oktober_november_december'.split('_'),
    monthsShort : 'jan_feb_mar_apr_maj_jun_jul_aug_sep_okt_nov_dec'.split('_'),
    weekdays : 'söndag_måndag_tisdag_onsdag_torsdag_fredag_lördag'.split('_'),
    weekdaysShort : 'sön_mån_tis_ons_tor_fre_lör'.split('_'),
    weekdaysMin : 'sö_må_ti_on_to_fr_lö'.split('_'),
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'YYYY-MM-DD',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY [kl.] HH:mm',
        LLLL : 'dddd D MMMM YYYY [kl.] HH:mm',
        lll : 'D MMM YYYY HH:mm',
        llll : 'ddd D MMM YYYY HH:mm'
    },
    calendar : {
        sameDay: '[Idag] LT',
        nextDay: '[Imorgon] LT',
        lastDay: '[Igår] LT',
        nextWeek: '[På] dddd LT',
        lastWeek: '[I] dddd[s] LT',
        sameElse: 'L'
    },
    relativeTime : {
        future : 'om %s',
        past : 'för %s sedan',
        s : 'några sekunder',
        ss : '%d sekunder',
        m : 'en minut',
        mm : '%d minuter',
        h : 'en timme',
        hh : '%d timmar',
        d : 'en dag',
        dd : '%d dagar',
        M : 'en månad',
        MM : '%d månader',
        y : 'ett år',
        yy : '%d år'
    },
    dayOfMonthOrdinalParse: /\d{1,2}(e|a)/,
    ordinal : function (number) {
        var b = number % 10,
            output = (~~(number % 100 / 10) === 1) ? 'e' :
            (b === 1) ? 'a' :
            (b === 2) ? 'a' :
            (b === 3) ? 'e' : 'e';
        return number + output;
    },
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return sv;

})));


/***/ }),
/* 126 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Swahili [sw]
//! author : Fahad Kassim : https://github.com/fadsel

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var sw = moment.defineLocale('sw', {
    months : 'Januari_Februari_Machi_Aprili_Mei_Juni_Julai_Agosti_Septemba_Oktoba_Novemba_Desemba'.split('_'),
    monthsShort : 'Jan_Feb_Mac_Apr_Mei_Jun_Jul_Ago_Sep_Okt_Nov_Des'.split('_'),
    weekdays : 'Jumapili_Jumatatu_Jumanne_Jumatano_Alhamisi_Ijumaa_Jumamosi'.split('_'),
    weekdaysShort : 'Jpl_Jtat_Jnne_Jtan_Alh_Ijm_Jmos'.split('_'),
    weekdaysMin : 'J2_J3_J4_J5_Al_Ij_J1'.split('_'),
    weekdaysParseExact : true,
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD.MM.YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY HH:mm',
        LLLL : 'dddd, D MMMM YYYY HH:mm'
    },
    calendar : {
        sameDay : '[leo saa] LT',
        nextDay : '[kesho saa] LT',
        nextWeek : '[wiki ijayo] dddd [saat] LT',
        lastDay : '[jana] LT',
        lastWeek : '[wiki iliyopita] dddd [saat] LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : '%s baadaye',
        past : 'tokea %s',
        s : 'hivi punde',
        ss : 'sekunde %d',
        m : 'dakika moja',
        mm : 'dakika %d',
        h : 'saa limoja',
        hh : 'masaa %d',
        d : 'siku moja',
        dd : 'masiku %d',
        M : 'mwezi mmoja',
        MM : 'miezi %d',
        y : 'mwaka mmoja',
        yy : 'miaka %d'
    },
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 7  // The week that contains Jan 1st is the first week of the year.
    }
});

return sw;

})));


/***/ }),
/* 127 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Tamil [ta]
//! author : Arjunkumar Krishnamoorthy : https://github.com/tk120404

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var symbolMap = {
    '1': '௧',
    '2': '௨',
    '3': '௩',
    '4': '௪',
    '5': '௫',
    '6': '௬',
    '7': '௭',
    '8': '௮',
    '9': '௯',
    '0': '௦'
};
var numberMap = {
    '௧': '1',
    '௨': '2',
    '௩': '3',
    '௪': '4',
    '௫': '5',
    '௬': '6',
    '௭': '7',
    '௮': '8',
    '௯': '9',
    '௦': '0'
};

var ta = moment.defineLocale('ta', {
    months : 'ஜனவரி_பிப்ரவரி_மார்ச்_ஏப்ரல்_மே_ஜூன்_ஜூலை_ஆகஸ்ட்_செப்டெம்பர்_அக்டோபர்_நவம்பர்_டிசம்பர்'.split('_'),
    monthsShort : 'ஜனவரி_பிப்ரவரி_மார்ச்_ஏப்ரல்_மே_ஜூன்_ஜூலை_ஆகஸ்ட்_செப்டெம்பர்_அக்டோபர்_நவம்பர்_டிசம்பர்'.split('_'),
    weekdays : 'ஞாயிற்றுக்கிழமை_திங்கட்கிழமை_செவ்வாய்கிழமை_புதன்கிழமை_வியாழக்கிழமை_வெள்ளிக்கிழமை_சனிக்கிழமை'.split('_'),
    weekdaysShort : 'ஞாயிறு_திங்கள்_செவ்வாய்_புதன்_வியாழன்_வெள்ளி_சனி'.split('_'),
    weekdaysMin : 'ஞா_தி_செ_பு_வி_வெ_ச'.split('_'),
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY, HH:mm',
        LLLL : 'dddd, D MMMM YYYY, HH:mm'
    },
    calendar : {
        sameDay : '[இன்று] LT',
        nextDay : '[நாளை] LT',
        nextWeek : 'dddd, LT',
        lastDay : '[நேற்று] LT',
        lastWeek : '[கடந்த வாரம்] dddd, LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : '%s இல்',
        past : '%s முன்',
        s : 'ஒரு சில விநாடிகள்',
        ss : '%d விநாடிகள்',
        m : 'ஒரு நிமிடம்',
        mm : '%d நிமிடங்கள்',
        h : 'ஒரு மணி நேரம்',
        hh : '%d மணி நேரம்',
        d : 'ஒரு நாள்',
        dd : '%d நாட்கள்',
        M : 'ஒரு மாதம்',
        MM : '%d மாதங்கள்',
        y : 'ஒரு வருடம்',
        yy : '%d ஆண்டுகள்'
    },
    dayOfMonthOrdinalParse: /\d{1,2}வது/,
    ordinal : function (number) {
        return number + 'வது';
    },
    preparse: function (string) {
        return string.replace(/[௧௨௩௪௫௬௭௮௯௦]/g, function (match) {
            return numberMap[match];
        });
    },
    postformat: function (string) {
        return string.replace(/\d/g, function (match) {
            return symbolMap[match];
        });
    },
    // refer http://ta.wikipedia.org/s/1er1
    meridiemParse: /யாமம்|வைகறை|காலை|நண்பகல்|எற்பாடு|மாலை/,
    meridiem : function (hour, minute, isLower) {
        if (hour < 2) {
            return ' யாமம்';
        } else if (hour < 6) {
            return ' வைகறை';  // வைகறை
        } else if (hour < 10) {
            return ' காலை'; // காலை
        } else if (hour < 14) {
            return ' நண்பகல்'; // நண்பகல்
        } else if (hour < 18) {
            return ' எற்பாடு'; // எற்பாடு
        } else if (hour < 22) {
            return ' மாலை'; // மாலை
        } else {
            return ' யாமம்';
        }
    },
    meridiemHour : function (hour, meridiem) {
        if (hour === 12) {
            hour = 0;
        }
        if (meridiem === 'யாமம்') {
            return hour < 2 ? hour : hour + 12;
        } else if (meridiem === 'வைகறை' || meridiem === 'காலை') {
            return hour;
        } else if (meridiem === 'நண்பகல்') {
            return hour >= 10 ? hour : hour + 12;
        } else {
            return hour + 12;
        }
    },
    week : {
        dow : 0, // Sunday is the first day of the week.
        doy : 6  // The week that contains Jan 1st is the first week of the year.
    }
});

return ta;

})));


/***/ }),
/* 128 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Telugu [te]
//! author : Krishna Chaitanya Thota : https://github.com/kcthota

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var te = moment.defineLocale('te', {
    months : 'జనవరి_ఫిబ్రవరి_మార్చి_ఏప్రిల్_మే_జూన్_జూలై_ఆగస్టు_సెప్టెంబర్_అక్టోబర్_నవంబర్_డిసెంబర్'.split('_'),
    monthsShort : 'జన._ఫిబ్ర._మార్చి_ఏప్రి._మే_జూన్_జూలై_ఆగ._సెప్._అక్టో._నవ._డిసె.'.split('_'),
    monthsParseExact : true,
    weekdays : 'ఆదివారం_సోమవారం_మంగళవారం_బుధవారం_గురువారం_శుక్రవారం_శనివారం'.split('_'),
    weekdaysShort : 'ఆది_సోమ_మంగళ_బుధ_గురు_శుక్ర_శని'.split('_'),
    weekdaysMin : 'ఆ_సో_మం_బు_గు_శు_శ'.split('_'),
    longDateFormat : {
        LT : 'A h:mm',
        LTS : 'A h:mm:ss',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY, A h:mm',
        LLLL : 'dddd, D MMMM YYYY, A h:mm'
    },
    calendar : {
        sameDay : '[నేడు] LT',
        nextDay : '[రేపు] LT',
        nextWeek : 'dddd, LT',
        lastDay : '[నిన్న] LT',
        lastWeek : '[గత] dddd, LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : '%s లో',
        past : '%s క్రితం',
        s : 'కొన్ని క్షణాలు',
        ss : '%d సెకన్లు',
        m : 'ఒక నిమిషం',
        mm : '%d నిమిషాలు',
        h : 'ఒక గంట',
        hh : '%d గంటలు',
        d : 'ఒక రోజు',
        dd : '%d రోజులు',
        M : 'ఒక నెల',
        MM : '%d నెలలు',
        y : 'ఒక సంవత్సరం',
        yy : '%d సంవత్సరాలు'
    },
    dayOfMonthOrdinalParse : /\d{1,2}వ/,
    ordinal : '%dవ',
    meridiemParse: /రాత్రి|ఉదయం|మధ్యాహ్నం|సాయంత్రం/,
    meridiemHour : function (hour, meridiem) {
        if (hour === 12) {
            hour = 0;
        }
        if (meridiem === 'రాత్రి') {
            return hour < 4 ? hour : hour + 12;
        } else if (meridiem === 'ఉదయం') {
            return hour;
        } else if (meridiem === 'మధ్యాహ్నం') {
            return hour >= 10 ? hour : hour + 12;
        } else if (meridiem === 'సాయంత్రం') {
            return hour + 12;
        }
    },
    meridiem : function (hour, minute, isLower) {
        if (hour < 4) {
            return 'రాత్రి';
        } else if (hour < 10) {
            return 'ఉదయం';
        } else if (hour < 17) {
            return 'మధ్యాహ్నం';
        } else if (hour < 20) {
            return 'సాయంత్రం';
        } else {
            return 'రాత్రి';
        }
    },
    week : {
        dow : 0, // Sunday is the first day of the week.
        doy : 6  // The week that contains Jan 1st is the first week of the year.
    }
});

return te;

})));


/***/ }),
/* 129 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Tetun Dili (East Timor) [tet]
//! author : Joshua Brooks : https://github.com/joshbrooks
//! author : Onorio De J. Afonso : https://github.com/marobo

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var tet = moment.defineLocale('tet', {
    months : 'Janeiru_Fevereiru_Marsu_Abril_Maiu_Juniu_Juliu_Augustu_Setembru_Outubru_Novembru_Dezembru'.split('_'),
    monthsShort : 'Jan_Fev_Mar_Abr_Mai_Jun_Jul_Aug_Set_Out_Nov_Dez'.split('_'),
    weekdays : 'Domingu_Segunda_Tersa_Kuarta_Kinta_Sexta_Sabadu'.split('_'),
    weekdaysShort : 'Dom_Seg_Ters_Kua_Kint_Sext_Sab'.split('_'),
    weekdaysMin : 'Do_Seg_Te_Ku_Ki_Sex_Sa'.split('_'),
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY HH:mm',
        LLLL : 'dddd, D MMMM YYYY HH:mm'
    },
    calendar : {
        sameDay: '[Ohin iha] LT',
        nextDay: '[Aban iha] LT',
        nextWeek: 'dddd [iha] LT',
        lastDay: '[Horiseik iha] LT',
        lastWeek: 'dddd [semana kotuk] [iha] LT',
        sameElse: 'L'
    },
    relativeTime : {
        future : 'iha %s',
        past : '%s liuba',
        s : 'minutu balun',
        ss : 'minutu %d',
        m : 'minutu ida',
        mm : 'minutus %d',
        h : 'horas ida',
        hh : 'horas %d',
        d : 'loron ida',
        dd : 'loron %d',
        M : 'fulan ida',
        MM : 'fulan %d',
        y : 'tinan ida',
        yy : 'tinan %d'
    },
    dayOfMonthOrdinalParse: /\d{1,2}(st|nd|rd|th)/,
    ordinal : function (number) {
        var b = number % 10,
            output = (~~(number % 100 / 10) === 1) ? 'th' :
            (b === 1) ? 'st' :
            (b === 2) ? 'nd' :
            (b === 3) ? 'rd' : 'th';
        return number + output;
    },
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return tet;

})));


/***/ }),
/* 130 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Thai [th]
//! author : Kridsada Thanabulpong : https://github.com/sirn

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var th = moment.defineLocale('th', {
    months : 'มกราคม_กุมภาพันธ์_มีนาคม_เมษายน_พฤษภาคม_มิถุนายน_กรกฎาคม_สิงหาคม_กันยายน_ตุลาคม_พฤศจิกายน_ธันวาคม'.split('_'),
    monthsShort : 'ม.ค._ก.พ._มี.ค._เม.ย._พ.ค._มิ.ย._ก.ค._ส.ค._ก.ย._ต.ค._พ.ย._ธ.ค.'.split('_'),
    monthsParseExact: true,
    weekdays : 'อาทิตย์_จันทร์_อังคาร_พุธ_พฤหัสบดี_ศุกร์_เสาร์'.split('_'),
    weekdaysShort : 'อาทิตย์_จันทร์_อังคาร_พุธ_พฤหัส_ศุกร์_เสาร์'.split('_'), // yes, three characters difference
    weekdaysMin : 'อา._จ._อ._พ._พฤ._ศ._ส.'.split('_'),
    weekdaysParseExact : true,
    longDateFormat : {
        LT : 'H:mm',
        LTS : 'H:mm:ss',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY เวลา H:mm',
        LLLL : 'วันddddที่ D MMMM YYYY เวลา H:mm'
    },
    meridiemParse: /ก่อนเที่ยง|หลังเที่ยง/,
    isPM: function (input) {
        return input === 'หลังเที่ยง';
    },
    meridiem : function (hour, minute, isLower) {
        if (hour < 12) {
            return 'ก่อนเที่ยง';
        } else {
            return 'หลังเที่ยง';
        }
    },
    calendar : {
        sameDay : '[วันนี้ เวลา] LT',
        nextDay : '[พรุ่งนี้ เวลา] LT',
        nextWeek : 'dddd[หน้า เวลา] LT',
        lastDay : '[เมื่อวานนี้ เวลา] LT',
        lastWeek : '[วัน]dddd[ที่แล้ว เวลา] LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : 'อีก %s',
        past : '%sที่แล้ว',
        s : 'ไม่กี่วินาที',
        ss : '%d วินาที',
        m : '1 นาที',
        mm : '%d นาที',
        h : '1 ชั่วโมง',
        hh : '%d ชั่วโมง',
        d : '1 วัน',
        dd : '%d วัน',
        M : '1 เดือน',
        MM : '%d เดือน',
        y : '1 ปี',
        yy : '%d ปี'
    }
});

return th;

})));


/***/ }),
/* 131 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Tagalog (Philippines) [tl-ph]
//! author : Dan Hagman : https://github.com/hagmandan

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var tlPh = moment.defineLocale('tl-ph', {
    months : 'Enero_Pebrero_Marso_Abril_Mayo_Hunyo_Hulyo_Agosto_Setyembre_Oktubre_Nobyembre_Disyembre'.split('_'),
    monthsShort : 'Ene_Peb_Mar_Abr_May_Hun_Hul_Ago_Set_Okt_Nob_Dis'.split('_'),
    weekdays : 'Linggo_Lunes_Martes_Miyerkules_Huwebes_Biyernes_Sabado'.split('_'),
    weekdaysShort : 'Lin_Lun_Mar_Miy_Huw_Biy_Sab'.split('_'),
    weekdaysMin : 'Li_Lu_Ma_Mi_Hu_Bi_Sab'.split('_'),
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'MM/D/YYYY',
        LL : 'MMMM D, YYYY',
        LLL : 'MMMM D, YYYY HH:mm',
        LLLL : 'dddd, MMMM DD, YYYY HH:mm'
    },
    calendar : {
        sameDay: 'LT [ngayong araw]',
        nextDay: '[Bukas ng] LT',
        nextWeek: 'LT [sa susunod na] dddd',
        lastDay: 'LT [kahapon]',
        lastWeek: 'LT [noong nakaraang] dddd',
        sameElse: 'L'
    },
    relativeTime : {
        future : 'sa loob ng %s',
        past : '%s ang nakalipas',
        s : 'ilang segundo',
        ss : '%d segundo',
        m : 'isang minuto',
        mm : '%d minuto',
        h : 'isang oras',
        hh : '%d oras',
        d : 'isang araw',
        dd : '%d araw',
        M : 'isang buwan',
        MM : '%d buwan',
        y : 'isang taon',
        yy : '%d taon'
    },
    dayOfMonthOrdinalParse: /\d{1,2}/,
    ordinal : function (number) {
        return number;
    },
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return tlPh;

})));


/***/ }),
/* 132 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Klingon [tlh]
//! author : Dominika Kruk : https://github.com/amaranthrose

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var numbersNouns = 'pagh_wa’_cha’_wej_loS_vagh_jav_Soch_chorgh_Hut'.split('_');

function translateFuture(output) {
    var time = output;
    time = (output.indexOf('jaj') !== -1) ?
    time.slice(0, -3) + 'leS' :
    (output.indexOf('jar') !== -1) ?
    time.slice(0, -3) + 'waQ' :
    (output.indexOf('DIS') !== -1) ?
    time.slice(0, -3) + 'nem' :
    time + ' pIq';
    return time;
}

function translatePast(output) {
    var time = output;
    time = (output.indexOf('jaj') !== -1) ?
    time.slice(0, -3) + 'Hu’' :
    (output.indexOf('jar') !== -1) ?
    time.slice(0, -3) + 'wen' :
    (output.indexOf('DIS') !== -1) ?
    time.slice(0, -3) + 'ben' :
    time + ' ret';
    return time;
}

function translate(number, withoutSuffix, string, isFuture) {
    var numberNoun = numberAsNoun(number);
    switch (string) {
        case 'ss':
            return numberNoun + ' lup';
        case 'mm':
            return numberNoun + ' tup';
        case 'hh':
            return numberNoun + ' rep';
        case 'dd':
            return numberNoun + ' jaj';
        case 'MM':
            return numberNoun + ' jar';
        case 'yy':
            return numberNoun + ' DIS';
    }
}

function numberAsNoun(number) {
    var hundred = Math.floor((number % 1000) / 100),
    ten = Math.floor((number % 100) / 10),
    one = number % 10,
    word = '';
    if (hundred > 0) {
        word += numbersNouns[hundred] + 'vatlh';
    }
    if (ten > 0) {
        word += ((word !== '') ? ' ' : '') + numbersNouns[ten] + 'maH';
    }
    if (one > 0) {
        word += ((word !== '') ? ' ' : '') + numbersNouns[one];
    }
    return (word === '') ? 'pagh' : word;
}

var tlh = moment.defineLocale('tlh', {
    months : 'tera’ jar wa’_tera’ jar cha’_tera’ jar wej_tera’ jar loS_tera’ jar vagh_tera’ jar jav_tera’ jar Soch_tera’ jar chorgh_tera’ jar Hut_tera’ jar wa’maH_tera’ jar wa’maH wa’_tera’ jar wa’maH cha’'.split('_'),
    monthsShort : 'jar wa’_jar cha’_jar wej_jar loS_jar vagh_jar jav_jar Soch_jar chorgh_jar Hut_jar wa’maH_jar wa’maH wa’_jar wa’maH cha’'.split('_'),
    monthsParseExact : true,
    weekdays : 'lojmItjaj_DaSjaj_povjaj_ghItlhjaj_loghjaj_buqjaj_ghInjaj'.split('_'),
    weekdaysShort : 'lojmItjaj_DaSjaj_povjaj_ghItlhjaj_loghjaj_buqjaj_ghInjaj'.split('_'),
    weekdaysMin : 'lojmItjaj_DaSjaj_povjaj_ghItlhjaj_loghjaj_buqjaj_ghInjaj'.split('_'),
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD.MM.YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY HH:mm',
        LLLL : 'dddd, D MMMM YYYY HH:mm'
    },
    calendar : {
        sameDay: '[DaHjaj] LT',
        nextDay: '[wa’leS] LT',
        nextWeek: 'LLL',
        lastDay: '[wa’Hu’] LT',
        lastWeek: 'LLL',
        sameElse: 'L'
    },
    relativeTime : {
        future : translateFuture,
        past : translatePast,
        s : 'puS lup',
        ss : translate,
        m : 'wa’ tup',
        mm : translate,
        h : 'wa’ rep',
        hh : translate,
        d : 'wa’ jaj',
        dd : translate,
        M : 'wa’ jar',
        MM : translate,
        y : 'wa’ DIS',
        yy : translate
    },
    dayOfMonthOrdinalParse: /\d{1,2}\./,
    ordinal : '%d.',
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return tlh;

})));


/***/ }),
/* 133 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Turkish [tr]
//! authors : Erhan Gundogan : https://github.com/erhangundogan,
//!           Burak Yiğit Kaya: https://github.com/BYK

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var suffixes = {
    1: '\'inci',
    5: '\'inci',
    8: '\'inci',
    70: '\'inci',
    80: '\'inci',
    2: '\'nci',
    7: '\'nci',
    20: '\'nci',
    50: '\'nci',
    3: '\'üncü',
    4: '\'üncü',
    100: '\'üncü',
    6: '\'ncı',
    9: '\'uncu',
    10: '\'uncu',
    30: '\'uncu',
    60: '\'ıncı',
    90: '\'ıncı'
};

var tr = moment.defineLocale('tr', {
    months : 'Ocak_Şubat_Mart_Nisan_Mayıs_Haziran_Temmuz_Ağustos_Eylül_Ekim_Kasım_Aralık'.split('_'),
    monthsShort : 'Oca_Şub_Mar_Nis_May_Haz_Tem_Ağu_Eyl_Eki_Kas_Ara'.split('_'),
    weekdays : 'Pazar_Pazartesi_Salı_Çarşamba_Perşembe_Cuma_Cumartesi'.split('_'),
    weekdaysShort : 'Paz_Pts_Sal_Çar_Per_Cum_Cts'.split('_'),
    weekdaysMin : 'Pz_Pt_Sa_Ça_Pe_Cu_Ct'.split('_'),
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD.MM.YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY HH:mm',
        LLLL : 'dddd, D MMMM YYYY HH:mm'
    },
    calendar : {
        sameDay : '[bugün saat] LT',
        nextDay : '[yarın saat] LT',
        nextWeek : '[gelecek] dddd [saat] LT',
        lastDay : '[dün] LT',
        lastWeek : '[geçen] dddd [saat] LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : '%s sonra',
        past : '%s önce',
        s : 'birkaç saniye',
        ss : '%d saniye',
        m : 'bir dakika',
        mm : '%d dakika',
        h : 'bir saat',
        hh : '%d saat',
        d : 'bir gün',
        dd : '%d gün',
        M : 'bir ay',
        MM : '%d ay',
        y : 'bir yıl',
        yy : '%d yıl'
    },
    dayOfMonthOrdinalParse: /\d{1,2}'(inci|nci|üncü|ncı|uncu|ıncı)/,
    ordinal : function (number) {
        if (number === 0) {  // special case for zero
            return number + '\'ıncı';
        }
        var a = number % 10,
            b = number % 100 - a,
            c = number >= 100 ? 100 : null;
        return number + (suffixes[a] || suffixes[b] || suffixes[c]);
    },
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 7  // The week that contains Jan 1st is the first week of the year.
    }
});

return tr;

})));


/***/ }),
/* 134 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Talossan [tzl]
//! author : Robin van der Vliet : https://github.com/robin0van0der0v
//! author : Iustì Canun

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


// After the year there should be a slash and the amount of years since December 26, 1979 in Roman numerals.
// This is currently too difficult (maybe even impossible) to add.
var tzl = moment.defineLocale('tzl', {
    months : 'Januar_Fevraglh_Març_Avrïu_Mai_Gün_Julia_Guscht_Setemvar_Listopäts_Noemvar_Zecemvar'.split('_'),
    monthsShort : 'Jan_Fev_Mar_Avr_Mai_Gün_Jul_Gus_Set_Lis_Noe_Zec'.split('_'),
    weekdays : 'Súladi_Lúneçi_Maitzi_Márcuri_Xhúadi_Viénerçi_Sáturi'.split('_'),
    weekdaysShort : 'Súl_Lún_Mai_Már_Xhú_Vié_Sát'.split('_'),
    weekdaysMin : 'Sú_Lú_Ma_Má_Xh_Vi_Sá'.split('_'),
    longDateFormat : {
        LT : 'HH.mm',
        LTS : 'HH.mm.ss',
        L : 'DD.MM.YYYY',
        LL : 'D. MMMM [dallas] YYYY',
        LLL : 'D. MMMM [dallas] YYYY HH.mm',
        LLLL : 'dddd, [li] D. MMMM [dallas] YYYY HH.mm'
    },
    meridiemParse: /d\'o|d\'a/i,
    isPM : function (input) {
        return 'd\'o' === input.toLowerCase();
    },
    meridiem : function (hours, minutes, isLower) {
        if (hours > 11) {
            return isLower ? 'd\'o' : 'D\'O';
        } else {
            return isLower ? 'd\'a' : 'D\'A';
        }
    },
    calendar : {
        sameDay : '[oxhi à] LT',
        nextDay : '[demà à] LT',
        nextWeek : 'dddd [à] LT',
        lastDay : '[ieiri à] LT',
        lastWeek : '[sür el] dddd [lasteu à] LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : 'osprei %s',
        past : 'ja%s',
        s : processRelativeTime,
        ss : processRelativeTime,
        m : processRelativeTime,
        mm : processRelativeTime,
        h : processRelativeTime,
        hh : processRelativeTime,
        d : processRelativeTime,
        dd : processRelativeTime,
        M : processRelativeTime,
        MM : processRelativeTime,
        y : processRelativeTime,
        yy : processRelativeTime
    },
    dayOfMonthOrdinalParse: /\d{1,2}\./,
    ordinal : '%d.',
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

function processRelativeTime(number, withoutSuffix, key, isFuture) {
    var format = {
        's': ['viensas secunds', '\'iensas secunds'],
        'ss': [number + ' secunds', '' + number + ' secunds'],
        'm': ['\'n míut', '\'iens míut'],
        'mm': [number + ' míuts', '' + number + ' míuts'],
        'h': ['\'n þora', '\'iensa þora'],
        'hh': [number + ' þoras', '' + number + ' þoras'],
        'd': ['\'n ziua', '\'iensa ziua'],
        'dd': [number + ' ziuas', '' + number + ' ziuas'],
        'M': ['\'n mes', '\'iens mes'],
        'MM': [number + ' mesen', '' + number + ' mesen'],
        'y': ['\'n ar', '\'iens ar'],
        'yy': [number + ' ars', '' + number + ' ars']
    };
    return isFuture ? format[key][0] : (withoutSuffix ? format[key][0] : format[key][1]);
}

return tzl;

})));


/***/ }),
/* 135 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Central Atlas Tamazight Latin [tzm-latn]
//! author : Abdel Said : https://github.com/abdelsaid

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var tzmLatn = moment.defineLocale('tzm-latn', {
    months : 'innayr_brˤayrˤ_marˤsˤ_ibrir_mayyw_ywnyw_ywlywz_ɣwšt_šwtanbir_ktˤwbrˤ_nwwanbir_dwjnbir'.split('_'),
    monthsShort : 'innayr_brˤayrˤ_marˤsˤ_ibrir_mayyw_ywnyw_ywlywz_ɣwšt_šwtanbir_ktˤwbrˤ_nwwanbir_dwjnbir'.split('_'),
    weekdays : 'asamas_aynas_asinas_akras_akwas_asimwas_asiḍyas'.split('_'),
    weekdaysShort : 'asamas_aynas_asinas_akras_akwas_asimwas_asiḍyas'.split('_'),
    weekdaysMin : 'asamas_aynas_asinas_akras_akwas_asimwas_asiḍyas'.split('_'),
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY HH:mm',
        LLLL : 'dddd D MMMM YYYY HH:mm'
    },
    calendar : {
        sameDay: '[asdkh g] LT',
        nextDay: '[aska g] LT',
        nextWeek: 'dddd [g] LT',
        lastDay: '[assant g] LT',
        lastWeek: 'dddd [g] LT',
        sameElse: 'L'
    },
    relativeTime : {
        future : 'dadkh s yan %s',
        past : 'yan %s',
        s : 'imik',
        ss : '%d imik',
        m : 'minuḍ',
        mm : '%d minuḍ',
        h : 'saɛa',
        hh : '%d tassaɛin',
        d : 'ass',
        dd : '%d ossan',
        M : 'ayowr',
        MM : '%d iyyirn',
        y : 'asgas',
        yy : '%d isgasn'
    },
    week : {
        dow : 6, // Saturday is the first day of the week.
        doy : 12  // The week that contains Jan 1st is the first week of the year.
    }
});

return tzmLatn;

})));


/***/ }),
/* 136 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Central Atlas Tamazight [tzm]
//! author : Abdel Said : https://github.com/abdelsaid

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var tzm = moment.defineLocale('tzm', {
    months : 'ⵉⵏⵏⴰⵢⵔ_ⴱⵕⴰⵢⵕ_ⵎⴰⵕⵚ_ⵉⴱⵔⵉⵔ_ⵎⴰⵢⵢⵓ_ⵢⵓⵏⵢⵓ_ⵢⵓⵍⵢⵓⵣ_ⵖⵓⵛⵜ_ⵛⵓⵜⴰⵏⴱⵉⵔ_ⴽⵟⵓⴱⵕ_ⵏⵓⵡⴰⵏⴱⵉⵔ_ⴷⵓⵊⵏⴱⵉⵔ'.split('_'),
    monthsShort : 'ⵉⵏⵏⴰⵢⵔ_ⴱⵕⴰⵢⵕ_ⵎⴰⵕⵚ_ⵉⴱⵔⵉⵔ_ⵎⴰⵢⵢⵓ_ⵢⵓⵏⵢⵓ_ⵢⵓⵍⵢⵓⵣ_ⵖⵓⵛⵜ_ⵛⵓⵜⴰⵏⴱⵉⵔ_ⴽⵟⵓⴱⵕ_ⵏⵓⵡⴰⵏⴱⵉⵔ_ⴷⵓⵊⵏⴱⵉⵔ'.split('_'),
    weekdays : 'ⴰⵙⴰⵎⴰⵙ_ⴰⵢⵏⴰⵙ_ⴰⵙⵉⵏⴰⵙ_ⴰⴽⵔⴰⵙ_ⴰⴽⵡⴰⵙ_ⴰⵙⵉⵎⵡⴰⵙ_ⴰⵙⵉⴹⵢⴰⵙ'.split('_'),
    weekdaysShort : 'ⴰⵙⴰⵎⴰⵙ_ⴰⵢⵏⴰⵙ_ⴰⵙⵉⵏⴰⵙ_ⴰⴽⵔⴰⵙ_ⴰⴽⵡⴰⵙ_ⴰⵙⵉⵎⵡⴰⵙ_ⴰⵙⵉⴹⵢⴰⵙ'.split('_'),
    weekdaysMin : 'ⴰⵙⴰⵎⴰⵙ_ⴰⵢⵏⴰⵙ_ⴰⵙⵉⵏⴰⵙ_ⴰⴽⵔⴰⵙ_ⴰⴽⵡⴰⵙ_ⴰⵙⵉⵎⵡⴰⵙ_ⴰⵙⵉⴹⵢⴰⵙ'.split('_'),
    longDateFormat : {
        LT : 'HH:mm',
        LTS: 'HH:mm:ss',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY HH:mm',
        LLLL : 'dddd D MMMM YYYY HH:mm'
    },
    calendar : {
        sameDay: '[ⴰⵙⴷⵅ ⴴ] LT',
        nextDay: '[ⴰⵙⴽⴰ ⴴ] LT',
        nextWeek: 'dddd [ⴴ] LT',
        lastDay: '[ⴰⵚⴰⵏⵜ ⴴ] LT',
        lastWeek: 'dddd [ⴴ] LT',
        sameElse: 'L'
    },
    relativeTime : {
        future : 'ⴷⴰⴷⵅ ⵙ ⵢⴰⵏ %s',
        past : 'ⵢⴰⵏ %s',
        s : 'ⵉⵎⵉⴽ',
        ss : '%d ⵉⵎⵉⴽ',
        m : 'ⵎⵉⵏⵓⴺ',
        mm : '%d ⵎⵉⵏⵓⴺ',
        h : 'ⵙⴰⵄⴰ',
        hh : '%d ⵜⴰⵙⵙⴰⵄⵉⵏ',
        d : 'ⴰⵙⵙ',
        dd : '%d oⵙⵙⴰⵏ',
        M : 'ⴰⵢoⵓⵔ',
        MM : '%d ⵉⵢⵢⵉⵔⵏ',
        y : 'ⴰⵙⴳⴰⵙ',
        yy : '%d ⵉⵙⴳⴰⵙⵏ'
    },
    week : {
        dow : 6, // Saturday is the first day of the week.
        doy : 12  // The week that contains Jan 1st is the first week of the year.
    }
});

return tzm;

})));


/***/ }),
/* 137 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Ukrainian [uk]
//! author : zemlanin : https://github.com/zemlanin
//! Author : Menelion Elensúle : https://github.com/Oire

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


function plural(word, num) {
    var forms = word.split('_');
    return num % 10 === 1 && num % 100 !== 11 ? forms[0] : (num % 10 >= 2 && num % 10 <= 4 && (num % 100 < 10 || num % 100 >= 20) ? forms[1] : forms[2]);
}
function relativeTimeWithPlural(number, withoutSuffix, key) {
    var format = {
        'ss': withoutSuffix ? 'секунда_секунди_секунд' : 'секунду_секунди_секунд',
        'mm': withoutSuffix ? 'хвилина_хвилини_хвилин' : 'хвилину_хвилини_хвилин',
        'hh': withoutSuffix ? 'година_години_годин' : 'годину_години_годин',
        'dd': 'день_дні_днів',
        'MM': 'місяць_місяці_місяців',
        'yy': 'рік_роки_років'
    };
    if (key === 'm') {
        return withoutSuffix ? 'хвилина' : 'хвилину';
    }
    else if (key === 'h') {
        return withoutSuffix ? 'година' : 'годину';
    }
    else {
        return number + ' ' + plural(format[key], +number);
    }
}
function weekdaysCaseReplace(m, format) {
    var weekdays = {
        'nominative': 'неділя_понеділок_вівторок_середа_четвер_п’ятниця_субота'.split('_'),
        'accusative': 'неділю_понеділок_вівторок_середу_четвер_п’ятницю_суботу'.split('_'),
        'genitive': 'неділі_понеділка_вівторка_середи_четверга_п’ятниці_суботи'.split('_')
    };

    if (!m) {
        return weekdays['nominative'];
    }

    var nounCase = (/(\[[ВвУу]\]) ?dddd/).test(format) ?
        'accusative' :
        ((/\[?(?:минулої|наступної)? ?\] ?dddd/).test(format) ?
            'genitive' :
            'nominative');
    return weekdays[nounCase][m.day()];
}
function processHoursFunction(str) {
    return function () {
        return str + 'о' + (this.hours() === 11 ? 'б' : '') + '] LT';
    };
}

var uk = moment.defineLocale('uk', {
    months : {
        'format': 'січня_лютого_березня_квітня_травня_червня_липня_серпня_вересня_жовтня_листопада_грудня'.split('_'),
        'standalone': 'січень_лютий_березень_квітень_травень_червень_липень_серпень_вересень_жовтень_листопад_грудень'.split('_')
    },
    monthsShort : 'січ_лют_бер_квіт_трав_черв_лип_серп_вер_жовт_лист_груд'.split('_'),
    weekdays : weekdaysCaseReplace,
    weekdaysShort : 'нд_пн_вт_ср_чт_пт_сб'.split('_'),
    weekdaysMin : 'нд_пн_вт_ср_чт_пт_сб'.split('_'),
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD.MM.YYYY',
        LL : 'D MMMM YYYY р.',
        LLL : 'D MMMM YYYY р., HH:mm',
        LLLL : 'dddd, D MMMM YYYY р., HH:mm'
    },
    calendar : {
        sameDay: processHoursFunction('[Сьогодні '),
        nextDay: processHoursFunction('[Завтра '),
        lastDay: processHoursFunction('[Вчора '),
        nextWeek: processHoursFunction('[У] dddd ['),
        lastWeek: function () {
            switch (this.day()) {
                case 0:
                case 3:
                case 5:
                case 6:
                    return processHoursFunction('[Минулої] dddd [').call(this);
                case 1:
                case 2:
                case 4:
                    return processHoursFunction('[Минулого] dddd [').call(this);
            }
        },
        sameElse: 'L'
    },
    relativeTime : {
        future : 'за %s',
        past : '%s тому',
        s : 'декілька секунд',
        ss : relativeTimeWithPlural,
        m : relativeTimeWithPlural,
        mm : relativeTimeWithPlural,
        h : 'годину',
        hh : relativeTimeWithPlural,
        d : 'день',
        dd : relativeTimeWithPlural,
        M : 'місяць',
        MM : relativeTimeWithPlural,
        y : 'рік',
        yy : relativeTimeWithPlural
    },
    // M. E.: those two are virtually unused but a user might want to implement them for his/her website for some reason
    meridiemParse: /ночі|ранку|дня|вечора/,
    isPM: function (input) {
        return /^(дня|вечора)$/.test(input);
    },
    meridiem : function (hour, minute, isLower) {
        if (hour < 4) {
            return 'ночі';
        } else if (hour < 12) {
            return 'ранку';
        } else if (hour < 17) {
            return 'дня';
        } else {
            return 'вечора';
        }
    },
    dayOfMonthOrdinalParse: /\d{1,2}-(й|го)/,
    ordinal: function (number, period) {
        switch (period) {
            case 'M':
            case 'd':
            case 'DDD':
            case 'w':
            case 'W':
                return number + '-й';
            case 'D':
                return number + '-го';
            default:
                return number;
        }
    },
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 7  // The week that contains Jan 1st is the first week of the year.
    }
});

return uk;

})));


/***/ }),
/* 138 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Urdu [ur]
//! author : Sawood Alam : https://github.com/ibnesayeed
//! author : Zack : https://github.com/ZackVision

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var months = [
    'جنوری',
    'فروری',
    'مارچ',
    'اپریل',
    'مئی',
    'جون',
    'جولائی',
    'اگست',
    'ستمبر',
    'اکتوبر',
    'نومبر',
    'دسمبر'
];
var days = [
    'اتوار',
    'پیر',
    'منگل',
    'بدھ',
    'جمعرات',
    'جمعہ',
    'ہفتہ'
];

var ur = moment.defineLocale('ur', {
    months : months,
    monthsShort : months,
    weekdays : days,
    weekdaysShort : days,
    weekdaysMin : days,
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY HH:mm',
        LLLL : 'dddd، D MMMM YYYY HH:mm'
    },
    meridiemParse: /صبح|شام/,
    isPM : function (input) {
        return 'شام' === input;
    },
    meridiem : function (hour, minute, isLower) {
        if (hour < 12) {
            return 'صبح';
        }
        return 'شام';
    },
    calendar : {
        sameDay : '[آج بوقت] LT',
        nextDay : '[کل بوقت] LT',
        nextWeek : 'dddd [بوقت] LT',
        lastDay : '[گذشتہ روز بوقت] LT',
        lastWeek : '[گذشتہ] dddd [بوقت] LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : '%s بعد',
        past : '%s قبل',
        s : 'چند سیکنڈ',
        ss : '%d سیکنڈ',
        m : 'ایک منٹ',
        mm : '%d منٹ',
        h : 'ایک گھنٹہ',
        hh : '%d گھنٹے',
        d : 'ایک دن',
        dd : '%d دن',
        M : 'ایک ماہ',
        MM : '%d ماہ',
        y : 'ایک سال',
        yy : '%d سال'
    },
    preparse: function (string) {
        return string.replace(/،/g, ',');
    },
    postformat: function (string) {
        return string.replace(/,/g, '،');
    },
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return ur;

})));


/***/ }),
/* 139 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Uzbek Latin [uz-latn]
//! author : Rasulbek Mirzayev : github.com/Rasulbeeek

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var uzLatn = moment.defineLocale('uz-latn', {
    months : 'Yanvar_Fevral_Mart_Aprel_May_Iyun_Iyul_Avgust_Sentabr_Oktabr_Noyabr_Dekabr'.split('_'),
    monthsShort : 'Yan_Fev_Mar_Apr_May_Iyun_Iyul_Avg_Sen_Okt_Noy_Dek'.split('_'),
    weekdays : 'Yakshanba_Dushanba_Seshanba_Chorshanba_Payshanba_Juma_Shanba'.split('_'),
    weekdaysShort : 'Yak_Dush_Sesh_Chor_Pay_Jum_Shan'.split('_'),
    weekdaysMin : 'Ya_Du_Se_Cho_Pa_Ju_Sha'.split('_'),
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY HH:mm',
        LLLL : 'D MMMM YYYY, dddd HH:mm'
    },
    calendar : {
        sameDay : '[Bugun soat] LT [da]',
        nextDay : '[Ertaga] LT [da]',
        nextWeek : 'dddd [kuni soat] LT [da]',
        lastDay : '[Kecha soat] LT [da]',
        lastWeek : '[O\'tgan] dddd [kuni soat] LT [da]',
        sameElse : 'L'
    },
    relativeTime : {
        future : 'Yaqin %s ichida',
        past : 'Bir necha %s oldin',
        s : 'soniya',
        ss : '%d soniya',
        m : 'bir daqiqa',
        mm : '%d daqiqa',
        h : 'bir soat',
        hh : '%d soat',
        d : 'bir kun',
        dd : '%d kun',
        M : 'bir oy',
        MM : '%d oy',
        y : 'bir yil',
        yy : '%d yil'
    },
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 7  // The week that contains Jan 1st is the first week of the year.
    }
});

return uzLatn;

})));


/***/ }),
/* 140 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Uzbek [uz]
//! author : Sardor Muminov : https://github.com/muminoff

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var uz = moment.defineLocale('uz', {
    months : 'январ_феврал_март_апрел_май_июн_июл_август_сентябр_октябр_ноябр_декабр'.split('_'),
    monthsShort : 'янв_фев_мар_апр_май_июн_июл_авг_сен_окт_ноя_дек'.split('_'),
    weekdays : 'Якшанба_Душанба_Сешанба_Чоршанба_Пайшанба_Жума_Шанба'.split('_'),
    weekdaysShort : 'Якш_Душ_Сеш_Чор_Пай_Жум_Шан'.split('_'),
    weekdaysMin : 'Як_Ду_Се_Чо_Па_Жу_Ша'.split('_'),
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY HH:mm',
        LLLL : 'D MMMM YYYY, dddd HH:mm'
    },
    calendar : {
        sameDay : '[Бугун соат] LT [да]',
        nextDay : '[Эртага] LT [да]',
        nextWeek : 'dddd [куни соат] LT [да]',
        lastDay : '[Кеча соат] LT [да]',
        lastWeek : '[Утган] dddd [куни соат] LT [да]',
        sameElse : 'L'
    },
    relativeTime : {
        future : 'Якин %s ичида',
        past : 'Бир неча %s олдин',
        s : 'фурсат',
        ss : '%d фурсат',
        m : 'бир дакика',
        mm : '%d дакика',
        h : 'бир соат',
        hh : '%d соат',
        d : 'бир кун',
        dd : '%d кун',
        M : 'бир ой',
        MM : '%d ой',
        y : 'бир йил',
        yy : '%d йил'
    },
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 7  // The week that contains Jan 4th is the first week of the year.
    }
});

return uz;

})));


/***/ }),
/* 141 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Vietnamese [vi]
//! author : Bang Nguyen : https://github.com/bangnk

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var vi = moment.defineLocale('vi', {
    months : 'tháng 1_tháng 2_tháng 3_tháng 4_tháng 5_tháng 6_tháng 7_tháng 8_tháng 9_tháng 10_tháng 11_tháng 12'.split('_'),
    monthsShort : 'Th01_Th02_Th03_Th04_Th05_Th06_Th07_Th08_Th09_Th10_Th11_Th12'.split('_'),
    monthsParseExact : true,
    weekdays : 'chủ nhật_thứ hai_thứ ba_thứ tư_thứ năm_thứ sáu_thứ bảy'.split('_'),
    weekdaysShort : 'CN_T2_T3_T4_T5_T6_T7'.split('_'),
    weekdaysMin : 'CN_T2_T3_T4_T5_T6_T7'.split('_'),
    weekdaysParseExact : true,
    meridiemParse: /sa|ch/i,
    isPM : function (input) {
        return /^ch$/i.test(input);
    },
    meridiem : function (hours, minutes, isLower) {
        if (hours < 12) {
            return isLower ? 'sa' : 'SA';
        } else {
            return isLower ? 'ch' : 'CH';
        }
    },
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM [năm] YYYY',
        LLL : 'D MMMM [năm] YYYY HH:mm',
        LLLL : 'dddd, D MMMM [năm] YYYY HH:mm',
        l : 'DD/M/YYYY',
        ll : 'D MMM YYYY',
        lll : 'D MMM YYYY HH:mm',
        llll : 'ddd, D MMM YYYY HH:mm'
    },
    calendar : {
        sameDay: '[Hôm nay lúc] LT',
        nextDay: '[Ngày mai lúc] LT',
        nextWeek: 'dddd [tuần tới lúc] LT',
        lastDay: '[Hôm qua lúc] LT',
        lastWeek: 'dddd [tuần rồi lúc] LT',
        sameElse: 'L'
    },
    relativeTime : {
        future : '%s tới',
        past : '%s trước',
        s : 'vài giây',
        ss : '%d giây' ,
        m : 'một phút',
        mm : '%d phút',
        h : 'một giờ',
        hh : '%d giờ',
        d : 'một ngày',
        dd : '%d ngày',
        M : 'một tháng',
        MM : '%d tháng',
        y : 'một năm',
        yy : '%d năm'
    },
    dayOfMonthOrdinalParse: /\d{1,2}/,
    ordinal : function (number) {
        return number;
    },
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return vi;

})));


/***/ }),
/* 142 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Pseudo [x-pseudo]
//! author : Andrew Hood : https://github.com/andrewhood125

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var xPseudo = moment.defineLocale('x-pseudo', {
    months : 'J~áñúá~rý_F~ébrú~árý_~Márc~h_Áp~ríl_~Máý_~Júñé~_Júl~ý_Áú~gúst~_Sép~témb~ér_Ó~ctób~ér_Ñ~óvém~bér_~Décé~mbér'.split('_'),
    monthsShort : 'J~áñ_~Féb_~Már_~Ápr_~Máý_~Júñ_~Júl_~Áúg_~Sép_~Óct_~Ñóv_~Déc'.split('_'),
    monthsParseExact : true,
    weekdays : 'S~úñdá~ý_Mó~ñdáý~_Túé~sdáý~_Wéd~ñésd~áý_T~húrs~dáý_~Fríd~áý_S~átúr~dáý'.split('_'),
    weekdaysShort : 'S~úñ_~Móñ_~Túé_~Wéd_~Thú_~Frí_~Sát'.split('_'),
    weekdaysMin : 'S~ú_Mó~_Tú_~Wé_T~h_Fr~_Sá'.split('_'),
    weekdaysParseExact : true,
    longDateFormat : {
        LT : 'HH:mm',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY HH:mm',
        LLLL : 'dddd, D MMMM YYYY HH:mm'
    },
    calendar : {
        sameDay : '[T~ódá~ý át] LT',
        nextDay : '[T~ómó~rró~w át] LT',
        nextWeek : 'dddd [át] LT',
        lastDay : '[Ý~ést~érdá~ý át] LT',
        lastWeek : '[L~ást] dddd [át] LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : 'í~ñ %s',
        past : '%s á~gó',
        s : 'á ~féw ~sécó~ñds',
        ss : '%d s~écóñ~ds',
        m : 'á ~míñ~úté',
        mm : '%d m~íñú~tés',
        h : 'á~ñ hó~úr',
        hh : '%d h~óúrs',
        d : 'á ~dáý',
        dd : '%d d~áýs',
        M : 'á ~móñ~th',
        MM : '%d m~óñt~hs',
        y : 'á ~ýéár',
        yy : '%d ý~éárs'
    },
    dayOfMonthOrdinalParse: /\d{1,2}(th|st|nd|rd)/,
    ordinal : function (number) {
        var b = number % 10,
            output = (~~(number % 100 / 10) === 1) ? 'th' :
            (b === 1) ? 'st' :
            (b === 2) ? 'nd' :
            (b === 3) ? 'rd' : 'th';
        return number + output;
    },
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return xPseudo;

})));


/***/ }),
/* 143 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Yoruba Nigeria [yo]
//! author : Atolagbe Abisoye : https://github.com/andela-batolagbe

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var yo = moment.defineLocale('yo', {
    months : 'Sẹ́rẹ́_Èrèlè_Ẹrẹ̀nà_Ìgbé_Èbibi_Òkùdu_Agẹmo_Ògún_Owewe_Ọ̀wàrà_Bélú_Ọ̀pẹ̀̀'.split('_'),
    monthsShort : 'Sẹ́r_Èrl_Ẹrn_Ìgb_Èbi_Òkù_Agẹ_Ògú_Owe_Ọ̀wà_Bél_Ọ̀pẹ̀̀'.split('_'),
    weekdays : 'Àìkú_Ajé_Ìsẹ́gun_Ọjọ́rú_Ọjọ́bọ_Ẹtì_Àbámẹ́ta'.split('_'),
    weekdaysShort : 'Àìk_Ajé_Ìsẹ́_Ọjr_Ọjb_Ẹtì_Àbá'.split('_'),
    weekdaysMin : 'Àì_Aj_Ìs_Ọr_Ọb_Ẹt_Àb'.split('_'),
    longDateFormat : {
        LT : 'h:mm A',
        LTS : 'h:mm:ss A',
        L : 'DD/MM/YYYY',
        LL : 'D MMMM YYYY',
        LLL : 'D MMMM YYYY h:mm A',
        LLLL : 'dddd, D MMMM YYYY h:mm A'
    },
    calendar : {
        sameDay : '[Ònì ni] LT',
        nextDay : '[Ọ̀la ni] LT',
        nextWeek : 'dddd [Ọsẹ̀ tón\'bọ] [ni] LT',
        lastDay : '[Àna ni] LT',
        lastWeek : 'dddd [Ọsẹ̀ tólọ́] [ni] LT',
        sameElse : 'L'
    },
    relativeTime : {
        future : 'ní %s',
        past : '%s kọjá',
        s : 'ìsẹjú aayá die',
        ss :'aayá %d',
        m : 'ìsẹjú kan',
        mm : 'ìsẹjú %d',
        h : 'wákati kan',
        hh : 'wákati %d',
        d : 'ọjọ́ kan',
        dd : 'ọjọ́ %d',
        M : 'osù kan',
        MM : 'osù %d',
        y : 'ọdún kan',
        yy : 'ọdún %d'
    },
    dayOfMonthOrdinalParse : /ọjọ́\s\d{1,2}/,
    ordinal : 'ọjọ́ %d',
    week : {
        dow : 1, // Monday is the first day of the week.
        doy : 4 // The week that contains Jan 4th is the first week of the year.
    }
});

return yo;

})));


/***/ }),
/* 144 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Chinese (China) [zh-cn]
//! author : suupic : https://github.com/suupic
//! author : Zeno Zeng : https://github.com/zenozeng

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var zhCn = moment.defineLocale('zh-cn', {
    months : '一月_二月_三月_四月_五月_六月_七月_八月_九月_十月_十一月_十二月'.split('_'),
    monthsShort : '1月_2月_3月_4月_5月_6月_7月_8月_9月_10月_11月_12月'.split('_'),
    weekdays : '星期日_星期一_星期二_星期三_星期四_星期五_星期六'.split('_'),
    weekdaysShort : '周日_周一_周二_周三_周四_周五_周六'.split('_'),
    weekdaysMin : '日_一_二_三_四_五_六'.split('_'),
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'YYYY/MM/DD',
        LL : 'YYYY年M月D日',
        LLL : 'YYYY年M月D日Ah点mm分',
        LLLL : 'YYYY年M月D日ddddAh点mm分',
        l : 'YYYY/M/D',
        ll : 'YYYY年M月D日',
        lll : 'YYYY年M月D日 HH:mm',
        llll : 'YYYY年M月D日dddd HH:mm'
    },
    meridiemParse: /凌晨|早上|上午|中午|下午|晚上/,
    meridiemHour: function (hour, meridiem) {
        if (hour === 12) {
            hour = 0;
        }
        if (meridiem === '凌晨' || meridiem === '早上' ||
                meridiem === '上午') {
            return hour;
        } else if (meridiem === '下午' || meridiem === '晚上') {
            return hour + 12;
        } else {
            // '中午'
            return hour >= 11 ? hour : hour + 12;
        }
    },
    meridiem : function (hour, minute, isLower) {
        var hm = hour * 100 + minute;
        if (hm < 600) {
            return '凌晨';
        } else if (hm < 900) {
            return '早上';
        } else if (hm < 1130) {
            return '上午';
        } else if (hm < 1230) {
            return '中午';
        } else if (hm < 1800) {
            return '下午';
        } else {
            return '晚上';
        }
    },
    calendar : {
        sameDay : '[今天]LT',
        nextDay : '[明天]LT',
        nextWeek : '[下]ddddLT',
        lastDay : '[昨天]LT',
        lastWeek : '[上]ddddLT',
        sameElse : 'L'
    },
    dayOfMonthOrdinalParse: /\d{1,2}(日|月|周)/,
    ordinal : function (number, period) {
        switch (period) {
            case 'd':
            case 'D':
            case 'DDD':
                return number + '日';
            case 'M':
                return number + '月';
            case 'w':
            case 'W':
                return number + '周';
            default:
                return number;
        }
    },
    relativeTime : {
        future : '%s内',
        past : '%s前',
        s : '几秒',
        ss : '%d 秒',
        m : '1 分钟',
        mm : '%d 分钟',
        h : '1 小时',
        hh : '%d 小时',
        d : '1 天',
        dd : '%d 天',
        M : '1 个月',
        MM : '%d 个月',
        y : '1 年',
        yy : '%d 年'
    },
    week : {
        // GB/T 7408-1994《数据元和交换格式·信息交换·日期和时间表示法》与ISO 8601:1988等效
        dow : 1, // Monday is the first day of the week.
        doy : 4  // The week that contains Jan 4th is the first week of the year.
    }
});

return zhCn;

})));


/***/ }),
/* 145 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Chinese (Hong Kong) [zh-hk]
//! author : Ben : https://github.com/ben-lin
//! author : Chris Lam : https://github.com/hehachris
//! author : Konstantin : https://github.com/skfd

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var zhHk = moment.defineLocale('zh-hk', {
    months : '一月_二月_三月_四月_五月_六月_七月_八月_九月_十月_十一月_十二月'.split('_'),
    monthsShort : '1月_2月_3月_4月_5月_6月_7月_8月_9月_10月_11月_12月'.split('_'),
    weekdays : '星期日_星期一_星期二_星期三_星期四_星期五_星期六'.split('_'),
    weekdaysShort : '週日_週一_週二_週三_週四_週五_週六'.split('_'),
    weekdaysMin : '日_一_二_三_四_五_六'.split('_'),
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'YYYY/MM/DD',
        LL : 'YYYY年M月D日',
        LLL : 'YYYY年M月D日 HH:mm',
        LLLL : 'YYYY年M月D日dddd HH:mm',
        l : 'YYYY/M/D',
        ll : 'YYYY年M月D日',
        lll : 'YYYY年M月D日 HH:mm',
        llll : 'YYYY年M月D日dddd HH:mm'
    },
    meridiemParse: /凌晨|早上|上午|中午|下午|晚上/,
    meridiemHour : function (hour, meridiem) {
        if (hour === 12) {
            hour = 0;
        }
        if (meridiem === '凌晨' || meridiem === '早上' || meridiem === '上午') {
            return hour;
        } else if (meridiem === '中午') {
            return hour >= 11 ? hour : hour + 12;
        } else if (meridiem === '下午' || meridiem === '晚上') {
            return hour + 12;
        }
    },
    meridiem : function (hour, minute, isLower) {
        var hm = hour * 100 + minute;
        if (hm < 600) {
            return '凌晨';
        } else if (hm < 900) {
            return '早上';
        } else if (hm < 1130) {
            return '上午';
        } else if (hm < 1230) {
            return '中午';
        } else if (hm < 1800) {
            return '下午';
        } else {
            return '晚上';
        }
    },
    calendar : {
        sameDay : '[今天]LT',
        nextDay : '[明天]LT',
        nextWeek : '[下]ddddLT',
        lastDay : '[昨天]LT',
        lastWeek : '[上]ddddLT',
        sameElse : 'L'
    },
    dayOfMonthOrdinalParse: /\d{1,2}(日|月|週)/,
    ordinal : function (number, period) {
        switch (period) {
            case 'd' :
            case 'D' :
            case 'DDD' :
                return number + '日';
            case 'M' :
                return number + '月';
            case 'w' :
            case 'W' :
                return number + '週';
            default :
                return number;
        }
    },
    relativeTime : {
        future : '%s內',
        past : '%s前',
        s : '幾秒',
        ss : '%d 秒',
        m : '1 分鐘',
        mm : '%d 分鐘',
        h : '1 小時',
        hh : '%d 小時',
        d : '1 天',
        dd : '%d 天',
        M : '1 個月',
        MM : '%d 個月',
        y : '1 年',
        yy : '%d 年'
    }
});

return zhHk;

})));


/***/ }),
/* 146 */
/***/ (function(module, exports, __webpack_require__) {

//! moment.js locale configuration
//! locale : Chinese (Taiwan) [zh-tw]
//! author : Ben : https://github.com/ben-lin
//! author : Chris Lam : https://github.com/hehachris

;(function (global, factory) {
    true ? factory(__webpack_require__(1)) :
   typeof define === 'function' && define.amd ? define(['../moment'], factory) :
   factory(global.moment)
}(this, (function (moment) { 'use strict';


var zhTw = moment.defineLocale('zh-tw', {
    months : '一月_二月_三月_四月_五月_六月_七月_八月_九月_十月_十一月_十二月'.split('_'),
    monthsShort : '1月_2月_3月_4月_5月_6月_7月_8月_9月_10月_11月_12月'.split('_'),
    weekdays : '星期日_星期一_星期二_星期三_星期四_星期五_星期六'.split('_'),
    weekdaysShort : '週日_週一_週二_週三_週四_週五_週六'.split('_'),
    weekdaysMin : '日_一_二_三_四_五_六'.split('_'),
    longDateFormat : {
        LT : 'HH:mm',
        LTS : 'HH:mm:ss',
        L : 'YYYY/MM/DD',
        LL : 'YYYY年M月D日',
        LLL : 'YYYY年M月D日 HH:mm',
        LLLL : 'YYYY年M月D日dddd HH:mm',
        l : 'YYYY/M/D',
        ll : 'YYYY年M月D日',
        lll : 'YYYY年M月D日 HH:mm',
        llll : 'YYYY年M月D日dddd HH:mm'
    },
    meridiemParse: /凌晨|早上|上午|中午|下午|晚上/,
    meridiemHour : function (hour, meridiem) {
        if (hour === 12) {
            hour = 0;
        }
        if (meridiem === '凌晨' || meridiem === '早上' || meridiem === '上午') {
            return hour;
        } else if (meridiem === '中午') {
            return hour >= 11 ? hour : hour + 12;
        } else if (meridiem === '下午' || meridiem === '晚上') {
            return hour + 12;
        }
    },
    meridiem : function (hour, minute, isLower) {
        var hm = hour * 100 + minute;
        if (hm < 600) {
            return '凌晨';
        } else if (hm < 900) {
            return '早上';
        } else if (hm < 1130) {
            return '上午';
        } else if (hm < 1230) {
            return '中午';
        } else if (hm < 1800) {
            return '下午';
        } else {
            return '晚上';
        }
    },
    calendar : {
        sameDay : '[今天]LT',
        nextDay : '[明天]LT',
        nextWeek : '[下]ddddLT',
        lastDay : '[昨天]LT',
        lastWeek : '[上]ddddLT',
        sameElse : 'L'
    },
    dayOfMonthOrdinalParse: /\d{1,2}(日|月|週)/,
    ordinal : function (number, period) {
        switch (period) {
            case 'd' :
            case 'D' :
            case 'DDD' :
                return number + '日';
            case 'M' :
                return number + '月';
            case 'w' :
            case 'W' :
                return number + '週';
            default :
                return number;
        }
    },
    relativeTime : {
        future : '%s內',
        past : '%s前',
        s : '幾秒',
        ss : '%d 秒',
        m : '1 分鐘',
        mm : '%d 分鐘',
        h : '1 小時',
        hh : '%d 小時',
        d : '1 天',
        dd : '%d 天',
        M : '1 個月',
        MM : '%d 個月',
        y : '1 年',
        yy : '%d 年'
    }
});

return zhTw;

})));


/***/ }),
/* 147 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function(jQuery) {var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/**
  * Genera un datatable
  *
  * @summary 		Componente RUP Datatable
  * @module			"rup.datatable"
  * @version     1.0.0
  * @license
  * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
  * Solo podrá usarse esta obra si se respeta la Licencia.
  * Puede obtenerse una copia de la Licencia en
  *
  *      http://ec.europa.eu/idabc/eupl.html
  *
  * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
  * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
  * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
  * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
  * que establece la Licencia.
  * @copyright   Copyright 2018 E.J.I.E., S.A.
  *
  */

/*global define */
/*global jQuery */

(function (factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(207), __webpack_require__(25), __webpack_require__(263), __webpack_require__(206), __webpack_require__(201), __webpack_require__(203), __webpack_require__(209), __webpack_require__(202), __webpack_require__(210), __webpack_require__(208), __webpack_require__(204), __webpack_require__(205)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		factory(jQuery);
	}
})(function ($, TableRequest) {

	//****************************************************************************************************************
	// DEFINICIÓN BASE DEL PATRÓN (definición de la variable privada que contendrá los métodos y la función de jQuery)
	//****************************************************************************************************************

	var DataTable = $.fn.dataTable;
	var rup_datatable = {};

	//Se configura el arranque de UDA para que alberge el nuevo patrón
	$.extend($.rup.iniRup, $.rup.rupSelectorObjectConstructor('rup_datatable', rup_datatable));

	//*******************************
	// DEFINICIÓN DE MÉTODOS RUP
	//*******************************
	$.fn.rup_datatable('extend', {
		getRupValue: function getRupValue() {
			return null;
		},
		setRupValue: function setRupValue(value) {}
	});

	//*******************************
	// DEFINICIÓN DE MÉTODOS PÚBLICOS
	//*******************************
	$.fn.rup_datatable('extend', {
		foo: function foo() {
			return this;
		}
	});

	//*******************************
	// DEFINICIÓN DE MÉTODOS PRIVADOS
	//*******************************

	$.fn.rup_datatable('extend', {

		/**
  	* Inicializa ciertas opciones del componente
  	*
  	* @name _initOptions
  	* @function
  	* @since UDA 3.4.0 // Datatable 1.0.0
  	*
  	* @param {object} options Opciones del componente
  	*
    */
		_initOptions: function _initOptions(options) {
			var $self = this;

			options.processing = true;
			options.serverSide = true;
			options.columns = options.columns || $self._getColumns(options);

			//filter

			// options.filterForm = $self.attr('data-filter-form');
			options.$filterForm = $(options.filterForm);

			options.$filterButton = options.$filterForm.find('.rup-filtrar');
			options.$clearButton = options.$filterForm.find('.rup-limpiar');
			options.$filterButton.on('click', function () {
				$self._doFilter(options);
			});
			options.$clearButton.on('click', function () {
				$self._clearFilter(options);
			});

			// Urls
			var baseUrl = options.urlBase;
			options.urls = {
				base: baseUrl,
				filter: baseUrl + '/filter'
			};

			options.ajax = this._ajaxOptions(options);

			options.language = {
				'url': $.rup.RUP + '/resources/rup.i18n_' + $.rup.lang + '.json'
			};

			//Extend 
			/*{targets:   4,data: "download_link",render: function (  ) {
           return '<a href="">Download</a>';
       }}*/
			var defes = {};
			var columnDefs = $.extend({}, options.columnDefs, defes);
			//options.columnDefs = columnDefs;

			//Se cargan los metodos en la API, Se referencia al Register
			var apiRegister = DataTable.Api.register;

			DataTable.Api.register('rupTable.selectPencil()', function (ctx, idRow) {
				//Se limina el lapicero indicador.
				$('#' + ctx.sTableId + ' tbody tr td.select-checkbox span.ui-icon-pencil').remove();
				//se añade el span con el lapicero
				if (idRow >= 0) {
					var spanPencil = $("<span/>").addClass('ui-icon ui-icon-rupInfoCol ui-icon-pencil selected-pencil');
					$($('#' + ctx.sTableId + ' tbody tr td.select-checkbox')[idRow]).append(spanPencil);
				}
			});

			apiRegister('rupTable.reorderDataFromServer()', function (json, ctx) {
				//Se mira la nueva reordenacion y se ordena.

				ctx.multiselection.selectedIds = [];
				ctx.multiselection.selectedRowsPerPage = [];
				//Viene del servidor por eso la linea de la pagina es 1 menos.
				$.each(json.reorderedSelection, function (index, p) {
					var arra = { id: DataTable.Api().rupTable.getIdPk(p.pk), page: p.page, line: p.pageLine - 1 };
					ctx.multiselection.selectedIds.splice(index, 0, arra.id);
					ctx.multiselection.selectedRowsPerPage.splice(index, 0, arra);
				});
				if (!ctx.multiselection.selectedAll) {
					ctx.multiselection.numSelected = ctx.multiselection.selectedIds.length;
				}
				// Detecta cuando se pulsa sobre el boton de filtrado o de limpiar lo filtrado
				if (options.buttons !== undefined) {
					DataTable.Api().buttons.displayRegex(ctx);
				}
			});

			apiRegister('rupTable.getIdPk()', function (json) {

				var id = '';

				$.each(options.primaryKey, function (index, key) {
					id = id + json[key];
					if (options.primaryKey.length > 1 && index < options.primaryKey.length - 1) {
						id = id + options.multiplePkToken;
					}
				});

				return id;
			});

			return options;
		},

		/**
  	* Obtiene las columnas
  	*
  	* @name _getColumns
  	* @function
  	* @since UDA 3.4.0 // Datatable 1.0.0
  	*
  	* @param {object} options Opciones del componente
  	*
    */
		_getColumns: function _getColumns(options) {
			$self = this;
			//Se crea la columna del select.
			if (options.columnDefs !== undefined && options.columnDefs.length > 0 && options.columnDefs[0].className !== undefined && options.columnDefs[0].className === 'select-checkbox' && options.multiSelect !== undefined) {
				//Se crear el th thead, se añade la columnal.

				var th = $("<th/>").attr('data-col-prop', '');

				if ($self[0].tHead !== null) {
					$(th).insertBefore($self[0].tHead.rows[0].cells[0]);
				}
				//se crea el th tfoot
				if ($self[0].tFoot !== null) {
					$('<th/>').insertBefore($self[0].tFoot.rows[0].cells[0]);
				}
				//Se aseguro que no sea orderable
				if (options.columnDefs.length > 0) {
					options.columnDefs[0].orderable = false;
				}
			}
			var columns = this.find('th[data-col-prop]').map(function (i, e) {
				if (e.getAttribute('data-col-type') === 'Checkbox') {
					options.columnDefs.push({ targets: i, data: "", render: function render(data, visibility, object, colRows) {
							var iconCheck = 'fa fa-times';
							if (data === '1') {
								iconCheck = 'fa fa-check';
							}
							return '<div class="datatable_checkbox"><i class="' + iconCheck + '"></i></div>';
						} });
				}
				return {
					data: e.getAttribute('data-col-prop'), sidx: e.getAttribute('data-col-sidx')
				};
			});

			columns[0].sDefaultContent = '';

			return columns;
		},


		/**
  	* Filtrado
  	*
  	* @name _doFilter
  	* @function
  	* @since UDA 3.4.0 // Datatable 1.0.0
  	*
  	* @param {object} options Opciones del componente
  	*
    */
		_doFilter: function _doFilter(options) {
			var $self = this;
			$self._showSearchCriteria();
			$('#' + options.id).triggerHandler('tableFilterSearch');
			$self.DataTable().ajax.reload();
		},


		/**
  	* Prepara el objeto necesario para la consulta de registros al servidor
  	*
  	* @name _ajaxOptions
  	* @function
  	* @since UDA 3.4.0 // Datatable 1.0.0
  	*
  	* @param {object} options Opciones del componente
  	*
    */
		_ajaxOptions: function _ajaxOptions(options) {

			options.id = this[0].id;
			$('#' + options.id).triggerHandler('tableFilterInitialize');
			var ajaxData = {
				'url': options.urls.filter,
				'dataSrc': function dataSrc(json) {
					var ret = {};
					$('#' + options.id).triggerHandler('tableFilterBeforeShow');
					json.recordsTotal = json.records;
					json.recordsFiltered = json.records;

					ret.recordsTotal = json.records;
					ret.recordsFiltered = json.records;
					ret.data = json.rows;

					var table = $('#' + options.id).DataTable();
					var ctx = table.context[0];

					var settings = ctx.oInit; //$(ctx.nTable).data('settings'+ctx.sTableId);
					if (settings !== undefined && (settings.multiSelect !== undefined || settings.select !== undefined)) {
						DataTable.Api().rupTable.reorderDataFromServer(json, ctx);
					}
					if (ctx.seeker !== undefined && ctx.seeker.search !== undefined && json.reorderedSeeker !== undefined) {
						ctx.seeker.search.funcionParams = json.reorderedSeeker;
					}

					return ret.data;
				},
				'type': 'POST',
				'data': this._ajaxRequestData,
				'contentType': 'application/json',
				'dataType': 'json'

			};

			return ajaxData;
		},

		/**
  	* Solicita los datos al servidor
  	*
  	* @name _ajaxRequestData
  	* @function
  	* @since UDA 3.4.0 // Datatable 1.0.0
  	*
  	* @param {object} data Opciones del datatable
  	* @param {object} ctx contexto  del componente table
  	*
    */
		_ajaxRequestData: function _ajaxRequestData(data, ctx) {

			//PAra añadir un id de busqueda distinto al value, como por ejemplo la fecha.
			data.columns[data.order[0].column].colSidx = ctx.aoColumns[data.order[0].column].colSidx;
			//el data viene del padre:Jqueru.datatable y como no tiene el prefijo de busqueda se añade.
			data.filter = form2object(ctx.oInit.$filterForm[0]);
			data.multiselection = undefined;
			if (ctx.multiselection !== undefined && ctx.multiselection.selectedIds.length > 0) {
				data.multiselection = ctx.multiselection;
			}
			if (ctx.seeker !== undefined && ctx.seeker.search !== undefined && ctx.seeker.search.funcionParams !== undefined && ctx.seeker.search.funcionParams.length > 0) {
				data.seeker = {};
				data.seeker.selectedIds = [];
				$.each(ctx.seeker.search.funcionParams, function (index, p) {
					data.seeker.selectedIds.splice(index, 0, DataTable.Api().rupTable.getIdPk(p.pk));
				});
			}
			var tableRequest = new TableRequest(data);
			var json = $.extend({}, data, tableRequest.getData());

			json.core.pkNames = ctx.oInit.primaryKey;

			ctx.aBaseJson = json;
			return JSON.stringify(json);
		},


		/**
  	* Gestiona la paginación
  	*
  	* @name _createSearchPaginator
  	* @function
  	* @since UDA 3.4.0 // Datatable 1.0.0
  	*
  	* @param {object} tabla Objeto que contiene la tabla
  	* @param {object} settingsT Opciones del componente
  	*
    */
		_createSearchPaginator: function _createSearchPaginator(tabla, settingsT) {
			//buscar la paginación.
			if ($('#' + tabla[0].id + '_paginate').length === 1 && settingsT.json !== undefined && settingsT.json.total !== '0') {
				var liSearch = $('<li/>').addClass('paginate_button page-item pageSearch searchPaginator');
				var textPagina = jQuery.rup.i18nTemplate(settingsT.oLanguage, 'pagina', settingsT.json.total);
				var toPagina = jQuery.rup.i18nTemplate(settingsT.oLanguage, 'toPagina', settingsT.json.total);
				var input = $('<input/>').attr({ type: "text", size: "3", value: settingsT.json.page, maxlength: "3" }).addClass('ui-pg-input');
				liSearch.append(textPagina);
				liSearch.append(input);
				liSearch.append(toPagina);
				$('#' + tabla[0].id + '_previous').after(liSearch);
				input.keypress(function (e) {
					if (e.which === 13) // the enter key code
						{
							var page = parseInt(this.value);
							if ($.isNumeric(page) && page > 0) {
								tabla.dataTable().fnPageChange(page - 1);
							}
							return false;
						}
				});
			} else {}
			//Sacar un error


			// Crea un div que albergara la lista de botones de paginacion
			$('#' + tabla[0].id + '_paginate').prepend("<div id='" + tabla[0].id + "_buttons' class='recolocatedPagination_buttons' />");

			// Añade iconos para versiones moviles/tablets
			$('#' + tabla[0].id + '_first').addClass('recolocatedPagination_iconButton').append("<i class='fa fa-angle-double-left'/>");
			$('#' + tabla[0].id + '_previous').addClass('recolocatedPagination_iconButton').append("<i class='fa fa-angle-left'/>");
			$('#' + tabla[0].id + '_next').addClass('recolocatedPagination_iconButton').append("<i class='fa fa-angle-right'/>");
			$('#' + tabla[0].id + '_last').addClass('recolocatedPagination_iconButton').append("<i class='fa fa-angle-double-right'/>");

			// Inserta la lista de botones de paginacion al div anteriormente creado
			$('#' + tabla[0].id + '_paginate ul').detach().appendTo($('#' + tabla[0].id + '_buttons'));

			// Añadimos clases para acabar con la recolocacion
			$('#' + tabla[0].id + '_paginate').addClass('recolocatedPagination_container');
			$('#' + tabla[0].id + '_buttons').addClass('recolocatedPagination_rellenoCtr');
			$('#' + tabla[0].id + '_info').addClass('recolocatedPagination_rellenoDrc');
			$('#' + tabla[0].id + '_length').addClass('recolocatedPagination_length');
		},


		/**
  	* Limpia el filtro
  	*
  	* @name _clearFilter
  	* @function
  	* @since UDA 3.4.0 // Datatable 1.0.0
  	*
  	* @param {object} options Opciones del componente
  	*
    */
		_clearFilter: function _clearFilter(options) {
			var $self = this;
			$('#' + options.id).triggerHandler('tableFilterReset');
			options.$filterForm.resetForm();
			$self.DataTable().ajax.reload();
			options.filter.$filterSummary.html(' <i></i>');

			// Provoca un mal funcionamiento del filtrado de Maestro-Detalle en la tabla esclava, 
			// ya que elimina la referencia del padre y muestra todos los valores en vez de los relacionados.
			//jQuery('input,textarea').val('');

			// No es necesario ya que se usa bootstrap
			//jQuery('.ui-selectmenu-status','.rup-table-filter-fieldset').text('--');

			$.rup_utils.populateForm([], options.$filterForm);
		},

		/**
  * Metodo que realiza la configuración del plugin filter del componente RUP DataTable.
  *
  * @name preConfigureFilter
  * @function
  *
  * @param {object} settings - Parámetros de configuración del componente.
  *
  */
		_ConfigureFiltern: function _ConfigureFiltern(settings) {
			var $self = this,
			    tableId = this[0].id,
			    filterSettings = settings.filter,
			    toggleIcon1Tmpl,
			    toggleLabelTmpl,
			    filterSummaryTmpl,
			    toggleIcon2Tmpl,
			    $toggleIcon1,
			    $toggleLabel,
			    $filterSummary,
			    $toggleIcon2;

			/*
    * Inicialización de los identificadores y componentes por defecto de los componentes de filtrado
    */
			filterSettings.id = filterSettings.id !== undefined ? filterSettings.id : tableId + '_filter_form';
			filterSettings.filterToolbarId = filterSettings.filterToolbar !== undefined ? filterSettings.filterToolbar : tableId + '_filter_toolbar';

			filterSettings.collapsableLayerId = filterSettings.collapsableLayerId !== undefined ? filterSettings.collapsableLayerId : tableId + '_filter_fieldset';

			filterSettings.toggleIcon1Id = filterSettings.toggleIcon1 !== undefined ? filterSettings.toggleIcon1 : tableId + '_filter_toggle_icon1';
			filterSettings.toggleLabelId = filterSettings.toggleLabelId !== undefined ? filterSettings.toggleLabelId : tableId + '_filter_toggle_label';
			filterSettings.filterSummaryId = filterSettings.filterSummaryId !== undefined ? filterSettings.filterSummaryId : tableId + '_filter_summary';
			filterSettings.toggleIcon2Id = filterSettings.toggleIcon2 !== undefined ? filterSettings.toggleIcon2 : tableId + '_filter_toggle_icon2';

			filterSettings.$filterContainer = jQuery('#' + filterSettings.id);
			filterSettings.$filterToolbar = jQuery('#' + filterSettings.filterToolbarId);

			settings.filter.showHidden = false;

			if (filterSettings.$filterContainer.length === 0) {
				alert('El identificador especificado para el fomulario de búsqueda no existe.');
			} else if (filterSettings.$filterToolbar.length === 0) {
				alert('El identificador especificado para la barra de controles del formulario de filtrado no existe.');
			} else {
				/*
     * Se almacena la referencia de los diferentes componentes
     *
     * $filterContainer : Contenedor del formulario de filtrado
     * $filterButton : Botón que realiza el filtrado
     * $cleanLink : Enlace para limpiar el formulario
     * $collapsableLayer : Capa que puede ser ocultada/mostrada
     * $toggleIcon1Id : Control que oculta muestra el fomulario
     * $filterSummary : Contenedor donde se especifican los criterios de filtrado
     */
				toggleIcon1Tmpl = jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_table.templates.filter.toggleIcon1');
				toggleLabelTmpl = jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_table.templates.filter.toggleLabel');
				filterSummaryTmpl = jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_table.templates.filter.filterSummary');
				toggleIcon2Tmpl = jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_table.templates.filter.toggleIcon2');

				$toggleIcon1 = $(jQuery.jgrid.format(toggleIcon1Tmpl, filterSettings.toggleIcon1Id));
				$toggleLabel = $(jQuery.jgrid.format(toggleLabelTmpl, filterSettings.toggleLabelId, $.rup.i18n.base.rup_table.plugins.filter.filterCriteria));
				$filterSummary = $(jQuery.jgrid.format(filterSummaryTmpl, filterSettings.filterSummaryId));
				$toggleIcon2 = $(jQuery.jgrid.format(toggleIcon2Tmpl, filterSettings.toggleIcon2Id));

				filterSettings.$filterToolbar.append($toggleIcon1).append($toggleLabel).append($filterSummary).append($toggleIcon2);

				filterSettings.$filterContainer = jQuery('#' + filterSettings.id);

				filterSettings.$collapsableLayer = jQuery('#' + filterSettings.collapsableLayerId);

				filterSettings.$toggleIcon1 = $toggleIcon1;
				filterSettings.$toggleLabel = $toggleLabel;
				filterSettings.$filterSummary = $filterSummary;
				filterSettings.$toggleIcon2 = $toggleIcon2;

				// Se asigna a la tecla ENTER la funcion de busqueda.
				filterSettings.$filterContainer.bind('keydown', function (evt) {
					if (evt.keyCode === 13) {
						$self._doFilter(settings);
					}
				});

				filterSettings.$filterToolbar.addClass('cursor_pointer').on({
					'click': function click() {
						if (settings.filter.showHidden === false) {
							filterSettings.$collapsableLayer.hide();
							filterSettings.$toggleIcon1.removeClass('ui-icon-triangle-1-s').addClass('ui-icon-triangle-1-e');
							filterSettings.$toggleIcon2.removeClass('ui-icon-circle-triangle-s').addClass('ui-icon-circle-triangle-n');
							settings.filter.showHidden = true;
						} else {
							filterSettings.$collapsableLayer.show();
							filterSettings.$toggleIcon1.removeClass('ui-icon-triangle-1-e').addClass('ui-icon-triangle-1-s');
							filterSettings.$toggleIcon2.removeClass('ui-icon-circle-triangle-n').addClass('ui-icon-circle-triangle-s');
							settings.filter.showHidden = false;
						}
					}
				});

				if (settings.filter.showHidden === true) {
					filterSettings.$collapsableLayer.hide();
					filterSettings.$toggleIcon1.removeClass('ui-icon-triangle-1-s').addClass('ui-icon-triangle-1-e');
					filterSettings.$toggleIcon2.removeClass('ui-icon-circle-triangle-s').addClass('ui-icon-circle-triangle-n');
					settings.filter.showHidden = true;
				} else {
					filterSettings.$collapsableLayer.show();
					filterSettings.$toggleIcon1.removeClass('ui-icon-triangle-1-e').addClass('ui-icon-triangle-1-s');
					filterSettings.$toggleIcon2.removeClass('ui-icon-circle-triangle-n').addClass('ui-icon-circle-triangle-s');
					settings.filter.showHidden = false;
				}
			}
		},

		/**
      * Actualiza el resumen de los criterios de filtrado a partir de los valores existentes en el formulario.
      *
      * @name showSearchCriteria
      * @function
      *
      */
		_showSearchCriteria: function _showSearchCriteria() {
			var ctx = this.DataTable().context[0];
			var $self = this,
			    settings = $('#' + $self[0].id).data('settings' + $self[0].id),
			    searchString = ' ',
			    label,
			    numSelected,
			    field,
			    fieldId,
			    fieldName,
			    fieldValue,
			    aux = settings.filter.$filterContainer.serializeArray(),
			    searchForm = settings.filter.$filterContainer,
			    filterMulticombo = new Array();
			var obj;

			//añadir arbol

			var arboles = $('.jstree', settings.filter.$filterContainer);
			$.each(arboles, function (index, item) {
				obj = new Object();
				obj.name = $(item).attr('name');
				obj.value = $(item).rup_tree('getRupValue').length;
				obj.type = 'rup_tree';
				aux.push(obj);
			});

			for (var i = 0; i < aux.length; i++) {
				if (aux[i].value !== '' && $.inArray(aux[i].name, settings.filter.excludeSummary) !== 0) {

					//CAMPO a tratar
					field = $('[name=\'' + aux[i].name + '\']', searchForm);

					//Comprobar si se debe excluir el campo
					if ($.inArray(field.attr('id'), settings.filter.filterExclude) !== -1) {
						continue;
					}

					//Seleccionar radio
					if (field.length > 1) {
						field = $('[name=\'' + aux[i].name + '\']:checked', searchForm);
					}
					//Omitir campos hidden
					if ($(field).attr('type') === 'hidden') {
						continue;
					}

					//ID del campo
					fieldId = $(field).attr('id');
					//ID para elementos tipo rup.combo
					if ($(field).attr('ruptype') === 'combo' && field.next('.ui-multiselect').length === 0) {
						fieldId += '-button';
					}
					//ID para elementos tipo rup.autocomplete
					if ($(field).attr('ruptype') === 'autocomplete') {
						fieldId = fieldId.substring(0, fieldId.indexOf('_label'));
					}

					//NAME
					label = $('label[for^=\'' + fieldId + '\']', searchForm);
					if (label.length > 0) {
						// <label for='xxx' />
						fieldName = label.html();
					} else {
						// <div />
						// <div />
						if ($(field).attr('ruptype') !== 'combo') {
							fieldName = $('[name=\'' + aux[i].name + '\']', searchForm).prev('div').find('label').first().html();
						} else {

							// Buscamos el label asociado al combo
							// Primero por id
							var $auxField = $('[name=\'' + aux[i].name + '\']', searchForm),
							    $labelField;

							$labelField = jQuery('[for=\'' + $auxField.attr('id') + '\']');

							if ($labelField.length > 0) {
								fieldName = $labelField.first().text();
							} else {

								fieldName = $('[name=\'' + aux[i].name + '\']', searchForm).parent().prev('div').find('label').first().html();
							}
						}
					}
					if (fieldName === null || fieldName === undefined) {
						fieldName = '';
					}

					//VALUE
					fieldValue = ' = ';
					switch ($(field)[0].tagName) {
						case 'INPUT':
							fieldValue = fieldValue + $(field).val();
							if ($(field)[0].type === 'checkbox' || $(field)[0].type === 'radio') {
								fieldValue = '';
							}
							break;
						//Rup-tree
						case 'DIV':
							$.each(aux, function (index, item) {
								if (item.name === field.attr('id')) {
									if (item.value != 0) {
										fieldValue += ' = ' + item.value;
									}
								} else {
									fieldValue = '';
								}
							});
							if (fieldValue === '') {
								fieldName = '';
							}
							break;
						case 'SELECT':
							if (field.next('.ui-multiselect').length === 0) {
								fieldValue = fieldValue + $('option[value=\'' + aux[i].value + '\']', field).html();
							} else {
								if ($.inArray($(field).attr('id'), filterMulticombo) === -1) {
									numSelected = field.rup_combo('value').length;
									if (numSelected !== 0) {
										fieldValue += numSelected;
									} else {
										fieldName = '';
										fieldValue = '';
									}
									filterMulticombo.push($(field).attr('id'));
								} else {
									fieldName = '';
									fieldValue = '';
								}
							}
							break;
					}

					//Parsear NAME
					var parseableChars = new Array(':', '=');
					for (var j = 0; j < parseableChars.length; j++) {
						if (fieldName !== '' && fieldName.indexOf(parseableChars[j]) !== -1) {
							fieldName = fieldName.substring(0, fieldName.indexOf(parseableChars[j]));
							break;
						}
					}

					//Controlar rup.combo con valor vacío
					while (fieldValue.indexOf('&amp;nbsp;') !== -1) {
						fieldValue = fieldValue.replace('&amp;nbsp;', '');
					}

					//Si no tiene NAME sacar solo el valor
					if (fieldName === '' && fieldValue.indexOf(' = ') !== -1) {
						fieldValue = fieldValue.substring(2, fieldValue.length);
					}

					//Si no tiene NAME ni VALUE omitir
					if (fieldName === '' && $.trim(fieldValue) === '') {
						continue;
					}
					searchString = searchString + fieldName + fieldValue + ', ';
				}
			}

			//Añadir criterios
			if (settings.multiFilter !== undefined && jQuery.isFunction(settings.multiFilter.fncFilterName)) {
				searchString = jQuery.proxy(settings.multiFilter.fncFilterName, $self, searchString)();
			}

			settings.filter.$filterSummary.html(' <i>' + searchString + '</i>');
		},

		/**
      * Crea un evente para mantener la multiseleccion, el seeker y el select ya que accede a bbdd.
      *
      * @name createEventSelect
      * @function
      *
      * @param {object} tabla - La configuración de la tabla.
      *
      */
		_createEventSelect: function _createEventSelect(tabla) {
			tabla.on('draw.dtSelect.dt select.dtSelect.dt', function () {
				//Si lleva parametros es que estamos en la navegacion interna.
				var ctx = tabla.context[0];
				if (ctx.oInit.formEdit !== undefined && ctx.oInit.formEdit.$navigationBar !== undefined && ctx.oInit.formEdit.$navigationBar.funcionParams !== undefined && ctx.oInit.formEdit.$navigationBar.funcionParams.length > 0) {
					var params = ctx.oInit.formEdit.$navigationBar.funcionParams;
					//Si hay selectAll, comprobar la linea ya que puede variar al no tener ningún selected.Se recorre el json.
					if (ctx.multiselection.selectedAll) {
						var linea = -1;
						if (params[3] !== undefined && (params[3] === 'prev' || params[3] === 'last')) {
							linea = ctx.json.rows.length;
							params[2] = DataTable.Api().editForm.getLineByPageSelectedReverse(ctx, linea);
						} else {
							if (params[2] !== undefined && params[2] > 0) {
								linea = params[2] - 1;
							}
							params[2] = DataTable.Api().editForm.getLineByPageSelected(ctx, linea); //Se inicia en -1 para que coja desde la primera linea.next y prev.
						}
					}
					DataTable.editForm.fnOpenSaveDialog(params[0], params[1], params[2]);
					ctx.oInit.formEdit.$navigationBar.funcionParams = {};
				}
			});
		},

		/**
  * Metodo que inicialida las propiedades para el multiselect y el Select.
  *
  * @name initializeMultiselectionProps
  * @function
  * @since UDA 3.4.0 // Datatable 1.0.0
  *
  *
  */
		_initializeMultiselectionProps: function _initializeMultiselectionProps(ctx) {

			var multi = {};
			// Se almacenan en los settings internos las estructuras de control de los registros seleccionados
			if (multi.multiselection === undefined) {
				multi.multiselection = {};
			}
			if (ctx.multiselection !== undefined) {
				multi.multiselection.internalFeedback = ctx.multiselection.internalFeedback;
			}
			// Flag indicador de selección de todos los registros
			multi.multiselection.selectedAll = false;
			// Numero de registros seleccionados
			multi.multiselection.numSelected = 0;
			// Propiedades de selección de registros
			multi.multiselection.selectedRowsPerPage = [];
			//$self.multiselection.selectedLinesPerPage = [];
			//$self.multiselection.selectedRows = [];
			multi.multiselection.selectedIds = [];
			multi.multiselection.lastSelectedId = "";
			//$self.multiselection.selectedPages = [];
			// Propiedades de deselección de registros
			multi.multiselection.deselectedRowsPerPage = [];
			//$self.multiselection.deselectedLinesPerPage = [];
			//$self.multiselection.deselectedRows = [];
			multi.multiselection.deselectedIds = [];
			multi.multiselection.accion = ""; //uncheckAll,uncheck
			//$self.multiselection.deselectedPages = [];
			$("#contextMenu1 li.context-menu-icon-uncheck").addClass('disabledDatatable');
			$("#contextMenu1 li.context-menu-icon-uncheck_all").addClass('disabledDatatable');
			// Desmarcamos el check del tHead
			$("#labelSelectTableHead" + ctx.sTableId).removeClass('selectTableHeadCheck');
			$("#linkSelectTableHead" + ctx.sTableId).removeClass('rup-datatable_checkmenu_arrow_margin');

			DataTable.Api().rupTable.selectPencil(ctx, -1);
			if (ctx.multiselection === undefined) {
				ctx.multiselection = {};
			}
			ctx.multiselection = multi.multiselection;
		},
		_createTooltip: function _createTooltip(id) {
			if (id !== undefined && id.text() !== undefined && id.text() !== '') {
				id.rup_tooltip({
					content: {
						text: id.text()
					},
					show: {
						event: 'hover'
					},
					position: {
						viewport: $(window),
						adjust: {
							method: 'flip'
						}
					}

				});
			}
		}
	});

	//*******************************
	// MÉTODO DE INICIALIZACION
	//*******************************
	$.fn.rup_datatable('extend', {
		_init: function _init(args) {
			var $self = this,
			    settings = $.extend({}, $.fn.rup_datatable.defaults, $self[0].dataset, args[0]);

			$self.triggerHandler('tableBeforeInit');

			var clone = jQuery("#" + $self[0].id).clone(true);
			// Se identifica el tipo de componente RUP mediante el valor en el atributo ruptype
			$self.attr('ruptype', 'datatable');
			$self.triggerHandler('tableInit');
			if (args[0].primaryKey !== undefined) {
				settings.primaryKey = args[0].primaryKey.split(";");
			}

			//Comprobar plugin dependientes
			if (settings.multiSelect !== undefined) {
				settings.columnDefs.push({
					orderable: false,
					className: 'select-checkbox',
					targets: 0
				});
				//Modulo incompatible
				settings.select = undefined;
			}

			if (settings.formEdit === undefined) {
				settings.buttons = undefined;
			}

			// getDefault multifilter
			if (settings.multiFilter !== undefined && settings.multiFilter.getDefault === undefined) {
				var usuario;
				if (settings.multiFilter.userFilter != null) {
					usuario = settings.multiFilter.userFilter;
				} else {
					usuario = LOGGED_USER;
				}
				var ctx = {};
				ctx.oInit = settings;
				ctx.sTableId = $self[0].id;
				$.rup_ajax({
					url: settings.urlBase + '/multiFilter/getDefault?filterSelector=' + settings.multiFilter.idFilter + '&user=' + usuario,
					type: 'GET',
					dataType: 'json',
					showLoading: false,
					contentType: 'application/json',
					//async : false,
					complete: function complete(jqXHR, textStatus) {
						$('#' + ctx.sTableId).triggerHandler('tableMultiFilterCompleteGetDefaultFilter');
					},
					success: function success(data, status, xhr) {
						if (data != null) {
							var valorFiltro = $.parseJSON(data.filterValue);

							DataTable.Api().multiFilter.fillForm(valorFiltro, ctx);
							$self._doFilter(data);
							$(settings.filter.$filterSummary, 'i').prepend(data.filterName + '{');
							$(settings.filter.$filterSummary, 'i').append('}');
						}
						$('#' + ctx.sTableId).triggerHandler('tableMultiFilterSuccessGetDefaultFilter');
					},
					error: function error(xhr, ajaxOptions, thrownError) {
						$('#' + ctx.sTableId).triggerHandler('tableMultiFilterErrorGetDefaultFilter');
					}
				});
			}

			$self._initOptions(settings);

			var tabla = $self.DataTable(settings);

			settings.sTableId = $self[0].id;
			$self._initializeMultiselectionProps(tabla.context[0]);

			//Crear tooltips cabecera;
			$.each($('#' + $self[0].id + ' thead th'), function () {
				$self._createTooltip($(this));
			});

			tabla.on('draw', function (e, settingsTable) {
				if (settings.searchPaginator) {
					//Mirar el crear paginador
					$self._createSearchPaginator($(this), settingsTable);
					//Si el seeker esta vacio ocultarlo
					if (settingsTable.seeker !== undefined && settingsTable.seeker.search !== undefined && settingsTable.seeker.search.$searchRow !== undefined) {
						if (settingsTable._iRecordsDisplay > 0) {
							settingsTable.seeker.search.$searchRow.show();
						} else {
							settingsTable.seeker.search.$searchRow.hide();
						}
					}
				}

				if (settings.select !== undefined || settings.multiSelect !== undefined) {
					//AL repintar vigilar el select.
					if (settings.select !== undefined) {
						//AL repintar vigilar el select.
						if (settingsTable.select.selectedRowsPerPage !== undefined) {
							//viene de la navegacion buscar el id.
							var line = 0;
							var ctx = tabla.context[0];
							if (settingsTable.select.selectedRowsPerPage.cambio === 'prev' || settingsTable.select.selectedRowsPerPage.cambio === 'last') {
								line = ctx.json.rows.length - 1;
							}

							ctx.multiselection.selectedRowsPerPage = [];
							var rowSelectAux = ctx.json.rows[line];
							var id = DataTable.Api().rupTable.getIdPk(rowSelectAux);
							ctx.multiselection.selectedRowsPerPage.push({ line: line, page: ctx.select.selectedRowsPerPage.page, id: id });
							settingsTable.select.selectedRowsPerPage = undefined;
							var numTotal = ctx.json.recordsTotal;
							var index = (Number(ctx.json.page) - 1) * 10;
							index = index + line + 1;
							DataTable.Api().editForm.updateDetailPagination(ctx, index, numTotal);
						}
						DataTable.Api().select.drawSelectId(tabla.context[0]);
					}
					if (settingsTable.seeker !== undefined && settingsTable.seeker.search !== undefined) {
						var ctx = tabla.context[0];
						if (settingsTable.seeker.search.funcionParams !== undefined && settingsTable.seeker.search.funcionParams.length > 0 && //Paginar para el seek y que siempre selecione
						ctx.json.page !== settingsTable.seeker.search.funcionParams[settingsTable.seeker.search.pos].page && ctx.fnRecordsTotal() > 0) {
							//ver si hay cambio de pagina.
							DataTable.Api().seeker.selectSearch(tabla, ctx, settingsTable.seeker.search.funcionParams);
						}
					}
				}

				//Crear tooltips tds;
				$.each($('#' + settingsTable.sTableId + ' tbody td'), function () {
					$self._createTooltip($(this));
				});
			});

			tabla.on('destroy', function (e, settingsTable) {
				/*if(settingsTable.oInit.clone === true){
    	$('#'+settingsTable.sTableId+'_filter_form').append(clone);
    }*/
				$('#' + settingsTable.sTableId + '_filter_toolbar').empty();
				$('#' + settingsTable.sTableId + '_detail_navigation').empty();
				/*	tabla.off( 'draw');
    	tabla.off( 'destroy');
    	tabla.off( 'draw.dtSelect.dt select.dtSelect.dt');*/
			});

			if (settings.buttons !== undefined) {
				// Toolbar por defecto del datatable
				new $.fn.dataTable.Buttons(tabla, DataTable.Buttons.defaults.buttons).container().insertBefore($('#' + $self[0].id + '_filter_form'));
			}

			if (settings.multiSelect !== undefined || settings.select !== undefined) {
				$self._createEventSelect(tabla);
			}
			$self._ConfigureFiltern(settings);

			// Se almacena el objeto settings para facilitar su acceso desde los métodos del componente.
			$self.data('settings' + $self[0].id, settings);
			$('#' + tabla.context[0].sTableId).triggerHandler('tableAfterComplete');

			$self.triggerHandler('tableAfterInit');
		}
	});

	//******************************************************
	// DEFINICIÓN DE LA CONFIGURACION POR DEFECTO DEL PATRON
	//******************************************************
	$.fn.rup_datatable.defaults = {
		foobar: false,
		headerContextMenu: {
			show: true,
			selectAllPage: true,
			deselectAllPage: true,
			separator: true,
			selectAll: true,
			deselectAll: true,
			items: {}
		},
		fixedHeader: {
			header: false,
			footer: true
		},
		feedback: {
			okFeedbackConfig: {
				closeLink: true,
				delay: 1000
			}
		},
		dom: 't<"paginationContainer"pli>r', //i: Info, t: table, p:pagination, r: procesing , l:length:
		multiplePkToken: '~',
		primaryKey: ["id"],
		responsive: true,
		searchPaginator: true,
		pagingType: "full",
		columnDefs: [],
		filter: {
			id: "table_filter_form",
			filterToolbar: "table_filter_toolbar",
			collapsableLayerId: "table_filter_fieldset"
		},
		//adapter: "datatable_jqueryui",
		adapter: 'datatable_bootstrap',
		order: [[1, 'asc']]
	};
});
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))

/***/ }),
/* 148 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;

/**
 * @param  {String} `key` The name of the property to use as context.
 * @param  {Object} `options`
 * @return {Object}
 */

/*global jQuery */
/*global Handlebars */

(function (factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(26)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		factory(jQuery, Handlebars);
	}
})(function ($, Handlebars) {
	Handlebars.i18n = {};
	Handlebars.i18n.languages = [];

	Handlebars.registerHelper('i18nLanguages', function (options) {
		options.data.languages = [];
	});

	Handlebars.registerHelper('i18nLanguage', function (options) {

		var langJSON = {};
		langJSON[options.hash.lang] = $.parseJSON('{' + options.fn(this) + '}');

		options.data.languages = $.extend(true, {}, options.data.languages, langJSON);
	});

	Handlebars.registerHelper('i18n', function (key, options) {
		options = options || {};
		options.hash = options.hash || {};

		var language;

		if (typeof key !== 'string') {
			throw '{{i18n}} helper: invalid key. Object keys must be formatted as strings.';
		}

		if (typeof options.hash.language === 'string') {
			language = options.hash.language;
		} else {
			language = this.datosIdioma;
		}

		//return options.data.languages[language][key];
		return $.rup.i18nParse($.rup.i18n.base, key);
	});

	return Handlebars;
});

/***/ }),
/* 149 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*!
 * Copyright 2016 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 */

/**
 * Tiene como objetivo presentar un contenido donde conceptos relacionados pueden agruparse (ej. secciones) de manera que el usuario puede mostrar u ocultar información sin perder el contexto del contenido principal.
 *
 * @summary Componente RUP Accordion.
 * @module rup_accordion
 * @see El componente está basado en el plugin {@link https://jqueryui.com/accordion/|jQuery UI Accordion}. Para mas información acerca de las funcionalidades y opciones de configuración pinche {@link http://api.jqueryui.com/accordion/|aquí}.
 * @example
 * $(".rup_accordion").rup_accordion({
 *   animate: "bounceslide",
 *	active: false,
 *	autoHeight: false,
 *	collapsible: true
 * });
 */

/*global define */
/*global jQuery */

(function (factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(2)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		factory(jQuery);
	}
})(function ($) {

	//*****************************************************************************************************************
	// DEFINICIÓN BASE DEL PATRÓN (definición de la variable privada que contendrá los métodos y la función de jQuery)
	//*****************************************************************************************************************


	var rup_accordion = {};

	//Se configura el arranque de UDA para que alberge el nuevo patrón
	$.extend($.rup.iniRup, $.rup.rupSelectorObjectConstructor('rup_accordion', rup_accordion));

	//********************************
	// DEFINICIÓN DE MÉTODOS PÚBLICOS
	//********************************

	$.fn.rup_accordion('extend', {
		/**
    * Elimina completamente la funcionalidad del Accordion. Como resultado, se devuelven los
  objetos html, tal y como estaban, antes de aplicar el componente Accordion.
    *
    * @function destroy
    * @example
    * $("#idAccordion").rup_accordion("destroy");
    */
		destroy: function destroy() {
			$(this).removeData('settings');
			$(this).accordion('destroy');
		},
		/**
         * Deshabilita el componente Accordion.
         *
         * @function disable
         * @example
         * $("#idAccordion").rup_accordion("disable");
         */
		disable: function disable() {
			$(this).accordion('disable');
		},
		/**
         * Habilita el componente Accordion.
         *
         * @function enable
         * @example
         * $("#idAccordion").rup_accordion("enable");
         */
		enable: function enable() {
			$(this).accordion('enable');
		},
		/**
         * Dependiendo de si se informa un valor asociado a una parámetro o se introduce un json con relaciones variable-valor o no se pasan parámetros asociados a la opción especificada, la función asigna el nuevo valor al parámetro asociado o asigna el nuevo conjunto de valores a los parámetros asociados o devuelve el valor actual del parámetro especificado (actuando como un get), respectivamente..
         *
         * @function option
         * @param {String | Object} opt - Nombre de la propiedad u objeto con varias propiedades.
         * @param {*} [value] - Valor a asignar a la propiedad especificada por su nombre en el primer parámetro.
         * @example
         * // Asignar el valor "bounceslide" a la propiedad "animate"
         * $("#idAccordion").rup_accordion("option", "animate", "bounceslide");
         * // Se asignan valores a varias propiedades por medio de un objeto json.
         * $("#idAccordion").rup_accordion("option",{active: false, collapsible : true});
         * // Se recupera el valor de la propiedad "animate"
         * $("#idAccordion").rup_accordion("option", "animate");
         */
		option: function option(opt, value) {
			//Se establecen la propiedad o propiedades que reciben como parametro y se leen las que no vienen con una asignación.
			if (value !== undefined) {
				$(this).accordion('option', opt, value);
			} else {
				if (opt !== undefined) {
					return $(this).accordion('option', opt);
				} else {
					return $(this).accordion('option');
				}
			}
		},
		/**
         * Devuelve el elemento .ui-accordion:.
         *
         * @function widget
         * @returns {object} - Objeto jQuery que contiene el accordion.
         * @example
         * $("#idAccordion").rup_accordion("widget");
         */
		widget: function widget() {
			return $(this).accordion('widget');
		},
		/**
         * Activación programática de la sección especificada por parámetro.
         *
         * @function activate
         * @param {number | object | boolean} - Valor numérico diferente de cero que indique la sección seleccionada o un selector que determine el elemento activado. En caso de tener el collapsible activado, es posible pasar el valor false para que se cierren todas las secciones.
         * @example
         * // Activar la seción tercera.
         * $("#idAccordion").rup_accordion("activate", 3);
         * // Activar la seción identificada con el selector seccion3.
         * $("#idAccordion").rup_accordion("activate", "#seccion3");
         * // Colapsar todas las secciones.
         * $("#idAccordion").rup_accordion("activate", false);
         */
		activate: function activate(index) {
			$(this).accordion('option', 'active', index);
		},
		/**
         * La función provoca el reajuste de los height (tamaño vertical) de las distintas secciones del Accordion. La ejecución de esta función solo tiene sentido si la opción fillSpace está activada y el height del contenedor cambia.
         *
         * @function resize
         * @deprecated desde la version 2.5.0. Utilizar en su lugar el método refresh.
         * @example
         * $("#idAccordion").rup_accordion("resize");
         */
		resize: function resize() {
			$(this).accordion('resize');
		}
	});

	//********************************
	// DEFINICIÓN DE MÉTODOS PRIVADOS
	//********************************

	function create_default(event) {
		$(event.target).addClass('rup_accordion_create');
	}

	$.fn.rup_accordion('extend', {
		_init: function _init(args) {
			if (args.length > 1) {
				$.rup.errorGestor($.rup.i18n.base.rup_global.initError + $(this).attr('id'));
			} else {
				var elements = this.children(),
				    elementsNum = elements.length / 2,
				    settings = $.extend({}, $.fn.rup_accordion.defaults, args[0]),
				    createUserEvent;
				//Se recogen y cruzan las paremetrizaciones del objeto
				//Se tapa la creación del accordion para evitar visualizaciones inapropiadas
				//Se recomienda que el componente, inicialmente, sea invisible. Para ello se dispone del estilo rup_accordion
				this.removeClass('rup_accordion');

				//Se almacenan los settings en el data del objeto
				this.data('settings', settings);

				//Se sobreescribe uno de los eventos para hacer reaparecer, una vez creado, el accordion
				createUserEvent = settings.create;
				settings.create = function (event, ui) {
					if (createUserEvent !== undefined) {
						if (createUserEvent(event, ui) === false) {
							return false;
						}
					}
					//Comportamiento por defecto del evento
					create_default(event, ui);
				};

				//Se comprueba la corrección del html con el que se creara el accordion
				if (settings.validation) {
					if (parseInt(elementsNum) !== elementsNum) {
						$.rup.errorGestor($.rup.i18n.base.rup_accordion.strucPairError);
						return false;
					} else {
						elements.each(function (index, object) {
							if (parseInt(index / 2) === index / 2 && $(object).find('a').length === 0) {
								$.rup.errorGestor($.rup.i18n.base.rup_accordion.headFormatError);
								return false;
							}
						});
					}
				}

				//Se invoca la creacion del accordion
				this.accordion(settings);
			}
		}
	});

	//*******************************************************
	// DEFINICIÓN DE LA CONFIGURACION POR DEFECTO DEL PATRON
	//*******************************************************

	/**
     * @description Opciones por defecto de configuración del componente.
     * @name defaults
     * @property {boolean} [validation=true] - Parámetro de configuración que determina la aplicación de la validación estructural asociada a las necesidades estructurales del Accordion.
     * @property {boolean} [disabled=false]- Parámetro de configuración que determina si está habilitado (false) o deshabilitado (true) el componente Accordion. Por defecto el valor de este parámetro es false.
     * @property { boolean| number} [active=0] - Determina la sección que está activa. Si se le especifica el valor false, el Accordion permanecerá totalmente cerrado (este caso requiere del parámetro collapsible true). Por defecto, su valor es la primera sección del Accordion.
     * @property {boolean | number | String | Object}   [animate ={}]   - Elemento de configuración que determina el tipo de animación aplicada al pliegue y despliegue de las secciones del Accordion. Puede aceptar los distintos tipos de animaciones asociados a JQuery–Ui (por ejemplo bounceslide). Con un valor false se deshabilita la animación. El valor por defecto es slide (deslizable básico).
     * @property {boolean }[collapsible=false] - Parámetro que habilita la posibilidad de que todas las secciones del Accordion estén cerradas a la vez.
     * @property {String} [event='click'] - Determina el tipo de evento necesario para que cada una de las secciones sea habilitada o deshabilitada.
     * @property {selector}[header="> li > :first-child,> :not(li):even"] -  Selector que determina el objeto cabecera de cada una de las secciones del Accordion. Por defecto recoge como cabeceras los primeros elementos de cada pareja integrada en el Accordion.
     * @property {Object} [icons='{"header": "ui-icon-triangle-1-e","activeHeader": "ui-icon-triangle-1-s"}'] - Parámetro estructural que determina el icono utilizado para indicar el estado de sección abierta o cerrada. Se puede especificar tanto uno como otro como los dos. Por defecto se usan los iconos nativos del propio de JQuery-UI.
     *
     */
	$.fn.rup_accordion.defaults = {
		validation: true
	};
});

/***/ }),
/* 150 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function($) {var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;var _typeof = typeof Symbol === "function" && typeof Symbol.iterator === "symbol" ? function (obj) { return typeof obj; } : function (obj) { return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj; };

/*!
 * Copyright 2016 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 */

/**
 * Permite al usuario recuperar un elemento de una gran lista de elementos o de varias listas dependientes de forma sencilla y ocupando poco espacio en la interfaz.
 *
 * @summary Componente RUP Autocomplete.
 * @module rup_autocomplete
 * @see El componente está basado en el plugin {@link https://jqueryui.com/autocomplete/|jQuery UI Autocomplete}. Para mas información acerca de las funcionalidades y opciones de configuración pinche {@link http://api.jqueryui.com/autocomplete/|aquí}.
 * @example
 * $("#idAutocomplete").rup_autocomplete({
 *	source : "autocomplete/remote",
 *	sourceParam : {label:"desc"+$.rup_utils.capitalizedLang(), value:"code"}
 * });
 */

/*global define */
/*global jQuery */
/*global $ */

(function (factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(2)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		factory(jQuery);
	}
})(function (jQuery) {

	//****************************************************************************************************************
	// DEFINICIÓN BASE DEL PATRÓN (definición de la variable privada que contendrá los métodos y la función de jQuery)
	//****************************************************************************************************************

	var rup_autocomplete = {};

	$.extend($.ui.autocomplete.prototype, {
		_renderMenu: function _renderMenu(ul, items) {
			var settings = this.options;

			if (settings.category) {
				//categorización de los resultados
				var that = this,
				    currentCategory = '';
				$.each(items, function (index, item) {
					var li;
					if (item.category != currentCategory) {
						ul.append('<li class=\'ui-autocomplete-category\'>' + item.category + '</li>');
						currentCategory = item.category;
					}
					li = that._renderItemData(ul, item);
					if (item.category) {
						li.attr('aria-label', item.category + ' : ' + item.label);
					}
				});
			} else {
				var self = this;
				$.each(items, function (index, item) {
					self._renderItemData(ul, item);
				});
			}
		},
		_renderItem: function _renderItem(ul, item) {

			// Replace the matched text with a custom span. This
			// span uses the class found in the "highlightClass" option.
			var re = new RegExp('(?![^&;]+;)(?!<[^<>]*)(' + $.ui.autocomplete.escapeRegex(this.term) + ')(?![^<>]*>)(?![^&;]+;)', 'gi'),
			    cls = 'matched-text',
			    template = '<span class=\'' + cls + '\'>$1</span>',
			    label = item.label.replace(re, template),
			    $li = $('<li/>').appendTo(ul);

			// Create and return the custom menu item content.
			$('<a/>').attr('href', '#').html(label).appendTo($li);
			var settings = this.options;
			$li.find('a').mousedown(function (event) {
				var ui = { item: { label: item.label, value: item.value } };
				settings.select(event, ui);
			});
			return $li;
		}
	});

	//Se configura el arranque de UDA para que alberge el nuevo patrón
	$.extend($.rup.iniRup, $.rup.rupSelectorObjectConstructor('rup_autocomplete', rup_autocomplete));

	//*******************************
	// DEFINICIÓN DE MÉTODOS PÚBLICOS
	//*******************************
	$.fn.rup_autocomplete('extend', {
		/**
         * Método utilizado para obtener el valor del componente. Este método es el utilizado
        por el resto de componentes RUP para estandarizar la obtención del valor del Autocomplete.
         *
         * @function getRupValue
         * @return {string | number} - Devuelve el valor actual del componente seleccionado por el usuario.
         * @example
         * $("#idAutocomplete").rup_autocomplete("getRupValue");
         */
		getRupValue: function getRupValue() {
			return $(this).val();
		},
		/**
     * Método utilizado para asignar el valor al componente. Este método es el utilizado por
  el resto de componentes RUP para estandarizar la asignación del valor al Autocomplete.
     *
     * @function setRupValue
     * @param {string | number} param - Valor que se va a asignar al componente.
     * @example
     * $("#idAutocomplete").rup_autocomplete("setRupValue", "Si");
     */
		setRupValue: function setRupValue(value) {
			var $self = this,
			    data = $self.data('rup.autocomplete'),
			    loadObjects,
			    newObject = {};

			if (data) {

				// Comprobamos si tiene la referencia al campo hidden
				if (data.$hiddenField) {
					data.$hiddenField.attr('rup_autocomplete_label', value);

					loadObjects = $self.data('loadObjects');
					newObject[value] = data.$hiddenField.val();
					$self.data('loadObjects', jQuery.extend(true, {}, loadObjects, newObject));
				}

				if (data.$labelField) {
					loadObjects = data.$labelField.data('loadObjects');
					newObject[$self.attr('rup_autocomplete_label')] = value;
					data.$labelField.data('loadObjects', jQuery.extend(true, {}, loadObjects, newObject));
				}
			}

			$(this).val(value);
		},
		/**
         * Elimina el autocomplete.
         *
         * @function destroy
         * @example
         * $("#idAutocomplete").rup_autocomplete("destroy");
         */
		destroy: function destroy() {
			var self;

			if ($(this).attr('id').indexOf('_label') >= 0) {
				self = $(this);
			} else {
				self = $('#' + $(this).attr('id') + '_label');
			}

			self.autocomplete('destroy');
		},
		/**
         * Deshabilita el autocomplete (solo la parte de sugerencias, el input sigue habilitado).
         *
         * @function off
         * @example
         * $("#idAutocomplete").rup_autocomplete("off");
         */
		off: function off() {
			var self;

			if ($(this).attr('id').indexOf('_label') >= 0) {
				self = $(this);
			} else {
				self = $('#' + $(this).attr('id') + '_label');
			}

			self.storeEvents();
		},
		/**
         * Habilita el autocomplete (solo la parte de sugerencias).
         *
         * @function on
         * @example
         * $("#idAutocomplete").rup_autocomplete("on");
         */
		on: function on() {
			var self;

			if ($(this).attr('id').indexOf('_label') >= 0) {
				self = $(this);
			} else {
				self = $('#' + $(this).attr('id') + '_label');
			}

			self.restoreEvents();
		},
		/**
         * Deshabilita el autocomplete. Internamente invoca al método {@link module:rup_autocomplete~off}.
         *
         * @function disable
         * @example
         * $("#idAutocomplete").rup_autocomplete("disable");
         */
		disable: function disable() {
			var self, settings;

			if ($(this).attr('id').indexOf('_label') >= 0) {
				self = $(this);
			} else {
				self = $('#' + $(this).attr('id') + '_label');
			}

			settings = self.data('settings');

			if (settings.combobox) {
				settings.$comboboxToogle.button('disable');
			}

			self.attr('disabled', 'disabled');
		},
		/**
         * Habilita el autocomplete. Internamente invoca al método {@link module:rup_autocomplete~on}.
         *
         * @function enable
         * @example
         * $("#idAutocomplete").rup_autocomplete("enable");
         */
		enable: function enable() {
			var self, settings;

			if ($(this).attr('id').indexOf('_label') >= 0) {
				self = $(this);
			} else {
				self = $('#' + $(this).attr('id') + '_label');
			}

			settings = self.data('settings');

			if (settings.combobox) {
				settings.$comboboxToogle.button('enable');
			}

			self.removeAttr('disabled');
		},
		/**
         * Permite consultar y modificar la configuración del componente.
         *
         * @param {string | object} optionName - Nombre de la propiedad que se desea gestionar o objeto de compuesto de varias propiedades.
         * @param {*} [value] - Corresponde al valor de la propiedad en caso de haberse especificado el nombre de la misma en el primér parámetro.
         * @param {*} aux - Parámetro extra de confirguración para la propiedad "source".
         * @function option
         * @example
         * // Establecer una propiedad
         * $("#idAutocomplete").rup_autocomplete("option", "minLegth", 2);
         * // Establecer varias propiedad
         * $("#idAutocomplete").rup_autocomplete("option", {minLegth:2, delay:1000});
         */
		option: function option(optionName, value, aux) {
			var self;

			if ($(this).attr('id').indexOf('_label') >= 0) {
				self = $(this);
			} else {
				self = $('#' + $(this).attr('id') + '_label');
			}

			var settings = self.data('settings');
			if (optionName === 'source') {
				if ((typeof value === 'undefined' ? 'undefined' : _typeof(value)) === 'object') {
					//LOCAL
					if (aux !== undefined) {
						settings.i18nId = aux;
					} else {
						settings.i18nId = settings.id;
					}
					self.autocomplete('option', optionName, this._sourceLOCAL);
					self.autocomplete('option', 'minLength', settings.minLength !== undefined ? settings.minLength : 0);
				} else {
					if (aux !== undefined) {
						if (optionName == 'data') {
							self.autocomplete('option', 'data', aux);
						} else {
							//REMOTO
							settings.sourceParam = aux;
							//Nos aseguramos que el número mínimo de teclas para búsquedas sea 3
							self.autocomplete('option', optionName, this._sourceREMOTE);
							self.autocomplete('option', 'minLength', settings.minLength > 3 ? settings.minLength : 3);
						}
					} else {
						return undefined;
					}
				}
				settings.data = value;
				self.data('settings', settings);
			} else {
				settings[optionName] = value;
				self.data('settings', settings);
				self.autocomplete('option', optionName, value);
			}
		},
		/**
     * Lanza una búsqueda en el autocomplete con el parámetro indicado y el foco va a parar al
  input.
     *
     * @param {string} term - Cadena de texto utilizada para realizar la búsqueda.
     * @function search
     * @example
     * $("#idAutocomplete").rup_autocomplete("search", "java");
     */
		search: function search(term) {
			//Si tiene eventos (no está deshabilitado) se hace búsqueda
			if ($._data($(this)[0], 'events') !== undefined) {
				$(this).focus();
				$(this).val(term);
				$(this).autocomplete('search', term);
			}
		},
		/**
         * Oculta el autocomplete.
         *
         * @function close
         * @example
         * $("#idAutocomplete").rup_autocomplete("close");
         */
		close: function close() {
			$(this).autocomplete('close');
		},
		/**
         * Devuelve el valor del autocomplete. Este es el valor que se guarda en el campo oculto antes descrito al final del apartado 7.Para obtener la descripción (dato que se muestra en el input) se invocará a la función estándar de jQuery.
         *
         * @function val
         * @example
         * // Recuperar el valor
         * $("#idAutocomplete").rup_autocomplete("val");
         * // Recuperar la descripción
         * $("#idAutocomplete").val();
         */
		val: function val() {
			return $('#' + $(this).attr('id')).val();
		},
		/**
         * Método utilizado para asignar el valor y el literal al componente. El valor se almacena en el campo hidden creado por el componente. El contenido indicado en la propiedad label se mostrará en el campo input del componente.
         *
         * @function set
         * @param {string | number} value - Valor que se va a almacenar en el campo hidden y que se corresponde con el value seleccionado.
         * @param {string} label - Texto que se va a mostrar en el campo de texto del componente.
         * @example
         * $("#idAutocomplete").rup_autocomplete("set", "48", "Bizkaia");
         */
		set: function set(value, label) {
			var $self = $(this),
			    $selfLabel = jQuery('[id=\'' + $self.attr('id') + '_label\']'),
			    loadObjects,
			    newObject = {};

			$self.val(value);
			$self.attr('rup_autocomplete_label', label);
			$selfLabel.val(label);
			loadObjects = $selfLabel.data('loadObjects');
			newObject[label] = value;
			$selfLabel.data('loadObjects', jQuery.extend(true, {}, loadObjects, newObject));
		}
	});

	//*******************************
	// DEFINICIÓN DE MÉTODOS PRIVADOS
	//*******************************
	$.fn.rup_autocomplete('extend', {
		/**
         * Procesa los elementos recibidos en la respuesta de la petición de búsqueda realizada.
         *
         * @function _parseResponse
         * @private
         * @param {string} term - Cadena de texto empleada para realizar la búsqueda.
         * @param {string} label - Texto a mostrar del elemento enviado en la respuesta.
         * @param {string | number} value - Valor del elemento enviado en la respuesta.
         * @param {string} [category] - Texto identificador de la categoría del elemento en el caso de que exista.
         */
		_parseResponse: function _parseResponse(term, label, value, category) {
			if (category === undefined) {
				return {

					label: label.replace(new RegExp('(?![^&;]+;)(?!<[^<>]*)(' + $.ui.autocomplete.escapeRegex(term) + ')(?![^<>]*>)(?![^&;]+;)', 'gi'), '<strong>$1</strong>'),
					value: value
				};
			} else {
				return {

					label: label.replace(new RegExp('(?![^&;]+;)(?!<[^<>]*)(' + $.ui.autocomplete.escapeRegex(term) + ')(?![^<>]*>)(?![^&;]+;)', 'gi'), '<strong>$1</strong>'),
					value: value,
					category: category
				};
			}
		},
		/**
         * Procesa la respuesta a partir de una petición de búsqueda sobre una fuente de datos local.
         *
         * @function _sourceLOCAL
         * @private
         * @param {object} request - Objeto que contiene la petición de búsqueda.
         * @param {object} response - Objeto que contiene la respuesta a partir de la fuente de datos local.
         */
		_sourceLOCAL: function _sourceLOCAL(request, response) {
			var settings,
			    loadObjects = {},
			    returnValue,
			    stock;

			if (this.element.data('settings') !== undefined) {
				settings = this.element.data('settings');
			} else {
				settings = this.options;
			}

			if (settings.loadObjects !== undefined) {
				stock = settings.loadObjects;
			} else {
				stock = settings.id;
			}

			var textoOrigen = request.term;
			if (settings.accentFolding) {
				textoOrigen = $.rup_utils.normalize(request.term);
			}
			var data,
			    matcher = settings.contains ? $.ui.autocomplete.escapeRegex(textoOrigen) : '^' + $.ui.autocomplete.escapeRegex(textoOrigen),
			    json_i18n = $.rup.i18n.app[settings.i18nId];

			matcher = new RegExp(matcher, 'i');
			data = $.map(settings.data, function (item) {
				var label = item,
				    value = item,
				    category;
				if ((typeof item === 'undefined' ? 'undefined' : _typeof(item)) === 'object') {
					//multi-idioma
					if (item.i18nCaption !== undefined) {
						label = $.rup.i18nParse(json_i18n, item.i18nCaption);
					} else if (item.label !== undefined) {
						label = item.label;
					} else {
						label = item.value;
					}
					value = item.value;
					if (settings.category) category = item.category;
				}
				var labelLimpio = label;
				if (settings.accentFolding) {
					labelLimpio = $.rup_utils.normalize(label);
				}
				if (!request.term || matcher.test(labelLimpio)) {
					var termLimpio = $.rup_utils.normalize(request.term);
					if (settings.category) returnValue = settings._parseResponse(termLimpio, labelLimpio, value, category);else returnValue = settings._parseResponse(termLimpio, labelLimpio, value);
					loadObjects[returnValue.label.replace(/<strong>/g, '').replace(/<\/strong>/g, '')] = returnValue.value;

					if (settings.accentFolding && labelLimpio !== label) {
						//limpiar acentos y mayúsculas
						//parte delantera
						//returnValue.label = literal.substr(0,nDelante)+label.substr(0,termLimpio.length)+literal.substr(nDelante+termLimpio.length);

						var literal = returnValue.label;
						var nDelante = literal.indexOf(termLimpio);
						var n = labelLimpio.indexOf(termLimpio);
						returnValue.label = literal.substr(0, nDelante) + item.label.substr(n, termLimpio.length) + literal.substr(nDelante + termLimpio.length);
						//parte trasera
						//var nAtras = literal.indexOf(labelLimpio.substr(termLimpio.length));

						var nAtras = literal.indexOf("</strong>") + 9;
						literal = returnValue.label;
						returnValue.label = literal.substr(0, nAtras) + label.substr(n + termLimpio.length);
					}
					return returnValue;
				}
			});

			//Se almacenan los datos cargados
			$('#' + stock).data('loadObjects', loadObjects);

			//Eliminar elementos vacíos
			data = $.grep(data, function (value) {
				return value != undefined;
			});
			response(data);
		},
		/**
         * Procesa la respuesta a partir de una petición de búsqueda sobre una fuente de datos remota.
         *
         * @function _sourceREMOTE
         * @private
         * @param {object} request - Objeto que contiene la petición de búsqueda.
         * @param {object} response - Objeto que contiene la respuesta a partir de la fuente de datos remota.
         */
		_sourceREMOTE: function _sourceREMOTE(request, response) {
			//Se escapan los comodines/wildcards de BD
			var $self = this.element,
			    settings,
			    loadObjects = {},
			    returnValue,
			    stock,
			    term,
			    data,
			    lastTerm,
			    bckData,
			    $stock;

			if (this.element.data('settings') !== undefined) {
				settings = this.element.data('settings');
			} else {
				settings = this.options;
			}

			if (settings.loadObjects !== undefined) {
				stock = settings.loadObjects;
			} else {
				stock = settings.id;
			}

			$stock = jQuery('#' + stock);

			term = request.term.replace(/%/g, '\\%').replace(/_/g, '\\_');
			data = $.extend({
				q: term,
				c: this.options.contains
			}, this.options.extraParams);

			// Comprobar si se puede cachear
			lastTerm = $stock.data('tmp.loadObjects.term');

			if (term.indexOf(lastTerm) === 0) {

				$stock.data('tmp.loadObjects.term', term);

				bckData = settings.data;

				settings.data = $stock.data('tmp.data');
				jQuery.proxy(settings.$self._sourceLOCAL, this, request, response)();
				settings.data = bckData;
			} else {

				$.rup_ajax({
					url: settings.data,
					data: data,
					dataType: 'json',
					contentType: 'application/json',
					//Cabecera RUP
					beforeSend: function beforeSend(xhr) {
						//LOADING...
						$('#' + settings.id + '_label').addClass('rup-autocomplete_loading');

						xhr.setRequestHeader('RUP', $.toJSON(settings.sourceParam));
					},
					/**
                     *
                     * @fires  {[event]} rupAutocomplete_beforeLoadComplete [description]
                     */
					success: function success(data) {

						$self.triggerHandler('rupAutocomplete_beforeLoadComplete', [data]);
						//Si no hay datos en el autocomplete que se cierre
						if (data.length === 0) {
							jQuery('#' + settings.id + '_label').autocomplete('close');
							return null;
						}
						response($.map(data, function (item) {
							//Si hay sourcePAram se serielizan los paramtros desde el js y no desde el bean.
							if (settings.sourceParam !== undefined && settings.sourceParam.category !== undefined && settings.sourceParam.category === 'filter') {
								if (settings.sourceParam.label !== undefined) {
									item.label = item[settings.sourceParam.label];
								}
								if (settings.sourceParam.data !== undefined) {
									item.value = item[settings.sourceParam.data];
								}
								if (settings.sourceParam.category !== undefined) {
									item.category = item[settings.sourceParam.category];
								}
							}
							var labelLimpio = item.label;
							if (settings.accentFolding) {
								labelLimpio = $.rup_utils.normalize(item.label);
							}
							var termLimpio = $.rup_utils.normalize(request.term);
							if (settings.category === true) returnValue = settings._parseResponse(termLimpio, labelLimpio, item.value, item.category);else returnValue = settings._parseResponse(termLimpio, labelLimpio, item.value);

							loadObjects[returnValue.label.replace(/<strong>/g, '').replace(/<\/strong>/g, '')] = returnValue.value;
							if (settings.accentFolding && labelLimpio !== item.label) {
								//limpiar acentos y mayúsculas
								//parte delantera
								var literal = returnValue.label;
								var nDelante = literal.indexOf(termLimpio);
								var n = labelLimpio.indexOf(termLimpio);
								returnValue.label = literal.substr(0, nDelante) + item.label.substr(n, termLimpio.length) + literal.substr(nDelante + termLimpio.length);
								//parte trasera
								var nAtras = literal.indexOf("</strong>") + 9;
								literal = returnValue.label;
								returnValue.label = literal.substr(0, nAtras) + item.label.substr(n + termLimpio.length);
							}
							return returnValue;
						}));

						//se almacenan los datos cargados
						$stock.data('loadObjects', loadObjects);
						$stock.data('tmp.loadObjects.term', term);
						$stock.data('tmp.data', data);

						$self.triggerHandler('rupAutocomplete_loadComplete', [data]);
					},
					error: function error(xhr, textStatus, errorThrown) {
						if (settings.onLoadError !== null && typeof settings.onLoadError === 'function') {
							jQuery(settings.onLoadError(xhr, textStatus, errorThrown));
						} else {
							$.rup.showErrorToUser($.rup.i18n.base.rup_autocomplete.ajaxError);
						}
					},
					complete: function complete() {
						//UNLOADING...
						$('#' + settings.id + '_label').removeClass('rup-autocomplete_loading');
					}
				});
			}
		},
		/**
         * Función encargada de crear el control encargado de mostrar todos los resultados cuando el componente tiene activado el modo de funcionamiento combobox.
         *
         * @function _createShowAllButton
         * @private
         */
		_createShowAllButton: function _createShowAllButton(settings) {
			var input = this,
			    wasOpen = false;
			input.wrap(jQuery('<span>').addClass('rup-combobox'));
			var $wrapper = input.parent();
			var $button = $('<a>').attr('tabIndex', -1).attr('title', $.rup.i18n.base.rup_autocomplete.showAllItems).rup_tooltip().rup_button({
				icons: {
					primary: 'ui-icon-triangle-1-s'
				},
				text: false
			}).removeClass('ui-corner-all').addClass('rup-combobox-toggle ui-corner-right').mousedown(function () {
				wasOpen = input.autocomplete('widget').is(':visible');
			}).click(function () {
				input.focus();
				// Close if already visible
				if (wasOpen) {
					return true;
				}
				// Pass empty string as value to search
				// for, displaying all results
				input.autocomplete('search', '');
			});

			$button.appendTo($wrapper);
			settings.$comboboxToogle = $button;
		},
		/**
         * Método de inicialización del componente.
         *
         * @function _init
         * @private
         */
		_init: function _init(args) {

			if (args.length > 1) {
				$.rup.errorGestor($.rup.i18nParse($.rup.i18n.base, 'rup_global.initError') + $(this).attr('id'));
			} else {
				//Se recogen y cruzan las paremetrizaciones del objeto
				var $self = $(this),
				    settings = $.extend({}, $.fn.rup_autocomplete.defaults, args[0]),
				    name = $(this).attr('name'),
				    selected_value;

				$(this).attr('ruptype', 'autocomplete');

				//Recopilar datos necesarios
				settings.id = $(this).attr('id');
				settings.loadObjects = settings.id;
				settings.data = settings.source; //Guardar los datos en "data" ya que source la emplea autocomplete internamente
				settings._parseResponse = this._parseResponse; //Guardar referencia a rup.autocomplete para invocar las funciones privadas
				settings._sourceLOCAL = this._sourceLOCAL; //Guardar referencia a rup.autocomplete para invocar las funciones privadas
				settings.$self = this; //Guardar referencia a rup.autocomplete para invocar las funciones privadas

				//Guardar valor del INPUT
				settings.loadValue = $('#' + settings.id).attr('value');

				//Si no se recibe identificador para el acceso a literales se usa el ID del objeto
				if (!settings.i18nId) {
					settings.i18nId = settings.id;
				}

				//Eventos
				//*******
				//Guardar referencia
				settings._change = settings.change;
				settings._select = settings.select;
				settings._focus = settings.focus;

				//Sobrecargar tratamiento
				settings.change = function (event, ui) {
					if (selected_value != null) {
						//Puede que se ejecute este evento sin ejecutarse el select. Con esta condición nos aseguramos
						$('#' + event.target.id).val(selected_value);
						$('#' + event.target.id).focus();
					}
					selected_value = null;
					if (settings._change !== undefined) {
						settings._change(event, ui);
					}
					$self.triggerHandler('rupAutocomplete_change');
				};
				settings.select = function (event, ui) {
					selected_value = ui.item.label.replace(/<strong>/g, '').replace(/<\/strong>/g, '');
					if (settings._select !== undefined) {
						$('#' + settings.id).val(ui.item.value);
						settings._select(event, ui);
					}
					$('#' + settings.id).attr('rup_autocomplete_label', selected_value);
					$('#' + settings.id).data('selected', true);
					$self.triggerHandler('rupAutocomplete_select', [ui]);
					$('#' + settings.id).val(ui.item.value);
					return false;
				};
				settings.focus = function (event, ui) {
					$('#' + event.target.id).val(ui.item.label.replace(/<strong>/g, '').replace(/<\/strong>/g, ''));
					if (settings._focus !== undefined) {
						settings._focus(event, ui);
					}
					return false; //Evitar acciones jquery.autocomplete.js
				};

				//Generación de campo oculto para almacenar 'value' (en el input definido se guarda el 'label')
				var $hidden = $('<input>').attr({
					type: 'hidden',
					id: settings.id + '_value',
					name: settings.valueName === null ? name : settings.valueName,
					ruptype: 'autocomplete'
				});

				$('#' + settings.id).after($hidden).attr('name', settings.labelName === null ? name + '_label' : settings.labelName).addClass('rup-autocomplete_label');

				//					settings.$hidden = $hidden;

				if (_typeof(settings.source) === 'object') {
					//LOCAL
					settings.source = this._sourceLOCAL;
				} else {
					//REMOTO
					//Nos aseguramos que el número mínimo de teclas para búsquedas sea 3
					settings.minLength = settings.minLength > 3 ? settings.minLength : 3;
					settings.source = this._sourceREMOTE;
				}

				//Se prepara el almacenaje de datos
				$('#' + settings.id).data('loadObjects', {});

				if (settings.combobox === true) {
					$('#' + settings.id).addClass('rup-combobox-input ui-corner-left');
					settings.minLength = 0;
				}

				jQuery(settings.appendTo).addClass('ui-front');

				//Invocación al componente subyacente
				jQuery('#' + settings.id).autocomplete(settings);

				//Se anyade un id al menu desplegable del autocomplete
				settings.$menu = jQuery('#' + settings.id).data('ui-autocomplete').menu.element.attr('id', settings.id + '_menu');

				//override mousedown para corregir el fallo del scrollbar en IE (bug 5610)
				settings.$menu.off('mousedown');
				// prevent the close-on-blur in case of a "slow" click on the menu (long mousedown) y corrección del bug 5610 (scrollbar en IE)
				settings.$menu.on('mousedown', function (event) {

					var menuElement = jQuery('#' + settings.id + '_menu')[0];

					if (!$(event.target).closest('.ui-menu-item').length) {
						setTimeout(function () {
							$(document).one('mousedown', function (event) {
								if (event.target !== jQuery('#' + settings.id + '_label') && event.target !== menuElement && !$.ui.contains(menuElement, event.target)) {
									jQuery('#' + settings.id + '_label').autocomplete('close');
								}
							});
						}, 1);
					} else {

						$('#' + settings.id + '_label').triggerHandler('blur');
					}

					// use another timeout to make sure the blur-event-handler on the input was already triggered
					setTimeout(function () {
						clearTimeout($('#' + settings.id + '_label').data('ui-autocomplete').closing);
					}, 13);
				});

				if (settings.combobox === true) {
					this._createShowAllButton(settings);
				}

				// Altura del menu desplegable

				jQuery('#' + settings.id).on('autocompleteopen', function () {
					if (settings.menuMaxHeight === false) {
						settings.$menu.css('overflow-y', 'auto').css('overflow-x', 'hidden').css('max-height', settings.menuMaxHeight).css('width', jQuery('#' + settings.id + '_label').innerWidth());
					}
					jQuery('#' + settings.id + '_menu').css('z-index', '1000');
					jQuery('#' + settings.id + '_menu').removeClass('ui-front');
				});

				//Buscar el UL del autocomplete y colocarlo tras el elemento sobre el que debe ir
				//$("#"+settings.id).after($("body > .ui-autocomplete"));


				//Buscar el UL del autocomplete y colocarlo tras el elemento sobre el que debe ir

				if (settings.menuAppendTo !== null) {
					if (jQuery(settings.menuAppendTo).length === 0) {
						alert('Es necesario especificar un selector válido para la propiedad menuAppendTo');
					} else {
						jQuery(settings.menuAppendTo).append(settings.$menu);
					}
				} else {
					if ($.rup_utils.aplicatioInPortal()) {
						//						$("div.r01gContainer").append($("body > .ui-autocomplete"));
						$('div.r01gContainer').append(settings.$menu);
					}
				}

				//Deshabilitar
				// if (settings.disabled===true) { $("#"+settings.id).rup_autocomplete("disable");
				//     if (settings.combobox)
				//         $('span').has('#'+settings.id+'_label').find("a").attr("style","display:none");
				//
				// }else if (settings.disabled===false){ //habilitar
				//     $("#"+settings.id).rup_autocomplete("enable");
				//     if (settings.combobox){
				//         $('span').has('#'+settings.id+'_label').find("a").removeAttr("style");
				//     }
				// }

				//Valor por defecto
				if (settings.defaultValue) {
					$('#' + settings.id).rup_autocomplete('search', settings.defaultValue);
				}

				//Valor pre-cargado
				if (settings.loadValue) {
					$('#' + settings.id).val(settings.loadValue);
					$('#' + settings.id + '_value').val(settings.loadValue);
				}

				// Modificar identificadores
				settings.loadObjects = settings.id + '_label';
				$('#' + settings.id).attr('id', settings.id + '_label');
				$('#' + settings.id + '_value').attr('id', settings.id);

				//eventos internos de borrado y perdida de foco
				$('#' + settings.id + '_menu').on('mousedown', function (event) {
					var selected = $('#' + settings.id).data('selected'),
					    isShowingMenu = $('.ui-autocomplete:visible').length > 0 ? true : false;
					if (!selected && isShowingMenu) {
						$('#' + settings.id).data('ieIssueScrollVisible', true);
						event.preventDefault();
					}
				});

				$('#' + settings.id + '_label').bind('keydown', function () {
					$('#' + settings.id).data('ieIssueScrollVisible', false);
				});

				$('#' + settings.id + '_label').bind('blur', function (event) {
					//Obtener datos de si viene de seleccionar elemento o si el menú de selección está desplegado
					var selected = $('#' + settings.id).data('selected'),
					    isShowingMenu = $('.ui-autocomplete:visible').length > 0 ? true : false;
					//Borrar índicador de que viene de seleccionar elemento
					$('#' + settings.id).data('selected', false);
					//Si es un evento de teclado pero no es ENTER, omitir esta función
					if (event.type === 'keydown' && event.keyCode !== 13) {
						return true;
					}
					if ($('#' + settings.id).data('ieIssueScrollVisible') === true) {
						$('#' + settings.id).focus();
						event.stopPropagation();
						$('#' + settings.id).data('ieIssueScrollVisible', false);
						return true;
					}

					var autoCompObject = $(event.currentTarget),
					    loadObjects = $('#' + settings.loadObjects).data('loadObjects');

					if (settings.getText == true) {
						if (loadObjects[autoCompObject.val()] !== undefined) {
							$('#' + settings.id).val(autoCompObject.val());
							$('#' + settings.id).attr('rup_autocomplete_label', autoCompObject.val());
						} else {
							$('#' + settings.id).val(autoCompObject.val());
							$('#' + settings.id).attr('rup_autocomplete_label', autoCompObject.val());
						}
					} else {
						if (loadObjects[$.rup_utils.normalize(autoCompObject.val())] !== undefined) {
							$('#' + settings.id).val(loadObjects[$.rup_utils.normalize(autoCompObject.val())]);
							$('#' + settings.id).attr('rup_autocomplete_label', loadObjects[$.rup_utils.normalize(autoCompObject.val())]);
						} else {

							$('#' + settings.id).val('');
							$('#' + settings.id).attr('rup_autocomplete_label', '');
							autoCompObject.val('');
							autoCompObject.autocomplete('close');
						}
					}
					//Si el evento es ENTER y viene de seleccionar un elemento o el menú se estaba mostrando, omitir resto de funciones (ej. buscar)
					if (event.type === 'keydown' && event.keyCode === 13 && (selected || isShowingMenu)) {
						return false;
					}
				});

				//se guarda la configuracion general (settings) del componente
				$('#' + settings.id + '_label').data('settings', settings);
				$('#' + settings.id + '_label').data('rup.autocomplete', {
					$hiddenField: $('#' + settings.id)
				});
				$('#' + settings.id).data('rup.autocomplete', {
					$labelField: $('#' + settings.id + '_label')
				});

				//Deshabilitar
				if (settings.disabled === true) {
					$('#' + settings.id).rup_autocomplete('disable');
				} else if (settings.disabled === false) {
					//habilitar
					$('#' + settings.id).rup_autocomplete('enable');
				}
			}
		}
	});

	//******************************************************
	// DEFINICIÓN DE LA CONFIGURACION POR DEFECTO DEL PATRON
	//******************************************************
	/**
     * Función a ejecutar en caso de producirse un error a la hora de obtener los elementos a mostrar.
     *
     * @callback module:rup_autocomplete~onLoadError
     * @param {Object} xhr - Objeto XHR que contiene la respuesta de la petición realizada.
     * @param {string} textStatus - Texto que identifica el error producido.
     * @param {Object} errorThrown - Objeto error que contiene las propiedades del error devuelto en la petición.
     */

	/**
     * @description Opciones por defecto de configuración del componente.
     *
     * @name defaults
     *
     * @property {module:rup_autocomplete~onLoadError} [onLoadError] - Función de callback a ejecutar en caso de que se produzca un error en la petición de obtención de la lista de elementos a mostrar.
     * @property {boolean} [contains=true] - Valor que determina si la búsqueda debe ser del tipo “contiene” (se buscarán elementos que contengan en cualquier posición el literal introducido) o del tipo “comienza por” (se buscarán elementos que comiencen por el literal introducido).
     * @property {string} [valueName=null] - Determina el valor de la propiedad name del campo que utilizará internamente el componente para almacenar el identificador del elemento seleccionado por el usuario. En caso de no especificarse, se tomará como valor el valor de la propiedad name del elemento sobre el cual se ha definido el componente.
     * @property {string} [labelName=null] - Determina el valor de la propiedad name del campo que utilizará internamente el componente para almacenar el texto del elemento seleccionado por el usuario. En caso de no especificarse, se tomará como valor el valor de la propiedad name del elemento sobre el cual se ha definido el componente, añadiéndole el sufijo “_label”.
     * @property {boolean} [getText=false] - En caso de ser true el componente devolverá como resultado seleccionado el texto en vez del value del elemento.
     * @property {boolean} [combobox=false] - Habilita/deshabilita el modo de funcionamiento combobox.
     * @property {number} [menuMaxHeight=false] - Determina la altura máxima que podrá tener la capa del menú desplegable antes de mostrar scroll.
     * @property {object} [menuAppendTo=null] - Permite especificar mediante un selector de jQuery el elemento del DOM al que se añadirá el menú desplegable.
     * @property {boolean} [disabled=false] - Determina si se deshabilita el componente Autocomplete sobre el input al que se aplica. De tal modo que por mucho que se interactué con el elemento no se hará una búsqueda.
     * @property {string} [defaultValue] - Valor que se cargará por defecto en el input y con el que se lanzará una búsqueda para mostrar valores propuestos
     */
	$.fn.rup_autocomplete.defaults = {
		onLoadError: null,
		contains: true,
		valueName: null,
		labelName: null,
		getText: false,
		combobox: false,
		menuMaxHeight: false,
		menuAppendTo: null,
		disabled: false,
		accentFolding: true
	};

	/**
     * Permite asociar una función que se ejecutará cuando se complete la carga de los registros correspondientes al texto de búsqueda introducido.
     * @event module:rup_autocomplete#rupAutocomplete_loadComplete
     * @example
     * $("#autocomplete").on("rupAutocomplete_loadComplete", function(event, data){});
     */

	/**
     * Permite asociar una función que se ejecutará cuando se produzca un cambio en el valor seleccionado del comonente
     * @event module:rup_autocomplete#rupAutocomplete_change
     * @example
     * $("#autocomplete").on("rupAutocomplete_change", function(event, data){});
     */

	/**
     * Permite asociar una función que se ejecutará cuando se produzca la selección de un registro de entre la lista de resultados
     * @event module:rup_autocomplete#rupAutocomplete_select
     * @example
     * $("#autocomplete").on("rupAutocomplete_select", function(event, data){});
     */

	/**
     * Permite manipular la respuesta del servidor antes de construir la lista de resultados.
     * @event module:rup_autocomplete#rupAutocomplete_beforeLoadComplete
     * @example
     * $("#autocomplete").on("rupAutocomplete_beforeLoadComplete", function(event, data){});
     */
});
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))

/***/ }),
/* 151 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*!
 * Copyright 2016 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 */

/**
 * El componente de migas muestra a los usuarios la ruta de navegación que ha seguido por la aplicación permitiéndoles volver hacia niveles superiores hasta la página de inicio.
 *
 * @summary Componente RUP BeadCrumb.
 * @module rup_breadCrumb
 * @example
 * var properties = {
 *   logOutUrl: "/x21aAppWar/logout",
 *   breadCrumb: {
 *       "patrones" : {
 *           // Literal
 *		    "i18nCaption" : "patrones",
 *		    "tabsMixto" : {"i18nCaption":"tabsMixto"},
 *		    "grid" : { "i18nCaption" : "grid" },
 *		    // Submenu
 *		    "subLevel":[
 *			   {"i18nCaption":"all", "url": "/x21aAppWar/patrones/all" },
 *			   {"i18nCaption":"accordion", "url": "/x21aAppWar/patrones/accordion" }
 *		    ]
 *	     },
 *	     "experimental" : {
 *		    // Literal
 *		    "i18nCaption" : "experimental",
 *		    "maestro_detalle" : { "i18nCaption" : "maestro_detalle" },
 *		    "mant_multi_entidad": { "i18nCaption" : "mant_multi_entidad" },"
 *        }
 *	}
 * };
 * jQuery("#x21aAppWar_migas").rup_breadCrumb(properties);
 */

/*global define */
/*global jQuery */
/*global DESTROY_XLNETS_SESSION */
/*global LOGGED_USER */

(function (factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(200)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		factory(jQuery);
	}
})(function ($) {

	$.widget('$.rup_breadCrumb', {
		/**
         * @description Opciones por defecto de configuración del widget.
         *
         * @name options
         *
         * @property {string}  [showSpeed=fast] - Propiedad que indica la velocidad de despliegue del subnivel en milisegundos o en términos de jQuery (posibles valores: “normal”,”slow”)..
         * @property {string}  [hideSpeed=''] - Propiedad que indica la velocidad de colapso del subnivel en milisegundos o en términos de jQuery (posibles valores: “normal”,”slow”)..
         * @property {boolean}  [collapsible=false] - Propiedad que indica si el primer nivel es plegable.
         * @property {Number}  [collapsedWidth=10] - Propiedad de indica el tamaño del texto cuando está colapsado (en pixeles).
         * @property {module:rup_breadCrumb~breadCrumb} breadCrumb - La estructura de las migas se define mediante un array en notación json cuyo nombre será el mismo que el identificador del elemento sobre el que se aplica el componente.
         * @property {string} [initURL] -  Define la ruta a seguir cuando se pulse sobre el primer elemento (ej. “Inicio”). Tomará como valor la ruta del contexto (contextPath) y le concatenará el literal indicado. El literal se definirá sin barra ‘/’ inicial.
         * @property {string} [i18nId] - Indica el identificador del objeto JSON para la resolución de los literales del componente. En caso de no definirse se tomará el ID del objeto sobre el que se crea el componente.
         */

		/**
         * @description Configuración de la estructura de las migas
         * @typedef breadCrumb
         *
         * @property {string}  [i18nCaption] - Texto que se mostrará como miga. Obtenido del fichero de literales de la aplicación.
         * @property {string}  [literal] - Submiga (mapeada mediante la URL). Internamente tendrá una estructura definida con los atributos i18nCaption, literales (submigas) y sublevel.
         * @property {module:rup_breadCrumb~sublevel}  [sublevel] - Define un submenú para la miga a la que se asocia.
         */

		/**
         * @description Define un submenú para la miga a la que se asocia.
         * @typedef sublevel
         *
         * @property {string} [i18nCaption] - Texto que se mostrará como elemento del menú obtenido del fichero de literales de la aplicación.
         * @property {string} [url] - Define la ruta a seguir cuando se pulse sobre el elemento.
         */
		options: {
			showSpeed: 'fast',
			hideSpeed: '',
			collapsible: false,
			collapsedWidth: 10,
			breadCrumb: $.rup.APP_RESOURCES + '.breadCrumb'
		},
		/**
         * Función encargada de crear los elementos visuales e inicializar el componente.
         *
         * @name _create
         * @function
         * @private
         */
		_create: function _create() {
			var pathname = window.location.pathname,
			    breadCrumbEntry = pathname.substring($.rup.CTX_PATH.length),
			    breadCrumbElems = breadCrumbEntry.split('/'),
			    breadCrumbSpan,

			//breadCrumbSpan = $("<span>").addClass("rup-breadCrumbs_span").text($.rup.i18nParse($.rup.i18n.base,"rup_breadCrumb.youAre")),
			ulBreadCrumb = $('<ul>').attr('id', 'rup_breadCrumbs_ul').addClass('rup-breadCrumb_main'),
			    breadCrumbStruct = null,
			    lastCrum = null,
			    initURL = this.options.initUrl !== undefined ? $.rup.CTX_PATH + this.options.initUrl : $.rup.CTX_PATH,
			    i18nId = this.options.i18nId === undefined ? this.element.attr('id') : this.options.i18nId;
			//Obtenemos la estructura del fichero que se recibe como parametro o el de por defecto del patrón
			if (this.options.breadCrumb instanceof Object) {
				breadCrumbStruct = this.options.breadCrumb;
			} else {
				$.rup.getFile(this.options.breadCrumb);
				breadCrumbStruct = $.rup.i18n[this.options.breadCrumb];
			}

			if (!window.LOGGED_USER || LOGGED_USER === 'NULL') {
				LOGGED_USER = '';
			}
			if (!window.DESTROY_XLNETS_SESSION) {
				DESTROY_XLNETS_SESSION = 'false';
			}
			if (LOGGED_USER !== '') {
				//Se añade el boton de desconexion si este fuera necesario
				if (this.options.logOutUrl !== undefined) {

					if (DESTROY_XLNETS_SESSION === 'false') {

						//función encargada de poner el icono y el literal de salida
						this.element.append($('<div id=\'logOutDiv\' class=\'rup-breadCrumb_logoutDiv\'>').append($('<a>').addClass('rup-breadCrumb_link').attr('logOutHref', this.options.logOutUrl).bind('click', function () {
							$.rup_messages('msgConfirm', {
								message: $.rup.i18nParse($.rup.i18n.base, 'rup_breadCrumb.menuDisconnectMessage'),
								title: $.rup.i18nParse($.rup.i18n.base, 'rup_breadCrumb.menuDisconnectTitle'),
								OKFunction: function OKFunction() {
									$(window).attr('location', $('#logOutLink').attr('logOutHref'));
								}
							});
						}).html($.rup.i18nParse($.rup.i18n.base, 'rup_breadCrumb.exit')).attr('id', 'logOutLink').append($('<span>').addClass('ui-icon rup-icon rup-icon-door-out rup-breadCrumb_exitImg'))));
					} else {

						//función encargada de poner el icono y el literal de desconexion
						this.element.append($('<div id=\'logOutDiv\' class=\'rup-breadCrumb_logoutDiv\'>').append($('<a>').addClass('rup-breadCrumb_link').attr('logOutHref', this.options.logOutUrl).bind('click', function () {
							$.rup_messages('msgConfirm', {
								message: $.rup.i18nParse($.rup.i18n.base, 'rup_breadCrumb.menuSecuritySystemDisconnectMessage'),
								title: $.rup.i18nParse($.rup.i18n.base, 'rup_breadCrumb.menuDisconnectTitle'),
								OKFunction: function OKFunction() {
									$(window).attr('location', $('#logOutLink').attr('logOutHref'));
								}
							});
						}).mouseover(function () {
							$(this).find('span').removeClass('rup-breadCrumb_logoutImg').addClass('rup-breadCrumb_logoutImg_active');
						}).mouseleave(function () {
							$(this).find('span').addClass('rup-breadCrumb_logoutImg').removeClass('rup-breadCrumb_logoutImg_active');
						}).html($.rup.i18nParse($.rup.i18n.base, 'rup_breadCrumb.disconnect')).attr('id', 'logOutLink').append($('<span>').addClass('rup-breadCrumb_logoutImg ui-icon'))));
					}
				}
				//se añade el span con el texto de "xxx esta aqui"
				breadCrumbSpan = $('<span>').addClass('rup-breadCrumbs_span').text(LOGGED_USER + $.rup.i18nParse($.rup.i18n.base, 'rup_breadCrumb.userAre'));
				this.element.append(breadCrumbSpan);
			} else {
				breadCrumbSpan = $('<span>').addClass('rup-breadCrumbs_span').text($.rup.i18nParse($.rup.i18n.base, 'rup_breadCrumb.youAre'));
				//se añade el span con el texto de "Usted esta aqui"
				this.element.append(breadCrumbSpan);
			}

			//se le añade el link de Incio
			ulBreadCrumb.append(this._createLI($.rup.i18nParse($.rup.i18n.base, 'rup_breadCrumb.start'), initURL));
			//nos recorremos los elementos del path y los buscamos en el fichero json de migas para crear los enlaces
			for (var i = 0; i < breadCrumbElems.length; i++) {
				//Si encontramos dentro del fichero de estructura de las migas el parte de la url
				if (breadCrumbStruct[breadCrumbElems[i]]) {
					//Generamos su miga de actualimos la estructura en la que buscar, devolviendo las estructura del nivel que se ha añadido
					breadCrumbStruct = this._createBreadCrumb(breadCrumbStruct[breadCrumbElems[i]], breadCrumbElems[i], ulBreadCrumb, i18nId);
				}
			}
			//se le añade al ultimo elemento el estilo current
			//$("li:last-child", ulBreadCrumb).addClass("rup-breadCrumb_current");
			//$("li:last", ulBreadCrumb).addClass("rup-breadCrumb_current");
			$(ulBreadCrumb.children()[ulBreadCrumb.children().length - 1]).addClass('rup-breadCrumb_current').find('img.rup-icon, span.rup-icon').remove();
			//el último elemento no es navegable
			//lastCrum = $("li:last a", ulBreadCrumb);
			lastCrum = $('a:first', $(ulBreadCrumb.children()[ulBreadCrumb.children().length - 1]));

			lastCrum.replaceWith($('<span>').text(lastCrum.text()).css({
				'font-weight': 'bold',
				'color': '#333333'
			}));
			// delete lastCrum;
			//y por ultimo se añade todo el ul a div que lo contiene
			this.element.append(ulBreadCrumb);
			ulBreadCrumb.xBreadcrumbs();
		},
		/**
         * Funcion que crea el li correspondiente de la miga accediendo al fichero de lenguage correspondiente.
         *
         * @name _createLI
         * @function
         * @private
         * @param {string} i18nCaption - Key del recurso i18n a buscar en los ficheros idiomáticos correspondientes.
         * @param {string} href - Url a la que debe navegar la miga.
         * @param {boolean} [separator] - Indica si se debe de pintar un separador posterior a la miga actual.
         * @return {object} - Devuelve el li resultante correspondiente a la miga que se está procesando.
         */
		_createLI: function _createLI(i18nCaption, href, separator) {
			var li = $('<li>'),
			    a = $('<a>').attr('href', /*$.rup.CTX_PATH + */href).text(i18nCaption);
			li.append(a);
			if (separator !== false) {
				li.append($('<span>').addClass('ui-icon rup-icon rup-icon-separator-arrow'));
			}
			return li;
		},
		/**
         * Funcion que añade al ul el li correspondiente en cada nivel y devuelve la nueva entructura en la que seguir iterando.
         *
         * @name _createBreadCrumb
         * @function
         * @private
         * @param {object} breadCrumbStruct - Objeto que contiene la estructura de migas de pan que se están creando.
         * @param {object} elem - Elemento actual que se está procesando.
         * @param {object} parentUl - Referencia al ul padre donde insertar la li correspondiente.
         * @param {string} i18nId - Key del recurso i18n a buscar en los ficheros idiomáticos correspondientes.
         * @return {object} - Devuelve la nueva entructura en la que seguir iterando.
         */
		_createBreadCrumb: function _createBreadCrumb(breadCrumbStruct, elem, parentUl, i18nId) {
			//nos recorremos la entrada correspondiente
			var createdLI,
			    subLevelUL = $('<ul>');
			if (breadCrumbStruct.i18nCaption) {
				//si tengo i18nCaption es que es elemento final
				createdLI = this._createLI($.rup.i18nParse($.rup.i18n.app[i18nId], breadCrumbStruct.i18nCaption), breadCrumbStruct.url ? $.rup.CTX_PATH + breadCrumbStruct.url : '#');
			}
			//si tengo subLevel se crearan hijo como si fuesen un menu
			if (breadCrumbStruct.subLevel) {
				//nos recorremos todos los submenus
				for (var i = 0; i < breadCrumbStruct.subLevel.length; i++) {
					//creamos cada li y se lo añadimos al ul nuevo
					subLevelUL.append(this._createLI($.rup.i18nParse($.rup.i18n.app[i18nId], breadCrumbStruct.subLevel[i].i18nCaption), breadCrumbStruct.subLevel[i].url ? breadCrumbStruct.subLevel[i].url : '#', false).css('background', 'none'));
				}
				//añadimos al li padre el nuevo ul con todos li de los sublevels
				createdLI.append(subLevelUL);
				$(createdLI).bind('mouseover', function () {
					$(this).find('a:eq(1)').focus();
				});
				createdLI.bind('keydown', function (event) {
					switch (event.keyCode) {
						case $.ui.keyCode.UP:
							var enlaces = $(this).find('li > a');
							for (var i = 0; i <= enlaces.length; i++) {
								if (enlaces[i].text === $(event.target).text()) {
									break;
								}
							}
							if ($(enlaces[i - 1]).length > 0) {
								$(enlaces[i - 1]).focus();
							} else {
								$(this).find('li > a').last().focus();
							}
							break;
						case $.ui.keyCode.DOWN:
							// var enlaces = $(this).find('li > a');
							for (var j = 0; j <= enlaces.length; j++) {
								if (enlaces[j].text === $(event.target).text()) {
									break;
								}
							}
							if ($(enlaces[i + 1]).length > 0) {
								$(enlaces[i + 1]).focus();
							} else {
								$(this).find('li > a').first().focus();
							}
							break;
						case $.ui.keyCode.ESCAPE:
							$(this).children('ul').hide();
							break;
						default:
					}
				});
			}
			parentUl.append(createdLI);
			return breadCrumbStruct;
		},
		/**
         * Modifica las opciones de configuración del componente.
         *
         * @name _setOption
         * @function
         * @private
         * @param {string} key - Nombre de la propiedad.
         * @param {*} value - Valor que se desea asignar a la propiedad.
         */
		_setOption: function _setOption() {
			$.Widget.prototype._setOption.apply(this, arguments);
		},
		/**
         * Elimina los componenes visuales generados para el widget así como las estructuras internas.
         *
         * @name destroy
         * @function
         * @example
         * // Elimina el feedback
         * jQuery("#breadCrumb").rup_breadCrumb("destroy");
         */
		destroy: function destroy() {
			$.Widget.prototype.destroy.apply(this, arguments);
		}
	});
});

/***/ }),
/* 152 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function(jQuery) {var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*!
 * Copyright 2016 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 */

/**
 *
 * Presenta un control de interación con el usuario. Se trata de extender los botones estandar del HTML para dotarles de mayores funcionalidades con las que mejorar la usabilidad de la aplicación.
 *
 * @summary Componente RUP Button.
 * @module rup_button
 * @example
 * // Botón por defecto
 * $("#idButton").rup_button({});
 * // Botón desplegable
 * $("#idButtonDrop").rup_button({
 *	  dropdown:{
 *		  dropdownListId:"dropdownHtmlList"
 *	  }
 * });
 */

/*global define */
/*global jQuery */

(function (factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(2), __webpack_require__(12)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		factory(jQuery);
	}
})(function ($) {

	//****************************************************************************************************************
	// DEFINICIÓN BASE DEL PATRÓN (definición de la variable privada que contendrá los métodos y la función de jQuery)
	//****************************************************************************************************************

	var rup_button = {};

	//Se configura el arranque de UDA para que alberge el nuevo patrón
	$.extend($.rup.iniRup, $.rup.rupSelectorObjectConstructor('rup_button', rup_button));

	//*******************************
	// DEFINICIÓN DE MÉTODOS PÚBLICOS
	//*******************************
	$.fn.rup_button('extend', {
		addButtonToDropdown: function addButtonToDropdown() {}
	});

	//*******************************
	// DEFINICIÓN DE MÉTODOS PRIVADOS
	//*******************************

	$.fn.rup_button('extend', {
		_doDropdownListById: function _doDropdownListById($dropdownButton, $container, dropdownSettings) {
			var $dropdownList = jQuery('#' + dropdownSettings.dropdownListId);
			dropdownSettings.$dropdownList = $dropdownList;

			$container.append($dropdownList);
			$dropdownButton.on('click.rup_dopdown', function (event) {
				$dropdownList.toggleClass('open');
				event.stopPropagation();
			});

			$dropdownList.on('click.rup_dopdown', function (event) {
				event.stopPropagation();
			});

			jQuery(document).on('click.rup_dopdown.close', function () {
				$dropdownList.removeClass('open');
			});
		},
		_doDropdownByDialog: function _doDropdownByDialog($dropdownButton, $container, dropdownSettings) {
			var $dropdownDialog = jQuery('#' + dropdownSettings.dropdownDialog).rup_dialog(dropdownSettings.dropdownDialogConfig);

			jQuery.extend(dropdownSettings.dropdownDialogConfig, {
				autoOpen: false,
				position: {
					my: 'right top',
					at: 'right bottom',
					of: $container
				}
			});

			// Estilos
			$dropdownDialog.parent().addClass('rup-dropdown-dialog');

			$dropdownButton.on('click', function () {
				$dropdownDialog.rup_dialog('open');
			});
		},
		_doDropdownByButtons: function _doDropdownByButtons($dropdownButton, $container, dropdownSettings) {
			var $self = this,
			    $ul = $('<ul>'),
			    $li,
			    buttons = dropdownSettings.buttons;

			$ul.attr({
				id: $self.attr('id') + '_dropdownList'
			}).addClass('rup-dropdown-option-list rup-toolbar_menuButtonContainer');

			for (var i = 0; i < buttons.length; i++) {
				$li = $('<li>');
				$self._addButtonToDropdown($li, buttons[i]);
				$ul.append($li);
			}

			$dropdownButton.on('click.rup_dopdown', function (event) {
				$ul.toggleClass('open');
				event.stopPropagation();
			});

			$ul.on('click.rup_dropdown', function (event) {
				event.stopPropagation();
			});

			jQuery(document).on('click.rup_dopdown.close', function () {
				$ul.removeClass('open');
			});

			$container.append($ul);
		},
		_addButtonToDropdown: function _addButtonToDropdown($base, obj, json_i18n) {
			//añade a la toolbar un 'mbutton' (sin botones)
			var boton = '',
			    buttonId;
			if (obj.id === undefined) {
				alert('El atributo ID es obligatorio en los MButtons.');
				boton = null;
			} else {
				buttonId = obj.id;
				// Se comprueba si el id del boton contiene el identificador de la botonera. En caso de no existir se añade al principio.
				if (buttonId.indexOf($(this).attr('id')) !== 0) {
					buttonId = $(this).attr('id') + '##' + obj.id;
				}

				boton = $('<a/>').attr('id', buttonId).text($.rup.i18nParse(json_i18n, obj.i18nCaption)).addClass('rup-toolbar_button');
				//Si no se define un estilo especial se aplica por defecto
				if (obj.css === undefined) {
					obj.css = 'rup-toolbar_menuButtonIcon';
				}
				boton.button().button('option', 'icons', {
					primary: obj.css,
					secondary: null
				});
			}

			$base.append(boton);

			//Añadir evento keydown
			this._setKeyDown(boton);

			if (obj.click) {
				//Añadir eventos
				boton.click({
					i18nCaption: obj.i18nCaption
				}, obj.click);
			}
			return boton;
		},
		_setKeyDown: function _setKeyDown(boton) {
			boton.bind('keydown', function (event) {
				var object = $(event.currentTarget),
				    objectParent = object.parent(),
				    nextObject;
				switch (event.keyCode) {
					case $.ui.keyCode.TAB:
						if (!event.shiftKey) {
							if (object.next().attr('id') !== objectParent.attr('id') + '-rightButtons') {
								//Siguiente boton
								nextObject = object.next(':focusable');
							} else {
								//Primer botón de los alineados derecha
								nextObject = object.next().children(':focusable:first');
							}

							//Navegar entre botones
							if (nextObject.size() === 1) {
								nextObject.focus();
								$.rup_toolbar.focusedExternally[objectParent.attr('id')] = true;
								return false;
							}
						}
				}
			});
		}
	});

	//*******************************
	// MÉTODO DE INICIALIZACION
	//*******************************
	$.fn.rup_button('extend', {
		/**
         * Método de inicialización del componente.
         *
         * @function _init
         * @private
         */
		_init: function _init(args) {
			var settings = $.extend(true, {}, $.fn.rup_button.defaults, $(this).data(), args[0]);

			return this.each(function () {

				var self = this,
				    $self = $(this),
				    $dropdownList,
				    $container,
				    dropdownSettings;

				self._ADAPTER = $.rup.adapter[settings.adapter];

				if (settings.fab === true) {
					$self.addClass('rup-button-fab');

					if (settings.fixed === true) {
						$self.addClass('rup-button-fixed');
					}

					if (settings.fixed === true) {
						$self.addClass('rup-button-fixed');
					}

					if (settings.list !== null || settings.layer !== null) {
						var $fabGroupDiv = $('<div>').addClass('rup-button-fab-group');
						//$self.wrap($fabListDiv);
						$self.add($('#' + settings.list)).wrapAll($fabGroupDiv);

						if (settings.list !== null) {
							$('#' + settings.list).addClass('rup-button-fab-list');
							$('button', '#' + settings.list).addClass('rup-button-fab-sm').rup_button();
						}

						if (settings.layer !== null) {
							$('#' + settings.layer).addClass('rup-button-fab-layer');
						}
					}
				}

				// Se envuelve el texto en un span
				if ($self.find(settings.labelBaseCss).length === 0) {
					$self.contents().filter(function () {
						return this.nodeType === Node.TEXT_NODE && /\S/.test(this.nodeValue);
					}).wrap($('<span>').addClass(settings.labelBaseCss));
				}
				// Se añade los css al label
				if (settings.labelCss) {
					$self.find('.' + settings.labelBaseCss).addClass(settings.labelCss);
				}

				// Se añade el icono al botón
				if (settings.iconCss) {
					$self.prepend($('<i>').attr('aria-hidden', 'true').addClass(settings.iconCss));
				}

				// Se gestiona el evento del click
				if (settings.click && $.isFunction(settings.click)) {
					$self.on('click', settings.click);
				}

				if (settings.dropdown === undefined || settings.dropdown === false) {

					// Botón normal

					$self.button(settings);
					$self.addClass('rup-button');

					if (settings.mbutton === true) {
						// Configuramos el mbutton
						var $mbuttonContainer = $self.siblings('[aria-labelledby=\'' + $self.attr('id') + '\']');
						if ($mbuttonContainer) {
							$self.on('click.rup_mbutton', function (event) {
								$mbuttonContainer.addClass('rup-mbutton-open');
								event.stopPropagation();
							});

							$mbuttonContainer.on('click.rup_mbutton', function (event) {
								event.stopPropagation();
							});

							jQuery(document).on('click.rup_mbutton.close', function () {
								$mbuttonContainer.removeClass('rup-mbutton-open');
							});
						}
					}
				} else {
					// Inicialización del dropdown
					$.extend(true, settings.dropdown, $.fn.rup_button.dropdown_defaults, args[0].dropdown);

					dropdownSettings = settings.dropdown;

					$self.addClass('rup-button rup-dropdown');

					// Wrap into div
					$container = jQuery('<div>').attr('class', 'rup-dropdown-btn-group');

					$container = $self.wrap($container).parent();

					dropdownSettings.$container = $container;

					$self.button({});

					$self.addClass('rup-dropdown');

					var $dropdownButton = $.proxy(self._ADAPTER.createDropdownButton, $self)(settings);
					// var $dropdownButton = jQuery("<button>").attr({
					// 	type: "button",
					// 	id: $self.prop("id")+"_dropdown"
					//
					// }).text("Administración de filtros").button({
					// 	icons:{
					// 		primary: dropdownSettings.dropdownIcon
					// 	},
					// 	text: false
					// }).addClass("rup-dropdown-button");

					$self.after($dropdownButton);

					if (dropdownSettings.dropdownListId) {
						$dropdownList = jQuery('#' + dropdownSettings.dropdownListId);
						dropdownSettings.$dropdownList = $dropdownList;

						$container.append($dropdownList);
						$dropdownButton.on('click.rup_dopdown', function (event) {
							$dropdownList.toggleClass('open');
							event.stopPropagation();
						});

						$dropdownList.on('click.rup_dopdown', function (event) {
							event.stopPropagation();
						});

						jQuery(document).on('click.rup_dopdown.close', function () {
							$dropdownList.removeClass('open');
						});
					} else if (dropdownSettings.dropdownDialog) {
						// Configuracion del dropdown con un RUP dialog

						jQuery.extend(dropdownSettings.dropdownDialogConfig, {
							autoOpen: false,
							position: {
								my: 'right top',
								at: 'right bottom',
								of: $container
							}
						});
						var $dropdownDialog = jQuery('#' + dropdownSettings.dropdownDialog).rup_dialog(dropdownSettings.dropdownDialogConfig);

						// Estilos
						$dropdownDialog.parent().addClass('rup-dropdown-dialog');

						$dropdownButton.on('click', function () {
							$dropdownDialog.rup_dialog('open');
						});
					} else if (dropdownSettings.buttons) {
						// Configuración del dropdown a partir de buttons
						$self._doDropdownByButtons($dropdownButton, $container, dropdownSettings);
					}
				}
			});
			// TODO : Invocación al plugin
		}
	});

	//******************************************************
	// DEFINICIÓN DE LA CONFIGURACION POR DEFECTO DEL PATRON
	//******************************************************

	/**
     * Opciones por defecto de configuración del componente.
     *
     * @function defaults
     * @property {boolean | Object} [dropdown=false] - Determina si el botón va a contar con un menú desplegable de acciones secundarias. En caso de mostrar un desplegable esta propiedad contendrá el objeto de configuración del mismo.
     */
	$.fn.rup_button.defaults = {
		adapter: 'button_bootstrap',
		dropdown: false,
		fab: false,
		fixed: false,
		list: null,
		layer: null,
		iconCss: undefined,
		labelCss: undefined,
		mbutton: false,
		click: undefined,
		labelBaseCss: 'rup-ui-button-text'
	};

	/**
     * @description Opciones por defecto del objeto de configuración del menú desplegable asociado al botón.
     *
     * @name dropdown_defaults
     *
     * @property {string} [dropdownIcon=ui-icon-triangle-1-s] - Clase css correspondiente al icono del control que despliega el menú.
     */
	$.fn.rup_button.dropdown_defaults = {

		// dropdownIcon: "ui-icon-triangle-1-s",

		dropdownIcon: 'fa fa-caret-down',
		dropdownListId: undefined,
		dropdownDialog: undefined,
		dropdownDialogConfig: {
			type: $.rup.dialog.DIV
		}
	};
});
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))

/***/ }),
/* 153 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*!
 * Copyright 2014 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 */

/**
 * Herramientas para mostrar gráficas atractivas para mostrar
 * informacón al usuario de forma atractiva.
 *
 * @summary Componente RUP Chart.
 * @module rup_chart
 * @see El componente está basado en el plugin {@link http://www.chartjs.org/|Chart.js}. Para mas información acerca de las funcionalidades y opciones de configuración pinche {@link http://www.chartjs.org/docs/|aquí}.
 */

/*global define */
/*global jQuery */
(function (factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(2), __webpack_require__(222)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		factory(jQuery);
	}
})(function ($) {

	// DEFINICIÓN BASE DEL PATRÓN (definición de la variable privada que contendrá
	// los métodos y la función de jQuery)


	var rup_chart = {};

	//Se configura el arranque de UDA para que alberge el nuevo patrón
	$.extend($.rup.iniRup, $.rup.rupSelectorObjectConstructor('rup_chart', rup_chart));

	// DEFINICIÓN DE MÉTODOS PÚBLICOS
	$.fn.rup_chart('extend', {

		/**
         * Destruye la instancia del grafico creado, limpia cualquier referencia almacenada del componente. Debe ser utilizado antes de usar el canvas para un nuevo gráfico]
         * @function destroy
         */
		destroy: function destroy() {
			var grafico = this.data('chart');
			grafico.destroy();
			this.data('chart', '');
			this.data('settings', '');
		},

		/**
         * Método utilizado para actualizar los datos de los gráficos en caliente, tanto los labels como los datos numéricos
         * @function updateData
         * @param  {Object} param - Estructura de datos de rup_chart
         * @param  {array} param.datasets - Valores númericos a representar en el gráfico
         * @param  {array} param.labels - Etiquetas de literales asociados al dataset de datos
         */
		updateData: function updateData(param) {
			var settings = this.data('settings');
			var grafico = this.data('chart');
			grafico.data.datasets = param.datasets;
			grafico.data.labels = param.labels;
			grafico.update();

			settings.data = param;
			//actualizo los datos del componente rup
			this.data('settings', settings);
		},

		/**
         * Método que actualiza los labels asociados a los datos
         * @function  updateLabels
         * @param  {array} param - Los labels a actualizar
         */
		updateLabels: function updateLabels(param) {
			var settings = this.data('settings');
			var grafico = this.data('chart');
			//actualizar grafico
			grafico.data.labels = param;
			grafico.update();
			//actualizar datos del componente
			settings.data.labels = param;
		},
		/**
         * Método que actualiza los datasets con los valores numéricos a representar por el gráfico
         * @function  updateDatasets
         * @param  {array} param - Los datasets a actualizar
         */
		updateDatasets: function updateDatasets(param) {
			var settings = this.data('settings');
			var grafico = this.data('chart');
			//actualizar grafico
			grafico.data.datasets = param;
			grafico.update();
			//actualizar datos del componente
			settings.data.datasets = param;
		},
		/**
         * Método que devuelve los datasets de datos del gráfico
         * @function  getDatasets
         * @return {object} - El conjunto de datasets de datos del componente
         */
		getDatasets: function getDatasets() {
			return this.data('settings').data.datasets;
		},

		/**
         * Método que devuelve los labels asociados a los datasets del gráfico
         * @function  getLabels
         * @return {object}  - El conjunto de labels del componente
         */
		getLabels: function getLabels() {
			return this.data('settings').data.labels;
		},
		/**
         * Método que devuelve la estructura de datos de datasets y labels que definen el gráfico
         * @function  getData
         * @return {object} - [El conjunto de datos del componente]
         */
		getData: function getData() {
			return this.data('settings').data;
		},

		/**
         * Devuelve la instancia del objeto chart.js
         * @function  getChart
         * @return {object} - la instancia del objecto
         */
		getChart: function getChart() {
			return this.data('chart');
		},

		/**
         * Devuelve el grafico en un string base64
         * @function  toBase64Image
         * @return {object} -  string en base64 del gráfico
         */
		toBase64Image: function toBase64Image() {
			var grafico = this.data('chart');
			return grafico.toBase64Image();
		}

	});

	// DEFINICIÓN DE MÉTODOS PRIVADOS

	$.fn.rup_chart('extend', {});

	// methodo INICIALIZACION
	$.fn.rup_chart('extend', {

		_init: function _init(args) {
			var settings = $.extend({}, $.fn.rup_chart.defaults, args[0]);
			settings.id = $(this).attr('id');
			$self = this;
			var ctx = document.getElementById(settings.id).getContext('2d');
			var grafico;

			if (args.length > 1) {
				$.rup.errorGestor($.rup.i18nParse($.rup.i18n.base, 'rup_global.initError') + $(this).attr('id'));
			} else {

				if (settings.options !== undefined) {
					grafico = new Chart(ctx, {
						type: settings.type,
						data: settings.data,
						options: settings.options
					});
				} else {

					grafico = new Chart(ctx, {
						type: settings.type,
						data: settings.data

					});
				}

				$self.attr('role', 'graphics-data');
				$self.addClass('rup-chart');
				//atributo ruptype
				$self.attr('ruptype', 'chart');

				//Almacenar los settings
				$('#' + settings.id).data('settings', settings);

				//almacenar el Objecto Chart
				$('#' + settings.id).data('chart', grafico);
			}
		}

	});

	//******************************************************
	// DEFINICIÓN DE LA CONFIGURACION POR DEFECTO DEL PATRON
	//******************************************************


	$.fn.rup_chart.defaults = {};
});

/***/ }),
/* 154 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function(jQuery) {var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;var _typeof = typeof Symbol === "function" && typeof Symbol.iterator === "symbol" ? function (obj) { return typeof obj; } : function (obj) { return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj; };

/*!
 * Copyright 2016 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 */

//Modificado "jquery.ui.selectmenu.js" línea 70
//Modificado "jquery.ui.selectmenu.js" línea 438-442
//Modificado "jquery.ui.selectmenu.js" línea 270 [jQuery 1.8 compatible]

//Modificado "jquery.multiselect.js" línea 53 [Estilo flecha como combos
//Añadido	 "jquery.multiselect.js" línea 65 [Id al componete]
//Modificado "jquery.multiselect.js" línea 581 [jQuery 1.8 compatible]
//Modificadro "IE Fixes" (evitar problemas con elementos deshabilitados en IE)

//Arregos para resaltado con el teclado (UDA - focus): líneas 446-448, 494-496, 519-522

/**
 * Permite al usuario recuperar un elemento de una gran lista de elementos o de varias listas dependientes de forma sencilla y ocupando poco espacio en la interfaz.
 *
 * @summary Componente RUP Combo.
 * @module rup_combo
 * @see El componente está basado en el plugin {@link http://jqueryui.com/selectmenu/|jQuery UI Selectmenu}. Para mas información acerca de las funcionalidades y opciones de configuración pinche {@link http://api.jqueryui.com/selectmenu/|aquí}.
 * @example
 * $("#idCombo").rup_combo({
 *	source : "comboSimple/remote",
 *	sourceParam : {label:"desc"+$.rup_utils.capitalizedLang(), value:"code", style:"css"}
 * });
 */

/*global define */
/*global jQuery */

(function (factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(2), __webpack_require__(20), __webpack_require__(193)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		factory(jQuery);
	}
})(function ($) {

	//****************************************************************************************************************
	// DEFINICIÓN BASE DEL PATRÁN (definición de la variable privada que contendrá los métodos y la función de jQuery)
	//****************************************************************************************************************


	var rup_combo = {};

	//Se configura el arranque de UDA para que alberge el nuevo patrón
	$.extend($.rup.iniRup, $.rup.rupSelectorObjectConstructor('rup_combo', rup_combo));

	//*******************************
	// DEFINICIÓN DE MÉTODOS PÚBLICOS
	//*******************************
	$.fn.rup_combo('extend', {
		/**
         * Método utilizado para obtener el valor del componente. Este método es el utilizado por el resto de componentes RUP para estandarizar la obtención del valor del Combo.
         *
         * @function  getRupValue
         * @return {string | number} - Devuelve el valor actual del componente seleccionado por el usuario.
         * @example
         * $("#idCombo").rup_combo("getRupValue");
         */
		getRupValue: function getRupValue(param) {
			var $self = $(this),
			    settings = $self.data('settings'),
			    retObj,
			    arrayTMP,
			    prop,
			    valueArray,
			    valueArray_length,
			    returnArray,
			    wrapObj = {},
			    name;

			name = $self.attr('name');

			if (name) {
				arrayTMP = $self.attr('name').split('.');
			}

			if (settings.submitAsJSON) {
				//					arrayTMP = $self.attr("name").split(".");
				//					prop = arrayTMP[arrayTMP.length-1];
				//					valueArray = $self.rup_combo("value");
				//					valueArray_length = valueArray.length;
				//					returnArray = [];
				//				for(var i=0; i<valueArray_length; i++){
				//					var map = {};
				//					map[prop] = valueArray[i];
				//					returnArray.push(map);
				//				}
				return jQuery.rup_utils.getRupValueAsJson(name, $self.rup_combo('value'));
			}

			retObj = settings.submitAsString ? $self.rup_combo('value').toString() : $self.rup_combo('value');

			if (arrayTMP !== undefined && arrayTMP !== null && settings.multiselect) {
				wrapObj[arrayTMP[arrayTMP.length - 1]] = retObj;
			}

			return settings.multiselect === true && arrayTMP !== undefined && arrayTMP.length > 1 && settings.legacyWrapMode === false ? wrapObj : retObj;
		},
		/**
         * Método utilizado para asignar el valor al componente. Este método es el utilizado por
  el resto de componentes RUP para estandarizar la asignación del valor al Combo.
         *
         * @function  setRupValue
         * @param {string | number} param - Valor que se va a asignar al componente.
         * @example
         * $("#idCombo").rup_combo("setRupValue", "Si");
         */
		setRupValue: function setRupValue(param) {
			var $self = $(this),
			    settings = $self.data('settings');

			//Tipo de combo
			if (this.length === 0 || !$(this).data('settings').multiselect) {
				//Simple > selectmenu
				$.data(this[0], 'setRupValue', param.toString());
				$(this).rup_combo('select', param.toString());
			} else {
				//Multiple > multiselect
				$(this).rup_combo('select', settings.readAsString === true ? param.split(',') : param);
			}
		},
		/**
         * Método que limpia el valor seleccionado en el combo. En el caso de selección múltiple los valores seleccionados.
         *
         * @function clear
         * @example
         * $("#idCombo").rup_combo("clear");
         */
		clear: function clear() {
			//Tipo de combo
			if (this.length === 0 || !$(this).data('settings').multiselect) {
				//Simple > selectmenu
				$(this).rup_combo('select');
			} else {
				//Multiple > multiselect
				$(this).multiselect('uncheckAll');
			}
		},
		/**
         * Método que lanza el evento change del componente.
         *
         * @function change
         * @example
         * $("#idCombo").rup_combo("change");
         */
		change: function change() {
			//Tipo de combo
			if (this.length === 0 || !$(this).data('settings').multiselect) {
				//Simple > selectmenu
				$(this).selectmenu('change');
			} else {
				//Multiple > multiselect
				$(this).triggerHandler('change');
			}
		},
		/**
         * Realiza una reinicizalización del estado del componente.
         *
         * @function  reset
         * @example
         * $("#idCombo").rup_combo("reset");
         */
		reset: function reset() {
			var $self = $(this);

			$self.rup_combo('select', $self.find('option[selected]').attr('value'));
		},
		/**
         * Selecciona todos los elementos en el caso de tratarse de un combo multilesección.
         *
         * @function  checkAll
         * @example
         * $("#idCombo").rup_combo("checkAll");
         */
		checkAll: function checkAll() {
			//Tipo de combo
			if ($(this).data('settings').multiselect) {
				//Multiple > multiselect
				$(this).multiselect('checkAll');
			} else {
				//Simple > selectmenu
				alert('Función no soportada.');
			}
		},
		/**
         * Selecciona el elemento enviado como parámetro. En caso de ser un numérico se selecciona por la posición (comenzando en 0) y si es un literal se selecciona por el valor. En el caso de selección múltiple el parámetro será un array.
         *
         * @function  select
         * @param {string | number | string[] | number[]} param - Parámetro utilzado para determinar los elementos a seleccionar.
         * @example
         * // Simple
         * $("#idCombo").rup_combo("select", 2);
         * // Multiple
         * $("#idCombo").rup_combo("select", [0,2]);
         */
		select: function select(param) {
			//Tipo de combo
			if (this.length === 0 || !$(this).data('settings').multiselect) {
				//Simple > selectmenu
				var elementSet = this._setElement($(this), param); //Cargar elemento
				//Si se ha cargado un elemento válido, se hace los hijos en el change solo.
				/*if (elementSet) {
    	//Lanzar cambio para que se recarguen hijos
    	var hijos = $(this).data('childs');
    	if (hijos !== undefined) {
    		for (var i = 0; i < hijos.length; i = i + 1) {
    			$('#' + hijos[i]).rup_combo('reload', hijos[i]);
    		}
    	}
    }*/
			} else {
				//Multiple > multiselect
				this._setElement($(this), param, true);
			}
		},
		/**
         * Selecciona el elemento del combo que contiene como texto el indicado. En caso de no existir el texto a buscar el combo no sufrirá cambios En el caso de selección múltiple el parámetro será un array.
         *
         * @function  selectLabel
         * @param {string | string[]} param - Parámetro utilzado para determinar los elementos a seleccionar.
         * @example
         * // Simple
         * $("#idCombo").rup_combo("selectLabel", "No");
         * // Multiple
         * $("#idCombo").rup_combo("selectLabel", ["No","Si"]);
         */
		selectLabel: function selectLabel(param) {
			//Tipo de combo
			if (this.length === 0 || !$(this).data('settings').multiselect) {
				//Simple > selectmenu
				var elementSet = this._selectLabel($(this), param, true); //Cargar elemento
				//Si se ha cargado un elemento válido
				if (elementSet) {
					//Lanzar cambio para que se recarguen hijos
					var hijos = $(this).data('childs');
					if (hijos !== undefined) {
						for (var i = 0; i < hijos.length; i = i + 1) {
							$('#' + hijos[i]).rup_combo('reload', hijos[i]);
						}
					}
				}
			} else {
				//Multiple > multiselect
				for (var i = 0; i < param.length; i++) {
					$('input[name=\'multiselect_' + $(this).attr('id') + '\'][title=\'' + param[i] + '\']').attr('checked', true);
				}
				//Actualizar literal de elementos seleccionados
				$(this).multiselect('update');
			}
		},
		/**
         * Método que devuelve el valor seleccionado en el combo. En caso de ser el valor vació, o sin selección, el valor devuelto es el asociado al “blank”. En el caso de la selección múltiple se devolverá un array.
         *
         * @function  value
         * @return {string | string[]} - Valor del elemento o elementos seleccionados.
         * @example
         * $("#idCombo").rup_combo("value");
         */
		value: function value() {
			//Tipo de combo
			if (this.length === 0 || !$(this).data('settings').multiselect) {
				//Simple > selectmenu
				return $(this).selectmenu('value');
			} else {
				//Multiple > multiselect
				var retorno = [],
				    checked = $(this).multiselect('getChecked');
				for (var i = 0; i < checked.size(); i++) {
					retorno.push($(checked[i]).val());
				}
				return retorno;
			}
		},
		/**
         * Método que devuelve el label asociado al valor seleccionado en el combo. En el caso de la selección múltiple se devolverá un array.
         *
         * @function  label
         * @return {string | string[]} - Texto del elemento o elementos seleccionado.
         * @example
         * $("#idCombo").rup_combo("label");
         */
		label: function label() {
			//Tipo de combo
			if (this.length === 0 || !$(this).data('settings').multiselect) {
				return this[0].options[$(this).selectmenu('index')].text;
			} else {
				//Multiple > multiselect
				var retorno = [],
				    checked = $(this).multiselect('getChecked');
				for (var i = 0; i < checked.size(); i++) {
					retorno.push($(checked[i]).next().text());
				}
				return retorno;
			}
		},
		/**
         * Devuelve el índice de la opción seleccionada en el combo (empezando en 0). En el caso de la selección múltiple se devolverá un array.
         *
         * @function  index
         * @return {number | number[]} - Índice del elemento o elementos seleccionados.
         * @example
         * $("#idCombo").rup_combo("index");
         */
		index: function index() {
			//Tipo de combo
			if (this.length === 0 || !$(this).data('settings').multiselect) {
				//Simple > selectmenu
				return $(this).selectmenu('index');
			} else {
				//Multiple > multiselect
				var retorno = [],
				    checked = $(this).rup_combo('value'),
				    options = $(this).find('option');
				for (var i = 0; i < options.size(); i++) {
					if ($.inArray($(options[i]).val(), checked) !== -1) {
						retorno.push(i);
					}
				}
				return retorno;
			}
		},
		/**
         * Deshabilita el combo.
         *
         * @function  disable
         * @example
         * $("#idCombo").rup_combo("disable");
         */
		disable: function disable() {
			//Tipo de combo
			var $self = $(this);
			$('#' + $(this).attr('id') + '-button').attr('tabindex', -1);

			// Añadimos el handler del evento focus para evitar que adquiera el foco cuando está deshabilitado
			$('#' + $(this).attr('id') + '-button').on('focus.rup_combo', function (event) {
				$('#' + $self.attr('id') + '-button').blur();
				return false;
			});
			if (this.length === 0 || !$(this).data('settings').multiselect) {
				//Simple > selectmenu
				$(this).selectmenu('disable');
			} else {
				//Multiple > multiselect
				$(this).multiselect('disable');
			}
		},
		/**
         * Habilita el combo.
         *
         * @function  enable
         * @example
         * $("#idCombo").rup_combo("enable");
         */
		enable: function enable() {
			//Tipo de combo
			var $self = $(this),
			    settings = $(this).data('settings');
			// Eliminamos el handler del evento focus para evitar que adquiera el foco cuando está deshabilitado
			$('#' + $(this).attr('id') + '-button').off('focus.rup_combo');

			$('#' + $(this).attr('id') + '-button').attr('tabindex', settings.tabindex ? settings.tabindex : 0);
			if (this.length === 0 || !$(this).data('settings').multiselect) {
				//Simple > selectmenu
				$(this).selectmenu('enable');
			} else {
				//Multiple > multiselect
				$(this).multiselect('enable');
			}
		},
		/**
         * Indica si el combo está deshabilitado o no.
         *
         * @function  isDisabled
         * @param {boolean} - Devuelve si el combo está deshabilitado o no.
         * @example
         * $("#idCombo").rup_combo("isDisabled");
         */
		isDisabled: function isDisabled() {
			if ($(this).attr('aria-disabled') === 'false') {
				return false;
			} else {
				return true;
			}
		},
		/**
         * Vacía y deshabilita el combo sobre el que se aplica así como todos los combos que depende de él. Su uso principalmente es interno para las peticiones remotas.
         *
         * @function  disableChild
         * @example
         * $("#idCombo").rup_combo("disableChild");
         */
		disableChild: function disableChild() {
			//Vaciar combo, deshabilitarlo
			$(this).empty().append('<option></option>').rup_combo('disable');
			//Eliminar texto que se muestra
			$('#' + $(this).attr('id') + '-button span:first-child').text('');
			//Propagar evento de selección a hijos (recursivo)
			var hijos = $(this).data('childs');
			if (hijos !== undefined) {
				for (var i = 0; i < hijos.length; i = i + 1) {
					$('#' + hijos[i]).rup_combo('disableChild');
				}
			}
		},
		/**
         * Deshabilita una opción de un combo multiselección.
         *
         * @function  disableOpt
         * @param {string} optValue - Value del option que queremos deshabilitar.
         * @example
         * $("#idCombo").rup_combo("disableOpt", "opt1");
         */
		disableOpt: function disableOpt(optValue) {
			if ($(this).data('settings').multiselect) {
				//Deshabilitar select
				this.find('[value=\'' + optValue + '\']').attr('disabled', 'disabled');

				var obj = $('#rup-multiCombo_' + $(this).attr('id')).find('[value=\'' + optValue + '\']');

				//Deshabilitar input
				obj.attr('disabled', 'disabled');

				//Estilos línea (label)
				obj.parent().css('color', 'grey');

				//Si pertenece a OptGroup y es el último en deshabilitarse > Cambiar estilos optGroupLabel
				if ($(this).data('settings').sourceGroup != undefined) {
					//Obtener inicio optGroup
					var li = obj.parentsUntil('ul').last().prevAll('li.ui-multiselect-optgroup-label').first(),
					    inputs = li.nextUntil('li.ui-multiselect-optgroup-label').find('input'),
					    allDisabled = true;
					for (var i = 0; i < inputs.length; i++) {
						if (!inputs[i].disabled) {
							allDisabled = false;
							break;
						}
					}
					if (allDisabled) {
						//Estilos optGroup
						li.css('color', 'grey');
						li.children('a').remove();
						li.children('span').not('.rup-combo_multiOptgroupLabel').remove();
					}
				}
			} else {
				alert('Función no soportada.');
			}
		},
		/**
         * Deshabilita varias opciones del combo. Las opciones se identifican mediante un array.
         *
         * @function disableOptArr
         * @param {string[]} optValueArr - Array en el que se indican los values de las opciones a deshabilitar.
         * @example
         * $("#idCombo").rup_combo("disableOptArr", ["opt1","opt2"]);
         */
		disableOptArr: function disableOptArr(optValueArr) {
			if ($(this).data('settings').multiselect) {
				for (var i = 0; i < optValueArr.length; i++) {
					$(this).rup_combo('disableOpt', optValueArr[i]);
				}
			} else {
				alert('Función no soportada.');
			}
		},
		/**
         * Habilita una opción de un combo multiselección.
         *
         * @function enableOpt
         * @param {string} enableOpt - Value del option que queremos habilitar.
         * @example
         * $("#idCombo").rup_combo("enableOpt", "opt1");
         */
		enableOpt: function enableOpt(optValue) {
			if ($(this).data('settings').multiselect) {
				//Habilitar select
				this.find('[value=\'' + optValue + '\']').removeAttr('disabled');

				var obj = $('#rup-multiCombo_' + $(this).attr('id')).find('[value=\'' + optValue + '\']');

				//Habilitar input
				obj.removeAttr('disabled');

				//Estilos línea (label)
				obj.parent().css('color', 'black');

				//Si pertenece a OptGroup y es el primero en habilitarse > Cambiar estilos optGroupLabel
				if ($(this).data('settings').sourceGroup != undefined) {
					//Obtener inicio optGroup
					var li = obj.parentsUntil('ul').last().prevAll('li.ui-multiselect-optgroup-label').first();

					//Estilos optGroup
					if (li.children('a').length === 0) {
						li.css('color', 'black');
						this._generateOptGroupLabel(li, $(this).data('settings').multiOptgroupIconText);
					}
				}
			} else {
				alert('Función no soportada.');
			}
		},
		/**
         * Habilita varias opciones del combo. Las opciones se identifican mediante un array.
         *
         * @function enableOptArr
         * @param {string[]} optValueArr - Array en el que se indican los values de las opciones a habilitar.
         * @example
         * $("#idCombo").rup_combo("enableOptArr", ["opt1","opt2"]);
         */
		enableOptArr: function enableOptArr(optValueArr) {
			if ($(this).data('settings').multiselect) {
				for (var i = 0; i < optValueArr.length; i++) {
					$(this).rup_combo('enableOpt', optValueArr[i]);
				}
			} else {
				alert('Función no soportada.');
			}
		},
		/**
         * Refresca los valores asociados al combo.
         *
         * @function  refresh
         * @example
         * $("#idCombo").rup_combo("refresh");
         */
		refresh: function refresh() {
			//Tipo de combo
			if (this.length === 0 || !$(this).data('settings').multiselect) {
				//Simple > selectmenu
				return $(this).selectmenu();
			} else {
				//Multiple > multiselect
				$(this).multiselect('refresh');

				//Modificar literal en optgroups y asociarle el evento de "seleccionar/deseleccionar"
				var multiOptgroupIconText = $(this).data('settings').multiOptgroupIconText,
				    self = this;
				$.each($('#rup-multiCombo_' + $(this).attr('id')).find('.ui-multiselect-optgroup-label'), function (index, object) {
					self._generateOptGroupLabel(object, multiOptgroupIconText);
				});

				//Titles de botones por defecto
				$('#rup-multiCombo_' + $(this).attr('id')).find('.ui-multiselect-all').attr('title', $.rup.i18n.base.rup_combo.multiselect.checkAllTitle).rup_tooltip();
				$('#rup-multiCombo_' + $(this).attr('id')).find('.ui-multiselect-none').attr('title', $.rup.i18n.base.rup_combo.multiselect.uncheckAllTitle).rup_tooltip();

				//Deseleccionar todos
				return $(this).multiselect('uncheckAll');
			}
		},
		/**
         * Realiza una recarga de los combos.
         *
         * @function   reload
         * @example
         * $("#idCombo").rup_combo("reload");
         */
		reload: function reload(id) {
			if (this.length !== 0) {
				var settings = $(this).data('settings'),
				    source,
				    setRupValue;

				//Vaciar combo, quitarle valor y deshabilitar
				$('#' + settings.id).rup_combo('disableChild');

				if (_typeof(settings.source) === 'object' || _typeof(settings.sourceGroup) === 'object') {
					//LOCAL
					source = settings.source[this._getParentsValues(settings.parent, false, settings.multiValueToken)];
					if (source !== undefined) {
						//Parsear datos
						this._parseLOCAL(source, settings, $('#' + settings.id));

						//Crear combo
						this._makeCombo(settings);

						// Evento de finalizacion de carga (necesario para trabajar con el manteniminto)
						if (settings.onLoadSuccess !== null) {
							jQuery(settings.onLoadSuccess($('#' + settings.id)));
						}

						//Lanzar cambio para que se recarguen hijos
						$('#' + settings.id).rup_combo('change');

						setRupValue = $.data($('#' + settings.id)[0], 'setRupValue');
						if (setRupValue) {
							//Vaciar combo, quitarle valor y deshabilitar
							$('#' + settings.id).rup_combo('select', setRupValue);
						}
					}
				} else if (typeof settings.source === 'string' || typeof settings.sourceGroup === 'string') {
					//REMOTO
					var data = this._getParentsValues(settings.parent, true),
					    rupCombo = this;
					if (data === null) {
						return false;
					} //Se para la petición porque algún padre no tiene el dato cargado
					var labelBlank = this._getBlankLabel(settings.id);
					$.rup_ajax({
						url: settings.source ? settings.source : settings.sourceGroup,
						data: data,
						dataType: 'json',
						contentType: 'application/json',
						beforeSend: function beforeSend(xhr) {
							rupCombo._ajaxBeforeSend(xhr, settings);
						},
						success: function success(data, textStatus, jqXHR) {
							if (settings.blank != null) {
								data.splice(0, 0, { style: "", value: settings.blank, label: labelBlank });
							}
							rupCombo._ajaxSuccess(data, settings, $('#' + settings.id));

							// Evento de finalizacion de carga (necesario para trabajar con el manteniminto)
							if (settings.onLoadSuccess !== null) {
								jQuery(settings.onLoadSuccess($('#' + settings.id)));
							}
						},
						error: function error(xhr, textStatus, errorThrown) {
							if (settings.onLoadError !== null) {
								jQuery(settings.onLoadError(xhr, textStatus, errorThrown));
							} else {
								self._ajaxError(xhr, textStatus, errorThrown);
							}
						}
					});

					//delete rupCombo;
				} else if (typeof settings.source === 'function' || typeof settings.sourceGroup === 'function') {
					//Se lanza la funcion que obtiene los valores a mostrar
					jQuery(settings.source);
					this._makeCombo(settings);
				}
			}
		},
		/**
         * Ordena alfanumericamente y en orden ascendente el combo sobre el que se aplica. Se invoca por defecto al cargarse los combos a no se que se cambie el valor del atributo ordered en la creación.
         *
         * @function  order
         * @param {boolean} orderedByValue - Indica si la búsqueda es por texto (por defecto) o si la búsqueda es por el valor.
         * @param {boolean} orderAsNumber - Indica si se debe den de ordenar como valores numéricos en vez de alfabéticos.
         * @param {boolean} skipFirst - Determina si se debe de obviar el primer elemento.
         * @example
         * $("#idCombo").rup_combo("reload");
         */
		order: function order(orderedByValue, orderAsNumber, skipFirst) {
			var combo = $(this),
			    options = $('option', combo),
			    arrVals = [],
			    skippedValue = null;

			//Comprobar que se ha obtenido el combo deseado
			if (combo.length > 0) {

				//Guardar elemento seleccionado
				var selectedVal = combo.rup_combo('value');

				//Obtener elementos combo
				options.each(function () {
					//Omitir posible opción vacía
					if (skipFirst) {
						skipFirst = false;
						skippedValue = {
							val: $(this).val(),
							text: $(this).text()
						};
						return true;
					}
					arrVals.push({
						val: $(this).val(),
						text: $(this).text(),
						clazz: $(this).attr('class')
					});
				});

				//Ordenar elementos (segun parametros, por defecto de texto)
				if (!orderedByValue) {
					if (!orderAsNumber) {
						arrVals.sort(function (a, b) {
							return a.text.localeCompare(b.text);
						});
					} else {
						arrVals.sort(function (a, b) {
							return a.text - b.text;
						});
					}
				} else {
					if (!orderAsNumber) {
						arrVals.sort(function (a, b) {
							if (a.val > b.val) {
								return 1;
							} else if (a.val == b.val) {
								return 0;
							} else {
								return -1;
							}
						});
					} else {
						arrVals.sort(function (a, b) {
							return a.val - b.val;
						});
					}
				}

				//Actualizar combo con elementos ordenados
				for (var i = 0, l = arrVals.length; i < l; i++) {
					$(options[i]).val(arrVals[i].val).text(arrVals[i].text);
					if (arrVals[i].clazz) {
						$(options[i]).attr('class', arrVals[i].clazz);
					}
				}

				//Añadir opción vacía al inicio
				if (skippedValue) {
					combo.prepend($('<option>').attr('value', skippedValue.val).text(skippedValue.text)); //Añadir opción vacía
					$(options[arrVals.length]).remove(); //Eliminar ultimo elemento
				}

				//Regenerar combo
				combo.rup_combo('refresh');

				//Restaurar elemento seleccionado
				this._setElement($(this), selectedVal, $(this).data('settings').multiselect);

				//Eliminar referencias
				// delete combo;
				// delete options;
				// delete arrVals;
			}
		}
	});

	//*******************************
	// DEFINICIÓN DE MÉTODOS PRIVADOS
	//*******************************
	$.fn.rup_combo('extend', {
		/**
         * Establece un elemento del combo por posición o valor.
         *
         * @function  _setElement
         * @private
         * @param {object} selector - Referencia al objeto jQuery del combo.
         * @param {object} param - Value correspondiente.
         * @param {boolean} multicombo - Indica si el combo permite la multiselección.
         * @param {boolean} markOptSelected - Determina si se debe marcar como seleccionado el elemento.
         */
		_setElement: function _setElement(selector, param, multicombo, markOptSelected) {
			if (multicombo !== true) {
				//Simple > selectmenu
				if (typeof param === 'string') {
					if ($('option[value=\'' + param + '\']', selector).length > 0) {
						//Controlamos que se intenten seleccionar un valor existente
						if (markOptSelected === true) {
							$('option[value=\'' + param + '\']', selector).attr('selected', 'selected');
						}
						$(selector).selectmenu('value', param);
						$(selector).trigger('_setElement');
					} else {
						return false;
					}
				} else if (typeof param === 'number') {
					if ($('option', selector).length >= param) {
						//Controlamos que se intenten seleccionar una posición existente
						if (markOptSelected === true) {
							$('option:eq(' + param + ')', selector).attr('selected', 'selected');
						}
						$(selector).selectmenu('index', param);
						$(selector).trigger('_setElement');
					} else {
						return false;
					}
				} else {
					$(selector).selectmenu('index', 0);
					$(selector).trigger('_setElement');
				}
				return true;
			} else {
				//Multiple > multiselect
				if (param !== null && (typeof param === 'undefined' ? 'undefined' : _typeof(param)) === 'object') {
					//Recorrer array parametros
					for (var i = 0; i < param.length; i++) {
						if (typeof param[i] === 'number') {
							//Acceso por posición
							$($('input[name=\'multiselect_' + $(this).attr('id') + '\']')[param[i]]).attr('checked', true);
						} else if (typeof param[i] === 'string') {
							//Acceso por valor
							$('input[name=\'multiselect_' + $(this).attr('id') + '\'][value=\'' + param[i] + '\']').attr('checked', true);
						}
					}
					// Se altualiza el valor almacenado en el objeto HTML select.
					$(selector).val(param).trigger('_setElement');
					//Actualizar literal de elementos seleccionados
					$(selector).multiselect('update');
				}
				return true;
			}
		},
		/**
         * Selecciona el elemento correspondiente al label indicado
         *
         * @function  _selectLabel
         * @private
         * @param {object} selector - Referencia al objeto jQuery del combo.
         * @param {object} param - Value correspondiente.
         */
		_selectLabel: function _selectLabel(selector, param) {
			var $option;
			for (var i = 0; i < $('option', selector).length; i = i + 1) {
				$option = jQuery('option:eq(' + i + ')', selector);
				if (jQuery('option:eq(' + i + ')', selector).text() === param) {
					$(selector).selectmenu('index', $option.prop('index'));
					return true;
				}
			}
			return false;
		},
		/**
         * Obtener la opción vacía a partir del fichero de internacionalización de la aplicación o del fichero por defecto.
         *
         * @function  _getBlankLabel
         * @private
         * @param {string} id - Identificador del fichero
         */
		_getBlankLabel: function _getBlankLabel(id) {
			var app = $.rup.i18n.app;
			if (app[id] && app[id]._blank) {
				return app[id]._blank;
			}
			return $.rup.i18n.base.rup_combo.blankNotDefined;
		},
		/**
         * Realiza el formateo de los registros que se muestran en la lista desplegable del combo.
         *
         * @function  _defaultFormatting
         * @private
         */
		_defaultFormatting: function _defaultFormatting(text) {
			var findreps = [{
				find: /^([^\-]+) \- /g,
				rep: '<span class="ui-selectmenu-item-header">$1</span>'
			}, {
				find: /([^\|><]+) \| /g,
				rep: '<span class="ui-selectmenu-item-content">$1</span>'
			}, {
				find: /([^\|><\(\)]+) (\()/g,
				rep: '<span class="ui-selectmenu-item-content">$1</span>$2'
			}, {
				find: /([^\|><\(\)]+)$/g,
				rep: '<span class="ui-selectmenu-item-content">$1</span>'
			}, {
				find: /(\([^\|><]+\))$/g,
				rep: '<span class="ui-selectmenu-item-footer">$1</span>'
			}];
			for (var i in findreps) {
				text = text.replace(findreps[i].find, findreps[i].rep);
			}
			return text;
		},
		/**
         * Obtener valores de los combos padres (si no están cargados o valores 'vacíos' devuelve null). En caso de disponer de varios combos padres se devolverán separados por un caracter delimitador.
         *
         * @function  _getParentsValues
         * @private
         * @param {object[]} array - Array con los elementos a mostrar.
         * @param {boolean} remote - Determina si la fuente de datos es remota o no.
         * @param {string} multiValueToken - Caracter separador en el caso de devolver varios elementos.
         * @return {string} - Devuelve los values seleccionados de los combos padres.
         */
		_getParentsValues: function _getParentsValues(array, remote, multiValueToken) {
			var retorno = '',
			    id,
			    texto,
			    multiValueToken = multiValueToken != null ? multiValueToken : '',
			    parentBlankValue;
			//Puede que se lance una recarga de un combo sin padres
			if (array === undefined) {
				return retorno;
			}
			for (var i = 0; i < array.length; i = i + 1) {
				id = array[i];
				//Si tiene seleccionado la primera opción puede que está seleccionada opción vacia
				if ($('#' + id).rup_combo('index') === 0) {
					texto = $('#' + id + '-button span:first-child').text();
					//Comprobar si tiene valor por defecto (bien propio o valor base por no haberlo definido)
					if (texto === $.rup.i18n.base.rup_combo.blankNotDefined || $.rup.i18n.app[id] !== undefined && texto === $.rup.i18n.app[array[i]]._blank) {
						return null;
					}
				}

				//Si el valor de algún padre es null (no se ha cargado aún)
				if ($('#' + id).data('settings').blank !== undefined && $('#' + id).data('settings').blank !== null) {
					parentBlankValue = $('#' + id).data('settings').blank;
				} else {
					parentBlankValue = '';
				}
				if ($('#' + id).val() === null || $('#' + id).val() === parentBlankValue) {
					return null;
				}

				if (remote) {
					retorno += $('#' + id).attr('name') + '=' + $('#' + id).val() + '&';
				} else {
					retorno += $('#' + id).val() + multiValueToken;
				}
			}
			//Evitar & o multiValueToken finales
			if (retorno !== '') {
				if (remote) {
					retorno = retorno.substring(0, retorno.length - 1);
				} else {
					retorno = retorno.substring(0, retorno.length - multiValueToken.length);
				}
			}
			return retorno;
		},
		/**
         * Función principal en el proceso de crear un combo. Genera todos los elementos html y objetos js internos necesarios para el funcionamiento del mismo.
         *
         * @function  _makeCombo
         * @private
         * @param {object} settings - Parametros de configuración con los que se ha inicializado el combo.
         */
		_makeCombo: function _makeCombo(settings) {

			//Opción vacía
			if (settings.blank != null) {}
			//$('#' + settings.id).prepend($('<option>').attr('value', settings.blank).text(this._getBlankLabel(settings.id)));


			//Gestionar Imagenes
			if (settings.imgs) {
				var icons = [],
				    values = [];
				$.map(settings.imgs, function (item) {
					$.each(item, function (key, elemImg) {
						if (key.indexOf('###') == -1) {
							$('#' + settings.id + ' [value=\'' + key + '\']').addClass(elemImg);
							icons[icons.length] = {
								find: '.' + elemImg
							};
						} else {
							values = key.split('###');
							$('#' + settings.id + ' > [label=\'' + values[0] + '\'] > [value=\'' + values[1] + '\']').addClass(item[values[0] + '###' + values[1]]);
							icons[icons.length] = {
								find: '.' + item[values[0] + '###' + values[1]]
							};
						}
					});
				});
				settings.icons = icons;
			}

			//Formato texto
			settings.format = settings.format === 'default' ? this._defaultFormatting : settings.format;

			//Almacenar los settings
			$('#' + settings.id).data('settings', settings);

			//Tipo de combo
			if (!settings.multiselect) {
				//Simple > selectmenu
				$('#' + settings.id).selectmenu(settings);
				if (settings.selected !== undefined && settings.selected !== '') {
					$('#' + settings.id).rup_combo("setRupValue", settings.selected);
				}
			} else {
				//Multiple > multiselect
				$('#' + settings.id).width('0'); //Iniciar a tamaño cero para que el multiselect calcule el tamaño
				settings.minWidth = settings.width;
				$('#' + settings.id).multiselect(settings);
				$('#' + settings.id).data('echMultiselect').button.attr('id', settings.id + '-button');
				$('#' + settings.id).rup_combo('refresh'); //Actualizar cambios (remotos)
				$('#' + settings.id).attr('multiple', 'multiple');

				// Asignaci�n de eventos de teclado
				var self = this;
				$('#' + settings.id).data('echMultiselect').button.on('keypress.selectmenu', function (event) {
					if (event.which > 0) {
						self._typeAheadMultiselect(event.which, 'focus', settings);
					}
					return true;
				});
				//						$("#rup-multiCombo_remoteGroup_comboHijo").on('keypress', function(event) {
				$('#' + settings.id).data('echMultiselect').menu.delegate('label', 'keydown.multiselect', function (event) {
					if (event.which > 0) {
						self._typeAheadMultiselect(event.which, 'focus', settings);
					}
					return true;
				});
			}

			//Buscar el UL del combo y colocarlo tras el elemento sobre el que debe ir
			if ($.rup_utils.aplicatioInPortal()) {
				if (!settings.multiselect) {
					//Simple > selectmenu
					$('div.r01gContainer').append($('#' + settings.id + '-menu').parent());
				} else {
					//Multiple > multiselect
					$('div.r01gContainer').append($('#rup-multiCombo_' + settings.id));
				}
			}

			//Ordenar elementos del combo
			if (settings.ordered) {
				$('#' + settings.id).rup_combo('order', settings.orderedByValue, settings.orderAsNumber, settings.blank);
			}

			//Seleccionar elemento (valor del input, valor settings combo)
			if (!settings.loadFromSelect && (settings.inputValue === undefined || settings.inputValue === '') || settings.loadFromSelect && settings.selected !== undefined) {
				this._setElement($('#' + settings.id), settings.selected, settings.multiselect, true);
			} else {
				if (settings.multiselect) {
					//Convertir inputValue en array
					if (jQuery.isArray(settings.inputValue) === false) {
						settings.inputValue = settings.inputValue.split('##');
					}
				}
				this._setElement($('#' + settings.id), settings.inputValue, settings.multiselect, true);
			}

			//Habilitar/Deshabilitar combo
			if (!settings.disabled) {
				$('#' + settings.id).rup_combo('enable');
			} else {
				$('#' + settings.id).rup_combo('disable');
			}

			//Habilitar/Deshabilitar elementos (multicombo)
			if (settings.multiselect) {
				if (settings.disabledOpts !== undefined) {
					$('#' + settings.id).rup_combo('disableOptArr', settings.disabledOpts);
				}
				if (settings.enabledOpts !== undefined) {
					$('#' + settings.id).rup_combo('enableOptArr', settings.enabledOpts);
				}
			}

			//Si los padres están deshabilitados, se deshabilita el combo
			var padres = settings.parent;
			if (padres !== undefined) {
				$.each(padres, function (index, object) {
					if ($('#' + object).rup_combo('isDisabled')) {
						$('#' + settings.id).rup_combo('disable');
						return;
					}
				});
			}

			//Clases para el pijama
			if (settings.rowStriping) {
				if (!settings.multiselect) {
					$('#' + settings.id + '-menu li:nth-child(2n+1):not(.ui-selectmenu-group)').addClass('rup-combo_odd');
					$('#' + settings.id + '-menu li:nth-child(2n):not(.ui-selectmenu-group)').addClass('rup-combo_even');
					$('#' + settings.id + '-menu li:nth-child(2n+1).ui-selectmenu-group').addClass('rup-combo_groupOdd');
					$('#' + settings.id + '-menu li:nth-child(2n).ui-selectmenu-group').addClass('rup-combo_groupEven');
				} else {
					$('#rup-multiCombo_' + settings.id + ' .ui-multiselect-checkboxes li:nth-child(2n+1):not(.ui-multiselect-optgroup-label)').addClass('rup-combo_odd');
					$('#rup-multiCombo_' + settings.id + ' .ui-multiselect-checkboxes li:nth-child(2n):not(.ui-multiselect-optgroup-label)').addClass('rup-combo_even');
					$.each($('#rup-multiCombo_' + settings.id + ' .ui-multiselect-optgroup-label'), function (index, value) {
						index % 2 == 0 ? $(value).addClass('rup-combo_groupOdd') : $(value).addClass('rup-combo_groupEven');
					});
				}
			}
		},
		/**
         * Procesa el conjunto de registros devueltos por una petición sobre un origen de datos local.
         *
         * @function  _parseLOCAL
         * @private
         * @param {object[]} array - Array de registros obtenidos a partir del origen de datos.
         * @param {object} settings - Objeto de propiedades de configuración con el que se ha inicializado el componente.
         * @param {jQuery} html - Referencia al objeto jQuery que contiene los elementos.
         */
		_parseLOCAL: function _parseLOCAL(array, settings, html) {
			var imgs = settings.imgs ? settings.imgs : [],
			    label,
			    value;
			for (var i = 0; i < array.length; i = i + 1) {
				label = value = array[i];
				if (_typeof(array[i]) === 'object') {
					//multi-idioma
					if (array[i].i18nCaption) {
						label = $.rup.i18nParse($.rup.i18n.app[settings.i18nId], array[i].i18nCaption);
					} else {
						label = array[i].label;
					}
					value = array[i].value;
				}
				if (array[i] != undefined && array[i].style) {
					imgs[imgs.length] = {};
					imgs[imgs.length - 1][value] = array[i].style;
					settings.imgs = imgs;
				}
				html.append($('<option>').attr('value', value).text(settings.showValue ? value + settings.token + label : label));
			}
		},
		/**
         * Procesa el conjunto de registros devueltos por una petición sobre un origen de datos local. Este método se emplea en el caso de existir agrupación de los mismos.
         *
         * @function  _parseOptGroupLOCAL
         * @private
         * @param {object[]} arrayGroup - Array de registros obtenidos a partir del origen de datos.
         * @param {object} settings - Objeto de propiedades de configuración con el que se ha inicializado el componente.
         * @param {jQuery} html - Referencia al objeto jQuery que contiene los elementos.
         */
		_parseOptGroupLOCAL: function _parseOptGroupLOCAL(arrayGroup, settings, html) {
			var optGroup,
			    self = this;

			for (var i = 0; i < arrayGroup.length; i = i + 1) {
				optGroup = arrayGroup[i];
				$.each(optGroup, function (key, elemGroup) {
					if (typeof elemGroup[0] !== 'string') {
						html.append($('<optgroup>').attr('label', $.rup.i18nParse($.rup.i18n.app[settings.i18nId], key)));
					} else {
						html.append($('<optgroup>').attr('label', key));
					}
					html = $(html).children('optgroup:last-child');
					self._parseLOCAL(elemGroup, settings, html);
					html = $(html).parent();
				});
			}
		},
		/**
         * Procesa el conjunto de registros devueltos por una petición sobre un origen de datos remoto.
         *
         * @function  _parseREMOTE
         * @private
         * @param {object[]} array - Array de registros obtenidos a partir del origen de datos.
         * @param {object} settings - Objeto de propiedades de configuración con el que se ha inicializado el componente.
         * @param {jQuery} html - Referencia al objeto jQuery que contiene los elementos.
         * @param {string} optGroupKey - Identificador del optionGroup al que pertenece.
         */
		_parseREMOTE: function _parseREMOTE(array, settings, html, optGroupKey) {
			var remoteImgs = settings.imgs ? settings.imgs : [],
			    item,
			    setRupValue;
			for (var i = 0; i < array.length; i = i + 1) {
				item = array[i];
				if (item.style) {
					remoteImgs[remoteImgs.length] = {};
					if (optGroupKey == null) {
						remoteImgs[remoteImgs.length - 1][item.value] = item.style;
					} else {
						remoteImgs[remoteImgs.length - 1][optGroupKey + '###' + item.value] = item.style;
					}
					settings.imgs = remoteImgs;
				}
				html.append($('<option>').attr('value', item.value).text(settings.showValue ? item.value + settings.token + item.label : item.label));
			}
		},
		/**
         * Procesa el conjunto de registros devueltos por una petición sobre un origen de datos remoto. Este método se emplea en el caso de existir agrupación de los mismos.
         *
         * @function  _parseOptGroupREMOTE
         * @private
         * @param {object[]} arrayGroup - Array de registros obtenidos a partir del origen de datos.
         * @param {object} settings - Objeto de propiedades de configuración con el que se ha inicializado el componente.
         * @param {jQuery} html - Referencia al objeto jQuery que contiene los elementos.
         */
		_parseOptGroupREMOTE: function _parseOptGroupREMOTE(arrayGroup, settings, html) {
			var optGroup,
			    self = this;
			for (var i = 0; i < arrayGroup.length; i = i + 1) {
				optGroup = arrayGroup[i];
				$.each(optGroup, function (key, elemGroup) {
					html.append($('<optgroup>').attr('label', key));
					html = $(html).children('optgroup:last-child');
					self._parseREMOTE(elemGroup, settings, html, key);
					html = $(html).parent();
				});
			}
		},
		/**
         * Prepara la petición AJAX que se va a realizar para obtener los registros a partir de un origen remoto. Se añaden las cabeceras RUP correspondientes para realizar la serialización json de manera correcta.
         *
         * @function  _ajaxBeforeSend
         * @private
         * @param {object} xhr - Objeto xhr que se va a enviar en la petición
         * @param {object} settings - Objeto de propiedades de configuración con el que se ha inicializado el componente.
         * @param {jQuery} html - Referencia al objeto jQuery que contiene los elementos.
         */
		_ajaxBeforeSend: function _ajaxBeforeSend(xhr, settings, html) {
			//Crear combo (vacío) y deshabilitarlo
			if (html !== undefined) {
				$('#' + settings.id).replaceWith(html);
			} //Si no es 'reload' se debe inicializar vacío
			this._makeCombo(settings);
			$('#' + settings.id).rup_combo('disable');

			//LOADING...
			$('#' + settings.id + '-button span:first-child').addClass('rup-combo_loadingText').text($.rup.i18n.base.rup_combo.loadingText);
			var icon = $('#' + settings.id + '-button span:last-child');
			$(icon).removeClass('ui-icon-triangle-1-s');
			$(icon).addClass('rup-combo_loading');

			//Cabecera RUP
			xhr.setRequestHeader('RUP', $.toJSON(settings.sourceParam));
		},
		/**
         * Procesa la respuesta de la petición AJAX en el caso de que esta haya finalizado correctamente.
         *
         * @function  _ajaxSuccess
         * @private
         * @param {object} data - Objeto enviado en la respuesta.
         * @param {object} settings - Objeto de propiedades de configuración con el que se ha inicializado el componente.
         * @param {jQuery} html - Referencia al objeto jQuery que contiene los elementos.
         */
		_ajaxSuccess: function _ajaxSuccess(data, settings, html) {
			//UNLOADING...
			$('#' + settings.id + '-button span:first-child').removeClass('rup-combo_loadingText').text('');
			var icon = $('#' + settings.id + '-button span:last-child');
			$(icon).removeClass('rup-combo_loading');
			$(icon).addClass('ui-icon-triangle-1-s');

			//Vaciar combo
			$('#' + settings.id).empty();

			//Cargar combo (si se reciben datos)
			if (data.length > 0) {
				if (settings.source) {
					this._parseREMOTE(data, settings, html);
				} else {
					settings.ordered = false;
					this._parseOptGroupREMOTE(data, settings, html);
				}

				//Crear combo
				this._makeCombo(settings);

				setRupValue = $.data($('#' + settings.id)[0], 'setRupValue');
				if (setRupValue) {
					//Vaciar combo, quitarle valor y deshabilitar
					$('#' + settings.id).rup_combo('select', setRupValue);
				} else {
					//Lanzar cambio para que se recarguen hijos
					$('#' + settings.id).rup_combo('change');
				}
			} else {
				$('#' + settings.id).append('<option></option>');
			}
		},
		/**
         * Procesa la respuesta de la petición AJAX en el caso de que se haya producido un error en la misma.
         *
         * @function  _ajaxError
         * @private
         * @param {object} xhr - Objeto xhr enviado en la respuesta.
         * @param {string} textStatus - Cadena identificadora del error que se ha producido en la petición.
         * @param {object} errorThrown - Objeto error correspondiente al que se ha producido en la petición.
         * @param {object} settings - Objeto de propiedades de configuración con el que se ha inicializado el componente.
         */
		_ajaxError: function _ajaxError(xhr, textStatus, errorThrown, settings) {
			if (xhr.responseText !== null) {
				$.rup.showErrorToUser(xhr.responseText);
			} else {
				$.rup.showErrorToUser($.rup.i18n.base.rup_combo.ajaxError);
			}
		},
		/**
         * Crea la etiqueta correspondiente a una agrupación.
         *
         * @function  _generateOptGroupLabel
         * @private
         * @param {jQuery} object - Referencia al propio componente.
         * @param {string} multiOptgroupIconText - Prefijo de los option group.
         */
		_generateOptGroupLabel: function _generateOptGroupLabel(object, multiOptgroupIconText) {
			//Texto A > SPAN
			$(object).append($('<span />').text($(object).children('a').text()).addClass('rup-combo_multiOptgroupLabel'));
			$(object).children('a').remove();

			$(object).append($('<span />').text(' ['));
			$(object).append($('<a />').text(multiOptgroupIconText ? $.rup.i18n.base.rup_combo.multiselect.optGroupSelect : '').prepend($('<span />').addClass('ui-icon ui-icon-check rup-combo_multiOptgroupIcon')).attr('title', $.rup.i18n.base.rup_combo.multiselect.optGroupSelectTitle).rup_tooltip({
				applyToPortal: true
			}).click(function () {
				var inputs = $(object).nextUntil('li.ui-multiselect-optgroup-label').find('input');
				for (var i = 0; i < inputs.length; i++) {
					if (!inputs[i].disabled) {
						inputs[i].checked = false;
					}
				}
			}));
			$(object).append($('<span />').text(' | '));
			$(object).append($('<a />').text(multiOptgroupIconText ? $.rup.i18n.base.rup_combo.multiselect.optGroupDeselect : '').prepend($('<span />').addClass('ui-icon ui-icon-closethick rup-combo_multiOptgroupIcon')).attr('title', $.rup.i18n.base.rup_combo.multiselect.optGroupDeselectTitle).rup_tooltip({
				applyToPortal: true
			}).click(function () {
				var inputs = $(object).nextUntil('li.ui-multiselect-optgroup-label').find('input');
				for (var i = 0; i < inputs.length; i++) {
					if (!inputs[i].disabled) {
						inputs[i].checked = true;
					}
				}
			}));
			$(object).append($('<span />').text(' ]'));
		},
		/**
         * Devuelve los li de los elementos seleccionados en un combo multiselección.
         *
         * @function  _selectedOptionLiMultiselect
         * @private
         * @param {object} settings - Objeto de propiedades de configuración con el que se ha inicializado el componente.
         * @return {jQuery | jQuery[]} - Objetos jQuery con referencias a los elementos seleccionados.
         */
		_selectedOptionLiMultiselect: function _selectedOptionLiMultiselect(settings) {
			var multiselectSettings = $('#' + settings.id).data('echMultiselect');
			return this._optionLis.eq(this._selectedIndex());
		},
		/**
         * Devuelve el li del elemento que contiene el foco en un combo multiselección.
         *
         * @function  _focusedOptionLiMultiselect
         * @private
         * @param {object} settings - Objeto de propiedades de configuración con el que se ha inicializado el componente.
         * @return {jQuery} - Objeto jQuery con referencia al elemento que contiene el foco.
         */

		_focusedOptionLiMultiselect: function _focusedOptionLiMultiselect(settings) {
			var multiselectSettings = $('#' + settings.id).data('echMultiselect');
			//				return this.list.find('.' + this.widgetBaseClass + '-item-focus');
			var $elem = undefined;

			jQuery.each(multiselectSettings.inputs, function (index, elem) {
				if ($(elem).parent().has('.ui-state-hover')) {
					$elem = $(elem);
				}
			});

			return $elem;
		},
		/**
         * Procesa los eventos de introducción de caracteres de teclado por parte del usuario.
         *
         * @function  _typeAheadMultiselect
         * @private
         * @param {number} code - Código ASCII correspondiente al caracter introducido por el usuario.
         * @param {object} eventType - Objeto event de jQuery.
         * @param {object} settings - Objeto de propiedades de configuración con el que se ha inicializado el componente.
         */
		_typeAheadMultiselect: function _typeAheadMultiselect(code, eventType, settings) {
			var self = this,
			    c = String.fromCharCode(code).toLowerCase(),
			    matchee = null,
			    nextIndex = null;

			// Clear any previous timer if present
			if (self._typeAhead_timer) {
				window.clearTimeout(self._typeAhead_timer);
				self._typeAhead_timer = undefined;
			}

			// Store the character typed
			self._typeAhead_chars = (self._typeAhead_chars === undefined ? '' : self._typeAhead_chars).concat(c);

			// Detect if we are in cyciling mode or direct selection mode
			if (self._typeAhead_chars.length < 2 || self._typeAhead_chars.substr(-2, 1) === c && self._typeAhead_cycling) {
				self._typeAhead_cycling = true;

				// Match only the first character and loop
				matchee = c;
			} else {
				// We won't be cycling anymore until the timer expires
				self._typeAhead_cycling = false;

				// Match all the characters typed
				matchee = self._typeAhead_chars;
			}

			// We need to determine the currently active index, but it depends on
			// the used context: if it's in the element, we want the actual
			// selected index, if it's in the menu, just the focused one
			// I copied this code from _moveSelection() and _moveFocus()
			// respectively --thg2k
			var selectedIndex = (eventType !== 'focus' ? this._selectedOptionLiMultiselect(settings).data('index') : this._focusedOptionLiMultiselect(settings).data('index')) || 0;

			var multiselectSettings = $('#' + settings.id).data('echMultiselect');

			for (var i = 0; i < multiselectSettings.inputs.length; i++) {
				var thisText = multiselectSettings.inputs.eq(i).next('span').text().substr(0, matchee.length).toLowerCase();

				if (thisText === matchee) {
					if (self._typeAhead_cycling) {
						if (nextIndex === null) nextIndex = i;

						if (i > selectedIndex) {
							nextIndex = i;
							break;
						}
					} else {
						nextIndex = i;
					}
				}
			}

			if (nextIndex !== null) {
				// Why using trigger() instead of a direct method to select the
				// index? Because we don't what is the exact action to do, it
				// depends if the user is typing on the element or on the popped
				// up menu
				multiselectSettings.inputs.eq(i).parent().trigger('mouseover');
				multiselectSettings.inputs.eq(i).trigger(eventType);
				//					jQuery.each(multiselectSettings.inputs, function(index, elem){
				//					    if($(elem).parent().has(".ui-state-hover") && index!==i){
				//					    	$(elem).parent().removeClass("ui-state-hover");
				//					    }
				//					});
				//					multiselectSettings.inputs.eq(i).parent().addClass("ui-state-hover");
				//					multiselectSettings.inputs.eq(i).parent().focus();
			}

			self._typeAhead_timer = window.setTimeout(function () {
				self._typeAhead_timer = undefined;
				self._typeAhead_chars = undefined;
				self._typeAhead_cycling = undefined;
			}, settings.typeAhead);
		},
		/**
         * Método de inicialización del componente.
         *
         * @function  _init
         * @private
         * @param {object} args - Parámetros de inicialización del componente.
         */
		_init: function _init(args) {
			if (args.length > 1) {
				$.rup.errorGestor($.rup.i18nParse($.rup.i18n.base, 'rup_global.initError') + $(this).attr('id'));
			} else {
				//Se recogen y cruzan las paremetrizaciones del objeto
				var settings = $.extend({}, $.fn.rup_combo.defaults, args[0]),
				    html,
				    loadAsLocal = false,
				    isValidableElem = false,
				    attrsJson = {},
				    attrs;

				//Se recoge el tabindex indicado en el elemento
				settings.tabindex = $(this).attr('tabindex');

				//Sobreescribir literales por defecto para multicombo
				$.extend($.ech.multiselect.prototype.options, $.rup.i18n.base.rup_combo.multiselect);

				//Se carga el identificador del padre del patron
				settings.id = $.rup_utils.escapeId($(this).attr('id'));
				settings.name = $(this).attr('name');

				//Si no se recibe identificador para el acceso a literales se usa el ID del objeto
				if (!settings.i18nId) {
					settings.i18nId = settings.id;
				}

				//Guardar valor del INPUT
				settings.inputValue = $('#' + settings.id).val() === null ? $('#' + settings.id).prop('value') : $('#' + settings.id).val();

				attrs = $(this).prop('attributes');

				for (var i = 0; i < attrs.length; i++) {
					attrsJson[attrs[i].name] = attrs[i].value;
				}

				$.extend(attrsJson, {
					name: settings.name,
					ruptype: 'combo'
				});

				//Contenido combo
				html = $('<select>').attr(attrsJson).addClass('rup_combo');

				if ($(this).hasClass('validableElem')) {
					isValidableElem = true;
					html.addClass('validableElem');
				}
				if ($(this).hasClass('customelement')) {
					isValidableElem = true;
					html.addClass('customelement');
				}

				if (settings.firstLoad === null && $(this).is('select') && settings.loadFromSelect) {
					loadAsLocal = true;
				}

				if (settings.parent) {
					//DEPENDIENTE
					//Guardar referencia a hijos en cada uno de los padres (propagación de carga)
					$.map(settings.parent, function (item) {
						var childsArray = $('#' + item).data('childs') === undefined ? [] : $('#' + item).data('childs');
						childsArray[childsArray.length] = settings.id;
						$('#' + item).data('childs', childsArray);
					});

					if (settings.loadFromSelect === false) {
						if (settings.firstLoad !== null) {
							this._parseLOCAL(settings.firstLoad, settings, html);
						}
						//Crear combo y deshabilitarlo
						$('#' + settings.id).replaceWith(html);
					} else {
						$('#' + settings.id).attr('ruptype', 'combo').removeClass().addClass('rup_combo');
						if (isValidableElem) {
							$('#' + settings.id).removeClass().addClass('validableElem');
						}
					}

					this._makeCombo(settings);

					if (!($(this).is('select') && settings.loadFromSelect)) {
						$('#' + settings.id).rup_combo('disable');
					} else {
						var options = $(this).find('option');
						var vacio = true;
						for (var i = 0; i < options.size(); i = i + 1) {
							if ($(options[i]).attr('value') !== '') {
								vacio = false;
								break;
							}
						}
						if (vacio) {
							$('#' + settings.id).rup_combo('disable');
						}
					}

					//Almacenar los settings
					$('#' + settings.id).data('settings', settings);

					//Comprobar si los padres ya tienen datos seleccionados (si son LOCALES puede suceder)
					if (this._getParentsValues(settings.parent) !== null && settings.firstLoad === null && settings.loadFromSelect === false) {
						$('#' + settings.id).rup_combo('reload', settings.id);
					}
				} else if (_typeof(settings.source) === 'object' || _typeof(settings.sourceGroup) === 'object' || loadAsLocal) {
					//LOCAL
					//Parsear datos
					if (settings.loadFromSelect === false) {
						if (settings.source) {
							this._parseLOCAL(settings.firstLoad !== null ? settings.firstLoad : settings.source, settings, html);
						} else {
							settings.ordered = false;
							this._parseOptGroupLOCAL(settings.firstLoad !== null ? settings.firstLoad : settings.sourceGroup, settings, html);
						}
						$('#' + settings.id).replaceWith(html);
					} else {
						$('#' + settings.id).attr('ruptype', 'combo').removeClass().addClass('rup_combo');
						if (isValidableElem) {
							$('#' + settings.id).removeClass().addClass('validableElem');
						}
					}

					//Crear combo
					this._makeCombo(settings);

					if (settings.onLoadSuccess !== null) {
						jQuery(settings.onLoadSuccess($('#' + settings.id)));
					}

					//Almacenar los settings
					$('#' + settings.id).data('settings', settings);
				} else if (typeof settings.source === 'string' || typeof settings.sourceGroup === 'string') {
					//REMOTO
					var url = settings.source ? settings.source : settings.sourceGroup,
					    rupCombo = this,
					    self = this;
					var labelBlank = this._getBlankLabel(settings.id);
					$.rup_ajax({
						url: url,
						dataType: 'json',
						contentType: 'application/json',
						beforeSend: function beforeSend(xhr) {
							rupCombo._ajaxBeforeSend(xhr, settings, html);
						},
						success: function success(data, textStatus, jqXHR) {
							if (settings.blank != null) {
								data.splice(0, 0, { style: "", value: settings.blank, label: labelBlank });
							}
							rupCombo._ajaxSuccess(data, settings, html);
							if (settings.onLoadSuccess !== null) {
								jQuery(settings.onLoadSuccess($('#' + settings.id)));
							}
						},
						error: function error(xhr, textStatus, errorThrown) {
							if (settings.onLoadError !== null) {
								jQuery(settings.onLoadError(xhr, textStatus, errorThrown));
							} else {
								self._ajaxError(xhr, textStatus, errorThrown);
							}
						}
					});
					// delete rupCombo;

					//Almacenar los settings
					$('#' + settings.id).data('settings', settings);
				} else if (typeof settings.source === 'function' || typeof settings.sourceGroup === 'function') {
					jQuery(settings.source);
					this._makeCombo(settings);

					//Almacenar los settings
					$('#' + settings.id).data('settings', settings);
				}

				//Asociar evento CHANGE para propagar cambios a los hijos
				$('#' + settings.id).bind('change', function (event, ui) {
					// En caso de modificarse el valor del select, se actualiza el valor del rup.combo (con esta accion se recargan tambien los hijos)
					if (!settings.multiselect) {
						$('#' + settings.id).rup_combo('select', $('#' + settings.id).val());
					} else {
						$('#' + settings.id).rup_combo('select', $('#' + settings.id).rup_combo('getRupvalue'));
					}

					//Lanzar cambio para que se recarguen hijos, si los tiene
					var hijos = $(this).data('childs');
					if (hijos !== undefined) {
						for (var i = 0; i < hijos.length; i = i + 1) {
							$('#' + hijos[i]).rup_combo('reload', hijos[i]);
						}
					}
				});

				//Borrar referencia
				// delete html;

				//Ocultar posibles elementos de fechas/horas
				$('#' + settings.id).next('a').click(function (event) {
					$('#ui-datepicker-div').hide();
				});
			}
		}
	});

	//******************************************************
	// DEFINICIÓN DE LA CONFIGURACION POR DEFECTO DEL PATRON
	//******************************************************

	/**
     * Función a ejecutar en caso de producirse un error a la hora de obtener los elementos a mostrar.
     *
     * @callback jQuery.rup_combo~onLoadError
     * @param {Object} xhr - Objeto XHR que contiene la respuesta de la petición realizada.
     * @param {string} textStatus - Texto que identifica el error producido.
     * @param {Object} errorThrown - Objeto error que contiene las propiedades del error devuelto en la petición.
     */

	/**
     * Función a ejecutar en caso de producirse un error a la hora de obtener los elementos a mostrar.
     *
     * @callback jQuery.rup_combo~onLoadSuccess
     * @param {jQuery} self - Referencia al objeto jQuery del propio combo.
     */

	/**
     * @description Opciones por defecto de configuración del componente.
     *
     * @name defaults
     *
     * @property {jQuery.rup_combo~onLoadError} [onLoadError] - Función de callback a ejecutar en caso de que se produzca un error en la petición de obtención de la lista de elementos a mostrar.
     * @property {number} [width=200] - Determina el tamaño del combo. Su valor por defecto es 200 para la selección simple. En el caso de selección múltiple su declaración es obligatoria.
     * @property {string} [blank=null] - Se utiliza para declarar un valor independiente de la lógica del negocio. En ocasiones se representa como “Seleccione un elemento.
     * @property {string} [style=dropdown] - Tipo de visualización de la lista de opciones del combo.
     * @property {boolean} [showValue=false] - Determina si el combo debe mostrar el valor asociado concatenado al literal (sólo selección simple).
     * @property {string} [token="|"] - Define el separador a utilizar cuando se muestra el valor asociado al combo concatenado al literal.
     * @property {string} [multiValueToken="##"] - Define el separador a utilizar en combos enlazados locales.
     * @property {boolean} [ordered=true] - Indica si el combo debe ordenarse.
     * @property {boolean} [orderedByValue=false] - Indica si el la ordenación del combo debe realizarse por el valor de los elementos en lugar de por el texto.
     * @property {jQuery.rup_combo~onLoadSuccess} [onLoadSuccess=null] - Función de callback a ejecutar en el caso de que la petición de carga de datos se haya producido correctamente.
     * @property {boolean} [loadFromSelect=false] - Determina si se debe de utilizar los elementos option del elemento html sobre el que se inicializa el componente para inicializar los datos del elemento.
     * @property {boolean} [multiselect=false] - Indica si el combo permite la selección múltiple.
     * @property {boolean} [multiOptgroupIconText=false] - Indica si se desea que en la selección múltiple con grupos, el nombre del grupo tenga descripción en los iconos para seleccionar/deseleccionar los elementos del grupo.
     * @property {boolean} [submitAsString=false] - Indica si el envío de los elementos seleccionados en la selección múltiple se realiza como un literal separados por coma.
     * @property {boolean} [submitAsJSON=false] - Indica si el envío de los elementos seleccionados en la selección múltiple se realiza como un array JSON donde el nombre del mapa será el nombre del combo. En el caso de que el nombre contenga notación dot se tomará el último literal. Ej: [{id:1}, {id:2}, …].
     * @property {boolean} [readAsString=false] - Determina si la asignación de un valor inicial se va a realizar a partir de un string con los ids de los elementos separados por comas en vez de un array de json.
     * @property {boolean} [rowStriping=false] - Indica si se debe aplicar un estilo diferente a las filas pares e impares para poder distinguirlas mediante un color diferente.
     * @property {number} [typeAhead=false] - Especifica en milisegundos el tiempo de espera que toma el componente antes de procesar los eventos de escritura realizados por el usuario.
     * @property {number} [legacyWrapMode=false] - Determina si se emplea el método obsoleto a la hora de empaquetar en objetos json los elementos seleccionados. Su propósito es mantener la retrocompatibilidad.
     */
	$.fn.rup_combo.defaults = {
		onLoadError: null,
		width: 200,
		blank: null,
		style: 'dropdown',
		showValue: false,
		token: '|',
		multiValueToken: '##',
		ordered: true,
		orderedByValue: false,
		firstLoad: null,
		onLoadSuccess: null,
		loadFromSelect: false,
		multiselect: false,
		multiOptgroupIconText: true,
		submitAsString: false,
		submitAsJSON: false,
		readAsString: false,
		rowStriping: false,
		typeAhead: 1000,
		legacyWrapMode: false
	};
});
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))

/***/ }),
/* 155 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;var _typeof = typeof Symbol === "function" && typeof Symbol.iterator === "symbol" ? function (obj) { return typeof obj; } : function (obj) { return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj; };

/*!
 * Copyright 2016 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 */

/**
 * Permite al usuario introducir y seleccionar una fecha, tanto de forma manual como visual, moviéndose fácilmente por días, meses y años. Además, para minimizar las posibilidades de introducir una fecha incorrecta, ofrece al usuario ayudas y sugerencias de formato. <br/><br/> Además, este sistema permite la introducción de fechas independiente de dispositivo y flexible, ya que tanto los usuarios avanzados como los novatos podrán utilizarlo sin problemas.
 *
 * @summary Componente RUP Date.
 * @module rup_date
 * @see El componente está basado en el plugin {@link http://jqueryui.com/datepicker/|jQuery UI DatePicker}. Para mas información acerca de las funcionalidades y opciones de configuración pinche {@link http://api.jqueryui.com/datepicker/|aquí}.
 * @example
 * // Ejemplo de selector de fecha simple.
 * $("#fecha").rup_date({
 *	labelMaskId : "fecha-mask",
 *	showButtonPanel : true,
 *	showOtherMonths : true,
 *	noWeekend : true
 * });
 *
 * // Ejemplo de selector de fecha simple que permite seleccionar tres fechas.
 * $("#fecha_multi").rup_date({
 *	multiSelect: 3,
 *	labelMaskId : "fecha_multi-mask",
 *	buttonImage : "/rup/css/images/exclamation.png"
 * });
 *
 * // Ejemplo de selectores de fecha desde y hasta
 * $.rup_date({
 *	from: "desde",
 *	to: "hasta",
 *	//Resto igual que en date
 *	labelMaskId : "intervalo-mask",
 *	numberOfMonths: 3
 * });
 */

/*global define */
/*global jQuery */

(function (factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(2), __webpack_require__(19), __webpack_require__(192)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		factory(jQuery);
	}
})(function ($) {

	//****************************************************************************************************************
	//DEFINICIÓN BASE DEL PATRÓN (definición de la variable privada que contendrá los métodos y la función de jQuery)
	//****************************************************************************************************************


	var rup_date = {};
	var rup_interval = {};

	//Se configura el arranque de UDA para que alberge el nuevo patrón
	$.extend($.rup.iniRup, $.rup.rupSelectorObjectConstructor('rup_date', rup_date));
	$.extend($.rup.iniRup, $.rup.rupObjectConstructor('rup_date', rup_interval));

	//*******************************
	// DEFINICIÓN DE MÉTODOS PÚBLICOS
	//*******************************

	$.fn.rup_date('extend', {
		/**
     * Método utilizado para obtener el valor del componente. Este método es el utilizado por el resto de componentes RUP para estandarizar la obtención del valor del componente fecha.
     *
     * @function  getRupValue
     * @return {string | array} - Devuelve el valor actual del componente seleccionado por el usuario.
     * @example
     * $("#idDate").rup_date("getRupValue");
     */
		getRupValue: function getRupValue() {
			if ($(this).data('datepicker').settings.datetimepicker) {

				var tmpDate = $(this).datepicker('getDate');

				if (tmpDate === null || tmpDate.toString() === 'Invalid Date') {
					return '';
				}
				var fechaArray = $(this).rup_date('getDate').split(' ');

				var formattedTime = $(this).data('datepicker').settings.timeFormat;
				var separator = formattedTime[2];
				var tmpTime = fechaArray[1].split(separator).join(":");
				var dateFormat = $(this).data('datepicker').settings.dateFormat;

				return $.datepicker.formatDate(dateFormat, tmpDate) + ' ' + tmpTime;
			} else {
				return $(this).rup_date('getDate');
			}
		},
		/**
             * Método utilizado para asignar el valor al componente. Este método es el utilizado por
    el resto de componentes RUP para estandarizar la asignación del valor al componente fecha.
             *
             * @function  setRupValue
             * @param {string | array} param - Valor que se va a asignar al componente. En caso de tratarse de uan configuración en la que se permite seleccionar varias fechas se indicará mediante un array.
             * @example
             * // Fecha simple
             * $("#idDate").rup_date("setRupValue", "21/06/2015");
             * // Varias fechas
             * $("#idDate").rup_date("setRupValue", ["21/06/2015", "22/06/2015"]);
             */
		setRupValue: function setRupValue(param) {

			if ($(this).data('datepicker').settings.datetimepicker) {
				var fechaArray = param.split(' ');
				var tmpTime = undefined;
				var tmpDate = new Date(fechaArray[0]);
				if (fechaArray[1] !== undefined) {
					var time = "01/01/2000 " + fechaArray[1];
					tmpTime = new Date(time);
				}

				if (tmpDate.toString() === 'Invalid Date') {
					return '';
				}

				var formattedTime = '';
				if (tmpTime !== undefined) {
					var dateObj = {
						hour: tmpTime.getHours(),
						minute: tmpTime.getMinutes(),
						second: tmpTime.getSeconds()
					};
					tmpDate.setHours(dateObj.hour + "", dateObj.minute + "", dateObj.second + "");
					formattedTime = $.timepicker._formatTime(dateObj, $(this).data('datepicker').settings.timeFormat);
				}

				$(this).datepicker('setTime', tmpDate);

				$(this).val(fechaArray[0] + ' ' + formattedTime);
			} else {
				$(this).val(param);
			}
		},
		/**
     * Elimina el componente de la pantalla. En caso de tener máscara también se restaura el label con un texto vacío
     *
     * @function  destroy
     * @example
     * $("#idDate").rup_date("destroy");
     */
		destroy: function destroy() {
			//Eliminar máscara
			var labelMaskId = $(this).data('datepicker').settings.labelMaskId;
			if (labelMaskId) {
				$('#' + labelMaskId).text('');
			}
			//delete labelMaskId;
			$(this).datepicker('destroy');
		},
		/**
     * Deshabilita el componente en pantalla no pudiendo introducirse ninguna fecha ni se despliega el calendario.
     *
     * @function  disable
     * @example
     * $("#idDate").rup_date("disable");
     */
		disable: function disable() {
			$(this).datepicker('disable');
		},
		/**
     * Habilita el componente permitiendo introducir la fecha tanto mediante teclado como mediante el desplegable del calendario
     *
     * @function  enable
     * @example
     * $("#idDate").rup_date("enable");
     */
		enable: function enable() {
			$(this).datepicker('enable');
		},
		/**
     * Indica si el componente se encuentra deshabilitado o no.
     *
     * @function  isDisabled
     * @return {boolean} - Devuelve si el componente está deshabilitado o no.
     * @example
     * $("#idDate").rup_date("isDisabled");
     */
		isDisabled: function isDisabled() {
			return $(this).datepicker('isDisabled');
		},
		/**
     * Oculta el calendario para seleccionar una fecha.
     *
     * @function  hide
     * @example
     * $("#idDate").rup_date("hide");
     */
		hide: function hide() {
			$(this).datepicker('hide');
		},
		/**
     * Muestra el calendario para seleccionar una fecha.
     *
     * @function  show
     * @example
     * $("#idDate").rup_date("show");
     */
		show: function show() {
			$(this).datepicker('show');
		},
		/**
     * Devuelve la fecha seleccionada, si no se ha seleccionado nada devuelve vacío.
     *
     * @function  getDate
     * @return {date} - Fecha seleccionada.
     * @example
     * $("#idDate").rup_date("getDate");
     */
		getDate: function getDate() {
			return $(this).val();
		},
		/**
     * Establece la fecha del componente. El parámetro debe ser un objeto date.
     *
     * @param {date} - Fecha que se desea asignar.
     * @example
     * $("#idDate").rup_date("setDate", new Date());
     */
		setDate: function setDate(date) {
			$(this).datepicker('setDate', date);
		},
		/**
     * Refresca el calendario desplegado por si ha habido algún cambio.
     *
     * @function  refresh
     * @example
     * $("#idDate").rup_date("refresh");
     */
		refresh: function refresh() {
			$(this).datepicker('refresh');
		},
		/**
     * Permite consultar y modificar la configuración del componente.
     *
     * @function option
     * @param {string | object} optionName - Nombre de la propiedad que se desea gestionar o objeto de compuesto de varias propiedades.
     * @param  [value] - Corresponde al valor de la propiedad en caso de haberse especificado el nombre de la misma en el primér parámetro.
     * @example
     * // Consultar una propiedad
     * $("#idCombo").rup_date("option", "multiselect");
     * // Establecer una propiedad
     * $("#idCombo").rup_date("option", "multiselect", 2);
     * // Establecer varias propiedad
     * $("#idCombo").rup_date("option", {datetimepicker:true, multiselect:3});
     */
		option: function option(optionName, value) {
			$(this).datepicker('option', optionName, value);
		}
		//No soportadas: widget, dialog
	});

	//*******************************
	// DEFINICIÓN DE MÉTODOS PRIVADOS
	//*******************************
	$.fn.rup_date('extend', {

		_init: function _init(args) {
			if (args.length > 1) {
				$.rup.errorGestor($.rup.i18nParse($.rup.i18n.base, 'rup_global.initError') + $(this).attr('id'));
			} else {
				//Se recogen y cruzan las paremetrizaciones del objeto
				var settings = $.extend({}, $.fn.rup_date.defaults, args[0]);

				// Se carga el adapter
				this._ADAPTER = $.rup.adapter[settings.adapter];

				//Eventos
				//Guardar referencia
				settings._onClose = settings.onClose;
				settings.onClose = function (event, ui) {
					if (settings._onClose !== undefined) {
						settings._onClose(event, ui);
					}
					if (!$.rup.browser.isIE) {
						$(this).focus();
					}
				};

				if (settings.multiSelect) {
					settings._beforeShow = settings.beforeShow;
					settings.beforeShow = function (ui, obj) {
						if (settings._beforeShow !== undefined) {
							settings._beforeShow(ui, obj);
						}

						var $dateInput = $(ui),
						    dateValue = $dateInput.attr('value'),
						    dates;

						if (dateValue !== undefined && dateValue !== '') {
							dates = dateValue.split(',');
							if (dates.length > 1) {
								$dateInput.multiDatesPicker('addDates', dates);
							}
						}
					};
				}

				//Se carga el identificador del padre del patron
				settings.id = $(this).attr('id');

				$(this).attr('ruptype', 'date');

				//Carga de propiedades/literales
				//var literales = $.extend($.rup.i18n.base.rup_time,$.rup.i18n.base.rup_date);
				var literales = $.rup.i18n.base.rup_date;
				for (var key in literales) {
					if (settings[key] === undefined) {
						settings[key] = literales[key];
					}
				}

				//Mostrar máscara
				if (settings.labelMaskId) {
					if (settings.datetimepicker) {
						if (settings.showSecond) {
							$('#' + settings.labelMaskId).text($.rup.i18nParse($.rup.i18n.base, 'rup_date.maskDateTimeSec') + ' ');
						} else {
							$('#' + settings.labelMaskId).text($.rup.i18nParse($.rup.i18n.base, 'rup_date.maskDateTime') + ' ');
						}
					} else {
						$('#' + settings.labelMaskId).text($.rup.i18nParse($.rup.i18n.base, 'rup_date.mask') + ' ');
					}
				}

				//Mostrar placeholder
				if (settings.placeholderMask) {
					if (settings.datetimepicker) {
						if (settings.showSecond) {
							$(this).attr('placeholder', $.rup.i18nParse($.rup.i18n.base, 'rup_date.maskDateTimeSec') + ' ');
						} else {
							$(this).attr('placeholder', $.rup.i18nParse($.rup.i18n.base, 'rup_date.maskDateTime') + ' ');
						}
					} else {
						$(this).attr('placeholder', $.rup.i18nParse($.rup.i18n.base, 'rup_date.mask') + ' ');
					}
				}

				//Fix: Arregla problema tamaño capa cuando selector es DIV y meses es array [X,1]
				if ($('#' + settings.id).is('div') && settings.numberOfMonths[1] === 1) {
					if (!settings.showWeek) {
						$('#' + settings.id).css('width', '15.4em');
					} else {
						$('#' + settings.id).css('width', '17.1em');
					}
				}

				//Sab-Dom deshabilitados
				if (settings.noWeekend) {
					settings.beforeShowDay = $.datepicker.noWeekends;
				}

				this._ADAPTER.initIconTrigger(settings);

				//Datepicker
				if (!settings.multiSelect) {
					if (settings.datetimepicker) {
						if (settings.showSecond) {
							this.attr('maxlength', '19');
						} else {
							this.attr('maxlength', '16');
						}
						//i18n datetimepicker
						settings.timeText = $.rup.i18nParse($.rup.i18n.base, 'rup_time.timeText');
						settings.hourText = $.rup.i18nParse($.rup.i18n.base, 'rup_time.hourText');
						settings.minuteText = $.rup.i18nParse($.rup.i18n.base, 'rup_time.minuteText');
						settings.secondText = $.rup.i18nParse($.rup.i18n.base, 'rup_time.secondText');
						$('#' + settings.id).datetimepicker(settings);
					} else {
						this.attr('maxlength', '10');
						$('#' + settings.id).datepicker(settings);
					}
				} else {
					var maxlength = 0;
					if (typeof settings.multiSelect === 'number') {
						settings.mode = {
							modeName: 'normal',
							options: {
								maxPicks: settings.multiSelect
							}
						};
						maxlength = 10 * settings.multiSelect + (settings.multiSelect - 1);
					} else if (_typeof(settings.multiSelect) === 'object') {
						settings.mode = {
							modeName: 'daysRange',
							options: {
								autoselectRange: settings.multiSelect
							}
						};
						maxlength = settings.multiSelect[1] - settings.multiSelect[0];
						maxlength = 10 * maxlength + (maxlength - 1);
					}
					this.attr('maxlength', maxlength);

					//Sobreescribir valores por defecto para multiselección
					$.datepicker._defaults.dateFormat = settings.dateFormat;
					$('#' + settings.id).multiDatesPicker(settings);

					//Permitir separador de intervalos (coma)
					$(this).keypress(function (event) {
						if (event.charCode === 44) {
							var value = $(event.currentTarget).val(),
							    cursorPosStart = event.originalEvent.originalTarget.selectionStart,
							    cursorPosEnd = event.originalEvent.originalTarget.selectionEnd;
							begin = value.substring(0, cursorPosStart), end = value.substring(cursorPosEnd);
							//Si no tiene tamaño máximo o tiene selección de caracteres
							if (value.length < $(event.currentTarget).attr('maxlength') || cursorPosStart !== cursorPosEnd) {
								$(event.currentTarget).val(begin + ',' + end);
								event.originalEvent.originalTarget.selectionStart = cursorPosStart + 1;
								event.originalEvent.originalTarget.selectionEnd = cursorPosStart + 1;
							}
						}
					});
				}

				$.proxy(this._ADAPTER.postConfigure, $(this))(settings);

				//Ajuste para el comportamiento de portales
				if ($.rup_utils.aplicatioInPortal() && !$('#' + settings.id).is('div')) {
					$('.r01gContainer').append($('.ui-datepicker:not(.r01gContainer .ui-datepicker)'));
				}

				// Se aplica el tooltip
				$(this).parent().find('[title]').rup_tooltip({
					'applyToPortal': true
				});

				//Deshabilitar
				if (settings.disabled) {
					$('#' + settings.id).rup_date('disable');
				}
			}
		}
	});
	$.rup_date('extend', {
		_init: function _init(args) {
			if (args.length > 1) {
				$.rup.errorGestor($.rup.i18nParse($.rup.i18n.base, 'rup_global.initError') + $(this).attr('id'));
			} else {
				//Se recogen y cruzan las paremetrizaciones del objeto (duplicado de objetos)
				var settings = $.extend({}, $.fn.rup_date.defaults, args[0]),
				    from_settings = $.extend(true, {}, settings),
				    to_settings = $.extend(true, {}, settings);

				//Gestionar intervalo del campo desde
				from_settings.onClose = function (dateText, inst) {
					//				        var endDateTextBox = $("#"+settings.to);
					var $endDateTextBox = $('#' + settings.to),
					    $startDateTextBox = inst.input,
					    startDateData,
					    toDateData,
					    testStartDate,
					    testEndDate;

					if ($endDateTextBox.attr('value') != '') {
						startDateData = $startDateTextBox.data('datepicker');
						toDateData = $endDateTextBox.data('datepicker');

						if (startDateData.settings.timepicker !== undefined) {
							testStartDate = new Date(startDateData.selectedYear, startDateData.selectedMonth, startDateData.selectedDay, startDateData.settings.hour, startDateData.settings.minute, startDateData.settings.second);
						} else {
							testStartDate = new Date(startDateData.selectedYear, startDateData.selectedMonth, startDateData.selectedDay);
						}
						if (toDateData.settings.timepicker !== undefined) {
							testEndDate = new Date(toDateData.selectedYear, toDateData.selectedMonth, toDateData.selectedDay, toDateData.settings.hour, toDateData.settings.minute, toDateData.settings.second);
						} else {
							testEndDate = new Date(toDateData.selectedYear, toDateData.selectedMonth, toDateData.selectedDay);
						}

						if (testStartDate > testEndDate) {
							$endDateTextBox.attr('value', dateText);
						}
					} else if (!settings.autoFillToField) {
						$endDateTextBox.attr('value', dateText);
					}
					if (settings.onClose !== undefined) {
						settings.onClose(dateText, inst);
					}
				};
				from_settings.onSelect = to_settings.beforeShow = function (selectedDate) {
					var start = $('#' + settings.from).datetimepicker('getDate'),
					    startDate;

					startDate = start !== null ? new Date(start.getTime()) : null;

					$('#' + settings.to).datetimepicker('option', 'minDate', startDate);

					if (settings.datetimepicker) {
						$('#' + settings.to).datetimepicker('option', 'minDateTime', startDate);
					}

					if (settings.onSelect !== undefined) {
						settings.onSelect(selectedDate);
					}
				};

				//Gestionar intervalo del campo hasta
				to_settings.onClose = function (dateText, inst) {
					var $startDateTextBox = $('#' + settings.from),
					    $endDateTextBox = inst.input,
					    startDateData,
					    toDateData,
					    testStartDate,
					    testEndDate;

					if ($startDateTextBox.attr('value') != '') {
						startDateData = $startDateTextBox.data('datepicker');
						toDateData = $endDateTextBox.data('datepicker');

						if (startDateData.settings.timepicker !== undefined) {
							testStartDate = new Date(startDateData.selectedYear, startDateData.selectedMonth, startDateData.selectedDay, startDateData.settings.hour, startDateData.settings.minute, startDateData.settings.second);
						} else {
							testStartDate = new Date(startDateData.selectedYear, startDateData.selectedMonth, startDateData.selectedDay);
						}
						if (toDateData.settings.timepicker !== undefined) {
							testEndDate = new Date(toDateData.selectedYear, toDateData.selectedMonth, toDateData.selectedDay, toDateData.settings.hour, toDateData.settings.minute, toDateData.settings.second);
						} else {
							testEndDate = new Date(toDateData.selectedYear, toDateData.selectedMonth, toDateData.selectedDay);
						}

						if (testStartDate > testEndDate) {
							$startDateTextBox.attr('value', dateText);
						}
					} else if (!settings.autoFillFromField) {
						$startDateTextBox.attr('value', dateText);
					}
					if (settings.onClose !== undefined) {
						settings.onClose(dateText, inst);
					}
				};
				to_settings.onSelect = from_settings.beforeShow = function (selectedDate) {
					var end = $('#' + settings.to).datetimepicker('getDate'),
					    endDate;

					endDate = end !== null ? new Date(end.getTime()) : null;

					$('#' + settings.from).datetimepicker('option', 'maxDate', endDate);

					if (settings.datetimepicker) {
						$('#' + settings.from).datetimepicker('option', 'maxDateTime', endDate);
					}

					if (settings.onSelect !== undefined) {
						settings.onSelect(selectedDate);
					}
				};

				//Lanzar componente
				$('#' + settings.from).rup_date(from_settings);
				$('#' + settings.to).rup_date(to_settings);
			}
		}
	});

	//******************************************************
	// DEFINICIÓN DE LA CONFIGURACION POR DEFECTO DEL PATRON
	//******************************************************
	/**
   * A continuación se muestran los posibles parámetros de configuración que recibe el componente.
   * @name options
   * @property {boolean} [datetimepicker=false] - Indica si el componente permite introducir la hora además de la fecha
   * @property {boolean} [disabled=false] - Indica si el componente debe aparecer deshabilitado o no.
   * @property {string} altField - Identificador de un campo adicional para que muestre la fecha en otro formato.
   * @property {string} altFormat - Formato que debe seguir la fecha en el campo adicional
   * @property {string} appendText - Texto que se puede añadir detrás de cada campo de fecha. Se recomienda el uso del atributo “labelMaskId” que se detalla a continuación en lugar de este atributo.
   * @property {string} labelMaskId - Identificador del label que contendrá la máscara que indica el formato de la fecha.
   * @property {string} mask - Texto empleado para la máscara de la fecha. Su valor por defecto se obtiene del fichero de idioma.
   * @property {boolean} [autoSize=false] - Booleano que indica si el campo para la fecha se tiene que redimensionar automáticamente para adaptares al texto introducido
   * @property {string} buttonImage - Ruta a la imagen que se muestra junto al campo de la fecha y que sirve para desplegar el calendario pulsando sobre ella. Por defecto se muestra una imagen incluida en los ficheros de RUP.
   * @property {string} buttonText - Texto alternativo de la imagen que se muestra junto al campo de la fecha. Su valor por defecto se obtiene del fichero de idioma.
   * @property {boolean} [changeMonth=true] - Indica si se muestra un combo que en la cabecera que facilita el cambio de mes
   * @property {boolean} [changeYear=true] - indica si se muestra un combo que en la cabecera que facilita el cambio de año
   * @property {string} [closeText] - Texto a mostrar en el botón que se muestra en el panel inferior (requiere el activarlo mediante el atributo showButtonPanel) para cerrar el calendario. Su valor por defecto se obtiene del fichero de idioma.
   * @property {string} currentText - Texto a mostrar en el botón que se muestra en el panel inferior (requiere el activarlo mediante el atributo showButtonPanel) para seleccionar la fecha actual en el calendario. Su valor por defecto se obtiene del fichero de idioma.
   * @property {string} dateFormat - Formato de la fecha a introducir (ej: dd/mm/yy para 20/01/2011). Su valor por defecto se obtiene del fichero de idioma.
   * @property {array} dayNames - Literales para los días [array]. Su valor por defecto se obtiene del fichero de idioma.
   * @property {array} dayNamesMin - Literales para los días (mínimos) [array]. Su valor por defecto se obtiene del fichero de idioma.
   * @property {array} 	dayNamesShort - Literales para los días (corto) [array]. Su valor por defecto se obtiene del fichero de idioma.
   * @property {date|string|number} defaultDate  - fecha que se muestra por defecto destacada cuando se abre el calendario y no hay ninguna fecha escrita. El tipo de parámetro puede ser Date, String o Number (ver la explicación al final de este apartado). Por defecto se destaca la fecha del día.
   * @property {string|number} [duration=normal] - Velocidad a la que aparece el calendario en pantalla (animación). Sus posibles valores son: ‘slow’, ‘normal’ y ‘fast’ o un valor numérico (milisegundos).
   * @property {number} firstDay -Número que indica en qué día de la semana debe empezar el calendario. El valor 0 equivale al domingo, el 1 al lunes y así sucesivamente.
   * @property {boolean} [hideIfNoPrevNext=false] - Oculta los enlaces de siguiente/anterior mes cuando no se puede navegar. En caso contrario, los enlaces se deshabilitan
   * @property {date|string|number} maxDate - Fecha máxima que se puede seleccionar (límite superior). Por defecto no hay límite.
   * @property {date|string|number} minDate - Fecha mínima que se puede seleccionar (límite inferior). Por defecto no hay límite.
   * @property {array} monthNames - Literales para los meses [array]. Su valor por defecto se obtiene del fichero de idioma.
   * @property {array} monthNamesShort - Literales para los meses (corto) [array]. Su valor por defecto se obtiene del fichero de idioma.
   * @property {string} nextText - Literal a mostrar en el enlace de siguiente. Su valor por defecto se obtiene del fichero de idioma.
   * @property {number|array} [numberOfMonths=1] -Puede definirse como un numérico (ej. 2) o como un array indicando filas y columnas (ej. [2, 3]).
   * @property {string} prevText - Literal a mostrar en el enlace de anterior. Su valor por defecto se obtiene del fichero de idioma.
   * @property {boolean} [selectOtherMonths=false] - Permite seleccionar los días del meses anterior/posterior del que se muesta. Requiere que estén activos dichos días mediante el parámetro showOtherMonths
   * @property {string} [showAnim=show] - Indica el tipo de animación que se emplea para mostrar el calendario en pantalla.
   * @property {boolean} [showButtonPanel=false] - Indica si se muestran los botones de la parte inferior (hoy y cerrar).
   * @property {number} [showCurrentAtPos=0] - Cuando se muestra más de un mes, indica la posición que ocupa el mes actual.
   * @property {boolean} showMonthAfterYear - Intercambia la posición del mes y del año en la cabecera del calendario.
   * @property {object} showOptions - Objeto que determina las propiedades de la animación del calendario. Para más información ver la siguiente  {@link http://api.jqueryui.com/datepicker/#option-showAnim|página} .
   * @property {boolean} [showWeek=false] - Indica si se debe mostrar el número de semana.
   * @property {number} stepMonths - Indica el número de meses que se avanzan al pulsar los enlaces anterior/siguiente.
   * @property {string} weekHeader - Literal que aparece sobre los números de semana. Su valor por defecto se obtiene del fichero de idioma.
   * @property {string}  yearRange - Determina el rango de años a mostrar en el combo de la cabecera del calendario. No implica que sea el límite de años a seleccionar. Se debe definir como un literal que indique el inicio y el fin separado por dos puntos ej. 2001:2011. Puede usarse el la letra c como valor actual restándole y sumándole un numérico ej. c-10:c+10. Su valor por defecto es c-10:c+10
   * @property {string} yearSuffix - Texto adicional a mostrar en la cabecera del calendario junto al año.
   * @property {booelan} 	[noWeekend=false] - Indica si se muestran o no los días del fin de semana (sábado y domingo).
   * @property {string} from - Indica el selector del campo inicial en los intervalos de fechas
   * @property {string} to - Indica el selector del campo final en los intervalos de fechas
   * @property {array|number} 	multiselect - Atributo que indica si se permite la multiselección de fechas y el modo en el que se aplica.
   * @property {boolean} [autoFillToField=true] - Atributo que indica si se auto rellena el campo hasta
   * @property {boolean} [autoFillFromField=true] - Atributo que indica si se auto rellena el campo desde
 
   */

	$.fn.rup_date.defaults = {
		adapter: 'date_bootstrap',
		placeholderMask: false,
		datetimepicker: false,
		multiSelect: false,
		changeMonth: true,
		changeYear: true,
		noWeekend: false,
		showSecond: true,
		autoFillToField: true,
		autoFillFromField: true
	};

	//EVENTOS

	/**
   * Función que se lanza cuando se crea el calendario. La invocación es automática por parte del componente
   * @event module:rup_date#create
   * @example
   * $(selector).rup_date({ create: function(){...} });
   */

	/**
   * Permite asociar una función que se ejecutará antes de que se muestre el calendario. Los parámetros recibidos son el campo del calendario y la instancia del componente.
   * @event module:rup_date#beforeShow
   * @example
   * $(selector).rup_date({ beforeShow: function(input, inst){...} });
   */

	/**
   * Permite asociar una función que se ejecutará cuando se cambie de mes o de año en el calendario. Los parámetros recibidos son el año y mes seleccionados así como la instancia del componente
   * @event module:rup_date#onChangeMonthYear
   * @example
   * $(selector).rup_date({onChangeMonthYear: function(y,m,inst){...} });
   */

	/**
   * Permite asociar una función que se ejecutará cuando se seleccione un valor del calendario. Los parámetros recibidos son la fecha seleccionada (texto) y la instancia del componente.
   * @event module:rup_date#onSelect
   * @example
   * $(selector).rup_date({ onSelect: function(dateText, inst){...} });
   */

	/**
   * Permite asociar una función que se ejecutará cuando se oculte el calendario. Los parámetros recibidos son la fecha seleccionada (texto) y la instancia del componente.
   *  @event module:rup_date#onClose
   *  @example
   *  $(selector).rup_date({ onClose: function(dateText, inst){...} });
   */
});

/***/ }),
/* 156 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function(jQuery) {/*!
 * Copyright 2016 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 */

/**
 * @fileOverview Implementa el patrón RUP Dav.
 *  
 * @version 2.4.8
 */

/*global jQuery */

(function ($) {

	//*****************************************************************************************************************
	// DEFINICIÓN BASE DEL PATRÓN (definición de la variable privada que contendrá los métodos y la función de jQuery)
	//*****************************************************************************************************************
	/**
    * Permite al usuario editar online documentos almacenados en el servidor de aplicaciones.
    *
    * @summary Componente RUP Dav.
    * @namespace jQuery.rup_dav
    * @memberOf jQuery
    * @tutorial rup_dav
    * @example
    * jQuery.rup_dav.editOnline({
 *	url:"webdavServlet/webdav.doc",
 *	xlnetsAuth:true,
 *	downloadOnError:true,
 *	alternateDownloadURL:"../upload?fileName=webdav.doc"
 * });
    */
	jQuery.rup_dav = {};

	//Se configura el arranque de UDA para que alberge el nuevo patrón
	//	$.extend($.rup.iniRup, $.rup.rupSelectorObjectConstructor("rup_dav", rup_dav));

	$.extend(jQuery.rup_dav, {
		/**
         * TODO
         *
         * @name jQuery.rup_dav#editOnline
         * @function
         */
		editOnline: function editOnline(args) {
			var url, settings;

			if (typeof args === 'string') {
				settings = jQuery.extend({}, jQuery.rup_dav.defaults, { url: args });
			} else {
				settings = jQuery.extend({}, jQuery.rup_dav.defaults, args);
			}

			// Se comprueba y completa la url
			jQuery.rup_dav._checkUrl(settings);

			// En caso de necesitarse se aplica
			if (settings.xlnetsAuth) {
				jQuery.rup_dav._xlnetsAuth(settings);
			}

			if ($.browser.msie === true) {
				jQuery.rup_dav._editOnlineIE(settings);
			} else {
				jQuery.rup_dav._editOnlineFF(settings);
			}
		}
	});

	$.extend(jQuery.rup_dav, {
		_checkUrl: function _checkUrl(settings) {
			var tmpUrl = '';

			if (settings.url.indexOf(location.protocol) === -1) {
				// Se añade la sección de protocolo (http, https...)
				tmpUrl += location.protocol + '//';

				if (settings.url.indexOf(location.host) === -1) {
					// Se añade la sección del host
					tmpUrl += location.host;
				}

				if (settings.url.indexOf(CTX_PATH) === -1) {
					// Se añade la sección del host
					tmpUrl += CTX_PATH;
				}

				settings.url = tmpUrl + settings.url;
			}
		},
		_xlnetsAuth: function _xlnetsAuth(settings) {
			var n38UidSesionCookie = $.rup_utils.readCookie('n38UidSesion'),
			    n38DominioUidCookie = $.rup_utils.readCookie('n38DominioUid'),
			    urlParams = {};

			if (n38UidSesionCookie !== undefined && n38UidSesionCookie !== null && n38UidSesionCookie !== '') {
				jQuery.extend(true, urlParams, { n38UidSesion: n38UidSesionCookie });
			}

			if (n38DominioUidCookie !== undefined && n38DominioUidCookie !== null && n38DominioUidCookie !== '') {
				jQuery.extend(true, urlParams, { n38DominioUid: n38DominioUidCookie });
			}

			if (!jQuery.isEmptyObject(urlParams)) {
				settings.url += '?' + settings.xlnetsAuthParam + '=' + jQuery.rup_utils.base64.encode(jQuery.param(urlParams));
			}
		},
		_editOnlineIE: function _editOnlineIE(settings) {
			var obj;
			// Gestión para Internet Explorer
			try {
				// Microsoft Office 2007 y superiores
				obj = new ActiveXObject('SharePoint.OpenDocuments.3');
				obj.EditDocument(encodeURI(settings.url));
			} catch (e) {
				try {
					// Microsoft Office 2003 e inferiores
					obj = new ActiveXObject('Word.Application');
					obj.Visible = true;
					obj.Documents.Open(encodeURI(settings.url));
				} catch (e) {
					if (settings.downloadOnError === true) {
						// No se puede editar en línea, se descarga el archivo
						window.open(encodeURI(settings.alternateDownloadURL), '_blank');
					}

					if (jQuery.isFunction(settings.fncErrorOnEditOnline)) {
						jQuery.proxy(settings.fncErrorOnEditOnline)(settings);
					}
				}
			}
		},
		_editOnlineFF: function _editOnlineFF(settings) {
			var hownowPlugin, version;
			// Gestión para Firefox y Chrome
			try {
				// Microsoft Office 2007 y superiores
				hownowPlugin = document.getElementById('winFirefoxPlugin');
				version = hownowPlugin.GetOfficeVersion();
				hownowPlugin.EditDocument(settings.url, version);
			} catch (e) {
				if (settings.downloadOnError === true) {
					// No se puede editar en línea, se descarga el archivo
					window.open(encodeURI(settings.alternateDownloadURL), '_blank');
				}

				if (jQuery.isFunction(settings.fncErrorOnEditOnline)) {
					jQuery.proxy(settings.fncErrorOnEditOnline)(settings);
				}
			}
		}
	});

	//*******************************************************
	// DEFINICIÓN DE LA CONFIGURACION POR DEFECTO DEL PATRON
	//*******************************************************

	$.rup_dav.defaults = {
		xlnetsAuth: false,
		xlnetsAuthParam: 'c',
		downloadOnError: false,
		alternateDownloadURL: null,
		fncErrorOnEditOnline: null

	};
})(jQuery);
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))

/***/ }),
/* 157 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*!
 * Copyright 2016 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 */

/*
	 Plugin que genera la combo de idiomas con el siguiente formato.
		<ul>
			<li id="idiomaActivo" class="activo">Castellano </li>
			<li id="enlace" class="ultimo cambio_idioma" >
				<a href="#">Cambiar Idioma</a>
			</li>
			<li id="listado" class="ultimo cambio_idioma_desplegado" style="display: none;">
				<div  class="caja_idiomas">
					<a id="caja_listado" class="opcion_cambio" >Cambiar Idioma</a>
					<div class="listado_idiomas">
						<a id="cerrar" class="cerrar_idiomas" href="#" title="Cerrar"><span class="hidden">Cerrar</span></a>

						<ul class="principal">
								<li id="idioma_es" class="activo">
									<a class="idioma">Castellano</a>
								</li>
								<li id="idioma_eu">
									<a class="idioma">Euskera</a>
								</li>
						</ul>
					 </div>
				 </div>
			</li>
		</ul>
*/

/**
 * El componente de idioma esta diseñado para permitir al usuario elegir, de forma intuitiva, el idioma en el que se presenta la aplicación.
 *
 * @summary Componente RUP Language.
 * @module rup_language
 * @example
 * var properties={
 *   // Propiedades de configuración
 * };
 *
 * $("#idlanguage").rup_language(properties);
 */

/*global define */
/*global jQuery */

(function (factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(2), __webpack_require__(9)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		factory(jQuery);
	}
})(function ($) {

	$.widget('$.rup_language', {
		options: {
			languages: null,
			active: null,
			modo: 'default' //portal
		},
		/**
         * Función encargada de crear en el DOM los elementos necesarios para el componente.
         *
         * @function	_create
         * @private
         */
		_create: function _create() {

			var active;

			this.options.active = $.rup.lang == null ? '[lang]' : $.rup.lang;
			active = this.options.active;
			this.options.languages = $.rup.AVAILABLE_LANGS.split(',');
			var self = this.element,
			    aChangeLang = $('<a>').attr('id', 'rup_language_choice').addClass('rup-language_change_option').text($.rup.i18nParse($.rup.i18n.base, 'rup_language.changeLanguage'));

			//gestion de estilos de jquery-ui
			$(self).addClass('ui-widget');

			if (this.options.modo === 'default') {
				var $parent = self.parent(),
				    $langCurrentText = self.find('[data-rup-lang-current]'),
				    $languagesDropdown,
				    value;

				$parent.addClass('dropdown');
				self.addClass('dropdown-toggle').attr({
					'data-toogle': 'dropdown',
					'aria-haspopup': 'true',
					'aria-expanded': 'false'
				});

				$langCurrentText.text($.rup.i18nParse($.rup.i18n.base, 'rup_language.' + this.options.active));
				// $languagesDropdown = $("<div>").addClass("dropdown-menu").attr("aria-labelledby",self.attr("id"));
				$languagesDropdown = $parent.find('[aria-labelledby=' + self.attr('id') + ']');
				$.each(this.options.languages, function (key, value) {
					value = value.replace(/^\s*|\s*$/g, '');
					var txt = $.rup.i18nParse($.rup.i18n.base, 'rup_language.' + value);

					$languagesDropdown.append($('<a>').addClass('dropdown-item').attr('href', '?' + $.rup.LOCALE_PARAM_NAME + '=' + value).text(txt));
				});
				$parent.append($languagesDropdown);
			} else if (this.options.modo === 'portal') {
				var ul = $('<ul>').addClass('rup-language_portal'),
				    lng_lenght = $(this.options.languages).size();

				$.each(this.options.languages, function (key, value) {
					value = value.replace(/^\s*|\s*$/g, '');
					var txt = $.rup.i18nParse($.rup.i18n.base, 'rup_language.' + value + '_short');
					if (value !== active) {
						$('<li>').append($('<a>').attr('href', '?' + $.rup.LOCALE_PARAM_NAME + '=' + value).text(txt).addClass('rup-language_portal_list ui-corner-all').attr('title', $.rup.i18nParse($.rup.i18n.base, 'rup_language.changeLanguageLiteral_' + value) + $.rup.i18nParse($.rup.i18n.base, 'rup_language.' + value))).appendTo(ul);
					} else {
						$('<li>').addClass('ui-state-active').append($('<a>').attr('href', 'javascript:void(0);').text(txt).addClass('rup-language_portal_list_active ui-corner-all').attr('title', $.rup.i18nParse($.rup.i18n.base, 'rup_language.changeLanguageLiteral') + $.rup.i18nParse($.rup.i18n.base, 'rup_language.' + value))).appendTo(ul);
					}
					//div.appendTo(ulPrincipal);
					if (key < lng_lenght - 1) {
						ul.append($('<div>').html('|').addClass('rup-language_portal_separator'));
					}
				});

				self.append(ul);
			} else if (this.options.modo === 'classic' || this.options.modo === 'jquery-ui') {

				// Carga de los valores por defecto para los atributos que no ha introducido el usuario
				var ul = $('<ul>').attr('id', 'ulGeneral'),
				    timerID,
				    liIdiomaActivo = $('<li>').attr('id', 'rup_active_language').addClass('rup-language_active').text($.rup.i18nParse($.rup.i18n.base, 'rup_language.' + this.options.active)).attr('title', $.rup.i18nParse($.rup.i18n.base, 'rup_language.changeLanguageLiteral') + $.rup.i18nParse($.rup.i18n.base, 'rup_language.' + active)),
				    liEnlace = $('<li>').addClass('rup-language_change').attr('id', 'rup_language_link'),
				    liListado = $('<li>').attr('id', 'rup_language_list').addClass('rup-language_change_opened').css('visibility', 'hidden'),
				    divCajaIdiomas = $('<div>'),
				    listadoIdiomas = $('<div>').addClass('rup-language_language_list'),
				    cerrarIdioma = $('<a>').addClass('rup-language_close_languages').attr('id', 'rup_language_close').attr('href', '#').attr('title', $.rup.i18nParse($.rup.i18n.base, 'rup_language.closingLiteral')).html($.rup.i18nParse($.rup.i18n.base, 'rup_global.cerrar')),
				    ulPrincipal = $('<ul>');

				ul.append(liIdiomaActivo);

				$('<a>').attr('href', '#').text($.rup.i18nParse($.rup.i18n.base, 'rup_language.changeLanguage')).appendTo(liEnlace);
				ul.append(liEnlace);
				divCajaIdiomas.append(aChangeLang);

				listadoIdiomas.append(cerrarIdioma);

				$.each(this.options.languages, function (key, value) {
					value = value.replace(/^\s*|\s*$/g, '');
					var liIdioma = $('<li>').attr('id', 'rup_language_lng_' + value),
					    txt = $.rup.i18nParse($.rup.i18n.base, 'rup_language.' + value);
					if (value !== active) {
						$('<a>').appendTo(liIdioma).attr('href', '?' + $.rup.LOCALE_PARAM_NAME + '=' + value).text(txt).attr('title', $.rup.i18nParse($.rup.i18n.base, 'rup_language.changeLanguageLiteral_' + value) + $.rup.i18nParse($.rup.i18n.base, 'rup_language.' + value));
					} else {
						//hacemos que sea el lenguage actual el activo
						$('<a>').appendTo(liIdioma).attr('href', 'javascript:void(0);').text(txt).attr('title', $.rup.i18nParse($.rup.i18n.base, 'rup_language.changeLanguageLiteral') + $.rup.i18nParse($.rup.i18n.base, 'rup_language.' + value));
					}
					liIdioma.appendTo(ulPrincipal);
				});
				listadoIdiomas.append(ulPrincipal);
				divCajaIdiomas.append(listadoIdiomas);
				liListado.append(divCajaIdiomas);
				ul.append(liListado);
				self.append(ul);

				var ajust = listadoIdiomas.css('width', '0.8em').width();
				var saveMargin = liEnlace.css('margin-right');
				liEnlace.css('margin-right', '0px');
				listadoIdiomas.width(liListado.position().left - ajust);
				listadoIdiomas.css('padding-left', '0.6em');
				listadoIdiomas.css('padding-right', '0.2em');
				listadoIdiomas.css('top', liIdiomaActivo.height() - 1);
				liListado.hide();
				liListado.css('visibility', '');
				liEnlace.css('margin-right', saveMargin);

				//se aplica el lenguage actual el activo
				$('#rup_language_lng_' + $.rup.lang).addClass('ui-state-active');

				//evento click para mostrar el listado de idiomas
				liEnlace.click(function () {
					liEnlace.hide();
					liListado.show();
					$('.rup-language_language_list').find('li:not(.rup-language_language_list_active)').first().children('a').focus();
				});

				//evento del enlace de cambio de idioma
				aChangeLang.click(function () {
					liListado.hide();
					liEnlace.show();
				});
				//evento del boton de cerrar
				cerrarIdioma.click(function () {
					liListado.hide();
					liEnlace.show();
				});

				// gestion de eventos del raton sobre la parte del cambio de idioma
				liListado.mouseenter(function () {
					self.one('mouseleave', function () {
						liListado.hide();
						liEnlace.show();
					});
				});

				self.bind('keydown', function (event) {
					switch (event.keyCode) {
						case $.ui.keyCode.UP:
							if ($(event.target).parent().prevAll('li:not(.rup-language_language_list_active)').length > 0) {
								$(event.target).parent().prevAll('li:not(.rup-language_language_list_active)').first().children().focus();
							} else {
								$(event.target).parent().siblings('li:not(.rup-language_language_list_active)').last().children().focus();
							}
							break;
						case $.ui.keyCode.DOWN:
							if ($(event.target).parent().nextAll('li:not(.rup-language_language_list_active)').length > 0) {
								$(event.target).parent().nextAll('li:not(.rup-language_language_list_active)').first().children().focus();
							} else {
								$(event.target).parent().siblings('li:not(.rup-language_language_list_active)').first().children().focus();
							}
							break;
						case $.ui.keyCode.ESCAPE:
							liListado.hide();
							liEnlace.show();
							break;
						default:
					}
				});
			}

			// Se aplica el tooltip
			self.find('[title]').rup_tooltip({
				'applyToPortal': true
			});
		},
		/**
         * Modifica las opciones de configuración del componente.
         *
         * @function	_setOption
         * @private
         */
		_setOption: function _setOption(key, value) {
			$.Widget.prototype._setOption.apply(this, arguments);
		},
		/**
         * Elimina el componente.
         *
         * @function	destroy
         * @example
         * $("#idlanguage").rup_language("destroy");
         */
		destroy: function destroy() {
			$.Widget.prototype.destroy.apply(this, arguments);
		}
	});

	/**
     * Opciones por defecto de configuración del componente.
     * @name defaults
     *
     * @property {object} languages - Conjunto de idiomas que serán gestionados con el componente. El listado de los mismos, por configuración general, se gestiona a través de la variable jQuery “$.rup.AVAILABLE_LANGS_ARRAY”. Para mas información, consultar el documento “Anexo-Gestion_idiomatica.doc” de la documentación de UDA.
     * @property {string} [modo] - Determina el tipo de maquetación que utilizara el componente para presentar las diferentes opciones idiomáticas. Si el valor especificado es “portal”, los idiomas se presentaran en un listado horizontal separado por barras (ver ejemplo visual del capítulo/Sección “2. Ejemplo”). En cualquier otro caso, se mostrara el modo por defecto (ver ejemplo visual del capítulo/Sección “2. Ejemplo”).
     */
});

/***/ }),
/* 158 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*!
 * Copyright 2014 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 */

/**
 * Ccomponente de list.
 *
 * @summary Componente RUP List.
 * @module rup_list
 *
 * $("#idList").rup_list(properties);
 */

(function (factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(2)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		factory(jQuery);
	}
})(function ($) {
	var settingsInit;

	//****************************************************************************************************************
	// DEFINICIÓN BASE DEL PATRÓN (definición de la variable privada que contendrá los métodos y la función de jQuery)
	//****************************************************************************************************************

	$.extend($.rup, {
		/**
     *  Lista creada a partir de un texto.
     * @typedef {string} module:rup_list~JSON
     * @example
     * $.rup.list.JSON
     */
		/**
     *  Lista creado a partir de la respuesta de una petición AJAX.
     * @typedef {string} module:rup_list~AJAX
     * @example
     * $.rup.list.AJAX
     */

		list: {
			JSON: 'jsonList',
			AJAX: 'ajaxList'
		}
	});

	var rup_list = {};

	//Se configura el arranque de UDA para que alberge el nuevo patrón
	$.extend($.rup.iniRup, $.rup.rupSelectorObjectConstructor('rup_list', rup_list));

	//*******************************
	// DEFINICIÓN DE MÉTODOS PÚBLICOS
	//*******************************
	// 
	// $("#idLista).rup_list("foo");
	// $("#idLista).rup_list("getNumElems");
	// $("#idLista).rup_list("setElem", 2, {});
	$.fn.rup_list('extend', {
		inicio: function inicio(paramJson) {
			var $self = this;
			var settings = settingsInit,
			    json = $.extend(true, {}, paramJson);

			if (settings.type !== undefined && settings.type !== null) {
				if ($.rup.list.JSON === settings.type) {
					$self._jsonLoad(settings, json);
				} else if ($.rup.list.AJAX === settings.type) {
					$self._ajaxLoad(settings);
				} else {
					$.rup_messages("msgAlert", {
						message: "Tipo de lista Incompatible"
					});
				}
			} else {
				$.rup_messages("msgAlert", {
					message: "El tipo de lista es obligatorio"
				});
			}

			return $self;
		},
		setElem: function setElem(id, obj, json) {
			return $self;
		}
	});

	//*******************************
	// DEFINICIÓN DE MÉTODOS PRIVADOS
	//*******************************

	$.fn.rup_list('extend', {
		_bar: function _bar() {
			return this;
		},
		/**
      * Realiza la carga del contenido de la lista a partir de una petición AJAX.
      *
      * @function  _ajaxLoad
      * @private
      * @param {object} settings - Propiedades de configuración del componente.
      */
		_ajaxLoad: function _ajaxLoad(settings) {
			var $self = this;
			//Si el tipo de dialogo es AJAX y no se establece url se muestra un error y se devuelve el control
			if (!settings.url || settings.url === null || settings.url === '') {
				$.rup.msgAlert({
					title: $.rup.i18nParse($.rup.i18n.base, 'rup_global.error'),
					message: $.rup.i18nParse($.rup.i18n.base, 'rup_dialog.noURL')
				});
				return false;
			}

			//Peticion ajax para obtener los datos a mostrar
			$.rup_ajax({
				type: 'GET',
				contentType: 'application/json',
				dataType: 'json',
				url: settings.url,
				success: function success(data) {
					$self._jsonLoad(settings, data);
				},
				error: function error() {
					alert('Se ha producido un error al recuperar los datos del servidor');
				}
			});
		},
		/**
      * Realiza la carga del contenido de la lista a partir de un Json.
      *
      * @function  _jsonLoad
      * @private
      * @param {object} settings - Propiedades de configuración del componente.
      */
		_jsonLoad: function _jsonLoad(settings, json) {
			var $self = this;
			$self.text("");
			//Si el tipo de dialogo es AJAX y no se establece url se muestra un error y se devuelve el control
			if (!json || json === null || json === '') {
				$.rup_messages("msgAlert", {
					message: "Json incorrecto"
				});
				return false;
			}
			var cadena = "";
			var $ul = $('<ul>', { class: "list-group" });
			$.each(json, function (j, jsonObj) {
				//Se establece el orden por defecto;
				var listDefault = settings.template.split(",");
				$.each(listDefault, function (idx, obj) {
					if (jsonObj[obj] !== undefined) {
						cadena += jsonObj[obj] + " ";
						delete jsonObj[obj];
					}
				});
				//Se lista  el resto
				$.each(jsonObj, function (idx, obj) {
					cadena += obj + " ";
				});
				$('<li/>').addClass('list-group-item').attr('role', 'menuitem').text(cadena).appendTo($ul);
				cadena = "";
			});
			$self.append($ul);
		}
	});

	//*******************************
	// MÉTODO DE INICIALIZACION
	//*******************************
	// <ul id="idLista">...</ul>
	// $("#idLista).rup_list({
	//  	template:"zspna
	//});
	$.fn.rup_list('extend', {
		_init: function _init(args) {
			settingsInit = $.extend({}, $.fn.rup_list.defaults, args[0]);

			var $self = this;
			if ($.rup.list.AJAX === settingsInit.type) {
				$self._ajaxLoad(settingsInit);
			}

			return $self;
		}
	});

	//******************************************************
	// DEFINICIÓN DE LA CONFIGURACION POR DEFECTO DEL PATRON
	//******************************************************
	$.fn.rup_list.defaults = {
		ajaxCache: true,
		template: "nombre,apellido1,apellido2",
		type: null,
		url: null
	};
});

/***/ }),
/* 159 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*!
 * Copyright 2016 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 */
//require(["jquery", "require-jqueryui"],function (jQuery, widgetMenu) {

/**
 * Menú de la aplicación mantenido a lo largo de todas las páginas de forma consistente que muestra entradas directas a secciones clave de la aplicación.
 *
 * @summary Componente RUP Menu.
 * @module rup_menu
 * @example
 * var properties={
 *   // Propiedades de configuración
 * };
 *
 * $("#idMenu").rup_menu(properties);
 */

/*global define */
/*global jQuery */

(function (factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(2)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		factory(jQuery);
	}
})(function ($) {

	//*****************************************************************************************************************
	// DEFINICIÓN BASE DEL PATRÓN (definición de la variable privada que contendrá los métodos y la función de jQuery)
	//*****************************************************************************************************************


	var rup_menu = {};

	//Se configura el arranque de UDA para que alberge el nuevo patrón
	$.extend($.rup.iniRup, $.rup.rupSelectorObjectConstructor('rup_menu', rup_menu));

	//********************************
	// DEFINICIÓN DE MÉTODOS PÚBLICOS
	//********************************

	$.fn.rup_menu('extend', {
		/**
         * Deshabilita una opción de menú.
         *
         * @function disable
         * @param {string} entryMenuId - Identificador de la opción de menú que se desea deshabilitar.
         * @example
         * $("#idlanguage").rup_menu("disable","opAdmin);
         */
		disable: function disable(entryMenuId) {
			var entryMenu = $('#' + entryMenuId);
			entryMenu.addClass('ui-state-disabled');
			//			entryMenu.bind("click", function(event){event.preventDefault(); event.stopImmediatePropagation();});
		},
		/**
         * Habilita una opción de menú.
         *
         * @name enable
         * @function
         * @param {string} entryMenuId - Identificador de la opción de menú que se desea habilitar.
         * @example
         * $("#idlanguage").rup_menu("enable","opAdmin);
         */
		enable: function enable(entryMenuId) {
			var entryMenu = $('#' + entryMenuId);
			entryMenu.removeClass('ui-state-disabled');
			//			entryMenu.unbind("click");
		}
	});

	//********************************
	// DEFINICIÓN DE MÉTODOS PRIVADOS
	//********************************

	$.fn.rup_menu('extend', {
		/**
         * Método de inicialización del componente.
         *
         * @function  _init
         * @private
         * @param {string} args - Opciones de configuración del componente.
         */
		_init: function _init(args) {

			if (args.length > 1) {
				$.rup.errorGestor($.rup.i18nParse($.rup.i18n.base, 'rup_global.initError' + $(this).attr('id')));
			} else {
				if (this.length > 0) {

					//Se recogen y cruzan las paremetrizaciones del objeto
					var settings = $.extend(true, {}, $.fn.rup_menu.defaults, args[0]),
					    self = this,
					    selectorSelf = this,
					    menuId = self[0].id,
					    json,
					    json_i18n;

					//visualizacion de los menus
					//Se oculta la capa para que no aparezca deformada
					selectorSelf.removeClass('rup_invisible_menu');

					//Se determina el identificador de los literales y se cargan los mismos
					if (settings.i18nId === undefined) {
						settings.i18nId = menuId;
					}

					json_i18n = $.rup.i18n.app[settings.i18nId];

					//Obtener estructura y literales
					if (settings.menu !== undefined) {
						json = settings.menu;
					} else if (settings.json !== undefined) {
						json = settings.json;
					}

					//Se extienden las funcionalidades del menú para ajustarlas a las necesidades de funcionamiento del rup_menu
					//						widgetMenu.widget( "ui.rupMenu", widgetMenu.ui.menu, $.rup.compatibility.menu );

					//En caso de ser necesario, se secra el objeto que compondra la estructura del menu
					if (json !== undefined) {
						//Generar estructura de menu
						self._parseJSON(json, json_i18n, selectorSelf, settings.forceAbs);
						selectorSelf = widgetMenu('#' + self.attr('id'));
					}

					//Se trata el evento de selección para que se produzca una redirección de menú automática
					selectUserEvent = settings.select;
					settings.select = function (event, ui) {
						if (selectUserEvent !== undefined && selectUserEvent !== null) {
							if (typeof selectUserEvent === 'function') {
								if (selectUserEvent(event, ui) === false) {
									return false;
								}
							}
						}
						//Comportamiento por defecto del evento
						if (/^keydown/.test(event.originalEvent.type)) {
							event.stopImmediatePropagation();

							redirectObject = $(ui.item.children());

							if (redirectObject.attr('target') !== '_blank') {
								$(location).attr('href', redirectObject.attr('href'));
							} else {
								if ($.rup.browser.isFF) {
									var wm = Components.classes['@mozilla.org/appshell/window-mediator;1'].getService(Components.interfaces.nsIWindowMediator);
									var recentWindow = wm.getMostRecentWindow('navigator:browser');
									recentWindow.delayedOpenTab(redirectObject.attr('href'), null, null, null, null);
								} else if ($.rup.browser.isChrome) {
									chrome.tabs.create({
										'url': redirectObject.attr('href')
									});
								} else {
									window.open(redirectObject.attr('href'), '_blank');
								}
							}
						}

						return false;
					};

					//Enlaces externos (add icon)
					selectorSelf.find('a[target=\'_blank\']').append('<span class=\'ui-icon ui-icon-extlink rup_external_link\'></span>');

					//Se comienza a crear el menu segun el tipo
					if (settings.display === 'horizontal') {

						//							selectorSelf.on("mouseenter", ".rup_menu_horizontal_children.ui-menu-item", function( event ) {
						//								event.stopImmediatePropagation();
						//								event.preventDefault();
						//								event.stopPropagation();
						//								return false;
						//							});

						selectorSelf.on('mouseenter', '.ui-menu-item', function (event) {
							// Ignore mouse events while typeahead is active, see #10458.
							// Prevents focusing the wrong item when typeahead causes a scroll while the mouse
							// is over an item in the menu
							var $uiMenu = selectorSelf.data().uiMenu;

							if ($uiMenu.previousFilter) {
								return;
							}
							var target = $(event.currentTarget);
							//								console.log("rup-this:");
							//								console.log($uiMenu);
							//								console.log("rup-taget:");
							//								console.log(target);
							//								console.log("position:");
							//								console.log($uiMenu.options.position);

							if (target.hasClass('rup_menu_horizontal_children')) {
								$uiMenu.options.position = {
									my: 'left top',
									at: 'left bottom',
									collision: 'none none',
									of: this
								};
							} else {
								$uiMenu.options.position = {
									my: 'left bottom',
									at: 'right bottom'
								};
							}

							// Remove ui-state-active class from siblings of the newly focused menu item
							// to avoid a jump caused by adjacent elements both having a class with a border
							target.siblings('.ui-state-active').removeClass('ui-state-active');
							$uiMenu.focus(event, target);
							event.stopImmediatePropagation();
							event.preventDefault();
							event.stopPropagation();
							return false;
						});

						//							selectorSelf.on("mouseenter", " .rup_menu_vertical_horizontal.ui-menu", function( event ) {
						//
						//								$(this).addClass(".ui-state-active");
						//
						//								event.stopImmediatePropagation();
						//								event.preventDefault();
						//								event.stopPropagation();
						//								return false;
						//							});

						//							selectorSelf.on("mouseleave",".rup_menu_horizontal_children.ui-menu-item,.rup_menu_vertical_horizontal.ui-menu",function(event){
						//
						//								$(this).parents(".ui-state-active").removeClass("ui-state-active");
						//
						//								return false;
						//							});
						selectorSelf.on('keydown', function (event) {

							var $uiMenu = selectorSelf.data().uiMenu;
							//								console.log($uiMenu.active);

							switch (event.keyCode) {
								case $.ui.keyCode.UP:
									$uiMenu.previous(event);
									event.stopImmediatePropagation();
									event.preventDefault();
									event.stopPropagation();
									break;
								case $.ui.keyCode.DOWN:
									if ($uiMenu.active && !$uiMenu.active.is('.ui-state-disabled')) {
										if ($uiMenu.active.hasClass('rup_menu_horizontal_children')) {
											$uiMenu.options.position = {
												my: 'left top',
												at: 'left bottom',
												collision: 'none none',
												of: $uiMenu.active
											};
											$uiMenu.expand(event);
										} else {
											$uiMenu.next(event);
										}
									}
									event.stopImmediatePropagation();
									event.preventDefault();
									event.stopPropagation();
									break;
								case $.ui.keyCode.LEFT:
									if (!$uiMenu.active.hasClass('rup_menu_horizontal_children')) {
										$uiMenu.collapse(event);
									} else {
										$uiMenu.previous(event);
									}
									event.stopImmediatePropagation();
									event.preventDefault();
									event.stopPropagation();
									break;
								case $.ui.keyCode.RIGHT:
									if (!$uiMenu.active.hasClass('rup_menu_horizontal_children') && $uiMenu.active.is('[aria-haspopup=\'true\']')) {
										$uiMenu.options.position = {
											my: 'left bottom',
											at: 'right bottom'
										};
										$uiMenu.expand(event);
									} else {
										$uiMenu.next(event);
									}
									event.stopImmediatePropagation();
									event.preventDefault();
									event.stopPropagation();
									break;
								case $.ui.keyCode.HOME:
									$uiMenu._move('first', 'first', event);
									event.stopImmediatePropagation();
									event.preventDefault();
									event.stopPropagation();
									break;
							}
						});

						//
						//							selectorSelf.on("click", ".rup_menu_horizontal_children.ui-menu-item", function( event ) {
						//								event.stopImmediatePropagation();
						//								event.preventDefault();
						//								event.stopPropagation();
						//								this.focus();
						//								return false;
						//							});

						//							selectorSelf.on("click", ".rup_menu_horizontal_children.rup_menu_horizontal_children_double.ui-menu-item", function( event ) {
						//								console.log(this);
						////								$(this).removeClass("ui-state-active");
						//
						//								var $uiMenu = selectorSelf.data().uiMenu;
						//
						//
						////								var $submenu = $(this).children("ul");
						//								$uiMenu.options.position = { my: "left top", at: "left bottom", collision:"none none", of: this };
						//
						//								if ( $uiMenu.previousFilter ) {
						//									return;
						//								}
						//								var target = $( this);
						//								// Remove ui-state-active class from siblings of the newly focused menu item
						//								// to avoid a jump caused by adjacent elements both having a class with a border
						//								target.siblings( ".ui-state-active" ).removeClass( "ui-state-active" );
						//								$uiMenu.focus( event, target );
						//
						////								$submenu
						////									.show()
						////									.removeAttr( "aria-hidden" )
						////									.attr( "aria-expanded", "true" )
						////									.position($uiMenu.options.position);
						////								$(this).removeClass("ui-state-active");
						////								event.stopImmediatePropagation();
						////								event.preventDefault();
						////								event.stopPropagation();
						////								return false;
						//							});

						//Se asocian los estilos específicos del menú horizontal
						selectorSelf.addClass('rup_menu_horizontal').addClass('ui-widget-header');
						selectorSelf.children().addClass('rup_menu_horizontal_children');
						selectorSelf.children().children('a').addClass('rup_menu_horizontal_children_entry');

						selectorSelf.menu(settings);

						//Se borran las entradas separadoras. En el menu horizontal no tienen sentido.
						selectorSelf.children('.ui-menu-divider').remove();

						//Ajustes de estilos para la primera capa del menu horizontal
						selectorSelf.children('.ui-state-disabled').css({
							'margin-top': '0em',
							'margin-bottom': '0em'
						});
						$('#' + menuId + ' li.rup_menu_horizontal_children > a .ui-icon-caret-1-e').removeClass('ui-icon-caret-1-e').addClass('ui-icon-caret-1-s').addClass('rup-menu_horizontalIcon');
						selectorSelf.children().children('a').css('font-weight', 'bold');
						selectorSelf.children().each(function (position, object) {
							var iconsWidth = 0;
							$(object).children('.rup_menu_horizontal_children_entry:has(span:not(.rup-menu_horizontalIcon))').each(function (position, object) {
								if ($(object).find('span').size() === 1) {
									iconsWidth = $(object).find('span').width();
								} else {
									iconsWidth = $(object).find('span:not(.rup-menu_horizontalIcon)').width() / 2;
								}
							});
							$(object).css('width', $(object).width() + iconsWidth);
						});
						selectorSelf.children().children('a').css('font-weight', '');
						selectorSelf.children(':has(.rup_menu_horizontal_children_entry span:not(.rup-menu_horizontalIcon))').addClass('rup_menu_horizontal_childrenIcon');
						selectorSelf.find('.rup_menu_horizontal_children_entry span:not(.rup-menu_horizontalIcon)').addClass('rup_menu_horizontal_children_icon');
						selectorSelf.children(':has(.rup_menu_horizontal_children_entry span.rup-menu_horizontalIcon)').addClass('rup_menu_horizontal_childrenMenuIcon');
						selectorSelf.children(':has(.rup_menu_horizontal_children_entry span.rup_menu_horizontal_children_icon):has(span.rup-menu_horizontalIcon)').addClass('rup_menu_horizontal_children_double');
						selectorSelf.children(':last-child').addClass('rup_menu_horizontal_children_last');

						//Asignación de los menús desplegables de primer menú

						selectorSelf.children().children('[aria-haspopup=\'true\']').parent().attr('rupMenu_firsLevel', 'true');
						$('#' + menuId + ' [rupmenu_firslevel=\'true\'] [role=\'menu\']').addClass('rup_menu_vertical_horizontal');
						if (settings.verticalWidth === undefined) {
							$('#' + menuId + ' [rupmenu_firslevel=\'true\'] [role=\'menu\']').css('white-space', 'nowrap');
						} else {
							$('#' + menuId + ' [rupmenu_firslevel=\'true\'] [role=\'menu\']').css('width', settings.verticalWidth);
						}

						//Enlaces externos en primer nivel: editar estilos
						selectorSelf.find('a[target=\'_blank\'] span.rup_menu_horizontal_children_icon').each(function (span_pos, span) {
							//Cambiarlo en span con enlace externo (puede que haya otros span con iconos)
							if ($(span).is('.ui-icon-extlink')) {
								$(span).addClass('ui-menu-icon').removeClass('rup_menu_horizontal_children_icon');
							}
						});

						//Si tiene enlace externo y otro enlace, se debe ampliar el LI y cambiar el margen del ext_link
						var twoIconsLI = selectorSelf.find('a[target=\'_blank\'] span.rup_menu_horizontal_children_icon').parents('li');
						twoIconsLI.css('width', twoIconsLI.width() + 16);
						twoIconsLI.find('span.ui-icon-extlink').css('margin-left', '-1em');
					} else if (settings.display === 'vertical') {

						//Se le especifica el tamaño del menu
						selectorSelf.addClass('rup_menu_vertical');
						if (settings.verticalWidth === undefined) {
							selectorSelf.css('white-space', 'nowrap');
						} else {
							selectorSelf.css('width', settings.verticalWidth);
						}
						selectorSelf.children().addClass('rup_menu_vertical_children');

						//Se invoca a la generacion del menu
						selectorSelf.menu(settings);

						//Se ajustan los tamaños de las sub-entradas del menú
						if (settings.verticalWidth !== undefined) {
							$('#' + menuId + ' .ui-menu .ui-menu-item').css('width', settings.verticalWidth);
						}
					} else {
						$.rup.errorGestor($.rup.i18n.base.rup_menu.displayMenuError);
					}

					// Ajuste estilos
					selectorSelf.addClass('ui-corner-all');
					selectorSelf.find('ul.rup_menu_vertical_horizontal').addClass('ui-corner-all');

					//Ajuste margen iconos
					var icon = false;
					//Buscar ULs verticales
					$('ul.rup_menu_vertical, ul.rup_menu_vertical ul, ul.rup_menu_vertical_horizontal').each(function (ul_pos, ul) {
						//Localizar SPANS
						$(ul).children('li').children('a').children('span').each(function (span_pos, span) {
							//Comprobar que el SPAN tiene un icono propio
							if (!$(span).is('.ui-icon.ui-icon-extlink, .ui-icon.ui-icon-carat-1-e')) {
								icon = true;
								return false;
							}
						});
						//Si tiene icono propio se aplica estilo a todos enlaces (margen)
						if (icon) {
							$(ul).children('li').children('a').css('padding-left', '2em');
						}
						//Restablecer variable
						icon = false;
					});

					//Ajuste de estilos para cubrir arista
					//						$("#"+menuId+" [role = 'menuitem']").not($("[aria-haspopup = 'true']")).css("text-decoration","underline");

					//Se deshabilitan los botones desconectados
					selectorSelf.find('a').bind('click', function (event) {
						if ($(event.currentTarget).hasClass('ui-state-disabled')) {
							event.preventDefault();
							event.stopImmediatePropagation();
						}
					});

					//Se asocia un "tabIndex=-1" a todos los enlaces deshabilitados
					//						selectorSelf.find(".ui-state-disabled").attr("tabindex","-1");
				}
			}
		},
		/**
         * Parsea un objeto json para generar la estructura de menú de acuerdo a la información contenida en el.
         *
         * @function  _parseJSON
         * @private
         */
		_parseJSON: function _parseJSON(json, json_i18n, self, force) {
			var submenu,
			    element,
			    objectUrl = '',
			    entry;

			//Se transforma el objeto base del menu
			if (self.attr('uda-submenu') === 'true') {
				self.attr('uda-submenu', '');
			} else {
				self.replaceWith($('<ul>').attr('id', self.attr('id')).attr('style', self.attr('style')).attr('class', self.attr('class')));
				self = $('#' + self.attr('id'));
			}

			//Recorrer json para añadir elementos
			for (var i = json.length; i--;) {
				element = json[i];
				entry = $('<a>');
				if (element !== undefined) {
					if (element.divider !== null && element.divider !== true) {
						if (element.pathUrl !== undefined || element.url !== undefined) {
							if (element.pathUrl !== undefined) {
								if (force === true || element.forceAbs === true) {
									objectUrl = $.rup_utils.relToAbsUrl(element.pathUrl);
								} else {
									objectUrl = element.pathUrl;
								}
							} else {
								objectUrl = $.rup.CTX_PATH + element.url;
							}

							if (element.newWindow !== true) {
								if (element.icon !== undefined) {
									self.prepend($('<li>').append(entry.text($.rup.i18nParse(json_i18n, element.i18nCaption)).attr('href', objectUrl).css('text-decoration', 'underline').append($('<span>').addClass('ui-icon').addClass(element.icon))));
								} else {
									self.prepend($('<li>').append(entry.text($.rup.i18nParse(json_i18n, element.i18nCaption)).attr('href', objectUrl).css('text-decoration', 'underline')));
								}
							} else {
								if (element.icon !== undefined) {
									self.prepend($('<li>').append(entry.text($.rup.i18nParse(json_i18n, element.i18nCaption)).attr('href', objectUrl).attr('target', '_blank').css('text-decoration', 'underline').append($('<span>').addClass('ui-icon').addClass(element.icon))));
								} else {
									self.prepend($('<li>').append(entry.text($.rup.i18nParse(json_i18n, element.i18nCaption)).attr('href', objectUrl).attr('target', '_blank').css('text-decoration', 'underline')));
								}
							}
						} else {
							//Si no tiene enlace es submenu
							if (element.icon !== undefined) {
								self.prepend($('<li>').append(entry.text($.rup.i18nParse(json_i18n, element.i18nCaption)).css('cursor', 'default').append($('<span>').addClass('ui-icon').addClass(element.icon))).append($('<ul>').attr('uda-submenu', 'true')));
							} else {
								self.prepend($('<li>').append(entry.text($.rup.i18nParse(json_i18n, element.i18nCaption)).css('cursor', 'default')).append($('<ul>').attr('uda-submenu', 'true')));
							}
							//Obtener el elemento que va a ser el submenu
							submenu = $('[uda-submenu = \'true\']');
							//Llamada recursiva para añadir subelementos del submenu
							submenu.append(this._parseJSON(element.submenu, json_i18n, submenu));
						}

						if (element.disabled === true) {
							entry.parent().addClass('ui-state-disabled');
						}
					} else {
						if (element.i18nCaption === undefined) {
							self.prepend($('<li>').addClass('ui-widget-content ui-menu-divider'));
						} else {
							self.prepend($('<li>').append($('<strong>').text($.rup.i18nParse(json_i18n, element.i18nCaption))));
						}
					}
				}
			}
		}
	});

	//*******************************************************
	// DEFINICIÓN DE LA CONFIGURACION POR DEFECTO DEL PATRON
	//*******************************************************
	/**
     * Opciones por defecto de configuración del componente.
     * @name defaults
     *
     * @property {string} [verticalWidth=undefined] - Valor asociado a cada menú que determinara la anchura vertical del mismo. Este parámetro tiene cabida, tanto, en menús verticales, como, en menús horizontales (al fin y al cabo los dos tienen partes verticales). En caso de no especificar ningún valor, cada uno de los submenús verticales se ajustara al ancho máximo de sus literales.
     * @property {string} [display=horizontal] - Orientación del menú: horizontal o vertical.
     * @property {string} [i18nId] - Indica el identificador del objeto JSON para la resolución de los literales del componente. En caso de no definirse se tomará el ID del objeto sobre el que se crea el componente.
     * @property {string} [menus=ul] - Parámetro que determina el tag de html que hará de padre para determinar las entradas del menú (tanto para las entradas normales como para las de los submenús).
     * @property {boolean} [forceAbs=false] - Parámetro de configuración que activa el uso de la función relToAbsUrl. Dicha función hace que todas las llamadas relativas se transformen a absolutas. El uso de este parámetro responde a situaciones en el que el navegador, por diferentes cuestiones funcionales, no gestiona bien las urls relativas (se tratan todas las urls relativas como urls absolutas para evitar el posible problema. Por ejemplo: problemas con portales). Este parámetro se puede aplicar tanto a nivel de entrada como a nivel general del menú.
     *
     * @property {object} [menu] - Estructura del menú se define mediante un array en notación JSON cuyo nombre será el mismo que el identificador del elemento sobre el que se aplica el componente. No se limita el número de submenús. Por coherencia se ha decidido que los elementos que contengan submenús no serán enlaces y viceversa.
     * @property {string} menu.i18nCaption - Define la ruta (url) a seguir cuando se pulse sobre el elemento, en caso de no tener submenú. La especificación de las rutas (urls), se puede hacer de forma relativa o de forma absoluta. (véase el capítulo 11. Formato de las urls).
     * @property {object} menu.submenu - Define una estructura JSON submenú.
     * @property {boolean} [menu.newWindow=false] - Si el valor es true, el enlace del menú se abrirá en una nueva ventana del navegador, en caso contrario (false), se aplicará sobre la ventana que alberga el menu. Todas las entradas de este tipo, serán indicadas mediante el icono “external link”.
     * @property {boolean} [menu.divider=false] - Parámetro encargado de indicar si la entrada del menú es un elemento de división o un objeto del menú. Cuando el valor de “divider” sea true, la entrada en cuestión, es un divisor. Existen dos tipos de divisores que se diferencian en la presencia del parámetro "i18nCaption". En caso de no tenerlo, el divisor es únicamente una línea divisora de entradas. En caso contrario, el divisor es una cabecera. En ambos casos, el resto de parámetros no tienen importancia y no serán tomados en cuanta a la hora de componer el menú. Su valor por defecto es false.
     * @property {boolean} menu.disabled - Determina si la entrada del menú esta habilitada o deshabilitada. El valor por defecto del campo es false. Dicho estado puede ser variado mediante las funciones enable y disable del componente.
     * @property {string} menu.icon - Especifica el class que tiene asociado el icono que regirá la entrada de menú.
     */
	$.fn.rup_menu.defaults = {
		verticalWidth: undefined,
		display: 'horizontal',
		forceAbs: false,
		i18nId: undefined,
		menus: 'ul',
		position: {
			my: 'left bottom',
			at: 'right bottom'
		}
	};
});

/***/ }),
/* 160 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function(jQuery) {var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*!
 * Copyright 2016 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 */

/**
 * Tiene como objetivo mostrar al usuario de forma homogénea, clara y llamativa, los posibles mensajes que pueden desencadenar las acciones en la aplicación. Estos mensajes predefinidos pueden ser de diferente tipología: error, confirmación, aviso o alerta.
 *
 * @summary Componente RUP Message.
 * @module rup_messages
 * @example
 * $.rup_messages("msgOK", {
 *		title: "Correcto",
 *		message: "Todo ha ido OK."
 * });
 */

/*global define */
/*global jQuery */

(function (factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(2)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		factory(jQuery);
	}
})(function ($) {

	//*****************************************************************************************************************
	// DEFINICIÓN BASE DEL PATRÓN (definición de la variable privada que contendrá los métodos y la función de jQuery)
	//*****************************************************************************************************************

	var rup_messages = {};

	//Se configura el arranque de UDA para que alberge el nuevo patrón
	$.extend($.rup.iniRup, $.rup.rupObjectConstructor('rup_messages', rup_messages));

	window.alert = function (text) {
		$.rup_messages('msgAlert', {
			title: $.rup.i18nParse($.rup.i18n.base, 'rup_message.alert'),
			message: text
		});
	};

	//********************************
	// DEFINICIÓN DE MÉTODOS PÚBLICOS
	//********************************

	/**
     * Función a ejecutar justo antes de que se cierre la ventana.
     *
     * @callback jQuery.rup_messages~beforeCloseCallback
     * @param {Object} event - Objeto Event de jQuery.
     */

	/**
     * Función a ejecutar cuando el usuario pulsa el botón de Aceptar.
     *
     * @callback jQuery.rup_messages~OKFunctionCallback
     * @param {Object} event - Objeto Event de jQuery.
     * @param {Object} ui - Objeto de tipo jQueryUi Dialog.
     */

	/**
     * Función a ejecutar cuando el usuario pulsa el enlace de Cancelar.
     *
     * @callback jQuery.rup_messages~CANCELFunctionCallback
     * @param {Object} event - Objeto Event de jQuery.
     * @param {Object} ui - Objeto de tipo jQueryUi Dialog
     */

	$.rup_messages('extend', {
		/**
         * Muestra un mensaje de error.
         *
         * @function  msgError
         * @param {Object} properties - Objeto de configuración del mensaje de error.
         * @param {String} properties.title - Función a ejecutar justo antes de que se cierre la ventana.
         * @param {String} properties.message - El mensaje de error que se quiere mostrar. Dicho mensaje se situará a la derecha de la imagen de error. El mensaje puede ser texto plano o contener etiquetas HTML que se reflejarán en el mismo.
         * @param {jQuery.rup_messages~beforeCloseCallback} properties.beforeClose - Texto que aparecerá en la barra del titulo del mensaje.
         *
         * @example
         * // Mostrar un mensaje de error.
         * $.rup_messages("msgError", {
         *      title: "Error grave",
         *      message: "<p>Se ha producido un error a la hora de intentar guardar el registro.<br>Consulte con el administrador.</p>"
         * });
         */
		msgError: function msgError(properties) {
			//Se recogen y cruzan las paremetrizaciones del objeto
			var $this = this,
			    settings = $.extend({}, $.rup_messages.defaults, properties),
			    docHeight,
			    docWidth,
			    focused = $(document.activeElement);
			this._rupProperties(settings, $.rup.i18nParse($.rup.i18n.base, 'rup_message.tituloError'));

			settings._close = settings.close;
			settings.close = function (event, ui) {
				focused.focus();
				if (settings._close !== undefined) {
					$this._destroy(self);
				}
			};

			//parámetros específicos de tipo de mensaje
			settings.buttons = [{
				text: $.rup.i18nParse($.rup.i18n.base, 'rup_message.aceptar'),
				click: function click() {
					$this._destroy(self);
				}
			}];

			var self = this._createDiv().appendTo('body');
			self.dialog(settings);
			self.data('uiDialog').uiDialog.addClass('rup-message rup-message-error');
			this._createCloseLink(self);
			this._addStyles(self, 'error', settings.message);
			docHeight = $(document).height();
			docWidth = $(document).width();
			self.dialog('open');
			this._dialogInPortal(docWidth, docHeight, self, settings);
		},
		/**
         * Muestra un mensaje de confirmación.
         *
         * @function  msgConfirm
         * @param {Object} properties - Objeto de configuración del mensaje de error.
         * @param {String} properties.title - Texto que aparecerá en la barra del titulo del mensaje.
         * @param {String} properties.message - El mensaje de error que se quiere mostrar. Dicho mensaje se situará a la derecha de la imagen de error. El mensaje puede ser texto plano o contener etiquetas HTML que se reflejarán en el mismo.
         * @param {jQuery.rup_messages~beforeCloseCallback} properties.beforeClose - Función a ejecutar justo antes de que se cierre la ventana.
         * @param {jQuery.rup_messages~OKFunctionCallback} properties.OKFunction - Función a ejecutar cuando el usuario pulsa el botón de Aceptar.
         * @param {jQuery.rup_messages~CANCELFunctionCallback} properties.CANCELFunction - Función a ejecutar cuando el usuario pulsa el enlace de Cancelar.
         * @example
         * // funciones de callback.
         * function acceptClicked() { alert("Ha pulsado aceptar."); }
         * function cancelClicked() { alert("Ha pulsado cancelar."); }
         *
         * // Mostrar un mensaje de error.
         * $.rup_messages("msgConfirm", {
         *      title: "Confirmación",
         *      message: "¿Está seguro que desea cancelar?",
         *      OKFunction : acceptClicked,
         *      CANCELFunction : cancelClicked
         * });
         */
		msgConfirm: function msgConfirm(properties) {
			//Se recogen y cruzan las paremetrizaciones del objeto
			var $this = this,
			    settings = $.extend({}, $.rup_messages.defaults, properties),
			    docHeight,
			    docWidth,
			    focused = $(document.activeElement);
			this._rupProperties(settings, $.rup.i18nParse($.rup.i18n.base, 'rup_message.confirmacion'));

			settings._close = settings.close;
			settings.close = function (event, ui) {
				focused.focus();
				if (settings._close !== undefined) {
					$this._destroy(self);
				}
			};

			var self = this._createDiv().appendTo('body'),
			    aceptButton;
			self.dialog(settings);
			self.data('uiDialog').uiDialog.addClass('rup-message rup-message-confirm');

			//parámetros específicos de tipo de mensaje
			aceptButton = [{
				text: $.rup.i18nParse($.rup.i18n.base, 'rup_message.aceptar'),
				class: "btn-outline-primary",
				click: function click() {
					$this._destroy(self);
					settings.OKFunction.call(this, self);
				}
			}];
			self.dialog('option', 'buttons', aceptButton);

			this._createCloseLink(self);
			this._addStyles(self, 'confirm', settings.message);
			this._createLinkButton(self, settings.CANCELFunction);
			docHeight = $(document).height();
			docWidth = $(document).width();
			self.dialog('open');
			this._dialogInPortal(docWidth, docHeight, self, settings);

			//Le ponemos el foco al botón aceptar en vez de al enlace
			$('div[aria-describedby=' + self[0].id + '] .ui-dialog-buttonpane button:first').focus();
		},
		/**
         * Muestra un mensaje de aviso.
         *
         * @function  msgOK
         * @param {Object} properties - Objeto de configuración del mensaje de aviso.
         * @param {String} properties.title - Texto que aparecerá en la barra del titulo del mensaje.
         * @param {String} properties.message - El mensaje de error que se quiere mostrar. Dicho mensaje se situará a la derecha de la imagen de error. El mensaje puede ser texto plano o contener etiquetas HTML que se reflejarán en el mismo.
         * @param {jQuery.rup_messages~beforeCloseCallback} properties.beforeClose - Función a ejecutar justo antes de que se cierre la ventana.
         * @example
         * // Mostrar un mensaje de aviso.
         * $.rup_messages("msgOK", {
         *      title: "Correcto",
         *      message: "Todo ha ido OK."
         * });
         */
		msgOK: function msgOK(properties) {
			//Se recogen y cruzan las paremetrizaciones del objeto
			var $this = this,
			    settings = $.extend({}, $.rup_messages.defaults, properties),
			    docHeight,
			    docWidth,
			    focused = $(document.activeElement);
			this._rupProperties(settings, $.rup.i18nParse($.rup.i18n.base, 'rup_message.correct'));

			settings._close = settings.close;
			settings.close = function (event, ui) {
				focused.focus();
				if (settings._close !== undefined) {
					$this._destroy(self);
				}
			};

			//parámetros específicos de tipo de mensaje
			settings.buttons = [{
				text: $.rup.i18nParse($.rup.i18n.base, 'rup_message.aceptar'),
				click: function click() {
					$this._destroy(self);
				}
			}];

			var self = this._createDiv().appendTo('body');
			self.dialog(settings);
			self.data('uiDialog').uiDialog.addClass('rup-message rup-message-ok');

			this._createCloseLink(self);
			this._addStyles(self, 'ok', settings.message);
			docHeight = $(document).height();
			docWidth = $(document).width();
			self.dialog('open');
			this._dialogInPortal(docWidth, docHeight, self, settings);
		},
		/**
         * Muestra un mensaje de alerta.
         *
         * @function  msgAlert
         * @param {Object} properties - Objeto de configuración del mensaje de alerta.
         * @param {String} properties.title - Texto que aparecerá en la barra del titulo del mensaje.
         * @param {String} properties.message - El mensaje de error que se quiere mostrar. Dicho mensaje se situará a la derecha de la imagen de error. El mensaje puede ser texto plano o contener etiquetas HTML que se reflejarán en el mismo.
         * @param {jQuery.rup_messages~beforeCloseCallback} properties.beforeClose - Función a ejecutar justo antes de que se cierre la ventana.
         * @example
         * // Mostrar un mensaje de aviso.
         * $.rup_messages("msgAlert", {
         *      title: "Alerta",
         *      message: "Esto es una alerta."
         * });
         */
		msgAlert: function msgAlert(properties) {
			//Se recogen y cruzan las paremetrizaciones del objeto
			var $this = this,
			    settings = $.extend({}, $.rup_messages.defaults, properties),
			    docHeight,
			    docWidth,
			    focused = $(document.activeElement);
			this._rupProperties(settings, $.rup.i18nParse($.rup.i18n.base, 'rup_message.alert'));

			settings._close = settings.close;
			settings.close = function (event, ui) {
				focused.focus();
				if (settings._close !== undefined) {
					$this._destroy(self);
				}
			};

			//parámetros específicos de tipo de mensaje
			settings.buttons = [{
				text: $.rup.i18nParse($.rup.i18n.base, 'rup_message.aceptar'),
				click: function click() {
					$this._destroy(self);
				}
			}];

			var self = this._createDiv().appendTo('body');
			self.dialog(settings);
			self.data('uiDialog').uiDialog.addClass('rup-message rup-message-alert');
			this._createCloseLink(self);
			this._addStyles(self, 'alert', settings.message);
			docHeight = $(document).height();
			docWidth = $(document).width();
			self.dialog('open');
			this._dialogInPortal(docWidth, docHeight, self, settings);
		}
	});

	//********************************
	// DEFINICIÓN DE MÉTODOS PRIVADOS
	//********************************

	$.rup_messages('extend', {
		_destroy: function _destroy(self) {
			self.dialog('destroy').remove();
		},
		/**
         * Crea los divs de los mensajes.
         *
         * @function  _createDiv
         * @private
         */
		_createDiv: function _createDiv() {
			return $('<div/>').attr('id', 'rup_msgDIV_' + new Date().getTime()).attr('rup_message', 'true');
		},
		/**
         * Crea los el enlace de cerrar en el título del mensaje de acuerdo a los estándares de accesibilidad.
         *
         * @param {Object} self - Referencia a la propia instancia.
         * @function  _createCloseLink
         * @private
         */
		_createCloseLink: function _createCloseLink(self) {
			//Crea el enlace de cerrar junto a la x de cerrar.
			var closeSpan = '<span id=\'closeText_' + self[0].id + '\' style=\'float:right;font-size:0.85em;\'>' + $.rup.i18nParse($.rup.i18n.base, 'rup_global.cerrar') + '</span>',
			    aClose = $('<a href=\'#\'></a>').attr('role', 'button').css('margin-right', '0.9em').css('float', 'right').addClass('ui-dialog-title').html(closeSpan).click(function (event) {
				self.dialog('close');
				return false;
			}).hover(function (eventObject) {
				//Evento lanzado para que se cambie el icono de la X a hover, marcado por ARISTA
				$('div[aria-describedby=' + self[0].id + '] .ui-dialog-titlebar-close').addClass('ui-state-hover');
				$('div[aria-describedby=' + self[0].id + '] .ui-dialog-titlebar-close').css('padding', '0px');
			}, function (eventObject) {
				$('div[aria-describedby=' + self[0].id + '] .ui-dialog-titlebar-close').removeClass('ui-state-hover');
				$('div[aria-describedby=' + self[0].id + '] .ui-dialog-titlebar-close').attr('style', '');
			}).insertAfter(jQuery('span.ui-dialog-title', self.parent()));
			$('div[aria-describedby=' + self[0].id + '] .ui-dialog-titlebar-close').hover(function () {
				aClose.css('text-decoration', 'none');
			}, function () {
				aClose.css('text-decoration', '');
			});
		},
		/**
         * Aplica el estilo correspondiente al tipo de mensaje a mostrar así como el contenido del mensaje en sí.
         *
         * @param {Object} self - Referencia a la propia instancia.
         * @param {string} css - Clase css correspondiente al tipo de mensaje a mostrar.
         * @param {string} message - Cuerpo del mensaje a visualizar.
         * @function  _addStyles
         * @private
         */
		_addStyles: function _addStyles(self, css, message) {
			//Le a?ade los divs del mensaje a mostrar y el icono correpondiente
			var divMessageIcon = $('<div>').attr('id', 'rup_msgDIV_msg_icon').addClass('rup-message_icon-' + css),
			    divMessage = $('<div>').attr('id', 'rup_msgDIV_msg').addClass('rup-message_msg-' + css).html(message);
			self.append(divMessageIcon);
			self.append(divMessage);
		},
		/**
         * Genera un enlace "Cancelar" para el mensaje de tipo confirmación.
         *
         * @param {Object} self - Referencia a la propia instancia.
         * @param {string} css - Clase css correspondiente al tipo de mensaje a mostrar.
         * @param {jQuery.rup_messages~CANCELFunctionCallback} CANCELFunction - Función a ejecutar cuando el usuario pulsa el enlace de Cancelar.
         * @function  _createLinkButton
         * @private
         */
		_createLinkButton: function _createLinkButton(self, CANCELFunction) {
			//Creamos un boton
			var clickFnc = CANCELFunction,
			    cancelHREF = $('<button></button>').attr('type', 'button').attr('id', self[0].id + '_cancel').addClass('btn-outline-primary ui-button ui-corner-all ui-widget').html($.rup.i18nParse($.rup.i18n.base, 'rup_global.cancel')).click(function (event) {
				self.dialog('close');
				if (clickFnc !== undefined) {
					clickFnc.call(this, self);
				}
				return false;
			});
			$('div[aria-describedby=' + self[0].id + '] .ui-dialog-buttonset ').append(cancelHREF);
		},
		/**
         * Ajuste en la visualización del mensaje para que se muestre correctamente en aplicaciones integradas en portal.
         *
         * @param {Number} docWidth - Anchura en pixeles del objeto document.
         * @param {Number} docHeight - Altura en pixeles del objeto document.
         * @param {Object} $self - Referencia a la propia instancia.
         * @param {Object} settings - Objeto de configuración del componente.
         * @function  _dialogInPortal
         * @private
         */
		_dialogInPortal: function _dialogInPortal(docWidth, docHeight, $self, settings) {
			var $overlayEl;

			if ($.rup_utils.aplicatioInPortal()) {
				if ($self.data('uiDialog').overlay !== null) {
					$overlayEl = $self.data('uiDialog').overlay;
					$overlayEl.css('height', docHeight).css('width', docWidth);
					$('.r01gContainer').append($overlayEl).append($self.data('uiDialog').uiDialog);
				}
				if (settings.position === undefined || settings.position === null) {
					$self.data('uiDialog').uiDialog.css('position', 'absolute').css('top', docHeight / 2 - $('.ui-dialog:visible').height() / 2);
				}
			}
		},
		/**
         * Realiza la inicialización de las propiedades utilizadas para configurar correctamente el plugin jQueryUi Dialog. </br></br>
         * La inicialización se realiza sobre las propiedades introducidas por el usuario de modo que se garantiza que la visualización del componente es siempre la adecuada.
         *
         * @name _rupProperties
         * @param {Object} properties - Propiedades de configuración sobre las que se va a realizar la inicialización-
         * @param {string} title - Titulo a mostrar en el mensaje.
         * @function
         * @private
         */
		_rupProperties: function _rupProperties(properties, title) {
			properties.autoOpen = false;
			properties.modal = true, properties.resizable = false, properties.title = properties.title === null || properties.title === '' ? title : properties.title;
			properties.closeText = $.rup.i18nParse($.rup.i18n.base, 'rup_message.tituloError.cerrar'), properties.close = function () {
				$(this).remove();
			};
		}
	});

	//******************************************************
	// DEFINICIN DE LA CONFIGURACION POR DEFECTO DEL PATRON
	//******************************************************
	/**
     * @description Opciones por defecto de configuración del componente.
     *
     * @name defaults
     *
     * @property {Number}  [minHeight=100] - Altura mínima con la que se va a mostrar el mensaje.
     */
	$.rup_messages.defaults = {
		minHeight: 100
	};
});
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))

/***/ }),
/* 161 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*!
 * Copyright 2016 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 */

/*global define */
/*global jQuery */

/**
 * Proporciona una herramienta para navegar a través de las aplicación web.
 * 
 * @summary Componente RUP Navbar
 * @module rup_navbar
 * @example
 * var html = '<nav class="rup-navbar navbar">\
                <button type="button" class="navbar-toggler hidden-lg-up navbar-toggle" \
                    type="button" data-toggle="rup-collapse" data-target="#navbarResponsive"\
                    aria-controls="navbarResponsive" aria-expanded="false" aria-label="Toggle navigation">\
                </button>\
                <a class="navbar-brand" href="#">Uda</a>\
                    <ul class="nav navbar-nav">\
                        <li class="nav-item dropdown">\
                            <a class="nav-link dropdown-toggle" href="#"\
                                id="navDropdownUno" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false">\
                                Padre1\
                            </a>\
                            <div class="collapse dropdown-toggle" aria-labelledby="navDropdownUno">\
                                <a href="#" class="dropdown-item">Elem11</a>\
                                <a href="#" class="dropdown-item">Elem12</a>\
                            </div>\
                        </li>\
                        <li class="nav-item dropdown">\
                                <a class="nav-link dropdown-toggle" href="#"\
                                    id="navDropdownUno" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false">\
                                    Padre2\
                                </a>\
                                <div class="collapse dropdown-toggle" aria-labelledby="navDropdownUno">\
                                    <a href="#" class="dropdown-item">Elem21</a>\
                                    <a href="#" class="dropdown-item">Elem22</a>\
                                </div>\
                            </li>\
                    </ul>\
                    <ul class="nav navbar-nav float-md-right rup-nav-tools">\
                        <li class="nav-item dropdown">\
                            <a class="nav-link dropdown-toggle" href="#"\
                                id="navDropdownUno" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false">\
                                Padre3\
                            </a>\
                            <div class="collapse dropdown-toggle" aria-labelledby="navDropdownUno">\
                                <a href="#" class="dropdown-item">Elem31</a>\
                                <a href="#" class="dropdown-item">Elem32</a>\
                            </div>\
                        </li>\
                        <li class="nav-item dropdown">\
                                <a class="nav-link dropdown-toggle" href="#"\
                                    id="navDropdownUno" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false">\
                                    Padre4\
                                </a>\
                                <div class="collapse dropdown-toggle" aria-labelledby="navDropdownUno">\
                                    <a href="#" class="dropdown-item">Elem41</a>\
                                    <a href="#" class="dropdown-item">Elem42</a>\
                                </div>\
                            </li>\
                    </ul>\
			  </nav>';
		$('#content').append(html);
		$('nav').rup_navbar(); 
 */
(function (factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(2), __webpack_require__(22), __webpack_require__(211), __webpack_require__(15)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		factory(jQuery);
	}
})(function ($, RupBase, Util, Dropdown) {

	var rup_navbar = {};

	var TRANSITION_DURATION = 600;
	var DATA_KEY = 'rup.collapse';
	var EVENT_KEY = '.' + DATA_KEY;
	var DATA_API_KEY = '.data-api';

	var Event = {
		SHOW: 'show' + EVENT_KEY,
		SHOWN: 'shown' + EVENT_KEY,
		HIDE: 'hide' + EVENT_KEY,
		HIDDEN: 'hidden' + EVENT_KEY,
		CLICK_DATA_API: 'click' + EVENT_KEY + DATA_API_KEY
	};

	var ClassName = {
		SHOW: 'show',
		COLLAPSE: 'rup-collapse',
		COLLAPSING: 'rup-collapsing',
		COLLAPSED: 'rup-collapsed'
	};

	var Selector = {
		ACTIVES: '.card > .show, .card > .collapsing',
		DATA_TOGGLE: '[data-toggle="collapse"]'
	};

	var Dimension = {
		WIDTH: 'width',
		HEIGHT: 'height'
	};

	// $(document).off(".dropdown.data-api");
	// $(document).off(".collapse.data-api");


	//Se configura el arranque de UDA para que alberge el nuevo patrón
	$.extend($.rup.iniRup, $.rup.rupSelectorObjectConstructor('rup_navbar', rup_navbar));

	//*******************************
	// DEFINICIÓN DE MÉTODOS PÚBLICOS
	//*******************************
	$.fn.rup_navbar('extend', {});

	$.fn.rup_navbar('extend', {
		/**
   * Funcion que alterna el estado del navbar entre desplegado y oculto.
   * @function
   * @name toggle
   * @example
   * $('nav').rup_navbar('toggle');
   */
		toggle: function toggle() {
			if ($(this._element).hasClass(ClassName.SHOW)) {
				this.hide();
			} else {
				this.show();
			}
		},
		/**
   * Funcion que despliega el navbar.
   * @function
   * @name show
   * @example
   * $('nav').rup_navbar('show');
   */
		show: function show() {
			var _this = this;

			if (this._isTransitioning || $(this._element).hasClass(ClassName.SHOW)) {
				return;
			}

			var actives = void 0;
			var activesData = void 0;
			this._element = $(this)[0];

			if (this._parent) {
				actives = $.makeArray($(Selector.ACTIVES));
				if (!actives.length) {
					actives = null;
				}
			}

			// if (actives) {
			// 	activesData = $(actives).data(DATA_KEY);
			// 	if (activesData && activesData._isTransitioning) {
			// 		return;
			// 	}
			// }

			var startEvent = $.Event(Event.SHOW);
			$(this._element).trigger(startEvent);
			if (startEvent.isDefaultPrevented()) {
				return;
			}

			// if (actives) {
			// 	Collapse._jQueryInterface.call($(actives), 'hide');
			// 	if (!activesData) {
			// 		$(actives).data(DATA_KEY, null);
			// 	}
			// }

			var dimension = this._getDimension();

			$(this._element).removeClass(ClassName.COLLAPSE).addClass(ClassName.COLLAPSING);

			this._element.style[dimension] = 0;
			this._element.setAttribute('aria-expanded', true);

			if (this._triggerArray.length) {
				$(this._triggerArray).removeClass(ClassName.COLLAPSED).attr('aria-expanded', true);
			}

			this.setTransitioning(true);

			var complete = function complete() {
				$(_this._element).removeClass(ClassName.COLLAPSING).addClass(ClassName.COLLAPSE).addClass(ClassName.SHOW);

				_this._element.style[dimension] = '';

				_this.setTransitioning(false);

				$(_this._element).trigger(Event.SHOWN);
			};

			// if (!Util.default.supportsTransitionEnd()) {
			complete();
			// return;
			// }

			var capitalizedDimension = dimension[0].toUpperCase() + dimension.slice(1);
			var scrollSize = 'scroll' + capitalizedDimension;

			$(this._element).one(Util.TRANSITION_END, complete).emulateTransitionEnd(TRANSITION_DURATION);
		},
		/**
   * Funcion que oculta el navbar.
   * @function
   * @name hide
   * @example
   * $('nav').rup_navbar('hide');
   */
		hide: function hide() {
			var _this2 = this;

			if (this._isTransitioning || !$(this._element).hasClass(ClassName.SHOW)) {
				return;
			}

			var startEvent = $.Event(Event.HIDE);
			$(this._element).trigger(startEvent);
			if (startEvent.isDefaultPrevented()) {
				return;
			}

			var dimension = this._getDimension();
			var offsetDimension = dimension === Dimension.WIDTH ? 'offsetWidth' : 'offsetHeight';

			Util.default.reflow(this._element);

			$(this._element).addClass(ClassName.COLLAPSING).removeClass(ClassName.COLLAPSE).removeClass(ClassName.SHOW);

			this._element.setAttribute('aria-expanded', false);

			if (this._triggerArray.length) {
				$(this._triggerArray).addClass(ClassName.COLLAPSED).attr('aria-expanded', false);
			}

			this.setTransitioning(true);

			var complete = function complete() {
				_this2.setTransitioning(false);
				$(_this2._element).removeClass(ClassName.COLLAPSING).addClass(ClassName.COLLAPSE).trigger(Event.HIDDEN);
			};

			this._element.style[dimension] = '';

			// if (!Util.default.supportsTransitionEnd()) {
			complete();
			// return;
			// }

			$(this._element).one(Util.defaultTRANSITION_END, complete).emulateTransitionEnd(TRANSITION_DURATION);
		},
		/**
   * Define si habrá o no transición al desplegar y ocultar el navbar
   * @function
   * @name setTransitioning
   * @param {boolean} transición -True: hay transicion; False: no hay transicion
   * @example
   * $('nav').rup_navbar('setTransitioning', true);
   */
		setTransitioning: function setTransitioning(isTransitioning) {
			this._isTransitioning = isTransitioning;
		},
		_getDimension: function _getDimension() {
			var hasWidth = $(this._element).hasClass(Dimension.WIDTH);
			return hasWidth ? Dimension.WIDTH : Dimension.HEIGHT;
		},

		_init: function _init(args) {
			var $self = this;

			$self._isTransitioning = false;
			$self._element = $self[0];
			// this._config          = this._getConfig(args);

			// $('[data-toggle="collapse"]', $self).each(function(elem){
			// 	elem.attr('data-toggle', 'rup-colapse');
			// });

			$self._triggerArray = $.makeArray($('[data-toggle="rup-colapse"][href="#' + $self._element.id + '"],' + ('[data-toggle="rup-colapse"][data-target="#' + $self._element.id + '"]')));

			// this._parent = this._config.parent ? this._getParent() : null;

			// if (!this._config.parent) {
			// 	this._addAriaAndCollapsedClass(this._element, this._triggerArray);
			// }

			// if (this._config.toggle) {
			// 	this.toggle();
			// }

			// El botón de volver a la parte superior del contenido
			$('nav .swingTop').off('click').on('click', function () {
				$('.navbar-toggler:visible').click();
				$.rup_utils.swing2Top();
			});

			// Hacer click fuera de menú lo cierra
			$('#overlay').on('click tap', function () {
				$('.navbar-toggler:visible').click();
			});

			// Funcionamiento de apertura del menú
			$('.navbar-toggler').on('click tap', function () {
				$self.toggle();
				$('#overlay').toggleClass('on');
				$('.navbar-toggleable-md .rup-open').removeClass('rup-open');
			});

			// Cierre de menú al navegar a un item
			$('nav .dropdown-item').not('.dropdown-toggle').on('click', function () {
				$('.navbar-toggler:visible').click();
			});

			// Funcionamiento acordeón entre desplegables en el menú
			$('nav .dropdown>a').on('click tap', function () {
				$('nav .dropdown>a').not($(this)).parent().removeClass('rup-open');
				$(this).parent().toggleClass('rup-open');
			});

			$('.dropdown-toggle', $self).dropdown();

			// Funcionamiento de apertura de sub-desplegables en el menú
			$('nav .dropdown-submenu a').on('click tap', function () {
				$('nav .dropdown-submenu a').not($(this)).parent().removeClass('rup-open');
				$(this).parent().toggleClass('rup-open');

				var menuScrollPos = 0;
				var end = $(this).parent().index();
				$(this).parent().siblings().each(function (i, e) {
					if (i < end) {
						if ($(e).children('.dropdown-menu').length > 0) {
							menuScrollPos += $(e).children('.dropdown-item:first').outerHeight(true);
						} else {
							menuScrollPos += $(e).outerHeight(true);
						}
					}
				});
				$(this).parent().parent().animate({
					scrollTop: menuScrollPos
				}, 500);
			});
		}
	});
});

/***/ }),
/* 162 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*!
 * Copyright 2016 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 */

/**
 * Tiene como objetivo mostrar al usuario de manera gráfica el estado de avance de una tarea o proceso.
 *
 * @summary Componente RUP ProgressBar.
 * @module rup_progressbar
 * @see El componente está basado en el plugin {@link https://jqueryui.com/progressbar/|jQuery UI ProgressBar}. Para mas información acerca de las funcionalidades y opciones de configuración pinche {@link http://api.jqueryui.com/progressbar/|aquí}.
 * @example
 * var properties = {
 *		value: 50
 *	};
 * $("#idProgressbar").rup_progressbar(properties);
 */

/*global define */
/*global jQuery */

(function (factory) {
  if (true) {

    // AMD. Register as an anonymous module.
    !(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(2)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
  } else {

    // Browser globals
    factory(jQuery);
  }
})(function ($) {

  //****************************************************************************************************************
  // DEFINICIÓN BASE DEL PATRÓN (definición de la variable privada que contendrá los métodos y la función de jQuery)
  //****************************************************************************************************************

  var rup_progressbar = {};

  //Se configura el arranque de UDA para que alberge el nuevo patrón
  $.extend($.rup.iniRup, $.rup.rupSelectorObjectConstructor('rup_progressbar', rup_progressbar));

  //*******************************
  // DEFINICIÓN DE MÉTODOS PÚBLICOS
  //*******************************
  $.fn.rup_progressbar('extend', {
    /**
           * Método utilizado para obtener el valor del componente. Este método es el utilizado por el resto de componentes RUP para estandarizar la obtención del valor de la barra de progreso.
           *
           * @name getRupValue
           * @function
           * @return {number} - Devuelve el valor actual del componente. El valor retornado se corresponderá con el progreso actual.
           * @example
           * $("#idProgressbar").rup_progressbar("getRupValue");
           */
    getRupValue: function getRupValue() {
      var $self = this;
      return $self.progressbar('value');
    },
    /**
     * Método utilizado para asignar el valor al componente. Este método es el utilizado por
    el resto de componentes RUP para estandarizar la asignación del valor a la barra de progreso.
     *
     * @name setRupValue
     * @function
     * @param {number} param - Valor que se va a asignar al componente.
     * @return {jQuery} - Retorna la referencia al elemento.
     * @example
     * $("#idProgressbar").rup_progressbar("setRupValue", 50);
     */
    setRupValue: function setRupValue(param) {
      var $self = this;

      $self.progressbar('value', param);

      return $self;
    },
    /**
           * Elimina las modificaciones realizadas sobre elemento del DOM.
           *
           * @name destroy
           * @function
           * @return {jQuery} - Retorna la referencia al elemento.
           * @example
           * // Elimina la barra de progreso
           * jQuery("#idProgressbar").rup_progressbar("destroy");
           */
    destroy: function destroy() {
      var $self = this;

      $self.removeClass('rup_progressbar');
      $self.removeAttr('ruptype');
      $self.progressbar('destroy');
      $self.find('div.rup-progressbar-label').remove();

      return $self;
    },
    /**
           * Deshabilita la barra de progreso.
           *
           * @name disable
           * @function
           * @return {jQuery} - Retorna la referencia al elemento.
           * @example
           * jQuery("#idProgressbar").rup_progressbar("disable");
           */
    disable: function disable() {
      this.progressbar('disable');
      this.addClass('rup-progressbar-disabled');
      return this;
    },
    /**
           * Habilita la barra de progreso.
           *
           * @name enable
           * @function
           * @return {jQuery} - Retorna la referencia al elemento.
           * @example
           * jQuery("#idProgressbar").rup_progressbar("enable");
           */
    enable: function enable() {
      this.progressbar('enable');
      this.removeClass('rup-progressbar-disabled');
      return this;
    },
    /**
           * Devuelve la instancia de jQueryUI asociada a la barra de progreso. Si no ha sido inicializada retorna undefined.
           *
           * @name instance
           * @function
           * @return {object} - Instancia de jQueryUI asociada.
           * @example
           * jQuery("#idProgressbar").rup_progressbar("instance");
           */
    instance: function instance() {
      return this.progressbar('instance');
    },
    /**
           * Devuelve un objeto clave/valor que contiene las propiedades de configuración de la barra de progreso.
           *
           * @name option
           * @function
           * @return {object} - Objeto clave/valor con las propiedades de configuración.
           * @example
           * jQuery("#idProgressbar").rup_progressbar("option");
           */
    /**
           * Devuelve el valor asociado a la propiedad identificada por parámetro.
           *
           * @name option
           * @function
           * @param {string} paramName - Nombre de la propiedad.
           * @return {object} - Valor asociado a la propiedad.
           * @example
           * jQuery("#idProgressbar").rup_progressbar("option", "value");
           */
    /**
           * Asigna un valor a la propiedad indentificada por parámetro.
           *
           * @name option
           * @function
           * @param {string} paramName - Nombre de la propiedad.
           * @param {object} paramValue - Valor de la propiedad.
           * @return {jQuery} - Retorna la referencia al elemento.
           * @example
           * jQuery("#idProgressbar").rup_progressbar("option", "value", 50);
           */
    /**
           * Permite asignar el valor de una o varias propiedades de configuración.
           *
           * @name option
           * @function
           * @param {object} param - Objeto clave/valor con las propiedades de configuración y sus valores.
           * @return {jQuery} - Retorna la referencia al elemento.
           * @example
           * jQuery("#idProgressbar").rup_progressbar("option", {value:50, max:0});
           */
    option: function option() {
      if (arguments.length === 0) {
        return this.progressbar('option');
      } else if (arguments.length === 1) {
        return this.progressbar('option', arguments[0]);
      } else {
        return this.progressbar('option', arguments[0], arguments[1]);
      }
    },
    /**
           * Devuelve el valor actual de la barra de progreso.
           *
           * @name value
           * @function
           * @return {number} - Valor actual de la barra de progreso.
           * @example
           * jQuery("#idProgressbar").rup_progressbar("value");
           */
    /**
           * Asigna un valor a la barra de progreso.
           *
           * @name value
           * @function
           * @param {number} value - Valor a asignar.
           * @return {jQuery} - Retorna la referencia al elemento.
           * @example
           * jQuery("#idProgressbar").rup_progressbar("value", 50);
           */
    value: function value(args) {
      return this.progressbar('value', args);
    },
    /**
           * Devuelve el objeto widget de jQuery que contiene la barra de progreso.
           *
           * @name widget
           * @function
           * @return {jQuery} - Objeto widget jQuery.
           * @example
           * jQuery("#idProgressbar").rup_progressbar("widget");
           */
    widget: function widget() {
      return this.progressbar('widget');
    }
  });

  $.fn.rup_progressbar('extend', {
    _printLabel: function _printLabel() {
      var $self = this;
    }
  });

  //*******************************
  // MÉTODO DE INICIALIZACION
  //*******************************
  $.fn.rup_progressbar('extend', {
    _init: function _init(args) {
      var $self = this,
          settings = $.extend({}, $.fn.rup_progressbar.defaults, args[0]);

      $self.addClass('rup-progressbar');
      $self.attr('ruptype', 'progressbar');

      $self.progressbar(settings);

      if (settings.label) {
        settings.$label = $('<div>').addClass('rup-progressbar-label');
        $self.append(settings.$label);
        settings.$label.html(settings.label.replace('${value}', $self.rup_progressbar('getRupValue')).replace('${max}', $self.rup_progressbar('option', 'max')));
        $self.on('progressbarchange', function () {
          settings.$label.html(settings.label.replace('${value}', $self.rup_progressbar('getRupValue')).replace('${max}', $self.rup_progressbar('option', 'max')));
        });
      }
    }
  });

  //******************************************************
  // DEFINICIÓN DE LA CONFIGURACION POR DEFECTO DEL PATRON
  //******************************************************
  /**
      * @description Propiedades de configuración del componente.
      *
      * @name defaults
      * @property {boolean} [disabled=false] - Determina si la barra de progreso está habilitada o deshabilitada.
      * @property {number} [max=100] - Indica el valor máximo que determinará el 100% de progreso.
      * @property {number} [value=0] - Determina el valor de progreso con el que se incializará la barra de progreso.
      */
  $.fn.rup_progressbar.defaults = {
    disabled: false,
    max: 100,
    value: 0,
    label: undefined
  };
});

/***/ }),
/* 163 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*!
 * Copyright 2016 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 */

/**
 * Tiene como objetivo permitir al usuario introducir datos mediante un control que se desplaza dentro de un rango de valores.
 *
 * @summary Componente RUP Slider.
 * @module rup_slider
 * @see El componente está basado en el plugin {@link https://jqueryui.com/slider/|jQuery UI Slider}. Para mas información acerca de las funcionalidades y opciones de configuración pinche {@link http://api.jqueryui.com/slider/|aquí}.
 * @example
 * var properties = {
 *		min: 0,
 *		max: 500
 *	};
 * $("#idSlider").rup_slider(properties);
 */

/*global define */
/*global jQuery */

(function (factory) {
  if (true) {

    // AMD. Register as an anonymous module.
    !(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(2)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
  } else {

    // Browser globals
    factory(jQuery);
  }
})(function ($) {

  //****************************************************************************************************************
  // DEFINICIÓN BASE DEL PATRÓN (definición de la variable privada que contendrá los métodos y la función de jQuery)
  //****************************************************************************************************************


  var rup_slider = {};

  //Se configura el arranque de UDA para que alberge el nuevo patrón
  $.extend($.rup.iniRup, $.rup.rupSelectorObjectConstructor('rup_slider', rup_slider));

  //*******************************
  // DEFINICIÓN DE MÉTODOS PÚBLICOS
  //*******************************
  $.fn.rup_slider('extend', {
    /**
           * Método utilizado para obtener el valor del componente. Este método es el utilizado por el resto de componentes RUP para estandarizar la obtención del valor del componente Slider.
           *
           * @name getRupValue
           * @function
           * @return {number} - Devuelve el valor actual del componente.
           * @example
           * $("#idSlider").rup_slider("getRupValue");
           */
    getRupValue: function getRupValue() {
      var $self = this,
          value;

      value = $self.slider('values');

      if (value.length === 0) {
        return $self.slider('value');
      } else {
        return value;
      }
    },
    /**
           * Método utilizado para asignar el valor al componente. Este método es el utilizado por el resto de componentes RUP para estandarizar la asignación del valor al componente Slider.
           *
           * @name setRupValue
           * @function
           * @param {number} param - Valor que se va a asignar al componente.
           * @return {jQuery} - Retorna la referencia al elemento.
           * @example
           * // Un único desplazador
           * $("#idSlider").rup_slider("setRupValue", 40);
           * // Varios desplazadores
           * $("#idSlider").rup_slider("setRupValue", [10,60]);
           */
    setRupValue: function setRupValue(value) {
      var $self = this;

      if ($.isArray(value)) {
        $self.slider('values', value);
      } else {
        $self.slider('value', value);
      }
      return $self;
    },
    /**
           * Elimina las modificaciones realizadas sobre elemento del DOM.
           *
           * @name destroy
           * @function
           * @return {jQuery} - Retorna la referencia al elemento.
           * @example
           * // Elimina el control slider
           * jQuery("#idSlider").rup_slider("destroy");
           */
    destroy: function destroy() {
      var $self = this;

      $self.slider('destroy');
      $self.removeClass('rup-slider');
      $self.removeAttr('ruptype');

      return $self;
    },
    /**
           * Habilita el control.
           *
           * @name enable
           * @function
           * @return {jQuery} - Retorna la referencia al elemento.
           * @example
           * jQuery("#idSlider").rup_slider("enable");
           */
    enable: function enable() {
      var $self = this;

      $self.slider('enable');
      $self.removeClass('rup-slider-disabled');

      return $self;
    },
    /**
           * Deshabilita el control.
           *
           * @name disable
           * @function
           * @return {jQuery} - Retorna la referencia al elemento.
           * @example
           * jQuery("#idSlider").rup_slider("disable");
           */
    disable: function disable() {
      var $self = this;

      $self.slider('disable');
      $self.addClass('rup-slider-disabled');

      return $self;
    },
    /**
           * Devuelve la instancia de jQueryUI asociada al control. Si no ha sido inicializada retorna undefined.
           *
           * @name instance
           * @function
           * @return {object} - Instancia de jQueryUI asociada.
           * @example
           * jQuery("#idSlider").rup_slider("instance");
           */
    instance: function instance() {
      return this.progressbar('instance');
    },
    /**
           * Devuelve un objeto clave/valor que contiene las propiedades de configuración del control.
           *
           * @name option
           * @function
           * @return {object} - Objeto clave/valor con las propiedades de configuración.
           * @example
           * jQuery("#idSlider").rup_slider("option");
           */
    /**
           * Devuelve el valor asociado a la propiedad identificada por parámetro.
           *
           * @name option
           * @function
           * @param {string} paramName - Nombre de la propiedad.
           * @return {object} - Valor asociado a la propiedad.
           * @example
           * jQuery("#idSlider").rup_slider("option", "min");
           */
    /**
           * Asigna un valor a la propiedad indentificada por parámetro.
           *
           * @name option
           * @function
           * @param {string} paramName - Nombre de la propiedad.
           * @param {object} paramValue - Valor de la propiedad.
           * @return {jQuery} - Retorna la referencia al elemento.
           * @example
           * jQuery("#idSlider").rup_slider("option", "min", 50);
           */
    /**
           * Permite asignar el valor de una o varias propiedades de configuración.
           *
           * @name option
           * @function
           * @param {object} param - Objeto clave/valor con las propiedades de configuración y sus valores.
           * @return {jQuery} - Retorna la referencia al elemento.
           * @example
           * jQuery("#idSlider").rup_slider("option", {min:10, max:60});
           */
    option: function option() {
      if (arguments.length === 0) {
        return this.slider('option');
      } else if (arguments.length === 1) {
        return this.slider('option', arguments[0]);
      } else {
        return this.slider('option', arguments[0], arguments[1]);
      }
    },
    value: function value(args) {
      return this.slider('value', args);
    },
    values: function values(args) {
      return this.slider('values', args);
    },
    widget: function widget() {
      return this.slider('widget');
    }
  });

  //*******************************
  // DEFINICIÓN DE MÉTODOS PRIVADOS
  //*******************************

  $.fn.rup_slider('extend', {
    _bar: function _bar() {
      return this;
    }
  });

  //*******************************
  // MÉTODO DE INICIALIZACION
  //*******************************
  $.fn.rup_slider('extend', {
    _init: function _init(args) {
      var $self = this,
          settings = $.extend({}, $.fn.rup_slider.defaults, args[0]);

      $self.addClass('rup-slider');
      $self.attr('ruptype', 'slider');
      $self.slider(settings);
      // TODO : Invocación al plugin

    }
  });

  //******************************************************
  // DEFINICIÓN DE LA CONFIGURACION POR DEFECTO DEL PATRON
  //******************************************************
  $.fn.rup_slider.defaults = {
    foobar: false
  };
});

/***/ }),
/* 164 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*!
 * Copyright 2014 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 */

/*global define */
/*global jQuery */

(function (factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(2)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		factory(jQuery);
	}
})(function ($) {

	//****************************************************************************************************************
	// DEFINICIÓN BASE DEL PATRÓN (definición de la variable privada que contendrá los métodos y la función de jQuery)
	//****************************************************************************************************************

	var rup_spinner = {};

	//Se configura el arranque de UDA para que alberge el nuevo patrón
	$.extend($.rup.iniRup, $.rup.rupSelectorObjectConstructor('rup_spinner', rup_spinner));

	//*******************************
	// DEFINICIÓN DE MÉTODOS PÚBLICOS
	//*******************************
	$.fn.rup_spinner('extend', {
		getRupValue: function getRupValue() {
			var $self = this,
			    value;
			value = this.spinner('value');

			return value;
		},
		setRupValue: function setRupValue(value) {
			var $self = this;

			$self.spinner('value', 5);

			return $self;
		}
	});

	//*******************************
	// DEFINICIÓN DE MÉTODOS PRIVADOS
	//*******************************

	$.fn.rup_spinner('extend', {
		_bar: function _bar() {
			return this;
		}
	});

	//*******************************
	// MÉTODO DE INICIALIZACION
	//*******************************
	$.fn.rup_spinner('extend', {
		_init: function _init(args) {
			var $self = this,
			    settings = $.extend({}, $.fn.rup_spinner.defaults, args[0]);

			$self.addClass('rup_spinner');
			$self.attr('ruptype', 'spinner');
			$self.spinner(settings);
		}
	});

	//******************************************************
	// DEFINICIÓN DE LA CONFIGURACION POR DEFECTO DEL PATRON
	//******************************************************
	$.fn.rup_spinner.defaults = {
		foobar: false
	};
});

/***/ }),
/* 165 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function(jQuery) {var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;var _typeof=typeof Symbol==="function"&&typeof Symbol.iterator==="symbol"?function(obj){return typeof obj;}:function(obj){return obj&&typeof Symbol==="function"&&obj.constructor===Symbol&&obj!==Symbol.prototype?"symbol":typeof obj;};(function(factory){if(true){// AMD. Register as an anonymous module.
!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0),__webpack_require__(2),__webpack_require__(13),__webpack_require__(6),__webpack_require__(16),__webpack_require__(14),__webpack_require__(21)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));}else{// Browser globals
factory(jQuery);}})(function($){// ==ClosureCompiler==
// @compilation_level SIMPLE_OPTIMIZATIONS
/*
 * @license jqGrid  4.4.4  - jQuery Grid
 * Copyright (c) 2008, Tony Tomov, tony@trirand.com
 * Dual licensed under the MIT and GPL licenses
 * http://www.opensource.org/licenses/mit-license.php
 * http://www.gnu.org/licenses/gpl-2.0.html
 * Date: 2013-01-30
 *///jsHint options
/*jshint evil:true, eqeqeq:false, eqnull:true, devel:true *//*global jQuery, DOMParser, ActiveXObject */var rp_ge={};(function($){'use strict';$.jgrid=$.jgrid||{};$.extend($.jgrid,{version:'4.4.4',htmlDecode:function htmlDecode(value){if(value&&(value=='&nbsp;'||value=='&#160;'||value.length===1&&value.charCodeAt(0)===160)){return'';}return!value?value:String(value).replace(/&gt;/g,'>').replace(/&lt;/g,'<').replace(/&quot;/g,'"').replace(/&amp;/g,'&');},htmlEncode:function htmlEncode(value){return!value?value:String(value).replace(/&/g,'&amp;').replace(/\"/g,'&quot;').replace(/</g,'&lt;').replace(/>/g,'&gt;');},format:function format(_format){//jqgformat
var args=$.makeArray(arguments).slice(1);if(_format==null){_format='';}return _format.replace(/\{(\d+)\}/g,function(m,i){return args[i];});},msie:navigator.appName=='Microsoft Internet Explorer',msiever:function msiever(){var rv=-1;var ua=navigator.userAgent;var re=new RegExp('MSIE ([0-9]{1,}[\.0-9]{0,})');if(re.exec(ua)!=null){rv=parseFloat(RegExp.$1);}return rv;},getCellIndex:function getCellIndex(cell){var c=$(cell);if(c.is('tr')){return-1;}c=(!c.is('td')&&!c.is('th')?c.closest('td,th'):c)[0];if($.jgrid.msie){return $.inArray(c,c.parentNode.cells);}return c.cellIndex;},stripHtml:function stripHtml(v){v=String(v);var regexp=/<("[^"]*"|'[^']*'|[^'">])*>/gi;if(v){v=v.replace(regexp,'');return v&&v!=='&nbsp;'&&v!=='&#160;'?v.replace(/\"/g,'\''):'';}return v;},stripPref:function stripPref(pref,id){var obj=$.type(pref);if(obj=='string'||obj=='number'){pref=String(pref);id=pref!==''?String(id).replace(String(pref),''):id;}return id;},stringToDoc:function stringToDoc(xmlString){var xmlDoc;if(typeof xmlString!=='string'){return xmlString;}try{var parser=new DOMParser();xmlDoc=parser.parseFromString(xmlString,'text/xml');}catch(e){xmlDoc=new ActiveXObject('Microsoft.XMLDOM');xmlDoc.async=false;xmlDoc.loadXML(xmlString);}return xmlDoc&&xmlDoc.documentElement&&xmlDoc.documentElement.tagName!='parsererror'?xmlDoc:null;},parse:function parse(jsonString){var js=jsonString;if(js.substr(0,9)=='while(1);'){js=js.substr(9);}if(js.substr(0,2)=='/*'){js=js.substr(2,js.length-4);}if(!js){js='{}';}return $.jgrid.useJSON===true&&(typeof JSON==="undefined"?"undefined":_typeof(JSON))==='object'&&typeof JSON.parse==='function'?JSON.parse(js):eval('('+js+')');},parseDate:function parseDate(format,date){var tsp={m:1,d:1,y:1970,h:0,i:0,s:0,u:0},k,hl,dM,regdate=/[\\\/:_;.,\t\T\s-]/;if(date&&date!=null){date=$.trim(date);date=date.split(regdate);if($.jgrid.formatter.date.masks[format]!==undefined){format=$.jgrid.formatter.date.masks[format];}format=format.split(regdate);var dfmt=$.jgrid.formatter.date.monthNames;var afmt=$.jgrid.formatter.date.AmPm;var h12to24=function h12to24(ampm,h){if(ampm===0){if(h===12){h=0;}}else{if(h!==12){h+=12;}}return h;};for(k=0,hl=format.length;k<hl;k++){if(format[k]=='M'){dM=$.inArray(date[k],dfmt);if(dM!==-1&&dM<12){date[k]=dM+1;tsp.m=date[k];}}if(format[k]=='F'){dM=$.inArray(date[k],dfmt);if(dM!==-1&&dM>11){date[k]=dM+1-12;tsp.m=date[k];}}if(format[k]=='a'){dM=$.inArray(date[k],afmt);if(dM!==-1&&dM<2&&date[k]==afmt[dM]){date[k]=dM;tsp.h=h12to24(date[k],tsp.h);}}if(format[k]=='A'){dM=$.inArray(date[k],afmt);if(dM!==-1&&dM>1&&date[k]==afmt[dM]){date[k]=dM-2;tsp.h=h12to24(date[k],tsp.h);}}if(format[k]==='g'){tsp.h=parseInt(date[k],10);}if(date[k]!==undefined){tsp[format[k].toLowerCase()]=parseInt(date[k],10);}}tsp.m=parseInt(tsp.m,10)-1;var ty=tsp.y;if(ty>=70&&ty<=99){tsp.y=1900+tsp.y;}else if(ty>=0&&ty<=69){tsp.y=2000+tsp.y;}if(tsp.j!==undefined){tsp.d=tsp.j;}if(tsp.n!==undefined){tsp.m=parseInt(tsp.n,10)-1;}}return new Date(tsp.y,tsp.m,tsp.d,tsp.h,tsp.i,tsp.s,tsp.u);},jqID:function jqID(sid){return String(sid).replace(/[!"#$%&'()*+,.\/:; <=>?@\[\\\]\^`{|}~]/g,'\\$&');},guid:1,uidPref:'jqg',randId:function randId(prefix){return(prefix||$.jgrid.uidPref)+$.jgrid.guid++;},getAccessor:function getAccessor(obj,expr){var ret,p,prm=[],i;if(typeof expr==='function'){return expr(obj);}ret=obj[expr];if(ret===undefined){try{if(typeof expr==='string'){prm=expr.split('.');}i=prm.length;if(i){ret=obj;while(ret&&i--){p=prm.shift();ret=ret[p];}}}catch(e){}}return ret;},getXmlData:function getXmlData(obj,expr,returnObj){var ret,m=typeof expr==='string'?expr.match(/^(.*)\[(\w+)\]$/):null;if(typeof expr==='function'){return expr(obj);}if(m&&m[2]){// m[2] is the attribute selector
// m[1] is an optional element selector
// examples: "[id]", "rows[page]"
return m[1]?$(m[1],obj).attr(m[2]):$(obj).attr(m[2]);}ret=$(expr,obj);if(returnObj){return ret;}//$(expr, obj).filter(':last'); // we use ':last' to be more compatible with old version of jqGrid
return ret.length>0?$(ret).text():undefined;},cellWidth:function cellWidth(){var $testDiv=$('<div class=\'ui-jqgrid\' style=\'left:10000px\'><table class=\'ui-jqgrid-btable\' style=\'width:5px;\'><tr class=\'jqgrow\'><td style=\'width:5px;\'></td></tr></table></div>'),testCell=$testDiv.appendTo('body').find('td').width();$testDiv.remove();return testCell!==5;},cell_width:true,ajaxOptions:{},from:function from(source){// Original Author Hugo Bonacci
// License MIT http://jlinq.codeplex.com/license
var QueryObject=function QueryObject(d,q){if(typeof d==='string'){d=$.data(d);}var self=this,_data=d,_usecase=true,_trim=false,_query=q,_stripNum=/[\$,%]/g,_lastCommand=null,_lastField=null,_orDepth=0,_negate=false,_queuedOperator='',_sorting=[],_useProperties=true;if((typeof d==="undefined"?"undefined":_typeof(d))==='object'&&d.push){if(d.length>0){if(_typeof(d[0])!=='object'){_useProperties=false;}else{_useProperties=true;}}}else{throw'data provides is not an array';}this._hasData=function(){return _data===null?false:_data.length===0?false:true;};this._getStr=function(s){var phrase=[];if(_trim){phrase.push('jQuery.trim(');}phrase.push('String('+s+')');if(_trim){phrase.push(')');}if(!_usecase){phrase.push('.toLowerCase()');}return phrase.join('');};this._strComp=function(val){if(typeof val==='string'){return'.toString()';}return'';};this._group=function(f,u){return{field:f.toString(),unique:u,items:[]};};this._toStr=function(phrase){if(_trim){phrase=$.trim(phrase);}phrase=phrase.toString().replace(/\\/g,'\\\\').replace(/\"/g,'\\"');return _usecase?phrase:phrase.toLowerCase();};this._funcLoop=function(func){var results=[];$.each(_data,function(i,v){results.push(func(v));});return results;};this._append=function(s){var i;if(_query===null){_query='';}else{_query+=_queuedOperator===''?' && ':_queuedOperator;}for(i=0;i<_orDepth;i++){_query+='(';}if(_negate){_query+='!';}_query+='('+s+')';_negate=false;_queuedOperator='';_orDepth=0;};this._setCommand=function(f,c){_lastCommand=f;_lastField=c;};this._resetNegate=function(){_negate=false;};this._repeatCommand=function(f,v){if(_lastCommand===null){return self;}if(f!==null&&v!==null){return _lastCommand(f,v);}if(_lastField===null){return _lastCommand(f);}if(!_useProperties){return _lastCommand(f);}return _lastCommand(_lastField,f);};this._equals=function(a,b){return self._compare(a,b,1)===0;};this._compare=function(a,b,d){var toString=Object.prototype.toString;if(d===undefined){d=1;}if(a===undefined){a=null;}if(b===undefined){b=null;}if(a===null&&b===null){return 0;}if(a===null&&b!==null){return 1;}if(a!==null&&b===null){return-1;}if(toString.call(a)==='[object Date]'&&toString.call(b)==='[object Date]'){if(a<b){return-d;}if(a>b){return d;}return 0;}if(!_usecase&&typeof a!=='number'&&typeof b!=='number'){a=String(a);b=String(b);}if(a<b){return-d;}if(a>b){return d;}return 0;};this._performSort=function(){if(_sorting.length===0){return;}_data=self._doSort(_data,0);};this._doSort=function(d,q){var by=_sorting[q].by,dir=_sorting[q].dir,type=_sorting[q].type,dfmt=_sorting[q].datefmt;if(q==_sorting.length-1){return self._getOrder(d,by,dir,type,dfmt);}q++;var values=self._getGroup(d,by,dir,type,dfmt),results=[],i,j,sorted;for(i=0;i<values.length;i++){sorted=self._doSort(values[i].items,q);for(j=0;j<sorted.length;j++){results.push(sorted[j]);}}return results;};this._getOrder=function(data,by,dir,type,dfmt){var sortData=[],_sortData=[],newDir=dir=='a'?1:-1,i,ab,j,findSortKey;if(type===undefined){type='text';}if(type=='float'||type=='number'||type=='currency'||type=='numeric'){findSortKey=function findSortKey($cell){var key=parseFloat(String($cell).replace(_stripNum,''));return isNaN(key)?0.00:key;};}else if(type=='int'||type=='integer'){findSortKey=function findSortKey($cell){return $cell?parseFloat(String($cell).replace(_stripNum,'')):0;};}else if(type=='date'||type=='datetime'){findSortKey=function findSortKey($cell){return $.jgrid.parseDate(dfmt,$cell).getTime();};}else if($.isFunction(type)){findSortKey=type;}else{findSortKey=function findSortKey($cell){$cell=$cell?$.trim(String($cell)):'';return _usecase?$cell:$cell.toLowerCase();};}$.each(data,function(i,v){ab=by!==''?$.jgrid.getAccessor(v,by):v;if(ab===undefined){ab='';}ab=findSortKey(ab,v);_sortData.push({'vSort':ab,'index':i});});_sortData.sort(function(a,b){a=a.vSort;b=b.vSort;return self._compare(a,b,newDir);});j=0;var nrec=data.length;// overhead, but we do not change the original data.
while(j<nrec){i=_sortData[j].index;sortData.push(data[i]);j++;}return sortData;};this._getGroup=function(data,by,dir,type,dfmt){var results=[],group=null,last=null,val;$.each(self._getOrder(data,by,dir,type,dfmt),function(i,v){val=$.jgrid.getAccessor(v,by);if(val==null){val='';}if(!self._equals(last,val)){last=val;if(group!==null){results.push(group);}group=self._group(by,val);}group.items.push(v);});if(group!==null){results.push(group);}return results;};this.ignoreCase=function(){_usecase=false;return self;};this.useCase=function(){_usecase=true;return self;};this.trim=function(){_trim=true;return self;};this.noTrim=function(){_trim=false;return self;};this.execute=function(){var match=_query,results=[];if(match===null){return self;}$.each(_data,function(){if(eval(match)){results.push(this);}});_data=results;return self;};this.data=function(){return _data;};this.select=function(f){self._performSort();if(!self._hasData()){return[];}self.execute();if($.isFunction(f)){var results=[];$.each(_data,function(i,v){results.push(f(v));});return results;}return _data;};this.hasMatch=function(){if(!self._hasData()){return false;}self.execute();return _data.length>0;};this.andNot=function(f,v,x){_negate=!_negate;return self.and(f,v,x);};this.orNot=function(f,v,x){_negate=!_negate;return self.or(f,v,x);};this.not=function(f,v,x){return self.andNot(f,v,x);};this.and=function(f,v,x){_queuedOperator=' && ';if(f===undefined){return self;}return self._repeatCommand(f,v,x);};this.or=function(f,v,x){_queuedOperator=' || ';if(f===undefined){return self;}return self._repeatCommand(f,v,x);};this.orBegin=function(){_orDepth++;return self;};this.orEnd=function(){if(_query!==null){_query+=')';}return self;};this.isNot=function(f){_negate=!_negate;return self.is(f);};this.is=function(f){self._append('this.'+f);self._resetNegate();return self;};this._compareValues=function(func,f,v,how,t){var fld;if(_useProperties){fld='jQuery.jgrid.getAccessor(this,\''+f+'\')';}else{fld='this';}if(v===undefined){v=null;}//var val=v===null?f:v,
var val=v,swst=t.stype===undefined?'text':t.stype;if(v!==null){switch(swst){case'int':case'integer':val=isNaN(Number(val))||val===''?'0':val;// To be fixed with more inteligent code
fld='parseInt('+fld+',10)';val='parseInt('+val+',10)';break;case'float':case'number':case'numeric':val=String(val).replace(_stripNum,'');val=isNaN(Number(val))||val===''?'0':val;// To be fixed with more inteligent code
fld='parseFloat('+fld+')';val='parseFloat('+val+')';break;case'date':case'datetime':val=String($.jgrid.parseDate(t.newfmt||'Y-m-d',val).getTime());fld='jQuery.jgrid.parseDate("'+t.srcfmt+'",'+fld+').getTime()';break;default:fld=self._getStr(fld);val=self._getStr('"'+self._toStr(val)+'"');}}self._append(fld+' '+how+' '+val);self._setCommand(func,f);self._resetNegate();return self;};this.equals=function(f,v,t){return self._compareValues(self.equals,f,v,'==',t);};this.notEquals=function(f,v,t){return self._compareValues(self.equals,f,v,'!==',t);};this.isNull=function(f,v,t){return self._compareValues(self.equals,f,null,'===',t);};this.greater=function(f,v,t){return self._compareValues(self.greater,f,v,'>',t);};this.less=function(f,v,t){return self._compareValues(self.less,f,v,'<',t);};this.greaterOrEquals=function(f,v,t){return self._compareValues(self.greaterOrEquals,f,v,'>=',t);};this.lessOrEquals=function(f,v,t){return self._compareValues(self.lessOrEquals,f,v,'<=',t);};this.startsWith=function(f,v){var val=v==null?f:v,length=_trim?$.trim(val.toString()).length:val.toString().length;if(_useProperties){self._append(self._getStr('jQuery.jgrid.getAccessor(this,\''+f+'\')')+'.substr(0,'+length+') == '+self._getStr('"'+self._toStr(v)+'"'));}else{length=_trim?$.trim(v.toString()).length:v.toString().length;self._append(self._getStr('this')+'.substr(0,'+length+') == '+self._getStr('"'+self._toStr(f)+'"'));}self._setCommand(self.startsWith,f);self._resetNegate();return self;};this.endsWith=function(f,v){var val=v==null?f:v,length=_trim?$.trim(val.toString()).length:val.toString().length;if(_useProperties){self._append(self._getStr('jQuery.jgrid.getAccessor(this,\''+f+'\')')+'.substr('+self._getStr('jQuery.jgrid.getAccessor(this,\''+f+'\')')+'.length-'+length+','+length+') == "'+self._toStr(v)+'"');}else{self._append(self._getStr('this')+'.substr('+self._getStr('this')+'.length-"'+self._toStr(f)+'".length,"'+self._toStr(f)+'".length) == "'+self._toStr(f)+'"');}self._setCommand(self.endsWith,f);self._resetNegate();return self;};this.contains=function(f,v){if(_useProperties){self._append(self._getStr('jQuery.jgrid.getAccessor(this,\''+f+'\')')+'.indexOf("'+self._toStr(v)+'",0) > -1');}else{self._append(self._getStr('this')+'.indexOf("'+self._toStr(f)+'",0) > -1');}self._setCommand(self.contains,f);self._resetNegate();return self;};this.groupBy=function(by,dir,type,datefmt){if(!self._hasData()){return null;}return self._getGroup(_data,by,dir,type,datefmt);};this.orderBy=function(by,dir,stype,dfmt){dir=dir==null?'a':$.trim(dir.toString().toLowerCase());if(stype==null){stype='text';}if(dfmt==null){dfmt='Y-m-d';}if(dir=='desc'||dir=='descending'){dir='d';}if(dir=='asc'||dir=='ascending'){dir='a';}_sorting.push({by:by,dir:dir,type:stype,datefmt:dfmt});return self;};return self;};return new QueryObject(source,null);},getMethod:function getMethod(name){return this.getAccessor($.fn.jqGrid,name);},extend:function extend(methods){$.extend($.fn.jqGrid,methods);if(!this.no_legacy_api){$.fn.extend(methods);}}});$.fn.jqGrid=function(pin){if(typeof pin==='string'){var fn=$.jgrid.getMethod(pin);if(!fn){throw'jqGrid - No such method: '+pin;}var args=$.makeArray(arguments).slice(1);return fn.apply(this,args);}return this.each(function(){if(this.grid){return;}var p=$.extend(true,{url:'',height:150,page:1,rowNum:20,rowTotal:null,records:0,pager:'',pgbuttons:true,pginput:true,colModel:[],rowList:[],colNames:[],sortorder:'asc',sortname:'',datatype:'xml',mtype:'GET',altRows:false,selarrrow:[],savedRow:[],shrinkToFit:true,xmlReader:{},jsonReader:{},subGrid:false,subGridModel:[],reccount:0,lastpage:0,lastsort:0,selrow:null,beforeSelectRow:null,onSelectRow:null,onSortCol:null,ondblClickRow:null,onRightClickRow:null,onPaging:null,onSelectAll:null,onInitGrid:null,loadComplete:null,gridComplete:null,loadError:null,loadBeforeSend:null,afterInsertRow:null,beforeRequest:null,beforeProcessing:null,onHeaderClick:null,viewrecords:false,loadonce:false,multiselect:false,multikey:false,editurl:null,search:false,caption:'',hidegrid:true,hiddengrid:false,postData:{},userData:{},treeGrid:false,treeGridModel:'nested',treeReader:{},treeANode:-1,ExpandColumn:null,tree_root_level:0,prmNames:{page:'page',rows:'rows',sort:'sidx',order:'sord',search:'_search',nd:'nd',id:'id',oper:'oper',editoper:'edit',addoper:'add',deloper:'del',subgridid:'id',npage:null,totalrows:'totalrows'},forceFit:false,gridstate:'visible',cellEdit:false,cellsubmit:'remote',nv:0,loadui:'enable',toolbar:[false,''],scroll:false,multiboxonly:false,deselectAfterSort:true,scrollrows:false,autowidth:false,scrollOffset:18,cellLayout:5,subGridWidth:20,multiselectWidth:20,gridview:false,rownumWidth:25,rownumbers:false,pagerpos:'center',recordpos:'right',footerrow:false,userDataOnFooter:false,hoverrows:true,altclass:'ui-priority-secondary',viewsortcols:[false,'vertical',true],resizeclass:'',autoencode:false,remapColumns:[],ajaxGridOptions:{},direction:'ltr',toppager:false,headertitles:false,scrollTimeout:40,data:[],_index:{},grouping:false,groupingView:{groupField:[],groupOrder:[],groupText:[],groupColumnShow:[],groupSummary:[],showSummaryOnHide:false,sortitems:[],sortnames:[],summary:[],summaryval:[],plusicon:'ui-icon-circlesmall-plus',minusicon:'ui-icon-circlesmall-minus',displayField:[]},ignoreCase:false,cmTemplate:{},idPrefix:''},$.jgrid.defaults,pin||{});var ts=this,grid={headers:[],cols:[],footers:[],dragStart:function dragStart(i,x,y){this.resizing={idx:i,startX:x.clientX,sOL:y[0]};this.hDiv.style.cursor='col-resize';this.curGbox=$('#rs_m'+$.jgrid.jqID(p.id),'#gbox_'+$.jgrid.jqID(p.id));this.curGbox.css({display:'block',left:y[0],top:y[1],height:y[2]});$(ts).triggerHandler('jqGridResizeStart',[x,i]);if($.isFunction(p.resizeStart)){p.resizeStart.call(this,x,i);}document.onselectstart=function(){return false;};},dragMove:function dragMove(x){if(this.resizing){var diff=x.clientX-this.resizing.startX,h=this.headers[this.resizing.idx],newWidth=p.direction==='ltr'?h.width+diff:h.width-diff,hn,nWn;if(newWidth>33){this.curGbox.css({left:this.resizing.sOL+diff});if(p.forceFit===true){hn=this.headers[this.resizing.idx+p.nv];nWn=p.direction==='ltr'?hn.width-diff:hn.width+diff;if(nWn>33){h.newWidth=newWidth;hn.newWidth=nWn;}}else{this.newWidth=p.direction==='ltr'?p.tblwidth+diff:p.tblwidth-diff;h.newWidth=newWidth;}}}},dragEnd:function dragEnd(){this.hDiv.style.cursor='default';if(this.resizing){var idx=this.resizing.idx,nw=this.headers[idx].newWidth||this.headers[idx].width;nw=parseInt(nw,10);this.resizing=false;$('#rs_m'+$.jgrid.jqID(p.id)).css('display','none');p.colModel[idx].width=nw;this.headers[idx].width=nw;this.headers[idx].el.style.width=nw+'px';this.cols[idx].style.width=nw+'px';if(this.footers.length>0){this.footers[idx].style.width=nw+'px';}if(p.forceFit===true){nw=this.headers[idx+p.nv].newWidth||this.headers[idx+p.nv].width;this.headers[idx+p.nv].width=nw;this.headers[idx+p.nv].el.style.width=nw+'px';this.cols[idx+p.nv].style.width=nw+'px';if(this.footers.length>0){this.footers[idx+p.nv].style.width=nw+'px';}p.colModel[idx+p.nv].width=nw;}else{p.tblwidth=this.newWidth||p.tblwidth;$('table:first',this.bDiv).css('width',p.tblwidth+'px');$('table:first',this.hDiv).css('width',p.tblwidth+'px');this.hDiv.scrollLeft=this.bDiv.scrollLeft;if(p.footerrow){$('table:first',this.sDiv).css('width',p.tblwidth+'px');this.sDiv.scrollLeft=this.bDiv.scrollLeft;}}$(ts).triggerHandler('jqGridResizeStop',[nw,idx]);if($.isFunction(p.resizeStop)){p.resizeStop.call(this,nw,idx);}}this.curGbox=null;document.onselectstart=function(){return true;};},populateVisible:function populateVisible(){if(grid.timer){clearTimeout(grid.timer);}grid.timer=null;var dh=$(grid.bDiv).height();if(!dh){return;}var table=$('table:first',grid.bDiv);var rows,rh;if(table[0].rows.length){try{rows=table[0].rows[1];rh=rows?$(rows).outerHeight()||grid.prevRowHeight:grid.prevRowHeight;}catch(pv){rh=grid.prevRowHeight;}}if(!rh){return;}grid.prevRowHeight=rh;var rn=p.rowNum;var scrollTop=grid.scrollTop=grid.bDiv.scrollTop;var ttop=Math.round(table.position().top)-scrollTop;var tbot=ttop+table.height();var div=rh*rn;var page,npage,empty;if(tbot<dh&&ttop<=0&&(p.lastpage===undefined||parseInt((tbot+scrollTop+div-1)/div,10)<=p.lastpage)){npage=parseInt((dh-tbot+div-1)/div,10);if(tbot>=0||npage<2||p.scroll===true){page=Math.round((tbot+scrollTop)/div)+1;ttop=-1;}else{ttop=1;}}if(ttop>0){page=parseInt(scrollTop/div,10)+1;npage=parseInt((scrollTop+dh)/div,10)+2-page;empty=true;}if(npage){if(p.lastpage&&(page>p.lastpage||p.lastpage==1||page===p.page&&page===p.lastpage)){return;}if(grid.hDiv.loading){grid.timer=setTimeout(grid.populateVisible,p.scrollTimeout);}else{p.page=page;if(empty){grid.selectionPreserver(table[0]);grid.emptyRows.call(table[0],false,false);}grid.populate(npage);}}},scrollGrid:function scrollGrid(e){if(p.scroll){var scrollTop=grid.bDiv.scrollTop;if(grid.scrollTop===undefined){grid.scrollTop=0;}if(scrollTop!=grid.scrollTop){grid.scrollTop=scrollTop;if(grid.timer){clearTimeout(grid.timer);}grid.timer=setTimeout(grid.populateVisible,p.scrollTimeout);}}grid.hDiv.scrollLeft=grid.bDiv.scrollLeft;if(p.footerrow){grid.sDiv.scrollLeft=grid.bDiv.scrollLeft;}if(e){e.stopPropagation();}},selectionPreserver:function selectionPreserver(ts){var p=ts.p,sr=p.selrow,sra=p.selarrrow?$.makeArray(p.selarrrow):null,left=ts.grid.bDiv.scrollLeft,restoreSelection=function restoreSelection(){var i;p.selrow=null;p.selarrrow=[];if(p.multiselect&&sra&&sra.length>0){for(i=0;i<sra.length;i++){if(sra[i]!=sr){$(ts).jqGrid('setSelection',sra[i],false,null);}}}if(sr){$(ts).jqGrid('setSelection',sr,false,null);}ts.grid.bDiv.scrollLeft=left;$(ts).unbind('.selectionPreserver',restoreSelection);};$(ts).bind('jqGridGridComplete.selectionPreserver',restoreSelection);}};if(this.tagName.toUpperCase()!='TABLE'){alert('Element is not a table');return;}if(document.documentMode!==undefined){// IE only
if(document.documentMode<=5){alert('Grid can not be used in this (\'quirks\') mode!');return;}}$(this).empty().attr('tabindex','0');this.p=p;this.p.useProp=!!$.fn.prop;var i,dir;if(this.p.colNames.length===0){for(i=0;i<this.p.colModel.length;i++){this.p.colNames[i]=this.p.colModel[i].label||this.p.colModel[i].name;}}if(this.p.colNames.length!==this.p.colModel.length){alert($.jgrid.errors.model);return;}var gv=$('<div class=\'ui-jqgrid-view\'></div>'),isMSIE=$.jgrid.msie;ts.p.direction=$.trim(ts.p.direction.toLowerCase());if($.inArray(ts.p.direction,['ltr','rtl'])==-1){ts.p.direction='ltr';}dir=ts.p.direction;$(gv).insertBefore(this);$(this).removeClass('scroll').appendTo(gv);var eg=$('<div class=\'ui-jqgrid ui-widget ui-widget-content ui-corner-all\'></div>');$(eg).attr({'id':'gbox_'+this.id,'dir':dir}).insertBefore(gv);$(gv).attr('id','gview_'+this.id).appendTo(eg);$('<div class=\'ui-widget-overlay jqgrid-overlay\' id=\'lui_'+this.id+'\'></div>').insertBefore(gv);$('<div class=\'loading ui-state-default ui-state-active\' id=\'load_'+this.id+'\'>'+this.p.loadtext+'</div>').insertBefore(gv);$(this).attr({cellspacing:'0',cellpadding:'0',border:'0','role':'grid','aria-multiselectable':!!this.p.multiselect,'aria-labelledby':'gbox_'+this.id});var sortkeys=['shiftKey','altKey','ctrlKey'],intNum=function intNum(val,defval){val=parseInt(val,10);if(isNaN(val)){return defval||0;}return val;},formatCol=function formatCol(pos,rowInd,tv,rawObject,rowId,rdata){var cm=ts.p.colModel[pos],ral=cm.align,result='style="',clas=cm.classes,nm=cm.name,celp,acp=[];if(ral){result+='text-align:'+ral+';';}if(cm.hidden===true){result+='display:none;';}if(rowInd===0){result+='width: '+grid.headers[pos].width+'px;';}else if(cm.cellattr&&$.isFunction(cm.cellattr)){celp=cm.cellattr.call(ts,rowId,tv,rawObject,cm,rdata);if(celp&&typeof celp==='string'){celp=celp.replace(/style/i,'style').replace(/title/i,'title');if(celp.indexOf('title')>-1){cm.title=false;}if(celp.indexOf('class')>-1){clas=undefined;}acp=celp.split('style');if(acp.length===2){acp[1]=$.trim(acp[1].replace('=',''));if(acp[1].indexOf('\'')===0||acp[1].indexOf('"')===0){acp[1]=acp[1].substring(1);}result+=acp[1].replace(/'/gi,'"');}else{result+='"';}}}if(!acp.length){acp[0]='';result+='"';}result+=(clas!==undefined?' class="'+clas+'"':'')+(cm.title&&tv?' title="'+$.jgrid.stripHtml(tv)+'"':'');result+=' aria-describedby="'+ts.p.id+'_'+nm+'"';return result+acp[0];},cellVal=function cellVal(val){return val==null||val===''?'&#160;':ts.p.autoencode?$.jgrid.htmlEncode(val):String(val);},formatter=function formatter(rowId,cellval,colpos,rwdat,_act){var cm=ts.p.colModel[colpos],v;if(cm.formatter!==undefined){rowId=String(ts.p.idPrefix)!==''?$.jgrid.stripPref(ts.p.idPrefix,rowId):rowId;var opts={rowId:rowId,colModel:cm,gid:ts.p.id,pos:colpos};if($.isFunction(cm.formatter)){v=cm.formatter.call(ts,cellval,opts,rwdat,_act);}else if($.fmatter){v=$.fn.fmatter.call(ts,cm.formatter,cellval,opts,rwdat,_act);}else{v=cellVal(cellval);}}else{v=cellVal(cellval);}return v;},addCell=function addCell(rowId,cell,pos,irow,srvr,rdata){var v,prp;v=formatter(rowId,cell,pos,srvr,'add');prp=formatCol(pos,irow,v,srvr,rowId,rdata);return'<td role="gridcell" '+prp+'>'+v+'</td>';},addMulti=function addMulti(rowid,pos,irow,checked){var v='<input role="checkbox" type="checkbox"'+' id="jqg_'+ts.p.id+'_'+rowid+'" class="cbox" name="jqg_'+ts.p.id+'_'+rowid+'"'+(checked?'checked="checked"':'')+'/>',prp=formatCol(pos,irow,'',null,rowid,true);return'<td role="gridcell" '+prp+'>'+v+'</td>';},addRowNum=function addRowNum(pos,irow,pG,rN){var v=(parseInt(pG,10)-1)*parseInt(rN,10)+1+irow,prp=formatCol(pos,irow,v,null,irow,true);return'<td role="gridcell" class="ui-state-default jqgrid-rownum" '+prp+'>'+v+'</td>';},reader=function reader(datatype){var field,f=[],j=0,i;for(i=0;i<ts.p.colModel.length;i++){field=ts.p.colModel[i];if(field.name!=='cb'&&field.name!=='subgrid'&&field.name!=='rn'){f[j]=datatype=='local'?field.name:datatype=='xml'||datatype==='xmlstring'?field.xmlmap||field.name:field.jsonmap||field.name;j++;}}return f;},orderedCols=function orderedCols(offset){var order=ts.p.remapColumns;if(!order||!order.length){order=$.map(ts.p.colModel,function(v,i){return i;});}if(offset){order=$.map(order,function(v){return v<offset?null:v-offset;});}return order;},emptyRows=function emptyRows(scroll,locdata){var firstrow;if(this.p.deepempty){$(this.rows).slice(1).remove();}else{firstrow=this.rows.length>0?this.rows[0]:null;$(this.firstChild).empty().append(firstrow);}if(scroll&&this.p.scroll){$(this.grid.bDiv.firstChild).css({height:'auto'});$(this.grid.bDiv.firstChild.firstChild).css({height:0,display:'none'});if(this.grid.bDiv.scrollTop!==0){this.grid.bDiv.scrollTop=0;}}if(locdata===true&&this.p.treeGrid){this.p.data=[];this.p._index={};}},refreshIndex=function refreshIndex(){var datalen=ts.p.data.length,idname,i,val,ni=ts.p.rownumbers===true?1:0,gi=ts.p.multiselect===true?1:0,si=ts.p.subGrid===true?1:0;if(ts.p.keyIndex===false||ts.p.loadonce===true){idname=ts.p.localReader.id;}else{idname=ts.p.colModel[ts.p.keyIndex+gi+si+ni].name;}for(i=0;i<datalen;i++){val=$.jgrid.getAccessor(ts.p.data[i],idname);if(val===undefined){val=String(i+1);}ts.p._index[val]=i;}},constructTr=function constructTr(id,hide,altClass,rd,cur,selected){var tabindex='-1',restAttr='',attrName,style=hide?'display:none;':'',classes='ui-widget-content jqgrow ui-row-'+ts.p.direction+altClass+(selected?' ui-state-highlight':''),rowAttrObj=$.isFunction(ts.p.rowattr)?ts.p.rowattr.call(ts,rd,cur):{};if(!$.isEmptyObject(rowAttrObj)){if(rowAttrObj.hasOwnProperty('id')){id=rowAttrObj.id;delete rowAttrObj.id;}if(rowAttrObj.hasOwnProperty('tabindex')){tabindex=rowAttrObj.tabindex;delete rowAttrObj.tabindex;}if(rowAttrObj.hasOwnProperty('style')){style+=rowAttrObj.style;delete rowAttrObj.style;}if(rowAttrObj.hasOwnProperty('class')){classes+=' '+rowAttrObj['class'];delete rowAttrObj['class'];}// dot't allow to change role attribute
try{delete rowAttrObj.role;}catch(ra){}for(attrName in rowAttrObj){if(rowAttrObj.hasOwnProperty(attrName)){restAttr+=' '+attrName+'='+rowAttrObj[attrName];}}}return'<tr role="row" id="'+id+'" tabindex="'+tabindex+'" class="'+classes+'"'+(style===''?'':' style="'+style+'"')+restAttr+'>';},addXmlData=function addXmlData(xml,t,rcnt,more,adjust){var startReq=new Date(),locdata=ts.p.datatype!='local'&&ts.p.loadonce||ts.p.datatype=='xmlstring',xmlid='_id_',xmlRd=ts.p.xmlReader,frd=ts.p.datatype=='local'?'local':'xml';if(locdata){ts.p.data=[];ts.p._index={};ts.p.localReader.id=xmlid;}ts.p.reccount=0;if($.isXMLDoc(xml)){if(ts.p.treeANode===-1&&!ts.p.scroll){emptyRows.call(ts,false,true);rcnt=1;}else{rcnt=rcnt>1?rcnt:1;}}else{return;}var self=$(ts),i,fpos,ir=0,v,gi=ts.p.multiselect===true?1:0,si=0,addSubGridCell,ni=ts.p.rownumbers===true?1:0,idn,getId,f=[],F,rd={},xmlr,rid,rowData=[],cn=ts.p.altRows===true?' '+ts.p.altclass:'',cn1;if(ts.p.subGrid===true){si=1;addSubGridCell=$.jgrid.getMethod('addSubGridCell');}if(!xmlRd.repeatitems){f=reader(frd);}if(ts.p.keyIndex===false){idn=$.isFunction(xmlRd.id)?xmlRd.id.call(ts,xml):xmlRd.id;}else{idn=ts.p.keyIndex;}if(f.length>0&&!isNaN(idn)){if(ts.p.remapColumns&&ts.p.remapColumns.length){idn=$.inArray(idn,ts.p.remapColumns);}idn=f[idn];}if(String(idn).indexOf('[')===-1){if(f.length){getId=function getId(trow,k){return $(idn,trow).text()||k;};}else{getId=function getId(trow,k){return $(xmlRd.cell,trow).eq(idn).text()||k;};}}else{getId=function getId(trow,k){return trow.getAttribute(idn.replace(/[\[\]]/g,''))||k;};}ts.p.userData={};ts.p.page=$.jgrid.getXmlData(xml,xmlRd.page)||ts.p.page||0;ts.p.lastpage=$.jgrid.getXmlData(xml,xmlRd.total);if(ts.p.lastpage===undefined){ts.p.lastpage=1;}ts.p.records=$.jgrid.getXmlData(xml,xmlRd.records)||0;if($.isFunction(xmlRd.userdata)){ts.p.userData=xmlRd.userdata.call(ts,xml)||{};}else{$.jgrid.getXmlData(xml,xmlRd.userdata,true).each(function(){ts.p.userData[this.getAttribute('name')]=$(this).text();});}var gxml=$.jgrid.getXmlData(xml,xmlRd.root,true);gxml=$.jgrid.getXmlData(gxml,xmlRd.row,true);if(!gxml){gxml=[];}var gl=gxml.length,j=0,grpdata=[],rn=parseInt(ts.p.rowNum,10),br=ts.p.scroll?$.jgrid.randId():1,altr;if(gl>0&&ts.p.page<=0){ts.p.page=1;}if(gxml&&gl){if(adjust){rn*=adjust+1;}var afterInsRow=$.isFunction(ts.p.afterInsertRow),hiderow=false,groupingPrepare;if(ts.p.grouping){hiderow=ts.p.groupingView.groupCollapse===true;groupingPrepare=$.jgrid.getMethod('groupingPrepare');}while(j<gl){xmlr=gxml[j];rid=getId(xmlr,br+j);rid=ts.p.idPrefix+rid;altr=rcnt===0?0:rcnt+1;cn1=(altr+j)%2==1?cn:'';var iStartTrTag=rowData.length;rowData.push('');if(ni){rowData.push(addRowNum(0,j,ts.p.page,ts.p.rowNum));}if(gi){rowData.push(addMulti(rid,ni,j,false));}if(si){rowData.push(addSubGridCell.call(self,gi+ni,j+rcnt));}if(xmlRd.repeatitems){if(!F){F=orderedCols(gi+si+ni);}var cells=$.jgrid.getXmlData(xmlr,xmlRd.cell,true);$.each(F,function(k){var cell=cells[this];if(!cell){return false;}v=cell.textContent||cell.text;rd[ts.p.colModel[k+gi+si+ni].name]=v;rowData.push(addCell(rid,v,k+gi+si+ni,j+rcnt,xmlr,rd));});}else{for(i=0;i<f.length;i++){v=$.jgrid.getXmlData(xmlr,f[i]);rd[ts.p.colModel[i+gi+si+ni].name]=v;rowData.push(addCell(rid,v,i+gi+si+ni,j+rcnt,xmlr,rd));}}rowData[iStartTrTag]=constructTr(rid,hiderow,cn1,rd,xmlr,false);rowData.push('</tr>');if(ts.p.grouping){grpdata=groupingPrepare.call(self,rowData,grpdata,rd,j);rowData=[];}if(locdata||ts.p.treeGrid===true){rd[xmlid]=rid;ts.p.data.push(rd);ts.p._index[rid]=ts.p.data.length-1;}if(ts.p.gridview===false){$('tbody:first',t).append(rowData.join(''));self.triggerHandler('jqGridAfterInsertRow',[rid,rd,xmlr]);if(afterInsRow){ts.p.afterInsertRow.call(ts,rid,rd,xmlr);}rowData=[];}rd={};ir++;j++;if(ir==rn){break;}}}if(ts.p.gridview===true){fpos=ts.p.treeANode>-1?ts.p.treeANode:0;if(ts.p.grouping){self.jqGrid('groupingRender',grpdata,ts.p.colModel.length);grpdata=null;}else if(ts.p.treeGrid===true&&fpos>0){$(ts.rows[fpos]).after(rowData.join(''));}else{$('tbody:first',t).append(rowData.join(''));}}if(ts.p.subGrid===true){try{self.jqGrid('addSubGrid',gi+ni);}catch(_){}}ts.p.totaltime=new Date()-startReq;if(ir>0){if(ts.p.records===0){ts.p.records=gl;}}rowData=null;if(ts.p.treeGrid===true){try{self.jqGrid('setTreeNode',fpos+1,ir+fpos+1);}catch(e){}}if(!ts.p.treeGrid&&!ts.p.scroll){ts.grid.bDiv.scrollTop=0;}ts.p.reccount=ir;ts.p.treeANode=-1;if(ts.p.userDataOnFooter){self.jqGrid('footerData','set',ts.p.userData,true);}if(locdata){ts.p.records=gl;ts.p.lastpage=Math.ceil(gl/rn);}if(!more){ts.updatepager(false,true);}if(locdata){while(ir<gl){xmlr=gxml[ir];rid=getId(xmlr,ir+br);rid=ts.p.idPrefix+rid;if(xmlRd.repeatitems){if(!F){F=orderedCols(gi+si+ni);}var cells2=$.jgrid.getXmlData(xmlr,xmlRd.cell,true);$.each(F,function(k){var cell=cells2[this];if(!cell){return false;}v=cell.textContent||cell.text;rd[ts.p.colModel[k+gi+si+ni].name]=v;});}else{for(i=0;i<f.length;i++){v=$.jgrid.getXmlData(xmlr,f[i]);rd[ts.p.colModel[i+gi+si+ni].name]=v;}}rd[xmlid]=rid;ts.p.data.push(rd);ts.p._index[rid]=ts.p.data.length-1;rd={};ir++;}}},addJSONData=function addJSONData(data,t,rcnt,more,adjust){var startReq=new Date();if(data){if(ts.p.treeANode===-1&&!ts.p.scroll){emptyRows.call(ts,false,true);rcnt=1;}else{rcnt=rcnt>1?rcnt:1;}}else{return;}var dReader,locid='_id_',frd,locdata=ts.p.datatype!='local'&&ts.p.loadonce||ts.p.datatype=='jsonstring';if(locdata){ts.p.data=[];ts.p._index={};ts.p.localReader.id=locid;}ts.p.reccount=0;if(ts.p.datatype=='local'){dReader=ts.p.localReader;frd='local';}else{dReader=ts.p.jsonReader;frd='json';}var self=$(ts),ir=0,v,i,j,f=[],F,cur,gi=ts.p.multiselect?1:0,si=0,addSubGridCell,ni=ts.p.rownumbers===true?1:0,len,drows,idn,rd={},fpos,idr,rowData=[],cn=ts.p.altRows===true?' '+ts.p.altclass:'',cn1,lp;ts.p.page=$.jgrid.getAccessor(data,dReader.page)||ts.p.page||0;lp=$.jgrid.getAccessor(data,dReader.total);if(ts.p.subGrid===true){si=1;addSubGridCell=$.jgrid.getMethod('addSubGridCell');}ts.p.lastpage=lp===undefined?1:lp;ts.p.records=$.jgrid.getAccessor(data,dReader.records)||0;ts.p.userData=$.jgrid.getAccessor(data,dReader.userdata)||{};if(!dReader.repeatitems){F=f=reader(frd);}if(ts.p.keyIndex===false){idn=$.isFunction(dReader.id)?dReader.id.call(ts,data):dReader.id;}else{idn=ts.p.keyIndex;}if(f.length>0&&!isNaN(idn)){if(ts.p.remapColumns&&ts.p.remapColumns.length){idn=$.inArray(idn,ts.p.remapColumns);}idn=f[idn];}drows=$.jgrid.getAccessor(data,dReader.root);if(!drows){drows=[];}len=drows.length;i=0;if(len>0&&ts.p.page<=0){ts.p.page=1;}var rn=parseInt(ts.p.rowNum,10),br=ts.p.scroll?$.jgrid.randId():1,altr,selected=false,selr;if(adjust){rn*=adjust+1;}if(ts.p.datatype==='local'&&!ts.p.deselectAfterSort){selected=true;}var afterInsRow=$.isFunction(ts.p.afterInsertRow),grpdata=[],hiderow=false,groupingPrepare;if(ts.p.grouping){hiderow=ts.p.groupingView.groupCollapse===true;groupingPrepare=$.jgrid.getMethod('groupingPrepare');}while(i<len){cur=drows[i];idr=$.jgrid.getAccessor(cur,idn);if(idr===undefined){idr=br+i;if(f.length===0){if(dReader.cell){var ccur=$.jgrid.getAccessor(cur,dReader.cell);idr=ccur!==undefined?ccur[idn]||idr:idr;ccur=null;}}}idr=ts.p.idPrefix+idr;altr=rcnt===1?0:rcnt;cn1=(altr+i)%2==1?cn:'';if(selected){if(ts.p.multiselect){selr=$.inArray(idr,ts.p.selarrrow)!==-1;}else{selr=idr===ts.p.selrow;}}var iStartTrTag=rowData.length;rowData.push('');if(ni){rowData.push(addRowNum(0,i,ts.p.page,ts.p.rowNum));}if(gi){rowData.push(addMulti(idr,ni,i,selr));}if(si){rowData.push(addSubGridCell.call(self,gi+ni,i+rcnt));}if(dReader.repeatitems){if(dReader.cell){cur=$.jgrid.getAccessor(cur,dReader.cell);}if(!F){F=orderedCols(gi+si+ni);}}for(j=0;j<F.length;j++){v=$.jgrid.getAccessor(cur,F[j]);rd[ts.p.colModel[j+gi+si+ni].name]=v;rowData.push(addCell(idr,v,j+gi+si+ni,i+rcnt,cur,rd));}rowData[iStartTrTag]=constructTr(idr,hiderow,cn1,rd,cur,selr);rowData.push('</tr>');if(ts.p.grouping){grpdata=groupingPrepare.call(self,rowData,grpdata,rd,i);rowData=[];}if(locdata||ts.p.treeGrid===true){rd[locid]=idr;ts.p.data.push(rd);ts.p._index[idr]=ts.p.data.length-1;}if(ts.p.gridview===false){$('#'+$.jgrid.jqID(ts.p.id)+' tbody:first').append(rowData.join(''));self.triggerHandler('jqGridAfterInsertRow',[idr,rd,cur]);if(afterInsRow){ts.p.afterInsertRow.call(ts,idr,rd,cur);}rowData=[];//ari=0;
}rd={};ir++;i++;if(ir==rn){break;}}if(ts.p.gridview===true){fpos=ts.p.treeANode>-1?ts.p.treeANode:0;if(ts.p.grouping){self.jqGrid('groupingRender',grpdata,ts.p.colModel.length);grpdata=null;}else if(ts.p.treeGrid===true&&fpos>0){$(ts.rows[fpos]).after(rowData.join(''));}else{$('#'+$.jgrid.jqID(ts.p.id)+' tbody:first').append(rowData.join(''));}}if(ts.p.subGrid===true){try{self.jqGrid('addSubGrid',gi+ni);}catch(_){}}ts.p.totaltime=new Date()-startReq;if(ir>0){if(ts.p.records===0){ts.p.records=len;}}rowData=null;if(ts.p.treeGrid===true){try{self.jqGrid('setTreeNode',fpos+1,ir+fpos+1);}catch(e){}}if(!ts.p.treeGrid&&!ts.p.scroll){ts.grid.bDiv.scrollTop=0;}ts.p.reccount=ir;ts.p.treeANode=-1;if(ts.p.userDataOnFooter){self.jqGrid('footerData','set',ts.p.userData,true);}if(locdata){ts.p.records=len;ts.p.lastpage=Math.ceil(len/rn);}if(!more){ts.updatepager(false,true);}if(locdata){while(ir<len&&drows[ir]){cur=drows[ir];idr=$.jgrid.getAccessor(cur,idn);if(idr===undefined){idr=br+ir;if(f.length===0){if(dReader.cell){var ccur2=$.jgrid.getAccessor(cur,dReader.cell);idr=ccur2[idn]||idr;ccur2=null;}}}if(cur){idr=ts.p.idPrefix+idr;if(dReader.repeatitems){if(dReader.cell){cur=$.jgrid.getAccessor(cur,dReader.cell);}if(!F){F=orderedCols(gi+si+ni);}}for(j=0;j<F.length;j++){v=$.jgrid.getAccessor(cur,F[j]);rd[ts.p.colModel[j+gi+si+ni].name]=v;}rd[locid]=idr;ts.p.data.push(rd);ts.p._index[idr]=ts.p.data.length-1;rd={};}ir++;}}},addLocalData=function addLocalData(){var st,fndsort=false,cmtypes={},grtypes=[],grindexes=[],srcformat,sorttype,newformat;if(!$.isArray(ts.p.data)){return;}var grpview=ts.p.grouping?ts.p.groupingView:false,lengrp,gin;$.each(ts.p.colModel,function(){sorttype=this.sorttype||'text';if(sorttype=='date'||sorttype=='datetime'){if(this.formatter&&typeof this.formatter==='string'&&this.formatter=='date'){if(this.formatoptions&&this.formatoptions.srcformat){srcformat=this.formatoptions.srcformat;}else{srcformat=$.jgrid.formatter.date.srcformat;}if(this.formatoptions&&this.formatoptions.newformat){newformat=this.formatoptions.newformat;}else{newformat=$.jgrid.formatter.date.newformat;}}else{srcformat=newformat=this.datefmt||'Y-m-d';}cmtypes[this.name]={'stype':sorttype,'srcfmt':srcformat,'newfmt':newformat};}else{cmtypes[this.name]={'stype':sorttype,'srcfmt':'','newfmt':''};}if(ts.p.grouping){for(gin=0,lengrp=grpview.groupField.length;gin<lengrp;gin++){if(this.name==grpview.groupField[gin]){var grindex=this.name;if(this.index){grindex=this.index;}grtypes[gin]=cmtypes[grindex];grindexes[gin]=grindex;}}}if(!fndsort&&(this.index==ts.p.sortname||this.name==ts.p.sortname)){st=this.name;// ???
fndsort=true;}});if(ts.p.treeGrid){$(ts).jqGrid('SortTree',st,ts.p.sortorder,cmtypes[st].stype,cmtypes[st].srcfmt);return;}var compareFnMap={'eq':function eq(queryObj){return queryObj.equals;},'ne':function ne(queryObj){return queryObj.notEquals;},'lt':function lt(queryObj){return queryObj.less;},'le':function le(queryObj){return queryObj.lessOrEquals;},'gt':function gt(queryObj){return queryObj.greater;},'ge':function ge(queryObj){return queryObj.greaterOrEquals;},'cn':function cn(queryObj){return queryObj.contains;},'nc':function nc(queryObj,op){return op==='OR'?queryObj.orNot().contains:queryObj.andNot().contains;},'bw':function bw(queryObj){return queryObj.startsWith;},'bn':function bn(queryObj,op){return op==='OR'?queryObj.orNot().startsWith:queryObj.andNot().startsWith;},'en':function en(queryObj,op){return op==='OR'?queryObj.orNot().endsWith:queryObj.andNot().endsWith;},'ew':function ew(queryObj){return queryObj.endsWith;},'ni':function ni(queryObj,op){return op==='OR'?queryObj.orNot().equals:queryObj.andNot().equals;},'in':function _in(queryObj){return queryObj.equals;},'nu':function nu(queryObj){return queryObj.isNull;},'nn':function nn(queryObj,op){return op==='OR'?queryObj.orNot().isNull:queryObj.andNot().isNull;}},query=$.jgrid.from(ts.p.data);if(ts.p.ignoreCase){query=query.ignoreCase();}function tojLinq(group){var s=0,index,gor,ror,opr,rule;if(group.groups!=null){gor=group.groups.length&&group.groupOp.toString().toUpperCase()==='OR';if(gor){query.orBegin();}for(index=0;index<group.groups.length;index++){if(s>0&&gor){query.or();}try{tojLinq(group.groups[index]);}catch(e){alert(e);}s++;}if(gor){query.orEnd();}}if(group.rules!=null){//if(s>0) {
//	var result = query.select();
//	query = $.jgrid.from( result);
//	if (ts.p.ignoreCase) { query = query.ignoreCase(); }
//}
try{ror=group.rules.length&&group.groupOp.toString().toUpperCase()==='OR';if(ror){query.orBegin();}for(index=0;index<group.rules.length;index++){rule=group.rules[index];opr=group.groupOp.toString().toUpperCase();if(compareFnMap[rule.op]&&rule.field){if(s>0&&opr&&opr==='OR'){query=query.or();}query=compareFnMap[rule.op](query,opr)(rule.field,rule.data,cmtypes[rule.field]);}s++;}if(ror){query.orEnd();}}catch(g){alert(g);}}}if(ts.p.search===true){var srules=ts.p.postData.filters;if(srules){if(typeof srules==='string'){srules=$.jgrid.parse(srules);}tojLinq(srules);}else{try{query=compareFnMap[ts.p.postData.searchOper](query)(ts.p.postData.searchField,ts.p.postData.searchString,cmtypes[ts.p.postData.searchField]);}catch(se){}}}if(ts.p.grouping){for(gin=0;gin<lengrp;gin++){query.orderBy(grindexes[gin],grpview.groupOrder[gin],grtypes[gin].stype,grtypes[gin].srcfmt);}}if(st&&ts.p.sortorder&&fndsort){if(ts.p.sortorder.toUpperCase()=='DESC'){query.orderBy(ts.p.sortname,'d',cmtypes[st].stype,cmtypes[st].srcfmt);}else{query.orderBy(ts.p.sortname,'a',cmtypes[st].stype,cmtypes[st].srcfmt);}}var queryResults=query.select(),recordsperpage=parseInt(ts.p.rowNum,10),total=queryResults.length,page=parseInt(ts.p.page,10),totalpages=Math.ceil(total/recordsperpage),retresult={};queryResults=queryResults.slice((page-1)*recordsperpage,page*recordsperpage);query=null;cmtypes=null;retresult[ts.p.localReader.total]=totalpages;retresult[ts.p.localReader.page]=page;retresult[ts.p.localReader.records]=total;retresult[ts.p.localReader.root]=queryResults;retresult[ts.p.localReader.userdata]=ts.p.userData;queryResults=null;return retresult;},updatepager=function updatepager(rn,dnd){var cp,last,base,from,to,tot,fmt,pgboxes='',sppg,tspg=ts.p.pager?'_'+$.jgrid.jqID(ts.p.pager.substr(1)):'',tspg_t=ts.p.toppager?'_'+ts.p.toppager.substr(1):'';base=parseInt(ts.p.page,10)-1;if(base<0){base=0;}base=base*parseInt(ts.p.rowNum,10);to=base+ts.p.reccount;if(ts.p.scroll){var rows=$('tbody:first > tr:gt(0)',ts.grid.bDiv);base=to-rows.length;ts.p.reccount=rows.length;var rh=rows.outerHeight()||ts.grid.prevRowHeight;if(rh){var top=base*rh;var height=parseInt(ts.p.records,10)*rh;$('>div:first',ts.grid.bDiv).css({height:height}).children('div:first').css({height:top,display:top?'':'none'});}ts.grid.bDiv.scrollLeft=ts.grid.hDiv.scrollLeft;}pgboxes=ts.p.pager||'';pgboxes+=ts.p.toppager?pgboxes?','+ts.p.toppager:ts.p.toppager:'';if(pgboxes){fmt=$.jgrid.formatter.integer||{};cp=intNum(ts.p.page);last=intNum(ts.p.lastpage);$('.selbox',pgboxes)[this.p.useProp?'prop':'attr']('disabled',false);if(ts.p.pginput===true){$('.ui-pg-input',pgboxes).val(ts.p.page);sppg=ts.p.toppager?'#sp_1'+tspg+',#sp_1'+tspg_t:'#sp_1'+tspg;$(sppg).html($.fmatter?$.fmatter.util.NumberFormat(ts.p.lastpage,fmt):ts.p.lastpage);}if(ts.p.viewrecords){if(ts.p.reccount===0){$('.ui-paging-info',pgboxes).html(ts.p.emptyrecords);}else{from=base+1;tot=ts.p.records;if($.fmatter){from=$.fmatter.util.NumberFormat(from,fmt);to=$.fmatter.util.NumberFormat(to,fmt);tot=$.fmatter.util.NumberFormat(tot,fmt);}$('.ui-paging-info',pgboxes).html($.jgrid.format(ts.p.recordtext,from,to,tot));}}if(ts.p.pgbuttons===true){if(cp<=0){cp=last=0;}if(cp==1||cp===0){$('#first'+tspg+', #prev'+tspg).addClass('ui-state-disabled').removeClass('ui-state-hover');if(ts.p.toppager){$('#first_t'+tspg_t+', #prev_t'+tspg_t).addClass('ui-state-disabled').removeClass('ui-state-hover');}}else{$('#first'+tspg+', #prev'+tspg).removeClass('ui-state-disabled');if(ts.p.toppager){$('#first_t'+tspg_t+', #prev_t'+tspg_t).removeClass('ui-state-disabled');}}if(cp==last||cp===0){$('#next'+tspg+', #last'+tspg).addClass('ui-state-disabled').removeClass('ui-state-hover');if(ts.p.toppager){$('#next_t'+tspg_t+', #last_t'+tspg_t).addClass('ui-state-disabled').removeClass('ui-state-hover');}}else{$('#next'+tspg+', #last'+tspg).removeClass('ui-state-disabled');if(ts.p.toppager){$('#next_t'+tspg_t+', #last_t'+tspg_t).removeClass('ui-state-disabled');}}}}if(rn===true&&ts.p.rownumbers===true){$('td.jqgrid-rownum',ts.rows).each(function(i){$(this).html(base+1+i);});}if(dnd&&ts.p.jqgdnd){$(ts).jqGrid('gridDnD','updateDnD');}$(ts).triggerHandler('jqGridGridComplete');if($.isFunction(ts.p.gridComplete)){ts.p.gridComplete.call(ts);}$(ts).triggerHandler('jqGridAfterGridComplete');},beginReq=function beginReq(){ts.grid.hDiv.loading=true;if(ts.p.hiddengrid){return;}switch(ts.p.loadui){case'disable':break;case'enable':$('#load_'+$.jgrid.jqID(ts.p.id)).show();break;case'block':$('#lui_'+$.jgrid.jqID(ts.p.id)).show();$('#load_'+$.jgrid.jqID(ts.p.id)).show();break;}},endReq=function endReq(){ts.grid.hDiv.loading=false;switch(ts.p.loadui){case'disable':break;case'enable':$('#load_'+$.jgrid.jqID(ts.p.id)).hide();break;case'block':$('#lui_'+$.jgrid.jqID(ts.p.id)).hide();$('#load_'+$.jgrid.jqID(ts.p.id)).hide();break;}},populate=function populate(npage){if(!ts.grid.hDiv.loading){var pvis=ts.p.scroll&&npage===false,prm={},dt,dstr,pN=ts.p.prmNames;if(ts.p.page<=0){ts.p.page=1;}if(pN.search!==null){prm[pN.search]=ts.p.search;}if(pN.nd!==null){prm[pN.nd]=new Date().getTime();}if(pN.rows!==null){prm[pN.rows]=ts.p.rowNum;}if(pN.page!==null){prm[pN.page]=ts.p.page;}if(pN.sort!==null){prm[pN.sort]=ts.p.sortname;}if(pN.order!==null){prm[pN.order]=ts.p.sortorder;}if(ts.p.rowTotal!==null&&pN.totalrows!==null){prm[pN.totalrows]=ts.p.rowTotal;}var lcf=$.isFunction(ts.p.loadComplete),lc=lcf?ts.p.loadComplete:null;var adjust=0;npage=npage||1;if(npage>1){if(pN.npage!==null){prm[pN.npage]=npage;adjust=npage-1;npage=1;}else{lc=function lc(req){ts.p.page++;ts.grid.hDiv.loading=false;if(lcf){ts.p.loadComplete.call(ts,req);}populate(npage-1);};}}else if(pN.npage!==null){delete ts.p.postData[pN.npage];}if(ts.p.grouping){$(ts).jqGrid('groupingSetup');var grp=ts.p.groupingView,gi,gs='';for(gi=0;gi<grp.groupField.length;gi++){var index=grp.groupField[gi];$.each(ts.p.colModel,function(cmIndex,cmValue){if(cmValue.name==index&&cmValue.index){index=cmValue.index;}});gs+=index+' '+grp.groupOrder[gi]+', ';}prm[pN.sort]=gs+prm[pN.sort];}$.extend(ts.p.postData,prm);var rcnt=!ts.p.scroll?1:ts.rows.length-1;var bfr=$(ts).triggerHandler('jqGridBeforeRequest');if(bfr===false||bfr==='stop'){return;}if($.isFunction(ts.p.datatype)){ts.p.datatype.call(ts,ts.p.postData,'load_'+ts.p.id);return;}if($.isFunction(ts.p.beforeRequest)){bfr=ts.p.beforeRequest.call(ts);if(bfr===undefined){bfr=true;}if(bfr===false){return;}}dt=ts.p.datatype.toLowerCase();switch(dt){case'json':case'jsonp':case'xml':case'script':$.ajax($.extend({url:ts.p.url,type:ts.p.mtype,dataType:dt,data:$.isFunction(ts.p.serializeGridData)?ts.p.serializeGridData.call(ts,ts.p.postData):ts.p.postData,success:function success(data,st,xhr){if($.isFunction(ts.p.beforeProcessing)){if(ts.p.beforeProcessing.call(ts,data,st,xhr)===false){endReq();return;}}if(dt==='xml'){addXmlData(data,ts.grid.bDiv,rcnt,npage>1,adjust);}else{addJSONData(data,ts.grid.bDiv,rcnt,npage>1,adjust);}$(ts).triggerHandler('jqGridLoadComplete',[data]);if(lc){lc.call(ts,data);}$(ts).triggerHandler('jqGridAfterLoadComplete',[data]);if(pvis){ts.grid.populateVisible();}if(ts.p.loadonce||ts.p.treeGrid){ts.p.datatype='local';}data=null;if(npage===1){endReq();}},error:function error(xhr,st,err){if($.isFunction(ts.p.loadError)){ts.p.loadError.call(ts,xhr,st,err);}if(npage===1){endReq();}xhr=null;},beforeSend:function beforeSend(xhr,settings){var gotoreq=true;if($.isFunction(ts.p.loadBeforeSend)){gotoreq=ts.p.loadBeforeSend.call(ts,xhr,settings);}if(gotoreq===undefined){gotoreq=true;}if(gotoreq===false){return false;}beginReq();}},$.jgrid.ajaxOptions,ts.p.ajaxGridOptions));break;case'xmlstring':beginReq();dstr=$.jgrid.stringToDoc(ts.p.datastr);addXmlData(dstr,ts.grid.bDiv);$(ts).triggerHandler('jqGridLoadComplete',[dstr]);if(lcf){ts.p.loadComplete.call(ts,dstr);}$(ts).triggerHandler('jqGridAfterLoadComplete',[dstr]);ts.p.datatype='local';ts.p.datastr=null;endReq();break;case'jsonstring':beginReq();if(typeof ts.p.datastr==='string'){dstr=$.jgrid.parse(ts.p.datastr);}else{dstr=ts.p.datastr;}addJSONData(dstr,ts.grid.bDiv);$(ts).triggerHandler('jqGridLoadComplete',[dstr]);if(lcf){ts.p.loadComplete.call(ts,dstr);}$(ts).triggerHandler('jqGridAfterLoadComplete',[dstr]);ts.p.datatype='local';ts.p.datastr=null;endReq();break;case'local':case'clientside':beginReq();ts.p.datatype='local';var req=addLocalData();addJSONData(req,ts.grid.bDiv,rcnt,npage>1,adjust);$(ts).triggerHandler('jqGridLoadComplete',[req]);if(lc){lc.call(ts,req);}$(ts).triggerHandler('jqGridAfterLoadComplete',[req]);if(pvis){ts.grid.populateVisible();}endReq();break;}}},setHeadCheckBox=function setHeadCheckBox(checked){$('#cb_'+$.jgrid.jqID(ts.p.id),ts.grid.hDiv)[ts.p.useProp?'prop':'attr']('checked',checked);var fid=ts.p.frozenColumns?ts.p.id+'_frozen':'';if(fid){$('#cb_'+$.jgrid.jqID(ts.p.id),ts.grid.fhDiv)[ts.p.useProp?'prop':'attr']('checked',checked);}},setPager=function setPager(pgid,tp){// TBD - consider escaping pgid with pgid = $.jgrid.jqID(pgid);
var sep='<td class=\'ui-pg-button ui-state-disabled\' style=\'width:4px;\'><span class=\'ui-separator\'></span></td>',pginp='',pgl='<table cellspacing=\'0\' cellpadding=\'0\' border=\'0\' style=\'table-layout:auto;\' class=\'ui-pg-table\'><tbody><tr>',str='',pgcnt,lft,cent,rgt,twd,tdw,i,clearVals=function clearVals(onpaging){var ret;if($.isFunction(ts.p.onPaging)){ret=ts.p.onPaging.call(ts,onpaging);}ts.p.selrow=null;if(ts.p.multiselect){ts.p.selarrrow=[];setHeadCheckBox(false);}ts.p.savedRow=[];if(ret=='stop'){return false;}return true;};pgid=pgid.substr(1);tp+='_'+pgid;pgcnt='pg_'+pgid;lft=pgid+'_left';cent=pgid+'_center';rgt=pgid+'_right';$('#'+$.jgrid.jqID(pgid)).append('<div id=\''+pgcnt+'\' class=\'ui-pager-control\' role=\'group\'><table cellspacing=\'0\' cellpadding=\'0\' border=\'0\' class=\'ui-pg-table\' style=\'width:100%;table-layout:fixed;height:100%;\' role=\'row\'><tbody><tr><td id=\''+lft+'\' align=\'left\'></td><td id=\''+cent+'\' align=\'center\' style=\'white-space:pre;\'></td><td id=\''+rgt+'\' align=\'right\'></td></tr></tbody></table></div>').attr('dir','ltr');//explicit setting
if(ts.p.rowList.length>0){str='<td dir=\''+dir+'\'>';str+='<select class=\'ui-pg-selbox\' role=\'listbox\'>';for(i=0;i<ts.p.rowList.length;i++){str+='<option role="option" value="'+ts.p.rowList[i]+'"'+(ts.p.rowNum==ts.p.rowList[i]?' selected="selected"':'')+'>'+ts.p.rowList[i]+'</option>';}str+='</select></td>';}if(dir=='rtl'){pgl+=str;}if(ts.p.pginput===true){pginp='<td dir=\''+dir+'\'>'+$.jgrid.format(ts.p.pgtext||'','<input class=\'ui-pg-input\' type=\'text\' size=\'2\' maxlength=\'7\' value=\'0\' role=\'textbox\'/>','<span id=\'sp_1_'+$.jgrid.jqID(pgid)+'\'></span>')+'</td>';}if(ts.p.pgbuttons===true){var po=['first'+tp,'prev'+tp,'next'+tp,'last'+tp];if(dir=='rtl'){po.reverse();}pgl+='<td id=\''+po[0]+'\' class=\'ui-pg-button ui-corner-all\'><span class=\'ui-icon ui-icon-seek-first\'></span></td>';pgl+='<td id=\''+po[1]+'\' class=\'ui-pg-button ui-corner-all\'><span class=\'ui-icon ui-icon-seek-prev\'></span></td>';pgl+=pginp!==''?sep+pginp+sep:'';pgl+='<td id=\''+po[2]+'\' class=\'ui-pg-button ui-corner-all\'><span class=\'ui-icon ui-icon-seek-next\'></span></td>';pgl+='<td id=\''+po[3]+'\' class=\'ui-pg-button ui-corner-all\'><span class=\'ui-icon ui-icon-seek-end\'></span></td>';}else if(pginp!==''){pgl+=pginp;}if(dir=='ltr'){pgl+=str;}pgl+='</tr></tbody></table>';if(ts.p.viewrecords===true){$('td#'+pgid+'_'+ts.p.recordpos,'#'+pgcnt).append('<div dir=\''+dir+'\' style=\'text-align:'+ts.p.recordpos+'\' class=\'ui-paging-info\'></div>');}$('td#'+pgid+'_'+ts.p.pagerpos,'#'+pgcnt).append(pgl);tdw=$('.ui-jqgrid').css('font-size')||'11px';$(document.body).append('<div id=\'testpg\' class=\'ui-jqgrid ui-widget ui-widget-content\' style=\'font-size:'+tdw+';visibility:hidden;\' ></div>');twd=$(pgl).clone().appendTo('#testpg').width();$('#testpg').remove();if(twd>0){if(pginp!==''){twd+=50;}//should be param
$('td#'+pgid+'_'+ts.p.pagerpos,'#'+pgcnt).width(twd);}ts.p._nvtd=[];ts.p._nvtd[0]=twd?Math.floor((ts.p.width-twd)/2):Math.floor(ts.p.width/3);ts.p._nvtd[1]=0;pgl=null;$('.ui-pg-selbox','#'+pgcnt).bind('change',function(){if(!clearVals('records')){return false;}ts.p.page=Math.round(ts.p.rowNum*(ts.p.page-1)/this.value-0.5)+1;ts.p.rowNum=this.value;if(ts.p.pager){$('.ui-pg-selbox',ts.p.pager).val(this.value);}if(ts.p.toppager){$('.ui-pg-selbox',ts.p.toppager).val(this.value);}populate();return false;});if(ts.p.pgbuttons===true){$('.ui-pg-button','#'+pgcnt).hover(function(){if($(this).hasClass('ui-state-disabled')){this.style.cursor='default';}else{$(this).addClass('ui-state-hover');this.style.cursor='pointer';}},function(){if(!$(this).hasClass('ui-state-disabled')){$(this).removeClass('ui-state-hover');this.style.cursor='default';}});$('#first'+$.jgrid.jqID(tp)+', #prev'+$.jgrid.jqID(tp)+', #next'+$.jgrid.jqID(tp)+', #last'+$.jgrid.jqID(tp)).click(function(){var cp=intNum(ts.p.page,1),last=intNum(ts.p.lastpage,1),selclick=false,fp=true,pp=true,np=true,lp=true;if(last===0||last===1){fp=false;pp=false;np=false;lp=false;}else if(last>1&&cp>=1){if(cp===1){fp=false;pp=false;}//else if( cp>1 && cp <last){ }
else if(cp===last){np=false;lp=false;}}else if(last>1&&cp===0){np=false;lp=false;cp=last-1;}if(!clearVals(this.id)){return false;}if(this.id==='first'+tp&&fp){ts.p.page=1;selclick=true;}if(this.id==='prev'+tp&&pp){ts.p.page=cp-1;selclick=true;}if(this.id==='next'+tp&&np){ts.p.page=cp+1;selclick=true;}if(this.id==='last'+tp&&lp){ts.p.page=last;selclick=true;}if(selclick){populate();}return false;});}if(ts.p.pginput===true){$('input.ui-pg-input','#'+pgcnt).keypress(function(e){var key=e.charCode||e.keyCode||0;if(key==13){if(!clearVals('user')){return false;}ts.p.page=$(this).val()>0?$(this).val():ts.p.page;populate();return false;}return this;});}},sortData=function sortData(index,idxcol,reload,sor){if(!ts.p.colModel[idxcol].sortable){return;}var so;if(ts.p.savedRow.length>0){return;}if(!reload){if(ts.p.lastsort==idxcol){if(ts.p.sortorder=='asc'){ts.p.sortorder='desc';}else if(ts.p.sortorder=='desc'){ts.p.sortorder='asc';}}else{ts.p.sortorder=ts.p.colModel[idxcol].firstsortorder||'asc';}ts.p.page=1;}if(sor){if(ts.p.lastsort==idxcol&&ts.p.sortorder==sor&&!reload){return;}ts.p.sortorder=sor;}var previousSelectedTh=ts.grid.headers[ts.p.lastsort].el,newSelectedTh=ts.grid.headers[idxcol].el;$('span.ui-grid-ico-sort',previousSelectedTh).addClass('ui-state-disabled');$(previousSelectedTh).attr('aria-selected','false');$('span.ui-icon-'+ts.p.sortorder,newSelectedTh).removeClass('ui-state-disabled');$(newSelectedTh).attr('aria-selected','true');if(!ts.p.viewsortcols[0]){if(ts.p.lastsort!=idxcol){$('span.s-ico',previousSelectedTh).hide();$('span.s-ico',newSelectedTh).show();}}index=index.substring(5+ts.p.id.length+1);// bad to be changed!?!
ts.p.sortname=ts.p.colModel[idxcol].index||index;so=ts.p.sortorder;if($(ts).triggerHandler('jqGridSortCol',[index,idxcol,so])==='stop'){ts.p.lastsort=idxcol;return;}if($.isFunction(ts.p.onSortCol)){if(ts.p.onSortCol.call(ts,index,idxcol,so)=='stop'){ts.p.lastsort=idxcol;return;}}if(ts.p.datatype=='local'){if(ts.p.deselectAfterSort){$(ts).jqGrid('resetSelection');}}else{ts.p.selrow=null;if(ts.p.multiselect){setHeadCheckBox(false);}ts.p.selarrrow=[];ts.p.savedRow=[];}if(ts.p.scroll){var sscroll=ts.grid.bDiv.scrollLeft;emptyRows.call(ts,true,false);ts.grid.hDiv.scrollLeft=sscroll;}if(ts.p.subGrid&&ts.p.datatype=='local'){$('td.sgexpanded','#'+$.jgrid.jqID(ts.p.id)).each(function(){$(this).trigger('click');});}populate();ts.p.lastsort=idxcol;if(ts.p.sortname!=index&&idxcol){ts.p.lastsort=idxcol;}},setColWidth=function setColWidth(){var initwidth=0,brd=$.jgrid.cell_width?0:intNum(ts.p.cellLayout,0),vc=0,lvc,scw=intNum(ts.p.scrollOffset,0),cw,hs=false,aw,gw=0,cl=0,cr;$.each(ts.p.colModel,function(){if(this.hidden===undefined){this.hidden=false;}if(ts.p.grouping&&ts.p.autowidth){var ind=$.inArray(this.name,ts.p.groupingView.groupField);if(ind!==-1){this.hidden=!ts.p.groupingView.groupColumnShow[ind];}}this.widthOrg=cw=intNum(this.width,0);if(this.hidden===false){initwidth+=cw+brd;if(this.fixed){gw+=cw+brd;}else{vc++;}cl++;}});if(isNaN(ts.p.width)){ts.p.width=initwidth+(ts.p.shrinkToFit===false&&!isNaN(ts.p.height)?scw:0);}grid.width=ts.p.width;ts.p.tblwidth=initwidth;if(ts.p.shrinkToFit===false&&ts.p.forceFit===true){ts.p.forceFit=false;}if(ts.p.shrinkToFit===true&&vc>0){aw=grid.width-brd*vc-gw;if(!isNaN(ts.p.height)){aw-=scw;hs=true;}initwidth=0;$.each(ts.p.colModel,function(i){if(this.hidden===false&&!this.fixed){cw=Math.round(aw*this.width/(ts.p.tblwidth-brd*vc-gw));this.width=cw;initwidth+=cw;lvc=i;}});cr=0;if(hs){if(grid.width-gw-(initwidth+brd*vc)!==scw){cr=grid.width-gw-(initwidth+brd*vc)-scw;}}else if(!hs&&Math.abs(grid.width-gw-(initwidth+brd*vc))!==1){cr=grid.width-gw-(initwidth+brd*vc);}ts.p.colModel[lvc].width+=cr;ts.p.tblwidth=initwidth+cr+brd*vc+gw;if(ts.p.tblwidth>ts.p.width){ts.p.colModel[lvc].width-=ts.p.tblwidth-parseInt(ts.p.width,10);ts.p.tblwidth=ts.p.width;}}},nextVisible=function nextVisible(iCol){var ret=iCol,j=iCol,i;for(i=iCol+1;i<ts.p.colModel.length;i++){if(ts.p.colModel[i].hidden!==true){j=i;break;}}return j-ret;},getOffset=function getOffset(iCol){var i,ret=[0],brd1=$.jgrid.cell_width?0:ts.p.cellLayout;for(i=0;i<=iCol;i++){if(ts.p.colModel[i].hidden===false){ret[0]+=ts.p.colModel[i].width+brd1;}}if(ts.p.direction=='rtl'){ret[0]=ts.p.width-ret[0];}ret[0]-=ts.grid.bDiv.scrollLeft;ret.push($(ts.grid.hDiv).position().top);ret.push($(ts.grid.bDiv).offset().top-$(ts.grid.hDiv).offset().top+$(ts.grid.bDiv).height());return ret;},getColumnHeaderIndex=function getColumnHeaderIndex(th){var i,headers=ts.grid.headers,ci=$.jgrid.getCellIndex(th);for(i=0;i<headers.length;i++){if(th===headers[i].el){ci=i;break;}}return ci;};this.p.id=this.id;if($.inArray(ts.p.multikey,sortkeys)==-1){ts.p.multikey=false;}ts.p.keyIndex=false;for(i=0;i<ts.p.colModel.length;i++){ts.p.colModel[i]=$.extend(true,{},ts.p.cmTemplate,ts.p.colModel[i].template||{},ts.p.colModel[i]);if(ts.p.keyIndex===false&&ts.p.colModel[i].key===true){ts.p.keyIndex=i;}}ts.p.sortorder=ts.p.sortorder.toLowerCase();$.jgrid.cell_width=$.jgrid.cellWidth();if(ts.p.grouping===true){ts.p.scroll=false;ts.p.rownumbers=false;//ts.p.subGrid = false; expiremental
//			ts.p.treeGrid = false;
ts.p.gridview=true;}if(this.p.treeGrid===true){try{$(this).jqGrid('setTreeGrid');}catch(_){}if(ts.p.datatype!='local'){ts.p.localReader={id:'_id_'};}}if(this.p.subGrid){try{$(ts).jqGrid('setSubGrid');}catch(s){}}if(this.p.multiselect){this.p.colNames.unshift('<input role=\'checkbox\' id=\'cb_'+this.p.id+'\' class=\'cbox\' type=\'checkbox\'/>');this.p.colModel.unshift({name:'cb',width:$.jgrid.cell_width?ts.p.multiselectWidth+ts.p.cellLayout:ts.p.multiselectWidth,sortable:false,resizable:false,hidedlg:true,search:false,align:'center',fixed:true});}if(this.p.rownumbers){this.p.colNames.unshift('');this.p.colModel.unshift({name:'rn',width:ts.p.rownumWidth,sortable:false,resizable:false,hidedlg:true,search:false,align:'center',fixed:true});}ts.p.xmlReader=$.extend(true,{root:'rows',row:'row',page:'rows>page',total:'rows>total',records:'rows>records',repeatitems:true,cell:'cell',id:'[id]',userdata:'userdata',subgrid:{root:'rows',row:'row',repeatitems:true,cell:'cell'}},ts.p.xmlReader);ts.p.jsonReader=$.extend(true,{root:'rows',page:'page',total:'total',records:'records',repeatitems:true,cell:'cell',id:'id',userdata:'userdata',subgrid:{root:'rows',repeatitems:true,cell:'cell'}},ts.p.jsonReader);ts.p.localReader=$.extend(true,{root:'rows',page:'page',total:'total',records:'records',repeatitems:false,cell:'cell',id:'id',userdata:'userdata',subgrid:{root:'rows',repeatitems:true,cell:'cell'}},ts.p.localReader);if(ts.p.scroll){ts.p.pgbuttons=false;ts.p.pginput=false;ts.p.rowList=[];}if(ts.p.data.length){refreshIndex();}var thead='<thead><tr class=\'ui-jqgrid-labels\' role=\'rowheader\'>',tdc,idn,w,res,sort,td,ptr,tbody,imgs,iac='',idc='';if(ts.p.shrinkToFit===true&&ts.p.forceFit===true){for(i=ts.p.colModel.length-1;i>=0;i--){if(!ts.p.colModel[i].hidden){ts.p.colModel[i].resizable=false;break;}}}if(ts.p.viewsortcols[1]=='horizontal'){iac=' ui-i-asc';idc=' ui-i-desc';}tdc=isMSIE?'class=\'ui-th-div-ie\'':'';imgs='<span class=\'s-ico\' style=\'display:none\'><span sort=\'asc\' class=\'ui-grid-ico-sort ui-icon-asc'+iac+' ui-state-disabled ui-icon ui-icon-triangle-1-n ui-sort-'+dir+'\'></span>';imgs+='<span sort=\'desc\' class=\'ui-grid-ico-sort ui-icon-desc'+idc+' ui-state-disabled ui-icon ui-icon-triangle-1-s ui-sort-'+dir+'\'></span></span>';for(i=0;i<this.p.colNames.length;i++){var tooltip=ts.p.headertitles?' title="'+$.jgrid.stripHtml(ts.p.colNames[i])+'"':'';thead+='<th id=\''+ts.p.id+'_'+ts.p.colModel[i].name+'\' role=\'columnheader\' class=\'ui-state-default ui-th-column ui-th-'+dir+'\''+tooltip+'>';idn=ts.p.colModel[i].index||ts.p.colModel[i].name;thead+='<div id=\'jqgh_'+ts.p.id+'_'+ts.p.colModel[i].name+'\' '+tdc+'>'+ts.p.colNames[i];if(!ts.p.colModel[i].width){ts.p.colModel[i].width=150;}else{ts.p.colModel[i].width=parseInt(ts.p.colModel[i].width,10);}if(typeof ts.p.colModel[i].title!=='boolean'){ts.p.colModel[i].title=true;}if(idn==ts.p.sortname){ts.p.lastsort=i;}thead+=imgs+'</div></th>';}thead+='</tr></thead>';imgs=null;$(this).append(thead);$('thead tr:first th',this).hover(function(){$(this).addClass('ui-state-hover');},function(){$(this).removeClass('ui-state-hover');});if(this.p.multiselect){var emp=[],chk;$('#cb_'+$.jgrid.jqID(ts.p.id),this).bind('click',function(){ts.p.selarrrow=[];var froz=ts.p.frozenColumns===true?ts.p.id+'_frozen':'';if(this.checked){$(ts.rows).each(function(i){if(i>0){if(!$(this).hasClass('ui-subgrid')&&!$(this).hasClass('jqgroup')&&!$(this).hasClass('ui-state-disabled')){$('#jqg_'+$.jgrid.jqID(ts.p.id)+'_'+$.jgrid.jqID(this.id))[ts.p.useProp?'prop':'attr']('checked',true);$(this).addClass('ui-state-highlight').attr('aria-selected','true');ts.p.selarrrow.push(this.id);ts.p.selrow=this.id;if(froz){$('#jqg_'+$.jgrid.jqID(ts.p.id)+'_'+$.jgrid.jqID(this.id),ts.grid.fbDiv)[ts.p.useProp?'prop':'attr']('checked',true);$('#'+$.jgrid.jqID(this.id),ts.grid.fbDiv).addClass('ui-state-highlight');}}}});chk=true;emp=[];}else{$(ts.rows).each(function(i){if(i>0){if(!$(this).hasClass('ui-subgrid')&&!$(this).hasClass('ui-state-disabled')){$('#jqg_'+$.jgrid.jqID(ts.p.id)+'_'+$.jgrid.jqID(this.id))[ts.p.useProp?'prop':'attr']('checked',false);$(this).removeClass('ui-state-highlight').attr('aria-selected','false');emp.push(this.id);if(froz){$('#jqg_'+$.jgrid.jqID(ts.p.id)+'_'+$.jgrid.jqID(this.id),ts.grid.fbDiv)[ts.p.useProp?'prop':'attr']('checked',false);$('#'+$.jgrid.jqID(this.id),ts.grid.fbDiv).removeClass('ui-state-highlight');}}}});ts.p.selrow=null;chk=false;}$(ts).triggerHandler('jqGridSelectAll',[chk?ts.p.selarrrow:emp,chk]);if($.isFunction(ts.p.onSelectAll)){ts.p.onSelectAll.call(ts,chk?ts.p.selarrrow:emp,chk);}});}if(ts.p.autowidth===true){var pw=$(eg).innerWidth();ts.p.width=pw>0?pw:'nw';}setColWidth();$(eg).css('width',grid.width+'px').append('<div class=\'ui-jqgrid-resize-mark\' id=\'rs_m'+ts.p.id+'\'>&#160;</div>');$(gv).css('width',grid.width+'px');thead=$('thead:first',ts).get(0);var tfoot='';if(ts.p.footerrow){tfoot+='<table role=\'grid\' style=\'width:'+ts.p.tblwidth+'px\' class=\'ui-jqgrid-ftable\' cellspacing=\'0\' cellpadding=\'0\' border=\'0\'><tbody><tr role=\'row\' class=\'ui-widget-content footrow footrow-'+dir+'\'>';}var thr=$('tr:first',thead),firstr='<tr class=\'jqgfirstrow\' role=\'row\' style=\'height:auto\'>';ts.p.disableClick=false;$('th',thr).each(function(j){w=ts.p.colModel[j].width;if(ts.p.colModel[j].resizable===undefined){ts.p.colModel[j].resizable=true;}if(ts.p.colModel[j].resizable){res=document.createElement('span');$(res).html('&#160;').addClass('ui-jqgrid-resize ui-jqgrid-resize-'+dir).css('cursor','col-resize');$(this).addClass(ts.p.resizeclass);}else{res='';}$(this).css('width',w+'px').prepend(res);var hdcol='';if(ts.p.colModel[j].hidden){$(this).css('display','none');hdcol='display:none;';}firstr+='<td role=\'gridcell\' style=\'height:0px;width:'+w+'px;'+hdcol+'\'></td>';grid.headers[j]={width:w,el:this};sort=ts.p.colModel[j].sortable;if(typeof sort!=='boolean'){ts.p.colModel[j].sortable=true;sort=true;}var nm=ts.p.colModel[j].name;if(!(nm=='cb'||nm=='subgrid'||nm=='rn')){if(ts.p.viewsortcols[2]){$('>div',this).addClass('ui-jqgrid-sortable');}}if(sort){if(ts.p.viewsortcols[0]){$('div span.s-ico',this).show();if(j==ts.p.lastsort){$('div span.ui-icon-'+ts.p.sortorder,this).removeClass('ui-state-disabled');}}else if(j==ts.p.lastsort){$('div span.s-ico',this).show();$('div span.ui-icon-'+ts.p.sortorder,this).removeClass('ui-state-disabled');}}if(ts.p.footerrow){tfoot+='<td role=\'gridcell\' '+formatCol(j,0,'',null,'',false)+'>&#160;</td>';}}).mousedown(function(e){if($(e.target).closest('th>span.ui-jqgrid-resize').length!=1){return;}var ci=getColumnHeaderIndex(this);if(ts.p.forceFit===true){ts.p.nv=nextVisible(ci);}grid.dragStart(ci,e,getOffset(ci));return false;}).click(function(e){if(ts.p.disableClick){ts.p.disableClick=false;return false;}var s='th>div.ui-jqgrid-sortable',r,d;if(!ts.p.viewsortcols[2]){s='th>div>span>span.ui-grid-ico-sort';}var t=$(e.target).closest(s);if(t.length!=1){return;}var ci=getColumnHeaderIndex(this);if(!ts.p.viewsortcols[2]){r=true;d=t.attr('sort');}sortData($('div',this)[0].id,ci,r,d);return false;});if(ts.p.sortable&&$.fn.sortable){try{$(ts).jqGrid('sortableColumns',thr);}catch(e){}}if(ts.p.footerrow){tfoot+='</tr></tbody></table>';}firstr+='</tr>';tbody=document.createElement('tbody');this.appendChild(tbody);$(this).addClass('ui-jqgrid-btable').append(firstr);firstr=null;var hTable=$('<table class=\'ui-jqgrid-htable\' style=\'width:'+ts.p.tblwidth+'px\' role=\'grid\' aria-labelledby=\'gbox_'+this.id+'\' cellspacing=\'0\' cellpadding=\'0\' border=\'0\'></table>').append(thead),hg=ts.p.caption&&ts.p.hiddengrid===true?true:false,hb=$('<div class=\'ui-jqgrid-hbox'+(dir=='rtl'?'-rtl':'')+'\'></div>');thead=null;grid.hDiv=document.createElement('div');$(grid.hDiv).css({width:grid.width+'px'}).addClass('ui-state-default ui-jqgrid-hdiv').append(hb);$(hb).append(hTable);hTable=null;if(hg){$(grid.hDiv).hide();}if(ts.p.pager){// TBD -- escape ts.p.pager here?
if(typeof ts.p.pager==='string'){if(ts.p.pager.substr(0,1)!='#'){ts.p.pager='#'+ts.p.pager;}}else{ts.p.pager='#'+$(ts.p.pager).attr('id');}$(ts.p.pager).css({width:grid.width+'px'}).addClass('ui-state-default ui-jqgrid-pager ui-corner-bottom').appendTo(eg);if(hg){$(ts.p.pager).hide();}setPager(ts.p.pager,'');}if(ts.p.cellEdit===false&&ts.p.hoverrows===true){$(ts).bind('mouseover',function(e){ptr=$(e.target).closest('tr.jqgrow');if($(ptr).attr('class')!=='ui-subgrid'){$(ptr).addClass('ui-state-hover');}}).bind('mouseout',function(e){ptr=$(e.target).closest('tr.jqgrow');$(ptr).removeClass('ui-state-hover');});}var ri,ci,tdHtml;$(ts).before(grid.hDiv).click(function(e){td=e.target;ptr=$(td,ts.rows).closest('tr.jqgrow');if($(ptr).length===0||ptr[0].className.indexOf('ui-state-disabled')>-1||($(td,ts).closest('table.ui-jqgrid-btable').attr('id')||'').replace('_frozen','')!==ts.id){return this;}var scb=$(td).hasClass('cbox'),cSel=$(ts).triggerHandler('jqGridBeforeSelectRow',[ptr[0].id,e]);cSel=cSel===false||cSel==='stop'?false:true;if(cSel&&$.isFunction(ts.p.beforeSelectRow)){cSel=ts.p.beforeSelectRow.call(ts,ptr[0].id,e);}if(td.tagName=='A'||(td.tagName=='INPUT'||td.tagName=='TEXTAREA'||td.tagName=='OPTION'||td.tagName=='SELECT')&&!scb){return;}if(cSel===true){ri=ptr[0].id;ci=$.jgrid.getCellIndex(td);tdHtml=$(td).closest('td,th').html();$(ts).triggerHandler('jqGridCellSelect',[ri,ci,tdHtml,e]);if($.isFunction(ts.p.onCellSelect)){ts.p.onCellSelect.call(ts,ri,ci,tdHtml,e);}if(ts.p.cellEdit===true){if(ts.p.multiselect&&scb){$(ts).jqGrid('setSelection',ri,true,e);}else{ri=ptr[0].rowIndex;try{$(ts).jqGrid('editCell',ri,ci,true);}catch(_){}}}else if(!ts.p.multikey){if(ts.p.multiselect&&ts.p.multiboxonly){if(scb){$(ts).jqGrid('setSelection',ri,true,e);}else{var frz=ts.p.frozenColumns?ts.p.id+'_frozen':'';$(ts.p.selarrrow).each(function(i,n){var ind=ts.rows.namedItem(n);$(ind).removeClass('ui-state-highlight');$('#jqg_'+$.jgrid.jqID(ts.p.id)+'_'+$.jgrid.jqID(n))[ts.p.useProp?'prop':'attr']('checked',false);if(frz){$('#'+$.jgrid.jqID(n),'#'+$.jgrid.jqID(frz)).removeClass('ui-state-highlight');$('#jqg_'+$.jgrid.jqID(ts.p.id)+'_'+$.jgrid.jqID(n),'#'+$.jgrid.jqID(frz))[ts.p.useProp?'prop':'attr']('checked',false);}});ts.p.selarrrow=[];$(ts).jqGrid('setSelection',ri,true,e);}}else{$(ts).jqGrid('setSelection',ri,true,e);}}else{if(e[ts.p.multikey]){$(ts).jqGrid('setSelection',ri,true,e);}else if(ts.p.multiselect&&scb){scb=$('#jqg_'+$.jgrid.jqID(ts.p.id)+'_'+ri).is(':checked');$('#jqg_'+$.jgrid.jqID(ts.p.id)+'_'+ri)[ts.p.useProp?'prop':'attr']('checked',scb);}}}}).bind('reloadGrid',function(e,opts){if(ts.p.treeGrid===true){ts.p.datatype=ts.p.treedatatype;}if(opts&&opts.current){ts.grid.selectionPreserver(ts);}if(ts.p.datatype=='local'){$(ts).jqGrid('resetSelection');if(ts.p.data.length){refreshIndex();}}else if(!ts.p.treeGrid){ts.p.selrow=null;if(ts.p.multiselect){ts.p.selarrrow=[];setHeadCheckBox(false);}ts.p.savedRow=[];}if(ts.p.scroll){emptyRows.call(ts,true,false);}if(opts&&opts.page){var page=opts.page;if(page>ts.p.lastpage){page=ts.p.lastpage;}if(page<1){page=1;}ts.p.page=page;if(ts.grid.prevRowHeight){ts.grid.bDiv.scrollTop=(page-1)*ts.grid.prevRowHeight*ts.p.rowNum;}else{ts.grid.bDiv.scrollTop=0;}}if(ts.grid.prevRowHeight&&ts.p.scroll){delete ts.p.lastpage;ts.grid.populateVisible();}else{ts.grid.populate();}if(ts.p._inlinenav===true){$(ts).jqGrid('showAddEditButtons');}return false;}).dblclick(function(e){td=e.target;ptr=$(td,ts.rows).closest('tr.jqgrow');if($(ptr).length===0){return;}ri=ptr[0].rowIndex;ci=$.jgrid.getCellIndex(td);$(ts).triggerHandler('jqGridDblClickRow',[$(ptr).attr('id'),ri,ci,e]);if($.isFunction(this.p.ondblClickRow)){ts.p.ondblClickRow.call(ts,$(ptr).attr('id'),ri,ci,e);}}).bind('contextmenu',function(e){td=e.target;ptr=$(td,ts.rows).closest('tr.jqgrow');if($(ptr).length===0){return;}if(!ts.p.multiselect){$(ts).jqGrid('setSelection',ptr[0].id,true,e);}ri=ptr[0].rowIndex;ci=$.jgrid.getCellIndex(td);$(ts).triggerHandler('jqGridRightClickRow',[$(ptr).attr('id'),ri,ci,e]);if($.isFunction(this.p.onRightClickRow)){ts.p.onRightClickRow.call(ts,$(ptr).attr('id'),ri,ci,e);}});grid.bDiv=document.createElement('div');if(isMSIE){if(String(ts.p.height).toLowerCase()==='auto'){ts.p.height='100%';}}$(grid.bDiv).append($('<div style="position:relative;'+(isMSIE&&$.jgrid.msiever()<8?'height:0.01%;':'')+'"></div>').append('<div></div>').append(this)).addClass('ui-jqgrid-bdiv').css({height:ts.p.height+(isNaN(ts.p.height)?'':'px'),width:grid.width+'px'}).scroll(grid.scrollGrid);$('table:first',grid.bDiv).css({width:ts.p.tblwidth+'px'});if(!$.support.tbody){//IE
if($('tbody',this).length==2){$('tbody:gt(0)',this).remove();}}if(ts.p.multikey){if($.jgrid.msie){$(grid.bDiv).bind('selectstart',function(){return false;});}else{$(grid.bDiv).bind('mousedown',function(){return false;});}}if(hg){$(grid.bDiv).hide();}grid.cDiv=document.createElement('div');var arf=ts.p.hidegrid===true?$('<a role=\'link\' href=\'javascript:void(0)\'/>').addClass('ui-jqgrid-titlebar-close HeaderButton').hover(function(){arf.addClass('ui-state-hover');},function(){arf.removeClass('ui-state-hover');}).append('<span class=\'ui-icon ui-icon-circle-triangle-n\'></span>').css(dir=='rtl'?'left':'right','0px'):'';$(grid.cDiv).append(arf).append('<span class=\'ui-jqgrid-title'+(dir=='rtl'?'-rtl':'')+'\'>'+ts.p.caption+'</span>').addClass('ui-jqgrid-titlebar ui-widget-header ui-corner-top ui-helper-clearfix');$(grid.cDiv).insertBefore(grid.hDiv);if(ts.p.toolbar[0]){grid.uDiv=document.createElement('div');if(ts.p.toolbar[1]=='top'){$(grid.uDiv).insertBefore(grid.hDiv);}else if(ts.p.toolbar[1]=='bottom'){$(grid.uDiv).insertAfter(grid.hDiv);}if(ts.p.toolbar[1]=='both'){grid.ubDiv=document.createElement('div');$(grid.uDiv).addClass('ui-userdata ui-state-default').attr('id','t_'+this.id).insertBefore(grid.hDiv);$(grid.ubDiv).addClass('ui-userdata ui-state-default').attr('id','tb_'+this.id).insertAfter(grid.hDiv);if(hg){$(grid.ubDiv).hide();}}else{$(grid.uDiv).width(grid.width).addClass('ui-userdata ui-state-default').attr('id','t_'+this.id);}if(hg){$(grid.uDiv).hide();}}if(ts.p.toppager){ts.p.toppager=$.jgrid.jqID(ts.p.id)+'_toppager';grid.topDiv=$('<div id=\''+ts.p.toppager+'\'></div>')[0];ts.p.toppager='#'+ts.p.toppager;$(grid.topDiv).addClass('ui-state-default ui-jqgrid-toppager').width(grid.width).insertBefore(grid.hDiv);setPager(ts.p.toppager,'_t');}if(ts.p.footerrow){grid.sDiv=$('<div class=\'ui-jqgrid-sdiv\'></div>')[0];hb=$('<div class=\'ui-jqgrid-hbox'+(dir=='rtl'?'-rtl':'')+'\'></div>');$(grid.sDiv).append(hb).width(grid.width).insertAfter(grid.hDiv);$(hb).append(tfoot);grid.footers=$('.ui-jqgrid-ftable',grid.sDiv)[0].rows[0].cells;if(ts.p.rownumbers){grid.footers[0].className='ui-state-default jqgrid-rownum';}if(hg){$(grid.sDiv).hide();}}hb=null;if(ts.p.caption){var tdt=ts.p.datatype;if(ts.p.hidegrid===true){$('.ui-jqgrid-titlebar-close',grid.cDiv).click(function(e){var onHdCl=$.isFunction(ts.p.onHeaderClick),elems='.ui-jqgrid-bdiv, .ui-jqgrid-hdiv, .ui-jqgrid-pager, .ui-jqgrid-sdiv',counter,self=this;if(ts.p.toolbar[0]===true){if(ts.p.toolbar[1]=='both'){elems+=', #'+$(grid.ubDiv).attr('id');}elems+=', #'+$(grid.uDiv).attr('id');}counter=$(elems,'#gview_'+$.jgrid.jqID(ts.p.id)).length;if(ts.p.gridstate=='visible'){$(elems,'#gbox_'+$.jgrid.jqID(ts.p.id)).slideUp('fast',function(){counter--;if(counter===0){$('span',self).removeClass('ui-icon-circle-triangle-n').addClass('ui-icon-circle-triangle-s');ts.p.gridstate='hidden';if($('#gbox_'+$.jgrid.jqID(ts.p.id)).hasClass('ui-resizable')){$('.ui-resizable-handle','#gbox_'+$.jgrid.jqID(ts.p.id)).hide();}$(ts).triggerHandler('jqGridHeaderClick',[ts.p.gridstate,e]);if(onHdCl){if(!hg){ts.p.onHeaderClick.call(ts,ts.p.gridstate,e);}}}});}else if(ts.p.gridstate=='hidden'){$(elems,'#gbox_'+$.jgrid.jqID(ts.p.id)).slideDown('fast',function(){counter--;if(counter===0){$('span',self).removeClass('ui-icon-circle-triangle-s').addClass('ui-icon-circle-triangle-n');if(hg){ts.p.datatype=tdt;populate();hg=false;}ts.p.gridstate='visible';if($('#gbox_'+$.jgrid.jqID(ts.p.id)).hasClass('ui-resizable')){$('.ui-resizable-handle','#gbox_'+$.jgrid.jqID(ts.p.id)).show();}$(ts).triggerHandler('jqGridHeaderClick',[ts.p.gridstate,e]);if(onHdCl){if(!hg){ts.p.onHeaderClick.call(ts,ts.p.gridstate,e);}}}});}return false;});if(hg){ts.p.datatype='local';$('.ui-jqgrid-titlebar-close',grid.cDiv).trigger('click');}}}else{$(grid.cDiv).hide();}$(grid.hDiv).after(grid.bDiv).mousemove(function(e){if(grid.resizing){grid.dragMove(e);return false;}});$('.ui-jqgrid-labels',grid.hDiv).bind('selectstart',function(){return false;});$(document).mouseup(function(){if(grid.resizing){grid.dragEnd();return false;}return true;});ts.formatCol=formatCol;ts.sortData=sortData;ts.updatepager=updatepager;ts.refreshIndex=refreshIndex;ts.setHeadCheckBox=setHeadCheckBox;ts.constructTr=constructTr;ts.formatter=function(rowId,cellval,colpos,rwdat,act){return formatter(rowId,cellval,colpos,rwdat,act);};$.extend(grid,{populate:populate,emptyRows:emptyRows});this.grid=grid;ts.addXmlData=function(d){addXmlData(d,ts.grid.bDiv);};ts.addJSONData=function(d){addJSONData(d,ts.grid.bDiv);};this.grid.cols=this.rows[0].cells;$(ts).triggerHandler('jqGridInitGrid');if($.isFunction(ts.p.onInitGrid)){ts.p.onInitGrid.call(ts);}populate();ts.p.hiddengrid=false;});};$.jgrid.extend({getGridParam:function getGridParam(pName){var $t=this[0];if(!$t||!$t.grid){return;}if(!pName){return $t.p;}return $t.p[pName]!==undefined?$t.p[pName]:null;},setGridParam:function setGridParam(newParams){return this.each(function(){if(this.grid&&(typeof newParams==="undefined"?"undefined":_typeof(newParams))==='object'){$.extend(true,this.p,newParams);}});},getDataIDs:function getDataIDs(){var ids=[],i=0,len,j=0;this.each(function(){len=this.rows.length;if(len&&len>0){while(i<len){if($(this.rows[i]).hasClass('jqgrow')){ids[j]=this.rows[i].id;j++;}i++;}}});return ids;},setSelection:function setSelection(selection,onsr,e){return this.each(function(){var $t=this,stat,pt,ner,ia,tpsr,fid;if(selection===undefined){return;}onsr=onsr===false?false:true;pt=$t.rows.namedItem(String(selection));if(!pt||!pt.className||pt.className.indexOf('ui-state-disabled')>-1){return;}function scrGrid(iR){var ch=$($t.grid.bDiv)[0].clientHeight,st=$($t.grid.bDiv)[0].scrollTop,rpos=$($t.rows[iR]).position().top,rh=$t.rows[iR].clientHeight;if(rpos+rh>=ch+st){$($t.grid.bDiv)[0].scrollTop=rpos-(ch+st)+rh+st;}else if(rpos<ch+st){if(rpos<st){$($t.grid.bDiv)[0].scrollTop=rpos;}}}if($t.p.scrollrows===true){ner=$t.rows.namedItem(selection).rowIndex;if(ner>=0){scrGrid(ner);}}if($t.p.frozenColumns===true){fid=$t.p.id+'_frozen';}if(!$t.p.multiselect){if(pt.className!=='ui-subgrid'){if($t.p.selrow!=pt.id){$($t.rows.namedItem($t.p.selrow)).removeClass('ui-state-highlight').attr({'aria-selected':'false','tabindex':'-1'});$(pt).addClass('ui-state-highlight').attr({'aria-selected':'true','tabindex':'0'});//.focus();
if(fid){$('#'+$.jgrid.jqID($t.p.selrow),'#'+$.jgrid.jqID(fid)).removeClass('ui-state-highlight');$('#'+$.jgrid.jqID(selection),'#'+$.jgrid.jqID(fid)).addClass('ui-state-highlight');}stat=true;}else{stat=false;}$t.p.selrow=pt.id;$($t).triggerHandler('jqGridSelectRow',[pt.id,stat,e]);if($t.p.onSelectRow&&onsr){$t.p.onSelectRow.call($t,pt.id,stat,e);}}}else{//unselect selectall checkbox when deselecting a specific row
$t.setHeadCheckBox(false);$t.p.selrow=pt.id;ia=$.inArray($t.p.selrow,$t.p.selarrrow);if(ia===-1){if(pt.className!=='ui-subgrid'){$(pt).addClass('ui-state-highlight').attr('aria-selected','true');}stat=true;$t.p.selarrrow.push($t.p.selrow);}else{if(pt.className!=='ui-subgrid'){$(pt).removeClass('ui-state-highlight').attr('aria-selected','false');}stat=false;$t.p.selarrrow.splice(ia,1);tpsr=$t.p.selarrrow[0];$t.p.selrow=tpsr===undefined?null:tpsr;}$('#jqg_'+$.jgrid.jqID($t.p.id)+'_'+$.jgrid.jqID(pt.id))[$t.p.useProp?'prop':'attr']('checked',stat);if(fid){if(ia===-1){$('#'+$.jgrid.jqID(selection),'#'+$.jgrid.jqID(fid)).addClass('ui-state-highlight');}else{$('#'+$.jgrid.jqID(selection),'#'+$.jgrid.jqID(fid)).removeClass('ui-state-highlight');}$('#jqg_'+$.jgrid.jqID($t.p.id)+'_'+$.jgrid.jqID(selection),'#'+$.jgrid.jqID(fid))[$t.p.useProp?'prop':'attr']('checked',stat);}$($t).triggerHandler('jqGridSelectRow',[pt.id,stat,e]);if($t.p.onSelectRow&&onsr){$t.p.onSelectRow.call($t,pt.id,stat,e);}}});},resetSelection:function resetSelection(rowid){return this.each(function(){var t=this,ind,sr,fid;if(t.p.frozenColumns===true){fid=t.p.id+'_frozen';}if(rowid!==undefined){sr=rowid===t.p.selrow?t.p.selrow:rowid;$('#'+$.jgrid.jqID(t.p.id)+' tbody:first tr#'+$.jgrid.jqID(sr)).removeClass('ui-state-highlight').attr('aria-selected','false');if(fid){$('#'+$.jgrid.jqID(sr),'#'+$.jgrid.jqID(fid)).removeClass('ui-state-highlight');}if(t.p.multiselect){$('#jqg_'+$.jgrid.jqID(t.p.id)+'_'+$.jgrid.jqID(sr),'#'+$.jgrid.jqID(t.p.id))[t.p.useProp?'prop':'attr']('checked',false);if(fid){$('#jqg_'+$.jgrid.jqID(t.p.id)+'_'+$.jgrid.jqID(sr),'#'+$.jgrid.jqID(fid))[t.p.useProp?'prop':'attr']('checked',false);}t.setHeadCheckBox(false);}sr=null;}else if(!t.p.multiselect){if(t.p.selrow){$('#'+$.jgrid.jqID(t.p.id)+' tbody:first tr#'+$.jgrid.jqID(t.p.selrow)).removeClass('ui-state-highlight').attr('aria-selected','false');if(fid){$('#'+$.jgrid.jqID(t.p.selrow),'#'+$.jgrid.jqID(fid)).removeClass('ui-state-highlight');}t.p.selrow=null;}}else{$(t.p.selarrrow).each(function(i,n){ind=t.rows.namedItem(n);$(ind).removeClass('ui-state-highlight').attr('aria-selected','false');$('#jqg_'+$.jgrid.jqID(t.p.id)+'_'+$.jgrid.jqID(n))[t.p.useProp?'prop':'attr']('checked',false);if(fid){$('#'+$.jgrid.jqID(n),'#'+$.jgrid.jqID(fid)).removeClass('ui-state-highlight');$('#jqg_'+$.jgrid.jqID(t.p.id)+'_'+$.jgrid.jqID(n),'#'+$.jgrid.jqID(fid))[t.p.useProp?'prop':'attr']('checked',false);}});t.setHeadCheckBox(false);t.p.selarrrow=[];}if(t.p.cellEdit===true){if(parseInt(t.p.iCol,10)>=0&&parseInt(t.p.iRow,10)>=0){$('td:eq('+t.p.iCol+')',t.rows[t.p.iRow]).removeClass('edit-cell ui-state-highlight');$(t.rows[t.p.iRow]).removeClass('selected-row ui-state-hover');}}t.p.savedRow=[];});},getRowData:function getRowData(rowid){var res={},resall,getall=false,len,j=0;this.each(function(){var $t=this,nm,ind;if(rowid===undefined){getall=true;resall=[];len=$t.rows.length;}else{ind=$t.rows.namedItem(rowid);if(!ind){return res;}len=2;}while(j<len){if(getall){ind=$t.rows[j];}if($(ind).hasClass('jqgrow')){$('td[role="gridcell"]',ind).each(function(i){nm=$t.p.colModel[i].name;if(nm!=='cb'&&nm!=='subgrid'&&nm!=='rn'){if($t.p.treeGrid===true&&nm==$t.p.ExpandColumn){res[nm]=$.jgrid.htmlDecode($('span:first',this).html());}else{try{res[nm]=$.unformat.call($t,this,{rowId:ind.id,colModel:$t.p.colModel[i]},i);}catch(e){res[nm]=$.jgrid.htmlDecode($(this).html());}}}});if(getall){resall.push(res);res={};}}j++;}});return resall||res;},delRowData:function delRowData(rowid){var success=false,rowInd,ia,ri;this.each(function(){var $t=this;rowInd=$t.rows.namedItem(rowid);if(!rowInd){return false;}ri=rowInd.rowIndex;$(rowInd).remove();$t.p.records--;$t.p.reccount--;$t.updatepager(true,false);success=true;if($t.p.multiselect){ia=$.inArray(rowid,$t.p.selarrrow);if(ia!=-1){$t.p.selarrrow.splice(ia,1);}}if($t.p.multiselect&&$t.p.selarrrow.length>0){$t.p.selrow=$t.p.selarrrow[$t.p.selarrrow.length-1];}else{$t.p.selrow=null;}if($t.p.datatype=='local'){var id=$.jgrid.stripPref($t.p.idPrefix,rowid),pos=$t.p._index[id];if(pos!==undefined){$t.p.data.splice(pos,1);$t.refreshIndex();}}if($t.p.altRows===true&&success){var cn=$t.p.altclass;$($t.rows).each(function(i){if(i%2==1){$(this).addClass(cn);}else{$(this).removeClass(cn);}});}});return success;},setRowData:function setRowData(rowid,data,cssp){var nm,success=true,title;this.each(function(){if(!this.grid){return false;}var t=this,vl,ind,cp=typeof cssp==="undefined"?"undefined":_typeof(cssp),lcdata={};ind=t.rows.namedItem(rowid);if(!ind){return false;}if(data){try{$(this.p.colModel).each(function(i){nm=this.name;if(data[nm]!==undefined){lcdata[nm]=this.formatter&&typeof this.formatter==='string'&&this.formatter=='date'?$.unformat.date.call(t,data[nm],this):data[nm];vl=t.formatter(rowid,data[nm],i,data,'edit');title=this.title?{'title':$.jgrid.stripHtml(vl)}:{};if(t.p.treeGrid===true&&nm==t.p.ExpandColumn){$('td[role=\'gridcell\']:eq('+i+') > span:first',ind).html(vl).attr(title);}else{$('td[role=\'gridcell\']:eq('+i+')',ind).html(vl).attr(title);}}});if(t.p.datatype=='local'){var id=$.jgrid.stripPref(t.p.idPrefix,rowid),pos=t.p._index[id],key;if(t.p.treeGrid){for(key in t.p.treeReader){if(t.p.treeReader.hasOwnProperty(key)){delete lcdata[t.p.treeReader[key]];}}}if(pos!==undefined){t.p.data[pos]=$.extend(true,t.p.data[pos],lcdata);}lcdata=null;}}catch(e){success=false;}}if(success){if(cp==='string'){$(ind).addClass(cssp);}else if(cp==='object'){$(ind).css(cssp);}$(t).triggerHandler('jqGridAfterGridComplete');}});return success;},addRowData:function addRowData(rowid,rdata,pos,src){if(!pos){pos='last';}var success=false,nm,row,gi,si,ni,sind,i,v,prp='',aradd,cnm,cn,data,cm,id;if(rdata){if($.isArray(rdata)){aradd=true;pos='last';cnm=rowid;}else{rdata=[rdata];aradd=false;}this.each(function(){var t=this,datalen=rdata.length;ni=t.p.rownumbers===true?1:0;gi=t.p.multiselect===true?1:0;si=t.p.subGrid===true?1:0;if(!aradd){if(rowid!==undefined){rowid=String(rowid);}else{rowid=$.jgrid.randId();if(t.p.keyIndex!==false){cnm=t.p.colModel[t.p.keyIndex+gi+si+ni].name;if(rdata[0][cnm]!==undefined){rowid=rdata[0][cnm];}}}}cn=t.p.altclass;var k=0,cna='',lcdata={},air=$.isFunction(t.p.afterInsertRow)?true:false;while(k<datalen){data=rdata[k];row=[];if(aradd){try{rowid=data[cnm];if(rowid===undefined){rowid=$.jgrid.randId();}}catch(e){rowid=$.jgrid.randId();}cna=t.p.altRows===true?(t.rows.length-1)%2===0?cn:'':'';}id=rowid;rowid=t.p.idPrefix+rowid;if(ni){prp=t.formatCol(0,1,'',null,rowid,true);row[row.length]='<td role="gridcell" class="ui-state-default jqgrid-rownum" '+prp+'>0</td>';}if(gi){v='<input role="checkbox" type="checkbox"'+' id="jqg_'+t.p.id+'_'+rowid+'" class="cbox"/>';prp=t.formatCol(ni,1,'',null,rowid,true);row[row.length]='<td role="gridcell" '+prp+'>'+v+'</td>';}if(si){row[row.length]=$(t).jqGrid('addSubGridCell',gi+ni,1);}for(i=gi+si+ni;i<t.p.colModel.length;i++){cm=t.p.colModel[i];nm=cm.name;lcdata[nm]=data[nm];v=t.formatter(rowid,$.jgrid.getAccessor(data,nm),i,data);prp=t.formatCol(i,1,v,data,rowid,lcdata);row[row.length]='<td role="gridcell" '+prp+'>'+v+'</td>';}row.unshift(t.constructTr(rowid,false,cna,lcdata,data,false));row[row.length]='</tr>';if(t.rows.length===0){$('table:first',t.grid.bDiv).append(row.join(''));}else{switch(pos){case'last':$(t.rows[t.rows.length-1]).after(row.join(''));sind=t.rows.length-1;break;case'first':$(t.rows[0]).after(row.join(''));sind=1;break;case'after':sind=t.rows.namedItem(src);if(sind){if($(t.rows[sind.rowIndex+1]).hasClass('ui-subgrid')){$(t.rows[sind.rowIndex+1]).after(row);}else{$(sind).after(row.join(''));}}sind++;break;case'before':sind=t.rows.namedItem(src);if(sind){$(sind).before(row.join(''));sind=sind.rowIndex;}sind--;break;}}if(t.p.subGrid===true){$(t).jqGrid('addSubGrid',gi+ni,sind);}t.p.records++;t.p.reccount++;$(t).triggerHandler('jqGridAfterInsertRow',[rowid,data,data]);if(air){t.p.afterInsertRow.call(t,rowid,data,data);}k++;if(t.p.datatype=='local'){lcdata[t.p.localReader.id]=id;t.p._index[id]=t.p.data.length;t.p.data.push(lcdata);lcdata={};}}if(t.p.altRows===true&&!aradd){if(pos=='last'){if((t.rows.length-1)%2==1){$(t.rows[t.rows.length-1]).addClass(cn);}}else{$(t.rows).each(function(i){if(i%2==1){$(this).addClass(cn);}else{$(this).removeClass(cn);}});}}t.updatepager(true,true);success=true;});}return success;},footerData:function footerData(action,data,format){var nm,success=false,res={},title;function isEmpty(obj){var i;for(i in obj){if(obj.hasOwnProperty(i)){return false;}}return true;}if(action===undefined){action='get';}if(typeof format!=='boolean'){format=true;}action=action.toLowerCase();this.each(function(){var t=this,vl;if(!t.grid||!t.p.footerrow){return false;}if(action=='set'){if(isEmpty(data)){return false;}}success=true;$(this.p.colModel).each(function(i){nm=this.name;if(action=='set'){if(data[nm]!==undefined){vl=format?t.formatter('',data[nm],i,data,'edit'):data[nm];title=this.title?{'title':$.jgrid.stripHtml(vl)}:{};$('tr.footrow td:eq('+i+')',t.grid.sDiv).html(vl).attr(title);success=true;}}else if(action=='get'){res[nm]=$('tr.footrow td:eq('+i+')',t.grid.sDiv).html();}});});return action=='get'?res:success;},showHideCol:function showHideCol(colname,show){return this.each(function(){var $t=this,fndh=false,brd=$.jgrid.cell_width?0:$t.p.cellLayout,cw;if(!$t.grid){return;}if(typeof colname==='string'){colname=[colname];}show=show!='none'?'':'none';var sw=show===''?true:false,gh=$t.p.groupHeader&&(_typeof($t.p.groupHeader)==='object'||$.isFunction($t.p.groupHeader));if(gh){$($t).jqGrid('destroyGroupHeader',false);}$(this.p.colModel).each(function(i){if($.inArray(this.name,colname)!==-1&&this.hidden===sw){if($t.p.frozenColumns===true&&this.frozen===true){return true;}$('tr',$t.grid.hDiv).each(function(){$(this.cells[i]).css('display',show);});$($t.rows).each(function(){if(!$(this).hasClass('jqgroup')){$(this.cells[i]).css('display',show);}});if($t.p.footerrow){$('tr.footrow td:eq('+i+')',$t.grid.sDiv).css('display',show);}cw=parseInt(this.width,10);if(show==='none'){$t.p.tblwidth-=cw+brd;}else{$t.p.tblwidth+=cw+brd;}this.hidden=!sw;fndh=true;$($t).triggerHandler('jqGridShowHideCol',[sw,this.name,i]);}});if(fndh===true){if($t.p.shrinkToFit===true&&!isNaN($t.p.height)){$t.p.tblwidth+=parseInt($t.p.scrollOffset,10);}$($t).jqGrid('setGridWidth',$t.p.shrinkToFit===true?$t.p.tblwidth:$t.p.width);}if(gh){$($t).jqGrid('setGroupHeaders',$t.p.groupHeader);}});},hideCol:function hideCol(colname){return this.each(function(){$(this).jqGrid('showHideCol',colname,'none');});},showCol:function showCol(colname){return this.each(function(){$(this).jqGrid('showHideCol',colname,'');});},remapColumns:function remapColumns(permutation,updateCells,keepHeader){function resortArray(a){var ac;if(a.length){ac=$.makeArray(a);}else{ac=$.extend({},a);}$.each(permutation,function(i){a[i]=ac[this];});}var ts=this.get(0);function resortRows(parent,clobj){$('>tr'+(clobj||''),parent).each(function(){var row=this;var elems=$.makeArray(row.cells);$.each(permutation,function(){var e=elems[this];if(e){row.appendChild(e);}});});}resortArray(ts.p.colModel);resortArray(ts.p.colNames);resortArray(ts.grid.headers);resortRows($('thead:first',ts.grid.hDiv),keepHeader&&':not(.ui-jqgrid-labels)');if(updateCells){resortRows($('#'+$.jgrid.jqID(ts.p.id)+' tbody:first'),'.jqgfirstrow, tr.jqgrow, tr.jqfoot');}if(ts.p.footerrow){resortRows($('tbody:first',ts.grid.sDiv));}if(ts.p.remapColumns){if(!ts.p.remapColumns.length){ts.p.remapColumns=$.makeArray(permutation);}else{resortArray(ts.p.remapColumns);}}ts.p.lastsort=$.inArray(ts.p.lastsort,permutation);if(ts.p.treeGrid){ts.p.expColInd=$.inArray(ts.p.expColInd,permutation);}$(ts).triggerHandler('jqGridRemapColumns',[permutation,updateCells,keepHeader]);},setGridWidth:function setGridWidth(nwidth,shrink){return this.each(function(){if(!this.grid){return;}var $t=this,cw,initwidth=0,brd=$.jgrid.cell_width?0:$t.p.cellLayout,lvc,vc=0,hs=false,scw=$t.p.scrollOffset,aw,gw=0,cl=0,cr;if(typeof shrink!=='boolean'){shrink=$t.p.shrinkToFit;}if(isNaN(nwidth)){return;}nwidth=parseInt(nwidth,10);$t.grid.width=$t.p.width=nwidth;$('#gbox_'+$.jgrid.jqID($t.p.id)).css('width',nwidth+'px');$('#gview_'+$.jgrid.jqID($t.p.id)).css('width',nwidth+'px');$($t.grid.bDiv).css('width',nwidth+'px');$($t.grid.hDiv).css('width',nwidth+'px');if($t.p.pager){$($t.p.pager).css('width',nwidth+'px');}if($t.p.toppager){$($t.p.toppager).css('width',nwidth+'px');}if($t.p.toolbar[0]===true){$($t.grid.uDiv).css('width',nwidth+'px');if($t.p.toolbar[1]=='both'){$($t.grid.ubDiv).css('width',nwidth+'px');}}if($t.p.footerrow){$($t.grid.sDiv).css('width',nwidth+'px');}if(shrink===false&&$t.p.forceFit===true){$t.p.forceFit=false;}if(shrink===true){$.each($t.p.colModel,function(){if(this.hidden===false){cw=this.widthOrg;initwidth+=cw+brd;if(this.fixed){gw+=cw+brd;}else{vc++;}cl++;}});if(vc===0){return;}$t.p.tblwidth=initwidth;aw=nwidth-brd*vc-gw;if(!isNaN($t.p.height)){if($($t.grid.bDiv)[0].clientHeight<$($t.grid.bDiv)[0].scrollHeight||$t.rows.length===1){hs=true;aw-=scw;}}initwidth=0;var cle=$t.grid.cols.length>0;$.each($t.p.colModel,function(i){if(this.hidden===false&&!this.fixed){cw=this.widthOrg;cw=Math.round(aw*cw/($t.p.tblwidth-brd*vc-gw));if(cw<0){return;}this.width=cw;initwidth+=cw;$t.grid.headers[i].width=cw;$t.grid.headers[i].el.style.width=cw+'px';if($t.p.footerrow){$t.grid.footers[i].style.width=cw+'px';}if(cle){$t.grid.cols[i].style.width=cw+'px';}lvc=i;}});if(!lvc){return;}cr=0;if(hs){if(nwidth-gw-(initwidth+brd*vc)!==scw){cr=nwidth-gw-(initwidth+brd*vc)-scw;}}else if(Math.abs(nwidth-gw-(initwidth+brd*vc))!==1){cr=nwidth-gw-(initwidth+brd*vc);}$t.p.colModel[lvc].width+=cr;$t.p.tblwidth=initwidth+cr+brd*vc+gw;if($t.p.tblwidth>nwidth){var delta=$t.p.tblwidth-parseInt(nwidth,10);$t.p.tblwidth=nwidth;cw=$t.p.colModel[lvc].width=$t.p.colModel[lvc].width-delta;}else{cw=$t.p.colModel[lvc].width;}$t.grid.headers[lvc].width=cw;$t.grid.headers[lvc].el.style.width=cw+'px';if(cle){$t.grid.cols[lvc].style.width=cw+'px';}if($t.p.footerrow){$t.grid.footers[lvc].style.width=cw+'px';}}if($t.p.tblwidth){$('table:first',$t.grid.bDiv).css('width',$t.p.tblwidth+'px');$('table:first',$t.grid.hDiv).css('width',$t.p.tblwidth+'px');$t.grid.hDiv.scrollLeft=$t.grid.bDiv.scrollLeft;if($t.p.footerrow){$('table:first',$t.grid.sDiv).css('width',$t.p.tblwidth+'px');}}});},setGridHeight:function setGridHeight(nh){return this.each(function(){var $t=this;if(!$t.grid){return;}var bDiv=$($t.grid.bDiv);bDiv.css({height:nh+(isNaN(nh)?'':'px')});if($t.p.frozenColumns===true){//follow the original set height to use 16, better scrollbar width detection
$('#'+$.jgrid.jqID($t.p.id)+'_frozen').parent().height(bDiv.height()-16);}$t.p.height=nh;if($t.p.scroll){$t.grid.populateVisible();}});},setCaption:function setCaption(newcap){return this.each(function(){this.p.caption=newcap;$('span.ui-jqgrid-title, span.ui-jqgrid-title-rtl',this.grid.cDiv).html(newcap);$(this.grid.cDiv).show();});},setLabel:function setLabel(colname,nData,prop,attrp){return this.each(function(){var $t=this,pos=-1;if(!$t.grid){return;}if(colname!==undefined){$($t.p.colModel).each(function(i){if(this.name==colname){pos=i;return false;}});}else{return;}if(pos>=0){var thecol=$('tr.ui-jqgrid-labels th:eq('+pos+')',$t.grid.hDiv);if(nData){var ico=$('.s-ico',thecol);$('[id^=jqgh_]',thecol).empty().html(nData).append(ico);$t.p.colNames[pos]=nData;}if(prop){if(typeof prop==='string'){$(thecol).addClass(prop);}else{$(thecol).css(prop);}}if((typeof attrp==="undefined"?"undefined":_typeof(attrp))==='object'){$(thecol).attr(attrp);}}});},setCell:function setCell(rowid,colname,nData,cssp,attrp,forceupd){return this.each(function(){var $t=this,pos=-1,v,title;if(!$t.grid){return;}if(isNaN(colname)){$($t.p.colModel).each(function(i){if(this.name==colname){pos=i;return false;}});}else{pos=parseInt(colname,10);}if(pos>=0){var ind=$t.rows.namedItem(rowid);if(ind){var tcell=$('td:eq('+pos+')',ind);if(nData!==''||forceupd===true){v=$t.formatter(rowid,nData,pos,ind,'edit');title=$t.p.colModel[pos].title?{'title':$.jgrid.stripHtml(v)}:{};if($t.p.treeGrid&&$('.tree-wrap',$(tcell)).length>0){$('span',$(tcell)).html(v).attr(title);}else{$(tcell).html(v).attr(title);}if($t.p.datatype=='local'){var cm=$t.p.colModel[pos],index;nData=cm.formatter&&typeof cm.formatter==='string'&&cm.formatter=='date'?$.unformat.date.call($t,nData,cm):nData;index=$t.p._index[rowid];if(index!==undefined){$t.p.data[index][cm.name]=nData;}}}if(typeof cssp==='string'){$(tcell).addClass(cssp);}else if(cssp){$(tcell).css(cssp);}if((typeof attrp==="undefined"?"undefined":_typeof(attrp))==='object'){$(tcell).attr(attrp);}}}});},getCell:function getCell(rowid,col){var ret=false;this.each(function(){var $t=this,pos=-1;if(!$t.grid){return;}if(isNaN(col)){$($t.p.colModel).each(function(i){if(this.name===col){pos=i;return false;}});}else{pos=parseInt(col,10);}if(pos>=0){var ind=$t.rows.namedItem(rowid);if(ind){try{ret=$.unformat.call($t,$('td:eq('+pos+')',ind),{rowId:ind.id,colModel:$t.p.colModel[pos]},pos);}catch(e){ret=$.jgrid.htmlDecode($('td:eq('+pos+')',ind).html());}}}});return ret;},getCol:function getCol(col,obj,mathopr){var ret=[],val,sum=0,min,max,v;obj=typeof obj!=='boolean'?false:obj;if(mathopr===undefined){mathopr=false;}this.each(function(){var $t=this,pos=-1;if(!$t.grid){return;}if(isNaN(col)){$($t.p.colModel).each(function(i){if(this.name===col){pos=i;return false;}});}else{pos=parseInt(col,10);}if(pos>=0){var ln=$t.rows.length,i=0;if(ln&&ln>0){while(i<ln){if($($t.rows[i]).hasClass('jqgrow')){try{val=$.unformat.call($t,$($t.rows[i].cells[pos]),{rowId:$t.rows[i].id,colModel:$t.p.colModel[pos]},pos);}catch(e){val=$.jgrid.htmlDecode($t.rows[i].cells[pos].innerHTML);}if(mathopr){v=parseFloat(val);sum+=v;if(max===undefined){max=min=v;}min=Math.min(min,v);max=Math.max(max,v);}else if(obj){ret.push({id:$t.rows[i].id,value:val});}else{ret.push(val);}}i++;}if(mathopr){switch(mathopr.toLowerCase()){case'sum':ret=sum;break;case'avg':ret=sum/ln;break;case'count':ret=ln;break;case'min':ret=min;break;case'max':ret=max;break;}}}}});return ret;},clearGridData:function clearGridData(clearfooter){return this.each(function(){var $t=this;if(!$t.grid){return;}if(typeof clearfooter!=='boolean'){clearfooter=false;}if($t.p.deepempty){$('#'+$.jgrid.jqID($t.p.id)+' tbody:first tr:gt(0)').remove();}else{var trf=$('#'+$.jgrid.jqID($t.p.id)+' tbody:first tr:first')[0];$('#'+$.jgrid.jqID($t.p.id)+' tbody:first').empty().append(trf);}if($t.p.footerrow&&clearfooter){$('.ui-jqgrid-ftable td',$t.grid.sDiv).html('&#160;');}$t.p.selrow=null;$t.p.selarrrow=[];$t.p.savedRow=[];$t.p.records=0;$t.p.page=1;$t.p.lastpage=0;$t.p.reccount=0;$t.p.data=[];$t.p._index={};$t.updatepager(true,false);});},getInd:function getInd(rowid,rc){var ret=false,rw;this.each(function(){rw=this.rows.namedItem(rowid);if(rw){ret=rc===true?rw:rw.rowIndex;}});return ret;},bindKeys:function bindKeys(settings){var o=$.extend({onEnter:null,onSpace:null,onLeftKey:null,onRightKey:null,scrollingRows:true},settings||{});return this.each(function(){var $t=this;if(!$('body').is('[role]')){$('body').attr('role','application');}$t.p.scrollrows=o.scrollingRows;$($t).keydown(function(event){var target=$($t).find('tr[tabindex=0]')[0],id,r,mind,expanded=$t.p.treeReader.expanded_field;//check for arrow keys
if(target){mind=$t.p._index[target.id];if(event.keyCode===37||event.keyCode===38||event.keyCode===39||event.keyCode===40){// up key
if(event.keyCode===38){r=target.previousSibling;id='';if(r){if($(r).is(':hidden')){while(r){r=r.previousSibling;if(!$(r).is(':hidden')&&$(r).hasClass('jqgrow')){id=r.id;break;}}}else{id=r.id;}}$($t).jqGrid('setSelection',id,true,event);event.preventDefault();}//if key is down arrow
if(event.keyCode===40){r=target.nextSibling;id='';if(r){if($(r).is(':hidden')){while(r){r=r.nextSibling;if(!$(r).is(':hidden')&&$(r).hasClass('jqgrow')){id=r.id;break;}}}else{id=r.id;}}$($t).jqGrid('setSelection',id,true,event);event.preventDefault();}// left
if(event.keyCode===37){if($t.p.treeGrid&&$t.p.data[mind][expanded]){$(target).find('div.treeclick').trigger('click');}$($t).triggerHandler('jqGridKeyLeft',[$t.p.selrow]);if($.isFunction(o.onLeftKey)){o.onLeftKey.call($t,$t.p.selrow);}}// right
if(event.keyCode===39){if($t.p.treeGrid&&!$t.p.data[mind][expanded]){$(target).find('div.treeclick').trigger('click');}$($t).triggerHandler('jqGridKeyRight',[$t.p.selrow]);if($.isFunction(o.onRightKey)){o.onRightKey.call($t,$t.p.selrow);}}}//check if enter was pressed on a grid or treegrid node
else if(event.keyCode===13){$($t).triggerHandler('jqGridKeyEnter',[$t.p.selrow]);if($.isFunction(o.onEnter)){o.onEnter.call($t,$t.p.selrow);}}else if(event.keyCode===32){$($t).triggerHandler('jqGridKeySpace',[$t.p.selrow]);if($.isFunction(o.onSpace)){o.onSpace.call($t,$t.p.selrow);}}}});});},unbindKeys:function unbindKeys(){return this.each(function(){$(this).unbind('keydown');});},getLocalRow:function getLocalRow(rowid){var ret=false,ind;this.each(function(){if(rowid!==undefined){ind=this.p._index[rowid];if(ind>=0){ret=this.p.data[ind];}}});return ret;}});})(jQuery);/*jshint eqeqeq:false *//*global jQuery */(function($){/**
 * jqGrid extension for custom methods
 * Tony Tomov tony@trirand.com
 * http://trirand.com/blog/
 *
 * Wildraid wildraid@mail.ru
 * Oleg Kiriljuk oleg.kiriljuk@ok-soft-gmbh.com
 * Dual licensed under the MIT and GPL licenses:
 * http://www.opensource.org/licenses/mit-license.php
 * http://www.gnu.org/licenses/gpl-2.0.html
**/'use strict';$.jgrid.extend({getColProp:function getColProp(colname){var ret={},$t=this[0];if(!$t.grid){return false;}var cM=$t.p.colModel,i;for(i=0;i<cM.length;i++){if(cM[i].name==colname){ret=cM[i];break;}}return ret;},setColProp:function setColProp(colname,obj){//do not set width will not work
return this.each(function(){if(this.grid){if(obj){var cM=this.p.colModel,i;for(i=0;i<cM.length;i++){if(cM[i].name==colname){$.extend(true,this.p.colModel[i],obj);break;}}}}});},sortGrid:function sortGrid(colname,reload,sor){return this.each(function(){var $t=this,idx=-1,i;if(!$t.grid){return;}if(!colname){colname=$t.p.sortname;}for(i=0;i<$t.p.colModel.length;i++){if($t.p.colModel[i].index==colname||$t.p.colModel[i].name==colname){idx=i;break;}}if(idx!=-1){var sort=$t.p.colModel[idx].sortable;if(typeof sort!=='boolean'){sort=true;}if(typeof reload!=='boolean'){reload=false;}if(sort){$t.sortData('jqgh_'+$t.p.id+'_'+colname,idx,reload,sor);}}});},clearBeforeUnload:function clearBeforeUnload(){return this.each(function(){var grid=this.grid;grid.emptyRows.call(this,true,true);// this work quick enough and reduce the size of memory leaks if we have someone
//$(document).unbind("mouseup"); // TODO add namespace
$(grid.hDiv).unbind('mousemove');// TODO add namespace
$(this).unbind();grid.dragEnd=null;grid.dragMove=null;grid.dragStart=null;grid.emptyRows=null;grid.populate=null;grid.populateVisible=null;grid.scrollGrid=null;grid.selectionPreserver=null;grid.bDiv=null;grid.cDiv=null;grid.hDiv=null;grid.cols=null;var i,l=grid.headers.length;for(i=0;i<l;i++){grid.headers[i].el=null;}this.formatCol=null;this.sortData=null;this.updatepager=null;this.refreshIndex=null;this.setHeadCheckBox=null;this.constructTr=null;this.formatter=null;this.addXmlData=null;this.addJSONData=null;});},GridDestroy:function GridDestroy(){return this.each(function(){if(this.grid){if(this.p.pager){// if not part of grid
$(this.p.pager).remove();}try{$(this).jqGrid('clearBeforeUnload');$('#gbox_'+$.jgrid.jqID(this.id)).remove();}catch(_){}}});},GridUnload:function GridUnload(){return this.each(function(){if(!this.grid){return;}var defgrid={id:$(this).attr('id'),cl:$(this).attr('class')};if(this.p.pager){$(this.p.pager).empty().removeClass('ui-state-default ui-jqgrid-pager corner-bottom');}var newtable=document.createElement('table');$(newtable).attr({id:defgrid.id});newtable.className=defgrid.cl;var gid=$.jgrid.jqID(this.id);$(newtable).removeClass('ui-jqgrid-btable');if($(this.p.pager).parents('#gbox_'+gid).length===1){$(newtable).insertBefore('#gbox_'+gid).show();$(this.p.pager).insertBefore('#gbox_'+gid);}else{$(newtable).insertBefore('#gbox_'+gid).show();}$(this).jqGrid('clearBeforeUnload');$('#gbox_'+gid).remove();});},setGridState:function setGridState(state){return this.each(function(){if(!this.grid){return;}var $t=this;if(state=='hidden'){$('.ui-jqgrid-bdiv, .ui-jqgrid-hdiv','#gview_'+$.jgrid.jqID($t.p.id)).slideUp('fast');if($t.p.pager){$($t.p.pager).slideUp('fast');}if($t.p.toppager){$($t.p.toppager).slideUp('fast');}if($t.p.toolbar[0]===true){if($t.p.toolbar[1]=='both'){$($t.grid.ubDiv).slideUp('fast');}$($t.grid.uDiv).slideUp('fast');}if($t.p.footerrow){$('.ui-jqgrid-sdiv','#gbox_'+$.jgrid.jqID($t.p.id)).slideUp('fast');}$('.ui-jqgrid-titlebar-close span',$t.grid.cDiv).removeClass('ui-icon-circle-triangle-n').addClass('ui-icon-circle-triangle-s');$t.p.gridstate='hidden';}else if(state=='visible'){$('.ui-jqgrid-hdiv, .ui-jqgrid-bdiv','#gview_'+$.jgrid.jqID($t.p.id)).slideDown('fast');if($t.p.pager){$($t.p.pager).slideDown('fast');}if($t.p.toppager){$($t.p.toppager).slideDown('fast');}if($t.p.toolbar[0]===true){if($t.p.toolbar[1]=='both'){$($t.grid.ubDiv).slideDown('fast');}$($t.grid.uDiv).slideDown('fast');}if($t.p.footerrow){$('.ui-jqgrid-sdiv','#gbox_'+$.jgrid.jqID($t.p.id)).slideDown('fast');}$('.ui-jqgrid-titlebar-close span',$t.grid.cDiv).removeClass('ui-icon-circle-triangle-s').addClass('ui-icon-circle-triangle-n');$t.p.gridstate='visible';}});},filterToolbar:function filterToolbar(p){p=$.extend({autosearch:true,searchOnEnter:true,beforeSearch:null,afterSearch:null,beforeClear:null,afterClear:null,searchurl:'',stringResult:false,groupOp:'AND',defaultSearch:'bw'},p||{});return this.each(function(){var $t=this;if(this.ftoolbar){return;}var triggerToolbar=function triggerToolbar(){var sdata={},j=0,v,nm,sopt={},so;$.each($t.p.colModel,function(){nm=this.index||this.name;so=this.searchoptions&&this.searchoptions.sopt?this.searchoptions.sopt[0]:this.stype=='select'?'eq':p.defaultSearch;v=$('#gs_'+$.jgrid.jqID(this.name),this.frozen===true&&$t.p.frozenColumns===true?$t.grid.fhDiv:$t.grid.hDiv).val();if(v){sdata[nm]=v;sopt[nm]=so;j++;}else{try{delete $t.p.postData[nm];}catch(z){}}});var sd=j>0?true:false;if(p.stringResult===true||$t.p.datatype=='local'){var ruleGroup='{"groupOp":"'+p.groupOp+'","rules":[';var gi=0;$.each(sdata,function(i,n){if(gi>0){ruleGroup+=',';}ruleGroup+='{"field":"'+i+'",';ruleGroup+='"op":"'+sopt[i]+'",';n+='';ruleGroup+='"data":"'+n.replace(/\\/g,'\\\\').replace(/\"/g,'\\"')+'"}';gi++;});ruleGroup+=']}';$.extend($t.p.postData,{filters:ruleGroup});$.each(['searchField','searchString','searchOper'],function(i,n){if($t.p.postData.hasOwnProperty(n)){delete $t.p.postData[n];}});}else{$.extend($t.p.postData,sdata);}var saveurl;if($t.p.searchurl){saveurl=$t.p.url;$($t).jqGrid('setGridParam',{url:$t.p.searchurl});}var bsr=$($t).triggerHandler('jqGridToolbarBeforeSearch')==='stop'?true:false;if(!bsr&&$.isFunction(p.beforeSearch)){bsr=p.beforeSearch.call($t);}if(!bsr){$($t).jqGrid('setGridParam',{search:sd}).trigger('reloadGrid',[{page:1}]);}if(saveurl){$($t).jqGrid('setGridParam',{url:saveurl});}$($t).triggerHandler('jqGridToolbarAfterSearch');if($.isFunction(p.afterSearch)){p.afterSearch.call($t);}};var clearToolbar=function clearToolbar(trigger){var sdata={},j=0,nm;trigger=typeof trigger!=='boolean'?true:trigger;$.each($t.p.colModel,function(){var v;if(this.searchoptions&&this.searchoptions.defaultValue!==undefined){v=this.searchoptions.defaultValue;}nm=this.index||this.name;switch(this.stype){case'select':$('#gs_'+$.jgrid.jqID(this.name)+' option',this.frozen===true&&$t.p.frozenColumns===true?$t.grid.fhDiv:$t.grid.hDiv).each(function(i){if(i===0){this.selected=true;}if($(this).val()==v){this.selected=true;return false;}});if(v!==undefined){// post the key and not the text
sdata[nm]=v;j++;}else{try{delete $t.p.postData[nm];}catch(e){}}break;case'text':$('#gs_'+$.jgrid.jqID(this.name),this.frozen===true&&$t.p.frozenColumns===true?$t.grid.fhDiv:$t.grid.hDiv).val(v);if(v!==undefined){sdata[nm]=v;j++;}else{try{delete $t.p.postData[nm];}catch(y){}}break;}});var sd=j>0?true:false;if(p.stringResult===true||$t.p.datatype=='local'){var ruleGroup='{"groupOp":"'+p.groupOp+'","rules":[';var gi=0;$.each(sdata,function(i,n){if(gi>0){ruleGroup+=',';}ruleGroup+='{"field":"'+i+'",';ruleGroup+='"op":"'+'eq'+'",';n+='';ruleGroup+='"data":"'+n.replace(/\\/g,'\\\\').replace(/\"/g,'\\"')+'"}';gi++;});ruleGroup+=']}';$.extend($t.p.postData,{filters:ruleGroup});$.each(['searchField','searchString','searchOper'],function(i,n){if($t.p.postData.hasOwnProperty(n)){delete $t.p.postData[n];}});}else{$.extend($t.p.postData,sdata);}var saveurl;if($t.p.searchurl){saveurl=$t.p.url;$($t).jqGrid('setGridParam',{url:$t.p.searchurl});}var bcv=$($t).triggerHandler('jqGridToolbarBeforeClear')==='stop'?true:false;if(!bcv&&$.isFunction(p.beforeClear)){bcv=p.beforeClear.call($t);}if(!bcv){if(trigger){$($t).jqGrid('setGridParam',{search:sd}).trigger('reloadGrid',[{page:1}]);}}if(saveurl){$($t).jqGrid('setGridParam',{url:saveurl});}$($t).triggerHandler('jqGridToolbarAfterClear');if($.isFunction(p.afterClear)){p.afterClear();}};var toggleToolbar=function toggleToolbar(){var trow=$('tr.ui-search-toolbar',$t.grid.hDiv),trow2=$t.p.frozenColumns===true?$('tr.ui-search-toolbar',$t.grid.fhDiv):false;if(trow.css('display')=='none'){trow.show();if(trow2){trow2.show();}}else{trow.hide();if(trow2){trow2.hide();}}};// create the row
var tr=$('<tr class=\'ui-search-toolbar\' role=\'rowheader\'></tr>');var timeoutHnd;$.each($t.p.colModel,function(){var cm=this,thd,th,soptions,surl,self;th=$('<th role=\'columnheader\' class=\'ui-state-default ui-th-column ui-th-'+$t.p.direction+'\'></th>');thd=$('<div style=\'position:relative;height:100%;padding-right:0.3em;\'></div>');if(this.hidden===true){$(th).css('display','none');}this.search=this.search===false?false:true;if(this.stype===undefined){this.stype='text';}soptions=$.extend({},this.searchoptions||{});if(this.search){switch(this.stype){case'select':surl=this.surl||soptions.dataUrl;if(surl){// data returned should have already constructed html select
// primitive jQuery load
self=thd;$.ajax($.extend({url:surl,dataType:'html',success:function success(res){if(soptions.buildSelect!==undefined){var d=soptions.buildSelect(res);if(d){$(self).append(d);}}else{$(self).append(res);}if(soptions.defaultValue!==undefined){$('select',self).val(soptions.defaultValue);}$('select',self).attr({name:cm.index||cm.name,id:'gs_'+cm.name});if(soptions.attr){$('select',self).attr(soptions.attr);}$('select',self).css({width:'100%'});// preserve autoserch
$.jgrid.bindEv($('select',self)[0],soptions,$t);if(p.autosearch===true){$('select',self).change(function(){triggerToolbar();return false;});}res=null;}},$.jgrid.ajaxOptions,$t.p.ajaxSelectOptions||{}));}else{var oSv,sep,delim;if(cm.searchoptions){oSv=cm.searchoptions.value===undefined?'':cm.searchoptions.value;sep=cm.searchoptions.separator===undefined?':':cm.searchoptions.separator;delim=cm.searchoptions.delimiter===undefined?';':cm.searchoptions.delimiter;}else if(cm.editoptions){oSv=cm.editoptions.value===undefined?'':cm.editoptions.value;sep=cm.editoptions.separator===undefined?':':cm.editoptions.separator;delim=cm.editoptions.delimiter===undefined?';':cm.editoptions.delimiter;}if(oSv){var elem=document.createElement('select');elem.style.width='100%';$(elem).attr({name:cm.index||cm.name,id:'gs_'+cm.name});var so,sv,ov,key,k;if(typeof oSv==='string'){so=oSv.split(delim);for(k=0;k<so.length;k++){sv=so[k].split(sep);ov=document.createElement('option');ov.value=sv[0];ov.innerHTML=sv[1];elem.appendChild(ov);}}else if((typeof oSv==="undefined"?"undefined":_typeof(oSv))==='object'){for(key in oSv){if(oSv.hasOwnProperty(key)){ov=document.createElement('option');ov.value=key;ov.innerHTML=oSv[key];elem.appendChild(ov);}}}if(soptions.defaultValue!==undefined){$(elem).val(soptions.defaultValue);}if(soptions.attr){$(elem).attr(soptions.attr);}$.jgrid.bindEv(elem,soptions,$t);$(thd).append(elem);if(p.autosearch===true){$(elem).change(function(){triggerToolbar();return false;});}}}break;case'text':var df=soptions.defaultValue!==undefined?soptions.defaultValue:'';$(thd).append('<input type=\'text\' style=\'width:95%;padding:0px;\' name=\''+(cm.index||cm.name)+'\' id=\'gs_'+cm.name+'\' value=\''+df+'\'/>');if(soptions.attr){$('input',thd).attr(soptions.attr);}$.jgrid.bindEv($('input',thd)[0],soptions,$t);if(p.autosearch===true){if(p.searchOnEnter){$('input',thd).keypress(function(e){var key=e.charCode||e.keyCode||0;if(key==13){triggerToolbar();return false;}return this;});}else{$('input',thd).keydown(function(e){var key=e.which;switch(key){case 13:return false;case 9:case 16:case 37:case 38:case 39:case 40:case 27:break;default:if(timeoutHnd){clearTimeout(timeoutHnd);}timeoutHnd=setTimeout(function(){triggerToolbar();},500);}});}}break;}}$(th).append(thd);$(tr).append(th);});$('table thead',$t.grid.hDiv).append(tr);this.ftoolbar=true;this.triggerToolbar=triggerToolbar;this.clearToolbar=clearToolbar;this.toggleToolbar=toggleToolbar;});},destroyFilterToolbar:function destroyFilterToolbar(){return this.each(function(){if(!this.ftoolbar){return;}this.triggerToolbar=null;this.clearToolbar=null;this.toggleToolbar=null;this.ftoolbar=false;$(this.grid.hDiv).find('table thead tr.ui-search-toolbar').remove();});},destroyGroupHeader:function destroyGroupHeader(nullHeader){if(nullHeader===undefined){nullHeader=true;}return this.each(function(){var $t=this,$tr,i,l,headers,$th,$resizing,grid=$t.grid,thead=$('table.ui-jqgrid-htable thead',grid.hDiv),cm=$t.p.colModel,hc;if(!grid){return;}$(this).unbind('.setGroupHeaders');$tr=$('<tr>',{role:'rowheader'}).addClass('ui-jqgrid-labels');headers=grid.headers;for(i=0,l=headers.length;i<l;i++){hc=cm[i].hidden?'none':'';$th=$(headers[i].el).width(headers[i].width).css('display',hc);try{$th.removeAttr('rowSpan');}catch(rs){//IE 6/7
$th.attr('rowSpan',1);}$tr.append($th);$resizing=$th.children('span.ui-jqgrid-resize');if($resizing.length>0){// resizable column
$resizing[0].style.height='';}$th.children('div')[0].style.top='';}$(thead).children('tr.ui-jqgrid-labels').remove();$(thead).prepend($tr);if(nullHeader===true){$($t).jqGrid('setGridParam',{'groupHeader':null});}});},setGroupHeaders:function setGroupHeaders(o){o=$.extend({useColSpanStyle:false,groupHeaders:[]},o||{});return this.each(function(){this.p.groupHeader=o;var ts=this,i,cmi,skip=0,$tr,$colHeader,th,$th,thStyle,iCol,cghi,//startColumnName,
numberOfColumns,titleText,cVisibleColumns,colModel=ts.p.colModel,cml=colModel.length,ths=ts.grid.headers,$htable=$('table.ui-jqgrid-htable',ts.grid.hDiv),$trLabels=$htable.children('thead').children('tr.ui-jqgrid-labels:last').addClass('jqg-second-row-header'),$thead=$htable.children('thead'),$theadInTable,$firstHeaderRow=$htable.find('.jqg-first-row-header');if($firstHeaderRow[0]===undefined){$firstHeaderRow=$('<tr>',{role:'row','aria-hidden':'true'}).addClass('jqg-first-row-header').css('height','auto');}else{$firstHeaderRow.empty();}var $firstRow,inColumnHeader=function inColumnHeader(text,columnHeaders){var length=columnHeaders.length,i;for(i=0;i<length;i++){if(columnHeaders[i].startColumnName===text){return i;}}return-1;};$(ts).prepend($thead);$tr=$('<tr>',{role:'rowheader'}).addClass('ui-jqgrid-labels jqg-third-row-header');for(i=0;i<cml;i++){th=ths[i].el;$th=$(th);cmi=colModel[i];// build the next cell for the first header row
thStyle={height:'0px',width:ths[i].width+'px',display:cmi.hidden?'none':''};$('<th>',{role:'gridcell'}).css(thStyle).addClass('ui-first-th-'+ts.p.direction).appendTo($firstHeaderRow);th.style.width='';// remove unneeded style
iCol=inColumnHeader(cmi.name,o.groupHeaders);if(iCol>=0){cghi=o.groupHeaders[iCol];numberOfColumns=cghi.numberOfColumns;titleText=cghi.titleText;// caclulate the number of visible columns from the next numberOfColumns columns
for(cVisibleColumns=0,iCol=0;iCol<numberOfColumns&&i+iCol<cml;iCol++){if(!colModel[i+iCol].hidden){cVisibleColumns++;}}// The next numberOfColumns headers will be moved in the next row
// in the current row will be placed the new column header with the titleText.
// The text will be over the cVisibleColumns columns
$colHeader=$('<th>').attr({role:'columnheader'}).addClass('ui-state-default ui-th-column-header ui-th-'+ts.p.direction).css({'height':'22px','border-top':'0px none'}).html(titleText);if(cVisibleColumns>0){$colHeader.attr('colspan',String(cVisibleColumns));}if(ts.p.headertitles){$colHeader.attr('title',$colHeader.text());}// hide if not a visible cols
if(cVisibleColumns===0){$colHeader.hide();}$th.before($colHeader);// insert new column header before the current
$tr.append(th);// move the current header in the next row
// set the coumter of headers which will be moved in the next row
skip=numberOfColumns-1;}else{if(skip===0){if(o.useColSpanStyle){// expand the header height to two rows
$th.attr('rowspan','2');}else{$('<th>',{role:'columnheader'}).addClass('ui-state-default ui-th-column-header ui-th-'+ts.p.direction).css({'display':cmi.hidden?'none':'','border-top':'0px none'}).insertBefore($th);$tr.append(th);}}else{// move the header to the next row
//$th.css({"padding-top": "2px", height: "19px"});
$tr.append(th);skip--;}}}$theadInTable=$(ts).children('thead');$theadInTable.prepend($firstHeaderRow);$tr.insertAfter($trLabels);$htable.append($theadInTable);if(o.useColSpanStyle){// Increase the height of resizing span of visible headers
$htable.find('span.ui-jqgrid-resize').each(function(){var $parent=$(this).parent();if($parent.is(':visible')){this.style.cssText='height: '+$parent.height()+'px !important; cursor: col-resize;';}});// Set position of the sortable div (the main lable)
// with the column header text to the middle of the cell.
// One should not do this for hidden headers.
$htable.find('div.ui-jqgrid-sortable').each(function(){var $ts=$(this),$parent=$ts.parent();if($parent.is(':visible')&&$parent.is(':has(span.ui-jqgrid-resize)')){$ts.css('top',($parent.height()-$ts.outerHeight())/2+'px');}});}$firstRow=$theadInTable.find('tr.jqg-first-row-header');$(ts).bind('jqGridResizeStop.setGroupHeaders',function(e,nw,idx){$firstRow.find('th').eq(idx).width(nw);});});},setFrozenColumns:function setFrozenColumns(){return this.each(function(){if(!this.grid){return;}var $t=this,cm=$t.p.colModel,i=0,len=cm.length,maxfrozen=-1,frozen=false;// TODO treeGrid and grouping  Support
if($t.p.subGrid===true||$t.p.treeGrid===true||$t.p.cellEdit===true||$t.p.sortable||$t.p.scroll||$t.p.grouping){return;}if($t.p.rownumbers){i++;}if($t.p.multiselect){i++;}// get the max index of frozen col
while(i<len){// from left, no breaking frozen
if(cm[i].frozen===true){frozen=true;maxfrozen=i;}else{break;}i++;}if(maxfrozen>=0&&frozen){var top=$t.p.caption?$($t.grid.cDiv).outerHeight():0,hth=$('.ui-jqgrid-htable','#gview_'+$.jgrid.jqID($t.p.id)).height();//headers
if($t.p.toppager){top=top+$($t.grid.topDiv).outerHeight();}if($t.p.toolbar[0]===true){if($t.p.toolbar[1]!='bottom'){top=top+$($t.grid.uDiv).outerHeight();}}$t.grid.fhDiv=$('<div style="position:absolute;left:0px;top:'+top+'px;height:'+hth+'px;" class="frozen-div ui-state-default ui-jqgrid-hdiv"></div>');$t.grid.fbDiv=$('<div style="position:absolute;left:0px;top:'+(parseInt(top,10)+parseInt(hth,10)+1)+'px;overflow-y:hidden" class="frozen-bdiv ui-jqgrid-bdiv"></div>');$('#gview_'+$.jgrid.jqID($t.p.id)).append($t.grid.fhDiv);var htbl=$('.ui-jqgrid-htable','#gview_'+$.jgrid.jqID($t.p.id)).clone(true);// groupheader support - only if useColSpanstyle is false
if($t.p.groupHeader){$('tr.jqg-first-row-header, tr.jqg-third-row-header',htbl).each(function(){$('th:gt('+maxfrozen+')',this).remove();});var swapfroz=-1,fdel=-1;$('tr.jqg-second-row-header th',htbl).each(function(){var cs=parseInt($(this).attr('colspan'),10);if(cs){swapfroz=swapfroz+cs;fdel++;}if(swapfroz===maxfrozen){return false;}});if(swapfroz!==maxfrozen){fdel=maxfrozen;}$('tr.jqg-second-row-header',htbl).each(function(){$('th:gt('+fdel+')',this).remove();});}else{$('tr',htbl).each(function(){$('th:gt('+maxfrozen+')',this).remove();});}$(htbl).width(1);// resizing stuff
$($t.grid.fhDiv).append(htbl).mousemove(function(e){if($t.grid.resizing){$t.grid.dragMove(e);return false;}});$($t).bind('jqGridResizeStop.setFrozenColumns',function(e,w,index){var rhth=$('.ui-jqgrid-htable',$t.grid.fhDiv);$('th:eq('+index+')',rhth).width(w);var btd=$('.ui-jqgrid-btable',$t.grid.fbDiv);$('tr:first td:eq('+index+')',btd).width(w);});// sorting stuff
$($t).bind('jqGridOnSortCol.setFrozenColumns',function(index,idxcol){var previousSelectedTh=$('tr.ui-jqgrid-labels:last th:eq('+$t.p.lastsort+')',$t.grid.fhDiv),newSelectedTh=$('tr.ui-jqgrid-labels:last th:eq('+idxcol+')',$t.grid.fhDiv);$('span.ui-grid-ico-sort',previousSelectedTh).addClass('ui-state-disabled');$(previousSelectedTh).attr('aria-selected','false');$('span.ui-icon-'+$t.p.sortorder,newSelectedTh).removeClass('ui-state-disabled');$(newSelectedTh).attr('aria-selected','true');if(!$t.p.viewsortcols[0]){if($t.p.lastsort!=idxcol){$('span.s-ico',previousSelectedTh).hide();$('span.s-ico',newSelectedTh).show();}}});// data stuff
//TODO support for setRowData
$('#gview_'+$.jgrid.jqID($t.p.id)).append($t.grid.fbDiv);$($t.grid.bDiv).scroll(function(){$($t.grid.fbDiv).scrollTop($(this).scrollTop());});if($t.p.hoverrows===true){$('#'+$.jgrid.jqID($t.p.id)).unbind('mouseover').unbind('mouseout');}$($t).bind('jqGridAfterGridComplete.setFrozenColumns',function(){$('#'+$.jgrid.jqID($t.p.id)+'_frozen').remove();$($t.grid.fbDiv).height($($t.grid.bDiv).height()-16);var btbl=$('#'+$.jgrid.jqID($t.p.id)).clone(true);$('tr',btbl).each(function(){$('td:gt('+maxfrozen+')',this).remove();});$(btbl).width(1).attr('id',$t.p.id+'_frozen');$($t.grid.fbDiv).append(btbl);if($t.p.hoverrows===true){$('tr.jqgrow',btbl).hover(function(){$(this).addClass('ui-state-hover');$('#'+$.jgrid.jqID(this.id),'#'+$.jgrid.jqID($t.p.id)).addClass('ui-state-hover');},function(){$(this).removeClass('ui-state-hover');$('#'+$.jgrid.jqID(this.id),'#'+$.jgrid.jqID($t.p.id)).removeClass('ui-state-hover');});$('tr.jqgrow','#'+$.jgrid.jqID($t.p.id)).hover(function(){$(this).addClass('ui-state-hover');$('#'+$.jgrid.jqID(this.id),'#'+$.jgrid.jqID($t.p.id)+'_frozen').addClass('ui-state-hover');},function(){$(this).removeClass('ui-state-hover');$('#'+$.jgrid.jqID(this.id),'#'+$.jgrid.jqID($t.p.id)+'_frozen').removeClass('ui-state-hover');});}btbl=null;});$t.p.frozenColumns=true;}});},destroyFrozenColumns:function destroyFrozenColumns(){return this.each(function(){if(!this.grid){return;}if(this.p.frozenColumns===true){var $t=this;$($t.grid.fhDiv).remove();$($t.grid.fbDiv).remove();$t.grid.fhDiv=null;$t.grid.fbDiv=null;$(this).unbind('.setFrozenColumns');if($t.p.hoverrows===true){var ptr;$('#'+$.jgrid.jqID($t.p.id)).bind('mouseover',function(e){ptr=$(e.target).closest('tr.jqgrow');if($(ptr).attr('class')!=='ui-subgrid'){$(ptr).addClass('ui-state-hover');}}).bind('mouseout',function(e){ptr=$(e.target).closest('tr.jqgrow');$(ptr).removeClass('ui-state-hover');});}this.p.frozenColumns=false;}});}});})(jQuery);/*
 * jqModal - Minimalist Modaling with jQuery
 *   (http://dev.iceburg.net/jquery/jqmodal/)
 *
 * Copyright (c) 2007,2008 Brice Burgess <bhb@iceburg.net>
 * Dual licensed under the MIT and GPL licenses:
 *   http://www.opensource.org/licenses/mit-license.php
 *   http://www.gnu.org/licenses/gpl.html
 *
 * $Version: 07/06/2008 +r13
 */(function($){$.fn.jqm=function(o){var p={overlay:50,closeoverlay:true,overlayClass:'jqmOverlay',closeClass:'jqmClose',trigger:'.jqModal',ajax:F,ajaxText:'',target:F,modal:F,toTop:F,onShow:F,onHide:F,onLoad:F};return this.each(function(){if(this._jqm)return H[this._jqm].c=$.extend({},H[this._jqm].c,o);s++;this._jqm=s;H[s]={c:$.extend(p,$.jqm.params,o),a:F,w:$(this).addClass('jqmID'+s),s:s};if(p.trigger)$(this).jqmAddTrigger(p.trigger);});};$.fn.jqmAddClose=function(e){return hs(this,e,'jqmHide');};$.fn.jqmAddTrigger=function(e){return hs(this,e,'jqmShow');};$.fn.jqmShow=function(t){return this.each(function(){$.jqm.open(this._jqm,t);});};$.fn.jqmHide=function(t){return this.each(function(){$.jqm.close(this._jqm,t);});};$.jqm={hash:{},open:function open(s,t){var h=H[s],c=h.c,cc='.'+c.closeClass,z=parseInt(h.w.css('z-index'));z=z>0?z:3000;var o=$('<div></div>').css({height:'100%',width:'100%',position:'fixed',left:0,top:0,'z-index':z-1,opacity:c.overlay/100});if(h.a)return F;h.t=t;h.a=true;h.w.css('z-index',z);if(c.modal){if(!A[0])setTimeout(function(){L('bind');},1);A.push(s);}else if(c.overlay>0){if(c.closeoverlay)h.w.jqmAddClose(o);}else o=F;h.o=o?o.addClass(c.overlayClass).prependTo('body'):F;if(c.ajax){var r=c.target||h.w,u=c.ajax;r=typeof r=='string'?$(r,h.w):$(r);u=u.substr(0,1)=='@'?$(t).attr(u.substring(1)):u;r.html(c.ajaxText).load(u,function(){if(c.onLoad)c.onLoad.call(this,h);if(cc)h.w.jqmAddClose($(cc,h.w));e(h);});}else if(cc)h.w.jqmAddClose($(cc,h.w));if(c.toTop&&h.o)h.w.before('<span id="jqmP'+h.w[0]._jqm+'"></span>').insertAfter(h.o);c.onShow?c.onShow(h):h.w.show();e(h);return F;},close:function close(s){var h=H[s];if(!h.a)return F;h.a=F;if(A[0]){A.pop();if(!A[0])L('unbind');}if(h.c.toTop&&h.o)$('#jqmP'+h.w[0]._jqm).after(h.w).remove();if(h.c.onHide)h.c.onHide(h);else{h.w.hide();if(h.o)h.o.remove();}return F;},params:{}};var s=0,H=$.jqm.hash,A=[],F=false,e=function e(h){f(h);},f=function f(h){try{$(':input:visible',h.w)[0].focus();}catch(_){}},L=function L(t){$(document)[t]('keypress',m)[t]('keydown',m)[t]('mousedown',m);},m=function m(e){var h=H[A[A.length-1]],r=!$(e.target).parents('.jqmID'+h.s)[0];if(r)f(h);return!r;},hs=function hs(w,t,c){return w.each(function(){var s=this._jqm;$(t).each(function(){if(!this[c]){this[c]=[];$(this).click(function(){for(var i in{jqmShow:1,jqmHide:1}){for(var s in this[i]){if(H[this[i][s]])H[this[i][s]].w[i](this);}}return F;});}this[c].push(s);});});};})(jQuery);/*
 * jqDnR - Minimalistic Drag'n'Resize for jQuery.
 *
 * Copyright (c) 2007 Brice Burgess <bhb@iceburg.net>, http://www.iceburg.net
 * Licensed under the MIT License:
 * http://www.opensource.org/licenses/mit-license.php
 *
 * $Version: 2007.08.19 +r2
 */(function($){$.fn.jqDrag=function(h){return i(this,h,'d');};$.fn.jqResize=function(h,ar){return i(this,h,'r',ar);};$.jqDnR={dnr:{},e:0,drag:function drag(v){if(M.k=='d'){E.css({left:M.X+v.pageX-M.pX,top:M.Y+v.pageY-M.pY});}else{E.css({width:Math.max(v.pageX-M.pX+M.W,0),height:Math.max(v.pageY-M.pY+M.H,0)});if(M1){E1.css({width:Math.max(v.pageX-M1.pX+M1.W,0),height:Math.max(v.pageY-M1.pY+M1.H,0)});}}return false;},stop:function stop(){//E.css('opacity',M.o);
$(document).unbind('mousemove',J.drag).unbind('mouseup',J.stop);}};var J=$.jqDnR,M=J.dnr,E=J.e,E1,M1,i=function i(e,h,k,aR){return e.each(function(){h=h?$(h,e):e;h.bind('mousedown',{e:e,k:k},function(v){var d=v.data,p={};E=d.e;E1=aR?$(aR):false;// attempt utilization of dimensions plugin to fix IE issues
if(E.css('position')!='relative'){try{E.position(p);}catch(e){}}M={X:p.left||f('left')||0,Y:p.top||f('top')||0,W:f('width')||E[0].scrollWidth||0,H:f('height')||E[0].scrollHeight||0,pX:v.pageX,pY:v.pageY,k:d.k//o:E.css('opacity')
};// also resize
if(E1&&d.k!='d'){M1={X:p.left||f1('left')||0,Y:p.top||f1('top')||0,W:E1[0].offsetWidth||f1('width')||0,H:E1[0].offsetHeight||f1('height')||0,pX:v.pageX,pY:v.pageY,k:d.k};}else{M1=false;}//E.css({opacity:0.8});
if($('input.hasDatepicker',E[0])[0]){try{$('input.hasDatepicker',E[0]).datepicker('hide');}catch(dpe){}}$(document).mousemove($.jqDnR.drag).mouseup($.jqDnR.stop);return false;});});},f=function f(k){return parseInt(E.css(k),10)||false;},f1=function f1(k){return parseInt(E1.css(k),10)||false;};})(jQuery);/*
	The below work is licensed under Creative Commons GNU LGPL License.

	Original work:

	License:     http://creativecommons.org/licenses/LGPL/2.1/
	Author:      Stefan Goessner/2006
	Web:         http://goessner.net/

	Modifications made:

	Version:     0.9-p5
	Description: Restructured code, JSLint validated (no strict whitespaces),
	             added handling of empty arrays, empty strings, and int/floats values.
	Author:      Michael Schøler/2008-01-29
	Web:         http://michael.hinnerup.net/blog/2008/01/26/converting-json-to-xml-and-xml-to-json/

	Description: json2xml added support to convert functions as CDATA
	             so it will be easy to write characters that cause some problems when convert
	Author:      Tony Tomov
*//*global alert */var xmlJsonClass={// Param "xml": Element or document DOM node.
// Param "tab": Tab or indent string for pretty output formatting omit or use empty string "" to supress.
// Returns:     JSON string
xml2json:function xml2json(xml,tab){if(xml.nodeType===9){// document node
xml=xml.documentElement;}var nws=this.removeWhite(xml);var obj=this.toObj(nws);var json=this.toJson(obj,xml.nodeName,'\t');return'{\n'+tab+(tab?json.replace(/\t/g,tab):json.replace(/\t|\n/g,''))+'\n}';},// Param "o":   JavaScript object
// Param "tab": tab or indent string for pretty output formatting omit or use empty string "" to supress.
// Returns:     XML string
json2xml:function json2xml(o,tab){var toXml=function toXml(v,name,ind){var xml='';var i,n;if(v instanceof Array){if(v.length===0){xml+=ind+'<'+name+'>__EMPTY_ARRAY_</'+name+'>\n';}else{for(i=0,n=v.length;i<n;i+=1){var sXml=ind+toXml(v[i],name,ind+'\t')+'\n';xml+=sXml;}}}else if((typeof v==="undefined"?"undefined":_typeof(v))==='object'){var hasChild=false;xml+=ind+'<'+name;var m;for(m in v){if(v.hasOwnProperty(m)){if(m.charAt(0)==='@'){xml+=' '+m.substr(1)+'="'+v[m].toString()+'"';}else{hasChild=true;}}}xml+=hasChild?'>':'/>';if(hasChild){for(m in v){if(v.hasOwnProperty(m)){if(m==='#text'){xml+=v[m];}else if(m==='#cdata'){xml+='<![CDATA['+v[m]+']]>';}else if(m.charAt(0)!=='@'){xml+=toXml(v[m],m,ind+'\t');}}}xml+=(xml.charAt(xml.length-1)==='\n'?ind:'')+'</'+name+'>';}}else if(typeof v==='function'){xml+=ind+'<'+name+'>'+'<![CDATA['+v+']]>'+'</'+name+'>';}else{if(v===undefined){v='';}if(v.toString()==='""'||v.toString().length===0){xml+=ind+'<'+name+'>__EMPTY_STRING_</'+name+'>';}else{xml+=ind+'<'+name+'>'+v.toString()+'</'+name+'>';}}return xml;};var xml='';var m;for(m in o){if(o.hasOwnProperty(m)){xml+=toXml(o[m],m,'');}}return tab?xml.replace(/\t/g,tab):xml.replace(/\t|\n/g,'');},// Internal methods
toObj:function toObj(xml){var o={};var FuncTest=/function/i;if(xml.nodeType===1){// element node ..
if(xml.attributes.length){// element with attributes ..
var i;for(i=0;i<xml.attributes.length;i+=1){o['@'+xml.attributes[i].nodeName]=(xml.attributes[i].nodeValue||'').toString();}}if(xml.firstChild){// element has child nodes ..
var textChild=0,cdataChild=0,hasElementChild=false;var n;for(n=xml.firstChild;n;n=n.nextSibling){if(n.nodeType===1){hasElementChild=true;}else if(n.nodeType===3&&n.nodeValue.match(/[^ \f\n\r\t\v]/)){// non-whitespace text
textChild+=1;}else if(n.nodeType===4){// cdata section node
cdataChild+=1;}}if(hasElementChild){if(textChild<2&&cdataChild<2){// structured element with evtl. a single text or/and cdata node ..
this.removeWhite(xml);for(n=xml.firstChild;n;n=n.nextSibling){if(n.nodeType===3){// text node
o['#text']=this.escape(n.nodeValue);}else if(n.nodeType===4){// cdata node
if(FuncTest.test(n.nodeValue)){o[n.nodeName]=[o[n.nodeName],n.nodeValue];}else{o['#cdata']=this.escape(n.nodeValue);}}else if(o[n.nodeName]){// multiple occurence of element ..
if(o[n.nodeName]instanceof Array){o[n.nodeName][o[n.nodeName].length]=this.toObj(n);}else{o[n.nodeName]=[o[n.nodeName],this.toObj(n)];}}else{// first occurence of element ..
o[n.nodeName]=this.toObj(n);}}}else{// mixed content
if(!xml.attributes.length){o=this.escape(this.innerXml(xml));}else{o['#text']=this.escape(this.innerXml(xml));}}}else if(textChild){// pure text
if(!xml.attributes.length){o=this.escape(this.innerXml(xml));if(o==='__EMPTY_ARRAY_'){o='[]';}else if(o==='__EMPTY_STRING_'){o='';}}else{o['#text']=this.escape(this.innerXml(xml));}}else if(cdataChild){// cdata
if(cdataChild>1){o=this.escape(this.innerXml(xml));}else{for(n=xml.firstChild;n;n=n.nextSibling){if(FuncTest.test(xml.firstChild.nodeValue)){o=xml.firstChild.nodeValue;break;}else{o['#cdata']=this.escape(n.nodeValue);}}}}}if(!xml.attributes.length&&!xml.firstChild){o=null;}}else if(xml.nodeType===9){// document.node
o=this.toObj(xml.documentElement);}else{alert('unhandled node type: '+xml.nodeType);}return o;},toJson:function toJson(o,name,ind,wellform){if(wellform===undefined)wellform=true;var json=name?'"'+name+'"':'',tab='\t',newline='\n';if(!wellform){tab='';newline='';}if(o==='[]'){json+=name?':[]':'[]';}else if(o instanceof Array){var n,i,ar=[];for(i=0,n=o.length;i<n;i+=1){ar[i]=this.toJson(o[i],'',ind+tab,wellform);}json+=(name?':[':'[')+(ar.length>1?newline+ind+tab+ar.join(','+newline+ind+tab)+newline+ind:ar.join(''))+']';}else if(o===null){json+=(name&&':')+'null';}else if((typeof o==="undefined"?"undefined":_typeof(o))==='object'){var arr=[],m;for(m in o){if(o.hasOwnProperty(m)){arr[arr.length]=this.toJson(o[m],m,ind+tab,wellform);}}json+=(name?':{':'{')+(arr.length>1?newline+ind+tab+arr.join(','+newline+ind+tab)+newline+ind:arr.join(''))+'}';}else if(typeof o==='string'){/*
			var objRegExp  = /(^-?\d+\.?\d*$)/;
			var FuncTest = /function/i;
			var os = o.toString();
			if (objRegExp.test(os) || FuncTest.test(os) || os==="false" || os==="true") {
				// int or float
				json += (name && ":")  + "\"" +os + "\"";
			}
			else {
			*/json+=(name&&':')+'"'+o.replace(/\\/g,'\\\\').replace(/\"/g,'\\"')+'"';//}
}else{json+=(name&&':')+o.toString();}return json;},innerXml:function innerXml(node){var s='';if('innerHTML'in node){s=node.innerHTML;}else{var asXml=function asXml(n){var s='',i;if(n.nodeType===1){s+='<'+n.nodeName;for(i=0;i<n.attributes.length;i+=1){s+=' '+n.attributes[i].nodeName+'="'+(n.attributes[i].nodeValue||'').toString()+'"';}if(n.firstChild){s+='>';for(var c=n.firstChild;c;c=c.nextSibling){s+=asXml(c);}s+='</'+n.nodeName+'>';}else{s+='/>';}}else if(n.nodeType===3){s+=n.nodeValue;}else if(n.nodeType===4){s+='<![CDATA['+n.nodeValue+']]>';}return s;};for(var c=node.firstChild;c;c=c.nextSibling){s+=asXml(c);}}return s;},escape:function escape(txt){return txt.replace(/[\\]/g,'\\\\').replace(/[\"]/g,'\\"').replace(/[\n]/g,'\\n').replace(/[\r]/g,'\\r');},removeWhite:function removeWhite(e){e.normalize();var n;for(n=e.firstChild;n;){if(n.nodeType===3){// text node
if(!n.nodeValue.match(/[^ \f\n\r\t\v]/)){// pure whitespace text node
var nxt=n.nextSibling;e.removeChild(n);n=nxt;}else{n=n.nextSibling;}}else if(n.nodeType===1){// element node
this.removeWhite(n);n=n.nextSibling;}else{// any other node
n=n.nextSibling;}}return e;}};/*
**
 * formatter for values but most of the values if for jqGrid
 * Some of this was inspired and based on how YUI does the table datagrid but in jQuery fashion
 * we are trying to keep it as light as possible
 * Joshua Burnett josh@9ci.com
 * http://www.greenbill.com
 *
 * Changes from Tony Tomov tony@trirand.com
 * Dual licensed under the MIT and GPL licenses:
 * http://www.opensource.org/licenses/mit-license.php
 * http://www.gnu.org/licenses/gpl-2.0.html
 *
**//*jshint eqeqeq:false *//*global jQuery */(function($){'use strict';$.fmatter={};//opts can be id:row id for the row, rowdata:the data for the row, colmodel:the column model for this column
//example {id:1234,}
$.extend($.fmatter,{isBoolean:function isBoolean(o){return typeof o==='boolean';},isObject:function isObject(o){return o&&((typeof o==="undefined"?"undefined":_typeof(o))==='object'||$.isFunction(o))||false;},isString:function isString(o){return typeof o==='string';},isNumber:function isNumber(o){return typeof o==='number'&&isFinite(o);},isNull:function isNull(o){return o===null;},isUndefined:function isUndefined(o){return o===undefined;},isValue:function isValue(o){return this.isObject(o)||this.isString(o)||this.isNumber(o)||this.isBoolean(o);},isEmpty:function isEmpty(o){if(!this.isString(o)&&this.isValue(o)){return false;}if(!this.isValue(o)){return true;}o=$.trim(o).replace(/\&nbsp\;/ig,'').replace(/\&#160\;/ig,'');return o==='';}});$.fn.fmatter=function(formatType,cellval,opts,rwd,act){// build main options before element iteration
var v=cellval;opts=$.extend({},$.jgrid.formatter,opts);try{v=$.fn.fmatter[formatType].call(this,cellval,opts,rwd,act);}catch(fe){}return v;};$.fmatter.util={// Taken from YAHOO utils
NumberFormat:function NumberFormat(nData,opts){if(!$.fmatter.isNumber(nData)){nData*=1;}if($.fmatter.isNumber(nData)){var bNegative=nData<0;var sOutput=String(nData);var sDecimalSeparator=opts.decimalSeparator||'.';var nDotIndex;if($.fmatter.isNumber(opts.decimalPlaces)){// Round to the correct decimal place
var nDecimalPlaces=opts.decimalPlaces;var nDecimal=Math.pow(10,nDecimalPlaces);sOutput=String(Math.round(nData*nDecimal)/nDecimal);nDotIndex=sOutput.lastIndexOf('.');if(nDecimalPlaces>0){// Add the decimal separator
if(nDotIndex<0){sOutput+=sDecimalSeparator;nDotIndex=sOutput.length-1;}// Replace the "."
else if(sDecimalSeparator!=='.'){sOutput=sOutput.replace('.',sDecimalSeparator);}// Add missing zeros
while(sOutput.length-1-nDotIndex<nDecimalPlaces){sOutput+='0';}}}if(opts.thousandsSeparator){var sThousandsSeparator=opts.thousandsSeparator;nDotIndex=sOutput.lastIndexOf(sDecimalSeparator);nDotIndex=nDotIndex>-1?nDotIndex:sOutput.length;var sNewOutput=sOutput.substring(nDotIndex);var nCount=-1,i;for(i=nDotIndex;i>0;i--){nCount++;if(nCount%3===0&&i!==nDotIndex&&(!bNegative||i>1)){sNewOutput=sThousandsSeparator+sNewOutput;}sNewOutput=sOutput.charAt(i-1)+sNewOutput;}sOutput=sNewOutput;}// Prepend prefix
sOutput=opts.prefix?opts.prefix+sOutput:sOutput;// Append suffix
sOutput=opts.suffix?sOutput+opts.suffix:sOutput;return sOutput;}return nData;},// Tony Tomov
// PHP implementation. Sorry not all options are supported.
// Feel free to add them if you want
DateFormat:function DateFormat(format,date,newformat,opts){var token=/\\.|[dDjlNSwzWFmMntLoYyaABgGhHisueIOPTZcrU]/g,timezone=/\b(?:[PMCEA][SDP]T|(?:Pacific|Mountain|Central|Eastern|Atlantic) (?:Standard|Daylight|Prevailing) Time|(?:GMT|UTC)(?:[-+]\d{4})?)\b/g,timezoneClip=/[^-+\dA-Z]/g,msDateRegExp=new RegExp('^\/Date\\((([-+])?[0-9]+)(([-+])([0-9]{2})([0-9]{2}))?\\)\/$'),msMatch=typeof date==='string'?date.match(msDateRegExp):null,pad=function pad(value,length){value=String(value);length=parseInt(length,10)||2;while(value.length<length){value='0'+value;}return value;},ts={m:1,d:1,y:1970,h:0,i:0,s:0,u:0},timestamp=0,dM,k,hl,dateFormat=['i18n'];// Internationalization strings
dateFormat.i18n={dayNames:opts.dayNames,monthNames:opts.monthNames};if(opts.masks.hasOwnProperty(format)){format=opts.masks[format];}if(!isNaN(date-0)&&String(format).toLowerCase()=='u'){//Unix timestamp
timestamp=new Date(parseFloat(date)*1000);}else if(date.constructor===Date){timestamp=date;// Microsoft date format support
}else if(msMatch!==null){timestamp=new Date(parseInt(msMatch[1],10));if(msMatch[3]){var offset=Number(msMatch[5])*60+Number(msMatch[6]);offset*=msMatch[4]=='-'?1:-1;offset-=timestamp.getTimezoneOffset();timestamp.setTime(Number(Number(timestamp)+offset*60*1000));}}else{date=String(date).split(/[\\\/:_;.,\t\T\s-]/);format=format.split(/[\\\/:_;.,\t\T\s-]/);// parsing for month names
for(k=0,hl=format.length;k<hl;k++){if(format[k]=='M'){dM=$.inArray(date[k],dateFormat.i18n.monthNames);if(dM!==-1&&dM<12){date[k]=dM+1;}}if(format[k]=='F'){dM=$.inArray(date[k],dateFormat.i18n.monthNames);if(dM!==-1&&dM>11){date[k]=dM+1-12;}}if(date[k]){ts[format[k].toLowerCase()]=parseInt(date[k],10);}}if(ts.f){ts.m=ts.f;}if(ts.m===0&&ts.y===0&&ts.d===0){return'&#160;';}ts.m=parseInt(ts.m,10)-1;var ty=ts.y;if(ty>=70&&ty<=99){ts.y=1900+ts.y;}else if(ty>=0&&ty<=69){ts.y=2000+ts.y;}timestamp=new Date(ts.y,ts.m,ts.d,ts.h,ts.i,ts.s,ts.u);}if(opts.masks.hasOwnProperty(newformat)){newformat=opts.masks[newformat];}else if(!newformat){newformat='Y-m-d';}var G=timestamp.getHours(),i=timestamp.getMinutes(),j=timestamp.getDate(),n=timestamp.getMonth()+1,o=timestamp.getTimezoneOffset(),s=timestamp.getSeconds(),u=timestamp.getMilliseconds(),w=timestamp.getDay(),Y=timestamp.getFullYear(),N=(w+6)%7+1,z=(new Date(Y,n-1,j)-new Date(Y,0,1))/86400000,flags={// Day
d:pad(j),D:dateFormat.i18n.dayNames[w],j:j,l:dateFormat.i18n.dayNames[w+7],N:N,S:opts.S(j),//j < 11 || j > 13 ? ['st', 'nd', 'rd', 'th'][Math.min((j - 1) % 10, 3)] : 'th',
w:w,z:z,// Week
W:N<5?Math.floor((z+N-1)/7)+1:Math.floor((z+N-1)/7)||((new Date(Y-1,0,1).getDay()+6)%7<4?53:52),// Month
F:dateFormat.i18n.monthNames[n-1+12],m:pad(n),M:dateFormat.i18n.monthNames[n-1],n:n,t:'?',// Year
L:'?',o:'?',Y:Y,y:String(Y).substring(2),// Time
a:G<12?opts.AmPm[0]:opts.AmPm[1],A:G<12?opts.AmPm[2]:opts.AmPm[3],B:'?',g:G%12||12,G:G,h:pad(G%12||12),H:pad(G),i:pad(i),s:pad(s),u:u,// Timezone
e:'?',I:'?',O:(o>0?'-':'+')+pad(Math.floor(Math.abs(o)/60)*100+Math.abs(o)%60,4),P:'?',T:(String(timestamp).match(timezone)||['']).pop().replace(timezoneClip,''),Z:'?',// Full Date/Time
c:'?',r:'?',U:Math.floor(timestamp/1000)};return newformat.replace(token,function($0){return flags.hasOwnProperty($0)?flags[$0]:$0.substring(1);});}};$.fn.fmatter.defaultFormat=function(cellval,opts){return $.fmatter.isValue(cellval)&&cellval!==''?cellval:opts.defaultValue||'&#160;';};$.fn.fmatter.email=function(cellval,opts){if(!$.fmatter.isEmpty(cellval)){return'<a href="mailto:'+cellval+'">'+cellval+'</a>';}return $.fn.fmatter.defaultFormat(cellval,opts);};$.fn.fmatter.checkbox=function(cval,opts){var op=$.extend({},opts.checkbox),ds;if(opts.colModel!==undefined&&!$.fmatter.isUndefined(opts.colModel.formatoptions)){op=$.extend({},op,opts.colModel.formatoptions);}if(op.disabled===true){ds='disabled="disabled"';}else{ds='';}if($.fmatter.isEmpty(cval)||$.fmatter.isUndefined(cval)){cval=$.fn.fmatter.defaultFormat(cval,op);}cval=String(cval);cval=cval.toLowerCase();var bchk=cval.search(/(false|0|no|n|off)/i)<0?' checked=\'checked\' ':'';return'<input type="checkbox" '+bchk+' value="'+cval+'" offval="no" '+ds+'/>';};$.fn.fmatter.link=function(cellval,opts){var op={target:opts.target};var target='';if(opts.colModel!==undefined&&!$.fmatter.isUndefined(opts.colModel.formatoptions)){op=$.extend({},op,opts.colModel.formatoptions);}if(op.target){target='target='+op.target;}if(!$.fmatter.isEmpty(cellval)){return'<a '+target+' href="'+cellval+'">'+cellval+'</a>';}return $.fn.fmatter.defaultFormat(cellval,opts);};$.fn.fmatter.showlink=function(cellval,opts){var op={baseLinkUrl:opts.baseLinkUrl,showAction:opts.showAction,addParam:opts.addParam||'',target:opts.target,idName:opts.idName},target='',idUrl;if(opts.colModel!==undefined&&!$.fmatter.isUndefined(opts.colModel.formatoptions)){op=$.extend({},op,opts.colModel.formatoptions);}if(op.target){target='target='+op.target;}idUrl=op.baseLinkUrl+op.showAction+'?'+op.idName+'='+opts.rowId+op.addParam;if($.fmatter.isString(cellval)||$.fmatter.isNumber(cellval)){//add this one even if its blank string
return'<a '+target+' href="'+idUrl+'">'+cellval+'</a>';}return $.fn.fmatter.defaultFormat(cellval,opts);};$.fn.fmatter.integer=function(cellval,opts){var op=$.extend({},opts.integer);if(opts.colModel!==undefined&&!$.fmatter.isUndefined(opts.colModel.formatoptions)){op=$.extend({},op,opts.colModel.formatoptions);}if($.fmatter.isEmpty(cellval)){return op.defaultValue;}return $.fmatter.util.NumberFormat(cellval,op);};$.fn.fmatter.number=function(cellval,opts){var op=$.extend({},opts.number);if(opts.colModel!==undefined&&!$.fmatter.isUndefined(opts.colModel.formatoptions)){op=$.extend({},op,opts.colModel.formatoptions);}if($.fmatter.isEmpty(cellval)){return op.defaultValue;}return $.fmatter.util.NumberFormat(cellval,op);};$.fn.fmatter.currency=function(cellval,opts){var op=$.extend({},opts.currency);if(opts.colModel!==undefined&&!$.fmatter.isUndefined(opts.colModel.formatoptions)){op=$.extend({},op,opts.colModel.formatoptions);}if($.fmatter.isEmpty(cellval)){return op.defaultValue;}return $.fmatter.util.NumberFormat(cellval,op);};$.fn.fmatter.date=function(cellval,opts,rwd,act){var op=$.extend({},opts.date);if(opts.colModel!==undefined&&!$.fmatter.isUndefined(opts.colModel.formatoptions)){op=$.extend({},op,opts.colModel.formatoptions);}if(!op.reformatAfterEdit&&act=='edit'){return $.fn.fmatter.defaultFormat(cellval,opts);}if(!$.fmatter.isEmpty(cellval)){return $.fmatter.util.DateFormat(op.srcformat,cellval,op.newformat,op);}return $.fn.fmatter.defaultFormat(cellval,opts);};$.fn.fmatter.select=function(cellval,opts){// jqGrid specific
cellval=String(cellval);var oSelect=false,ret=[],sep,delim;if(!$.fmatter.isUndefined(opts.colModel.formatoptions)){oSelect=opts.colModel.formatoptions.value;sep=opts.colModel.formatoptions.separator===undefined?':':opts.colModel.formatoptions.separator;delim=opts.colModel.formatoptions.delimiter===undefined?';':opts.colModel.formatoptions.delimiter;}else if(!$.fmatter.isUndefined(opts.colModel.editoptions)){oSelect=opts.colModel.editoptions.value;sep=opts.colModel.editoptions.separator===undefined?':':opts.colModel.editoptions.separator;delim=opts.colModel.editoptions.delimiter===undefined?';':opts.colModel.editoptions.delimiter;}if(oSelect){var msl=opts.colModel.editoptions.multiple===true?true:false,scell=[],sv;if(msl){scell=cellval.split(',');scell=$.map(scell,function(n){return $.trim(n);});}if($.fmatter.isString(oSelect)){// mybe here we can use some caching with care ????
var so=oSelect.split(delim),j=0,i;for(i=0;i<so.length;i++){sv=so[i].split(sep);if(sv.length>2){sv[1]=$.map(sv,function(n,i){if(i>0){return n;}}).join(sep);}if(msl){if($.inArray(sv[0],scell)>-1){ret[j]=sv[1];j++;}}else if($.trim(sv[0])==$.trim(cellval)){ret[0]=sv[1];break;}}}else if($.fmatter.isObject(oSelect)){// this is quicker
if(msl){ret=$.map(scell,function(n){return oSelect[n];});}else{ret[0]=oSelect[cellval]||'';}}}cellval=ret.join(', ');return cellval===''?$.fn.fmatter.defaultFormat(cellval,opts):cellval;};$.fn.fmatter.rowactions=function(act){var $tr=$(this).closest('tr.jqgrow'),$actionsDiv=$(this).parent(),rid=$tr.attr('id'),$grid=$(this).closest('table.ui-jqgrid-btable'),$t=$grid[0],p=$t.p,cm=p.colModel[$.jgrid.getCellIndex(this)],op={keys:false,onEdit:null,onSuccess:null,afterSave:null,onError:null,afterRestore:null,extraparam:{},url:null,restoreAfterError:true,mtype:'POST',delOptions:{},editOptions:{}},saverow=function saverow(rowid,res){if($.isFunction(op.afterSave)){op.afterSave.call($t,rowid,res);}$actionsDiv.find('div.ui-inline-edit,div.ui-inline-del').show();$actionsDiv.find('div.ui-inline-save,div.ui-inline-cancel').hide();},restorerow=function restorerow(rowid){if($.isFunction(op.afterRestore)){op.afterRestore.call($t,rowid);}$actionsDiv.find('div.ui-inline-edit,div.ui-inline-del').show();$actionsDiv.find('div.ui-inline-save,div.ui-inline-cancel').hide();};if(!$.fmatter.isUndefined(cm.formatoptions)){op=$.extend(op,cm.formatoptions);}if(!$.fmatter.isUndefined(p.editOptions)){op.editOptions=p.editOptions;}if(!$.fmatter.isUndefined(p.delOptions)){op.delOptions=p.delOptions;}if($tr.hasClass('jqgrid-new-row')){op.extraparam[p.prmNames.oper]=p.prmNames.addoper;}var actop={keys:op.keys,oneditfunc:op.onEdit,successfunc:op.onSuccess,url:op.url,extraparam:op.extraparam,aftersavefunc:saverow,errorfunc:op.onError,afterrestorefunc:restorerow,restoreAfterError:op.restoreAfterError,mtype:op.mtype};switch(act){case'edit':$grid.jqGrid('editRow',rid,actop);$actionsDiv.find('div.ui-inline-edit,div.ui-inline-del').hide();$actionsDiv.find('div.ui-inline-save,div.ui-inline-cancel').show();$grid.triggerHandler('jqGridAfterGridComplete');break;case'save':if($grid.jqGrid('saveRow',rid,actop)){$actionsDiv.find('div.ui-inline-edit,div.ui-inline-del').show();$actionsDiv.find('div.ui-inline-save,div.ui-inline-cancel').hide();$grid.triggerHandler('jqGridAfterGridComplete');}break;case'cancel':$grid.jqGrid('restoreRow',rid,restorerow);$actionsDiv.find('div.ui-inline-edit,div.ui-inline-del').show();$actionsDiv.find('div.ui-inline-save,div.ui-inline-cancel').hide();$grid.triggerHandler('jqGridAfterGridComplete');break;case'del':$grid.jqGrid('delGridRow',rid,op.delOptions);break;case'formedit':$grid.jqGrid('setSelection',rid);$grid.jqGrid('editGridRow',rid,op.editOptions);break;}};$.fn.fmatter.actions=function(cellval,opts){var op={keys:false,editbutton:true,delbutton:true,editformbutton:false},rowid=opts.rowId,str='',ocl;if(!$.fmatter.isUndefined(opts.colModel.formatoptions)){op=$.extend(op,opts.colModel.formatoptions);}if(rowid===undefined||$.fmatter.isEmpty(rowid)){return'';}if(op.editformbutton){ocl='onclick=jQuery.fn.fmatter.rowactions.call(this,\'formedit\'); onmouseover=jQuery(this).addClass(\'ui-state-hover\'); onmouseout=jQuery(this).removeClass(\'ui-state-hover\'); ';str+='<div title=\''+$.jgrid.nav.edittitle+'\' style=\'float:left;cursor:pointer;\' class=\'ui-pg-div ui-inline-edit\' '+ocl+'><span class=\'ui-icon ui-icon-pencil\'></span></div>';}else if(op.editbutton){ocl='onclick=jQuery.fn.fmatter.rowactions.call(this,\'edit\'); onmouseover=jQuery(this).addClass(\'ui-state-hover\'); onmouseout=jQuery(this).removeClass(\'ui-state-hover\') ';str+='<div title=\''+$.jgrid.nav.edittitle+'\' style=\'float:left;cursor:pointer;\' class=\'ui-pg-div ui-inline-edit\' '+ocl+'><span class=\'ui-icon ui-icon-pencil\'></span></div>';}if(op.delbutton){ocl='onclick=jQuery.fn.fmatter.rowactions.call(this,\'del\'); onmouseover=jQuery(this).addClass(\'ui-state-hover\'); onmouseout=jQuery(this).removeClass(\'ui-state-hover\'); ';str+='<div title=\''+$.jgrid.nav.deltitle+'\' style=\'float:left;margin-left:5px;\' class=\'ui-pg-div ui-inline-del\' '+ocl+'><span class=\'ui-icon ui-icon-trash\'></span></div>';}ocl='onclick=jQuery.fn.fmatter.rowactions.call(this,\'save\'); onmouseover=jQuery(this).addClass(\'ui-state-hover\'); onmouseout=jQuery(this).removeClass(\'ui-state-hover\'); ';str+='<div title=\''+$.jgrid.edit.bSubmit+'\' style=\'float:left;display:none\' class=\'ui-pg-div ui-inline-save\' '+ocl+'><span class=\'ui-icon ui-icon-disk\'></span></div>';ocl='onclick=jQuery.fn.fmatter.rowactions.call(this,\'cancel\'); onmouseover=jQuery(this).addClass(\'ui-state-hover\'); onmouseout=jQuery(this).removeClass(\'ui-state-hover\'); ';str+='<div title=\''+$.jgrid.edit.bCancel+'\' style=\'float:left;display:none;margin-left:5px;\' class=\'ui-pg-div ui-inline-cancel\' '+ocl+'><span class=\'ui-icon ui-icon-cancel\'></span></div>';return'<div style=\'margin-left:8px;\'>'+str+'</div>';};$.unformat=function(cellval,options,pos,cnt){// specific for jqGrid only
var ret,formatType=options.colModel.formatter,op=options.colModel.formatoptions||{},sep,re=/([\.\*\_\'\(\)\{\}\+\?\\])/g,unformatFunc=options.colModel.unformat||$.fn.fmatter[formatType]&&$.fn.fmatter[formatType].unformat;if(unformatFunc!==undefined&&$.isFunction(unformatFunc)){ret=unformatFunc.call(this,$(cellval).text(),options,cellval);}else if(!$.fmatter.isUndefined(formatType)&&$.fmatter.isString(formatType)){var opts=$.jgrid.formatter||{},stripTag;switch(formatType){case'integer':op=$.extend({},opts.integer,op);sep=op.thousandsSeparator.replace(re,'\\$1');stripTag=new RegExp(sep,'g');ret=$(cellval).text().replace(stripTag,'');break;case'number':op=$.extend({},opts.number,op);sep=op.thousandsSeparator.replace(re,'\\$1');stripTag=new RegExp(sep,'g');ret=$(cellval).text().replace(stripTag,'').replace(op.decimalSeparator,'.');break;case'currency':op=$.extend({},opts.currency,op);sep=op.thousandsSeparator.replace(re,'\\$1');stripTag=new RegExp(sep,'g');ret=$(cellval).text();if(op.prefix&&op.prefix.length){ret=ret.substr(op.prefix.length);}if(op.suffix&&op.suffix.length){ret=ret.substr(0,ret.length-op.suffix.length);}ret=ret.replace(stripTag,'').replace(op.decimalSeparator,'.');break;case'checkbox':var cbv=options.colModel.editoptions?options.colModel.editoptions.value.split(':'):['Yes','No'];ret=$('input',cellval).is(':checked')?cbv[0]:cbv[1];break;case'select':ret=$.unformat.select(cellval,options,pos,cnt);break;case'actions':return'';default:ret=$(cellval).text();}}return ret!==undefined?ret:cnt===true?$(cellval).text():$.jgrid.htmlDecode($(cellval).html());};$.unformat.select=function(cellval,options,pos,cnt){// Spacial case when we have local data and perform a sort
// cnt is set to true only in sortDataArray
var ret=[];var cell=$(cellval).text();if(cnt===true){return cell;}var op=$.extend({},!$.fmatter.isUndefined(options.colModel.formatoptions)?options.colModel.formatoptions:options.colModel.editoptions),sep=op.separator===undefined?':':op.separator,delim=op.delimiter===undefined?';':op.delimiter;if(op.value){var oSelect=op.value,msl=op.multiple===true?true:false,scell=[],sv;if(msl){scell=cell.split(',');scell=$.map(scell,function(n){return $.trim(n);});}if($.fmatter.isString(oSelect)){var so=oSelect.split(delim),j=0,i;for(i=0;i<so.length;i++){sv=so[i].split(sep);if(sv.length>2){sv[1]=$.map(sv,function(n,i){if(i>0){return n;}}).join(sep);}if(msl){if($.inArray(sv[1],scell)>-1){ret[j]=sv[0];j++;}}else if($.trim(sv[1])==$.trim(cell)){ret[0]=sv[0];break;}}}else if($.fmatter.isObject(oSelect)||$.isArray(oSelect)){if(!msl){scell[0]=cell;}ret=$.map(scell,function(n){var rv;$.each(oSelect,function(i,val){if(val==n){rv=i;return false;}});if(rv!==undefined){return rv;}});}return ret.join(', ');}return cell||'';};$.unformat.date=function(cellval,opts){var op=$.jgrid.formatter.date||{};if(!$.fmatter.isUndefined(opts.formatoptions)){op=$.extend({},op,opts.formatoptions);}if(!$.fmatter.isEmpty(cellval)){return $.fmatter.util.DateFormat(op.newformat,cellval,op.srcformat,op);}return $.fn.fmatter.defaultFormat(cellval,opts);};})(jQuery);/*jshint eqeqeq:false *//*global jQuery */(function($){/*
 * jqGrid common function
 * Tony Tomov tony@trirand.com
 * http://trirand.com/blog/
 * Dual licensed under the MIT and GPL licenses:
 * http://www.opensource.org/licenses/mit-license.php
 * http://www.gnu.org/licenses/gpl-2.0.html
*/'use strict';$.extend($.jgrid,{// Modal functions
showModal:function showModal(h){h.w.show();},closeModal:function closeModal(h){h.w.hide().attr('aria-hidden','true');if(h.o){h.o.remove();}},hideModal:function hideModal(selector,o){o=$.extend({jqm:true,gb:''},o||{});if(o.onClose){var oncret=o.gb&&typeof o.gb==='string'&&o.gb.substr(0,6)==='#gbox_'?o.onClose.call($('#'+o.gb.substr(6))[0],selector):o.onClose(selector);if(typeof oncret==='boolean'&&!oncret){return;}}if($.fn.jqm&&o.jqm===true){$(selector).attr('aria-hidden','true').jqmHide();}else{if(o.gb!==''){try{$('.jqgrid-overlay:first',o.gb).hide();}catch(e){}}$(selector).hide().attr('aria-hidden','true');}},//Helper functions
findPos:function findPos(obj){var curleft=0,curtop=0;if(obj.offsetParent){do{curleft+=obj.offsetLeft;curtop+=obj.offsetTop;}while(obj=obj.offsetParent);//do not change obj == obj.offsetParent
}return[curleft,curtop];},createModal:function createModal(aIDs,content,p,insertSelector,posSelector,appendsel,css){p=$.extend(true,{},$.jgrid.jqModal||{},p);var mw=document.createElement('div'),rtlsup,self=this;css=$.extend({},css||{});rtlsup=$(p.gbox).attr('dir')=='rtl'?true:false;mw.className='ui-widget ui-widget-content ui-corner-all ui-jqdialog';mw.id=aIDs.themodal;var mh=document.createElement('div');mh.className='ui-jqdialog-titlebar ui-widget-header ui-corner-all ui-helper-clearfix';mh.id=aIDs.modalhead;$(mh).append('<span class=\'ui-jqdialog-title\'>'+p.caption+'</span>');var ahr=$('<a href=\'javascript:void(0)\' class=\'ui-jqdialog-titlebar-close ui-corner-all\'></a>').hover(function(){ahr.addClass('ui-state-hover');},function(){ahr.removeClass('ui-state-hover');}).append('<span class=\'ui-icon ui-icon-closethick\'></span>');$(mh).append(ahr);if(rtlsup){mw.dir='rtl';$('.ui-jqdialog-title',mh).css('float','right');$('.ui-jqdialog-titlebar-close',mh).css('left',0.3+'em');}else{mw.dir='ltr';$('.ui-jqdialog-title',mh).css('float','left');$('.ui-jqdialog-titlebar-close',mh).css('right',0.3+'em');}var mc=document.createElement('div');$(mc).addClass('ui-jqdialog-content ui-widget-content').attr('id',aIDs.modalcontent);$(mc).append(content);mw.appendChild(mc);$(mw).prepend(mh);if(appendsel===true){$('body').append(mw);}//append as first child in body -for alert dialog
else if(typeof appendsel==='string'){$(appendsel).append(mw);}else{$(mw).insertBefore(insertSelector);}$(mw).css(css);if(p.jqModal===undefined){p.jqModal=true;}// internal use
var coord={};if($.fn.jqm&&p.jqModal===true){if(p.left===0&&p.top===0&&p.overlay){var pos=[];pos=$.jgrid.findPos(posSelector);p.left=pos[0]+4;p.top=pos[1]+4;}coord.top=p.top+'px';coord.left=p.left;}else if(p.left!==0||p.top!==0){coord.left=p.left;coord.top=p.top+'px';}$('a.ui-jqdialog-titlebar-close',mh).click(function(){var oncm=$('#'+$.jgrid.jqID(aIDs.themodal)).data('onClose')||p.onClose;var gboxclose=$('#'+$.jgrid.jqID(aIDs.themodal)).data('gbox')||p.gbox;self.hideModal('#'+$.jgrid.jqID(aIDs.themodal),{gb:gboxclose,jqm:p.jqModal,onClose:oncm});return false;});if(p.width===0||!p.width){p.width=300;}if(p.height===0||!p.height){p.height=200;}if(!p.zIndex){var parentZ=$(insertSelector).parents('*[role=dialog]').filter(':first').css('z-index');if(parentZ){p.zIndex=parseInt(parentZ,10)+2;}else{p.zIndex=950;}}var rtlt=0;if(rtlsup&&coord.left&&!appendsel){rtlt=$(p.gbox).width()-(!isNaN(p.width)?parseInt(p.width,10):0)-8;// to do
// just in case
coord.left=parseInt(coord.left,10)+parseInt(rtlt,10);}if(coord.left){coord.left+='px';}$(mw).css($.extend({width:isNaN(p.width)?'auto':p.width+'px',height:isNaN(p.height)?'auto':p.height+'px',zIndex:p.zIndex,overflow:'hidden'},coord)).attr({tabIndex:'-1','role':'dialog','aria-labelledby':aIDs.modalhead,'aria-hidden':'true'});if(p.drag===undefined){p.drag=true;}if(p.resize===undefined){p.resize=true;}if(p.drag){$(mh).css('cursor','move');if($.fn.jqDrag){$(mw).jqDrag(mh);}else{try{$(mw).draggable({handle:$('#'+$.jgrid.jqID(mh.id))});}catch(e){}}}if(p.resize){if($.fn.jqResize){$(mw).append('<div class=\'jqResize ui-resizable-handle ui-resizable-se ui-icon ui-icon-gripsmall-diagonal-se\'></div>');$('#'+$.jgrid.jqID(aIDs.themodal)).jqResize('.jqResize',aIDs.scrollelm?'#'+$.jgrid.jqID(aIDs.scrollelm):false);}else{try{$(mw).resizable({handles:'se, sw',alsoResize:aIDs.scrollelm?'#'+$.jgrid.jqID(aIDs.scrollelm):false});}catch(r){}}}if(p.closeOnEscape===true){$(mw).keydown(function(e){if(e.which==27){var cone=$('#'+$.jgrid.jqID(aIDs.themodal)).data('onClose')||p.onClose;self.hideModal('#'+$.jgrid.jqID(aIDs.themodal),{gb:p.gbox,jqm:p.jqModal,onClose:cone});}});}},viewModal:function viewModal(selector,o){o=$.extend({toTop:true,overlay:10,modal:false,overlayClass:'ui-widget-overlay',onShow:$.jgrid.showModal,onHide:$.jgrid.closeModal,gbox:'',jqm:true,jqM:true},o||{});if($.fn.jqm&&o.jqm===true){if(o.jqM){$(selector).attr('aria-hidden','false').jqm(o).jqmShow();}else{$(selector).attr('aria-hidden','false').jqmShow();}}else{if(o.gbox!==''){$('.jqgrid-overlay:first',o.gbox).show();$(selector).data('gbox',o.gbox);}$(selector).show().attr('aria-hidden','false');try{$(':input:visible',selector)[0].focus();}catch(_){}}},info_dialog:function info_dialog(caption,content,c_b,modalopt){var mopt={width:290,height:'auto',dataheight:'auto',drag:true,resize:false,left:250,top:170,zIndex:1000,jqModal:true,modal:false,closeOnEscape:true,align:'center',buttonalign:'center',buttons:[]// {text:'textbutt', id:"buttid", onClick : function(){...}}
// if the id is not provided we set it like info_button_+ the index in the array - i.e info_button_0,info_button_1...
};$.extend(true,mopt,$.jgrid.jqModal||{},{caption:'<b>'+caption+'</b>'},modalopt||{});var jm=mopt.jqModal,self=this;if($.fn.jqm&&!jm){jm=false;}// in case there is no jqModal
var buttstr='',i;if(mopt.buttons.length>0){for(i=0;i<mopt.buttons.length;i++){if(mopt.buttons[i].id===undefined){mopt.buttons[i].id='info_button_'+i;}buttstr+='<a href=\'javascript:void(0)\' id=\''+mopt.buttons[i].id+'\' class=\'fm-button ui-state-default ui-corner-all\'>'+mopt.buttons[i].text+'</a>';}}var dh=isNaN(mopt.dataheight)?mopt.dataheight:mopt.dataheight+'px',cn='text-align:'+mopt.align+';';var cnt='<div id=\'info_id\'>';cnt+='<div id=\'infocnt\' style=\'margin:0px;padding-bottom:1em;width:100%;overflow:auto;position:relative;height:'+dh+';'+cn+'\'>'+content+'</div>';cnt+=c_b?'<div class=\'ui-widget-content ui-helper-clearfix\' style=\'text-align:'+mopt.buttonalign+';padding-bottom:0.8em;padding-top:0.5em;background-image: none;border-width: 1px 0 0 0;\'><a href=\'javascript:void(0)\' id=\'closedialog\' class=\'fm-button ui-state-default ui-corner-all\'>'+c_b+'</a>'+buttstr+'</div>':buttstr!==''?'<div class=\'ui-widget-content ui-helper-clearfix\' style=\'text-align:'+mopt.buttonalign+';padding-bottom:0.8em;padding-top:0.5em;background-image: none;border-width: 1px 0 0 0;\'>'+buttstr+'</div>':'';cnt+='</div>';try{if($('#info_dialog').attr('aria-hidden')=='false'){$.jgrid.hideModal('#info_dialog',{jqm:jm});}$('#info_dialog').remove();}catch(e){}$.jgrid.createModal({themodal:'info_dialog',modalhead:'info_head',modalcontent:'info_content',scrollelm:'infocnt'},cnt,mopt,'','',true);// attach onclick after inserting into the dom
if(buttstr){$.each(mopt.buttons,function(i){$('#'+$.jgrid.jqID(this.id),'#info_id').bind('click',function(){mopt.buttons[i].onClick.call($('#info_dialog'));return false;});});}$('#closedialog','#info_id').click(function(){self.hideModal('#info_dialog',{jqm:jm});return false;});$('.fm-button','#info_dialog').hover(function(){$(this).addClass('ui-state-hover');},function(){$(this).removeClass('ui-state-hover');});if($.isFunction(mopt.beforeOpen)){mopt.beforeOpen();}$.jgrid.viewModal('#info_dialog',{onHide:function onHide(h){h.w.hide().remove();if(h.o){h.o.remove();}},modal:mopt.modal,jqm:jm});if($.isFunction(mopt.afterOpen)){mopt.afterOpen();}try{$('#info_dialog').focus();}catch(m){}},bindEv:function bindEv(el,opt,$t){if($.isFunction(opt.dataInit)){opt.dataInit.call($t,el);}if(opt.dataEvents){$.each(opt.dataEvents,function(){if(this.data!==undefined){$(el).bind(this.type,this.data,this.fn);}else{$(el).bind(this.type,this.fn);}});}},// Form Functions
createEl:function createEl(eltype,options,vl,autowidth,ajaxso){var elem='',$t=this;function setAttributes(elm,atr,exl){var exclude=['dataInit','dataEvents','dataUrl','buildSelect','sopt','searchhidden','defaultValue','attr','custom_element','custom_value'];if(exl!==undefined&&$.isArray(exl)){$.merge(exclude,exl);}$.each(atr,function(key,value){if($.inArray(key,exclude)===-1){$(elm).attr(key,value);}});if(!atr.hasOwnProperty('id')){$(elm).attr('id',$.jgrid.randId());}}switch(eltype){case'textarea':elem=document.createElement('textarea');if(autowidth){if(!options.cols){$(elem).css({width:'98%'});}}else if(!options.cols){options.cols=20;}if(!options.rows){options.rows=2;}if(vl=='&nbsp;'||vl=='&#160;'||vl.length==1&&vl.charCodeAt(0)==160){vl='';}elem.value=vl;setAttributes(elem,options);$(elem).attr({'role':'textbox','multiline':'true'});break;case'checkbox'://what code for simple checkbox
elem=document.createElement('input');elem.type='checkbox';if(!options.value){var vl1=vl.toLowerCase();if(vl1.search(/(false|0|no|off|undefined)/i)<0&&vl1!==''){elem.checked=true;elem.defaultChecked=true;elem.value=vl;}else{elem.value='on';}$(elem).attr('offval','off');}else{var cbval=options.value.split(':');if(vl===cbval[0]){elem.checked=true;elem.defaultChecked=true;}elem.value=cbval[0];$(elem).attr('offval',cbval[1]);}setAttributes(elem,options,['value']);$(elem).attr('role','checkbox');break;case'select':elem=document.createElement('select');elem.setAttribute('role','select');var msl,ovm=[];if(options.multiple===true){msl=true;elem.multiple='multiple';$(elem).attr('aria-multiselectable','true');}else{msl=false;}if(options.dataUrl!==undefined){var rowid=options.name?String(options.id).substring(0,String(options.id).length-String(options.name).length-1):String(options.id),postData=options.postData||ajaxso.postData;if($t.p&&$t.p.idPrefix){rowid=$.jgrid.stripPref($t.p.idPrefix,rowid);}else{postData=undefined;// don't use postData for searching from jqFilter. One can implement the feature in the future if required.
}$.ajax($.extend({url:options.dataUrl,type:'GET',dataType:'html',data:$.isFunction(postData)?postData.call($t,rowid,vl,String(options.name)):postData,context:{elem:elem,options:options,vl:vl},success:function success(data){var a,ovm=[],elem=this.elem,vl=this.vl,options=$.extend({},this.options),msl=options.multiple===true;if($.isFunction(options.buildSelect)){var b=options.buildSelect.call($t,data);a=$(b).html();}else{a=$(data).html();}if(a){$(elem).append(a);setAttributes(elem,options);if(options.size===undefined){options.size=msl?3:1;}if(msl){ovm=vl.split(',');ovm=$.map(ovm,function(n){return $.trim(n);});}else{ovm[0]=$.trim(vl);}//$(elem).attr(options);
setTimeout(function(){$('option',elem).each(function(i){//if(i===0) { this.selected = ""; }
// fix IE8/IE7 problem with selecting of the first item on multiple=true
if(i===0&&elem.multiple){this.selected=false;}$(this).attr('role','option');if($.inArray($.trim($(this).text()),ovm)>-1||$.inArray($.trim($(this).val()),ovm)>-1){this.selected='selected';}});},0);}}},ajaxso||{}));}else if(options.value){var i;if(options.size===undefined){options.size=msl?3:1;}if(msl){ovm=vl.split(',');ovm=$.map(ovm,function(n){return $.trim(n);});}if(typeof options.value==='function'){options.value=options.value();}var so,sv,ov,sep=options.separator===undefined?':':options.separator,delim=options.delimiter===undefined?';':options.delimiter;if(typeof options.value==='string'){so=options.value.split(delim);for(i=0;i<so.length;i++){sv=so[i].split(sep);if(sv.length>2){sv[1]=$.map(sv,function(n,ii){if(ii>0){return n;}}).join(sep);}ov=document.createElement('option');ov.setAttribute('role','option');ov.value=sv[0];ov.innerHTML=sv[1];elem.appendChild(ov);if(!msl&&($.trim(sv[0])==$.trim(vl)||$.trim(sv[1])==$.trim(vl))){ov.selected='selected';}if(msl&&($.inArray($.trim(sv[1]),ovm)>-1||$.inArray($.trim(sv[0]),ovm)>-1)){ov.selected='selected';}}}else if(_typeof(options.value)==='object'){var oSv=options.value,key;for(key in oSv){if(oSv.hasOwnProperty(key)){ov=document.createElement('option');ov.setAttribute('role','option');ov.value=key;ov.innerHTML=oSv[key];elem.appendChild(ov);if(!msl&&($.trim(key)==$.trim(vl)||$.trim(oSv[key])==$.trim(vl))){ov.selected='selected';}if(msl&&($.inArray($.trim(oSv[key]),ovm)>-1||$.inArray($.trim(key),ovm)>-1)){ov.selected='selected';}}}}setAttributes(elem,options,['value']);}break;case'text':case'password':case'button':var role;if(eltype=='button'){role='button';}else{role='textbox';}elem=document.createElement('input');elem.type=eltype;elem.value=vl;setAttributes(elem,options);if(eltype!='button'){if(autowidth){if(!options.size){$(elem).css({width:'98%'});}}else if(!options.size){options.size=20;}}$(elem).attr('role',role);break;case'image':case'file':elem=document.createElement('input');elem.type=eltype;setAttributes(elem,options);break;case'custom':elem=document.createElement('span');try{if($.isFunction(options.custom_element)){var celm=options.custom_element.call($t,vl,options);if(celm){celm=$(celm).addClass('customelement').attr({id:options.id,name:options.name});$(elem).empty().append(celm);}else{throw'e2';}}else{throw'e1';}}catch(e){if(e=='e1'){$.jgrid.info_dialog($.jgrid.errors.errcap,'function \'custom_element\' '+$.jgrid.edit.msg.nodefined,$.jgrid.edit.bClose);}if(e=='e2'){$.jgrid.info_dialog($.jgrid.errors.errcap,'function \'custom_element\' '+$.jgrid.edit.msg.novalue,$.jgrid.edit.bClose);}else{$.jgrid.info_dialog($.jgrid.errors.errcap,typeof e==='string'?e:e.message,$.jgrid.edit.bClose);}}break;}return elem;},// Date Validation Javascript
checkDate:function checkDate(format,date){var daysInFebruary=function daysInFebruary(year){// February has 29 days in any year evenly divisible by four,
// EXCEPT for centurial years which are not also divisible by 400.
return year%4===0&&(year%100!==0||year%400===0)?29:28;},daysArray=function daysArray(n){var i;for(i=1;i<=n;i++){this[i]=31;if(i==4||i==6||i==9||i==11){this[i]=30;}if(i==2){this[i]=29;}}return this;};var tsp={},sep;format=format.toLowerCase();//we search for /,-,. for the date separator
if(format.indexOf('/')!=-1){sep='/';}else if(format.indexOf('-')!=-1){sep='-';}else if(format.indexOf('.')!=-1){sep='.';}else{sep='/';}format=format.split(sep);date=date.split(sep);if(date.length!=3){return false;}var j=-1,yln,dln=-1,mln=-1,i;for(i=0;i<format.length;i++){var dv=isNaN(date[i])?0:parseInt(date[i],10);tsp[format[i]]=dv;yln=format[i];if(yln.indexOf('y')!=-1){j=i;}if(yln.indexOf('m')!=-1){mln=i;}if(yln.indexOf('d')!=-1){dln=i;}}if(format[j]=='y'||format[j]=='yyyy'){yln=4;}else if(format[j]=='yy'){yln=2;}else{yln=-1;}var daysInMonth=daysArray(12),strDate;if(j===-1){return false;}strDate=tsp[format[j]].toString();if(yln==2&&strDate.length==1){yln=1;}if(strDate.length!=yln||tsp[format[j]]===0&&date[j]!='00'){return false;}if(mln===-1){return false;}strDate=tsp[format[mln]].toString();if(strDate.length<1||tsp[format[mln]]<1||tsp[format[mln]]>12){return false;}if(dln===-1){return false;}strDate=tsp[format[dln]].toString();if(strDate.length<1||tsp[format[dln]]<1||tsp[format[dln]]>31||tsp[format[mln]]==2&&tsp[format[dln]]>daysInFebruary(tsp[format[j]])||tsp[format[dln]]>daysInMonth[tsp[format[mln]]]){return false;}return true;},isEmpty:function isEmpty(val){if(val.match(/^\s+$/)||val===''){return true;}return false;},checkTime:function checkTime(time){// checks only hh:ss (and optional am/pm)
var re=/^(\d{1,2}):(\d{2})([ap]m)?$/,regs;if(!$.jgrid.isEmpty(time)){regs=time.match(re);if(regs){if(regs[3]){if(regs[1]<1||regs[1]>12){return false;}}else{if(regs[1]>23){return false;}}if(regs[2]>59){return false;}}else{return false;}}return true;},checkValues:function checkValues(val,valref,g,customobject,nam){var edtrul,i,nm,dft,len;if(customobject===undefined){if(typeof valref==='string'){for(i=0,len=g.p.colModel.length;i<len;i++){if(g.p.colModel[i].name==valref){edtrul=g.p.colModel[i].editrules;valref=i;try{nm=g.p.colModel[i].formoptions.label;}catch(e){}break;}}}else if(valref>=0){edtrul=g.p.colModel[valref].editrules;}}else{edtrul=customobject;nm=nam===undefined?'_':nam;}if(edtrul){if(!nm){nm=g.p.colNames[valref];}if(edtrul.required===true){if($.jgrid.isEmpty(val)){return[false,nm+': '+$.jgrid.edit.msg.required,''];}}// force required
var rqfield=edtrul.required===false?false:true;if(edtrul.number===true){if(!(rqfield===false&&$.jgrid.isEmpty(val))){if(isNaN(val)){return[false,nm+': '+$.jgrid.edit.msg.number,''];}}}if(edtrul.minValue!==undefined&&!isNaN(edtrul.minValue)){if(parseFloat(val)<parseFloat(edtrul.minValue)){return[false,nm+': '+$.jgrid.edit.msg.minValue+' '+edtrul.minValue,''];}}if(edtrul.maxValue!==undefined&&!isNaN(edtrul.maxValue)){if(parseFloat(val)>parseFloat(edtrul.maxValue)){return[false,nm+': '+$.jgrid.edit.msg.maxValue+' '+edtrul.maxValue,''];}}var filter;if(edtrul.email===true){if(!(rqfield===false&&$.jgrid.isEmpty(val))){// taken from $ Validate plugin
filter=/^((([a-z]|\d|[!#\$%&'\*\+\-\/=\?\^_`{\|}~]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])+(\.([a-z]|\d|[!#\$%&'\*\+\-\/=\?\^_`{\|}~]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])+)*)|((\x22)((((\x20|\x09)*(\x0d\x0a))?(\x20|\x09)+)?(([\x01-\x08\x0b\x0c\x0e-\x1f\x7f]|\x21|[\x23-\x5b]|[\x5d-\x7e]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(\\([\x01-\x09\x0b\x0c\x0d-\x7f]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF]))))*(((\x20|\x09)*(\x0d\x0a))?(\x20|\x09)+)?(\x22)))@((([a-z]|\d|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(([a-z]|\d|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])*([a-z]|\d|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])))\.)+(([a-z]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(([a-z]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])*([a-z]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])))\.?$/i;if(!filter.test(val)){return[false,nm+': '+$.jgrid.edit.msg.email,''];}}}if(edtrul.integer===true){if(!(rqfield===false&&$.jgrid.isEmpty(val))){if(isNaN(val)){return[false,nm+': '+$.jgrid.edit.msg.integer,''];}if(val%1!==0||val.indexOf('.')!=-1){return[false,nm+': '+$.jgrid.edit.msg.integer,''];}}}if(edtrul.date===true){if(!(rqfield===false&&$.jgrid.isEmpty(val))){if(g.p.colModel[valref].formatoptions&&g.p.colModel[valref].formatoptions.newformat){dft=g.p.colModel[valref].formatoptions.newformat;}else{dft=g.p.colModel[valref].datefmt||'Y-m-d';}if(!$.jgrid.checkDate(dft,val)){return[false,nm+': '+$.jgrid.edit.msg.date+' - '+dft,''];}}}if(edtrul.time===true){if(!(rqfield===false&&$.jgrid.isEmpty(val))){if(!$.jgrid.checkTime(val)){return[false,nm+': '+$.jgrid.edit.msg.date+' - hh:mm (am/pm)',''];}}}if(edtrul.url===true){if(!(rqfield===false&&$.jgrid.isEmpty(val))){filter=/^(((https?)|(ftp)):\/\/([\-\w]+\.)+\w{2,3}(\/[%\-\w]+(\.\w{2,})?)*(([\w\-\.\?\\\/+@&#;`~=%!]*)(\.\w{2,})?)*\/?)/i;if(!filter.test(val)){return[false,nm+': '+$.jgrid.edit.msg.url,''];}}}if(edtrul.custom===true){if(!(rqfield===false&&$.jgrid.isEmpty(val))){if($.isFunction(edtrul.custom_func)){var ret=edtrul.custom_func.call(g,val,nm);return $.isArray(ret)?ret:[false,$.jgrid.edit.msg.customarray,''];}return[false,$.jgrid.edit.msg.customfcheck,''];}}}return[true,'',''];}});})(jQuery);/*
 * jqFilter  jQuery jqGrid filter addon.
 * Copyright (c) 2011, Tony Tomov, tony@trirand.com
 * Dual licensed under the MIT and GPL licenses
 * http://www.opensource.org/licenses/mit-license.php
 * http://www.gnu.org/licenses/gpl-2.0.html
 *
 * The work is inspired from this Stefan Pirvu
 * http://www.codeproject.com/KB/scripting/json-filtering.aspx
 *
 * The filter uses JSON entities to hold filter rules and groups. Here is an example of a filter:

{ "groupOp": "AND",
      "groups" : [
        { "groupOp": "OR",
            "rules": [
                { "field": "name", "op": "eq", "data": "England" },
                { "field": "id", "op": "le", "data": "5"}
             ]
        }
      ],
      "rules": [
        { "field": "name", "op": "eq", "data": "Romania" },
        { "field": "id", "op": "le", "data": "1"}
      ]
}
*//*jshint eqeqeq:false, eqnull:true, devel:true *//*global jQuery */(function($){'use strict';$.fn.jqFilter=function(arg){if(typeof arg==='string'){var fn=$.fn.jqFilter[arg];if(!fn){throw'jqFilter - No such method: '+arg;}var args=$.makeArray(arguments).slice(1);return fn.apply(this,args);}var p=$.extend(true,{filter:null,columns:[],onChange:null,afterRedraw:null,checkValues:null,error:false,errmsg:'',errorcheck:true,showQuery:true,sopt:null,ops:[{'name':'eq','description':'equal','operator':'='},{'name':'ne','description':'not equal','operator':'<>'},{'name':'lt','description':'less','operator':'<'},{'name':'le','description':'less or equal','operator':'<='},{'name':'gt','description':'greater','operator':'>'},{'name':'ge','description':'greater or equal','operator':'>='},{'name':'bw','description':'begins with','operator':'LIKE'},{'name':'bn','description':'does not begin with','operator':'NOT LIKE'},{'name':'in','description':'in','operator':'IN'},{'name':'ni','description':'not in','operator':'NOT IN'},{'name':'ew','description':'ends with','operator':'LIKE'},{'name':'en','description':'does not end with','operator':'NOT LIKE'},{'name':'cn','description':'contains','operator':'LIKE'},{'name':'nc','description':'does not contain','operator':'NOT LIKE'},{'name':'nu','description':'is null','operator':'IS NULL'},{'name':'nn','description':'is not null','operator':'IS NOT NULL'}],numopts:['eq','ne','lt','le','gt','ge','nu','nn','in','ni'],stropts:['eq','ne','bw','bn','ew','en','cn','nc','nu','nn','in','ni'],strarr:['text','string','blob'],_gridsopt:[],// grid translated strings, do not tuch
groupOps:[{op:'AND',text:'AND'},{op:'OR',text:'OR'}],groupButton:true,ruleButtons:true,direction:'ltr'},$.jgrid.filter,arg||{});return this.each(function(){if(this.filter){return;}this.p=p;// setup filter in case if they is not defined
if(this.p.filter===null||this.p.filter===undefined){this.p.filter={groupOp:this.p.groupOps[0].op,rules:[],groups:[]};}var i,len=this.p.columns.length,cl,isIE=/msie/i.test(navigator.userAgent)&&!window.opera;// translating the options
if(this.p._gridsopt.length){// ['eq','ne','lt','le','gt','ge','bw','bn','in','ni','ew','en','cn','nc']
for(i=0;i<this.p._gridsopt.length;i++){this.p.ops[i].description=this.p._gridsopt[i];}}this.p.initFilter=$.extend(true,{},this.p.filter);// set default values for the columns if they are not set
if(!len){return;}for(i=0;i<len;i++){cl=this.p.columns[i];if(cl.stype){// grid compatibility
cl.inputtype=cl.stype;}else if(!cl.inputtype){cl.inputtype='text';}if(cl.sorttype){// grid compatibility
cl.searchtype=cl.sorttype;}else if(!cl.searchtype){cl.searchtype='string';}if(cl.hidden===undefined){// jqGrid compatibility
cl.hidden=false;}if(!cl.label){cl.label=cl.name;}if(cl.index){cl.name=cl.index;}if(!cl.hasOwnProperty('searchoptions')){cl.searchoptions={};}if(!cl.hasOwnProperty('searchrules')){cl.searchrules={};}}if(this.p.showQuery){$(this).append('<table class=\'queryresult ui-widget ui-widget-content\' style=\'display:block;max-width:440px;border:0px none;\' dir=\''+this.p.direction+'\'><tbody><tr><td class=\'query\'></td></tr></tbody></table>');}/*
		 *Perform checking.
		 *
		*/var checkData=function checkData(val,colModelItem){var ret=[true,''];if($.isFunction(colModelItem.searchrules)){ret=colModelItem.searchrules(val,colModelItem);}else if($.jgrid&&$.jgrid.checkValues){try{ret=$.jgrid.checkValues(val,-1,null,colModelItem.searchrules,colModelItem.label);}catch(e){}}if(ret&&ret.length&&ret[0]===false){p.error=!ret[0];p.errmsg=ret[1];}};/* moving to common
		randId = function() {
			return Math.floor(Math.random()*10000).toString();
		};
		*/this.onchange=function(){// clear any error
this.p.error=false;this.p.errmsg='';return $.isFunction(this.p.onChange)?this.p.onChange.call(this,this.p):false;};/*
		 * Redraw the filter every time when new field is added/deleted
		 * and field is  changed
		 */this.reDraw=function(){$('table.group:first',this).remove();var t=this.createTableForGroup(p.filter,null);$(this).append(t);if($.isFunction(this.p.afterRedraw)){this.p.afterRedraw.call(this,this.p);}};/*
		 * Creates a grouping data for the filter
		 * @param group - object
		 * @param parentgroup - object
		 */this.createTableForGroup=function(group,parentgroup){var that=this,i;// this table will hold all the group (tables) and rules (rows)
var table=$('<table class=\'group ui-widget ui-widget-content\' style=\'border:0px none;\'><tbody></tbody></table>'),// create error message row
align='left';if(this.p.direction=='rtl'){align='right';table.attr('dir','rtl');}if(parentgroup===null){table.append('<tr class=\'error\' style=\'display:none;\'><th colspan=\'5\' class=\'ui-state-error\' align=\''+align+'\'></th></tr>');}var tr=$('<tr></tr>');table.append(tr);// this header will hold the group operator type and group action buttons for
// creating subgroup "+ {}", creating rule "+" or deleting the group "-"
var th=$('<th colspan=\'5\' align=\''+align+'\'></th>');tr.append(th);if(this.p.ruleButtons===true){// dropdown for: choosing group operator type
var groupOpSelect=$('<select class=\'opsel\'></select>');th.append(groupOpSelect);// populate dropdown with all posible group operators: or, and
var str='',selected;for(i=0;i<p.groupOps.length;i++){selected=group.groupOp===that.p.groupOps[i].op?' selected=\'selected\'':'';str+='<option value=\''+that.p.groupOps[i].op+'\''+selected+'>'+that.p.groupOps[i].text+'</option>';}groupOpSelect.append(str).bind('change',function(){group.groupOp=$(groupOpSelect).val();that.onchange();// signals that the filter has changed
});}// button for adding a new subgroup
var inputAddSubgroup='<span></span>';if(this.p.groupButton){inputAddSubgroup=$('<input type=\'button\' value=\'+ {}\' title=\'Add subgroup\' class=\'add-group\'/>');inputAddSubgroup.bind('click',function(){if(group.groups===undefined){group.groups=[];}group.groups.push({groupOp:p.groupOps[0].op,rules:[],groups:[]});// adding a new group
that.reDraw();// the html has changed, force reDraw
that.onchange();// signals that the filter has changed
return false;});}th.append(inputAddSubgroup);if(this.p.ruleButtons===true){// button for adding a new rule
var inputAddRule=$('<input type=\'button\' value=\'+\' title=\'Add rule\' class=\'add-rule ui-add\'/>'),cm;inputAddRule.bind('click',function(){//if(!group) { group = {};}
if(group.rules===undefined){group.rules=[];}for(i=0;i<that.p.columns.length;i++){// but show only serchable and serchhidden = true fields
var searchable=that.p.columns[i].search===undefined?true:that.p.columns[i].search,hidden=that.p.columns[i].hidden===true,ignoreHiding=that.p.columns[i].searchoptions.searchhidden===true;if(ignoreHiding&&searchable||searchable&&!hidden){cm=that.p.columns[i];break;}}var opr;if(cm.searchoptions.sopt){opr=cm.searchoptions.sopt;}else if(that.p.sopt){opr=that.p.sopt;}else if($.inArray(cm.searchtype,that.p.strarr)!==-1){opr=that.p.stropts;}else{opr=that.p.numopts;}group.rules.push({field:cm.name,op:opr[0],data:''});// adding a new rule
that.reDraw();// the html has changed, force reDraw
// for the moment no change have been made to the rule, so
// this will not trigger onchange event
return false;});th.append(inputAddRule);}// button for delete the group
if(parentgroup!==null){// ignore the first group
var inputDeleteGroup=$('<input type=\'button\' value=\'-\' title=\'Delete group\' class=\'delete-group\'/>');th.append(inputDeleteGroup);inputDeleteGroup.bind('click',function(){// remove group from parent
for(i=0;i<parentgroup.groups.length;i++){if(parentgroup.groups[i]===group){parentgroup.groups.splice(i,1);break;}}that.reDraw();// the html has changed, force reDraw
that.onchange();// signals that the filter has changed
return false;});}// append subgroup rows
if(group.groups!==undefined){for(i=0;i<group.groups.length;i++){var trHolderForSubgroup=$('<tr></tr>');table.append(trHolderForSubgroup);var tdFirstHolderForSubgroup=$('<td class=\'first\'></td>');trHolderForSubgroup.append(tdFirstHolderForSubgroup);var tdMainHolderForSubgroup=$('<td colspan=\'4\'></td>');tdMainHolderForSubgroup.append(this.createTableForGroup(group.groups[i],group));trHolderForSubgroup.append(tdMainHolderForSubgroup);}}if(group.groupOp===undefined){group.groupOp=that.p.groupOps[0].op;}// append rules rows
if(group.rules!==undefined){for(i=0;i<group.rules.length;i++){table.append(this.createTableRowForRule(group.rules[i],group));}}return table;};/*
		 * Create the rule data for the filter
		 */this.createTableRowForRule=function(rule,group){// save current entity in a variable so that it could
// be referenced in anonimous method calls
var that=this,tr=$('<tr></tr>'),//document.createElement("tr"),
// first column used for padding
//tdFirstHolderForRule = document.createElement("td"),
i,op,trpar,cm,str='',selected;//tdFirstHolderForRule.setAttribute("class", "first");
tr.append('<td class=\'first\'></td>');// create field container
var ruleFieldTd=$('<td class=\'columns\'></td>');tr.append(ruleFieldTd);// dropdown for: choosing field
var ruleFieldSelect=$('<select></select>'),ina,aoprs=[];ruleFieldTd.append(ruleFieldSelect);ruleFieldSelect.bind('change',function(){rule.field=$(ruleFieldSelect).val();trpar=$(this).parents('tr:first');for(i=0;i<that.p.columns.length;i++){if(that.p.columns[i].name===rule.field){cm=that.p.columns[i];break;}}if(!cm){return;}cm.searchoptions.id=$.jgrid.randId();if(isIE&&cm.inputtype==='text'){if(!cm.searchoptions.size){cm.searchoptions.size=10;}}var elm=$.jgrid.createEl(cm.inputtype,cm.searchoptions,'',true,that.p.ajaxSelectOptions,true);$(elm).addClass('input-elm');//that.createElement(rule, "");
if(cm.searchoptions.sopt){op=cm.searchoptions.sopt;}else if(that.p.sopt){op=that.p.sopt;}else if($.inArray(cm.searchtype,that.p.strarr)!==-1){op=that.p.stropts;}else{op=that.p.numopts;}// operators
var s='',so=0;aoprs=[];$.each(that.p.ops,function(){aoprs.push(this.name);});for(i=0;i<op.length;i++){ina=$.inArray(op[i],aoprs);if(ina!==-1){if(so===0){rule.op=that.p.ops[ina].name;}s+='<option value=\''+that.p.ops[ina].name+'\'>'+that.p.ops[ina].description+'</option>';so++;}}$('.selectopts',trpar).empty().append(s);$('.selectopts',trpar)[0].selectedIndex=0;if($.jgrid.msie&&$.jgrid.msiever()<9){var sw=parseInt($('select.selectopts',trpar)[0].offsetWidth,10)+1;$('.selectopts',trpar).width(sw);$('.selectopts',trpar).css('width','auto');}// data
$('.data',trpar).empty().append(elm);$.jgrid.bindEv(elm,cm.searchoptions,that);$('.input-elm',trpar).bind('change',function(e){var tmo=$(this).hasClass('ui-autocomplete-input')?200:0;setTimeout(function(){var elem=e.target;rule.data=elem.nodeName.toUpperCase()==='SPAN'&&cm.searchoptions&&$.isFunction(cm.searchoptions.custom_value)?cm.searchoptions.custom_value($(elem).children('.customelement:first'),'get'):elem.value;that.onchange();// signals that the filter has changed
},tmo);});setTimeout(function(){//IE, Opera, Chrome
rule.data=$(elm).val();that.onchange();// signals that the filter has changed
},0);});// populate drop down with user provided column definitions
var j=0;for(i=0;i<that.p.columns.length;i++){// but show only serchable and serchhidden = true fields
var searchable=that.p.columns[i].search===undefined?true:that.p.columns[i].search,hidden=that.p.columns[i].hidden===true,ignoreHiding=that.p.columns[i].searchoptions.searchhidden===true;if(ignoreHiding&&searchable||searchable&&!hidden){selected='';if(rule.field===that.p.columns[i].name){selected=' selected=\'selected\'';j=i;}str+='<option value=\''+that.p.columns[i].name+'\''+selected+'>'+that.p.columns[i].label+'</option>';}}ruleFieldSelect.append(str);// create operator container
var ruleOperatorTd=$('<td class=\'operators\'></td>');tr.append(ruleOperatorTd);cm=p.columns[j];// create it here so it can be referentiated in the onchange event
//var RD = that.createElement(rule, rule.data);
cm.searchoptions.id=$.jgrid.randId();if(isIE&&cm.inputtype==='text'){if(!cm.searchoptions.size){cm.searchoptions.size=10;}}var ruleDataInput=$.jgrid.createEl(cm.inputtype,cm.searchoptions,rule.data,true,that.p.ajaxSelectOptions,true);if(rule.op=='nu'||rule.op=='nn'){$(ruleDataInput).attr('readonly','true');$(ruleDataInput).attr('disabled','true');}//retain the state of disabled text fields in case of null ops
// dropdown for: choosing operator
var ruleOperatorSelect=$('<select class=\'selectopts\'></select>');ruleOperatorTd.append(ruleOperatorSelect);ruleOperatorSelect.bind('change',function(){rule.op=$(ruleOperatorSelect).val();trpar=$(this).parents('tr:first');var rd=$('.input-elm',trpar)[0];if(rule.op==='nu'||rule.op==='nn'){// disable for operator "is null" and "is not null"
rule.data='';rd.value='';rd.setAttribute('readonly','true');rd.setAttribute('disabled','true');}else{rd.removeAttribute('readonly');rd.removeAttribute('disabled');}that.onchange();// signals that the filter has changed
});// populate drop down with all available operators
if(cm.searchoptions.sopt){op=cm.searchoptions.sopt;}else if(that.p.sopt){op=that.p.sopt;}else if($.inArray(cm.searchtype,that.p.strarr)!==-1){op=that.p.stropts;}else{op=that.p.numopts;}str='';$.each(that.p.ops,function(){aoprs.push(this.name);});for(i=0;i<op.length;i++){ina=$.inArray(op[i],aoprs);if(ina!==-1){selected=rule.op===that.p.ops[ina].name?' selected=\'selected\'':'';str+='<option value=\''+that.p.ops[ina].name+'\''+selected+'>'+that.p.ops[ina].description+'</option>';}}ruleOperatorSelect.append(str);// create data container
var ruleDataTd=$('<td class=\'data\'></td>');tr.append(ruleDataTd);// textbox for: data
// is created previously
//ruleDataInput.setAttribute("type", "text");
ruleDataTd.append(ruleDataInput);$.jgrid.bindEv(ruleDataInput,cm.searchoptions,that);$(ruleDataInput).addClass('input-elm').bind('change',function(){rule.data=cm.inputtype==='custom'?cm.searchoptions.custom_value($(this).children('.customelement:first'),'get'):$(this).val();that.onchange();// signals that the filter has changed
});// create action container
var ruleDeleteTd=$('<td></td>');tr.append(ruleDeleteTd);// create button for: delete rule
if(this.p.ruleButtons===true){var ruleDeleteInput=$('<input type=\'button\' value=\'-\' title=\'Delete rule\' class=\'delete-rule ui-del\'/>');ruleDeleteTd.append(ruleDeleteInput);//$(ruleDeleteInput).html("").height(20).width(30).button({icons: {  primary: "ui-icon-minus", text:false}});
ruleDeleteInput.bind('click',function(){// remove rule from group
for(i=0;i<group.rules.length;i++){if(group.rules[i]===rule){group.rules.splice(i,1);break;}}that.reDraw();// the html has changed, force reDraw
that.onchange();// signals that the filter has changed
return false;});}return tr;};this.getStringForGroup=function(group){var s='(',index;if(group.groups!==undefined){for(index=0;index<group.groups.length;index++){if(s.length>1){s+=' '+group.groupOp+' ';}try{s+=this.getStringForGroup(group.groups[index]);}catch(eg){alert(eg);}}}if(group.rules!==undefined){try{for(index=0;index<group.rules.length;index++){if(s.length>1){s+=' '+group.groupOp+' ';}s+=this.getStringForRule(group.rules[index]);}}catch(e){alert(e);}}s+=')';if(s==='()'){return'';// ignore groups that don't have rules
}return s;};this.getStringForRule=function(rule){var opUF='',opC='',i,cm,ret,val,numtypes=['int','integer','float','number','currency'];// jqGrid
for(i=0;i<this.p.ops.length;i++){if(this.p.ops[i].name===rule.op){opUF=this.p.ops[i].operator;opC=this.p.ops[i].name;break;}}for(i=0;i<this.p.columns.length;i++){if(this.p.columns[i].name===rule.field){cm=this.p.columns[i];break;}}if(cm==null){return'';}val=rule.data;if(opC==='bw'||opC==='bn'){val=val+'%';}if(opC==='ew'||opC==='en'){val='%'+val;}if(opC==='cn'||opC==='nc'){val='%'+val+'%';}if(opC==='in'||opC==='ni'){val=' ('+val+')';}if(p.errorcheck){checkData(rule.data,cm);}if($.inArray(cm.searchtype,numtypes)!==-1||opC==='nn'||opC==='nu'){ret=rule.field+' '+opUF+' '+val;}else{ret=rule.field+' '+opUF+' "'+val+'"';}return ret;};this.resetFilter=function(){this.p.filter=$.extend(true,{},this.p.initFilter);this.reDraw();this.onchange();};this.hideError=function(){$('th.ui-state-error',this).html('');$('tr.error',this).hide();};this.showError=function(){$('th.ui-state-error',this).html(this.p.errmsg);$('tr.error',this).show();};this.toUserFriendlyString=function(){return this.getStringForGroup(p.filter);};this.toString=function(){// this will obtain a string that can be used to match an item.
var that=this;function getStringRule(rule){if(that.p.errorcheck){var i,cm;for(i=0;i<that.p.columns.length;i++){if(that.p.columns[i].name===rule.field){cm=that.p.columns[i];break;}}if(cm){checkData(rule.data,cm);}}return rule.op+'(item.'+rule.field+',\''+rule.data+'\')';}function getStringForGroup(group){var s='(',index;if(group.groups!==undefined){for(index=0;index<group.groups.length;index++){if(s.length>1){if(group.groupOp==='OR'){s+=' || ';}else{s+=' && ';}}s+=getStringForGroup(group.groups[index]);}}if(group.rules!==undefined){for(index=0;index<group.rules.length;index++){if(s.length>1){if(group.groupOp==='OR'){s+=' || ';}else{s+=' && ';}}s+=getStringRule(group.rules[index]);}}s+=')';if(s==='()'){return'';// ignore groups that don't have rules
}return s;}return getStringForGroup(this.p.filter);};// Here we init the filter
this.reDraw();if(this.p.showQuery){this.onchange();}// mark is as created so that it will not be created twice on this element
this.filter=true;});};$.extend($.fn.jqFilter,{/*
	 * Return SQL like string. Can be used directly
	 */toSQLString:function toSQLString(){var s='';this.each(function(){s=this.toUserFriendlyString();});return s;},/*
	 * Return filter data as object.
	 */filterData:function filterData(){var s;this.each(function(){s=this.p.filter;});return s;},getParameter:function getParameter(param){if(param!==undefined){if(this.p.hasOwnProperty(param)){return this.p[param];}}return this.p;},resetFilter:function resetFilter(){return this.each(function(){this.resetFilter();});},addFilter:function addFilter(pfilter){if(typeof pfilter==='string'){pfilter=$.jgrid.parse(pfilter);}this.each(function(){this.p.filter=pfilter;this.reDraw();this.onchange();});}});})(jQuery);/*jshint eqeqeq:false, eqnull:true, devel:true *//*global xmlJsonClass, jQuery */(function($){/**
 * jqGrid extension for form editing Grid Data
 * Tony Tomov tony@trirand.com
 * http://trirand.com/blog/
 * Dual licensed under the MIT and GPL licenses:
 * http://www.opensource.org/licenses/mit-license.php
 * http://www.gnu.org/licenses/gpl-2.0.html
**/'use strict';$.jgrid.extend({searchGrid:function searchGrid(p){p=$.extend(true,{recreateFilter:false,drag:true,sField:'searchField',sValue:'searchString',sOper:'searchOper',sFilter:'filters',loadDefaults:true,// this options activates loading of default filters from grid's postData for Multipe Search only.
beforeShowSearch:null,afterShowSearch:null,onInitializeSearch:null,afterRedraw:null,afterChange:null,closeAfterSearch:false,closeAfterReset:false,closeOnEscape:false,searchOnEnter:false,multipleSearch:false,multipleGroup:false,//cloneSearchRowOnAdd: true,
top:0,left:0,jqModal:true,modal:false,resize:true,width:450,height:'auto',dataheight:'auto',showQuery:false,errorcheck:true,// translation
// if you want to change or remove the order change it in sopt
// ['eq','ne','lt','le','gt','ge','bw','bn','in','ni','ew','en','cn','nc'],
sopt:null,stringResult:undefined,onClose:null,onSearch:null,onReset:null,toTop:true,overlay:30,columns:[],tmplNames:null,tmplFilters:null,// translations - later in lang file
tmplLabel:' Template: ',showOnLoad:false,layer:null},$.jgrid.search,p||{});return this.each(function(){var $t=this;if(!$t.grid){return;}var fid='fbox_'+$t.p.id,showFrm=true,IDs={themodal:'searchmod'+fid,modalhead:'searchhd'+fid,modalcontent:'searchcnt'+fid,scrollelm:fid},defaultFilters=$t.p.postData[p.sFilter];if(typeof defaultFilters==='string'){defaultFilters=$.jgrid.parse(defaultFilters);}if(p.recreateFilter===true){$('#'+$.jgrid.jqID(IDs.themodal)).remove();}function showFilter(_filter){showFrm=$($t).triggerHandler('jqGridFilterBeforeShow',[_filter]);if(showFrm===undefined){showFrm=true;}if(showFrm&&$.isFunction(p.beforeShowSearch)){showFrm=p.beforeShowSearch.call($t,_filter);}if(showFrm){$.jgrid.viewModal('#'+$.jgrid.jqID(IDs.themodal),{gbox:'#gbox_'+$.jgrid.jqID(fid),jqm:p.jqModal,modal:p.modal,overlay:p.overlay,toTop:p.toTop});$($t).triggerHandler('jqGridFilterAfterShow',[_filter]);if($.isFunction(p.afterShowSearch)){p.afterShowSearch.call($t,_filter);}}}if($('#'+$.jgrid.jqID(IDs.themodal))[0]!==undefined){showFilter($('#fbox_'+$.jgrid.jqID(+$t.p.id)));}else{var fil=$('<div><div id=\''+fid+'\' class=\'searchFilter\' style=\'overflow:auto\'></div></div>').insertBefore('#gview_'+$.jgrid.jqID($t.p.id)),align='left',butleft='';if($t.p.direction=='rtl'){align='right';butleft=' style=\'text-align:left\'';fil.attr('dir','rtl');}var columns=$.extend([],$t.p.colModel),bS='<a href=\'javascript:void(0)\' id=\''+fid+'_search\' class=\'fm-button ui-state-default ui-corner-all fm-button-icon-right ui-reset\'><span class=\'ui-icon ui-icon-search\'></span>'+p.Find+'</a>',bC='<a href=\'javascript:void(0)\' id=\''+fid+'_reset\' class=\'fm-button ui-state-default ui-corner-all fm-button-icon-left ui-search\'><span class=\'ui-icon ui-icon-arrowreturnthick-1-w\'></span>'+p.Reset+'</a>',bQ='',tmpl='',colnm,found=false,bt,cmi=-1;if(p.showQuery){bQ='<a href=\'javascript:void(0)\' id=\''+fid+'_query\' class=\'fm-button ui-state-default ui-corner-all fm-button-icon-left\'><span class=\'ui-icon ui-icon-comment\'></span>Query</a>';}if(!p.columns.length){$.each(columns,function(i,n){if(!n.label){n.label=$t.p.colNames[i];}// find first searchable column and set it if no default filter
if(!found){var searchable=n.search===undefined?true:n.search,hidden=n.hidden===true,ignoreHiding=n.searchoptions&&n.searchoptions.searchhidden===true;if(ignoreHiding&&searchable||searchable&&!hidden){found=true;colnm=n.index||n.name;cmi=i;}}});}else{columns=p.columns;}// old behaviour
if(!defaultFilters&&colnm||p.multipleSearch===false){var cmop='eq';if(cmi>=0&&columns[cmi].searchoptions&&columns[cmi].searchoptions.sopt){cmop=columns[cmi].searchoptions.sopt[0];}else if(p.sopt&&p.sopt.length){cmop=p.sopt[0];}defaultFilters={'groupOp':'AND',rules:[{'field':colnm,'op':cmop,'data':''}]};}found=false;if(p.tmplNames&&p.tmplNames.length){found=true;tmpl=p.tmplLabel;tmpl+='<select class=\'ui-template\'>';tmpl+='<option value=\'default\'>Default</option>';$.each(p.tmplNames,function(i,n){tmpl+='<option value=\''+i+'\'>'+n+'</option>';});tmpl+='</select>';}bt='<table class=\'EditTable\' style=\'border:0px none;margin-top:5px\' id=\''+fid+'_2\'><tbody><tr><td colspan=\'2\'><hr class=\'ui-widget-content\' style=\'margin:1px\'/></td></tr><tr><td class=\'EditButton\' style=\'text-align:'+align+'\'>'+bC+tmpl+'</td><td class=\'EditButton\' '+butleft+'>'+bQ+bS+'</td></tr></tbody></table>';fid=$.jgrid.jqID(fid);$('#'+fid).jqFilter({columns:columns,filter:p.loadDefaults?defaultFilters:null,showQuery:p.showQuery,errorcheck:p.errorcheck,sopt:p.sopt,groupButton:p.multipleGroup,ruleButtons:p.multipleSearch,afterRedraw:p.afterRedraw,_gridsopt:$.jgrid.search.odata,ajaxSelectOptions:$t.p.ajaxSelectOptions,groupOps:p.groupOps,onChange:function onChange(){if(this.p.showQuery){$('.query',this).html(this.toUserFriendlyString());}if($.isFunction(p.afterChange)){p.afterChange.call($t,$('#'+fid),p);}},direction:$t.p.direction});fil.append(bt);if(found&&p.tmplFilters&&p.tmplFilters.length){$('.ui-template',fil).bind('change',function(){var curtempl=$(this).val();if(curtempl=='default'){$('#'+fid).jqFilter('addFilter',defaultFilters);}else{$('#'+fid).jqFilter('addFilter',p.tmplFilters[parseInt(curtempl,10)]);}return false;});}if(p.multipleGroup===true){p.multipleSearch=true;}$($t).triggerHandler('jqGridFilterInitialize',[$('#'+fid)]);if($.isFunction(p.onInitializeSearch)){p.onInitializeSearch.call($t,$('#'+fid));}p.gbox='#gbox_'+fid;if(p.layer){$.jgrid.createModal(IDs,fil,p,'#gview_'+$.jgrid.jqID($t.p.id),$('#gbox_'+$.jgrid.jqID($t.p.id))[0],'#'+$.jgrid.jqID(p.layer),{position:'relative'});}else{$.jgrid.createModal(IDs,fil,p,'#gview_'+$.jgrid.jqID($t.p.id),$('#gbox_'+$.jgrid.jqID($t.p.id))[0]);}if(p.searchOnEnter||p.closeOnEscape){$('#'+$.jgrid.jqID(IDs.themodal)).keydown(function(e){var $target=$(e.target);if(p.searchOnEnter&&e.which===13&&// 13 === $.ui.keyCode.ENTER
!$target.hasClass('add-group')&&!$target.hasClass('add-rule')&&!$target.hasClass('delete-group')&&!$target.hasClass('delete-rule')&&(!$target.hasClass('fm-button')||!$target.is('[id$=_query]'))){$('#'+fid+'_search').focus().click();return false;}if(p.closeOnEscape&&e.which===27){// 27 === $.ui.keyCode.ESCAPE
$('#'+$.jgrid.jqID(IDs.modalhead)).find('.ui-jqdialog-titlebar-close').focus().click();return false;}});}if(bQ){$('#'+fid+'_query').bind('click',function(){$('.queryresult',fil).toggle();return false;});}if(p.stringResult===undefined){// to provide backward compatibility, inferring stringResult value from multipleSearch
p.stringResult=p.multipleSearch;}$('#'+fid+'_search').bind('click',function(){var fl=$('#'+fid),sdata={},res,filters=fl.jqFilter('filterData');if(p.errorcheck){fl[0].hideError();if(!p.showQuery){fl.jqFilter('toSQLString');}if(fl[0].p.error){fl[0].showError();return false;}}if(p.stringResult){try{// xmlJsonClass or JSON.stringify
res=xmlJsonClass.toJson(filters,'','',false);}catch(e){try{res=JSON.stringify(filters);}catch(e2){}}if(typeof res==='string'){sdata[p.sFilter]=res;$.each([p.sField,p.sValue,p.sOper],function(){sdata[this]='';});}}else{if(p.multipleSearch){sdata[p.sFilter]=filters;$.each([p.sField,p.sValue,p.sOper],function(){sdata[this]='';});}else{sdata[p.sField]=filters.rules[0].field;sdata[p.sValue]=filters.rules[0].data;sdata[p.sOper]=filters.rules[0].op;sdata[p.sFilter]='';}}$t.p.search=true;$.extend($t.p.postData,sdata);$($t).triggerHandler('jqGridFilterSearch');if($.isFunction(p.onSearch)){p.onSearch.call($t);}$($t).trigger('reloadGrid',[{page:1}]);if(p.closeAfterSearch){$.jgrid.hideModal('#'+$.jgrid.jqID(IDs.themodal),{gb:'#gbox_'+$.jgrid.jqID($t.p.id),jqm:p.jqModal,onClose:p.onClose});}return false;});$('#'+fid+'_reset').bind('click',function(){var sdata={},fl=$('#'+fid);$t.p.search=false;if(p.multipleSearch===false){sdata[p.sField]=sdata[p.sValue]=sdata[p.sOper]='';}else{sdata[p.sFilter]='';}fl[0].resetFilter();if(found){$('.ui-template',fil).val('default');}$.extend($t.p.postData,sdata);$($t).triggerHandler('jqGridFilterReset');if($.isFunction(p.onReset)){p.onReset.call($t);}$($t).trigger('reloadGrid',[{page:1}]);return false;});showFilter($('#'+fid));$('.fm-button:not(.ui-state-disabled)',fil).hover(function(){$(this).addClass('ui-state-hover');},function(){$(this).removeClass('ui-state-hover');});}});},editGridRow:function editGridRow(rowid,p){p=$.extend(true,{top:0,left:0,width:300,datawidth:'auto',height:'auto',dataheight:'auto',modal:false,overlay:30,drag:true,resize:true,url:null,mtype:'POST',clearAfterAdd:true,closeAfterEdit:false,reloadAfterSubmit:true,onInitializeForm:null,beforeInitData:null,beforeShowForm:null,afterShowForm:null,beforeSubmit:null,afterSubmit:null,onclickSubmit:null,afterComplete:null,onclickPgButtons:null,afterclickPgButtons:null,editData:{},recreateForm:false,jqModal:true,closeOnEscape:false,addedrow:'first',topinfo:'',bottominfo:'',saveicon:[],closeicon:[],savekey:[false,13],navkeys:[false,38,40],checkOnSubmit:false,checkOnUpdate:false,_savedData:{},processing:false,onClose:null,ajaxEditOptions:{},serializeEditData:null,viewPagerButtons:true},$.jgrid.edit,p||{});rp_ge[$(this)[0].p.id]=p;return this.each(function(){var $t=this;if(!$t.grid||!rowid){return;}var gID=$t.p.id,frmgr='FrmGrid_'+gID,frmtborg='TblGrid_'+gID,frmtb='#'+$.jgrid.jqID(frmtborg),IDs={themodal:'editmod'+gID,modalhead:'edithd'+gID,modalcontent:'editcnt'+gID,scrollelm:frmgr},onBeforeShow=$.isFunction(rp_ge[$t.p.id].beforeShowForm)?rp_ge[$t.p.id].beforeShowForm:false,onAfterShow=$.isFunction(rp_ge[$t.p.id].afterShowForm)?rp_ge[$t.p.id].afterShowForm:false,onBeforeInit=$.isFunction(rp_ge[$t.p.id].beforeInitData)?rp_ge[$t.p.id].beforeInitData:false,onInitializeForm=$.isFunction(rp_ge[$t.p.id].onInitializeForm)?rp_ge[$t.p.id].onInitializeForm:false,showFrm=true,maxCols=1,maxRows=0,postdata,extpost,newData,diff,frmoper;frmgr=$.jgrid.jqID(frmgr);if(rowid==='new'){rowid='_empty';frmoper='add';p.caption=rp_ge[$t.p.id].addCaption;}else{p.caption=rp_ge[$t.p.id].editCaption;frmoper='edit';}if(p.recreateForm===true&&$('#'+$.jgrid.jqID(IDs.themodal))[0]!==undefined){$('#'+$.jgrid.jqID(IDs.themodal)).remove();}var closeovrl=true;if(p.checkOnUpdate&&p.jqModal&&!p.modal){closeovrl=false;}function getFormData(){$(frmtb+' > tbody > tr > td > .FormElement').each(function(){var celm=$('.customelement',this);if(celm.length){var elem=celm[0],nm=$(elem).attr('name');$.each($t.p.colModel,function(){if(this.name===nm&&this.editoptions&&$.isFunction(this.editoptions.custom_value)){try{postdata[nm]=this.editoptions.custom_value.call($t,$('#'+$.jgrid.jqID(nm),frmtb),'get');if(postdata[nm]===undefined){throw'e1';}}catch(e){if(e==='e1'){$.jgrid.info_dialog($.jgrid.errors.errcap,'function \'custom_value\' '+$.jgrid.edit.msg.novalue,$.jgrid.edit.bClose);}else{$.jgrid.info_dialog($.jgrid.errors.errcap,e.message,$.jgrid.edit.bClose);}}return true;}});}else{switch($(this).get(0).type){case'checkbox':if($(this).is(':checked')){postdata[this.name]=$(this).val();}else{var ofv=$(this).attr('offval');postdata[this.name]=ofv;}break;case'select-one':postdata[this.name]=$('option:selected',this).val();extpost[this.name]=$('option:selected',this).text();break;case'select-multiple':postdata[this.name]=$(this).val();if(postdata[this.name]){postdata[this.name]=postdata[this.name].join(',');}else{postdata[this.name]='';}var selectedText=[];$('option:selected',this).each(function(i,selected){selectedText[i]=$(selected).text();});extpost[this.name]=selectedText.join(',');break;case'password':case'text':case'textarea':case'button':postdata[this.name]=$(this).val();break;}if($t.p.autoencode){postdata[this.name]=$.jgrid.htmlEncode(postdata[this.name]);}}});return true;}function createData(rowid,obj,tb,maxcols){var nm,hc,trdata,cnt=0,tmp,dc,elc,retpos=[],ind=false,tdtmpl='<td class=\'CaptionTD\'>&#160;</td><td class=\'DataTD\'>&#160;</td>',tmpl='',i;//*2
for(i=1;i<=maxcols;i++){tmpl+=tdtmpl;}if(rowid!='_empty'){ind=$(obj).jqGrid('getInd',rowid);}$(obj.p.colModel).each(function(i){nm=this.name;// hidden fields are included in the form
if(this.editrules&&this.editrules.edithidden===true){hc=false;}else{hc=this.hidden===true?true:false;}dc=hc?'style=\'display:none\'':'';if(nm!=='cb'&&nm!=='subgrid'&&this.editable===true&&nm!=='rn'){if(ind===false){tmp='';}else{if(nm==obj.p.ExpandColumn&&obj.p.treeGrid===true){tmp=$('td[role=\'gridcell\']:eq('+i+')',obj.rows[ind]).text();}else{try{tmp=$.unformat.call(obj,$('td[role=\'gridcell\']:eq('+i+')',obj.rows[ind]),{rowId:rowid,colModel:this},i);}catch(_){tmp=this.edittype&&this.edittype=='textarea'?$('td[role=\'gridcell\']:eq('+i+')',obj.rows[ind]).text():$('td[role=\'gridcell\']:eq('+i+')',obj.rows[ind]).html();}if(!tmp||tmp=='&nbsp;'||tmp=='&#160;'||tmp.length==1&&tmp.charCodeAt(0)==160){tmp='';}}}var opt=$.extend({},this.editoptions||{},{id:nm,name:nm}),frmopt=$.extend({},{elmprefix:'',elmsuffix:'',rowabove:false,rowcontent:''},this.formoptions||{}),rp=parseInt(frmopt.rowpos,10)||cnt+1,cp=parseInt((parseInt(frmopt.colpos,10)||1)*2,10);if(rowid=='_empty'&&opt.defaultValue){tmp=$.isFunction(opt.defaultValue)?opt.defaultValue.call($t):opt.defaultValue;}if(!this.edittype){this.edittype='text';}if($t.p.autoencode){tmp=$.jgrid.htmlDecode(tmp);}elc=$.jgrid.createEl.call($t,this.edittype,opt,tmp,false,$.extend({},$.jgrid.ajaxOptions,obj.p.ajaxSelectOptions||{}));if(tmp===''&&this.edittype=='checkbox'){tmp=$(elc).attr('offval');}if(tmp===''&&this.edittype=='select'){tmp=$('option:eq(0)',elc).text();}if(rp_ge[$t.p.id].checkOnSubmit||rp_ge[$t.p.id].checkOnUpdate){rp_ge[$t.p.id]._savedData[nm]=tmp;}$(elc).addClass('FormElement');if($.inArray(this.edittype,['text','textarea','password','select'])>-1){$(elc).addClass('ui-widget-content ui-corner-all');}trdata=$(tb).find('tr[rowpos='+rp+']');if(frmopt.rowabove){var newdata=$('<tr><td class=\'contentinfo\' colspan=\''+maxcols*2+'\'>'+frmopt.rowcontent+'</td></tr>');$(tb).append(newdata);newdata[0].rp=rp;}if(trdata.length===0){trdata=$('<tr '+dc+' rowpos=\''+rp+'\'></tr>').addClass('FormData').attr('id','tr_'+nm);$(trdata).append(tmpl);$(tb).append(trdata);trdata[0].rp=rp;}$('td:eq('+(cp-2)+')',trdata[0]).html(frmopt.label===undefined?obj.p.colNames[i]:frmopt.label);$('td:eq('+(cp-1)+')',trdata[0]).append(frmopt.elmprefix).append(elc).append(frmopt.elmsuffix);if($.isFunction(opt.custom_value)&&rowid!=='_empty'){opt.custom_value.call($t,$('#'+nm,'#'+frmgr),'set',tmp);}$.jgrid.bindEv(elc,opt,$t);retpos[cnt]=i;cnt++;}});if(cnt>0){var idrow=$('<tr class=\'FormData\' style=\'display:none\'><td class=\'CaptionTD\'></td><td colspan=\''+(maxcols*2-1)+'\' class=\'DataTD\'><input class=\'FormElement\' id=\'id_g\' type=\'text\' name=\''+obj.p.id+'_id\' value=\''+rowid+'\'/></td></tr>');idrow[0].rp=cnt+999;$(tb).append(idrow);if(rp_ge[$t.p.id].checkOnSubmit||rp_ge[$t.p.id].checkOnUpdate){rp_ge[$t.p.id]._savedData[obj.p.id+'_id']=rowid;}}return retpos;}function fillData(rowid,obj,fmid){var nm,cnt=0,tmp,fld,opt,vl,vlc;if(rp_ge[$t.p.id].checkOnSubmit||rp_ge[$t.p.id].checkOnUpdate){rp_ge[$t.p.id]._savedData={};rp_ge[$t.p.id]._savedData[obj.p.id+'_id']=rowid;}var cm=obj.p.colModel;if(rowid=='_empty'){$(cm).each(function(){nm=this.name;opt=$.extend({},this.editoptions||{});fld=$('#'+$.jgrid.jqID(nm),'#'+fmid);if(fld&&fld.length&&fld[0]!==null){vl='';if(opt.defaultValue){vl=$.isFunction(opt.defaultValue)?opt.defaultValue.call($t):opt.defaultValue;if(fld[0].type=='checkbox'){vlc=vl.toLowerCase();if(vlc.search(/(false|0|no|off|undefined)/i)<0&&vlc!==''){fld[0].checked=true;fld[0].defaultChecked=true;fld[0].value=vl;}else{fld[0].checked=false;fld[0].defaultChecked=false;}}else{fld.val(vl);}}else{if(fld[0].type=='checkbox'){fld[0].checked=false;fld[0].defaultChecked=false;vl=$(fld).attr('offval');}else if(fld[0].type&&fld[0].type.substr(0,6)=='select'){fld[0].selectedIndex=0;}else{fld.val(vl);}}if(rp_ge[$t.p.id].checkOnSubmit===true||rp_ge[$t.p.id].checkOnUpdate){rp_ge[$t.p.id]._savedData[nm]=vl;}}});$('#id_g','#'+fmid).val(rowid);return;}var tre=$(obj).jqGrid('getInd',rowid,true);if(!tre){return;}$('td[role="gridcell"]',tre).each(function(i){nm=cm[i].name;// hidden fields are included in the form
if(nm!=='cb'&&nm!=='subgrid'&&nm!=='rn'&&cm[i].editable===true){if(nm==obj.p.ExpandColumn&&obj.p.treeGrid===true){tmp=$(this).text();}else{try{tmp=$.unformat.call(obj,$(this),{rowId:rowid,colModel:cm[i]},i);}catch(_){tmp=cm[i].edittype=='textarea'?$(this).text():$(this).html();}}if($t.p.autoencode){tmp=$.jgrid.htmlDecode(tmp);}if(rp_ge[$t.p.id].checkOnSubmit===true||rp_ge[$t.p.id].checkOnUpdate){rp_ge[$t.p.id]._savedData[nm]=tmp;}nm=$.jgrid.jqID(nm);switch(cm[i].edittype){case'password':case'text':case'button':case'image':case'textarea':if(tmp=='&nbsp;'||tmp=='&#160;'||tmp.length==1&&tmp.charCodeAt(0)==160){tmp='';}$('#'+nm,'#'+fmid).val(tmp);break;case'select':var opv=tmp.split(',');opv=$.map(opv,function(n){return $.trim(n);});$('#'+nm+' option','#'+fmid).each(function(){if(!cm[i].editoptions.multiple&&($.trim(tmp)==$.trim($(this).text())||opv[0]==$.trim($(this).text())||opv[0]==$.trim($(this).val()))){this.selected=true;}else if(cm[i].editoptions.multiple){if($.inArray($.trim($(this).text()),opv)>-1||$.inArray($.trim($(this).val()),opv)>-1){this.selected=true;}else{this.selected=false;}}else{this.selected=false;}});break;case'checkbox':tmp=String(tmp);if(cm[i].editoptions&&cm[i].editoptions.value){var cb=cm[i].editoptions.value.split(':');if(cb[0]==tmp){$('#'+nm,'#'+fmid)[$t.p.useProp?'prop':'attr']('checked',true);$('#'+nm,'#'+fmid)[$t.p.useProp?'prop':'attr']('defaultChecked',true);//ie
}else{$('#'+nm,'#'+fmid)[$t.p.useProp?'prop':'attr']('checked',false);$('#'+nm,'#'+fmid)[$t.p.useProp?'prop':'attr']('defaultChecked',false);//ie
}}else{tmp=tmp.toLowerCase();if(tmp.search(/(false|0|no|off|undefined)/i)<0&&tmp!==''){$('#'+nm,'#'+fmid)[$t.p.useProp?'prop':'attr']('checked',true);$('#'+nm,'#'+fmid)[$t.p.useProp?'prop':'attr']('defaultChecked',true);//ie
}else{$('#'+nm,'#'+fmid)[$t.p.useProp?'prop':'attr']('checked',false);$('#'+nm,'#'+fmid)[$t.p.useProp?'prop':'attr']('defaultChecked',false);//ie
}}break;case'custom':try{if(cm[i].editoptions&&$.isFunction(cm[i].editoptions.custom_value)){cm[i].editoptions.custom_value.call($t,$('#'+nm,'#'+fmid),'set',tmp);}else{throw'e1';}}catch(e){if(e=='e1'){$.jgrid.info_dialog($.jgrid.errors.errcap,'function \'custom_value\' '+$.jgrid.edit.msg.nodefined,$.jgrid.edit.bClose);}else{$.jgrid.info_dialog($.jgrid.errors.errcap,e.message,$.jgrid.edit.bClose);}}break;}cnt++;}});if(cnt>0){$('#id_g',frmtb).val(rowid);}}function setNulls(){$.each($t.p.colModel,function(i,n){if(n.editoptions&&n.editoptions.NullIfEmpty===true){if(postdata.hasOwnProperty(n.name)&&postdata[n.name]===''){postdata[n.name]='null';}}});}function postIt(){var copydata,ret=[true,'',''],onCS={},opers=$t.p.prmNames,idname,oper,key,selr,i;var retvals=$($t).triggerHandler('jqGridAddEditBeforeCheckValues',[$('#'+frmgr),frmoper]);if(retvals&&(typeof retvals==="undefined"?"undefined":_typeof(retvals))==='object'){postdata=retvals;}if($.isFunction(rp_ge[$t.p.id].beforeCheckValues)){retvals=rp_ge[$t.p.id].beforeCheckValues.call($t,postdata,$('#'+frmgr),postdata[$t.p.id+'_id']=='_empty'?opers.addoper:opers.editoper);if(retvals&&(typeof retvals==="undefined"?"undefined":_typeof(retvals))==='object'){postdata=retvals;}}for(key in postdata){if(postdata.hasOwnProperty(key)){ret=$.jgrid.checkValues.call($t,postdata[key],key,$t);if(ret[0]===false){break;}}}setNulls();if(ret[0]){onCS=$($t).triggerHandler('jqGridAddEditClickSubmit',[rp_ge[$t.p.id],postdata,frmoper]);if(onCS===undefined&&$.isFunction(rp_ge[$t.p.id].onclickSubmit)){onCS=rp_ge[$t.p.id].onclickSubmit.call($t,rp_ge[$t.p.id],postdata)||{};}ret=$($t).triggerHandler('jqGridAddEditBeforeSubmit',[postdata,$('#'+frmgr),frmoper]);if(ret===undefined){ret=[true,'',''];}if(ret[0]&&$.isFunction(rp_ge[$t.p.id].beforeSubmit)){ret=rp_ge[$t.p.id].beforeSubmit.call($t,postdata,$('#'+frmgr));}}if(ret[0]&&!rp_ge[$t.p.id].processing){rp_ge[$t.p.id].processing=true;$('#sData',frmtb+'_2').addClass('ui-state-active');oper=opers.oper;idname=opers.id;// we add to pos data array the action - the name is oper
postdata[oper]=$.trim(postdata[$t.p.id+'_id'])=='_empty'?opers.addoper:opers.editoper;if(postdata[oper]!=opers.addoper){postdata[idname]=postdata[$t.p.id+'_id'];}else{// check to see if we have allredy this field in the form and if yes lieve it
if(postdata[idname]===undefined){postdata[idname]=postdata[$t.p.id+'_id'];}}delete postdata[$t.p.id+'_id'];postdata=$.extend(postdata,rp_ge[$t.p.id].editData,onCS);if($t.p.treeGrid===true){if(postdata[oper]==opers.addoper){selr=$($t).jqGrid('getGridParam','selrow');var tr_par_id=$t.p.treeGridModel=='adjacency'?$t.p.treeReader.parent_id_field:'parent_id';postdata[tr_par_id]=selr;}for(i in $t.p.treeReader){if($t.p.treeReader.hasOwnProperty(i)){var itm=$t.p.treeReader[i];if(postdata.hasOwnProperty(itm)){if(postdata[oper]==opers.addoper&&i==='parent_id_field'){continue;}delete postdata[itm];}}}}postdata[idname]=$.jgrid.stripPref($t.p.idPrefix,postdata[idname]);var ajaxOptions=$.extend({url:rp_ge[$t.p.id].url||$($t).jqGrid('getGridParam','editurl'),type:rp_ge[$t.p.id].mtype,data:$.isFunction(rp_ge[$t.p.id].serializeEditData)?rp_ge[$t.p.id].serializeEditData.call($t,postdata):postdata,complete:function complete(data,status){var key;postdata[idname]=$t.p.idPrefix+postdata[idname];if(status!='success'){ret[0]=false;ret[1]=$($t).triggerHandler('jqGridAddEditErrorTextFormat',[data,frmoper]);if($.isFunction(rp_ge[$t.p.id].errorTextFormat)){ret[1]=rp_ge[$t.p.id].errorTextFormat.call($t,data);}else{ret[1]=status+' Status: \''+data.statusText+'\'. Error code: '+data.status;}}else{// data is posted successful
// execute aftersubmit with the returned data from server
ret=$($t).triggerHandler('jqGridAddEditAfterSubmit',[data,postdata,frmoper]);if(ret===undefined){ret=[true,'',''];}if(ret[0]&&$.isFunction(rp_ge[$t.p.id].afterSubmit)){ret=rp_ge[$t.p.id].afterSubmit.call($t,data,postdata);}}if(ret[0]===false){$('#FormError>td',frmtb).html(ret[1]);$('#FormError',frmtb).show();}else{// remove some values if formattaer select or checkbox
$.each($t.p.colModel,function(){if(extpost[this.name]&&this.formatter&&this.formatter=='select'){try{delete extpost[this.name];}catch(e){}}});postdata=$.extend(postdata,extpost);if($t.p.autoencode){$.each(postdata,function(n,v){postdata[n]=$.jgrid.htmlDecode(v);});}//rp_ge[$t.p.id].reloadAfterSubmit = rp_ge[$t.p.id].reloadAfterSubmit && $t.p.datatype != "local";
// the action is add
if(postdata[oper]==opers.addoper){//id processing
// user not set the id ret[2]
if(!ret[2]){ret[2]=$.jgrid.randId();}postdata[idname]=ret[2];if(rp_ge[$t.p.id].closeAfterAdd){if(rp_ge[$t.p.id].reloadAfterSubmit){$($t).trigger('reloadGrid');}else{if($t.p.treeGrid===true){$($t).jqGrid('addChildNode',ret[2],selr,postdata);}else{$($t).jqGrid('addRowData',ret[2],postdata,p.addedrow);$($t).jqGrid('setSelection',ret[2]);}}$.jgrid.hideModal('#'+$.jgrid.jqID(IDs.themodal),{gb:'#gbox_'+$.jgrid.jqID(gID),jqm:p.jqModal,onClose:rp_ge[$t.p.id].onClose});}else if(rp_ge[$t.p.id].clearAfterAdd){if(rp_ge[$t.p.id].reloadAfterSubmit){$($t).trigger('reloadGrid');}else{if($t.p.treeGrid===true){$($t).jqGrid('addChildNode',ret[2],selr,postdata);}else{$($t).jqGrid('addRowData',ret[2],postdata,p.addedrow);}}fillData('_empty',$t,frmgr);}else{if(rp_ge[$t.p.id].reloadAfterSubmit){$($t).trigger('reloadGrid');}else{if($t.p.treeGrid===true){$($t).jqGrid('addChildNode',ret[2],selr,postdata);}else{$($t).jqGrid('addRowData',ret[2],postdata,p.addedrow);}}}}else{// the action is update
if(rp_ge[$t.p.id].reloadAfterSubmit){$($t).trigger('reloadGrid');if(!rp_ge[$t.p.id].closeAfterEdit){setTimeout(function(){$($t).jqGrid('setSelection',postdata[idname]);},1000);}}else{if($t.p.treeGrid===true){$($t).jqGrid('setTreeRow',postdata[idname],postdata);}else{$($t).jqGrid('setRowData',postdata[idname],postdata);}}if(rp_ge[$t.p.id].closeAfterEdit){$.jgrid.hideModal('#'+$.jgrid.jqID(IDs.themodal),{gb:'#gbox_'+$.jgrid.jqID(gID),jqm:p.jqModal,onClose:rp_ge[$t.p.id].onClose});}}if($.isFunction(rp_ge[$t.p.id].afterComplete)){copydata=data;setTimeout(function(){$($t).triggerHandler('jqGridAddEditAfterComplete',[copydata,postdata,$('#'+frmgr),frmoper]);rp_ge[$t.p.id].afterComplete.call($t,copydata,postdata,$('#'+frmgr));copydata=null;},500);}if(rp_ge[$t.p.id].checkOnSubmit||rp_ge[$t.p.id].checkOnUpdate){$('#'+frmgr).data('disabled',false);if(rp_ge[$t.p.id]._savedData[$t.p.id+'_id']!='_empty'){for(key in rp_ge[$t.p.id]._savedData){if(rp_ge[$t.p.id]._savedData.hasOwnProperty(key)&&postdata[key]){rp_ge[$t.p.id]._savedData[key]=postdata[key];}}}}}rp_ge[$t.p.id].processing=false;$('#sData',frmtb+'_2').removeClass('ui-state-active');try{$(':input:visible','#'+frmgr)[0].focus();}catch(e){}}},$.jgrid.ajaxOptions,rp_ge[$t.p.id].ajaxEditOptions);if(!ajaxOptions.url&&!rp_ge[$t.p.id].useDataProxy){if($.isFunction($t.p.dataProxy)){rp_ge[$t.p.id].useDataProxy=true;}else{ret[0]=false;ret[1]+=' '+$.jgrid.errors.nourl;}}if(ret[0]){if(rp_ge[$t.p.id].useDataProxy){var dpret=$t.p.dataProxy.call($t,ajaxOptions,'set_'+$t.p.id);if(dpret===undefined){dpret=[true,''];}if(dpret[0]===false){ret[0]=false;ret[1]=dpret[1]||'Error deleting the selected row!';}else{if(ajaxOptions.data.oper==opers.addoper&&rp_ge[$t.p.id].closeAfterAdd){$.jgrid.hideModal('#'+$.jgrid.jqID(IDs.themodal),{gb:'#gbox_'+$.jgrid.jqID(gID),jqm:p.jqModal,onClose:rp_ge[$t.p.id].onClose});}if(ajaxOptions.data.oper==opers.editoper&&rp_ge[$t.p.id].closeAfterEdit){$.jgrid.hideModal('#'+$.jgrid.jqID(IDs.themodal),{gb:'#gbox_'+$.jgrid.jqID(gID),jqm:p.jqModal,onClose:rp_ge[$t.p.id].onClose});}}}else{$.ajax(ajaxOptions);}}}if(ret[0]===false){$('#FormError>td',frmtb).html(ret[1]);$('#FormError',frmtb).show();// return;
}}function compareData(nObj,oObj){var ret=false,key;for(key in nObj){if(nObj.hasOwnProperty(key)&&nObj[key]!=oObj[key]){ret=true;break;}}return ret;}function checkUpdates(){var stat=true;$('#FormError',frmtb).hide();if(rp_ge[$t.p.id].checkOnUpdate){postdata={};extpost={};getFormData();newData=$.extend({},postdata,extpost);diff=compareData(newData,rp_ge[$t.p.id]._savedData);if(diff){$('#'+frmgr).data('disabled',true);$('.confirm','#'+IDs.themodal).show();stat=false;}}return stat;}function restoreInline(){var i;if(rowid!=='_empty'&&$t.p.savedRow!==undefined&&$t.p.savedRow.length>0&&$.isFunction($.fn.jqGrid.restoreRow)){for(i=0;i<$t.p.savedRow.length;i++){if($t.p.savedRow[i].id==rowid){$($t).jqGrid('restoreRow',rowid);break;}}}}function updateNav(cr,posarr){var totr=posarr[1].length-1;if(cr===0){$('#pData',frmtb+'_2').addClass('ui-state-disabled');}else if(posarr[1][cr-1]!==undefined&&$('#'+$.jgrid.jqID(posarr[1][cr-1])).hasClass('ui-state-disabled')){$('#pData',frmtb+'_2').addClass('ui-state-disabled');}else{$('#pData',frmtb+'_2').removeClass('ui-state-disabled');}if(cr==totr){$('#nData',frmtb+'_2').addClass('ui-state-disabled');}else if(posarr[1][cr+1]!==undefined&&$('#'+$.jgrid.jqID(posarr[1][cr+1])).hasClass('ui-state-disabled')){$('#nData',frmtb+'_2').addClass('ui-state-disabled');}else{$('#nData',frmtb+'_2').removeClass('ui-state-disabled');}}function getCurrPos(){var rowsInGrid=$($t).jqGrid('getDataIDs'),selrow=$('#id_g',frmtb).val(),pos=$.inArray(selrow,rowsInGrid);return[pos,rowsInGrid];}if($('#'+$.jgrid.jqID(IDs.themodal))[0]!==undefined){showFrm=$($t).triggerHandler('jqGridAddEditBeforeInitData',[$('#'+$.jgrid.jqID(frmgr)),frmoper]);if(showFrm===undefined){showFrm=true;}if(showFrm&&onBeforeInit){showFrm=onBeforeInit.call($t,$('#'+frmgr));}if(showFrm===false){return;}restoreInline();$('.ui-jqdialog-title','#'+$.jgrid.jqID(IDs.modalhead)).html(p.caption);$('#FormError',frmtb).hide();if(rp_ge[$t.p.id].topinfo){$('.topinfo',frmtb).html(rp_ge[$t.p.id].topinfo);$('.tinfo',frmtb).show();}else{$('.tinfo',frmtb).hide();}if(rp_ge[$t.p.id].bottominfo){$('.bottominfo',frmtb+'_2').html(rp_ge[$t.p.id].bottominfo);$('.binfo',frmtb+'_2').show();}else{$('.binfo',frmtb+'_2').hide();}// filldata
fillData(rowid,$t,frmgr);///
if(rowid=='_empty'||!rp_ge[$t.p.id].viewPagerButtons){$('#pData, #nData',frmtb+'_2').hide();}else{$('#pData, #nData',frmtb+'_2').show();}if(rp_ge[$t.p.id].processing===true){rp_ge[$t.p.id].processing=false;$('#sData',frmtb+'_2').removeClass('ui-state-active');}if($('#'+frmgr).data('disabled')===true){$('.confirm','#'+$.jgrid.jqID(IDs.themodal)).hide();$('#'+frmgr).data('disabled',false);}$($t).triggerHandler('jqGridAddEditBeforeShowForm',[$('#'+frmgr),frmoper]);if(onBeforeShow){onBeforeShow.call($t,$('#'+frmgr));}$('#'+$.jgrid.jqID(IDs.themodal)).data('onClose',rp_ge[$t.p.id].onClose);$.jgrid.viewModal('#'+$.jgrid.jqID(IDs.themodal),{gbox:'#gbox_'+$.jgrid.jqID(gID),jqm:p.jqModal,jqM:false,overlay:p.overlay,modal:p.modal});if(!closeovrl){$('.jqmOverlay').click(function(){if(!checkUpdates()){return false;}$.jgrid.hideModal('#'+$.jgrid.jqID(IDs.themodal),{gb:'#gbox_'+$.jgrid.jqID(gID),jqm:p.jqModal,onClose:rp_ge[$t.p.id].onClose});return false;});}$($t).triggerHandler('jqGridAddEditAfterShowForm',[$('#'+frmgr),frmoper]);if(onAfterShow){onAfterShow.call($t,$('#'+frmgr));}}else{var dh=isNaN(p.dataheight)?p.dataheight:p.dataheight+'px',dw=isNaN(p.datawidth)?p.datawidth:p.datawidth+'px',frm=$('<form name=\'FormPost\' id=\''+frmgr+'\' class=\'FormGrid\' onSubmit=\'return false;\' style=\'width:'+dw+';overflow:auto;position:relative;height:'+dh+';\'></form>').data('disabled',false),tbl=$('<table id=\''+frmtborg+'\' class=\'EditTable\' cellspacing=\'0\' cellpadding=\'0\' border=\'0\'><tbody></tbody></table>');showFrm=$($t).triggerHandler('jqGridAddEditBeforeInitData',[$('#'+frmgr),frmoper]);if(showFrm===undefined){showFrm=true;}if(showFrm&&onBeforeInit){showFrm=onBeforeInit.call($t,$('#'+frmgr));}if(showFrm===false){return;}restoreInline();$($t.p.colModel).each(function(){var fmto=this.formoptions;maxCols=Math.max(maxCols,fmto?fmto.colpos||0:0);maxRows=Math.max(maxRows,fmto?fmto.rowpos||0:0);});$(frm).append(tbl);var flr=$('<tr id=\'FormError\' style=\'display:none\'><td class=\'ui-state-error\' colspan=\''+maxCols*2+'\'></td></tr>');flr[0].rp=0;$(tbl).append(flr);//topinfo
flr=$('<tr style=\'display:none\' class=\'tinfo\'><td class=\'topinfo\' colspan=\''+maxCols*2+'\'>'+rp_ge[$t.p.id].topinfo+'</td></tr>');flr[0].rp=0;$(tbl).append(flr);// set the id.
// use carefull only to change here colproperties.
// create data
var rtlb=$t.p.direction=='rtl'?true:false,bp=rtlb?'nData':'pData',bn=rtlb?'pData':'nData';createData(rowid,$t,tbl,maxCols);// buttons at footer
var bP='<a href=\'javascript:void(0)\' id=\''+bp+'\' class=\'fm-button ui-state-default ui-corner-left\'><span class=\'ui-icon ui-icon-triangle-1-w\'></span></a>',bN='<a href=\'javascript:void(0)\' id=\''+bn+'\' class=\'fm-button ui-state-default ui-corner-right\'><span class=\'ui-icon ui-icon-triangle-1-e\'></span></a>',bS='<a href=\'javascript:void(0)\' id=\'sData\' class=\'fm-button ui-state-default ui-corner-all\'>'+p.bSubmit+'</a>',bC='<a href=\'javascript:void(0)\' id=\'cData\' class=\'fm-button ui-state-default ui-corner-all\'>'+p.bCancel+'</a>';var bt='<table border=\'0\' cellspacing=\'0\' cellpadding=\'0\' class=\'EditTable\' id=\''+frmtborg+'_2\'><tbody><tr><td colspan=\'2\'><hr class=\'ui-widget-content\' style=\'margin:1px\'/></td></tr><tr id=\'Act_Buttons\'><td class=\'navButton\'>'+(rtlb?bN+bP:bP+bN)+'</td><td class=\'EditButton\'>'+bS+bC+'</td></tr>';bt+='<tr style=\'display:none\' class=\'binfo\'><td class=\'bottominfo\' colspan=\'2\'>'+rp_ge[$t.p.id].bottominfo+'</td></tr>';bt+='</tbody></table>';if(maxRows>0){var sd=[];$.each($(tbl)[0].rows,function(i,r){sd[i]=r;});sd.sort(function(a,b){if(a.rp>b.rp){return 1;}if(a.rp<b.rp){return-1;}return 0;});$.each(sd,function(index,row){$('tbody',tbl).append(row);});}p.gbox='#gbox_'+$.jgrid.jqID(gID);var cle=false;if(p.closeOnEscape===true){p.closeOnEscape=false;cle=true;}var tms=$('<div></div>').append(frm).append(bt);$.jgrid.createModal(IDs,tms,p,'#gview_'+$.jgrid.jqID($t.p.id),$('#gbox_'+$.jgrid.jqID($t.p.id))[0]);if(rtlb){$('#pData, #nData',frmtb+'_2').css('float','right');$('.EditButton',frmtb+'_2').css('text-align','left');}if(rp_ge[$t.p.id].topinfo){$('.tinfo',frmtb).show();}if(rp_ge[$t.p.id].bottominfo){$('.binfo',frmtb+'_2').show();}tms=null;bt=null;$('#'+$.jgrid.jqID(IDs.themodal)).keydown(function(e){var wkey=e.target;if($('#'+frmgr).data('disabled')===true){return false;}//??
if(rp_ge[$t.p.id].savekey[0]===true&&e.which==rp_ge[$t.p.id].savekey[1]){// save
if(wkey.tagName!='TEXTAREA'){$('#sData',frmtb+'_2').trigger('click');return false;}}if(e.which===27){if(!checkUpdates()){return false;}if(cle){$.jgrid.hideModal('#'+$.jgrid.jqID(IDs.themodal),{gb:p.gbox,jqm:p.jqModal,onClose:rp_ge[$t.p.id].onClose});}return false;}if(rp_ge[$t.p.id].navkeys[0]===true){if($('#id_g',frmtb).val()=='_empty'){return true;}if(e.which==rp_ge[$t.p.id].navkeys[1]){//up
$('#pData',frmtb+'_2').trigger('click');return false;}if(e.which==rp_ge[$t.p.id].navkeys[2]){//down
$('#nData',frmtb+'_2').trigger('click');return false;}}});if(p.checkOnUpdate){$('a.ui-jqdialog-titlebar-close span','#'+$.jgrid.jqID(IDs.themodal)).removeClass('jqmClose');$('a.ui-jqdialog-titlebar-close','#'+$.jgrid.jqID(IDs.themodal)).unbind('click').click(function(){if(!checkUpdates()){return false;}$.jgrid.hideModal('#'+$.jgrid.jqID(IDs.themodal),{gb:'#gbox_'+$.jgrid.jqID(gID),jqm:p.jqModal,onClose:rp_ge[$t.p.id].onClose});return false;});}p.saveicon=$.extend([true,'left','ui-icon-disk'],p.saveicon);p.closeicon=$.extend([true,'left','ui-icon-close'],p.closeicon);// beforeinitdata after creation of the form
if(p.saveicon[0]===true){$('#sData',frmtb+'_2').addClass(p.saveicon[1]=='right'?'fm-button-icon-right':'fm-button-icon-left').append('<span class=\'ui-icon '+p.saveicon[2]+'\'></span>');}if(p.closeicon[0]===true){$('#cData',frmtb+'_2').addClass(p.closeicon[1]=='right'?'fm-button-icon-right':'fm-button-icon-left').append('<span class=\'ui-icon '+p.closeicon[2]+'\'></span>');}if(rp_ge[$t.p.id].checkOnSubmit||rp_ge[$t.p.id].checkOnUpdate){bS='<a href=\'javascript:void(0)\' id=\'sNew\' class=\'fm-button ui-state-default ui-corner-all\' style=\'z-index:1002\'>'+p.bYes+'</a>';bN='<a href=\'javascript:void(0)\' id=\'nNew\' class=\'fm-button ui-state-default ui-corner-all\' style=\'z-index:1002\'>'+p.bNo+'</a>';bC='<a href=\'javascript:void(0)\' id=\'cNew\' class=\'fm-button ui-state-default ui-corner-all\' style=\'z-index:1002\'>'+p.bExit+'</a>';var zI=p.zIndex||999;zI++;$('<div class=\'ui-widget-overlay jqgrid-overlay confirm\' style=\'z-index:'+zI+';display:none;\'>&#160;'+'</div><div class=\'confirm ui-widget-content ui-jqconfirm\' style=\'z-index:'+(zI+1)+'\'>'+p.saveData+'<br/><br/>'+bS+bN+bC+'</div>').insertAfter('#'+frmgr);$('#sNew','#'+$.jgrid.jqID(IDs.themodal)).click(function(){postIt();$('#'+frmgr).data('disabled',false);$('.confirm','#'+$.jgrid.jqID(IDs.themodal)).hide();return false;});$('#nNew','#'+$.jgrid.jqID(IDs.themodal)).click(function(){$('.confirm','#'+$.jgrid.jqID(IDs.themodal)).hide();$('#'+frmgr).data('disabled',false);setTimeout(function(){$(':input','#'+frmgr)[0].focus();},0);return false;});$('#cNew','#'+$.jgrid.jqID(IDs.themodal)).click(function(){$('.confirm','#'+$.jgrid.jqID(IDs.themodal)).hide();$('#'+frmgr).data('disabled',false);$.jgrid.hideModal('#'+$.jgrid.jqID(IDs.themodal),{gb:'#gbox_'+$.jgrid.jqID(gID),jqm:p.jqModal,onClose:rp_ge[$t.p.id].onClose});return false;});}// here initform - only once
$($t).triggerHandler('jqGridAddEditInitializeForm',[$('#'+frmgr),frmoper]);if(onInitializeForm){onInitializeForm.call($t,$('#'+frmgr));}if(rowid=='_empty'||!rp_ge[$t.p.id].viewPagerButtons){$('#pData,#nData',frmtb+'_2').hide();}else{$('#pData,#nData',frmtb+'_2').show();}$($t).triggerHandler('jqGridAddEditBeforeShowForm',[$('#'+frmgr),frmoper]);if(onBeforeShow){onBeforeShow.call($t,$('#'+frmgr));}$('#'+$.jgrid.jqID(IDs.themodal)).data('onClose',rp_ge[$t.p.id].onClose);$.jgrid.viewModal('#'+$.jgrid.jqID(IDs.themodal),{gbox:'#gbox_'+$.jgrid.jqID(gID),jqm:p.jqModal,overlay:p.overlay,modal:p.modal});if(!closeovrl){$('.jqmOverlay').click(function(){if(!checkUpdates()){return false;}$.jgrid.hideModal('#'+$.jgrid.jqID(IDs.themodal),{gb:'#gbox_'+$.jgrid.jqID(gID),jqm:p.jqModal,onClose:rp_ge[$t.p.id].onClose});return false;});}$($t).triggerHandler('jqGridAddEditAfterShowForm',[$('#'+frmgr),frmoper]);if(onAfterShow){onAfterShow.call($t,$('#'+frmgr));}$('.fm-button','#'+$.jgrid.jqID(IDs.themodal)).hover(function(){$(this).addClass('ui-state-hover');},function(){$(this).removeClass('ui-state-hover');});$('#sData',frmtb+'_2').click(function(){postdata={};extpost={};$('#FormError',frmtb).hide();// all depend on ret array
//ret[0] - succes
//ret[1] - msg if not succes
//ret[2] - the id  that will be set if reload after submit false
getFormData();if(postdata[$t.p.id+'_id']=='_empty'){postIt();}else if(p.checkOnSubmit===true){newData=$.extend({},postdata,extpost);diff=compareData(newData,rp_ge[$t.p.id]._savedData);if(diff){$('#'+frmgr).data('disabled',true);$('.confirm','#'+$.jgrid.jqID(IDs.themodal)).show();}else{postIt();}}else{postIt();}return false;});$('#cData',frmtb+'_2').click(function(){if(!checkUpdates()){return false;}$.jgrid.hideModal('#'+$.jgrid.jqID(IDs.themodal),{gb:'#gbox_'+$.jgrid.jqID(gID),jqm:p.jqModal,onClose:rp_ge[$t.p.id].onClose});return false;});$('#nData',frmtb+'_2').click(function(){if(!checkUpdates()){return false;}$('#FormError',frmtb).hide();var npos=getCurrPos();npos[0]=parseInt(npos[0],10);if(npos[0]!=-1&&npos[1][npos[0]+1]){$($t).triggerHandler('jqGridAddEditClickPgButtons',['next',$('#'+frmgr),npos[1][npos[0]]]);var nposret;if($.isFunction(p.onclickPgButtons)){nposret=p.onclickPgButtons.call($t,'next',$('#'+frmgr),npos[1][npos[0]]);if(nposret!==undefined&&nposret===false){return false;}}if($('#'+$.jgrid.jqID(npos[1][npos[0]+1])).hasClass('ui-state-disabled')){return false;}fillData(npos[1][npos[0]+1],$t,frmgr);$($t).jqGrid('setSelection',npos[1][npos[0]+1]);$($t).triggerHandler('jqGridAddEditAfterClickPgButtons',['next',$('#'+frmgr),npos[1][npos[0]]]);if($.isFunction(p.afterclickPgButtons)){p.afterclickPgButtons.call($t,'next',$('#'+frmgr),npos[1][npos[0]+1]);}updateNav(npos[0]+1,npos);}return false;});$('#pData',frmtb+'_2').click(function(){if(!checkUpdates()){return false;}$('#FormError',frmtb).hide();var ppos=getCurrPos();if(ppos[0]!=-1&&ppos[1][ppos[0]-1]){$($t).triggerHandler('jqGridAddEditClickPgButtons',['prev',$('#'+frmgr),ppos[1][ppos[0]]]);var pposret;if($.isFunction(p.onclickPgButtons)){pposret=p.onclickPgButtons.call($t,'prev',$('#'+frmgr),ppos[1][ppos[0]]);if(pposret!==undefined&&pposret===false){return false;}}if($('#'+$.jgrid.jqID(ppos[1][ppos[0]-1])).hasClass('ui-state-disabled')){return false;}fillData(ppos[1][ppos[0]-1],$t,frmgr);$($t).jqGrid('setSelection',ppos[1][ppos[0]-1]);$($t).triggerHandler('jqGridAddEditAfterClickPgButtons',['prev',$('#'+frmgr),ppos[1][ppos[0]]]);if($.isFunction(p.afterclickPgButtons)){p.afterclickPgButtons.call($t,'prev',$('#'+frmgr),ppos[1][ppos[0]-1]);}updateNav(ppos[0]-1,ppos);}return false;});}var posInit=getCurrPos();updateNav(posInit[0],posInit);});},viewGridRow:function viewGridRow(rowid,p){p=$.extend(true,{top:0,left:0,width:0,datawidth:'auto',height:'auto',dataheight:'auto',modal:false,overlay:30,drag:true,resize:true,jqModal:true,closeOnEscape:false,labelswidth:'30%',closeicon:[],navkeys:[false,38,40],onClose:null,beforeShowForm:null,beforeInitData:null,viewPagerButtons:true},$.jgrid.view,p||{});rp_ge[$(this)[0].p.id]=p;return this.each(function(){var $t=this;if(!$t.grid||!rowid){return;}var gID=$t.p.id,frmgr='ViewGrid_'+$.jgrid.jqID(gID),frmtb='ViewTbl_'+$.jgrid.jqID(gID),frmgr_id='ViewGrid_'+gID,frmtb_id='ViewTbl_'+gID,IDs={themodal:'viewmod'+gID,modalhead:'viewhd'+gID,modalcontent:'viewcnt'+gID,scrollelm:frmgr},onBeforeInit=$.isFunction(rp_ge[$t.p.id].beforeInitData)?rp_ge[$t.p.id].beforeInitData:false,showFrm=true,maxCols=1,maxRows=0;function focusaref(){//Sfari 3 issues
if(rp_ge[$t.p.id].closeOnEscape===true||rp_ge[$t.p.id].navkeys[0]===true){setTimeout(function(){$('.ui-jqdialog-titlebar-close','#'+$.jgrid.jqID(IDs.modalhead)).focus();},0);}}function createData(rowid,obj,tb,maxcols){var nm,hc,trdata,cnt=0,tmp,dc,retpos=[],ind=false,i,tdtmpl='<td class=\'CaptionTD form-view-label ui-widget-content\' width=\''+p.labelswidth+'\'>&#160;</td><td class=\'DataTD form-view-data ui-helper-reset ui-widget-content\'>&#160;</td>',tmpl='',tdtmpl2='<td class=\'CaptionTD form-view-label ui-widget-content\'>&#160;</td><td class=\'DataTD form-view-data ui-widget-content\'>&#160;</td>',fmtnum=['integer','number','currency'],max1=0,max2=0,maxw,setme,viewfld;for(i=1;i<=maxcols;i++){tmpl+=i==1?tdtmpl:tdtmpl2;}// find max number align rigth with property formatter
$(obj.p.colModel).each(function(){if(this.editrules&&this.editrules.edithidden===true){hc=false;}else{hc=this.hidden===true?true:false;}if(!hc&&this.align==='right'){if(this.formatter&&$.inArray(this.formatter,fmtnum)!==-1){max1=Math.max(max1,parseInt(this.width,10));}else{max2=Math.max(max2,parseInt(this.width,10));}}});maxw=max1!==0?max1:max2!==0?max2:0;ind=$(obj).jqGrid('getInd',rowid);$(obj.p.colModel).each(function(i){nm=this.name;setme=false;// hidden fields are included in the form
if(this.editrules&&this.editrules.edithidden===true){hc=false;}else{hc=this.hidden===true?true:false;}dc=hc?'style=\'display:none\'':'';viewfld=typeof this.viewable!=='boolean'?true:this.viewable;if(nm!=='cb'&&nm!=='subgrid'&&nm!=='rn'&&viewfld){if(ind===false){tmp='';}else{if(nm==obj.p.ExpandColumn&&obj.p.treeGrid===true){tmp=$('td:eq('+i+')',obj.rows[ind]).text();}else{tmp=$('td:eq('+i+')',obj.rows[ind]).html();}}setme=this.align==='right'&&maxw!==0?true:false;var frmopt=$.extend({},{rowabove:false,rowcontent:''},this.formoptions||{}),rp=parseInt(frmopt.rowpos,10)||cnt+1,cp=parseInt((parseInt(frmopt.colpos,10)||1)*2,10);if(frmopt.rowabove){var newdata=$('<tr><td class=\'contentinfo\' colspan=\''+maxcols*2+'\'>'+frmopt.rowcontent+'</td></tr>');$(tb).append(newdata);newdata[0].rp=rp;}trdata=$(tb).find('tr[rowpos='+rp+']');if(trdata.length===0){trdata=$('<tr '+dc+' rowpos=\''+rp+'\'></tr>').addClass('FormData').attr('id','trv_'+nm);$(trdata).append(tmpl);$(tb).append(trdata);trdata[0].rp=rp;}$('td:eq('+(cp-2)+')',trdata[0]).html('<b>'+(frmopt.label===undefined?obj.p.colNames[i]:frmopt.label)+'</b>');$('td:eq('+(cp-1)+')',trdata[0]).append('<span>'+tmp+'</span>').attr('id','v_'+nm);if(setme){$('td:eq('+(cp-1)+') span',trdata[0]).css({'text-align':'right',width:maxw+'px'});}retpos[cnt]=i;cnt++;}});if(cnt>0){var idrow=$('<tr class=\'FormData\' style=\'display:none\'><td class=\'CaptionTD\'></td><td colspan=\''+(maxcols*2-1)+'\' class=\'DataTD\'><input class=\'FormElement\' id=\'id_g\' type=\'text\' name=\'id\' value=\''+rowid+'\'/></td></tr>');idrow[0].rp=cnt+99;$(tb).append(idrow);}return retpos;}function fillData(rowid,obj){var nm,hc,cnt=0,tmp,opt,trv;trv=$(obj).jqGrid('getInd',rowid,true);if(!trv){return;}$('td',trv).each(function(i){nm=obj.p.colModel[i].name;// hidden fields are included in the form
if(obj.p.colModel[i].editrules&&obj.p.colModel[i].editrules.edithidden===true){hc=false;}else{hc=obj.p.colModel[i].hidden===true?true:false;}if(nm!=='cb'&&nm!=='subgrid'&&nm!=='rn'){if(nm==obj.p.ExpandColumn&&obj.p.treeGrid===true){tmp=$(this).text();}else{tmp=$(this).html();}opt=$.extend({},obj.p.colModel[i].editoptions||{});nm=$.jgrid.jqID('v_'+nm);$('#'+nm+' span','#'+frmtb).html(tmp);if(hc){$('#'+nm,'#'+frmtb).parents('tr:first').hide();}cnt++;}});if(cnt>0){$('#id_g','#'+frmtb).val(rowid);}}function updateNav(cr,posarr){var totr=posarr[1].length-1;if(cr===0){$('#pData','#'+frmtb+'_2').addClass('ui-state-disabled');}else if(posarr[1][cr-1]!==undefined&&$('#'+$.jgrid.jqID(posarr[1][cr-1])).hasClass('ui-state-disabled')){$('#pData',frmtb+'_2').addClass('ui-state-disabled');}else{$('#pData','#'+frmtb+'_2').removeClass('ui-state-disabled');}if(cr==totr){$('#nData','#'+frmtb+'_2').addClass('ui-state-disabled');}else if(posarr[1][cr+1]!==undefined&&$('#'+$.jgrid.jqID(posarr[1][cr+1])).hasClass('ui-state-disabled')){$('#nData',frmtb+'_2').addClass('ui-state-disabled');}else{$('#nData','#'+frmtb+'_2').removeClass('ui-state-disabled');}}function getCurrPos(){var rowsInGrid=$($t).jqGrid('getDataIDs'),selrow=$('#id_g','#'+frmtb).val(),pos=$.inArray(selrow,rowsInGrid);return[pos,rowsInGrid];}if($('#'+$.jgrid.jqID(IDs.themodal))[0]!==undefined){if(onBeforeInit){showFrm=onBeforeInit.call($t,$('#'+frmgr));if(showFrm===undefined){showFrm=true;}}if(showFrm===false){return;}$('.ui-jqdialog-title','#'+$.jgrid.jqID(IDs.modalhead)).html(p.caption);$('#FormError','#'+frmtb).hide();fillData(rowid,$t);if($.isFunction(rp_ge[$t.p.id].beforeShowForm)){rp_ge[$t.p.id].beforeShowForm.call($t,$('#'+frmgr));}$.jgrid.viewModal('#'+$.jgrid.jqID(IDs.themodal),{gbox:'#gbox_'+$.jgrid.jqID(gID),jqm:p.jqModal,jqM:false,overlay:p.overlay,modal:p.modal});focusaref();}else{var dh=isNaN(p.dataheight)?p.dataheight:p.dataheight+'px',dw=isNaN(p.datawidth)?p.datawidth:p.datawidth+'px',frm=$('<form name=\'FormPost\' id=\''+frmgr_id+'\' class=\'FormGrid\' style=\'width:'+dw+';overflow:auto;position:relative;height:'+dh+';\'></form>'),tbl=$('<table id=\''+frmtb_id+'\' class=\'EditTable\' cellspacing=\'1\' cellpadding=\'2\' border=\'0\' style=\'table-layout:fixed\'><tbody></tbody></table>');if(onBeforeInit){showFrm=onBeforeInit.call($t,$('#'+frmgr));if(showFrm===undefined){showFrm=true;}}if(showFrm===false){return;}$($t.p.colModel).each(function(){var fmto=this.formoptions;maxCols=Math.max(maxCols,fmto?fmto.colpos||0:0);maxRows=Math.max(maxRows,fmto?fmto.rowpos||0:0);});// set the id.
$(frm).append(tbl);createData(rowid,$t,tbl,maxCols);var rtlb=$t.p.direction=='rtl'?true:false,bp=rtlb?'nData':'pData',bn=rtlb?'pData':'nData',// buttons at footer
bP='<a href=\'javascript:void(0)\' id=\''+bp+'\' class=\'fm-button ui-state-default ui-corner-left\'><span class=\'ui-icon ui-icon-triangle-1-w\'></span></a>',bN='<a href=\'javascript:void(0)\' id=\''+bn+'\' class=\'fm-button ui-state-default ui-corner-right\'><span class=\'ui-icon ui-icon-triangle-1-e\'></span></a>',bC='<a href=\'javascript:void(0)\' id=\'cData\' class=\'fm-button ui-state-default ui-corner-all\'>'+p.bClose+'</a>';if(maxRows>0){var sd=[];$.each($(tbl)[0].rows,function(i,r){sd[i]=r;});sd.sort(function(a,b){if(a.rp>b.rp){return 1;}if(a.rp<b.rp){return-1;}return 0;});$.each(sd,function(index,row){$('tbody',tbl).append(row);});}p.gbox='#gbox_'+$.jgrid.jqID(gID);var bt=$('<div></div>').append(frm).append('<table border=\'0\' class=\'EditTable\' id=\''+frmtb+'_2\'><tbody><tr id=\'Act_Buttons\'><td class=\'navButton\' width=\''+p.labelswidth+'\'>'+(rtlb?bN+bP:bP+bN)+'</td><td class=\'EditButton\'>'+bC+'</td></tr></tbody></table>');$.jgrid.createModal(IDs,bt,p,'#gview_'+$.jgrid.jqID($t.p.id),$('#gview_'+$.jgrid.jqID($t.p.id))[0]);if(rtlb){$('#pData, #nData','#'+frmtb+'_2').css('float','right');$('.EditButton','#'+frmtb+'_2').css('text-align','left');}if(!p.viewPagerButtons){$('#pData, #nData','#'+frmtb+'_2').hide();}bt=null;$('#'+IDs.themodal).keydown(function(e){if(e.which===27){if(rp_ge[$t.p.id].closeOnEscape){$.jgrid.hideModal('#'+$.jgrid.jqID(IDs.themodal),{gb:p.gbox,jqm:p.jqModal,onClose:p.onClose});}return false;}if(p.navkeys[0]===true){if(e.which===p.navkeys[1]){//up
$('#pData','#'+frmtb+'_2').trigger('click');return false;}if(e.which===p.navkeys[2]){//down
$('#nData','#'+frmtb+'_2').trigger('click');return false;}}});p.closeicon=$.extend([true,'left','ui-icon-close'],p.closeicon);if(p.closeicon[0]===true){$('#cData','#'+frmtb+'_2').addClass(p.closeicon[1]=='right'?'fm-button-icon-right':'fm-button-icon-left').append('<span class=\'ui-icon '+p.closeicon[2]+'\'></span>');}if($.isFunction(p.beforeShowForm)){p.beforeShowForm.call($t,$('#'+frmgr));}$.jgrid.viewModal('#'+$.jgrid.jqID(IDs.themodal),{gbox:'#gbox_'+$.jgrid.jqID(gID),jqm:p.jqModal,overlay:p.overlay,modal:p.modal});$('.fm-button:not(.ui-state-disabled)','#'+frmtb+'_2').hover(function(){$(this).addClass('ui-state-hover');},function(){$(this).removeClass('ui-state-hover');});focusaref();$('#cData','#'+frmtb+'_2').click(function(){$.jgrid.hideModal('#'+$.jgrid.jqID(IDs.themodal),{gb:'#gbox_'+$.jgrid.jqID(gID),jqm:p.jqModal,onClose:p.onClose});return false;});$('#nData','#'+frmtb+'_2').click(function(){$('#FormError','#'+frmtb).hide();var npos=getCurrPos();npos[0]=parseInt(npos[0],10);if(npos[0]!=-1&&npos[1][npos[0]+1]){if($.isFunction(p.onclickPgButtons)){p.onclickPgButtons.call($t,'next',$('#'+frmgr),npos[1][npos[0]]);}fillData(npos[1][npos[0]+1],$t);$($t).jqGrid('setSelection',npos[1][npos[0]+1]);if($.isFunction(p.afterclickPgButtons)){p.afterclickPgButtons.call($t,'next',$('#'+frmgr),npos[1][npos[0]+1]);}updateNav(npos[0]+1,npos);}focusaref();return false;});$('#pData','#'+frmtb+'_2').click(function(){$('#FormError','#'+frmtb).hide();var ppos=getCurrPos();if(ppos[0]!=-1&&ppos[1][ppos[0]-1]){if($.isFunction(p.onclickPgButtons)){p.onclickPgButtons.call($t,'prev',$('#'+frmgr),ppos[1][ppos[0]]);}fillData(ppos[1][ppos[0]-1],$t);$($t).jqGrid('setSelection',ppos[1][ppos[0]-1]);if($.isFunction(p.afterclickPgButtons)){p.afterclickPgButtons.call($t,'prev',$('#'+frmgr),ppos[1][ppos[0]-1]);}updateNav(ppos[0]-1,ppos);}focusaref();return false;});}var posInit=getCurrPos();updateNav(posInit[0],posInit);});},delGridRow:function delGridRow(rowids,p){p=$.extend(true,{top:0,left:0,width:240,height:'auto',dataheight:'auto',modal:false,overlay:30,drag:true,resize:true,url:'',mtype:'POST',reloadAfterSubmit:true,beforeShowForm:null,beforeInitData:null,afterShowForm:null,beforeSubmit:null,onclickSubmit:null,afterSubmit:null,jqModal:true,closeOnEscape:false,delData:{},delicon:[],cancelicon:[],onClose:null,ajaxDelOptions:{},processing:false,serializeDelData:null,useDataProxy:false},$.jgrid.del,p||{});rp_ge[$(this)[0].p.id]=p;return this.each(function(){var $t=this;if(!$t.grid){return;}if(!rowids){return;}var onBeforeShow=$.isFunction(rp_ge[$t.p.id].beforeShowForm),onAfterShow=$.isFunction(rp_ge[$t.p.id].afterShowForm),onBeforeInit=$.isFunction(rp_ge[$t.p.id].beforeInitData)?rp_ge[$t.p.id].beforeInitData:false,gID=$t.p.id,onCS={},showFrm=true,dtbl='DelTbl_'+$.jgrid.jqID(gID),postd,idname,opers,oper,dtbl_id='DelTbl_'+gID,IDs={themodal:'delmod'+gID,modalhead:'delhd'+gID,modalcontent:'delcnt'+gID,scrollelm:dtbl};if($.isArray(rowids)){rowids=rowids.join();}if($('#'+$.jgrid.jqID(IDs.themodal))[0]!==undefined){if(onBeforeInit){showFrm=onBeforeInit.call($t,$('#'+dtbl));if(showFrm===undefined){showFrm=true;}}if(showFrm===false){return;}$('#DelData>td','#'+dtbl).text(rowids);$('#DelError','#'+dtbl).hide();if(rp_ge[$t.p.id].processing===true){rp_ge[$t.p.id].processing=false;$('#dData','#'+dtbl).removeClass('ui-state-active');}if(onBeforeShow){rp_ge[$t.p.id].beforeShowForm.call($t,$('#'+dtbl));}$.jgrid.viewModal('#'+$.jgrid.jqID(IDs.themodal),{gbox:'#gbox_'+$.jgrid.jqID(gID),jqm:rp_ge[$t.p.id].jqModal,jqM:false,overlay:rp_ge[$t.p.id].overlay,modal:rp_ge[$t.p.id].modal});if(onAfterShow){rp_ge[$t.p.id].afterShowForm.call($t,$('#'+dtbl));}}else{var dh=isNaN(rp_ge[$t.p.id].dataheight)?rp_ge[$t.p.id].dataheight:rp_ge[$t.p.id].dataheight+'px',dw=isNaN(p.datawidth)?p.datawidth:p.datawidth+'px',tbl='<div id=\''+dtbl_id+'\' class=\'formdata\' style=\'width:'+dw+';overflow:auto;position:relative;height:'+dh+';\'>';tbl+='<table class=\'DelTable\'><tbody>';// error data
tbl+='<tr id=\'DelError\' style=\'display:none\'><td class=\'ui-state-error\'></td></tr>';tbl+='<tr id=\'DelData\' style=\'display:none\'><td >'+rowids+'</td></tr>';tbl+='<tr><td class="delmsg" style="white-space:pre;">'+rp_ge[$t.p.id].msg+'</td></tr><tr><td >&#160;</td></tr>';// buttons at footer
tbl+='</tbody></table></div>';var bS='<a href=\'javascript:void(0)\' id=\'dData\' class=\'fm-button ui-state-default ui-corner-all\'>'+p.bSubmit+'</a>',bC='<a href=\'javascript:void(0)\' id=\'eData\' class=\'fm-button ui-state-default ui-corner-all\'>'+p.bCancel+'</a>';tbl+='<table cellspacing=\'0\' cellpadding=\'0\' border=\'0\' class=\'EditTable\' id=\''+dtbl+'_2\'><tbody><tr><td><hr class=\'ui-widget-content\' style=\'margin:1px\'/></td></tr><tr><td class=\'DelButton EditButton\'>'+bS+'&#160;'+bC+'</td></tr></tbody></table>';p.gbox='#gbox_'+$.jgrid.jqID(gID);$.jgrid.createModal(IDs,tbl,p,'#gview_'+$.jgrid.jqID($t.p.id),$('#gview_'+$.jgrid.jqID($t.p.id))[0]);if(onBeforeInit){showFrm=onBeforeInit.call($t,$('#'+dtbl));if(showFrm===undefined){showFrm=true;}}if(showFrm===false){return;}$('.fm-button','#'+dtbl+'_2').hover(function(){$(this).addClass('ui-state-hover');},function(){$(this).removeClass('ui-state-hover');});p.delicon=$.extend([true,'left','ui-icon-scissors'],rp_ge[$t.p.id].delicon);p.cancelicon=$.extend([true,'left','ui-icon-cancel'],rp_ge[$t.p.id].cancelicon);if(p.delicon[0]===true){$('#dData','#'+dtbl+'_2').addClass(p.delicon[1]=='right'?'fm-button-icon-right':'fm-button-icon-left').append('<span class=\'ui-icon '+p.delicon[2]+'\'></span>');}if(p.cancelicon[0]===true){$('#eData','#'+dtbl+'_2').addClass(p.cancelicon[1]=='right'?'fm-button-icon-right':'fm-button-icon-left').append('<span class=\'ui-icon '+p.cancelicon[2]+'\'></span>');}$('#dData','#'+dtbl+'_2').click(function(){var ret=[true,''],pk,postdata=$('#DelData>td','#'+dtbl).text();//the pair is name=val1,val2,...
onCS={};if($.isFunction(rp_ge[$t.p.id].onclickSubmit)){onCS=rp_ge[$t.p.id].onclickSubmit.call($t,rp_ge[$t.p.id],postdata)||{};}if($.isFunction(rp_ge[$t.p.id].beforeSubmit)){ret=rp_ge[$t.p.id].beforeSubmit.call($t,postdata);}if(ret[0]&&!rp_ge[$t.p.id].processing){rp_ge[$t.p.id].processing=true;opers=$t.p.prmNames;postd=$.extend({},rp_ge[$t.p.id].delData,onCS);oper=opers.oper;postd[oper]=opers.deloper;idname=opers.id;postdata=String(postdata).split(',');if(!postdata.length){return false;}for(pk in postdata){if(postdata.hasOwnProperty(pk)){postdata[pk]=$.jgrid.stripPref($t.p.idPrefix,postdata[pk]);}}postd[idname]=postdata.join();$(this).addClass('ui-state-active');var ajaxOptions=$.extend({url:rp_ge[$t.p.id].url||$($t).jqGrid('getGridParam','editurl'),type:rp_ge[$t.p.id].mtype,data:$.isFunction(rp_ge[$t.p.id].serializeDelData)?rp_ge[$t.p.id].serializeDelData.call($t,postd):postd,complete:function complete(data,status){var i;if(status!='success'){ret[0]=false;if($.isFunction(rp_ge[$t.p.id].errorTextFormat)){ret[1]=rp_ge[$t.p.id].errorTextFormat.call($t,data);}else{ret[1]=status+' Status: \''+data.statusText+'\'. Error code: '+data.status;}}else{// data is posted successful
// execute aftersubmit with the returned data from server
if($.isFunction(rp_ge[$t.p.id].afterSubmit)){ret=rp_ge[$t.p.id].afterSubmit.call($t,data,postd);}}if(ret[0]===false){$('#DelError>td','#'+dtbl).html(ret[1]);$('#DelError','#'+dtbl).show();}else{if(rp_ge[$t.p.id].reloadAfterSubmit&&$t.p.datatype!='local'){$($t).trigger('reloadGrid');}else{if($t.p.treeGrid===true){try{$($t).jqGrid('delTreeNode',$t.p.idPrefix+postdata[0]);}catch(e){}}else{for(i=0;i<postdata.length;i++){$($t).jqGrid('delRowData',$t.p.idPrefix+postdata[i]);}}$t.p.selrow=null;$t.p.selarrrow=[];}if($.isFunction(rp_ge[$t.p.id].afterComplete)){setTimeout(function(){rp_ge[$t.p.id].afterComplete.call($t,data,postdata);},500);}}rp_ge[$t.p.id].processing=false;$('#dData','#'+dtbl+'_2').removeClass('ui-state-active');if(ret[0]){$.jgrid.hideModal('#'+$.jgrid.jqID(IDs.themodal),{gb:'#gbox_'+$.jgrid.jqID(gID),jqm:p.jqModal,onClose:rp_ge[$t.p.id].onClose});}}},$.jgrid.ajaxOptions,rp_ge[$t.p.id].ajaxDelOptions);if(!ajaxOptions.url&&!rp_ge[$t.p.id].useDataProxy){if($.isFunction($t.p.dataProxy)){rp_ge[$t.p.id].useDataProxy=true;}else{ret[0]=false;ret[1]+=' '+$.jgrid.errors.nourl;}}if(ret[0]){if(rp_ge[$t.p.id].useDataProxy){var dpret=$t.p.dataProxy.call($t,ajaxOptions,'del_'+$t.p.id);if(dpret===undefined){dpret=[true,''];}if(dpret[0]===false){ret[0]=false;ret[1]=dpret[1]||'Error deleting the selected row!';}else{$.jgrid.hideModal('#'+$.jgrid.jqID(IDs.themodal),{gb:'#gbox_'+$.jgrid.jqID(gID),jqm:p.jqModal,onClose:rp_ge[$t.p.id].onClose});}}else{$.ajax(ajaxOptions);}}}if(ret[0]===false){$('#DelError>td','#'+dtbl).html(ret[1]);$('#DelError','#'+dtbl).show();}return false;});$('#eData','#'+dtbl+'_2').click(function(){$.jgrid.hideModal('#'+$.jgrid.jqID(IDs.themodal),{gb:'#gbox_'+$.jgrid.jqID(gID),jqm:rp_ge[$t.p.id].jqModal,onClose:rp_ge[$t.p.id].onClose});return false;});if(onBeforeShow){rp_ge[$t.p.id].beforeShowForm.call($t,$('#'+dtbl));}$.jgrid.viewModal('#'+$.jgrid.jqID(IDs.themodal),{gbox:'#gbox_'+$.jgrid.jqID(gID),jqm:rp_ge[$t.p.id].jqModal,overlay:rp_ge[$t.p.id].overlay,modal:rp_ge[$t.p.id].modal});if(onAfterShow){rp_ge[$t.p.id].afterShowForm.call($t,$('#'+dtbl));}}if(rp_ge[$t.p.id].closeOnEscape===true){setTimeout(function(){$('.ui-jqdialog-titlebar-close','#'+$.jgrid.jqID(IDs.modalhead)).focus();},0);}});},navGrid:function navGrid(elem,o,pEdit,pAdd,pDel,pSearch,pView){o=$.extend({edit:true,editicon:'ui-icon-pencil',add:true,addicon:'ui-icon-plus',del:true,delicon:'ui-icon-trash',search:true,searchicon:'ui-icon-search',refresh:true,refreshicon:'ui-icon-refresh',refreshstate:'firstpage',view:false,viewicon:'ui-icon-document',position:'left',closeOnEscape:true,beforeRefresh:null,afterRefresh:null,cloneToTop:false,alertwidth:200,alertheight:'auto',alerttop:null,alertleft:null,alertzIndex:null},$.jgrid.nav,o||{});return this.each(function(){if(this.nav){return;}var alertIDs={themodal:'alertmod_'+this.p.id,modalhead:'alerthd_'+this.p.id,modalcontent:'alertcnt_'+this.p.id},$t=this,twd,tdw;if(!$t.grid||typeof elem!=='string'){return;}if($('#'+alertIDs.themodal)[0]===undefined){if(!o.alerttop&&!o.alertleft){if(window.innerWidth!==undefined){o.alertleft=window.innerWidth;o.alerttop=window.innerHeight;}else if(document.documentElement!==undefined&&document.documentElement.clientWidth!==undefined&&document.documentElement.clientWidth!==0){o.alertleft=document.documentElement.clientWidth;o.alerttop=document.documentElement.clientHeight;}else{o.alertleft=1024;o.alerttop=768;}o.alertleft=o.alertleft/2-parseInt(o.alertwidth,10)/2;o.alerttop=o.alerttop/2-25;}$.jgrid.createModal(alertIDs,'<div>'+o.alerttext+'</div><span tabindex=\'0\'><span tabindex=\'-1\' id=\'jqg_alrt\'></span></span>',{gbox:'#gbox_'+$.jgrid.jqID($t.p.id),jqModal:true,drag:true,resize:true,caption:o.alertcap,top:o.alerttop,left:o.alertleft,width:o.alertwidth,height:o.alertheight,closeOnEscape:o.closeOnEscape,zIndex:o.alertzIndex},'#gview_'+$.jgrid.jqID($t.p.id),$('#gbox_'+$.jgrid.jqID($t.p.id))[0],true);}var clone=1,i,onHoverIn=function onHoverIn(){if(!$(this).hasClass('ui-state-disabled')){$(this).addClass('ui-state-hover');}},onHoverOut=function onHoverOut(){$(this).removeClass('ui-state-hover');};if(o.cloneToTop&&$t.p.toppager){clone=2;}for(i=0;i<clone;i++){var tbd,navtbl=$('<table cellspacing=\'0\' cellpadding=\'0\' border=\'0\' class=\'ui-pg-table navtable\' style=\'float:left;table-layout:auto;\'><tbody><tr></tr></tbody></table>'),sep='<td class=\'ui-pg-button ui-state-disabled\' style=\'width:4px;\'><span class=\'ui-separator\'></span></td>',pgid,elemids;if(i===0){pgid=elem;elemids=$t.p.id;if(pgid==$t.p.toppager){elemids+='_top';clone=1;}}else{pgid=$t.p.toppager;elemids=$t.p.id+'_top';}if($t.p.direction=='rtl'){$(navtbl).attr('dir','rtl').css('float','right');}if(o.add){pAdd=pAdd||{};tbd=$('<td class=\'ui-pg-button ui-corner-all\'></td>');$(tbd).append('<div class=\'ui-pg-div\'><span class=\'ui-icon '+o.addicon+'\'></span>'+o.addtext+'</div>');$('tr',navtbl).append(tbd);$(tbd,navtbl).attr({'title':o.addtitle||'',id:pAdd.id||'add_'+elemids}).click(function(){if(!$(this).hasClass('ui-state-disabled')){if($.isFunction(o.addfunc)){o.addfunc.call($t);}else{$($t).jqGrid('editGridRow','new',pAdd);}}return false;}).hover(onHoverIn,onHoverOut);tbd=null;}if(o.edit){tbd=$('<td class=\'ui-pg-button ui-corner-all\'></td>');pEdit=pEdit||{};$(tbd).append('<div class=\'ui-pg-div\'><span class=\'ui-icon '+o.editicon+'\'></span>'+o.edittext+'</div>');$('tr',navtbl).append(tbd);$(tbd,navtbl).attr({'title':o.edittitle||'',id:pEdit.id||'edit_'+elemids}).click(function(){if(!$(this).hasClass('ui-state-disabled')){var sr=$t.p.selrow;if(sr){if($.isFunction(o.editfunc)){o.editfunc.call($t,sr);}else{$($t).jqGrid('editGridRow',sr,pEdit);}}else{$.jgrid.viewModal('#'+alertIDs.themodal,{gbox:'#gbox_'+$.jgrid.jqID($t.p.id),jqm:true});$('#jqg_alrt').focus();}}return false;}).hover(onHoverIn,onHoverOut);tbd=null;}if(o.view){tbd=$('<td class=\'ui-pg-button ui-corner-all\'></td>');pView=pView||{};$(tbd).append('<div class=\'ui-pg-div\'><span class=\'ui-icon '+o.viewicon+'\'></span>'+o.viewtext+'</div>');$('tr',navtbl).append(tbd);$(tbd,navtbl).attr({'title':o.viewtitle||'',id:pView.id||'view_'+elemids}).click(function(){if(!$(this).hasClass('ui-state-disabled')){var sr=$t.p.selrow;if(sr){if($.isFunction(o.viewfunc)){o.viewfunc.call($t,sr);}else{$($t).jqGrid('viewGridRow',sr,pView);}}else{$.jgrid.viewModal('#'+alertIDs.themodal,{gbox:'#gbox_'+$.jgrid.jqID($t.p.id),jqm:true});$('#jqg_alrt').focus();}}return false;}).hover(onHoverIn,onHoverOut);tbd=null;}if(o.del){tbd=$('<td class=\'ui-pg-button ui-corner-all\'></td>');pDel=pDel||{};$(tbd).append('<div class=\'ui-pg-div\'><span class=\'ui-icon '+o.delicon+'\'></span>'+o.deltext+'</div>');$('tr',navtbl).append(tbd);$(tbd,navtbl).attr({'title':o.deltitle||'',id:pDel.id||'del_'+elemids}).click(function(){if(!$(this).hasClass('ui-state-disabled')){var dr;if($t.p.multiselect){dr=$t.p.selarrrow;if(dr.length===0){dr=null;}}else{dr=$t.p.selrow;}if(dr){if($.isFunction(o.delfunc)){o.delfunc.call($t,dr);}else{$($t).jqGrid('delGridRow',dr,pDel);}}else{$.jgrid.viewModal('#'+alertIDs.themodal,{gbox:'#gbox_'+$.jgrid.jqID($t.p.id),jqm:true});$('#jqg_alrt').focus();}}return false;}).hover(onHoverIn,onHoverOut);tbd=null;}if(o.add||o.edit||o.del||o.view){$('tr',navtbl).append(sep);}if(o.search){tbd=$('<td class=\'ui-pg-button ui-corner-all\'></td>');pSearch=pSearch||{};$(tbd).append('<div class=\'ui-pg-div\'><span class=\'ui-icon '+o.searchicon+'\'></span>'+o.searchtext+'</div>');$('tr',navtbl).append(tbd);$(tbd,navtbl).attr({'title':o.searchtitle||'',id:pSearch.id||'search_'+elemids}).click(function(){if(!$(this).hasClass('ui-state-disabled')){if($.isFunction(o.searchfunc)){o.searchfunc.call($t,pSearch);}else{$($t).jqGrid('searchGrid',pSearch);}}return false;}).hover(onHoverIn,onHoverOut);if(pSearch.showOnLoad&&pSearch.showOnLoad===true){$(tbd,navtbl).click();}tbd=null;}if(o.refresh){tbd=$('<td class=\'ui-pg-button ui-corner-all\'></td>');$(tbd).append('<div class=\'ui-pg-div\'><span class=\'ui-icon '+o.refreshicon+'\'></span>'+o.refreshtext+'</div>');$('tr',navtbl).append(tbd);$(tbd,navtbl).attr({'title':o.refreshtitle||'',id:'refresh_'+elemids}).click(function(){if(!$(this).hasClass('ui-state-disabled')){if($.isFunction(o.beforeRefresh)){o.beforeRefresh.call($t);}$t.p.search=false;try{var gID=$t.p.id;$t.p.postData.filters='';$('#fbox_'+$.jgrid.jqID(gID)).jqFilter('resetFilter');if($.isFunction($t.clearToolbar)){$t.clearToolbar.call($t,false);}}catch(e){}switch(o.refreshstate){case'firstpage':$($t).trigger('reloadGrid',[{page:1}]);break;case'current':$($t).trigger('reloadGrid',[{current:true}]);break;}if($.isFunction(o.afterRefresh)){o.afterRefresh.call($t);}}return false;}).hover(onHoverIn,onHoverOut);tbd=null;}tdw=$('.ui-jqgrid').css('font-size')||'11px';$('body').append('<div id=\'testpg2\' class=\'ui-jqgrid ui-widget ui-widget-content\' style=\'font-size:'+tdw+';visibility:hidden;\' ></div>');twd=$(navtbl).clone().appendTo('#testpg2').width();$('#testpg2').remove();$(pgid+'_'+o.position,pgid).append(navtbl);if($t.p._nvtd){if(twd>$t.p._nvtd[0]){$(pgid+'_'+o.position,pgid).width(twd);$t.p._nvtd[0]=twd;}$t.p._nvtd[1]=twd;}tdw=null;twd=null;navtbl=null;this.nav=true;}});},navButtonAdd:function navButtonAdd(elem,p){p=$.extend({caption:'newButton',title:'',buttonicon:'ui-icon-newwin',onClickButton:null,position:'last',cursor:'pointer'},p||{});return this.each(function(){if(!this.grid){return;}if(typeof elem==='string'&&elem.indexOf('#')!==0){elem='#'+$.jgrid.jqID(elem);}var findnav=$('.navtable',elem)[0],$t=this;if(findnav){if(p.id&&$('#'+$.jgrid.jqID(p.id),findnav)[0]!==undefined){return;}var tbd=$('<td></td>');if(p.buttonicon.toString().toUpperCase()=='NONE'){$(tbd).addClass('ui-pg-button ui-corner-all').append('<div class=\'ui-pg-div\'>'+p.caption+'</div>');}else{$(tbd).addClass('ui-pg-button ui-corner-all').append('<div class=\'ui-pg-div\'><span class=\'ui-icon '+p.buttonicon+'\'></span>'+p.caption+'</div>');}if(p.id){$(tbd).attr('id',p.id);}if(p.position=='first'){if(findnav.rows[0].cells.length===0){$('tr',findnav).append(tbd);}else{$('tr td:eq(0)',findnav).before(tbd);}}else{$('tr',findnav).append(tbd);}$(tbd,findnav).attr('title',p.title||'').click(function(e){if(!$(this).hasClass('ui-state-disabled')){if($.isFunction(p.onClickButton)){p.onClickButton.call($t,e);}}return false;}).hover(function(){if(!$(this).hasClass('ui-state-disabled')){$(this).addClass('ui-state-hover');}},function(){$(this).removeClass('ui-state-hover');});}});},navSeparatorAdd:function navSeparatorAdd(elem,p){p=$.extend({sepclass:'ui-separator',sepcontent:'',position:'last'},p||{});return this.each(function(){if(!this.grid){return;}if(typeof elem==='string'&&elem.indexOf('#')!==0){elem='#'+$.jgrid.jqID(elem);}var findnav=$('.navtable',elem)[0];if(findnav){var sep='<td class=\'ui-pg-button ui-state-disabled\' style=\'width:4px;\'><span class=\''+p.sepclass+'\'></span>'+p.sepcontent+'</td>';if(p.position==='first'){if(findnav.rows[0].cells.length===0){$('tr',findnav).append(sep);}else{$('tr td:eq(0)',findnav).before(sep);}}else{$('tr',findnav).append(sep);}}});},GridToForm:function GridToForm(rowid,formid){return this.each(function(){var $t=this,i;if(!$t.grid){return;}var rowdata=$($t).jqGrid('getRowData',rowid);if(rowdata){for(i in rowdata){if(rowdata.hasOwnProperty(i)){if($('[name='+$.jgrid.jqID(i)+']',formid).is('input:radio')||$('[name='+$.jgrid.jqID(i)+']',formid).is('input:checkbox')){$('[name='+$.jgrid.jqID(i)+']',formid).each(function(){if($(this).val()==rowdata[i]){$(this)[$t.p.useProp?'prop':'attr']('checked',true);}else{$(this)[$t.p.useProp?'prop':'attr']('checked',false);}});}else{// this is very slow on big table and form.
$('[name='+$.jgrid.jqID(i)+']',formid).val(rowdata[i]);}}}}});},FormToGrid:function FormToGrid(rowid,formid,mode,position){return this.each(function(){var $t=this;if(!$t.grid){return;}if(!mode){mode='set';}if(!position){position='first';}var fields=$(formid).serializeArray();var griddata={};$.each(fields,function(i,field){griddata[field.name]=field.value;});if(mode=='add'){$($t).jqGrid('addRowData',rowid,griddata,position);}else if(mode=='set'){$($t).jqGrid('setRowData',rowid,griddata);}});}});})(jQuery);/*jshint eqeqeq:false, eqnull:true, devel:true *//*global jQuery */(function($){/**
 * jqGrid extension for manipulating Grid Data
 * Tony Tomov tony@trirand.com
 * http://trirand.com/blog/
 * Dual licensed under the MIT and GPL licenses:
 * http://www.opensource.org/licenses/mit-license.php
 * http://www.gnu.org/licenses/gpl-2.0.html
**/'use strict';$.jgrid.inlineEdit=$.jgrid.inlineEdit||{};$.jgrid.extend({//Editing
editRow:function editRow(rowid,keys,oneditfunc,successfunc,url,extraparam,aftersavefunc,errorfunc,afterrestorefunc){// Compatible mode old versions
var o={},args=$.makeArray(arguments).slice(1);if($.type(args[0])==='object'){o=args[0];}else{if(keys!==undefined){o.keys=keys;}if($.isFunction(oneditfunc)){o.oneditfunc=oneditfunc;}if($.isFunction(successfunc)){o.successfunc=successfunc;}if(url!==undefined){o.url=url;}if(extraparam!==undefined){o.extraparam=extraparam;}if($.isFunction(aftersavefunc)){o.aftersavefunc=aftersavefunc;}if($.isFunction(errorfunc)){o.errorfunc=errorfunc;}if($.isFunction(afterrestorefunc)){o.afterrestorefunc=afterrestorefunc;}// last two not as param, but as object (sorry)
//if (restoreAfterError !== undefined) { o.restoreAfterError = restoreAfterError; }
//if (mtype !== undefined) { o.mtype = mtype || "POST"; }
}o=$.extend(true,{keys:false,oneditfunc:null,successfunc:null,url:null,extraparam:{},aftersavefunc:null,errorfunc:null,afterrestorefunc:null,restoreAfterError:true,mtype:'POST'},$.jgrid.inlineEdit,o);// End compatible
return this.each(function(){var $t=this,nm,tmp,editable,cnt=0,focus=null,svr={},ind,cm;if(!$t.grid){return;}ind=$($t).jqGrid('getInd',rowid,true);if(ind===false){return;}editable=$(ind).attr('editable')||'0';if(editable=='0'&&!$(ind).hasClass('not-editable-row')){cm=$t.p.colModel;$('td[role="gridcell"]',ind).each(function(i){nm=cm[i].name;var treeg=$t.p.treeGrid===true&&nm==$t.p.ExpandColumn;if(treeg){tmp=$('span:first',this).html();}else{try{tmp=$.unformat.call($t,this,{rowId:rowid,colModel:cm[i]},i);}catch(_){tmp=cm[i].edittype&&cm[i].edittype=='textarea'?$(this).text():$(this).html();}}if(nm!='cb'&&nm!='subgrid'&&nm!='rn'){if($t.p.autoencode){tmp=$.jgrid.htmlDecode(tmp);}svr[nm]=tmp;if(cm[i].editable===true){if(focus===null){focus=i;}if(treeg){$('span:first',this).html('');}else{$(this).html('');}var opt=$.extend({},cm[i].editoptions||{},{id:rowid+'_'+nm,name:nm});if(!cm[i].edittype){cm[i].edittype='text';}if(tmp=='&nbsp;'||tmp=='&#160;'||tmp.length==1&&tmp.charCodeAt(0)==160){tmp='';}var elc=$.jgrid.createEl.call($t,cm[i].edittype,opt,tmp,true,$.extend({},$.jgrid.ajaxOptions,$t.p.ajaxSelectOptions||{}));$(elc).addClass('editable');if(treeg){$('span:first',this).append(elc);}else{$(this).append(elc);}$.jgrid.bindEv(elc,opt,$t);//Again IE
if(cm[i].edittype=='select'&&cm[i].editoptions!==undefined&&cm[i].editoptions.multiple===true&&cm[i].editoptions.dataUrl===undefined&&$.jgrid.msie){$(elc).width($(elc).width());}cnt++;}}});if(cnt>0){svr.id=rowid;$t.p.savedRow.push(svr);$(ind).attr('editable','1');$('td:eq('+focus+') input',ind).focus();if(o.keys===true){$(ind).bind('keydown',function(e){if(e.keyCode===27){$($t).jqGrid('restoreRow',rowid,o.afterrestorefunc);if($t.p._inlinenav){try{$($t).jqGrid('showAddEditButtons');}catch(eer1){}}return false;}if(e.keyCode===13){var ta=e.target;if(ta.tagName=='TEXTAREA'){return true;}if($($t).jqGrid('saveRow',rowid,o)){if($t.p._inlinenav){try{$($t).jqGrid('showAddEditButtons');}catch(eer2){}}}return false;}});}$($t).triggerHandler('jqGridInlineEditRow',[rowid,o]);if($.isFunction(o.oneditfunc)){o.oneditfunc.call($t,rowid);}}}});},saveRow:function saveRow(rowid,successfunc,url,extraparam,aftersavefunc,errorfunc,afterrestorefunc){// Compatible mode old versions
var args=$.makeArray(arguments).slice(1),o={};if($.type(args[0])==='object'){o=args[0];}else{if($.isFunction(successfunc)){o.successfunc=successfunc;}if(url!==undefined){o.url=url;}if(extraparam!==undefined){o.extraparam=extraparam;}if($.isFunction(aftersavefunc)){o.aftersavefunc=aftersavefunc;}if($.isFunction(errorfunc)){o.errorfunc=errorfunc;}if($.isFunction(afterrestorefunc)){o.afterrestorefunc=afterrestorefunc;}}o=$.extend(true,{successfunc:null,url:null,extraparam:{},aftersavefunc:null,errorfunc:null,afterrestorefunc:null,restoreAfterError:true,mtype:'POST'},$.jgrid.inlineEdit,o);// End compatible
var success=false;var $t=this[0],nm,tmp={},tmp2={},tmp3={},editable,fr,cv,ind;if(!$t.grid){return success;}ind=$($t).jqGrid('getInd',rowid,true);if(ind===false){return success;}editable=$(ind).attr('editable');o.url=o.url||$t.p.editurl;if(editable==='1'){var cm;$('td[role="gridcell"]',ind).each(function(i){cm=$t.p.colModel[i];nm=cm.name;if(nm!='cb'&&nm!='subgrid'&&cm.editable===true&&nm!='rn'&&!$(this).hasClass('not-editable-cell')){switch(cm.edittype){case'checkbox':var cbv=['Yes','No'];if(cm.editoptions){cbv=cm.editoptions.value.split(':');}tmp[nm]=$('input',this).is(':checked')?cbv[0]:cbv[1];break;case'text':case'password':case'textarea':case'button':tmp[nm]=$('input, textarea',this).val();break;case'select':if(!cm.editoptions.multiple){tmp[nm]=$('select option:selected',this).val();tmp2[nm]=$('select option:selected',this).text();}else{var sel=$('select',this),selectedText=[];tmp[nm]=$(sel).val();if(tmp[nm]){tmp[nm]=tmp[nm].join(',');}else{tmp[nm]='';}$('select option:selected',this).each(function(i,selected){selectedText[i]=$(selected).text();});tmp2[nm]=selectedText.join(',');}if(cm.formatter&&cm.formatter=='select'){tmp2={};}break;case'custom':try{if(cm.editoptions&&$.isFunction(cm.editoptions.custom_value)){tmp[nm]=cm.editoptions.custom_value.call($t,$('.customelement',this),'get');if(tmp[nm]===undefined){throw'e2';}}else{throw'e1';}}catch(e){if(e=='e1'){$.jgrid.info_dialog($.jgrid.errors.errcap,'function \'custom_value\' '+$.jgrid.edit.msg.nodefined,$.jgrid.edit.bClose);}if(e=='e2'){$.jgrid.info_dialog($.jgrid.errors.errcap,'function \'custom_value\' '+$.jgrid.edit.msg.novalue,$.jgrid.edit.bClose);}else{$.jgrid.info_dialog($.jgrid.errors.errcap,e.message,$.jgrid.edit.bClose);}}break;}cv=$.jgrid.checkValues(tmp[nm],i,$t);if(cv[0]===false){cv[1]=tmp[nm]+' '+cv[1];return false;}if($t.p.autoencode){tmp[nm]=$.jgrid.htmlEncode(tmp[nm]);}if(o.url!=='clientArray'&&cm.editoptions&&cm.editoptions.NullIfEmpty===true){if(tmp[nm]===''){tmp3[nm]='null';}}}});if(cv[0]===false){try{var positions=$.jgrid.findPos($('#'+$.jgrid.jqID(rowid),$t.grid.bDiv)[0]);$.jgrid.info_dialog($.jgrid.errors.errcap,cv[1],$.jgrid.edit.bClose,{left:positions[0],top:positions[1]});}catch(e){alert(cv[1]);}return success;}var idname,opers=$t.p.prmNames,oldRowId=rowid;if($t.p.keyIndex===false){idname=opers.id;}else{idname=$t.p.colModel[$t.p.keyIndex+($t.p.rownumbers===true?1:0)+($t.p.multiselect===true?1:0)+($t.p.subGrid===true?1:0)].name;}if(tmp){tmp[opers.oper]=opers.editoper;if(tmp[idname]===undefined){tmp[idname]=rowid;}else if(ind.id!==$t.p.idPrefix+tmp[idname]){// rename rowid
var oldid=$.jgrid.stripPref($t.p.idPrefix,rowid);if($t.p._index[oldid]!==undefined){$t.p._index[tmp[idname]]=$t.p._index[oldid];delete $t.p._index[oldid];}rowid=$t.p.idPrefix+tmp[idname];$(ind).attr('id',rowid);if($t.p.selrow===oldRowId){$t.p.selrow=rowid;}if($.isArray($t.p.selarrrow)){var i=$.inArray(oldRowId,$t.p.selarrrow);if(i>=0){$t.p.selarrrow[i]=rowid;}}if($t.p.multiselect){var newCboxId='jqg_'+$t.p.id+'_'+rowid;$('input.cbox',ind).attr('id',newCboxId).attr('name',newCboxId);}// TODO: to test the case of frozen columns
}if($t.p.inlineData===undefined){$t.p.inlineData={};}tmp=$.extend({},tmp,$t.p.inlineData,o.extraparam);}if(o.url=='clientArray'){tmp=$.extend({},tmp,tmp2);if($t.p.autoencode){$.each(tmp,function(n,v){tmp[n]=$.jgrid.htmlDecode(v);});}var k,resp=$($t).jqGrid('setRowData',rowid,tmp);$(ind).attr('editable','0');for(k=0;k<$t.p.savedRow.length;k++){if($t.p.savedRow[k].id==oldRowId){fr=k;break;}}if(fr>=0){$t.p.savedRow.splice(fr,1);}$($t).triggerHandler('jqGridInlineAfterSaveRow',[rowid,resp,tmp,o]);if($.isFunction(o.aftersavefunc)){o.aftersavefunc.call($t,rowid,resp,o);}success=true;$(ind).unbind('keydown');}else{$('#lui_'+$.jgrid.jqID($t.p.id)).show();tmp3=$.extend({},tmp,tmp3);tmp3[idname]=$.jgrid.stripPref($t.p.idPrefix,tmp3[idname]);$.ajax($.extend({url:o.url,data:$.isFunction($t.p.serializeRowData)?$t.p.serializeRowData.call($t,tmp3):tmp3,type:o.mtype,async:false,//?!?
complete:function complete(res,stat){$('#lui_'+$.jgrid.jqID($t.p.id)).hide();if(stat==='success'){var ret=true,sucret,k;sucret=$($t).triggerHandler('jqGridInlineSuccessSaveRow',[res,rowid,o]);if(!$.isArray(sucret)){sucret=[true,tmp];}if(sucret[0]&&$.isFunction(o.successfunc)){sucret=o.successfunc.call($t,res);}if($.isArray(sucret)){// expect array - status, data, rowid
ret=sucret[0];tmp=sucret[1]||tmp;}else{ret=sucret;}if(ret===true){if($t.p.autoencode){$.each(tmp,function(n,v){tmp[n]=$.jgrid.htmlDecode(v);});}tmp=$.extend({},tmp,tmp2);$($t).jqGrid('setRowData',rowid,tmp);$(ind).attr('editable','0');for(k=0;k<$t.p.savedRow.length;k++){if($t.p.savedRow[k].id==rowid){fr=k;break;}}if(fr>=0){$t.p.savedRow.splice(fr,1);}$($t).triggerHandler('jqGridInlineAfterSaveRow',[rowid,res,tmp,o]);if($.isFunction(o.aftersavefunc)){o.aftersavefunc.call($t,rowid,res);}success=true;$(ind).unbind('keydown');}else{$($t).triggerHandler('jqGridInlineErrorSaveRow',[rowid,res,stat,null,o]);if($.isFunction(o.errorfunc)){o.errorfunc.call($t,rowid,res,stat,null);}if(o.restoreAfterError===true){$($t).jqGrid('restoreRow',rowid,o.afterrestorefunc);}}}},error:function error(res,stat,err){$('#lui_'+$.jgrid.jqID($t.p.id)).hide();$($t).triggerHandler('jqGridInlineErrorSaveRow',[rowid,res,stat,err,o]);if($.isFunction(o.errorfunc)){o.errorfunc.call($t,rowid,res,stat,err);}else{var rT=res.responseText||res.statusText;try{$.jgrid.info_dialog($.jgrid.errors.errcap,'<div class="ui-state-error">'+rT+'</div>',$.jgrid.edit.bClose,{buttonalign:'right'});}catch(e){alert(rT);}}if(o.restoreAfterError===true){$($t).jqGrid('restoreRow',rowid,o.afterrestorefunc);}}},$.jgrid.ajaxOptions,$t.p.ajaxRowOptions||{}));}}return success;},restoreRow:function restoreRow(rowid,afterrestorefunc){// Compatible mode old versions
var args=$.makeArray(arguments).slice(1),o={};if($.type(args[0])==='object'){o=args[0];}else{if($.isFunction(afterrestorefunc)){o.afterrestorefunc=afterrestorefunc;}}o=$.extend(true,$.jgrid.inlineEdit,o);// End compatible
return this.each(function(){var $t=this,fr,ind,ares={},k;if(!$t.grid){return;}ind=$($t).jqGrid('getInd',rowid,true);if(ind===false){return;}for(k=0;k<$t.p.savedRow.length;k++){if($t.p.savedRow[k].id==rowid){fr=k;break;}}if(fr>=0){if($.isFunction($.fn.datepicker)){try{$('input.hasDatepicker','#'+$.jgrid.jqID(ind.id)).datepicker('hide');}catch(e){}}$.each($t.p.colModel,function(){if(this.editable===true&&$t.p.savedRow[fr].hasOwnProperty(this.name)){ares[this.name]=$t.p.savedRow[fr][this.name];}});$($t).jqGrid('setRowData',rowid,ares);$(ind).attr('editable','0').unbind('keydown');$t.p.savedRow.splice(fr,1);if($('#'+$.jgrid.jqID(rowid),'#'+$.jgrid.jqID($t.p.id)).hasClass('jqgrid-new-row')){setTimeout(function(){$($t).jqGrid('delRowData',rowid);},0);}}$($t).triggerHandler('jqGridInlineAfterRestoreRow',[rowid]);if($.isFunction(o.afterrestorefunc)){o.afterrestorefunc.call($t,rowid);}});},addRow:function addRow(p){p=$.extend(true,{rowID:null,initdata:{},position:'first',useDefValues:true,useFormatter:false,addRowParams:{extraparam:{}}},p||{});return this.each(function(){if(!this.grid){return;}var $t=this;p.rowID=$.isFunction(p.rowID)?p.rowID.call($t,p):p.rowID!=null?p.rowID:$.jgrid.randId();if(p.useDefValues===true){$($t.p.colModel).each(function(){if(this.editoptions&&this.editoptions.defaultValue){var opt=this.editoptions.defaultValue,tmp=$.isFunction(opt)?opt.call($t):opt;p.initdata[this.name]=tmp;}});}$($t).jqGrid('addRowData',p.rowID,p.initdata,p.position);p.rowID=$t.p.idPrefix+p.rowID;$('#'+$.jgrid.jqID(p.rowID),'#'+$.jgrid.jqID($t.p.id)).addClass('jqgrid-new-row');if(p.useFormatter){$('#'+$.jgrid.jqID(p.rowID)+' .ui-inline-edit','#'+$.jgrid.jqID($t.p.id)).click();}else{var opers=$t.p.prmNames,oper=opers.oper;p.addRowParams.extraparam[oper]=opers.addoper;$($t).jqGrid('editRow',p.rowID,p.addRowParams);$($t).jqGrid('setSelection',p.rowID);}});},inlineNav:function inlineNav(elem,o){o=$.extend({edit:true,editicon:'ui-icon-pencil',add:true,addicon:'ui-icon-plus',save:true,saveicon:'ui-icon-disk',cancel:true,cancelicon:'ui-icon-cancel',addParams:{},editParams:{},restoreAfterSelect:true},$.jgrid.nav,o||{});return this.each(function(){if(!this.grid){return;}var $t=this,onSelect,gID=$.jgrid.jqID($t.p.id);$t.p._inlinenav=true;// detect the formatactions column
if(o.addParams.useFormatter===true){var cm=$t.p.colModel,i;for(i=0;i<cm.length;i++){if(cm[i].formatter&&cm[i].formatter==='actions'){if(cm[i].formatoptions){var defaults={keys:false,onEdit:null,onSuccess:null,afterSave:null,onError:null,afterRestore:null,extraparam:{},url:null},ap=$.extend(defaults,cm[i].formatoptions);o.addParams.addRowParams={'keys':ap.keys,'oneditfunc':ap.onEdit,'successfunc':ap.onSuccess,'url':ap.url,'extraparam':ap.extraparam,'aftersavefunc':ap.afterSavef,'errorfunc':ap.onError,'afterrestorefunc':ap.afterRestore};}break;}}}if(o.add){$($t).jqGrid('navButtonAdd',elem,{caption:o.addtext,title:o.addtitle,buttonicon:o.addicon,id:$t.p.id+'_iladd',onClickButton:function onClickButton(){$($t).jqGrid('addRow',o.addParams);if(!o.addParams.useFormatter){$('#'+gID+'_ilsave').removeClass('ui-state-disabled');$('#'+gID+'_ilcancel').removeClass('ui-state-disabled');$('#'+gID+'_iladd').addClass('ui-state-disabled');$('#'+gID+'_iledit').addClass('ui-state-disabled');}}});}if(o.edit){$($t).jqGrid('navButtonAdd',elem,{caption:o.edittext,title:o.edittitle,buttonicon:o.editicon,id:$t.p.id+'_iledit',onClickButton:function onClickButton(){var sr=$($t).jqGrid('getGridParam','selrow');if(sr){$($t).jqGrid('editRow',sr,o.editParams);$('#'+gID+'_ilsave').removeClass('ui-state-disabled');$('#'+gID+'_ilcancel').removeClass('ui-state-disabled');$('#'+gID+'_iladd').addClass('ui-state-disabled');$('#'+gID+'_iledit').addClass('ui-state-disabled');}else{$.jgrid.viewModal('#alertmod',{gbox:'#gbox_'+gID,jqm:true});$('#jqg_alrt').focus();}}});}if(o.save){$($t).jqGrid('navButtonAdd',elem,{caption:o.savetext||'',title:o.savetitle||'Save row',buttonicon:o.saveicon,id:$t.p.id+'_ilsave',onClickButton:function onClickButton(){var sr=$t.p.savedRow[0].id;if(sr){var opers=$t.p.prmNames,oper=opers.oper;if(!o.editParams.extraparam){o.editParams.extraparam={};}if($('#'+$.jgrid.jqID(sr),'#'+gID).hasClass('jqgrid-new-row')){o.editParams.extraparam[oper]=opers.addoper;}else{o.editParams.extraparam[oper]=opers.editoper;}if($($t).jqGrid('saveRow',sr,o.editParams)){$($t).jqGrid('showAddEditButtons');}}else{$.jgrid.viewModal('#alertmod',{gbox:'#gbox_'+gID,jqm:true});$('#jqg_alrt').focus();}}});$('#'+gID+'_ilsave').addClass('ui-state-disabled');}if(o.cancel){$($t).jqGrid('navButtonAdd',elem,{caption:o.canceltext||'',title:o.canceltitle||'Cancel row editing',buttonicon:o.cancelicon,id:$t.p.id+'_ilcancel',onClickButton:function onClickButton(){var sr=$t.p.savedRow[0].id;if(sr){$($t).jqGrid('restoreRow',sr,o.editParams);$($t).jqGrid('showAddEditButtons');}else{$.jgrid.viewModal('#alertmod',{gbox:'#gbox_'+gID,jqm:true});$('#jqg_alrt').focus();}}});$('#'+gID+'_ilcancel').addClass('ui-state-disabled');}if(o.restoreAfterSelect===true){if($.isFunction($t.p.beforeSelectRow)){onSelect=$t.p.beforeSelectRow;}else{onSelect=false;}$t.p.beforeSelectRow=function(id,stat){var ret=true;if($t.p.savedRow.length>0&&$t.p._inlinenav===true&&id!==$t.p.selrow&&$t.p.selrow!==null){if($t.p.selrow==o.addParams.rowID){$($t).jqGrid('delRowData',$t.p.selrow);}else{$($t).jqGrid('restoreRow',$t.p.selrow,o.editParams);}$($t).jqGrid('showAddEditButtons');}if(onSelect){ret=onSelect.call($t,id,stat);}return ret;};}});},showAddEditButtons:function showAddEditButtons(){return this.each(function(){if(!this.grid){return;}var gID=$.jgrid.jqID(this.p.id);$('#'+gID+'_ilsave').addClass('ui-state-disabled');$('#'+gID+'_ilcancel').addClass('ui-state-disabled');$('#'+gID+'_iladd').removeClass('ui-state-disabled');$('#'+gID+'_iledit').removeClass('ui-state-disabled');});}//end inline edit
});})(jQuery);/*jshint eqeqeq:false *//*global jQuery */(function($){/*
**
 * jqGrid extension for cellediting Grid Data
 * Tony Tomov tony@trirand.com
 * http://trirand.com/blog/
 * Dual licensed under the MIT and GPL licenses:
 * http://www.opensource.org/licenses/mit-license.php
 * http://www.gnu.org/licenses/gpl-2.0.html
**//**
 * all events and options here are aded anonynous and not in the base grid
 * since the array is to big. Here is the order of execution.
 * From this point we use jQuery isFunction
 * formatCell
 * beforeEditCell,
 * onSelectCell (used only for noneditable cels)
 * afterEditCell,
 * beforeSaveCell, (called before validation of values if any)
 * beforeSubmitCell (if cellsubmit remote (ajax))
 * afterSubmitCell(if cellsubmit remote (ajax)),
 * afterSaveCell,
 * errorCell,
 * serializeCellData - new
 * Options
 * cellsubmit (remote,clientArray) (added in grid options)
 * cellurl
 * ajaxCellOptions
* */'use strict';$.jgrid.extend({editCell:function editCell(iRow,iCol,ed){return this.each(function(){var $t=this,nm,tmp,cc,cm;if(!$t.grid||$t.p.cellEdit!==true){return;}iCol=parseInt(iCol,10);// select the row that can be used for other methods
$t.p.selrow=$t.rows[iRow].id;if(!$t.p.knv){$($t).jqGrid('GridNav');}// check to see if we have already edited cell
if($t.p.savedRow.length>0){// prevent second click on that field and enable selects
if(ed===true){if(iRow==$t.p.iRow&&iCol==$t.p.iCol){return;}}// save the cell
$($t).jqGrid('saveCell',$t.p.savedRow[0].id,$t.p.savedRow[0].ic);}else{window.setTimeout(function(){$('#'+$.jgrid.jqID($t.p.knv)).attr('tabindex','-1').focus();},0);}cm=$t.p.colModel[iCol];nm=cm.name;if(nm=='subgrid'||nm=='cb'||nm=='rn'){return;}cc=$('td:eq('+iCol+')',$t.rows[iRow]);if(cm.editable===true&&ed===true&&!cc.hasClass('not-editable-cell')){if(parseInt($t.p.iCol,10)>=0&&parseInt($t.p.iRow,10)>=0){$('td:eq('+$t.p.iCol+')',$t.rows[$t.p.iRow]).removeClass('edit-cell ui-state-highlight');$($t.rows[$t.p.iRow]).removeClass('selected-row ui-state-hover');}$(cc).addClass('edit-cell ui-state-highlight');$($t.rows[iRow]).addClass('selected-row ui-state-hover');try{tmp=$.unformat.call($t,cc,{rowId:$t.rows[iRow].id,colModel:cm},iCol);}catch(_){tmp=cm.edittype&&cm.edittype=='textarea'?$(cc).text():$(cc).html();}if($t.p.autoencode){tmp=$.jgrid.htmlDecode(tmp);}if(!cm.edittype){cm.edittype='text';}$t.p.savedRow.push({id:iRow,ic:iCol,name:nm,v:tmp});if(tmp==='&nbsp;'||tmp==='&#160;'||tmp.length===1&&tmp.charCodeAt(0)===160){tmp='';}if($.isFunction($t.p.formatCell)){var tmp2=$t.p.formatCell.call($t,$t.rows[iRow].id,nm,tmp,iRow,iCol);if(tmp2!==undefined){tmp=tmp2;}}var opt=$.extend({},cm.editoptions||{},{id:iRow+'_'+nm,name:nm});var elc=$.jgrid.createEl.call($t,cm.edittype,opt,tmp,true,$.extend({},$.jgrid.ajaxOptions,$t.p.ajaxSelectOptions||{}));$($t).triggerHandler('jqGridBeforeEditCell',[$t.rows[iRow].id,nm,tmp,iRow,iCol]);if($.isFunction($t.p.beforeEditCell)){$t.p.beforeEditCell.call($t,$t.rows[iRow].id,nm,tmp,iRow,iCol);}$(cc).html('').append(elc).attr('tabindex','0');$.jgrid.bindEv(elc,opt,$t);window.setTimeout(function(){$(elc).focus();},0);$('input, select, textarea',cc).bind('keydown',function(e){if(e.keyCode===27){if($('input.hasDatepicker',cc).length>0){if($('.ui-datepicker').is(':hidden')){$($t).jqGrid('restoreCell',iRow,iCol);}else{$('input.hasDatepicker',cc).datepicker('hide');}}else{$($t).jqGrid('restoreCell',iRow,iCol);}}//ESC
if(e.keyCode===13){$($t).jqGrid('saveCell',iRow,iCol);// Prevent default action
return false;}//Enter
if(e.keyCode===9){if(!$t.grid.hDiv.loading){if(e.shiftKey){$($t).jqGrid('prevCell',iRow,iCol);}//Shift TAb
else{$($t).jqGrid('nextCell',iRow,iCol);}//Tab
}else{return false;}}e.stopPropagation();});$($t).triggerHandler('jqGridAfterEditCell',[$t.rows[iRow].id,nm,tmp,iRow,iCol]);if($.isFunction($t.p.afterEditCell)){$t.p.afterEditCell.call($t,$t.rows[iRow].id,nm,tmp,iRow,iCol);}}else{if(parseInt($t.p.iCol,10)>=0&&parseInt($t.p.iRow,10)>=0){$('td:eq('+$t.p.iCol+')',$t.rows[$t.p.iRow]).removeClass('edit-cell ui-state-highlight');$($t.rows[$t.p.iRow]).removeClass('selected-row ui-state-hover');}cc.addClass('edit-cell ui-state-highlight');$($t.rows[iRow]).addClass('selected-row ui-state-hover');tmp=cc.html().replace(/\&#160\;/ig,'');$($t).triggerHandler('jqGridSelectCell',[$t.rows[iRow].id,nm,tmp,iRow,iCol]);if($.isFunction($t.p.onSelectCell)){$t.p.onSelectCell.call($t,$t.rows[iRow].id,nm,tmp,iRow,iCol);}}$t.p.iCol=iCol;$t.p.iRow=iRow;});},saveCell:function saveCell(iRow,iCol){return this.each(function(){var $t=this,fr;if(!$t.grid||$t.p.cellEdit!==true){return;}if($t.p.savedRow.length>=1){fr=0;}else{fr=null;}if(fr!==null){var cc=$('td:eq('+iCol+')',$t.rows[iRow]),v,v2,cm=$t.p.colModel[iCol],nm=cm.name,nmjq=$.jgrid.jqID(nm);switch(cm.edittype){case'select':if(!cm.editoptions.multiple){v=$('#'+iRow+'_'+nmjq+' option:selected',$t.rows[iRow]).val();v2=$('#'+iRow+'_'+nmjq+' option:selected',$t.rows[iRow]).text();}else{var sel=$('#'+iRow+'_'+nmjq,$t.rows[iRow]),selectedText=[];v=$(sel).val();if(v){v.join(',');}else{v='';}$('option:selected',sel).each(function(i,selected){selectedText[i]=$(selected).text();});v2=selectedText.join(',');}if(cm.formatter){v2=v;}break;case'checkbox':var cbv=['Yes','No'];if(cm.editoptions){cbv=cm.editoptions.value.split(':');}v=$('#'+iRow+'_'+nmjq,$t.rows[iRow]).is(':checked')?cbv[0]:cbv[1];v2=v;break;case'password':case'text':case'textarea':case'button':v=$('#'+iRow+'_'+nmjq,$t.rows[iRow]).val();v2=v;break;case'custom':try{if(cm.editoptions&&$.isFunction(cm.editoptions.custom_value)){v=cm.editoptions.custom_value.call($t,$('.customelement',cc),'get');if(v===undefined){throw'e2';}else{v2=v;}}else{throw'e1';}}catch(e){if(e=='e1'){$.jgrid.info_dialog($.jgrid.errors.errcap,'function \'custom_value\' '+$.jgrid.edit.msg.nodefined,$.jgrid.edit.bClose);}if(e=='e2'){$.jgrid.info_dialog($.jgrid.errors.errcap,'function \'custom_value\' '+$.jgrid.edit.msg.novalue,$.jgrid.edit.bClose);}else{$.jgrid.info_dialog($.jgrid.errors.errcap,e.message,$.jgrid.edit.bClose);}}break;}// The common approach is if nothing changed do not do anything
if(v2!==$t.p.savedRow[fr].v){var vvv=$($t).triggerHandler('jqGridBeforeSaveCell',[$t.rows[iRow].id,nm,v,iRow,iCol]);if(vvv){v=vvv;v2=vvv;}if($.isFunction($t.p.beforeSaveCell)){var vv=$t.p.beforeSaveCell.call($t,$t.rows[iRow].id,nm,v,iRow,iCol);if(vv){v=vv;v2=vv;}}var cv=$.jgrid.checkValues(v,iCol,$t);if(cv[0]===true){var addpost=$($t).triggerHandler('jqGridBeforeSubmitCell',[$t.rows[iRow].id,nm,v,iRow,iCol])||{};if($.isFunction($t.p.beforeSubmitCell)){addpost=$t.p.beforeSubmitCell.call($t,$t.rows[iRow].id,nm,v,iRow,iCol);if(!addpost){addpost={};}}if($('input.hasDatepicker',cc).length>0){$('input.hasDatepicker',cc).datepicker('hide');}if($t.p.cellsubmit=='remote'){if($t.p.cellurl){var postdata={};if($t.p.autoencode){v=$.jgrid.htmlEncode(v);}postdata[nm]=v;var idname,oper,opers;opers=$t.p.prmNames;idname=opers.id;oper=opers.oper;postdata[idname]=$.jgrid.stripPref($t.p.idPrefix,$t.rows[iRow].id);postdata[oper]=opers.editoper;postdata=$.extend(addpost,postdata);$('#lui_'+$.jgrid.jqID($t.p.id)).show();$t.grid.hDiv.loading=true;$.ajax($.extend({url:$t.p.cellurl,data:$.isFunction($t.p.serializeCellData)?$t.p.serializeCellData.call($t,postdata):postdata,type:'POST',complete:function complete(result,stat){$('#lui_'+$t.p.id).hide();$t.grid.hDiv.loading=false;if(stat=='success'){var ret=$($t).triggerHandler('jqGridAfterSubmitCell',[$t,result,postdata.id,nm,v,iRow,iCol])||[true,''];if(ret[0]===true&&$.isFunction($t.p.afterSubmitCell)){ret=$t.p.afterSubmitCell.call($t,result,postdata.id,nm,v,iRow,iCol);}if(ret[0]===true){$(cc).empty();$($t).jqGrid('setCell',$t.rows[iRow].id,iCol,v2,false,false,true);$(cc).addClass('dirty-cell');$($t.rows[iRow]).addClass('edited');$($t).triggerHandler('jqGridAfterSaveCell',[$t.rows[iRow].id,nm,v,iRow,iCol]);if($.isFunction($t.p.afterSaveCell)){$t.p.afterSaveCell.call($t,$t.rows[iRow].id,nm,v,iRow,iCol);}$t.p.savedRow.splice(0,1);}else{$.jgrid.info_dialog($.jgrid.errors.errcap,ret[1],$.jgrid.edit.bClose);$($t).jqGrid('restoreCell',iRow,iCol);}}},error:function error(res,stat,err){$('#lui_'+$.jgrid.jqID($t.p.id)).hide();$t.grid.hDiv.loading=false;$($t).triggerHandler('jqGridErrorCell',[res,stat,err]);if($.isFunction($t.p.errorCell)){$t.p.errorCell.call($t,res,stat,err);$($t).jqGrid('restoreCell',iRow,iCol);}else{$.jgrid.info_dialog($.jgrid.errors.errcap,res.status+' : '+res.statusText+'<br/>'+stat,$.jgrid.edit.bClose);$($t).jqGrid('restoreCell',iRow,iCol);}}},$.jgrid.ajaxOptions,$t.p.ajaxCellOptions||{}));}else{try{$.jgrid.info_dialog($.jgrid.errors.errcap,$.jgrid.errors.nourl,$.jgrid.edit.bClose);$($t).jqGrid('restoreCell',iRow,iCol);}catch(e){}}}if($t.p.cellsubmit=='clientArray'){$(cc).empty();$($t).jqGrid('setCell',$t.rows[iRow].id,iCol,v2,false,false,true);$(cc).addClass('dirty-cell');$($t.rows[iRow]).addClass('edited');$($t).triggerHandler('jqGridAfterSaveCell',[$t.rows[iRow].id,nm,v,iRow,iCol]);if($.isFunction($t.p.afterSaveCell)){$t.p.afterSaveCell.call($t,$t.rows[iRow].id,nm,v,iRow,iCol);}$t.p.savedRow.splice(0,1);}}else{try{window.setTimeout(function(){$.jgrid.info_dialog($.jgrid.errors.errcap,v+' '+cv[1],$.jgrid.edit.bClose);},100);$($t).jqGrid('restoreCell',iRow,iCol);}catch(e){}}}else{$($t).jqGrid('restoreCell',iRow,iCol);}}window.setTimeout(function(){$('#'+$.jgrid.jqID($t.p.knv)).attr('tabindex','-1').focus();},0);});},restoreCell:function restoreCell(iRow,iCol){return this.each(function(){var $t=this,fr;if(!$t.grid||$t.p.cellEdit!==true){return;}if($t.p.savedRow.length>=1){fr=0;}else{fr=null;}if(fr!==null){var cc=$('td:eq('+iCol+')',$t.rows[iRow]);// datepicker fix
if($.isFunction($.fn.datepicker)){try{$('input.hasDatepicker',cc).datepicker('hide');}catch(e){}}$(cc).empty().attr('tabindex','-1');$($t).jqGrid('setCell',$t.rows[iRow].id,iCol,$t.p.savedRow[fr].v,false,false,true);$($t).triggerHandler('jqGridAfterRestoreCell',[$t.rows[iRow].id,$t.p.savedRow[fr].v,iRow,iCol]);if($.isFunction($t.p.afterRestoreCell)){$t.p.afterRestoreCell.call($t,$t.rows[iRow].id,$t.p.savedRow[fr].v,iRow,iCol);}$t.p.savedRow.splice(0,1);}window.setTimeout(function(){$('#'+$t.p.knv).attr('tabindex','-1').focus();},0);});},nextCell:function nextCell(iRow,iCol){return this.each(function(){var $t=this,nCol=false,i;if(!$t.grid||$t.p.cellEdit!==true){return;}// try to find next editable cell
for(i=iCol+1;i<$t.p.colModel.length;i++){if($t.p.colModel[i].editable===true){nCol=i;break;}}if(nCol!==false){$($t).jqGrid('editCell',iRow,nCol,true);}else{if($t.p.savedRow.length>0){$($t).jqGrid('saveCell',iRow,iCol);}}});},prevCell:function prevCell(iRow,iCol){return this.each(function(){var $t=this,nCol=false,i;if(!$t.grid||$t.p.cellEdit!==true){return;}// try to find next editable cell
for(i=iCol-1;i>=0;i--){if($t.p.colModel[i].editable===true){nCol=i;break;}}if(nCol!==false){$($t).jqGrid('editCell',iRow,nCol,true);}else{if($t.p.savedRow.length>0){$($t).jqGrid('saveCell',iRow,iCol);}}});},GridNav:function GridNav(){return this.each(function(){var $t=this;if(!$t.grid||$t.p.cellEdit!==true){return;}// trick to process keydown on non input elements
$t.p.knv=$t.p.id+'_kn';var selection=$('<div style=\'position:fixed;top:-1000000px;width:1px;height:1px;\' tabindex=\'0\'><div tabindex=\'-1\' style=\'width:1px;height:1px;\' id=\''+$t.p.knv+'\'></div></div>'),i,kdir;function scrollGrid(iR,iC,tp){if(tp.substr(0,1)=='v'){var ch=$($t.grid.bDiv)[0].clientHeight,st=$($t.grid.bDiv)[0].scrollTop,nROT=$t.rows[iR].offsetTop+$t.rows[iR].clientHeight,pROT=$t.rows[iR].offsetTop;if(tp=='vd'){if(nROT>=ch){$($t.grid.bDiv)[0].scrollTop=$($t.grid.bDiv)[0].scrollTop+$t.rows[iR].clientHeight;}}if(tp=='vu'){if(pROT<st){$($t.grid.bDiv)[0].scrollTop=$($t.grid.bDiv)[0].scrollTop-$t.rows[iR].clientHeight;}}}if(tp=='h'){var cw=$($t.grid.bDiv)[0].clientWidth,sl=$($t.grid.bDiv)[0].scrollLeft,nCOL=$t.rows[iR].cells[iC].offsetLeft+$t.rows[iR].cells[iC].clientWidth,pCOL=$t.rows[iR].cells[iC].offsetLeft;if(nCOL>=cw+parseInt(sl,10)){$($t.grid.bDiv)[0].scrollLeft=$($t.grid.bDiv)[0].scrollLeft+$t.rows[iR].cells[iC].clientWidth;}else if(pCOL<sl){$($t.grid.bDiv)[0].scrollLeft=$($t.grid.bDiv)[0].scrollLeft-$t.rows[iR].cells[iC].clientWidth;}}}function findNextVisible(iC,act){var ind,i;if(act=='lft'){ind=iC+1;for(i=iC;i>=0;i--){if($t.p.colModel[i].hidden!==true){ind=i;break;}}}if(act=='rgt'){ind=iC-1;for(i=iC;i<$t.p.colModel.length;i++){if($t.p.colModel[i].hidden!==true){ind=i;break;}}}return ind;}$(selection).insertBefore($t.grid.cDiv);$('#'+$t.p.knv).focus().keydown(function(e){kdir=e.keyCode;if($t.p.direction=='rtl'){if(kdir===37){kdir=39;}else if(kdir===39){kdir=37;}}switch(kdir){case 38:if($t.p.iRow-1>0){scrollGrid($t.p.iRow-1,$t.p.iCol,'vu');$($t).jqGrid('editCell',$t.p.iRow-1,$t.p.iCol,false);}break;case 40:if($t.p.iRow+1<=$t.rows.length-1){scrollGrid($t.p.iRow+1,$t.p.iCol,'vd');$($t).jqGrid('editCell',$t.p.iRow+1,$t.p.iCol,false);}break;case 37:if($t.p.iCol-1>=0){i=findNextVisible($t.p.iCol-1,'lft');scrollGrid($t.p.iRow,i,'h');$($t).jqGrid('editCell',$t.p.iRow,i,false);}break;case 39:if($t.p.iCol+1<=$t.p.colModel.length-1){i=findNextVisible($t.p.iCol+1,'rgt');scrollGrid($t.p.iRow,i,'h');$($t).jqGrid('editCell',$t.p.iRow,i,false);}break;case 13:if(parseInt($t.p.iCol,10)>=0&&parseInt($t.p.iRow,10)>=0){$($t).jqGrid('editCell',$t.p.iRow,$t.p.iCol,true);}break;default:return true;}return false;});});},getChangedCells:function getChangedCells(mthd){var ret=[];if(!mthd){mthd='all';}this.each(function(){var $t=this,nm;if(!$t.grid||$t.p.cellEdit!==true){return;}$($t.rows).each(function(j){var res={};if($(this).hasClass('edited')){$('td',this).each(function(i){nm=$t.p.colModel[i].name;if(nm!=='cb'&&nm!=='subgrid'){if(mthd=='dirty'){if($(this).hasClass('dirty-cell')){try{res[nm]=$.unformat.call($t,this,{rowId:$t.rows[j].id,colModel:$t.p.colModel[i]},i);}catch(e){res[nm]=$.jgrid.htmlDecode($(this).html());}}}else{try{res[nm]=$.unformat.call($t,this,{rowId:$t.rows[j].id,colModel:$t.p.colModel[i]},i);}catch(e){res[nm]=$.jgrid.htmlDecode($(this).html());}}}});res.id=this.id;ret.push(res);}});});return ret;}/// end  cell editing
});})(jQuery);/*jshint eqeqeq:false *//*global jQuery */(function($){/**
 * jqGrid extension for SubGrid Data
 * Tony Tomov tony@trirand.com
 * http://trirand.com/blog/
 * Dual licensed under the MIT and GPL licenses:
 * http://www.opensource.org/licenses/mit-license.php
 * http://www.gnu.org/licenses/gpl-2.0.html
**/'use strict';$.jgrid.extend({setSubGrid:function setSubGrid(){return this.each(function(){var $t=this,cm,i,suboptions={plusicon:'ui-icon-plus',minusicon:'ui-icon-minus',openicon:'ui-icon-carat-1-sw',expandOnLoad:false,delayOnLoad:50,selectOnExpand:false,reloadOnExpand:true};$t.p.subGridOptions=$.extend(suboptions,$t.p.subGridOptions||{});$t.p.colNames.unshift('');$t.p.colModel.unshift({name:'subgrid',width:$.jgrid.cell_width?$t.p.subGridWidth+$t.p.cellLayout:$t.p.subGridWidth,sortable:false,resizable:false,hidedlg:true,search:false,fixed:true});cm=$t.p.subGridModel;if(cm[0]){cm[0].align=$.extend([],cm[0].align||[]);for(i=0;i<cm[0].name.length;i++){cm[0].align[i]=cm[0].align[i]||'left';}}});},addSubGridCell:function addSubGridCell(pos,iRow){var prp='',ic,sid;this.each(function(){prp=this.formatCol(pos,iRow);sid=this.p.id;ic=this.p.subGridOptions.plusicon;});return'<td role="gridcell" aria-describedby="'+sid+'_subgrid" class="ui-sgcollapsed sgcollapsed" '+prp+'><a href=\'javascript:void(0);\'><span class=\'ui-icon '+ic+'\'></span></a></td>';},addSubGrid:function addSubGrid(pos,sind){return this.each(function(){var ts=this;if(!ts.grid){return;}//-------------------------
var subGridCell=function subGridCell(trdiv,cell,pos){var tddiv=$('<td align=\''+ts.p.subGridModel[0].align[pos]+'\'></td>').html(cell);$(trdiv).append(tddiv);};var subGridXml=function subGridXml(sjxml,sbid){var tddiv,i,sgmap,dummy=$('<table cellspacing=\'0\' cellpadding=\'0\' border=\'0\'><tbody></tbody></table>'),trdiv=$('<tr></tr>');for(i=0;i<ts.p.subGridModel[0].name.length;i++){tddiv=$('<th class=\'ui-state-default ui-th-subgrid ui-th-column ui-th-'+ts.p.direction+'\'></th>');$(tddiv).html(ts.p.subGridModel[0].name[i]);$(tddiv).width(ts.p.subGridModel[0].width[i]);$(trdiv).append(tddiv);}$(dummy).append(trdiv);if(sjxml){sgmap=ts.p.xmlReader.subgrid;$(sgmap.root+' '+sgmap.row,sjxml).each(function(){trdiv=$('<tr class=\'ui-widget-content ui-subtblcell\'></tr>');if(sgmap.repeatitems===true){$(sgmap.cell,this).each(function(i){subGridCell(trdiv,$(this).text()||'&#160;',i);});}else{var f=ts.p.subGridModel[0].mapping||ts.p.subGridModel[0].name;if(f){for(i=0;i<f.length;i++){subGridCell(trdiv,$(f[i],this).text()||'&#160;',i);}}}$(dummy).append(trdiv);});}var pID=$('table:first',ts.grid.bDiv).attr('id')+'_';$('#'+$.jgrid.jqID(pID+sbid)).append(dummy);ts.grid.hDiv.loading=false;$('#load_'+$.jgrid.jqID(ts.p.id)).hide();return false;};var subGridJson=function subGridJson(sjxml,sbid){var tddiv,result,i,cur,sgmap,j,dummy=$('<table cellspacing=\'0\' cellpadding=\'0\' border=\'0\'><tbody></tbody></table>'),trdiv=$('<tr></tr>');for(i=0;i<ts.p.subGridModel[0].name.length;i++){tddiv=$('<th class=\'ui-state-default ui-th-subgrid ui-th-column ui-th-'+ts.p.direction+'\'></th>');$(tddiv).html(ts.p.subGridModel[0].name[i]);$(tddiv).width(ts.p.subGridModel[0].width[i]);$(trdiv).append(tddiv);}$(dummy).append(trdiv);if(sjxml){sgmap=ts.p.jsonReader.subgrid;result=$.jgrid.getAccessor(sjxml,sgmap.root);if(result!==undefined){for(i=0;i<result.length;i++){cur=result[i];trdiv=$('<tr class=\'ui-widget-content ui-subtblcell\'></tr>');if(sgmap.repeatitems===true){if(sgmap.cell){cur=cur[sgmap.cell];}for(j=0;j<cur.length;j++){subGridCell(trdiv,cur[j]||'&#160;',j);}}else{var f=ts.p.subGridModel[0].mapping||ts.p.subGridModel[0].name;if(f.length){for(j=0;j<f.length;j++){subGridCell(trdiv,cur[f[j]]||'&#160;',j);}}}$(dummy).append(trdiv);}}}var pID=$('table:first',ts.grid.bDiv).attr('id')+'_';$('#'+$.jgrid.jqID(pID+sbid)).append(dummy);ts.grid.hDiv.loading=false;$('#load_'+$.jgrid.jqID(ts.p.id)).hide();return false;};var populatesubgrid=function populatesubgrid(rd){var sid,dp,i,j;sid=$(rd).attr('id');dp={nd_:new Date().getTime()};dp[ts.p.prmNames.subgridid]=sid;if(!ts.p.subGridModel[0]){return false;}if(ts.p.subGridModel[0].params){for(j=0;j<ts.p.subGridModel[0].params.length;j++){for(i=0;i<ts.p.colModel.length;i++){if(ts.p.colModel[i].name===ts.p.subGridModel[0].params[j]){dp[ts.p.colModel[i].name]=$('td:eq('+i+')',rd).text().replace(/\&#160\;/ig,'');}}}}if(!ts.grid.hDiv.loading){ts.grid.hDiv.loading=true;$('#load_'+$.jgrid.jqID(ts.p.id)).show();if(!ts.p.subgridtype){ts.p.subgridtype=ts.p.datatype;}if($.isFunction(ts.p.subgridtype)){ts.p.subgridtype.call(ts,dp);}else{ts.p.subgridtype=ts.p.subgridtype.toLowerCase();}switch(ts.p.subgridtype){case'xml':case'json':$.ajax($.extend({type:ts.p.mtype,url:ts.p.subGridUrl,dataType:ts.p.subgridtype,data:$.isFunction(ts.p.serializeSubGridData)?ts.p.serializeSubGridData.call(ts,dp):dp,complete:function complete(sxml){if(ts.p.subgridtype==='xml'){subGridXml(sxml.responseXML,sid);}else{subGridJson($.jgrid.parse(sxml.responseText),sid);}sxml=null;}},$.jgrid.ajaxOptions,ts.p.ajaxSubgridOptions||{}));break;}}return false;};var _id,pID,atd,nhc=0,bfsc,r;$.each(ts.p.colModel,function(){if(this.hidden===true||this.name==='rn'||this.name==='cb'){nhc++;}});var len=ts.rows.length,i=1;if(sind!==undefined&&sind>0){i=sind;len=sind+1;}while(i<len){if($(ts.rows[i]).hasClass('jqgrow')){$(ts.rows[i].cells[pos]).bind('click',function(){var tr=$(this).parent('tr')[0];r=tr.nextSibling;if($(this).hasClass('sgcollapsed')){pID=ts.p.id;_id=tr.id;if(ts.p.subGridOptions.reloadOnExpand===true||ts.p.subGridOptions.reloadOnExpand===false&&!$(r).hasClass('ui-subgrid')){atd=pos>=1?'<td colspan=\''+pos+'\'>&#160;</td>':'';bfsc=$(ts).triggerHandler('jqGridSubGridBeforeExpand',[pID+'_'+_id,_id]);bfsc=bfsc===false||bfsc==='stop'?false:true;if(bfsc&&$.isFunction(ts.p.subGridBeforeExpand)){bfsc=ts.p.subGridBeforeExpand.call(ts,pID+'_'+_id,_id);}if(bfsc===false){return false;}$(tr).after('<tr role=\'row\' class=\'ui-subgrid\'>'+atd+'<td class=\'ui-widget-content subgrid-cell\'><span class=\'ui-icon '+ts.p.subGridOptions.openicon+'\'></span></td><td colspan=\''+parseInt(ts.p.colNames.length-1-nhc,10)+'\' class=\'ui-widget-content subgrid-data\'><div id='+pID+'_'+_id+' class=\'tablediv\'></div></td></tr>');$(ts).triggerHandler('jqGridSubGridRowExpanded',[pID+'_'+_id,_id]);if($.isFunction(ts.p.subGridRowExpanded)){ts.p.subGridRowExpanded.call(ts,pID+'_'+_id,_id);}else{populatesubgrid(tr);}}else{$(r).show();}$(this).html('<a href=\'javascript:void(0);\'><span class=\'ui-icon '+ts.p.subGridOptions.minusicon+'\'></span></a>').removeClass('sgcollapsed').addClass('sgexpanded');if(ts.p.subGridOptions.selectOnExpand){$(ts).jqGrid('setSelection',_id);}}else if($(this).hasClass('sgexpanded')){bfsc=$(ts).triggerHandler('jqGridSubGridRowColapsed',[pID+'_'+_id,_id]);bfsc=bfsc===false||bfsc==='stop'?false:true;if(bfsc&&$.isFunction(ts.p.subGridRowColapsed)){_id=tr.id;bfsc=ts.p.subGridRowColapsed.call(ts,pID+'_'+_id,_id);}if(bfsc===false){return false;}if(ts.p.subGridOptions.reloadOnExpand===true){$(r).remove('.ui-subgrid');}else if($(r).hasClass('ui-subgrid')){// incase of dynamic deleting
$(r).hide();}$(this).html('<a href=\'javascript:void(0);\'><span class=\'ui-icon '+ts.p.subGridOptions.plusicon+'\'></span></a>').removeClass('sgexpanded').addClass('sgcollapsed');}return false;});}i++;}if(ts.p.subGridOptions.expandOnLoad===true){$(ts.rows).filter('.jqgrow').each(function(index,row){$(row.cells[0]).click();});}ts.subGridXml=function(xml,sid){subGridXml(xml,sid);};ts.subGridJson=function(json,sid){subGridJson(json,sid);};});},expandSubGridRow:function expandSubGridRow(rowid){return this.each(function(){var $t=this;if(!$t.grid&&!rowid){return;}if($t.p.subGrid===true){var rc=$(this).jqGrid('getInd',rowid,true);if(rc){var sgc=$('td.sgcollapsed',rc)[0];if(sgc){$(sgc).trigger('click');}}}});},collapseSubGridRow:function collapseSubGridRow(rowid){return this.each(function(){var $t=this;if(!$t.grid&&!rowid){return;}if($t.p.subGrid===true){var rc=$(this).jqGrid('getInd',rowid,true);if(rc){var sgc=$('td.sgexpanded',rc)[0];if(sgc){$(sgc).trigger('click');}}}});},toggleSubGridRow:function toggleSubGridRow(rowid){return this.each(function(){var $t=this;if(!$t.grid&&!rowid){return;}if($t.p.subGrid===true){var rc=$(this).jqGrid('getInd',rowid,true);if(rc){var sgc=$('td.sgcollapsed',rc)[0];if(sgc){$(sgc).trigger('click');}else{sgc=$('td.sgexpanded',rc)[0];if(sgc){$(sgc).trigger('click');}}}}});}});})(jQuery);/**
 * jqGrid extension - Tree Grid
 * Tony Tomov tony@trirand.com
 * http://trirand.com/blog/
 * Dual licensed under the MIT and GPL licenses:
 * http://www.opensource.org/licenses/mit-license.php
 * http://www.gnu.org/licenses/gpl.html
**//*jshint eqeqeq:false *//*global jQuery */(function($){'use strict';$.jgrid.extend({setTreeNode:function setTreeNode(i,len){return this.each(function(){var $t=this;if(!$t.grid||!$t.p.treeGrid){return;}var expCol=$t.p.expColInd,expanded=$t.p.treeReader.expanded_field,isLeaf=$t.p.treeReader.leaf_field,level=$t.p.treeReader.level_field,icon=$t.p.treeReader.icon_field,loaded=$t.p.treeReader.loaded,lft,rgt,curLevel,ident,lftpos,twrap,ldat,lf;while(i<len){var ind=$t.rows[i].id,dind=$t.p._index[ind],expan;ldat=$t.p.data[dind];//$t.rows[i].level = ldat[level];
if($t.p.treeGridModel=='nested'){if(!ldat[isLeaf]){lft=parseInt(ldat[$t.p.treeReader.left_field],10);rgt=parseInt(ldat[$t.p.treeReader.right_field],10);// NS Model
ldat[isLeaf]=rgt===lft+1?'true':'false';$t.rows[i].cells[$t.p._treeleafpos].innerHTML=ldat[isLeaf];}}//else {
//row.parent_id = rd[$t.p.treeReader.parent_id_field];
//}
if(ldat===undefined){i++,len++;continue;}curLevel=parseInt(ldat[level],10);if($t.p.tree_root_level===0){ident=curLevel+1;lftpos=curLevel;}else{ident=curLevel;lftpos=curLevel-1;}twrap='<div class=\'tree-wrap tree-wrap-'+$t.p.direction+'\' style=\'width:'+ident*18+'px;\'>';twrap+='<div style=\''+($t.p.direction=='rtl'?'right:':'left:')+lftpos*18+'px;\' class=\'ui-icon ';if(ldat[loaded]!==undefined){if(ldat[loaded]=='true'||ldat[loaded]===true){ldat[loaded]=true;}else{ldat[loaded]=false;}}if(ldat[isLeaf]=='true'||ldat[isLeaf]===true){twrap+=(ldat[icon]!==undefined&&ldat[icon]!==''?ldat[icon]:$t.p.treeIcons.leaf)+' tree-leaf treeclick';ldat[isLeaf]=true;lf='leaf';}else{ldat[isLeaf]=false;lf='';}ldat[expanded]=(ldat[expanded]=='true'||ldat[expanded]===true?true:false)&&(ldat[loaded]||ldat[loaded]===undefined);if(ldat[expanded]===false){twrap+=ldat[isLeaf]===true?'\'':$t.p.treeIcons.plus+' tree-plus treeclick\'';}else{twrap+=ldat[isLeaf]===true?'\'':$t.p.treeIcons.minus+' tree-minus treeclick\'';}twrap+='></div></div>';$($t.rows[i].cells[expCol]).wrapInner('<span class=\'cell-wrapper'+lf+'\'></span>').prepend(twrap);if(curLevel!==parseInt($t.p.tree_root_level,10)){var pn=$($t).jqGrid('getNodeParent',ldat);expan=pn&&pn.hasOwnProperty(expanded)?pn[expanded]:true;if(!expan){$($t.rows[i]).css('display','none');}}$($t.rows[i].cells[expCol]).find('div.treeclick').bind('click',function(e){var target=e.target||e.srcElement,ind2=$(target,$t.rows).closest('tr.jqgrow')[0].id,pos=$t.p._index[ind2];if(!$t.p.data[pos][isLeaf]){if($t.p.data[pos][expanded]){$($t).jqGrid('collapseRow',$t.p.data[pos]);$($t).jqGrid('collapseNode',$t.p.data[pos]);}else{$($t).jqGrid('expandRow',$t.p.data[pos]);$($t).jqGrid('expandNode',$t.p.data[pos]);}}return false;});if($t.p.ExpandColClick===true){$($t.rows[i].cells[expCol]).find('span.cell-wrapper').css('cursor','pointer').bind('click',function(e){var target=e.target||e.srcElement,ind2=$(target,$t.rows).closest('tr.jqgrow')[0].id,pos=$t.p._index[ind2];if(!$t.p.data[pos][isLeaf]){if($t.p.data[pos][expanded]){$($t).jqGrid('collapseRow',$t.p.data[pos]);$($t).jqGrid('collapseNode',$t.p.data[pos]);}else{$($t).jqGrid('expandRow',$t.p.data[pos]);$($t).jqGrid('expandNode',$t.p.data[pos]);}}$($t).jqGrid('setSelection',ind2);return false;});}i++;}});},setTreeGrid:function setTreeGrid(){return this.each(function(){var $t=this,i=0,pico,ecol=false,nm,key,tkey,dupcols=[];if(!$t.p.treeGrid){return;}if(!$t.p.treedatatype){$.extend($t.p,{treedatatype:$t.p.datatype});}$t.p.subGrid=false;$t.p.altRows=false;$t.p.pgbuttons=false;$t.p.pginput=false;$t.p.gridview=true;if($t.p.rowTotal===null){$t.p.rowNum=10000;}$t.p.multiselect=false;$t.p.rowList=[];$t.p.expColInd=0;pico='ui-icon-triangle-1-'+($t.p.direction=='rtl'?'w':'e');$t.p.treeIcons=$.extend({plus:pico,minus:'ui-icon-triangle-1-s',leaf:'ui-icon-radio-off'},$t.p.treeIcons||{});if($t.p.treeGridModel=='nested'){$t.p.treeReader=$.extend({level_field:'level',left_field:'lft',right_field:'rgt',leaf_field:'isLeaf',expanded_field:'expanded',loaded:'loaded',icon_field:'icon'},$t.p.treeReader);}else if($t.p.treeGridModel=='adjacency'){$t.p.treeReader=$.extend({level_field:'level',parent_id_field:'parent',leaf_field:'isLeaf',expanded_field:'expanded',loaded:'loaded',icon_field:'icon'},$t.p.treeReader);}for(key in $t.p.colModel){if($t.p.colModel.hasOwnProperty(key)){nm=$t.p.colModel[key].name;if(nm==$t.p.ExpandColumn&&!ecol){ecol=true;$t.p.expColInd=i;}i++;//
for(tkey in $t.p.treeReader){if($t.p.treeReader.hasOwnProperty(tkey)&&$t.p.treeReader[tkey]==nm){dupcols.push(nm);}}}}$.each($t.p.treeReader,function(j,n){if(n&&$.inArray(n,dupcols)===-1){if(j==='leaf_field'){$t.p._treeleafpos=i;}i++;$t.p.colNames.push(n);$t.p.colModel.push({name:n,width:1,hidden:true,sortable:false,resizable:false,hidedlg:true,editable:true,search:false});}});});},expandRow:function expandRow(record){this.each(function(){var $t=this;if(!$t.grid||!$t.p.treeGrid){return;}var childern=$($t).jqGrid('getNodeChildren',record),//if ($($t).jqGrid("isVisibleNode",record)) {
expanded=$t.p.treeReader.expanded_field,rows=$t.rows;$(childern).each(function(){var id=$.jgrid.getAccessor(this,$t.p.localReader.id);$(rows.namedItem(id)).css('display','');if(this[expanded]){$($t).jqGrid('expandRow',this);}});//}
});},collapseRow:function collapseRow(record){this.each(function(){var $t=this;if(!$t.grid||!$t.p.treeGrid){return;}var childern=$($t).jqGrid('getNodeChildren',record),expanded=$t.p.treeReader.expanded_field,rows=$t.rows;$(childern).each(function(){var id=$.jgrid.getAccessor(this,$t.p.localReader.id);$(rows.namedItem(id)).css('display','none');if(this[expanded]){$($t).jqGrid('collapseRow',this);}});});},// NS ,adjacency models
getRootNodes:function getRootNodes(){var result=[];this.each(function(){var $t=this;if(!$t.grid||!$t.p.treeGrid){return;}switch($t.p.treeGridModel){case'nested':var level=$t.p.treeReader.level_field;$($t.p.data).each(function(){if(parseInt(this[level],10)===parseInt($t.p.tree_root_level,10)){result.push(this);}});break;case'adjacency':var parent_id=$t.p.treeReader.parent_id_field;$($t.p.data).each(function(){if(this[parent_id]===null||String(this[parent_id]).toLowerCase()=='null'){result.push(this);}});break;}});return result;},getNodeDepth:function getNodeDepth(rc){var ret=null;this.each(function(){if(!this.grid||!this.p.treeGrid){return;}var $t=this;switch($t.p.treeGridModel){case'nested':var level=$t.p.treeReader.level_field;ret=parseInt(rc[level],10)-parseInt($t.p.tree_root_level,10);break;case'adjacency':ret=$($t).jqGrid('getNodeAncestors',rc).length;break;}});return ret;},getNodeParent:function getNodeParent(rc){var result=null;this.each(function(){var $t=this;if(!$t.grid||!$t.p.treeGrid){return;}switch($t.p.treeGridModel){case'nested':var lftc=$t.p.treeReader.left_field,rgtc=$t.p.treeReader.right_field,levelc=$t.p.treeReader.level_field,lft=parseInt(rc[lftc],10),rgt=parseInt(rc[rgtc],10),level=parseInt(rc[levelc],10);$(this.p.data).each(function(){if(parseInt(this[levelc],10)===level-1&&parseInt(this[lftc],10)<lft&&parseInt(this[rgtc],10)>rgt){result=this;return false;}});break;case'adjacency':var parent_id=$t.p.treeReader.parent_id_field,dtid=$t.p.localReader.id;$(this.p.data).each(function(){if(this[dtid]==rc[parent_id]){result=this;return false;}});break;}});return result;},getNodeChildren:function getNodeChildren(rc){var result=[];this.each(function(){var $t=this;if(!$t.grid||!$t.p.treeGrid){return;}switch($t.p.treeGridModel){case'nested':var lftc=$t.p.treeReader.left_field,rgtc=$t.p.treeReader.right_field,levelc=$t.p.treeReader.level_field,lft=parseInt(rc[lftc],10),rgt=parseInt(rc[rgtc],10),level=parseInt(rc[levelc],10);$(this.p.data).each(function(){if(parseInt(this[levelc],10)===level+1&&parseInt(this[lftc],10)>lft&&parseInt(this[rgtc],10)<rgt){result.push(this);}});break;case'adjacency':var parent_id=$t.p.treeReader.parent_id_field,dtid=$t.p.localReader.id;$(this.p.data).each(function(){if(this[parent_id]==rc[dtid]){result.push(this);}});break;}});return result;},getFullTreeNode:function getFullTreeNode(rc){var result=[];this.each(function(){var $t=this,len;if(!$t.grid||!$t.p.treeGrid){return;}switch($t.p.treeGridModel){case'nested':var lftc=$t.p.treeReader.left_field,rgtc=$t.p.treeReader.right_field,levelc=$t.p.treeReader.level_field,lft=parseInt(rc[lftc],10),rgt=parseInt(rc[rgtc],10),level=parseInt(rc[levelc],10);$(this.p.data).each(function(){if(parseInt(this[levelc],10)>=level&&parseInt(this[lftc],10)>=lft&&parseInt(this[lftc],10)<=rgt){result.push(this);}});break;case'adjacency':if(rc){result.push(rc);var parent_id=$t.p.treeReader.parent_id_field,dtid=$t.p.localReader.id;$(this.p.data).each(function(i){len=result.length;for(i=0;i<len;i++){if(result[i][dtid]==this[parent_id]){result.push(this);break;}}});}break;}});return result;},// End NS, adjacency Model
getNodeAncestors:function getNodeAncestors(rc){var ancestors=[];this.each(function(){if(!this.grid||!this.p.treeGrid){return;}var parent=$(this).jqGrid('getNodeParent',rc);while(parent){ancestors.push(parent);parent=$(this).jqGrid('getNodeParent',parent);}});return ancestors;},isVisibleNode:function isVisibleNode(rc){var result=true;this.each(function(){var $t=this;if(!$t.grid||!$t.p.treeGrid){return;}var ancestors=$($t).jqGrid('getNodeAncestors',rc),expanded=$t.p.treeReader.expanded_field;$(ancestors).each(function(){result=result&&this[expanded];if(!result){return false;}});});return result;},isNodeLoaded:function isNodeLoaded(rc){var result;this.each(function(){var $t=this;if(!$t.grid||!$t.p.treeGrid){return;}var isLeaf=$t.p.treeReader.leaf_field;if(rc!==undefined){if(rc.loaded!==undefined){result=rc.loaded;}else if(rc[isLeaf]||$($t).jqGrid('getNodeChildren',rc).length>0){result=true;}else{result=false;}}else{result=false;}});return result;},expandNode:function expandNode(rc){return this.each(function(){if(!this.grid||!this.p.treeGrid){return;}var expanded=this.p.treeReader.expanded_field,parent=this.p.treeReader.parent_id_field,loaded=this.p.treeReader.loaded,level=this.p.treeReader.level_field,lft=this.p.treeReader.left_field,rgt=this.p.treeReader.right_field;if(!rc[expanded]){var id=$.jgrid.getAccessor(rc,this.p.localReader.id);var rc1=$('#'+$.jgrid.jqID(id),this.grid.bDiv)[0];var position=this.p._index[id];if($(this).jqGrid('isNodeLoaded',this.p.data[position])){rc[expanded]=true;$('div.treeclick',rc1).removeClass(this.p.treeIcons.plus+' tree-plus').addClass(this.p.treeIcons.minus+' tree-minus');}else if(!this.grid.hDiv.loading){rc[expanded]=true;$('div.treeclick',rc1).removeClass(this.p.treeIcons.plus+' tree-plus').addClass(this.p.treeIcons.minus+' tree-minus');this.p.treeANode=rc1.rowIndex;this.p.datatype=this.p.treedatatype;if(this.p.treeGridModel=='nested'){$(this).jqGrid('setGridParam',{postData:{nodeid:id,n_left:rc[lft],n_right:rc[rgt],n_level:rc[level]}});}else{$(this).jqGrid('setGridParam',{postData:{nodeid:id,parentid:rc[parent],n_level:rc[level]}});}$(this).trigger('reloadGrid');rc[loaded]=true;if(this.p.treeGridModel=='nested'){$(this).jqGrid('setGridParam',{postData:{nodeid:'',n_left:'',n_right:'',n_level:''}});}else{$(this).jqGrid('setGridParam',{postData:{nodeid:'',parentid:'',n_level:''}});}}}});},collapseNode:function collapseNode(rc){return this.each(function(){if(!this.grid||!this.p.treeGrid){return;}var expanded=this.p.treeReader.expanded_field;if(rc[expanded]){rc[expanded]=false;var id=$.jgrid.getAccessor(rc,this.p.localReader.id);var rc1=$('#'+$.jgrid.jqID(id),this.grid.bDiv)[0];$('div.treeclick',rc1).removeClass(this.p.treeIcons.minus+' tree-minus').addClass(this.p.treeIcons.plus+' tree-plus');}});},SortTree:function SortTree(sortname,newDir,st,datefmt){return this.each(function(){if(!this.grid||!this.p.treeGrid){return;}var i,len,rec,records=[],$t=this,query,roots,rt=$(this).jqGrid('getRootNodes');// Sorting roots
query=$.jgrid.from(rt);query.orderBy(sortname,newDir,st,datefmt);roots=query.select();// Sorting children
for(i=0,len=roots.length;i<len;i++){rec=roots[i];records.push(rec);$(this).jqGrid('collectChildrenSortTree',records,rec,sortname,newDir,st,datefmt);}$.each(records,function(index){var id=$.jgrid.getAccessor(this,$t.p.localReader.id);$('#'+$.jgrid.jqID($t.p.id)+' tbody tr:eq('+index+')').after($('tr#'+$.jgrid.jqID(id),$t.grid.bDiv));});query=null;roots=null;records=null;});},collectChildrenSortTree:function collectChildrenSortTree(records,rec,sortname,newDir,st,datefmt){return this.each(function(){if(!this.grid||!this.p.treeGrid){return;}var i,len,child,ch,query,children;ch=$(this).jqGrid('getNodeChildren',rec);query=$.jgrid.from(ch);query.orderBy(sortname,newDir,st,datefmt);children=query.select();for(i=0,len=children.length;i<len;i++){child=children[i];records.push(child);$(this).jqGrid('collectChildrenSortTree',records,child,sortname,newDir,st,datefmt);}});},// experimental
setTreeRow:function setTreeRow(rowid,data){var success=false;this.each(function(){var t=this;if(!t.grid||!t.p.treeGrid){return;}success=$(t).jqGrid('setRowData',rowid,data);});return success;},delTreeNode:function delTreeNode(rowid){return this.each(function(){var $t=this,rid=$t.p.localReader.id,i,left=$t.p.treeReader.left_field,right=$t.p.treeReader.right_field,myright,width,res,key;if(!$t.grid||!$t.p.treeGrid){return;}var rc=$t.p._index[rowid];if(rc!==undefined){// nested
myright=parseInt($t.p.data[rc][right],10);width=myright-parseInt($t.p.data[rc][left],10)+1;var dr=$($t).jqGrid('getFullTreeNode',$t.p.data[rc]);if(dr.length>0){for(i=0;i<dr.length;i++){$($t).jqGrid('delRowData',dr[i][rid]);}}if($t.p.treeGridModel==='nested'){// ToDo - update grid data
res=$.jgrid.from($t.p.data).greater(left,myright,{stype:'integer'}).select();if(res.length){for(key in res){if(res.hasOwnProperty(key)){res[key][left]=parseInt(res[key][left],10)-width;}}}res=$.jgrid.from($t.p.data).greater(right,myright,{stype:'integer'}).select();if(res.length){for(key in res){if(res.hasOwnProperty(key)){res[key][right]=parseInt(res[key][right],10)-width;}}}}}});},addChildNode:function addChildNode(nodeid,parentid,data,expandData){//return this.each(function(){
var $t=this[0];if(data){// we suppose tha the id is autoincremet and
var expanded=$t.p.treeReader.expanded_field,isLeaf=$t.p.treeReader.leaf_field,level=$t.p.treeReader.level_field,//icon = $t.p.treeReader.icon_field,
parent=$t.p.treeReader.parent_id_field,left=$t.p.treeReader.left_field,right=$t.p.treeReader.right_field,loaded=$t.p.treeReader.loaded,method,parentindex,parentdata,parentlevel,i,len,max=0,rowind=parentid,leaf,maxright;if(expandData===undefined){expandData=false;}if(nodeid===undefined||nodeid===null){i=$t.p.data.length-1;if(i>=0){while(i>=0){max=Math.max(max,parseInt($t.p.data[i][$t.p.localReader.id],10));i--;}}nodeid=max+1;}var prow=$($t).jqGrid('getInd',parentid);leaf=false;// if not a parent we assume root
if(parentid===undefined||parentid===null||parentid===''){parentid=null;rowind=null;method='last';parentlevel=$t.p.tree_root_level;i=$t.p.data.length+1;}else{method='after';parentindex=$t.p._index[parentid];parentdata=$t.p.data[parentindex];parentid=parentdata[$t.p.localReader.id];parentlevel=parseInt(parentdata[level],10)+1;var childs=$($t).jqGrid('getFullTreeNode',parentdata);// if there are child nodes get the last index of it
if(childs.length){i=childs[childs.length-1][$t.p.localReader.id];rowind=i;i=$($t).jqGrid('getInd',rowind)+1;}else{i=$($t).jqGrid('getInd',parentid)+1;}// if the node is leaf
if(parentdata[isLeaf]){leaf=true;parentdata[expanded]=true;//var prow = $($t).jqGrid('getInd', parentid);
$($t.rows[prow]).find('span.cell-wrapperleaf').removeClass('cell-wrapperleaf').addClass('cell-wrapper').end().find('div.tree-leaf').removeClass($t.p.treeIcons.leaf+' tree-leaf').addClass($t.p.treeIcons.minus+' tree-minus');$t.p.data[parentindex][isLeaf]=false;parentdata[loaded]=true;}}len=i+1;if(data[expanded]===undefined){data[expanded]=false;}if(data[loaded]===undefined){data[loaded]=false;}data[level]=parentlevel;if(data[isLeaf]===undefined){data[isLeaf]=true;}if($t.p.treeGridModel==='adjacency'){data[parent]=parentid;}if($t.p.treeGridModel==='nested'){// this method requiere more attention
var query,res,key;//maxright = parseInt(maxright,10);
// ToDo - update grid data
if(parentid!==null){maxright=parseInt(parentdata[right],10);query=$.jgrid.from($t.p.data);query=query.greaterOrEquals(right,maxright,{stype:'integer'});res=query.select();if(res.length){for(key in res){if(res.hasOwnProperty(key)){res[key][left]=res[key][left]>maxright?parseInt(res[key][left],10)+2:res[key][left];res[key][right]=res[key][right]>=maxright?parseInt(res[key][right],10)+2:res[key][right];}}}data[left]=maxright;data[right]=maxright+1;}else{maxright=parseInt($($t).jqGrid('getCol',right,false,'max'),10);res=$.jgrid.from($t.p.data).greater(left,maxright,{stype:'integer'}).select();if(res.length){for(key in res){if(res.hasOwnProperty(key)){res[key][left]=parseInt(res[key][left],10)+2;}}}res=$.jgrid.from($t.p.data).greater(right,maxright,{stype:'integer'}).select();if(res.length){for(key in res){if(res.hasOwnProperty(key)){res[key][right]=parseInt(res[key][right],10)+2;}}}data[left]=maxright+1;data[right]=maxright+2;}}if(parentid===null||$($t).jqGrid('isNodeLoaded',parentdata)||leaf){$($t).jqGrid('addRowData',nodeid,data,method,rowind);$($t).jqGrid('setTreeNode',i,len);}if(parentdata&&!parentdata[expanded]&&expandData){$($t.rows[prow]).find('div.treeclick').click();}}//});
}});})(jQuery);/*jshint eqeqeq:false, eqnull:true *//*global jQuery */// Grouping module
(function($){'use strict';$.extend($.jgrid,{template:function template(format){//jqgformat
var args=$.makeArray(arguments).slice(1),j,al=args.length;if(format==null){format='';}return format.replace(/\{([\w\-]+)(?:\:([\w\.]*)(?:\((.*?)?\))?)?\}/g,function(m,i){if(!isNaN(parseInt(i,10))){return args[parseInt(i,10)];}for(j=0;j<al;j++){if($.isArray(args[j])){var nmarr=args[j],k=nmarr.length;while(k--){if(i===nmarr[k].nm){return nmarr[k].v;}}}}});}});$.jgrid.extend({groupingSetup:function groupingSetup(){return this.each(function(){var $t=this,i,j,cml,cm=$t.p.colModel,grp=$t.p.groupingView;if(grp!==null&&((typeof grp==="undefined"?"undefined":_typeof(grp))==='object'||$.isFunction(grp))){if(!grp.groupField.length){$t.p.grouping=false;}else{if(grp.visibiltyOnNextGrouping===undefined){grp.visibiltyOnNextGrouping=[];}grp.lastvalues=[];grp.groups=[];grp.counters=[];for(i=0;i<grp.groupField.length;i++){if(!grp.groupOrder[i]){grp.groupOrder[i]='';}if(!grp.groupText[i]){grp.groupText[i]='{0}';}if(typeof grp.groupColumnShow[i]!=='boolean'){grp.groupColumnShow[i]=true;}if(typeof grp.groupSummary[i]!=='boolean'){grp.groupSummary[i]=false;}if(grp.groupColumnShow[i]===true){grp.visibiltyOnNextGrouping[i]=true;$($t).jqGrid('showCol',grp.groupField[i]);}else{grp.visibiltyOnNextGrouping[i]=$('#'+$.jgrid.jqID($t.p.id+'_'+grp.groupField[i])).is(':visible');$($t).jqGrid('hideCol',grp.groupField[i]);}}grp.summary=[];for(j=0,cml=cm.length;j<cml;j++){if(cm[j].summaryType){grp.summary.push({nm:cm[j].name,st:cm[j].summaryType,v:'',sr:cm[j].summaryRound,srt:cm[j].summaryRoundType||'round'});}}}}else{$t.p.grouping=false;}});},groupingPrepare:function groupingPrepare(rData,gdata,record,irow){this.each(function(){var grp=this.p.groupingView,$t=this,i,grlen=grp.groupField.length,fieldName,v,displayName,displayValue,changed=0;for(i=0;i<grlen;i++){fieldName=grp.groupField[i];displayName=grp.displayField[i];v=record[fieldName];displayValue=displayName==null?null:record[displayName];if(displayValue==null){displayValue=v;}if(v!==undefined){if(irow===0){// First record always starts a new group
grp.groups.push({idx:i,dataIndex:fieldName,value:v,displayValue:displayValue,startRow:irow,cnt:1,summary:[]});grp.lastvalues[i]=v;grp.counters[i]={cnt:1,pos:grp.groups.length-1,summary:$.extend(true,[],grp.summary)};$.each(grp.counters[i].summary,function(){if($.isFunction(this.st)){this.v=this.st.call($t,this.v,this.nm,record);}else{this.v=$($t).jqGrid('groupingCalculations.handler',this.st,this.v,this.nm,this.sr,this.srt,record);}});grp.groups[grp.counters[i].pos].summary=grp.counters[i].summary;}else{if((typeof v==="undefined"?"undefined":_typeof(v))!=='object'&&grp.lastvalues[i]!==v){// This record is not in same group as previous one
grp.groups.push({idx:i,dataIndex:fieldName,value:v,displayValue:displayValue,startRow:irow,cnt:1,summary:[]});grp.lastvalues[i]=v;changed=1;grp.counters[i]={cnt:1,pos:grp.groups.length-1,summary:$.extend(true,[],grp.summary)};$.each(grp.counters[i].summary,function(){if($.isFunction(this.st)){this.v=this.st.call($t,this.v,this.nm,record);}else{this.v=$($t).jqGrid('groupingCalculations.handler',this.st,this.v,this.nm,this.sr,this.srt,record);}});grp.groups[grp.counters[i].pos].summary=grp.counters[i].summary;}else{if(changed===1){// This group has changed because an earlier group changed.
grp.groups.push({idx:i,dataIndex:fieldName,value:v,displayValue:displayValue,startRow:irow,cnt:1,summary:[]});grp.lastvalues[i]=v;grp.counters[i]={cnt:1,pos:grp.groups.length-1,summary:$.extend(true,[],grp.summary)};$.each(grp.counters[i].summary,function(){if($.isFunction(this.st)){this.v=this.st.call($t,this.v,this.nm,record);}else{this.v=$($t).jqGrid('groupingCalculations.handler',this.st,this.v,this.nm,this.sr,this.srt,record);}});grp.groups[grp.counters[i].pos].summary=grp.counters[i].summary;}else{grp.counters[i].cnt+=1;grp.groups[grp.counters[i].pos].cnt=grp.counters[i].cnt;$.each(grp.counters[i].summary,function(){if($.isFunction(this.st)){this.v=this.st.call($t,this.v,this.nm,record);}else{this.v=$($t).jqGrid('groupingCalculations.handler',this.st,this.v,this.nm,this.sr,this.srt,record);}});grp.groups[grp.counters[i].pos].summary=grp.counters[i].summary;}}}}}gdata.push(rData);});return gdata;},groupingToggle:function groupingToggle(hid){this.each(function(){var $t=this,grp=$t.p.groupingView,strpos=hid.split('_'),//uid = hid.substring(0,strpos+1),
num=parseInt(strpos[strpos.length-2],10);strpos.splice(strpos.length-2,2);var uid=strpos.join('_'),minus=grp.minusicon,plus=grp.plusicon,tar=$('#'+$.jgrid.jqID(hid)),r=tar.length?tar[0].nextSibling:null,tarspan=$('#'+$.jgrid.jqID(hid)+' span.'+'tree-wrap-'+$t.p.direction),collapsed=false,tspan;if(tarspan.hasClass(minus)){if(grp.showSummaryOnHide){if(r){while(r){if($(r).hasClass('jqfoot')){var lv=parseInt($(r).attr('jqfootlevel'),10);if(lv<=num){break;}}$(r).hide();r=r.nextSibling;}}}else{if(r){while(r){if($(r).hasClass(uid+'_'+String(num))||$(r).hasClass(uid+'_'+String(num-1))){break;}$(r).hide();r=r.nextSibling;}}}tarspan.removeClass(minus).addClass(plus);collapsed=true;}else{if(r){while(r){if($(r).hasClass(uid+'_'+String(num))||$(r).hasClass(uid+'_'+String(num-1))){break;}$(r).show();tspan=$(r).find('span.'+'tree-wrap-'+$t.p.direction);if(tspan&&$(tspan).hasClass(plus)){$(tspan).removeClass(plus).addClass(minus);}r=r.nextSibling;}}tarspan.removeClass(plus).addClass(minus);}$($t).triggerHandler('jqGridGroupingClickGroup',[hid,collapsed]);if($.isFunction($t.p.onClickGroup)){$t.p.onClickGroup.call($t,hid,collapsed);}});return false;},groupingRender:function groupingRender(grdata,colspans){return this.each(function(){var $t=this,grp=$t.p.groupingView,str='',icon='',hid,clid,pmrtl=grp.groupCollapse?grp.plusicon:grp.minusicon,gv,cp=[],len=grp.groupField.length;pmrtl+=' tree-wrap-'+$t.p.direction;$.each($t.p.colModel,function(i,n){var ii;for(ii=0;ii<len;ii++){if(grp.groupField[ii]===n.name){cp[ii]=i;break;}}});var toEnd=0;function findGroupIdx(ind,offset,grp){var ret=false,i;if(offset===0){ret=grp[ind];}else{var id=grp[ind].idx;if(id===0){ret=grp[ind];}else{for(i=ind;i>=0;i--){if(grp[i].idx===id-offset){ret=grp[i];break;}}}}return ret;}var sumreverse=$.makeArray(grp.groupSummary);sumreverse.reverse();$.each(grp.groups,function(i,n){toEnd++;clid=$t.p.id+'ghead_'+n.idx;hid=clid+'_'+i;icon='<span style=\'cursor:pointer;\' class=\'ui-icon '+pmrtl+'\' onclick="jQuery(\'#'+$.jgrid.jqID($t.p.id)+'\').jqGrid(\'groupingToggle\',\''+hid+'\');return false;"></span>';try{gv=$t.formatter(hid,n.displayValue,cp[n.idx],n.value);}catch(egv){gv=n.displayValue;}str+='<tr id="'+hid+'" role="row" class= "ui-widget-content jqgroup ui-row-'+$t.p.direction+' '+clid+'"><td style="padding-left:'+n.idx*12+'px;'+'" colspan="'+colspans+'">'+icon+$.jgrid.template(grp.groupText[n.idx],gv,n.cnt,n.summary)+'</td></tr>';var leaf=len-1===n.idx;if(leaf){var gg=grp.groups[i+1],k,kk,ik;var end=gg!==undefined?grp.groups[i+1].startRow:grdata.length;for(kk=n.startRow;kk<end;kk++){str+=grdata[kk].join('');}var jj;if(gg!==undefined){for(jj=0;jj<grp.groupField.length;jj++){if(gg.dataIndex===grp.groupField[jj]){break;}}toEnd=grp.groupField.length-jj;}for(ik=0;ik<toEnd;ik++){if(!sumreverse[ik]){continue;}var hhdr='';if(grp.groupCollapse&&!grp.showSummaryOnHide){hhdr=' style="display:none;"';}str+='<tr'+hhdr+' jqfootlevel="'+(n.idx-ik)+'" role="row" class="ui-widget-content jqfoot ui-row-'+$t.p.direction+'">';var fdata=findGroupIdx(i,ik,grp.groups),cm=$t.p.colModel,vv,grlen=fdata.cnt;for(k=0;k<colspans;k++){var tmpdata='<td '+$t.formatCol(k,1,'')+'>&#160;</td>',tplfld='{0}';$.each(fdata.summary,function(){if(this.nm===cm[k].name){if(cm[k].summaryTpl){tplfld=cm[k].summaryTpl;}if(typeof this.st==='string'&&this.st.toLowerCase()==='avg'){if(this.v&&grlen>0){this.v=this.v/grlen;}}try{vv=$t.formatter('',this.v,k,this);}catch(ef){vv=this.v;}tmpdata='<td '+$t.formatCol(k,1,'')+'>'+$.jgrid.format(tplfld,vv)+'</td>';return false;}});str+=tmpdata;}str+='</tr>';}toEnd=jj;}});$('#'+$.jgrid.jqID($t.p.id)+' tbody:first').append(str);// free up memory
str=null;});},groupingGroupBy:function groupingGroupBy(name,options){return this.each(function(){var $t=this;if(typeof name==='string'){name=[name];}var grp=$t.p.groupingView;$t.p.grouping=true;//Set default, in case visibilityOnNextGrouping is undefined
if(grp.visibiltyOnNextGrouping===undefined){grp.visibiltyOnNextGrouping=[];}var i;// show previous hidden groups if they are hidden and weren't removed yet
for(i=0;i<grp.groupField.length;i++){if(!grp.groupColumnShow[i]&&grp.visibiltyOnNextGrouping[i]){$($t).jqGrid('showCol',grp.groupField[i]);}}// set visibility status of current group columns on next grouping
for(i=0;i<name.length;i++){grp.visibiltyOnNextGrouping[i]=$('#'+$.jgrid.jqID($t.p.id)+'_'+$.jgrid.jqID(name[i])).is(':visible');}$t.p.groupingView=$.extend($t.p.groupingView,options||{});grp.groupField=name;$($t).trigger('reloadGrid');});},groupingRemove:function groupingRemove(current){return this.each(function(){var $t=this;if(current===undefined){current=true;}$t.p.grouping=false;if(current===true){var grp=$t.p.groupingView,i;// show previous hidden groups if they are hidden and weren't removed yet
for(i=0;i<grp.groupField.length;i++){if(!grp.groupColumnShow[i]&&grp.visibiltyOnNextGrouping[i]){$($t).jqGrid('showCol',grp.groupField);}}$('tr.jqgroup, tr.jqfoot','#'+$.jgrid.jqID($t.p.id)+' tbody:first').remove();$('tr.jqgrow:hidden','#'+$.jgrid.jqID($t.p.id)+' tbody:first').show();}else{$($t).trigger('reloadGrid');}});},groupingCalculations:{handler:function handler(fn,v,field,round,roundType,rc){var funcs={sum:function sum(){return parseFloat(v||0)+parseFloat(rc[field]||0);},min:function min(){if(v===''){return parseFloat(rc[field]||0);}return Math.min(parseFloat(v),parseFloat(rc[field]||0));},max:function max(){if(v===''){return parseFloat(rc[field]||0);}return Math.max(parseFloat(v),parseFloat(rc[field]||0));},count:function count(){if(v===''){v=0;}if(rc.hasOwnProperty(field)){return v+1;}return 0;},avg:function avg(){// the same as sum, but at end we divide it
// so use sum instead of duplicating the code (?)
return funcs.sum();}};if(!funcs[fn]){throw'jqGrid Grouping No such method: '+fn;}var res=funcs[fn]();if(round!=null){if(roundType=='fixed'){res=res.toFixed(round);}else{var mul=Math.pow(10,round);res=Math.round(res*mul)/mul;}}return res;}}});})(jQuery);/*jshint eqeqeq:false, eqnull:true, devel:true *//*global jQuery, xmlJsonClass */(function($){/*
 * jqGrid extension for constructing Grid Data from external file
 * Tony Tomov tony@trirand.com
 * http://trirand.com/blog/
 * Dual licensed under the MIT and GPL licenses:
 * http://www.opensource.org/licenses/mit-license.php
 * http://www.gnu.org/licenses/gpl-2.0.html
**/'use strict';$.jgrid.extend({jqGridImport:function jqGridImport(o){o=$.extend({imptype:'xml',// xml, json, xmlstring, jsonstring
impstring:'',impurl:'',mtype:'GET',impData:{},xmlGrid:{config:'roots>grid',data:'roots>rows'},jsonGrid:{config:'grid',data:'data'},ajaxOptions:{}},o||{});return this.each(function(){var $t=this;var xmlConvert=function xmlConvert(xml,o){var cnfg=$(o.xmlGrid.config,xml)[0];var xmldata=$(o.xmlGrid.data,xml)[0],jstr,jstr1,key;if(xmlJsonClass.xml2json&&$.jgrid.parse){jstr=xmlJsonClass.xml2json(cnfg,' ');jstr=$.jgrid.parse(jstr);for(key in jstr){if(jstr.hasOwnProperty(key)){jstr1=jstr[key];}}if(xmldata){// save the datatype
var svdatatype=jstr.grid.datatype;jstr.grid.datatype='xmlstring';jstr.grid.datastr=xml;$($t).jqGrid(jstr1).jqGrid('setGridParam',{datatype:svdatatype});}else{$($t).jqGrid(jstr1);}jstr=null;jstr1=null;}else{alert('xml2json or parse are not present');}};var jsonConvert=function jsonConvert(jsonstr,o){if(jsonstr&&typeof jsonstr=='string'){var _jsonparse=false;if($.jgrid.useJSON){$.jgrid.useJSON=false;_jsonparse=true;}var json=$.jgrid.parse(jsonstr);if(_jsonparse){$.jgrid.useJSON=true;}var gprm=json[o.jsonGrid.config];var jdata=json[o.jsonGrid.data];if(jdata){var svdatatype=gprm.datatype;gprm.datatype='jsonstring';gprm.datastr=jdata;$($t).jqGrid(gprm).jqGrid('setGridParam',{datatype:svdatatype});}else{$($t).jqGrid(gprm);}}};switch(o.imptype){case'xml':$.ajax($.extend({url:o.impurl,type:o.mtype,data:o.impData,dataType:'xml',complete:function complete(xml,stat){if(stat=='success'){xmlConvert(xml.responseXML,o);$($t).triggerHandler('jqGridImportComplete',[xml,o]);if($.isFunction(o.importComplete)){o.importComplete(xml);}}xml=null;}},o.ajaxOptions));break;case'xmlstring':// we need to make just the conversion and use the same code as xml
if(o.impstring&&typeof o.impstring=='string'){var xmld=$.jgrid.stringToDoc(o.impstring);if(xmld){xmlConvert(xmld,o);$($t).triggerHandler('jqGridImportComplete',[xmld,o]);if($.isFunction(o.importComplete)){o.importComplete(xmld);}o.impstring=null;}xmld=null;}break;case'json':$.ajax($.extend({url:o.impurl,type:o.mtype,data:o.impData,dataType:'json',complete:function complete(json){try{jsonConvert(json.responseText,o);$($t).triggerHandler('jqGridImportComplete',[json,o]);if($.isFunction(o.importComplete)){o.importComplete(json);}}catch(ee){}json=null;}},o.ajaxOptions));break;case'jsonstring':if(o.impstring&&typeof o.impstring=='string'){jsonConvert(o.impstring,o);$($t).triggerHandler('jqGridImportComplete',[o.impstring,o]);if($.isFunction(o.importComplete)){o.importComplete(o.impstring);}o.impstring=null;}break;}});},jqGridExport:function jqGridExport(o){o=$.extend({exptype:'xmlstring',root:'grid',ident:'\t'},o||{});var ret=null;this.each(function(){if(!this.grid){return;}var key,gprm=$.extend(true,{},$(this).jqGrid('getGridParam'));// we need to check for:
// 1.multiselect, 2.subgrid  3. treegrid and remove the unneded columns from colNames
if(gprm.rownumbers){gprm.colNames.splice(0,1);gprm.colModel.splice(0,1);}if(gprm.multiselect){gprm.colNames.splice(0,1);gprm.colModel.splice(0,1);}if(gprm.subGrid){gprm.colNames.splice(0,1);gprm.colModel.splice(0,1);}gprm.knv=null;if(gprm.treeGrid){for(key in gprm.treeReader){if(gprm.treeReader.hasOwnProperty(key)){gprm.colNames.splice(gprm.colNames.length-1);gprm.colModel.splice(gprm.colModel.length-1);}}}switch(o.exptype){case'xmlstring':ret='<'+o.root+'>'+xmlJsonClass.json2xml(gprm,o.ident)+'</'+o.root+'>';break;case'jsonstring':ret='{'+xmlJsonClass.toJson(gprm,o.root,o.ident,false)+'}';if(gprm.postData.filters!==undefined){ret=ret.replace(/filters":"/,'filters":');ret=ret.replace(/}]}"/,'}]}');}break;}});return ret;},excelExport:function excelExport(o){o=$.extend({exptype:'remote',url:null,oper:'oper',tag:'excel',exportOptions:{}},o||{});return this.each(function(){if(!this.grid){return;}var url;if(o.exptype=='remote'){var pdata=$.extend({},this.p.postData);pdata[o.oper]=o.tag;var params=jQuery.param(pdata);if(o.url.indexOf('?')!=-1){url=o.url+'&'+params;}else{url=o.url+'?'+params;}window.location=url;}});}});})(jQuery);/*jshint evil:true, eqeqeq:false, eqnull:true, devel:true *//*global jQuery */(function($){/*
**
 * jqGrid addons using jQuery UI
 * Author: Mark Williams
 * Dual licensed under the MIT and GPL licenses:
 * http://www.opensource.org/licenses/mit-license.php
 * http://www.gnu.org/licenses/gpl-2.0.html
 * depends on jQuery UI
**/'use strict';if($.jgrid.msie&&$.jgrid.msiever()==8){$.expr[':'].hidden=function(elem){return elem.offsetWidth===0||elem.offsetHeight===0||elem.style.display=='none';};}// requiere load multiselect before grid
$.jgrid._multiselect=false;if($.ui){if($.ui.multiselect){if($.ui.multiselect.prototype._setSelected){var setSelected=$.ui.multiselect.prototype._setSelected;$.ui.multiselect.prototype._setSelected=function(item,selected){var ret=setSelected.call(this,item,selected);if(selected&&this.selectedList){var elt=this.element;this.selectedList.find('li').each(function(){if($(this).data('optionLink')){$(this).data('optionLink').remove().appendTo(elt);}});}return ret;};}if($.ui.multiselect.prototype.destroy){$.ui.multiselect.prototype.destroy=function(){this.element.show();this.container.remove();if($.Widget===undefined){$.widget.prototype.destroy.apply(this,arguments);}else{$.Widget.prototype.destroy.apply(this,arguments);}};}$.jgrid._multiselect=true;}}$.jgrid.extend({sortableColumns:function sortableColumns(tblrow){return this.each(function(){var ts=this,tid=$.jgrid.jqID(ts.p.id);function start(){ts.p.disableClick=true;}var sortable_opts={'tolerance':'pointer','axis':'x','scrollSensitivity':'1','items':'>th:not(:has(#jqgh_'+tid+'_cb'+',#jqgh_'+tid+'_rn'+',#jqgh_'+tid+'_subgrid),:hidden)','placeholder':{element:function element(item){var el=$(document.createElement(item[0].nodeName)).addClass(item[0].className+' ui-sortable-placeholder ui-state-highlight').removeClass('ui-sortable-helper')[0];return el;},update:function update(self,p){p.height(self.currentItem.innerHeight()-parseInt(self.currentItem.css('paddingTop')||0,10)-parseInt(self.currentItem.css('paddingBottom')||0,10));p.width(self.currentItem.innerWidth()-parseInt(self.currentItem.css('paddingLeft')||0,10)-parseInt(self.currentItem.css('paddingRight')||0,10));}},'update':function update(event,ui){var p=$(ui.item).parent(),th=$('>th',p),colModel=ts.p.colModel,cmMap={},tid=ts.p.id+'_';$.each(colModel,function(i){cmMap[this.name]=i;});var permutation=[];th.each(function(){var id=$('>div',this).get(0).id.replace(/^jqgh_/,'').replace(tid,'');if(cmMap.hasOwnProperty(id)){permutation.push(cmMap[id]);}});$(ts).jqGrid('remapColumns',permutation,true,true);if($.isFunction(ts.p.sortable.update)){ts.p.sortable.update(permutation);}setTimeout(function(){ts.p.disableClick=false;},50);}};if(ts.p.sortable.options){$.extend(sortable_opts,ts.p.sortable.options);}else if($.isFunction(ts.p.sortable)){ts.p.sortable={'update':ts.p.sortable};}if(sortable_opts.start){var s=sortable_opts.start;sortable_opts.start=function(e,ui){start();s.call(this,e,ui);};}else{sortable_opts.start=start;}if(ts.p.sortable.exclude){sortable_opts.items+=':not('+ts.p.sortable.exclude+')';}tblrow.sortable(sortable_opts).data('sortable').floating=true;});},columnChooser:function columnChooser(opts){var self=this;if($('#colchooser_'+$.jgrid.jqID(self[0].p.id)).length){return;}var selector=$('<div id="colchooser_'+self[0].p.id+'" style="position:relative;overflow:hidden"><div><select multiple="multiple"></select></div></div>');var select=$('select',selector);function insert(perm,i,v){if(i>=0){var a=perm.slice();var b=a.splice(i,Math.max(perm.length-i,i));if(i>perm.length){i=perm.length;}a[i]=v;return a.concat(b);}}opts=$.extend({'width':420,'height':240,'classname':null,'done':function done(perm){if(perm){self.jqGrid('remapColumns',perm,true);}},/* msel is either the name of a ui widget class that
               extends a multiselect, or a function that supports
               creating a multiselect object (with no argument,
               or when passed an object), and destroying it (when
               passed the string "destroy"). */'msel':'multiselect',/* "msel_opts" : {}, *//* dlog is either the name of a ui widget class that
               behaves in a dialog-like way, or a function, that
               supports creating a dialog (when passed dlog_opts)
               or destroying a dialog (when passed the string
               "destroy")
               */'dlog':'dialog','dialog_opts':{'minWidth':470},/* dlog_opts is either an option object to be passed
               to "dlog", or (more likely) a function that creates
               the options object.
               The default produces a suitable options object for
               ui.dialog */'dlog_opts':function dlog_opts(opts){var buttons={};buttons[opts.bSubmit]=function(){opts.apply_perm();opts.cleanup(false);};buttons[opts.bCancel]=function(){opts.cleanup(true);};return $.extend(true,{'buttons':buttons,'close':function close(){opts.cleanup(true);},'modal':opts.modal||false,'resizable':opts.resizable||true,'width':opts.width+20},opts.dialog_opts||{});},/* Function to get the permutation array, and pass it to the
               "done" function */'apply_perm':function apply_perm(){$('option',select).each(function(){if(this.selected){self.jqGrid('showCol',colModel[this.value].name);}else{self.jqGrid('hideCol',colModel[this.value].name);}});var perm=[];//fixedCols.slice(0);
$('option:selected',select).each(function(){perm.push(parseInt(this.value,10));});$.each(perm,function(){delete colMap[colModel[parseInt(this,10)].name];});$.each(colMap,function(){var ti=parseInt(this,10);perm=insert(perm,ti,ti);});if(opts.done){opts.done.call(self,perm);}},/* Function to cleanup the dialog, and select. Also calls the
               done function with no permutation (to indicate that the
               columnChooser was aborted */'cleanup':function cleanup(calldone){call(opts.dlog,selector,'destroy');call(opts.msel,select,'destroy');selector.remove();if(calldone&&opts.done){opts.done.call(self);}},'msel_opts':{}},$.jgrid.col,opts||{});if($.ui){if($.ui.multiselect){if(opts.msel=='multiselect'){if(!$.jgrid._multiselect){// should be in language file
alert('Multiselect plugin loaded after jqGrid. Please load the plugin before the jqGrid!');return;}opts.msel_opts=$.extend($.ui.multiselect.defaults,opts.msel_opts);}}}if(opts.caption){selector.attr('title',opts.caption);}if(opts.classname){selector.addClass(opts.classname);select.addClass(opts.classname);}if(opts.width){$('>div',selector).css({'width':opts.width,'margin':'0 auto'});select.css('width',opts.width);}if(opts.height){$('>div',selector).css('height',opts.height);select.css('height',opts.height-10);}var colModel=self.jqGrid('getGridParam','colModel');var colNames=self.jqGrid('getGridParam','colNames');var colMap={},fixedCols=[];select.empty();$.each(colModel,function(i){colMap[this.name]=i;if(this.hidedlg){if(!this.hidden){fixedCols.push(i);}return;}select.append('<option value=\''+i+'\' '+(this.hidden?'':'selected=\'selected\'')+'>'+$.jgrid.stripHtml(colNames[i])+'</option>');});function call(fn,obj){if(!fn){return;}if(typeof fn=='string'){if($.fn[fn]){$.fn[fn].apply(obj,$.makeArray(arguments).slice(2));}}else if($.isFunction(fn)){fn.apply(obj,$.makeArray(arguments).slice(2));}}var dopts=$.isFunction(opts.dlog_opts)?opts.dlog_opts.call(self,opts):opts.dlog_opts;call(opts.dlog,selector,dopts);var mopts=$.isFunction(opts.msel_opts)?opts.msel_opts.call(self,opts):opts.msel_opts;call(opts.msel,select,mopts);},sortableRows:function sortableRows(opts){// Can accept all sortable options and events
return this.each(function(){var $t=this;if(!$t.grid){return;}// Currently we disable a treeGrid sortable
if($t.p.treeGrid){return;}if($.fn.sortable){opts=$.extend({'cursor':'move','axis':'y','items':'.jqgrow'},opts||{});if(opts.start&&$.isFunction(opts.start)){opts._start_=opts.start;delete opts.start;}else{opts._start_=false;}if(opts.update&&$.isFunction(opts.update)){opts._update_=opts.update;delete opts.update;}else{opts._update_=false;}opts.start=function(ev,ui){$(ui.item).css('border-width','0px');$('td',ui.item).each(function(i){this.style.width=$t.grid.cols[i].style.width;});if($t.p.subGrid){var subgid=$(ui.item).attr('id');try{$($t).jqGrid('collapseSubGridRow',subgid);}catch(e){}}if(opts._start_){opts._start_.apply(this,[ev,ui]);}};opts.update=function(ev,ui){$(ui.item).css('border-width','');if($t.p.rownumbers===true){$('td.jqgrid-rownum',$t.rows).each(function(i){$(this).html(i+1+(parseInt($t.p.page,10)-1)*parseInt($t.p.rowNum,10));});}if(opts._update_){opts._update_.apply(this,[ev,ui]);}};$('tbody:first',$t).sortable(opts);$('tbody:first',$t).disableSelection();}});},gridDnD:function gridDnD(opts){return this.each(function(){var $t=this,i,cn;if(!$t.grid){return;}// Currently we disable a treeGrid drag and drop
if($t.p.treeGrid){return;}if(!$.fn.draggable||!$.fn.droppable){return;}function updateDnD(){var datadnd=$.data($t,'dnd');$('tr.jqgrow:not(.ui-draggable)',$t).draggable($.isFunction(datadnd.drag)?datadnd.drag.call($($t),datadnd):datadnd.drag);}var appender='<table id=\'jqgrid_dnd\' class=\'ui-jqgrid-dnd\'></table>';if($('#jqgrid_dnd')[0]===undefined){$('body').append(appender);}if(typeof opts=='string'&&opts=='updateDnD'&&$t.p.jqgdnd===true){updateDnD();return;}opts=$.extend({'drag':function drag(opts){return $.extend({start:function start(ev,ui){var i,subgid;// if we are in subgrid mode try to collapse the node
if($t.p.subGrid){subgid=$(ui.helper).attr('id');try{$($t).jqGrid('collapseSubGridRow',subgid);}catch(e){}}// hack
// drag and drop does not insert tr in table, when the table has no rows
// we try to insert new empty row on the target(s)
for(i=0;i<$.data($t,'dnd').connectWith.length;i++){if($($.data($t,'dnd').connectWith[i]).jqGrid('getGridParam','reccount')=='0'){$($.data($t,'dnd').connectWith[i]).jqGrid('addRowData','jqg_empty_row',{});}}ui.helper.addClass('ui-state-highlight');$('td',ui.helper).each(function(i){this.style.width=$t.grid.headers[i].width+'px';});if(opts.onstart&&$.isFunction(opts.onstart)){opts.onstart.call($($t),ev,ui);}},stop:function stop(ev,ui){var i,ids;if(ui.helper.dropped&&!opts.dragcopy){ids=$(ui.helper).attr('id');if(ids===undefined){ids=$(this).attr('id');}$($t).jqGrid('delRowData',ids);}// if we have a empty row inserted from start event try to delete it
for(i=0;i<$.data($t,'dnd').connectWith.length;i++){$($.data($t,'dnd').connectWith[i]).jqGrid('delRowData','jqg_empty_row');}if(opts.onstop&&$.isFunction(opts.onstop)){opts.onstop.call($($t),ev,ui);}}},opts.drag_opts||{});},'drop':function drop(opts){return $.extend({accept:function accept(d){if(!$(d).hasClass('jqgrow')){return d;}var tid=$(d).closest('table.ui-jqgrid-btable');if(tid.length>0&&$.data(tid[0],'dnd')!==undefined){var cn=$.data(tid[0],'dnd').connectWith;return $.inArray('#'+$.jgrid.jqID(this.id),cn)!=-1?true:false;}return false;},drop:function drop(ev,ui){if(!$(ui.draggable).hasClass('jqgrow')){return;}var accept=$(ui.draggable).attr('id');var getdata=ui.draggable.parent().parent().jqGrid('getRowData',accept);if(!opts.dropbyname){var j=0,tmpdata={},nm,key;var dropmodel=$('#'+$.jgrid.jqID(this.id)).jqGrid('getGridParam','colModel');try{for(key in getdata){if(getdata.hasOwnProperty(key)){nm=dropmodel[j].name;if(!(nm=='cb'||nm=='rn'||nm=='subgrid')){if(getdata.hasOwnProperty(key)&&dropmodel[j]){tmpdata[nm]=getdata[key];}}j++;}}getdata=tmpdata;}catch(e){}}ui.helper.dropped=true;if(opts.beforedrop&&$.isFunction(opts.beforedrop)){//parameters to this callback - event, element, data to be inserted, sender, reciever
// should return object which will be inserted into the reciever
var datatoinsert=opts.beforedrop.call(this,ev,ui,getdata,$('#'+$.jgrid.jqID($t.p.id)),$(this));if(datatoinsert!==undefined&&datatoinsert!==null&&(typeof datatoinsert==="undefined"?"undefined":_typeof(datatoinsert))=='object'){getdata=datatoinsert;}}if(ui.helper.dropped){var grid;if(opts.autoid){if($.isFunction(opts.autoid)){grid=opts.autoid.call(this,getdata);}else{grid=Math.ceil(Math.random()*1000);grid=opts.autoidprefix+grid;}}// NULL is interpreted as undefined while null as object
$('#'+$.jgrid.jqID(this.id)).jqGrid('addRowData',grid,getdata,opts.droppos);}if(opts.ondrop&&$.isFunction(opts.ondrop)){opts.ondrop.call(this,ev,ui,getdata);}}},opts.drop_opts||{});},'onstart':null,'onstop':null,'beforedrop':null,'ondrop':null,'drop_opts':{'activeClass':'ui-state-active','hoverClass':'ui-state-hover'},'drag_opts':{'revert':'invalid','helper':'clone','cursor':'move','appendTo':'#jqgrid_dnd','zIndex':5000},'dragcopy':false,'dropbyname':false,'droppos':'first','autoid':true,'autoidprefix':'dnd_'},opts||{});if(!opts.connectWith){return;}opts.connectWith=opts.connectWith.split(',');opts.connectWith=$.map(opts.connectWith,function(n){return $.trim(n);});$.data($t,'dnd',opts);if($t.p.reccount!='0'&&!$t.p.jqgdnd){updateDnD();}$t.p.jqgdnd=true;for(i=0;i<opts.connectWith.length;i++){cn=opts.connectWith[i];$(cn).droppable($.isFunction(opts.drop)?opts.drop.call($($t),opts):opts.drop);}});},gridResize:function gridResize(opts){return this.each(function(){var $t=this,gID=$.jgrid.jqID($t.p.id);if(!$t.grid||!$.fn.resizable){return;}opts=$.extend({},opts||{});if(opts.alsoResize){opts._alsoResize_=opts.alsoResize;delete opts.alsoResize;}else{opts._alsoResize_=false;}if(opts.stop&&$.isFunction(opts.stop)){opts._stop_=opts.stop;delete opts.stop;}else{opts._stop_=false;}opts.stop=function(ev,ui){$($t).jqGrid('setGridParam',{height:$('#gview_'+gID+' .ui-jqgrid-bdiv').height()});$($t).jqGrid('setGridWidth',ui.size.width,opts.shrinkToFit);if(opts._stop_){opts._stop_.call($t,ev,ui);}};if(opts._alsoResize_){var optstest='{\'#gview_'+gID+' .ui-jqgrid-bdiv\':true,\''+opts._alsoResize_+'\':true}';opts.alsoResize=eval('('+optstest+')');// the only way that I found to do this
}else{opts.alsoResize=$('.ui-jqgrid-bdiv','#gview_'+gID);}delete opts._alsoResize_;$('#gbox_'+gID).resizable(opts);});}});})(jQuery);/*
 Transform a table to a jqGrid.
 Peter Romianowski <peter.romianowski@optivo.de>
 If the first column of the table contains checkboxes or
 radiobuttons then the jqGrid is made selectable.
*/// Addition - selector can be a class or id
function tableToGrid(selector,options){jQuery(selector).each(function(){if(this.grid){return;}//Adedd from Tony Tomov
// This is a small "hack" to make the width of the jqGrid 100%
jQuery(this).width('99%');var w=jQuery(this).width();// Text whether we have single or multi select
var inputCheckbox=jQuery('tr td:first-child input[type=checkbox]:first',jQuery(this));var inputRadio=jQuery('tr td:first-child input[type=radio]:first',jQuery(this));var selectMultiple=inputCheckbox.length>0;var selectSingle=!selectMultiple&&inputRadio.length>0;var selectable=selectMultiple||selectSingle;//var inputName = inputCheckbox.attr("name") || inputRadio.attr("name");
// Build up the columnModel and the data
var colModel=[];var colNames=[];jQuery('th',jQuery(this)).each(function(){if(colModel.length===0&&selectable){colModel.push({name:'__selection__',index:'__selection__',width:0,hidden:true});colNames.push('__selection__');}else{colModel.push({name:jQuery(this).attr('id')||jQuery.trim(jQuery.jgrid.stripHtml(jQuery(this).html())).split(' ').join('_'),index:jQuery(this).attr('id')||jQuery.trim(jQuery.jgrid.stripHtml(jQuery(this).html())).split(' ').join('_'),width:jQuery(this).width()||150});colNames.push(jQuery(this).html());}});var data=[];var rowIds=[];var rowChecked=[];jQuery('tbody > tr',jQuery(this)).each(function(){var row={};var rowPos=0;jQuery('td',jQuery(this)).each(function(){if(rowPos===0&&selectable){var input=jQuery('input',jQuery(this));var rowId=input.attr('value');rowIds.push(rowId||data.length);if(input.is(':checked')){rowChecked.push(rowId);}row[colModel[rowPos].name]=input.attr('value');}else{row[colModel[rowPos].name]=jQuery(this).html();}rowPos++;});if(rowPos>0){data.push(row);}});// Clear the original HTML table
jQuery(this).empty();// Mark it as jqGrid
jQuery(this).addClass('scroll');jQuery(this).jqGrid(jQuery.extend({datatype:'local',width:w,colNames:colNames,colModel:colModel,multiselect:selectMultiple//inputName: inputName,
//inputValueCol: imputName != null ? "__selection__" : null
},options||{}));// Add data
var a;for(a=0;a<data.length;a++){var id=null;if(rowIds.length>0){id=rowIds[a];if(id&&id.replace){// We have to do this since the value of a checkbox
// or radio button can be anything
id=encodeURIComponent(id).replace(/[.\-%]/g,'_');}}if(id===null){id=a+1;}jQuery(this).jqGrid('addRowData',id,data[a]);}// Set the selection
for(a=0;a<rowChecked.length;a++){jQuery(this).jqGrid('setSelection',rowChecked[a]);}});}/*!
 * Copyright 2013 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 */var rp_ge={};// (function ($) {
//
//
// 	$.extend($.jgrid,{
//
// 	});
//
//
//
// })(jQuery);
/*!
 * Copyright 2013 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito, 
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 */(function($){jQuery.jgrid.fluid={fluidWidth:function fluidWidth(options){var grid=$(this);var settings=$.extend({fluidBaseLayer:"#gbox_"+grid.attr("id"),fluidOffset:0,minWidth:null,maxWidth:null},options||{});var resizeLayer=function resizeLayer(layer,forceEvent){var currentWidth=layer.width(),previousWidth=$(layer).data("previousWidth"),evntCurrentWidth=currentWidth;if(forceEvent===true||currentWidth!=previousWidth){$(layer).data("previousWidth",currentWidth);evntCurrentWidth=settings.minWidth!==null&&currentWidth<settings.minWidth?settings.minWidth:evntCurrentWidth;evntCurrentWidth=settings.maxWidth!==null&&currentWidth>settings.maxWidth?settings.maxWidth:evntCurrentWidth;grid.trigger("fluidWidth.resize",[previousWidth,evntCurrentWidth-settings.fluidOffset]);}};// Comprobamos si se esta monitorizando la anchura de la capa
if($(settings.fluidBaseLayer).data("fluidWidth")!==true){//Inidicamos que la capa esta siendo monitorizada
$(settings.fluidBaseLayer).data("fluidWidth",true);setInterval(function(){resizeLayer($(settings.fluidBaseLayer),false);},100);}resizeLayer($(settings.fluidBaseLayer),true);}};})(jQuery);jQuery.fn.extend({fluidWidth:jQuery.jgrid.fluid.fluidWidth});/*!
 * Copyright 2013 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 *//**
 * Tiene como objetivo mostrar al usuario de manera gráfica el estado de avance de una tarea o proceso.
 *
 * @summary Componente RUP Table.
 * @module rup_table
 * @see El componente está basado en el plugin {@link http://www.trirand.com/blog/|jQuery Grid Plugin – jqGrid}. Para mas información acerca de las funcionalidades y opciones de configuración pinche {@link http://www.trirand.com/jqgridwiki/doku.php|aquí}.
 * @example
 *
 * var properties = {
 *		url: "../tableUrl",
 *		colNames: [
 *			"id","nombre","..."]
 *		],
 *		colModel: [
 *			{name: "id", label: "id"},
 *			{name: "nombre", label: "nombre"},
 *			{name: "...", label: "..."}
 *		],
 *		model:"Usuario",
 *		usePlugins:[
 *			"formEdit",
 *			"feedback",
 *			"toolbar",
 *			"contextMenu",
 *			"fluid",
 *			"filter",
 *			"search"
 *		],
 *		primaryKey: "id"
 *	};
 *
 * $("#table").rup_table(properties);
 *//*global jQuery */(function($){//*****************************************************************************************************************
// DEFINICIÓN BASE DEL PATRÓN (definición de la variable privada que contendrá los métodos y la función de jQuery)
//*****************************************************************************************************************
var rup_table={};rup_table.plugins=[];jQuery.rup_table=jQuery.rup_table||{};jQuery.extend(jQuery.rup_table,{registerPlugin:function registerPlugin(name,settings){if(jQuery.inArray(name,rup_table.plugins)===-1){rup_table.plugins.push(name);rup_table.plugins[name]=settings;}}});//Se configura el arranque de UDA para que alberge el nuevo patrón
jQuery.extend(jQuery.rup.iniRup,jQuery.rup.rupSelectorObjectConstructor('rup_table',rup_table));$.fn.fmatter.rup_combo=function(cellval,opts,rwd,act){var labelProp,label,settings;var formatterData=$(this).data('rup.table.formatter')!==undefined?$(this).data('rup.table.formatter'):{};// Se añade la info del formatter
var formatterObj={};formatterObj['rup_combo']={value:cellval};//		formatterObj["rup_combo"] = cellval;
// Se añade la info de la columna
var colFormatter={};colFormatter[opts.colModel.name]=formatterObj;// Se añade el id de la fila
var rowObj={};rowObj[opts.rowId]=colFormatter;if(opts.colModel.formatoptions&&opts.colModel.formatoptions.labelName){labelProp=opts.colModel.formatoptions.labelName;label=$.rup_utils.getJson(rwd,labelProp);}else{if(typeof opts.colModel.editoptions.source==='string'){// Combo remoto
// Obtener la propiedad que corresponde al texto a visualizar
if(opts.colModel.name.indexOf('.')!==-1){labelProp=opts.colModel.name.substring(0,opts.colModel.name.lastIndexOf('.'))+'.'+opts.colModel.editoptions.sourceParam.label;}else{labelProp=opts.colModel.editoptions.sourceParam.label;}label=$.rup_utils.getJson(rwd,labelProp);}else{// Combo local
var labelArr=$.grep(opts.colModel.editoptions.source,function(elem,index){if(elem.value===cellval){return true;}});if(labelArr.length===1){if(labelArr[0].i18nCaption){label=$.rup.i18nParse($.rup.i18n.app[settings.i18nId],labelArr[0].i18nCaption);}else{label=labelArr[0].label;}}}}formatterObj['rup_combo']['label']=label;$.extend(true,formatterData,rowObj);$(this).data('rup.table.formatter',formatterData);return label||'';};$.fn.fmatter.rup_combo.unformat=function(cellvalue,options){var val=$(this).data('rup.table.formatter')[options.rowId][options.colModel.name]['rup_combo']['value'];return val||'';};$.fn.fmatter.rup_autocomplete=function(cellval,opts,rwd,act){var labelProp,label,settings;var formatterData=$(this).data('rup.table.formatter')!==undefined?$(this).data('rup.table.formatter'):{};// Se añade la info del formatter
var formatterObj={};formatterObj['rup_autocomplete']={value:cellval};//		formatterObj["rup_combo"] = cellval;
// Se añade la info de la columna
var colFormatter={};colFormatter[opts.colModel.name]=formatterObj;// Se añade el id de la fila
var rowObj={};rowObj[opts.rowId]=colFormatter;if(opts.colModel.formatoptions&&opts.colModel.formatoptions.labelName){labelProp=opts.colModel.formatoptions.labelName;label=$.rup_utils.getJson(rwd,labelProp);}else{if(typeof opts.colModel.editoptions.source==='string'){// Combo remoto
// Obtener la propiedad que corresponde al texto a visualizar
if(opts.colModel.name.indexOf('.')!==-1){labelProp=opts.colModel.name.substring(0,opts.colModel.name.lastIndexOf('.'))+'.'+opts.colModel.editoptions.sourceParam.label;}else{labelProp=opts.colModel.editoptions.sourceParam.label;}label=$.rup_utils.getJson(rwd,labelProp);}else{// Combo local
var labelArr=$.grep(opts.colModel.editoptions.source,function(elem,index){if(elem.value===cellval){return true;}});if(labelArr.length===1){if(labelArr[0].i18nCaption){label=$.rup.i18nParse($.rup.i18n.app[settings.i18nId],labelArr[0].i18nCaption);}else{label=labelArr[0].label;}}}}formatterObj['rup_autocomplete']['label']=label;$.extend(true,formatterData,rowObj);$(this).data('rup.table.formatter',formatterData);return label||'';};$.fn.fmatter.rup_autocomplete.unformat=function(cellvalue,options){var val=$(this).data('rup.table.formatter')[options.rowId][options.colModel.name]['rup_autocomplete']['value'];return val||'';};/*
   * SOBREESCITURAS
   * Funciones extendidas (SOBREESCRITAS) del componente jqGrid
   *
   * Los métodos aquí indicados han sido extendidos y su implementación sustituida por completo.
   * La extensión ha sido realizada para ajustar el comportamiento del componente jqGrid a los requisitos exigidos.
   *
   * Los métodos extendidos para su modificación son los siguientes:
   *
   * - createModal
   * - hideModal
   * - viewModal
   */jQuery.extend(jQuery.jgrid,{createModal:function createModal(aIDs,content,p,insertSelector,posSelector,appendsel,css){// aIDs: Identificadores de la modal
// -- aIDs.modalcontent :
// -- aIDs.modalhead :
// -- aIDs.scrollelm :
// -- aIDs.themodal :
// content: Contenido HTML del díalogo
// p: parámetros de configuración del diálogo
// insertSelector: selector que corresponde al elemento despues del que se va a insertar la modal
// posSelector: elemento base sobre el que se calcula la posición
var $divModal=jQuery('<div/>').attr('id',aIDs.themodal).append($(content));var $scrollelm=$divModal.find('#'+aIDs.scrollelm);$divModal.insertBefore($(insertSelector));/* TODO : Añadir los parametros de configruación que puedan añadirse al rup_dialog. */$divModal.rup_dialog({type:$.rup.dialog.DIV,autoOpen:false,modal:true,resizable:p.resize,title:p.caption,width:p.width,buttons:p.buttons});// Eliminamos los eventos del boton de cerrar para mostrar el gestor de cambios
if(jQuery.isFunction(p.onClose)){jQuery('.ui-dialog-titlebar-close, a:has(#closeText_'+$divModal.first()[0].id+')',$divModal.parent()).off('click').on('click',function(event){p.onClose.call(event);});// Se elimina el evento de cerrar al texto de cierre del dialogo y se asigna el evento de la gestion de cambios.
//				prop.detailDiv.parent().find("#closeText_" + prop.detailDiv.first()[0].id).parent().unbind('click').bind("click", function () {
//					self._checkDetailFormModifications(function(){
//						prop.detailDiv.rup_dialog("close");
//					});
//				});
// Se elimina el evento de cerrar al icono de cierre del dialogo y se asigna el evento de la gestion de cambios.
//				prop.detailDiv.parent().find(".ui-dialog-titlebar-close").unbind('click').bind("click", function () {
//					self._checkDetailFormModifications(function(){
//						prop.detailDiv.rup_dialog("close");
//					});
//				});
}jQuery('#'+aIDs.scrollelm+'_2').addClass('botoneraModal');jQuery('.fm-button','#'+aIDs.scrollelm+'_2').on({focusin:function focusin(){jQuery(this).addClass('ui-state-focus');},focusout:function focusout(){jQuery(this).removeClass('ui-state-focus');}});},hideModal:function hideModal(selector,o){jQuery(selector).rup_dialog('close');},viewModal:function viewModal(selector,o){jQuery(selector).rup_dialog('open');}});jQuery.extend(jQuery.rup_table,{proxyAjax:function proxyAjax(ajaxOptions,identifier){jQuery.rup_ajax(ajaxOptions);}});/* ******************************
   * FUNCIONES DE CONFIGURACION
   * ******************************/jQuery.fn.rup_table('extend',{/**
     * Metodo que realiza la pre-configuración del core del componente RUP Table.
     * Este método se ejecuta antes de la pre-configuración de los plugins y de la invocación al componente jqGrid.
     *
     * @name preConfigureCore
     * @function
     * @param {object} settings - Parámetros de configuración del componente.
     * @fires module:rup_table#rupTable_checkOutOfGrid
     * @fires module:rup_table#rupTable_serializeGridData
     * @fires module:rup_table#rupTable_beforeProcessing
     */preConfigureCore:function preConfigureCore(settings){var $self=this,colModel,colModelObj;// Configuración del parámetro url
settings.baseUrl=settings.url;// Ajuste en caso de no utilizar el plugin de filter
if(jQuery.inArray('filter',settings.usePlugins)===-1){settings.url+='/filter';}// Se almacena el identificador del objeto en la propiedad settings.id
settings.id=$self.attr('id');// Se da valor a la propiedad ruptype
$self.attr('ruptype','table');settings.core.tableDiv=settings.id+'_div';settings.core.$tableDiv=jQuery('#'+settings.core.tableDiv);jQuery(document).bind('click',function(event){var $originalTarget=jQuery(event.target);if($originalTarget.parents().index(settings.core.$tableDiv)===-1){$self.triggerHandler('rupTable_checkOutOfGrid',[event,$originalTarget]);}});/*
       * Configuración de los identificadores por defecto de los componentes del rup_table
       */if(settings.pager!==false){settings.pager=$.rup_utils.getJQueryId(settings.pager!==null?settings.pager:settings.id+'_pager');settings.$pager=jQuery(settings.pager);if(settings.$pager.length===0){alert('El identificador '+settings.pager+' especificado para el paginador no existe.');}}colModel=settings.colModel;if(settings.loadOnStartUp===false||settings.multifilter!=undefined){$self.data('tmp.loadOnStartUp.datatype',settings.datatype);settings.datatype='clientSide';}// Configuración del colModel para los campos sobre los que se debe de configurar un componente RUP
for(var i=0;i<colModel.length;i++){colModelObj=colModel[i];// Se comprueba para cada uno de las entradas en el colModel si se debe de crear un componente RUP
if(colModelObj.rupType!==undefined&&colModelObj.rupType!==null){// En caso de tratarse de un componente RUP
// Se indica como edittype="custom" para que jqGrid lo trate como un componente personalizado
colModelObj.edittype='custom';// Si no se ha especificado una funcion custom_element se asigna la función genérica correspondiente a un componente RUP
if(!jQuery.isFunction(colModelObj.editoptions.custom_element)){colModelObj.editoptions.custom_element=function(value,options){return $('<input>').attr({'type':'text','id':options.id,'name':options.name,'class':'FormElement formulario_linea_input customelement','style':'width:98%','value':value})[0];};}// Si no se ha especificado una funcion custom_value se asigna la función genérica correspondiente a un componente RUP
if(!jQuery.isFunction(colModelObj.editoptions.custom_value)){colModelObj.editoptions.custom_value=function($elem,operation,value){var ruptype=$elem.attr('ruptype');if(ruptype!==undefined){if(operation==='set'){$elem['rup_'+ruptype]('setRupValue',value);}else if(operation==='get'){if(ruptype==='autocomplete'){return $('[id="'+$elem.attr('id').substring(0,$elem.attr('id').indexOf('_label'))+'"]')['rup_'+ruptype]('getRupValue');}else{return $elem['rup_'+ruptype]('getRupValue');}}}};}}}// Configuración de la columna extra utilizada para mostrar el estado de los registros
if(settings.showGridInfoCol){settings.colNames=$.merge([''],settings.colNames);settings.colModel=$.merge([settings.defaultGridInfoCol],settings.colModel);}// Configuración de las claves compuestas
if(settings.primaryKey!==undefined&&typeof settings.primaryKey==='string'){settings.primaryKey=[settings.primaryKey];}if(settings.primaryKey!==undefined&&_typeof(settings.primaryKey)==='object'){// Configuración de la columna extra para gestionar las claves compuestas
if(settings.primaryKey.length===1){settings.primaryKeyCol=settings.primaryKey[0];// Se configura la propiedad key para la columna correspondiente a a clave primaria
for(var i=0;i<colModel.length;i++){if(colModel[i].name===settings.primaryKeyCol){colModel[i].key=true;break;}}}else if(settings.primaryKey.length>1){settings.colNames=$.merge([''],settings.colNames);var pkColModel=$.extend({},settings.defaultGridMultiplePkCol,{key:true,formatter:function formatter(cellvalue,options,rowObject){var $self=$(this),settings=$self.data('settings'),retValue='';for(var i=0;i<settings.primaryKey.length;i++){retValue+=$.rup_utils.unnestjson(rowObject)[settings.primaryKey[i]]+settings.multiplePkToken;}retValue=retValue.substr(0,retValue.length-1);return retValue;}});settings.primaryKeyCol='pkCol';settings.colModel=$.merge([pkColModel],settings.colModel);}// Se actualiza el nombre de la columna que va a ejercer como clave primaria
$.extend(settings,{prmNames:{id:settings.primaryKeyCol}});}// Configuración del colModel para la gestión de la edición de las claves primarias en los modos add y edit
for(var i=0;i<colModel.length;i++){colModelObj=colModel[i];if(colModelObj.editable===true){if(colModelObj.editableOnAdd===undefined){colModelObj.editableOnAdd=true;}if(colModelObj.editableOnEdit===undefined){if(jQuery.inArray(colModel[i].name,settings.primaryKey)!==-1){colModelObj.editableOnEdit=false;}else{colModelObj.editableOnEdit=true;}}}}// Sobreescritura del método serialize grid data
settings.serializeGridData=function(postData){var newPostData,pageNum=parseInt(postData.page),lastpage=parseInt($self.rup_table('getGridParam','lastpage'));if(lastpage!==0&&pageNum>lastpage){postData.page=lastpage;}if(settings.core.startOnPage!==null){postData.page=settings.core.startOnPage;$self.data('tmp.firstLoad',true);}jQuery.extend(true,postData,{core:{'pkToken':settings.multiplePkToken,'pkNames':settings.primaryKey}});newPostData=$.extend({},{'filter':{}},postData);$self.triggerHandler('rupTable_serializeGridData',[newPostData]);$self.removeData('tmp.firstLoad');settings.core.startOnPage=null;return jQuery.toJSON(newPostData);};settings.beforeProcessing=function(data,st,xhr){if($self.triggerHandler('rupTable_beforeProcessing',[data,st,xhr]===false)){return false;}if(settings.primaryKey.length>1){$.each(data.rows,function(index,elem){var retValue='';for(var i=0;i<settings.primaryKey.length;i++){retValue+=$.rup_utils.unnestjson(elem)[settings.primaryKey[i]]+settings.multiplePkToken;}retValue=retValue.substr(0,retValue.length-1);elem['pkCol']=retValue;});}return true;};// Gestión de errores por defecto
//			if (!jQuery.isFunction(settings.loadError)){
//				settings.userDefined
//				settings.loadError = function(xhr,st,err){
//					jQuery.rup_messages("msgError", {
//						title: settings.core.defaultLoadErrorTitle,
//						message: xhr.responseText
//					});
//				};
//			}
var userLoadError=settings.loadError;settings.loadError=function(xhr,st,err){var $self=$(this),ret;ret=$self.triggerHandler('rupTable_loadError',xhr,st,err);if(ret!==false){jQuery.proxy(userLoadError,$self)(xhr,st,err);}};settings.getActiveLineId=function(){var $self=this,rowsInGrid=$self.jqGrid('getDataIDs'),selrow=$self.jqGrid('getGridParam','selrow');return $.inArray(selrow,rowsInGrid);};settings.getActiveRowId=function(){var $self=this;return $self.rup_table('getGridParam','selrow');};settings.getSelectedRows=function(){var $self=this,selrow=$self.rup_table('getGridParam','selrow');return selrow===null?[]:[selrow];};settings.getSelectedLines=function(){var $self=this,selrow=$self.rup_table('getGridParam','selrow');return selrow===null?[]:[$.inArray(selrow,$self.jqGrid('getDataIDs'))];};// Gestión de las operaciones que se pueden realizar sobre los registros
// Se unifican las operaciones por defecto con las indicadas por el usaurio
jQuery.each(settings.core.operations,function(index,operation){settings.core.showOperations[index]=true;});jQuery.extend(true,settings.core.defaultOperations,settings.core.operations);$self.on({'jqGridBeforeRequest':function jqGridBeforeRequest(){jQuery.set_uda_ajax_mode_on();},'jqGridLoadComplete.rup_table.tooltip':function jqGridLoadCompleteRup_tableTooltip(event,data){var $self=$(this);if(data!==undefined){// Redimensionado del campo de número de página en base al número de página máximo
jQuery('.pagControls input.ui-pg-input',settings.$pager).attr({size:data.total.length,maxlength:data.total.length});}},'jqGridResizeStart':function jqGridResizeStart(event,index){//rup_combo , close the menu of the rup_combo when a column is resized
$('#'+$self[0].id+'_search_rowInputs select').each(function(){$(this).selectmenu('close');});},'jqGridResizeStop':function jqGridResizeStop(event,index){//rup_combo, adjust the width of the menu to the new width after a column has been resized
$('#'+$self[0].id+'_search_rowInputs select').each(function(){$('[id=\''+this.id+'-menu\']').width($('[id=\''+this.id+'-button\']').width());});},'jqGridGridComplete.rup_table.core':function jqGridGridCompleteRup_tableCore(event){var $self=$(this),$tbody;if($self.rup_table('getGridParam','records')===0){// No se han encontrado registros
$self.prev().remove();//Borrar div vacío
$($self.jqGrid('getGridParam','pager')).hide();var content='<tr class="ui-widget-content jqgrow ui-row-ltr" role="row" id="'+$self[0].id+'_noRecords" aria-selected="false">';content+='<td aria-describedby="'+$self[0].id+'_NO_REGISTROS" title="'+$.rup.i18nParse($.rup.i18n.base,'rup_table.noRecordsFound')+'" style="border:0;padding-left: 0.5em ! important;text-align: left;width:'+$('#gview_'+$self.attr('id')).width()+'px;background:white;" role="gridcell">';//content += 	'<div id="RUP_GRID_' + self[0].id + '_noRecord_ext" class="cellLayout" style="padding-left: 0.5em ! important;">' + $.rup.i18nParse($.rup.i18n.base,"rup_table.noRecordsFound");
//content += '</div></td></tr>';
content+=$.rup.i18nParse($.rup.i18n.base,'rup_table.noRecordsFound');content+='</td></tr>';$self.before(content);$('[aria-describedby="'+$self[0].id+'_NO_REGISTROS"]').rup_tooltip({position:{my:'center',at:'center'}});}else{jQuery('#'+$self[0].id+'_noRecords').remove();//si tenemos la capa de no hay registros la borramos
jQuery($self.jqGrid('getGridParam','pager')).show();}},'jqGridGridComplete.rup_table.tooltip':function jqGridGridCompleteRup_tableTooltip(event){var $self=$(this),$tbody;// Se han encontrado registros
// Tooltips de la tabla
//					jQuery("[title]", $self).rup_tooltip({show:{delay:settings.tooltipDelay}});
//Se le aplica el tooltip de uda
$('#'+$(this).attr('id')+' [title]').each(function(i,elem){var $elem=$(elem);$elem.attr('grid_tooltip',$elem.attr('title')).removeAttr('title');});$tbody=jQuery('tbody:first',$self);$tbody.on('mousestop',{delay:500},function(event,originalEvent){var obj=$.rup_utils.elementFromPoint(originalEvent.clientX,originalEvent.clientY,true),$obj=$(obj),toolipTmpId,auxId,auxDescribedBy;if(!$obj.attr('rup_tooltip')&&$obj.attr('grid_tooltip')){auxId=$obj.parent().attr('id')?$obj.parent().attr('id'):$obj.parents('tr[role=\'row\']').attr('id');auxDescribedBy=$obj.attr('aria-describedby')?$obj.attr('aria-describedby'):$obj.parents('td[role=\'gridcell\']').attr('aria-describedby');$obj.attr('title',$obj.attr('grid_tooltip'));toolipTmpId=auxId+'_'+auxDescribedBy;$obj.rup_tooltip({show:{delay:0},id:toolipTmpId,position:{viewport:$(window),adjust:{method:'flip'}}});$obj.triggerHandler('mouseenter.qtip-'+toolipTmpId+'-create');//							$obj.triggerHandler("mouseenter");
$obj.rup_tooltip('option','show.delay',500);$obj.rup_tooltip('open');}});}});},/**
     * Metodo que realiza la post-configuración del core del componente RUP Table.
     * Este método se ejecuta antes de la post-configuración de los plugins y después de la invocación al componente jqGrid.
     *
     * @name postConfigureCore
     * @function
     * @param {object} settings - Parámetros de configuración del componente.
     */postConfigureCore:function postConfigureCore(settings){var $self=this;// Se configura la funcionalidad de redimensionado de la tabla.
if(settings.resizable!==false){$self.rup_table('gridResize',jQuery.isPlainObject(settings.resizable)?settings.resizable:{});}// Configruación pager
if(settings.pager!==false){$self.rup_table('configurePager',settings);}// Se añaden los tooltip a las cabeceras de la tabla
$.each($('#gview_table th:visible'),function(index,elem){var $elem=$(elem),text=$elem.find('div').text();if(text!==''){$elem.attr('title',text).rup_tooltip({show:{delay:500},position:{viewport:$(window),adjust:{method:'flip'}}});}});// Implementación del ellipsis en las cabeceras de las columnas de la tabla
jQuery($self.rup_table('getGridParam','colModel')).each(function(index,element){var $headerLabel;//Si la columna define ellipsis...
if(element.classes==='ui-ellipsis'){//Añadirle estilos para ellipsis al div que está dentro de la cabecera
jQuery('[id=\'jqgh_'+settings.id+'_'+element.name+'\']').css('display','block').css('text-overflow','ellipsis');}//Sustituir DIV del literal de la cabecera por SPAN (para que funcione ellipsis)
$headerLabel=jQuery('[id=\'jqgh_'+settings.id+'_'+element.name+'\']').children('div');$headerLabel.replaceWith(jQuery('<span>').text($headerLabel.text()).css('cursor','pointer'));});// Configuración de la columna extra utilizada para mostrar el estado de los registros
if(settings.showGridInfoCol){//				jQuery("#gview_"+settings.id+" table thead th#"+settings.id+"_rupInfoCol").css("padding-right","0px").css("padding-left","0px").css("border-right","0px none");
jQuery('#gview_'+settings.id+' table thead th#'+settings.id+'_rupInfoCol').css('border-right','0px none');}if(settings.loadOnStartUp===false||settings.multifilter!=undefined){settings.datatype=$self.data('tmp.loadOnStartUp.datatype');$self.rup_table('setGridParam',{datatype:$self.data('tmp.loadOnStartUp.datatype')});$self.removeData('tmp.loadOnStartUp.datatype');}}});//********************************
// DEFINICIÓN DE MÉTODOS PÚBLICOS
//********************************
jQuery.fn.rup_table('extend',{/**
     * Devuelve la propiedad colModel del jqGrid.
     *
     * @name getColModel
     * @function
     * @return {object} - Propiedad colModel del jqGrid.
     * @example
     * $("#idComponente").rup_table("getColModel");
     */getColModel:function getColModel(){return $(this).jqGrid('getGridParam','colModel');},/**
     * Devuelve el valor del parámetro del grid especificado.
     *
     * @name getGridParam
     * @function
     * @param {string} pName - Nombre del parámetro que se desea obtener.
     * @return {object} - Valor del parámetro.
     * @example
     * $("#idComponente").rup_table("getGridParam","nombreParametro");
     */getGridParam:function getGridParam(pName){return $(this).jqGrid('getGridParam',pName);},/**
     * Permite redimensionar la tabla de acuerdo a los parámetros indicados.
     *
     * @name getGridParam
     * @function
     * @param {object} options - Parámetros para configurar la altura y anchura del redimensionado.
     * @return {jQuery} - Referencia al propio componente.
     * @example
     * $("#idComponente").rup_table("gridResize",{});
     */gridResize:function gridResize(options){return $(this).jqGrid('gridResize',options);},/**
     * Devuelve un array con los identificadores de los registros seleccionados.
     *
     * @name getSelectedRows
     * @function
     * @return {string[]} - Array con los identificadores de los registros seleccionados.
     * @example
     * $("#idComponente").rup_table("getSelectedRows");
     */getSelectedRows:function getSelectedRows(){var $self=this,settings=$self.data('settings');return jQuery.proxy(settings.getSelectedRows,$self)();},/**
     * Devuelve un array con los índices de las líneas de los registros seleccionados.
     *
     * @name getSelectedLines
     * @function
     * @return {number[]} - Array con los índices de las líneas de los registros seleccionados.
     * @example
     * $("#idComponente").rup_table("getSelectedLines");
     */getSelectedLines:function getSelectedLines(){var $self=this,settings=$self.data('settings');return jQuery.proxy(settings.getSelectedLines,$self)();},/**
     * El objetivo de este método es construir una URL mediante la cual se pueda realizar una petición para obtener los datos de un registro concreto.
     * La URL se genera concatenando los valores de las propiedades que forman la primary key del resgistro a la url base especificada en los settings de inicialización.
     *
     * @name getPkUrl
     * @function
     * @param {string} rowId - Identificador del registro.
     * @return {string} - Url para obtener los valores del registro correspondiente.
     * @example
     * $("#idComponente").rup_table("getPkUrl","0001");
     */getPkUrl:function getPkUrl(rowId){var $self=this,settings=$self.data('settings'),tmpRowId;if(jQuery.isArray(rowId)){tmpRowId=rowId[0]!==undefined?rowId[0]:'';}else{tmpRowId=rowId;}return tmpRowId.split(settings.multiplePkToken).join('/');},/**
     * Lanza la recarga de la tabla.
     *
     * @name reloadGrid
     * @function
     * @param {boolean} async - Indica si la llamada debe ser asíncrona o síncrona.
     * @param {boolean} notSelect - Indica si debe seleccionar el primer elemento o no.
     * @example
     * $("#idComponente").rup_table("reloadGrid", true);
     */reloadGrid:function reloadGrid(async,notSelect){var $self=this,settings=$self.data('settings'),page=$self.rup_table('getGridParam','page');var ajaxOptions=$self.jqGrid('getGridParam','ajaxGridOptions');var ajaxOptionsAsync=ajaxOptions.async;ajaxOptions.async=false;//			var ajaxOptions = $self.jqGrid("setGridParam", {ajaxGridOptions:ajaxOptions});
$self.jqGrid('setGridParam',{ajaxGridOptions:ajaxOptions});$self.jqGrid('setGridParam',{page:1});$self.trigger('reloadGrid');ajaxOptions.async=true;$self.jqGrid('setGridParam',{ajaxGridOptions:ajaxOptions});if(!notSelect){var nextPagePos=jQuery.proxy(jQuery.jgrid.getCurrPos,$self[0])();$self.jqGrid('setSelection',nextPagePos[1][0]);}},/**
     * Resetea el formulario indicado.
     *
     * @name resetForm
     * @function
     * @param {jQuery} $form - Objeto jQuery que referencia el formulario que se desea resetear.
     * @return {jQuery} - Referencia al propio objeto.
     * @example
     * $("#idComponente").rup_table("resetForm", $("#idFormulario"));
     */resetForm:function resetForm($form){var $self=this,settings=$self.data('settings');// Se eliminan los estilos de errores de validacion
if($form.data('validator')!=undefined){var errorClass=$form.data('validator').settings.errorClass;$('.'+errorClass,$form).removeClass(errorClass);}// Se realiza el reset de los campos ordinarios
//form.resetForm();
jQuery('input[type!=\'button\'][type!=\'checkbox\'][type!=\'radio\'], textarea',$form).val('');jQuery('input[type=\'checkbox\']',$form).not('[name*=\'jqg_GRID_\']',$form).not('[disabled=\'disabled\']',$form).removeAttr('checked');// Se realiza el reset de los rup_combo
jQuery.each($('select.rup_combo',$form),function(index,elem){if(settings.filter&&settings.filter.clearSearchFormMode==='reset'){jQuery(elem).rup_combo('reset');}else{jQuery(elem).rup_combo('clear');}});//Vaciar los autocompletes
$('[ruptype=\'autocomplete\']',$form).each(function(index,element){$(element).val('');});//Vaciar los arboles
$('[ruptype=\'tree\']',$form).each(function(index,element){$(element).rup_tree('setRupValue','');});// Se realiza el reset del fomulario
if(settings.filter&&settings.filter.clearSearchFormMode==='reset'){$form.resetForm();}else{$('input[type=\'radio\']',$form).removeAttr('checked');}return $self;},/**
     * Asigna a uno o varios parámetros del grid los valores indicados.
     *
     * @name setGridParam
     * @function
     * @param {object} newParams - Objeto que contiene los parámetros y sus valores.
     * @return {jQuery} - Referencia al propio objeto.
     * @example
     * $("#idComponente").rup_table("setGridParam", {param1:value1, param2:value2});
     */setGridParam:function setGridParam(newParams){$(this).jqGrid('setGridParam',newParams);return $(this);},/**
     * Selecciona o deselecciona los registros indicados.
     *
     * @name setSelection
     * @function
     * @param {string | string[]} selectedRows - Identificador o array de identificadores de los registros que se desea seleccionar o deseleccionar.
     * @param {boolean} status - En caso de ser true se seleccionarán los registros indicados. En caso de ser false se deseleccionarán.
     * @example
     * $("#idComponente").rup_table("setSelection", ["3","7"], true);
     */setSelection:function setSelection(selection,status,e){var $self=this,settings=$self.data('settings'),ret;ret=$self.triggerHandler('rupTable_setSelection',arguments);if(ret!==false){$self.jqGrid('setSelection',selection,status,e);}},/**
     * Muestra en los campos del formulario los errores de validación indicados.
     *
     * @name showServerValidationFieldErrors
     * @function
     * @param {jQuery} $form - Objeto jQuery que referencia el formulario que se desea resetear.
     * @param {object} errors - Objeto json que contiene los errores de validación que se han dado para cada campo.
     * @example
     * $("#idComponente").rup_table("showServerValidationFieldErrors ", $("#idFormulario"), {});
     */showServerValidationFieldErrors:function showServerValidationFieldErrors($form,errors){var $self=$(this);if(errors.rupErrorFields!==undefined||errors.rupFeedback!==undefined){$form.validate().submitted=$.extend(true,$form.validate().submitted,errors.rupErrorFields);$form.validate().invalid=errors.rupErrorFields;$form.validate().showErrors(errors.rupErrorFields);}else if(errors.rupFeedback!==undefined){$self.rup_table('showFeedback',$form.validate().settings.feedback,$.rup_utils.printMsg(errors.rupFeedback.message),errors.rupFeedback.imgClass!==undefined?errors.rupFeedback.imgClass:null);}},/**
     * Elimina el resaltado de la línea especificada de la tabla.
     *
     * @name rupTableClearHighlightedRowAsSelected
     * @function
     * @param {jQuery} $row - Objeto jQuery que referencia a la línea de la tabla.
     * @fires module:rup_table#rupTableClearHighlightedRowAsSelected
     * @example
     * $("#idComponente").rup_table("clearHighlightedRowAsSelected", $("#idFila"));
     */clearHighlightedRowAsSelected:function clearHighlightedRowAsSelected($row){var $self=this,self=$self[0],internalProps=self.p,row=$row[0],froz=internalProps.frozenColumns===true?internalProps.id+'_frozen':'';if(!$row.hasClass('ui-subgrid')&&!$row.hasClass('ui-state-disabled')){$('#jqg_'+$.jgrid.jqID(internalProps.id)+'_'+$.jgrid.jqID(row.id))[internalProps.useProp?'prop':'attr']('checked',false);$row.removeClass('ui-state-highlight').attr('aria-selected','false');//				emp.push(row.id);
if(froz){$('#jqg_'+$.jgrid.jqID(internalProps.id)+'_'+$.jgrid.jqID(row.id),self.grid.fbDiv)[internalProps.useProp?'prop':'attr']('checked',false);$('#'+$.jgrid.jqID(row.id),self.grid.fbDiv).removeClass('ui-state-highlight');}}$self.trigger('rupTableClearHighlightedRowAsSelected',[$row]);},/**
     * Resalta la línea especificada de la tabla.
     *
     * @name highlightRowAsSelected
     * @function
     * @param {jQuery} $row - Objeto jQuery que referencia a la línea de la tabla.
     * @fires module:rup_table#rupTableHighlightRowAsSelected
     * @example
     * $("#idComponente").rup_table("highlightRowAsSelected", $("#idFila"));
     */highlightRowAsSelected:function highlightRowAsSelected($row){var $self=this,self=$self[0],internalProps=self.p,row=$row[0],froz=internalProps.frozenColumns===true?internalProps.id+'_frozen':'';if($row.length>0&&!$row.hasClass('ui-subgrid')&&!$row.hasClass('jqgroup')&&!$row.hasClass('ui-state-disabled')){$('#jqg_'+$.jgrid.jqID(internalProps.id)+'_'+$.jgrid.jqID(row.id))[internalProps.useProp?'prop':'attr']('checked',true);$row.addClass('ui-state-highlight').attr('aria-selected','true');internalProps.selarrrow.push(row.id);internalProps.selrow=row.id;if(froz){$('#jqg_'+$.jgrid.jqID(internalProps.id)+'_'+$.jgrid.jqID(row.id),self.grid.fbDiv)[internalProps.useProp?'prop':'attr']('checked',true);$('#'+$.jgrid.jqID(row.id),self.grid.fbDiv).addClass('ui-state-highlight');}$self.trigger('rupTableHighlightRowAsSelected',[$row]);}},/**
     * Actualiza el valor de los datos que se muestran en la barra de paginación.
     *
     * @name updateDetailPagination
     * @function
     * @param {string} currentRowNumArg - Número actual de los registros que se están mostrando.
     * @param {string} totalRowNumArg - Número total de los registros que se muestran en la tabla.
     * @example
     * $("#idComponente").rup_table("updateDetailPagination", "1-10", "586" );
     */updateDetailPagination:function updateDetailPagination(currentRowNumArg,totalRowNumArg){var $self=this,settings=$self.data('settings'),tableId=settings.id,currentRowNum,totalRowNum;currentRowNum=currentRowNumArg!==undefined?currentRowNumArg:$.proxy(settings.getDetailCurrentRowCount,$self)();totalRowNum=totalRowNumArg!==undefined?totalRowNumArg:$.proxy(settings.getDetailTotalRowCount,$self)();if(currentRowNum===1){$('#first_'+tableId+', #back_'+tableId,settings.$detailFormDiv).addClass('ui-state-disabled');}else{$('#first_'+tableId+', #back_'+tableId,settings.$detailFormDiv).removeClass('ui-state-disabled');}if(currentRowNum===totalRowNum){$('#forward_'+tableId+', #last_'+tableId,settings.$detailFormDiv).addClass('ui-state-disabled');}else{$('#forward_'+tableId+', #last_'+tableId,settings.$detailFormDiv).removeClass('ui-state-disabled');}$('#rup_table_selectedElements_'+$self.attr('id')).text(jQuery.jgrid.format(jQuery.rup.i18nParse(jQuery.rup.i18n.base,'rup_table.defaults.detailForm_pager'),currentRowNum,totalRowNum));},/**
     * Función de callback que se ejecutará desde el método updateSavedData.
     *
     * @callback jQuery.rup_validate~onSubmitHandler
     * @param {object} savedData - Objeto interno que almacena en formato json los datos con los que se han inicializado los campos del formulario.
     * @example <caption>Envia el formulario cuando este es válido.</caption>
     * $("#idComponente").rup_table("updateSavedData", function(savedData){
     * });
     *//**
     * Permite modificar el objeto interno _savedData que se utiliza en el control de cambios en el modo de edición en formulario y edición en línea.
     *
     * @name updateSavedData
     * @function
     * @param {module:rup_table~onUpdateSavedData} arg -Función de callback desde la que se puede modificar el objeto _savedData.
     * @example
     * $("#idComponente").rup_table("updateSavedData", function(savedData){
     * });
     */updateSavedData:function updateSavedData(arg){var $self=this,settings=$self.data('settings');if(jQuery.isFunction(arg)){jQuery.proxy(arg,$self)(rp_ge[settings.id]._savedData);}},isPluginLoaded:function isPluginLoaded(name){var $self=this,settings=$self.data('settings');return settings.usePlugins.indexOf(name)===-1?false:true;}});jQuery.fn.rup_table('extend',{/**
     * Realiza la configuración interna del paginador de acuerdo a los parámetros de configuración indicados en la inicialización del componente.
     *
     * @name configurePager
     * @function
     * @param {object} settings - Parámetros de configuración del componente.
     * @example
     * $("#idComponente").rup_table("configurePager", settings);
     */configurePager:function configurePager(settings){var $self=this;return $.proxy($self[0]._ADAPTER.configurePager,$self)(settings);}});//********************************
// DEFINICIÓN DE MÉTODOS PRIVADOS
//********************************
jQuery.fn.rup_table('extend',{/**
     * Método de inicialización del componente.
     *
     * @name _init
     * @function
     * @private
     * @param {object} args - Parámetros de configuración del componente.
     * @fires module:rup_table#rupTable_coreConfigFinished
     */_init:function _init(args){if(args.length>1){jQuery.rup.errorGestor(jQuery.rup.i18nParse(jQuery.rup.i18n.base,'rup_global.initError')+$(this).attr('id'));}else{var $self=this,settings={};/* *************************
         * CONFIGURACION
         * *************************/var defaultPugins=jQuery.isArray(args[0].defaultPlugins)?args[0].defaultPlugins:jQuery.fn.rup_table.defaults.defaultPlugins,userPlugins=jQuery.merge([],args[0].usePlugins),configuredPlugins=jQuery.merge(jQuery.merge([],defaultPugins),userPlugins);jQuery.rup_utils.sortArray(configuredPlugins,function(obj1,obj2){return rup_table.plugins[obj2].loadOrder-rup_table.plugins[obj1].loadOrder;});/* *********************************************************
         * SE PROCESA LAS CONFIGURACION POR DEFECTO DEL CORE y VALIDACIÓN DEL LOS DIALOGOS
         * *********************************************************
         */if($("[aria-describedby="+$self.attr('id')+"_detail_div]").length>0){$("[aria-describedby="+$self.attr('id')+"_detail_div]").remove();}settings=$.extend(true,{},settings,jQuery.fn.rup_table.plugins.core.defaults);$self[0]._ADAPTER=$.rup.adapter[settings.adapter];/* *********************************************************
         * SE PROCESAN LAS CONFIGURACIONES POR DEFECTO DE LOS PLUGINS
         * *********************************************************
         */$.each(configuredPlugins,function(index,name){if(rup_table.plugins[name]!==undefined&&jQuery.fn.rup_table.plugins[name]!==undefined){settings=$.extend(true,{},settings,jQuery.fn.rup_table.plugins[name].defaults);}});// Se sobreescribe la configuración por defecto con la especificada por el usaurio
settings=jQuery.extend(true,{},jQuery.fn.rup_table.defaults,settings,args[0]);/* *********************************************************
         * EJECUCION DE LA PRECONFIGURACION DEL CORE
         * *********************************************************/$self.rup_table('preConfigureCore',settings);/* *********************************************************
         * EJECUCION DE FUNCIONES DE PRECONFIGURACION DE LOS PLUGINS
         * *********************************************************
         */$.each(configuredPlugins,function(index,name){if(jQuery.isFunction(rup_table.plugins[name].preConfiguration)){jQuery.proxy(rup_table.plugins[name].preConfiguration,$self)(settings);}});/*
         * INVOCACIÓN al plugin subyacente jqGrid
         */$self.jqGrid(settings);/* *********************************************************
         * EJECUCION DE LA POSTCONFIGURACION DEL CORE
         * *********************************************************/$self.rup_table('postConfigureCore',settings);/* *********************************************************
         * EJECUCION DE FUNCIONES DE POSTCONFIGURACION DE LOS PLUGINS
         * *********************************************************/$.each(configuredPlugins,function(index,name){if(jQuery.isFunction(rup_table.plugins[name].postConfiguration)){jQuery.proxy(rup_table.plugins[name].postConfiguration,$self)(settings);}});// Se almacenan los settings medainte el data para ser accesibles en las invocaciones a los métodos públicos.
$self.data('settings',settings);$self.triggerHandler('rupTable_coreConfigFinished');}},/**
     * Devuelve el índice de la línea identificada mediante el valor indicado por parámetro.
     *
     * @name _getLineIndex
     * @function
     * @private
     * @param {string} rowId - Identificador del registro.
     * @return {number} - Índice de la línea.
     */_getLineIndex:function _getLineIndex(rowId){var $self=this,settings=$self.data('settings'),tableghead=settings.id+'ghead_',count=0,$row,id;if($self.rup_table('getGridParam','grouping')===true){for(var i=0;i<$self[0].rows.length;i++){$row=jQuery($self[0].rows[i]);id=$row.attr('id');if(id!==undefined&&id.indexOf(tableghead)===-1){count++;if(id===rowId){return count;}}}}else{return $self.jqGrid('getInd',rowId);}}});//*********************************************************************
// MÉTODOS PARA MANTENER LA RETROCOMPATIBILIDAD CON LA API DEL RUP.GRID
//*********************************************************************
jQuery.fn.rup_table('extend',{/**
     * Añade una nueva línea a la tabla. Esta operación no realiza una inserción del registro en el sistema de persistencia, sino que únicamente añade una nueva fila de modo visual.
     *
     * @name addRowData
     * @function
     * @param {string} rowid - Identificador del registro.
     * @param {object} data - Objeto json que contiene los valores de cada columna de la nueva línea.
     * @param {string} position - fisrt o last. Determina la posición donde se va a insertar el registro.
     * @param {string} srcrowid -En el caso de indicarse se insertará la nueva línea en la posición relativa al registro que identifica y el valor del parámetro position.
     * @return {jQuery} - Referencia al propio componente.
     * @example
     * $("#idComponente").rup_table("addRowData", "10", {campo1:valor1,campo2:valor2});
     */addRowData:function addRowData(rowid,data,position,srcrowid){var $self=$(this);//			//Se aade la capa de separacion para diferenciar los nuevos elementos incluidos
//			if ($("#" + tableName + " #separadorAadidos").html() === null) {
//				$("#" + tableName + " tr:first-child").after($("#" + tableName + " tr:first-child").clone(false).css("display", "none").css("height", "").attr("id", "separadorAadidos"));
//
//				$.each($("#" + tableName + " #separadorAadidos td") , function (index, object) {
//					$(this).html("").attr("class", "tdAddSeparator");
//				});
//
//				$("#" + tableName + " #separadorAadidos").addClass("trAddSeparator");
//				$("#" + tableName + " #separadorAadidos").css("display", "");
//			}
return $self.jqGrid('addRowData',rowid,data,position,srcrowid);//Añadimos los estilos de elemento añadido
//			$("#" + tableName + " #" + rowid).addClass("addElement");
//$("#" + tableName + " #" + rowid + " td").addClass("addElementBorder");
},/**
     * Elimina de la tabla un registro determinado. El registro no se elimina del sistema de persistencia. Solo se elimina de manera visual.
     *
     * @name delRowData
     * @function
     * @param {string} rowid - Identificador del registro.
     * @return {jQuery} - Referencia al propio componente.
     * @example
     * $("#idComponente").rup_table("delRowData","10");
     */delRowData:function delRowData(rowid){var $self=$(this);$self.jqGrid('delRowData',rowid);return $self;},/**
     * Devuelve el identificador de la línea activa.
     *
     * @name getActiveRowId
     * @function
     * @return {string} - Identificador de la línea activa.
     * @example
     * $("#idComponente").rup_table("getActiveRowId");
     */getActiveRowId:function getActiveRowId(){var $self=this,settings=$self.data('settings');return jQuery.proxy(settings.getActiveRowId,$self)();},/**
     * Devuelve el índice de la línea activa.
     *
     * @name getActiveLineId
     * @function
     * @return {string} - Índice de la línea activa.
     * @example
     * $("#idComponente").rup_table("getActiveLineId");
     */getActiveLineId:function getActiveLineId(){var $self=this,settings=$self.data('settings');return jQuery.proxy(settings.getActiveLineId,$self)();},/**
     * Actualiza los valores de las columnas de un registro determinado. La actualización de loa datos se realiza solo de manera visual. Los nuevos datos no se persisten.
     *
     * @name setRowData
     * @function
     * @param {string} rowid - Identificador del registro que se desea actualizar.
     * @param {object} data - Objeto json que contiene los valores de cada columna de la nueva línea.
     * @param {string} cssp - En caso de especificarse, se añadirán a la línea las class de estilos aquí indicadas.
     * @example
     * $("#idComponente").rup_table("setRowData", "10", {campo1:valor1,campo2:valor2});
     */setRowData:function setRowData(rowid,data,cssp){var $self=$(this);$self.jqGrid('setRowData',rowid,data,cssp);//Actualizar tooltip de las celdas de la fila
jQuery('td[title]',$self).each(function(index,elem){var $cell=jQuery(elem),title=$cell.prop('title');$cell.attr({'grid_tooltip':title,'oldtitle':title}).removeAttr('title');});},/**
     * Devuelve un objeto json con los valores de los campos del registro indicado.
     *
     * @name getRowData
     * @function
     * @param {string} rowid - Identificador del registro del que se quieren recuperar los datos.
     * @return {object} - Objecto json con los valores del registro.
     * @example
     * $("#idComponente").rup_table("getRowData", "10");
     */getRowData:function getRowData(rowid){var $self=$(this);return $self.jqGrid('getRowData',rowid);},/**
     * Devuelve un array con los identificadores de los registros que se muestran actualmente en la página de la tabla.
     *
     * @name getDataIDs
     * @function
     * @return {string[]} - Identificadores de lso registros mostrados en la página actual.
     * @example
     * $("#idComponente").rup_table("getDataIDs");
     */getDataIDs:function getDataIDs(){var $self=$(this);return $self.jqGrid('getDataIDs');},/**
     * Limpia los registros mostrados en la tabla.
     *
     * @name clearGridData
     * @function
     * @param {boolean} clearfooter - En caso de indicarse como true se elimina la información del pié de la tabla.
     * @example
     * $("#idComponente").rup_table("clearGridData", false);
     */clearGridData:function clearGridData(clearfooter){var $self=$(this);return $self.jqGrid('clearGridData',clearfooter);},/**
     * Devuelve el objeto colModel del componente jqGrid.
     *
     * @name getColModel
     * @function
     * @return {object} - Objeto colModel de la tabla.
     * @example
     * $("#idComponente").rup_table("getColModel");
     */getColModel:function getColModel(){// Función que devuelve el colModel directamente.
var $self=$(this);return $self.jqGrid('getGridParam','colModel');},/**
     * Devuelve el valor de la columna de la fila indicada.
     *
     * @name getCol
     * @function
     * @param {string} rowid - Identificador de la fila.
     * @param {string} colName - Nombre de la columna.
     * @example
     * $("#idComponente").rup_table("getCol", "10", "nombre");
     */getCol:function getCol(rowid,colName){//Función que devuelve el valor de la celda de la fila que se le pasa como paramtero. El colName puede ser o el indice de la columna o el nombre de la misma
var $self=$(this);return $self.jqGrid('getCell',rowid,colName);},/**
     * Devuelve un objeto json que contiene la serialización del formulario.
     *
     * @name getSerializedForm
     * @function
     * @param {jQuery} form - Formulario que se desea serializar.
     * @param {boolean} skipEmpty - En caso de indicarse true se omiten los campos que no contienen valor.
     * @example
     * $("#idComponente").rup_table("getSerializedForm", $("#idFormulario"), false);
     */getSerializedForm:function getSerializedForm(form,skipEmpty,delimeter){return form2object(form instanceof jQuery?form[0]:form,delimeter?delimeter:null,skipEmpty?skipEmpty:false);}});//*******************************************************
// DEFINICIÓN DE LA CONFIGURACION POR DEFECTO DEL PATRON
//*******************************************************
jQuery.fn.rup_table.plugins={};jQuery.fn.rup_table.plugins.core={};jQuery.fn.rup_table.plugins.core.defaults={// adapter: "table_jqueryui",
adapter:'table_bootstrap',core:{operations:{},defaultOperations:{},showOperations:{},defaultLoadErrorTitle:$.rup.i18n.base.rup_ajax.errorTitle}};/**
   * Función de callback que será ejecutada cuando el usuario realice una acción sobre la operación.
   *
   * @callback module:rup_table~onOperation
   * @param {string} key - Identificador de la operación
   * @param {object} options - Opciones de configuración de la operación.
   * @example
   * callback: function(key, options){
   *		alert("Operación 1");
   *	}
   *//**
   * Función de callback que determina si la operación debe estar habilitada o no.
   *
   * @callback module:rup_table~isEnabled
   * @return {boolean} - Devuelve si la operación debe de estar habilitada o no.
   * @example
   * enabled: function(){
   *		return true;
   *	}
   *//**
   * Mediante esta propiedad se definen las posibles operaciones a realizar sobre los registros mostrados en la tabla. Debido al carácter global de estas operaciones se toman en cuenta por otros componentes (toolbar, menú contextual) a la hora de mostrar sus controles. Las operaciones se definen mediante un objeto json en el cual el nombre de la propiedad será el identificador de la propiedad.
   *
   * @typedef {Object} module:rup_table~Operations
   * @property {string} [name] - Texto a mostrar al usuario a la hora de visualizar la operación.
   * @property {string} [icon] - Clase CSS correspondiente al icono que se quiere visualizar junto a la operación.
   * @property {module:rup_table~isEnabled} [enabled] - Función que determina si el botón se debe mostrar habilitado o deshabilitado. Esto se determina devolviendo true/false desde la función de callback aquí indicada.
   * @property {module:rup_table~onOperation} [callback] - Función de callback que será ejecutada cuando el usuario realice una acción sobre la operación.
   * @example
   * core:{
   * 	operations:{
   *			"operacion1": {
   *				name: "Operación 1",
   *				icon: "rup-icon rup-icon-new",
   *				enabled: function(){
   *					return true;
   *				},
   *				callback: function(key, options){
   *					alert("Operación 1");
   *				}
   *			},
   *			"operacion2": {
   *				name: "Operación 2",
   *				icon: "rup-icon rup-icon-new",
   *				enabled: function(){
   *					return true;
   *				},
   *				callback: function(key, options){
   *					alert("Operación 1");
   *				}
   *			}
   *		}
   * }
   *//**
   * Permite habilitar/deshabilitar las operaciones definidas por defecto por otros módulos.
   *
   * @typedef module:rup_table~ShowOperations
   * @example
   * core:{
   *		showOperations:{
   *			add:false;
   *			clone:false;
   *		}
   *	}
   *//**
   * @description Propiedades de configuración del componente.
   * @see Para mas información consulte la documentación acerca de las opciones de configuración del componente {@link http://www.trirand.com/jqgridwiki/doku.php|jqGrid}.
   *
   * @name options
   *
   * @property {boolean} [altRows=true] - Determina si se aplica o no el pijama en las filas de la tabla.
   * @property {string} [altclass=rupgrid_oddRow] - Estilo que se aplica a las filas impares para mostrar el efecto.
   * @property {string} [datatype=json] - Formato de dato esperado para representar los registros de la tabla.
   * @property {string} [height=auto] - Determina la altura de la tabla.
   * @property {object} [jsonReader={repeatitems: false}] - Parámetros de configuración que determinan el modo en el que se va a procesar el json de retorno del servidor
   * @property {boolean} [resizable=false] - Determina si la tabla puede ser redimensionada mediante el ratón.
   * @property {number} [rowNum=10] - Número de registros por página que se van a mostrar en la tabla.
   * @property {number[]} [rowList=[10,20,30]] - Lista de posibles valores para el número de elementos por página que se van a mostrar en el combo de selección correspondiente.
   * @property {boolean} [sortable=true] - Determina si se permite variar el orden de las columnas arrastrándolas.
   * @property {boolean} [viewrecords=true] - Indica si se debe mostrar el rango de elementos que se están visualizando en la tabla.
   * @property {boolean} [loadOnStartUp=true] - Determina si se debe realizar automáticamente la búsqueda al cargar la página.
   * @property {string} [multiplePkToken=~] - Separador que se utiliza en los casos en los que la clave primaria sea múltiple. Se creará una columna que contenga un identificador único resultante de la concatenación de las claves primarias realizada mediante el separador aquí indicado.
   * @property {module:rup_table~Operations} [operations] - Mediante esta propiedad se definen las posibles operaciones a realizar sobre los registros mostrados en la tabla. Debido al carácter global de estas operaciones se toman en cuenta por otros componentes (toolbar, menú contextual) a la hora de mostrar sus controles. Las operaciones se definen mediante un objeto json en el cual el nombre de la propiedad será el identificador de la propiedad.
   * @property {module:rup_table~ShowOperations} [showOperations] - Permite habilitar/deshabilitar las operaciones definidas por defecto por otros módulos.
   * @property {number} [startOnPage=1] - Permite especificar el número de página inicial que se mostrará al cargar la página.
   */jQuery.fn.rup_table.defaults={altRows:true,altclass:'rup-grid_oddRow',datatype:'json',// Tipo de dato esperado para representar los registros de la tabla (jqGrid)
editable:false,// Determina si la tabla permite la edición en línea (rup_table)
height:'auto',// Ajusta la altura de la tabla al contenido (jqGrid)
jsonReader:{repeatitems:false},// Parámetros de configuración que describen la estructura del json esperado (jqGrid)
pager:null,resizable:false,// Determina si la tabla puede ser redimensionada mediante el ratón (jqGrid)
rowNum:10,// Determina el número de registros que se van a mostrar por página
rowList:[10,20,30],// Valores a mostrar en el combo de selección de número de registros por página
sortable:true,// Determina si se puede realizar drag&drop con las columnas de la tabla (jqGrid)
viewrecords:true,// Muestra el rango de elementos que se están mostrando en la tabla (jqGrid)
mtype:'POST',loadError:function loadError(xhr,st,err){var $self=$(this),settings=$self.data('settings');jQuery.rup_messages('msgError',{title:settings.core.defaultLoadErrorTitle,message:xhr.responseText});},loadOnStartUp:true,// Callback ejecutado en las peticiones AJAX de la tabla
loadBeforeSend:function rup_table_defaults_loadBeforeSend(xhr,settings){// Se modifica la request para incluir las siguientes cabeceras:
// Se añade la cabecera JQGridModel para indicar que la petición ha sido realizada por el componente rup_table
xhr.setRequestHeader('JQGridModel','true');// Se indica que el tipo de contenido enviado en la cabecera es application/jsons
xhr.setRequestHeader('Content-Type','application/json');},loadui:'block',validate:{},defaultPlugins:[],dataProxy:jQuery.rup_table.proxyAjax,defaultGridInfoCol:{name:'rupInfoCol',index:'rupInfoCol',editable:false,fixed:true,sortable:false,width:16,resizable:false,classes:'rupInfoCol',search:false,formatter:function formatter(){return'<span class=\'ui-icon ui-icon-rupInfoCol\'/>';}},defaultGridMultiplePkCol:{name:'pkCol',index:'pkCol',hidden:true,editable:false,fixed:true,sortable:false,width:25,resizable:false,search:false},multiplePkToken:'~',scrollOffset:0,showGridInfoCol:false,tooltipDelay:500};/* ********* *//* EVENTOS
  /* ********* *//**
   * Evento que se produce al detectarse que el usuario interactua con un elemento externo a la tabla.
   *
   * @event module:rup_table#rupTable_checkOutOfGrid
   * @property {Event} e - Objeto Event correspondiente al evento disparado.
   * @property {jQuery} $originalTarget - Objeto jQuery que referencia el elemento del dom con el que ha interactuado el usuario.
   * @example
   * $("#idComponente").on("rupTable_checkOutOfGrid", function(event,
   * $originalTarget){ });
   *//**
   * Este evento se lanza durante el proceso de serialización de la información que va a ser enviada para obtener los registros que se van a mostrar en la tabla.
   *
   * @event module:rup_table#rupTable_serializeGridData
   * @property {Event} e - Objeto Event correspondiente al evento disparado.
   * @property {object} data - Información serializada que va a ser enviada. Se puede modificar o agregar nuevos campos para completarla.
   * @example
   * $("#idComponente").on("rupTable_serializeGridData", function(event, data){
   * });
   *//**
   * Evento que se lanza antes de que se procese la información recibida del servidor.
   *
   * @event module:rup_table#rupTable_beforeProcessing
   * @property {Event} e - Objeto Event correspondiente al evento disparado.
   * @property {object} data - Información recibida del servidor.
   * @property {string} st - Mensaje de status de la petición.
   * @property {object} xhr - Objeto xhr recibido.
   * @example
   * $("#idComponente").on("rupTable_beforeProcessing", function(event, data, st,
   * xhr){ });
   *//**
   * Se produce cuando se elimina el resaltado de un registro de la tabla.
   *
   * @event module:rup_table#rupTableClearHighlightedRowAsSelected
   * @property {Event} e - Objeto Event correspondiente al evento disparado.
   * @property {jQuery} $row - Objeto jQuery que identifica la línea que se ha procesado.
   * @example
   * $("#idComponente").on("rupTableClearHighlightedRowAsSelected", function(event, $row){ });
   *//**
   * Se produce cuando se añade el resaltado a un registro de la tabla.
   *
   * @event module:rup_table#rupTableHighlightRowAsSelected
   * @property {Event} e - Objeto Event correspondiente al evento disparado.
   * @property {jQuery} $row - Objeto jQuery que identifica la línea que se ha procesado.
   * @example
   * $("#idComponente").on("rupTableHighlightedRowAsSelected", function(event, $row){ });
   *//**
   * Evento que se lanza después de que el componente haya finalizado con el proceso de configuración e inicialización.
   *
   * @event module:rup_table#rupTable_coreConfigFinished
   * @property {Event} e - Objeto Event correspondiente al evento disparado.
   * @example
   * $("#idComponente").on("rupTable_coreConfigFinished", function(event, $row){ });
   */})(jQuery);/*!
 * Copyright 2013 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 *//**
 * Tiene como objetivo proporcionar al componente RUP Table de las funcionalidades que ofrece el uso de un menú contextual.
 *
 * @summary Plugin de menú contextual del componente RUP Table.
 * @module rup_table/contextMenu
 * @example
 * $("#idComponente").rup_table({
 * 	url: "../jqGridUsuario",
 *	usePlugins:["contextMenu"],
 *	contextMenu:{
 * 		// Propiedades de configuración del plugin contextMenu
 * 	}
 * });
 */(function($){/**
	 * Definición de los métodos principales que configuran la inicialización del plugin.
	 *
	 * postConfiguration: Método que se ejecuta después de la invocación del componente jqGrid.
	 *
	 *//*global jQuery */jQuery.rup_table.registerPlugin('contextMenu',{loadOrder:4,preConfiguration:function preConfiguration(settings){var $self=this;return $self.rup_table('preConfigureContextMenu',settings);},postConfiguration:function postConfiguration(settings){var $self=this;return $self.rup_table('postConfigureContextMenu',settings);}});//********************************
// DEFINICIÓN DE MÉTODOS PÚBLICOS
//********************************
/**
	 * Extensión del componente rup_table para permitir la gestión del diseño líquido del componente.
	 *
	 * Los métodos implementados son:
	 *
	 * postConfigureFilter(settings): Método que define la preconfiguración necesaria para el correcto funcionamiento del componente.
	 *
	 * Se almacena la referencia de los diferentes componentes:
	 *
	 * settings.$fluidBaseLayer : Referencia a la capa que se tomará como base para aplicar el diseño líquido.
	 *
	 */jQuery.fn.rup_table('extend',{/**
		 * Metodo que realiza la pre-configuración del plugin contextMenu del componente RUP Table.
		 * Este método se ejecuta antes de la incialización del plugin.
		 *
		 * @name preConfigureContextMenu
		 * @function
		 * @param {object} settings - Parámetros de configuración del componente.
		 */preConfigureContextMenu:function preConfigureContextMenu(settings){var $self=this,contextMenuSettings=settings.contextMenu;// Se unifican los parámetros de configuración de mostrar/ocultar los botones de la toolbar
if(contextMenuSettings.createDefaultRowOperations===true){contextMenuSettings.showOperations=jQuery.extend(true,{},contextMenuSettings.defaultRowOperations,settings.core.showOperations,contextMenuSettings.showOperations);}},/**
		 * Metodo que realiza la post-configuración del plugin contextMenu del componente RUP Table.
		 * Este método se ejecuta después de la incialización del plugin.
		 *
		 * @name postConfigureContextMenu
		 * @function
		 * @param {object} settings - Parámetros de configuración del componente.
		 */postConfigureContextMenu:function postConfigureContextMenu(settings){var $self=this,contextMenuSettings=settings.contextMenu;function getTdIndex(thArray,name){for(var i=0;i<thArray.length;i++){if(jQuery(thArray[i]).attr('id')===settings.id+'_'+name){return i+1;}}return-1;}$self.one({'jqGridLoadComplete.rupTable.contextMenu':function jqGridLoadCompleteRupTableContextMenu(data){var $tbodyTr=jQuery('[id=\''+$self.attr('id')+'\'] tbody:first tr[role=\'row\'].jqgrow'),contextRowItems={},cellLevelContextMenu=false,globalCellLevelContextMenu=jQuery.isArray(settings.contextMenu.colNames),itemsPerColumn={},colItem,thArray,$contextMenuSelector;//					jQuery.each(settings.contextMenu.defaultRowOperations, function(buttonId, value){
jQuery.each(settings.contextMenu.showOperations,function(buttonId,value){var operationCfg;if(value!==false){operationCfg=settings.core.operations[buttonId];if(operationCfg!==undefined){contextRowItems[buttonId]={name:operationCfg.name,id:settings.id+'_contextMenu_'+buttonId,cssSprite:operationCfg.icon,disabled:function disabled(){return!jQuery.proxy(operationCfg.enabled,$self)();},callback:function callback(key,options){jQuery.proxy(operationCfg.callback,$self)(key,options);},className:operationCfg.className};if(jQuery.isArray(value)===true){cellLevelContextMenu=true;contextRowItems[buttonId].colNames=value;}}}});jQuery.each(settings.contextMenu.items,function(index,oper){if(jQuery.isArray(oper.colNames)){cellLevelContextMenu=true;}});jQuery.extend(true,contextRowItems,settings.contextMenu.items);// En caso de especificar solo para unas columnas
thArray=jQuery('[id=\'gview_'+settings.id+'\'] '+settings.contextMenu.theadThSelector);// Eliminamos los contextMenu creados previamente
$('ul.context-menu-list',$tbodyTr).remove();if(globalCellLevelContextMenu&&!cellLevelContextMenu){for(var i=0;i<contextMenuSettings.colNames.length;i++){$contextMenuSelector=jQuery('[id=\''+$self.attr('id')+'\'] '+contextMenuSettings.tbodyTdSelector+':nth-child('+getTdIndex(thArray,contextMenuSettings.colNames[i])+')');$.contextMenu('destroy',$contextMenuSelector);$contextMenuSelector.rup_contextMenu({items:contextRowItems});}}else if(cellLevelContextMenu){//						// En caso de no especificarse un valor de colnames para indicar sobre cuales se debe de mostrar el menú contextual, se toman todas las visibles.
if(!jQuery.isArray(contextMenuSettings.colNames)){contextMenuSettings.colNames=jQuery.map(settings.colModel,function(elem,index){if(elem.hidden!==true){return elem.name;}});}jQuery.each(contextRowItems,function(index,item){var colNamesAux;if(jQuery.isArray(item.colNames)){colNamesAux=item.colNames;}else{colNamesAux=contextMenuSettings.colNames;}for(var i=0;i<colNamesAux.length;i++){colItem={};colItem[colNamesAux[i]]={};jQuery.extend(true,itemsPerColumn,colItem);var itemAux={};itemAux[index]=item;jQuery.extend(true,itemsPerColumn[colNamesAux[i]],itemAux);}});jQuery.each(itemsPerColumn,function(index,item){$contextMenuSelector=jQuery('[id=\''+$self.attr('id')+'\'] '+contextMenuSettings.tbodyTdSelector+':nth-child('+getTdIndex(thArray,index)+')');$.contextMenu('destroy',$contextMenuSelector);$contextMenuSelector.rup_contextMenu({items:item});});}else{$.contextMenu('destroy',$tbodyTr);$tbodyTr.rup_contextMenu({items:contextRowItems});}}});}});//*******************************************************
// DEFINICIÓN DE LA CONFIGURACION POR DEFECTO DEL PATRON
//*******************************************************
/**
   * @description Propiedades de configuración del plugin contextMenu del componente RUP Table.
   *
   * @name options
   *
   * @property {string[]} [colNames=null] - Mediante un array se puede configurar las columnas para las cuales se va a mostrar el menú contextual. En caso de especificar el valor null se mostrará en todas las columnas.
   * @property {boolean} [createDefaultRowOperations=true] - Propiedad que indica si el componente va a mostrar las operaciones por defecto como opciones dentro del menú contextual.
   * @property {string} [tbodySelector='tbody:first tr[role=\'row\'].jqgrow'] - Selector de jQuery que identifica el tbody de la tabla. Este selector se utiliza para mostrar el menú contextual a nivel de tabla.
	 * @property {string} [tbodyTdSelector='tbody:first tr.jqgrow td'] - Selector de jQuery que identifica las columnas de la tabla. Este selector se utiliza para mostrar el menú contextual a nivel de columna.
	 * @property {string} [theadThSelector='thead:first th'] - Selector de jQuery que identifica las cabeceras de las columnas de la tabla.
   * @property {object} [items={}}] - Se especifica la configuración de los diferentes items que se van a mostrar en el menú contextual para los registros.
	 * @property {rup_table~Operations[]} [showOperations] - Permite indicar que operaciones definidas de manera global van a ser mostradas como opciones en el menú contextual.
   */jQuery.fn.rup_table.plugins.contextMenu={};jQuery.fn.rup_table.plugins.contextMenu.defaults={contextMenu:{colNames:null,createDefaultRowOperations:true,defaultRowOperations:{},rowOperations:{},tbodySelector:'tbody:first tr[role=\'row\'].jqgrow',tbodyTdSelector:'tbody:first tr.jqgrow td',theadThSelector:'thead:first th',items:{}}};})(jQuery);/*!
 * Copyright 2013 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 *//*global jQuery *//**
 * Gestiona las operaciones de filtrado de datos sobre el origen de datos que utiliza el componente.
 *
 * @summary Plugin de filtrado del componente RUP Table.
 * @module rup_table/filter
 * @example
 *
 * $("#idComponente").rup_table({
 * 	url: "../jqGridUsuario",
 * 	usePlugins:["filter"],
 * 	filter:{
 * 		// Propiedades de configuración del plugin filter
 * 	}
 * });
 */(function($){/**
	 * Definición de los métodos principales que configuran la inicialización del plugin.
	 *
	 * postConfiguration: Método que se ejecuta después de la invocación del componente jqGrid.
	 *
	 */jQuery.rup_table.registerPlugin('filter',{loadOrder:1,preConfiguration:function preConfiguration(settings){var $self=this;return $self.rup_table('preConfigureFilter',settings);},postConfiguration:function postConfiguration(settings){var $self=this;return $self.rup_table('postConfigureFilter',settings);}});//********************************
// DEFINICIÓN DE MÉTODOS PÚBLICOS
//********************************
/**
	 * Extensión del componente rup_table para permitir la gestión del filtrado de registros de la tabla.
	 *
	 * Los métodos implementados son:
	 *
	 * postConfigureFilter(settings): Método que define la preconfiguración necesaria para el correcto funcionamiento del componente.
	 *
	 * Se almacena la referencia de los diferentes componentes:
	 *
	 * settings.filter.$filterContainer : Contenedor del formulario de filtrado
	 * settings.filter.$filterButton : Botón que realiza el filtrado
	 * settings.filter.$cleanButton : Botón para limpiar el formulario
	 * settings.filter.$collapsableLayer : Capa que puede ser ocultada/mostrada
	 * settings.filter.$toggleIcon1Id : Control que oculta muestra el fomulario
	 * settings.filter.$filterSummary : Contenedor donde se especifican los criterios de filtrado
	 *
	 */jQuery.fn.rup_table('extend',{/**
			* Metodo que realiza la pre-configuración del plugin filter del componente RUP Table.
			* Este método se ejecuta antes de la incialización del plugin.
			*
			* @name preConfigureFilter
			* @function
			* @param {object} settings - Parámetros de configuración del componente.
			*/preConfigureFilter:function preConfigureFilter(settings){var $self=this,tableId=settings.id,filterSettings=settings.filter,filterFormId,toggleIcon1Tmpl,toggleLabelTmpl,filterSummaryTmpl,toggleIcon2Tmpl,$toggleIcon1,$toggleLabel,$filterSummary,$toggleIcon2;/*
			 * Inicialización de los identificadores y componentes por defecto de los componentes de filtrado
			 */filterSettings.id=filterSettings.id!==undefined?filterSettings.id:tableId+'_filter_form';filterSettings.filterToolbarId=filterSettings.filterToolbar!==undefined?filterSettings.filterToolbar:tableId+'_filter_toolbar';filterSettings.filterButtonId=filterSettings.filterButtonId!==undefined?filterSettings.filterButtonId:tableId+'_filter_filterButton';filterSettings.cleanButtonId=filterSettings.cleanButtonId!==undefined?filterSettings.cleanButtonId:tableId+'_filter_cleanButton';filterSettings.collapsableLayerId=filterSettings.collapsableLayerId!==undefined?filterSettings.collapsableLayerId:tableId+'_filter_fieldset';filterSettings.toggleIcon1Id=filterSettings.toggleIcon1!==undefined?filterSettings.toggleIcon1:tableId+'_filter_toggle_icon1';filterSettings.toggleLabelId=filterSettings.toggleLabelId!==undefined?filterSettings.toggleLabelId:tableId+'_filter_toggle_label';filterSettings.filterSummaryId=filterSettings.filterSummaryId!==undefined?filterSettings.filterSummaryId:tableId+'_filter_summary';filterSettings.toggleIcon2Id=filterSettings.toggleIcon2!==undefined?filterSettings.toggleIcon2:tableId+'_filter_toggle_icon2';filterSettings.$filterContainer=jQuery('#'+filterSettings.id);filterSettings.$filterToolbar=jQuery('#'+filterSettings.filterToolbarId);if(filterSettings.$filterContainer.length===0){alert('El identificador especificado para el fomulario de búsqueda no existe.');}else if(filterSettings.$filterToolbar.length===0){alert('El identificador especificado para la barra de controles del formulario de filtrado no existe.');}else{/*
				 * Se almacena la referencia de los diferentes componentes
				 *
				 * $filterContainer : Contenedor del formulario de filtrado
				 * $filterButton : Botón que realiza el filtrado
				 * $cleanButton : Botón para limpiar el formulario
				 * $collapsableLayer : Capa que puede ser ocultada/mostrada
				 * $toggleIcon1Id : Control que oculta muestra el fomulario
				 * $filterSummary : Contenedor donde se especifican los criterios de filtrado
				 */toggleIcon1Tmpl=jQuery.rup.i18nParse(jQuery.rup.i18n.base,'rup_table.templates.filter.toggleIcon1');toggleLabelTmpl=jQuery.rup.i18nParse(jQuery.rup.i18n.base,'rup_table.templates.filter.toggleLabel');filterSummaryTmpl=jQuery.rup.i18nParse(jQuery.rup.i18n.base,'rup_table.templates.filter.filterSummary');toggleIcon2Tmpl=jQuery.rup.i18nParse(jQuery.rup.i18n.base,'rup_table.templates.filter.toggleIcon2');$toggleIcon1=$(jQuery.jgrid.format(toggleIcon1Tmpl,filterSettings.toggleIcon1Id));$toggleLabel=$(jQuery.jgrid.format(toggleLabelTmpl,filterSettings.toggleLabelId,$.rup.i18n.base.rup_table.plugins.filter.filterCriteria));$filterSummary=$(jQuery.jgrid.format(filterSummaryTmpl,filterSettings.filterSummaryId));$toggleIcon2=$(jQuery.jgrid.format(toggleIcon2Tmpl,filterSettings.toggleIcon2Id));filterSettings.$filterToolbar.append($toggleIcon1).append($toggleLabel).append($filterSummary).append($toggleIcon2);filterSettings.$filterContainer=jQuery('#'+filterSettings.id);filterSettings.$filterButton=jQuery('#'+filterSettings.filterButtonId);//Creacion del boton de filtrado
//filterSettings.$filterButton.addClass("dropdownButton");
//filterSettings.$filterButton.append('<ul><li class="dropdownButton-list"><a  class="dropdownButton-trigger" href="#">Filtro</a><div class="dropdownButton-content"><form><fieldset class="dropdownButton-inputs"><div id="dropdownButton-combo"></div></fieldset>       <fieldset class="dropdownButton-actions"><input class="ui-button ui-widget ui-state-default ui-corner-all"  value="Guardar" type="submit"><input  class="ui-button ui-widget ui-state-default ui-corner-all"  value="Aplicar" type="submit"> <input class="ui-button ui-widget ui-state-default ui-corner-all"  value="Eliminar" type="submit"></fieldset>                 </form>               </div></li>             <li class="dropdownButton-menu"><a class="dropdownButton-lanzador" href="#"><span>▼</span></a></li> </ul>');
filterSettings.$cleanButton=jQuery('#'+filterSettings.cleanButtonId);filterSettings.$collapsableLayer=jQuery('#'+filterSettings.collapsableLayerId);filterSettings.$toggleIcon1=$toggleIcon1;filterSettings.$toggleLabel=$toggleLabel;filterSettings.$filterSummary=$filterSummary;filterSettings.$toggleIcon2=$toggleIcon2;/*
				 * TODO: Comprobar que la configuración es correcta
				 */if(filterSettings.$filterContainer.prop('tagName')==='FORM'){filterSettings.$filterContainer.ajaxForm();}// Se utiliza el plugin ajaxForm de jQuery para configurar el formualario de busqueda como AJAX.
// Se redimensiona el formulario de busqueda al tamanyo del grid.
filterSettings.$filterContainer.parent().css('width',$self.rup_table('getGridParam','width'));// Se configura la url de filtrado
if(settings.filter.url===null){settings.filter.url=settings.baseUrl+'/filter';}settings.url=settings.filter.url;// Se almacena en las propiedades la url utilizada para la busqueda a partir de la especificada en el grid.
settings.searchURL=$self.rup_table('getGridParam','url');// Se asigna a la tecla ENTER la funcion de busqueda.
filterSettings.$filterContainer.bind('keydown',function(evt){if(evt.keyCode==13){// TODO : poner como evento
//$self.rup_table("showSearchCriteria");
$self.rup_table('filter');}});// Creacion del boton de busqueda.
filterSettings.$filterButton.bind('click',function(){// TODO: Control cambios
// TODO : poner como evento
//Deshabilitar el nombre del filtro en el filterSummary una vez que ha terminado el filtro por defecto
if(settings.$firstStartUp){settings.$firstStartUp=false;}//$self.rup_table("showSearchCriteria");
$self.rup_table('filter');});// Creacion del botón de limpiar formulario.
filterSettings.$cleanButton.bind('click',function(){// TODO : poner como evento
if(settings.$firstStartUp){settings.$firstStartUp=false;}$self.rup_table('cleanFilterForm').rup_table('filter');if(filterSettings.validate!==undefined){jQuery('.rup-maint_validateIcon',filterSettings.$filterContainer).remove();}//$self.rup_table("showSearchCriteria");
});filterSettings.$toggleIcon1.add(filterSettings.$toggleLabel).add(filterSettings.$toggleIcon2).attr('tabindex','0').on({'keydown':function keydown(evt){if(evt.keyCode==13){$self.rup_table('toggleFilterForm');}}});filterSettings.$filterToolbar.addClass('cursor_pointer').on({'click':function click(){$self.rup_table('toggleFilterForm');}});if(settings.filter.showHidden===true){filterSettings.$collapsableLayer.hide();//						filterSettings.$collapsableRowShow.show();
filterSettings.$toggleIcon1.removeClass('ui-icon-triangle-1-n').addClass('ui-icon-triangle-1-s');filterSettings.$filterSummary.parent().addClass('rup-maint_searchCriteria');}// Configuración de validaciones
if(filterSettings.validate!==undefined){filterSettings.$filterContainer.rup_validate(filterSettings.validate);$self.on({'rupTable_beforeFilter.filter.validate':function rupTable_beforeFilterFilterValidate(){//filterSettings.$filterContainer.rup_validate("resetForm");
if(multifilterSettings!==undefined){if(!settings.$firstStartUp){return filterSettings.$filterContainer.valid();}else{return null;}}else{return filterSettings.$filterContainer.valid();}}});}}$self.on({'rupTable_serializeGridData.filter':function rupTable_serializeGridDataFilter(events,postData){var filterParams=form2object(settings.filter.$filterContainer[0]),queryStrFilterParams=jQuery.param(filterParams),lastFilterParams=$self.data('tmp.lastFilterParams');var filtro;if(settings.$firstStartUp==true){var filtro=multifilterSettings.$filterDefaultValue;}if(filtro==undefined){jQuery.extend(postData,{'filter':filterParams});}else{jQuery.extend(postData,{'filter':filtro});}if(lastFilterParams===undefined||lastFilterParams!==queryStrFilterParams){jQuery.extend(postData,{page:$self.data('tmp.firstLoad')===true&&settings.core.startOnPage!==null?settings.core.startOnPage:'1'});$self.data('tmp.lastFilterParams',queryStrFilterParams);}}});$self.on('jqGridGridComplete',function(event){if($self.data('settings')!==undefined){$self.rup_table('showSearchCriteria');}});// gestion de evento por defecto Multifiltro
if(settings.multifilter!=undefined&&settings.multifilter!=null){var $filterForm,$filterDefaultName,$firstStartUp;var multifilterSettings=settings.multifilter;settings.filter.$filterForm=$('#'+settings.id+'_filter_form');var selector;settings.$firstStartUp=true;if(multifilterSettings.idFilter!=null){selector=multifilterSettings.idFilter;}else{selector=settings.id;}var usuario;if(multifilterSettings.userFilter!=null){usuario=multifilterSettings.userFilter;}else{usuario=LOGGED_USER;}var getDefault;if(multifilterSettings.getDefault!=null){getDefault=multifilterSettings.getDefault;}else{getDefault=true;}// getDefault
if(getDefault){$.rup_ajax({url:settings.baseUrl+'/multiFilter/getDefault?filterSelector='+selector+'&user='+usuario,type:'GET',dataType:'json',showLoading:false,contentType:'application/json',//async : false,
complete:function complete(jqXHR,textStatus){if(settings.loadOnStartUp){$self.rup_table('filter');}$self.triggerHandler('rupTable_multifilter_fillForm',$self.data.filterData);//												$self.triggerHandler("rupTable_multifilter_fillForm",form2object(settings.filter.$filterContainer[0]));
},success:function success(data,status,xhr){if(data!=null){var valorFiltro=$.parseJSON(data.filterValue);$self._fillForm(valorFiltro);//settings.filter.$filterSummary.html("<i>"+data.filterName+"</i>");
multifilterSettings.$filterDefaultName=data.filterName;multifilterSettings.$filterDefaultValue=valorFiltro;$self.data.filterData=valorFiltro;}},error:function error(xhr,ajaxOptions,thrownError){}});}}},/**
		 * Metodo que realiza la post-configuración del plugin filter del componente RUP Table.
		 * Este método se ejecuta después de la incialización del plugin.
		 *
		 * @name postConfigureFilter
		 * @function
		 * @param {object} settings - Parámetros de configuración del componente.
		 */postConfigureFilter:function postConfigureFilter(settings){var $self=this,filterFormId,filterSettings;}});//********************************
// DEFINICIÓN DE MÉTODOS PÚBLICOS
//********************************
/**
	 * Métodos públicos del plugin filter.
	 *
	 * cleanFilterForm: Realiza una limpieza de los campos del formulario.
	 * filter: Lanza el filtrado de la tabla de acuerdo a los criterios indicados en el formulario.
	 * toggleFilterForm: Método encargado de ocultar y mostrar el formulario de filtrado.
	 *
	 */jQuery.fn.rup_table('extend',{/**
     * Limpia los campos del formulario de filtrado.
     *
     * @function  cleanFilterForm
		 * @fires module:rup_table#rupTable_filter_beforeCleanFilterForm
		 * @fires module:rup_table#rupTable_filter_afterCleanFilterForm
     * @example
     * $("#idComponente").rup_table("cleanFilterForm");
     */cleanFilterForm:function cleanFilterForm(){var $self=this,settings=$self.data('settings');$self.triggerHandler('rupTable_filter_beforeCleanFilterForm');$self.rup_table('resetForm',settings.filter.$filterContainer);$self.triggerHandler('rupTable_filter_afterCleanFilterForm');return $self;},/**
     * Realiza el filtrado de acuerdo a los datos existentes en el formulario de filtrado.
     *
     * @function  filter
		 * @fires module:rup_table#rupTable_beforeFilter
     * @example
     * $("#idComponente").rup_table("filter");
     */filter:function filter(){var $self=this,settings=$self.data('settings');var bfr=$self.triggerHandler('rupTable_beforeFilter');if(bfr===false||bfr==='stop'){return;}if($.isFunction(settings.filter.beforeFilter)){bfr=settings.filter.beforeFilter.call($self);if(bfr===undefined){bfr=true;}if(bfr===false){return;}}$self.rup_table('setGridParam',{page:'1'});$self.trigger('reloadGrid');},/**
     * Devuelve los parámetros de filtrado empleados en el filtrado.
     *
     * @function  getFilterParams
     * @example
     * $("#idComponente").rup_table("getFilterParams");
     */getFilterParams:function getFilterParams(){var $self=this,settings=$self.data('settings');return form2object(settings.filter.$filterContainer[0]);},/**
     *  Oculta el formulario de filtrado.
     *
     * @function  hideFilterForm
     * @example
     * $("#idComponente").rup_table("hideFilterForm");
     */hideFilterForm:function hideFilterForm(){var $self=$(this),settings=$self.data('settings'),filterSettings=settings.filter;filterSettings.$collapsableLayer.hide(settings.filter.transitionConfig);//			filterSettings.$collapsableRowShow.show(settings.filter.transitionConfig);
filterSettings.$toggleIcon2.removeClass('ui-icon-circle-triangle-n').addClass('ui-icon-circle-triangle-s');filterSettings.$toggleIcon1.removeClass('ui-icon-triangle-1-s').addClass('ui-icon-triangle-1-e');filterSettings.$filterSummary.parent().addClass('rup-maint_searchCriteria');},/**
     * Muestra el formulario de filtrado.
     *
     * @function showFilterForm
     * @example
     * $("#idComponente").rup_table("showFilterForm");
     */showFilterForm:function showFilterForm(){var $self=$(this),settings=$self.data('settings'),filterSettings=settings.filter;// Se muestra el formulario de búsqueda
filterSettings.$collapsableLayer.show($.extend({},settings.filter.transitionConfig,{complete:function complete(){// Anadido el foco al primer campo del formulario
jQuery('input:first',filterSettings.$filterContainer).focus();}}));filterSettings.$toggleIcon2.removeClass('ui-icon-circle-triangle-s').addClass('ui-icon-circle-triangle-n');filterSettings.$toggleIcon1.removeClass('ui-icon-triangle-1-e').addClass('ui-icon-triangle-1-s');filterSettings.$filterSummary.parent().removeClass('rup-maint_searchCriteria');//Eliminar tooltip
//			$titleSearch.rup_tooltip("destroy");
//			filterSettings.$collapsableRowShow.hide(settings.filter.transitionConfig);
},/**
     * Alterna el estado del formulario de filtrado entre visible y oculto.
     *
     * @function toggleFilterForm
     * @example
     * $("#idComponente").rup_table("toggleFilterForm");
     */toggleFilterForm:function toggleFilterForm(){var $self=$(this),settings=$self.data('settings'),filterSettings=settings.filter;if(filterSettings.$collapsableLayer.is(':hidden')){//MOSTRAR
$self.rup_table('showFilterForm');}else{// OCULTAR
$self.rup_table('hideFilterForm');}return $self;},/**
     * Actualiza el resumen de los criterios de filtrado a partir de los valores existentes en el formulario.
     *
     * @function showSearchCriteria
     * @example
     * $("#idComponente").rup_table("showSearchCriteria");
     */showSearchCriteria:function showSearchCriteria(){var $self=this,settings=$self.data('settings'),searchString=' ',temp='',label,numSelected,field,fieldId,fieldName,fieldValue,aux=settings.filter.$filterContainer.serializeArray(),searchForm=settings.filter.$filterContainer,filterMulticombo=new Array();var obj;//añadir arbol
var nombreArbol=$('.jstree',settings.filter.$filterContainer);var arboles=$('.jstree',settings.filter.$filterContainer);$.each(arboles,function(index,item){obj=new Object();obj.name=$(item).attr('name');obj.value=$(item).rup_tree('getRupValue').length;obj.type='rup_tree';aux.push(obj);});for(var i=0;i<aux.length;i++){if(aux[i].value!==''&&$.inArray(aux[i].name,settings.filter.excludeSummary)!=0){//CAMPO a tratar
field=$('[name=\''+aux[i].name+'\']',searchForm);//Comprobar si se debe excluir el campo
if($.inArray(field.attr('id'),settings.filter.filterExclude)!==-1){continue;}//Seleccionar radio
if(field.length>1){field=$('[name=\''+aux[i].name+'\']:checked',searchForm);}//Omitir campos hidden
if($(field).attr('type')==='hidden'){continue;}//ID del campo
fieldId=$(field).attr('id');//ID para elementos tipo rup.combo
if($(field).attr('ruptype')==='combo'){if(field.next('.ui-multiselect').length==0){fieldId+='-button';}}//ID para elementos tipo rup.autocomplete
if($(field).attr('ruptype')==='autocomplete'){fieldId=fieldId.substring(0,fieldId.indexOf('_label'));}//NAME
label=$('label[for^=\''+fieldId+'\']',searchForm);if(label.length>0){// <label for='xxx' />
fieldName=label.html();}else{// <div />
// <div />
if($(field).attr('ruptype')!=='combo'){//fieldName= $("[name='" + aux[i].name + "']",searchForm).prev('div').html();
fieldName=$('[name=\''+aux[i].name+'\']',searchForm).prev('div').find('label').first().html();}else{//fieldName= $("[name='" + aux[i].name + "']",searchForm).parent().prev('div').html();
// Buscamos el label asociado al combo
// Primero por id
var $auxField=$('[name=\''+aux[i].name+'\']',searchForm),$labelField;$labelField=jQuery('[for=\''+$auxField.attr('id')+'\']');if($labelField.length>0){fieldName=$labelField.first().text();}else{fieldName=$('[name=\''+aux[i].name+'\']',searchForm).parent().prev('div').find('label').first().html();}}}if(fieldName===null||fieldName===undefined){fieldName='';}//VALUE
fieldValue=' = ';switch($(field)[0].tagName){case'INPUT':fieldValue=fieldValue+$(field).val();if($(field)[0].type==='checkbox'||$(field)[0].type==='radio'){fieldValue='';}break;//Rup-tree
case'DIV':$.each(aux,function(index,item){if(item.name==field.attr('id')){if(item.value!=0){fieldValue+=' = '+item.value;}}else{fieldValue='';}});if(fieldValue==''){fieldName='';}break;case'SELECT':if(field.next('.ui-multiselect').length==0){fieldValue=fieldValue+$('option[value=\''+aux[i].value+'\']',field).html();}else{if($.inArray($(field).attr('id'),filterMulticombo)===-1){numSelected=field.rup_combo('value').length;if(numSelected!==0){fieldValue+=numSelected;}else{fieldName='';fieldValue='';}filterMulticombo.push($(field).attr('id'));}else{fieldName='';fieldValue='';}}break;}//Parsear NAME
var parseableChars=new Array(':','=');for(var j=0;j<parseableChars.length;j++){if(fieldName!==''&&fieldName.indexOf(parseableChars[j])!==-1){fieldName=fieldName.substring(0,fieldName.indexOf(parseableChars[j]));break;}}//Controlar rup.combo con valor vacío
while(fieldValue.indexOf('&amp;nbsp;')!==-1){fieldValue=fieldValue.replace('&amp;nbsp;','');}//Si no tiene NAME sacar solo el valor
if(fieldName===''&&fieldValue.indexOf(' = ')!==-1){fieldValue=fieldValue.substring(2,fieldValue.length);}//Si no tiene NAME ni VALUE omitir
if(fieldName===''&&$.trim(fieldValue)===''){continue;}searchString=searchString+fieldName+fieldValue+', ';}}if(jQuery.isFunction(settings.filter.fncSearchCriteria)){searchString=jQuery.proxy(settings.filter.fncSearchCriteria,$self,searchString)();}if($.trim(searchString).length-1==$.trim(searchString).lastIndexOf(',')){searchString=searchString.substr(0,searchString.lastIndexOf(','))+' ';}if(settings.multifilter){if(jQuery.isFunction(settings.multifilter.fncFilterName)){searchString=jQuery.proxy(settings.multifilter.fncFilterName,$self,searchString)();}}//Contiene criterios
//			if (searchString.length>1){
//searchString = searchString.substring(0, searchString.length-2);
var initialHeight=$('#titleSearch_'+settings.id.name).css('height'),height,tmp=searchString,tooltip=false;//Añadir criterios
while(true){settings.filter.$filterSummary.html(' <i>'+tmp+'</i>');height=$('#titleSearch_'+settings.id.name).css('height');if(height===initialHeight){break;}tmp=tmp.substring(0,tmp.lastIndexOf(','))+' <b>...</b>';tooltip=true;}//Tooltip con criterios
if(tooltip){settings.filter.$filterSummary.rup_tooltip({content:{text:searchString.substring(1)},position:{my:'bottom center',at:'top center'}});}}//		}
});//*******************************
// DEFINICIÓN DE MÉTODOS PRIVADOS
//*******************************
jQuery.fn.rup_table('extend',{/**
     * Obtiene el label correspondiente a un campo por el que se realiza el filtrado.
     *
     * @function _getSearchFormFieldLabel
		 * @private
		 * @param {object} $field Referencia jQuery a un campo del formulario de filtrado.
		 * @param {object} $form Referencia jQuery al formulario de filtrado.
		 * @return {string} - Label identificador al campo del formulario indicado por parámetro.
     * @example
     * $self._getSearchFormFieldLabel($field, $form);
     */_getSearchFormFieldLabel:function _getSearchFormFieldLabel($field,$form){var fieldId=$field.attr('id'),$label,formFieldLabel='',rupType=$field.attr('ruptype');if(rupType!=='combo'){$label=jQuery('label[for=\''+fieldId+'\']',$form);}else{$label=jQuery('label[for=\''+fieldId+'-button\']',$form);}if($label.length>0){// <label for='xxx' />
formFieldLabel=$label.html();}else{// <div />
// <div />
if($field.attr('ruptype')!=='combo'){//fieldName= $("[name='" + aux[i].name + "']",searchForm).prev('div').html();
formFieldLabel=$('[name=\''+name+'\']',$form).prev('div').find('label').first().html();}else{//fieldName= $("[name='" + aux[i].name + "']",searchForm).parent().prev('div').html();
formFieldLabel=$('[name=\''+name+'\']',$form).parent().prev('div').find('label').first().html();}}// Eliminamos los caracteres ':' y '=' que puedan existir en el label
formFieldLabel=formFieldLabel.replace(/[:=]/g,'');return formFieldLabel;},/**
     * Obtiene el value del campo por el que se está filtrando.
     *
     * @function _getSearchFormFieldLabel
		 * @private
		 * @param {object} $field Referencia jQuery a un campo del formulario de filtrado.
		 * @param {object} $form Referencia jQuery al formulario de filtrado.
		 * @return {string} - Value correspondiente al campo del formulario indicado por parámetro.
     * @example
     * $self._getSearchFormFieldValue($field, $form);
     */_getSearchFormFieldValue:function _getSearchFormFieldValue($field,$form){var fieldValue=' = ',filterMulticombo=[],numSelected,fieldName;//VALUE
switch($field.prop('tagName')){case'INPUT':fieldValue=fieldValue+$field.val();if($field.attr('type')==='checkbox'||$field.attr('type')==='radio'){fieldValue='';}break;case'SELECT':if($field.next('.ui-multiselect').length==0){fieldValue=fieldValue+$('option[value=\''+$field.rup_combo('getRupValue')+'\']',$field).html();}else{if($.inArray($field.attr('id'),filterMulticombo)===-1){numSelected=$field.rup_combo('value').length;if(numSelected!==0){fieldValue+=numSelected;}else{fieldName='';fieldValue='';}filterMulticombo.push($field.attr('id'));}else{fieldName='';fieldValue='';}}break;}//Controlar rup.combo con valor vacío
while(fieldValue.indexOf('&amp;nbsp;')!==-1){fieldValue=fieldValue.replace('&amp;nbsp;','');}return fieldValue;}});//*******************************************************
// DEFINICIÓN DE LA CONFIGURACION POR DEFECTO DEL PATRON
//*******************************************************
/**
	 * Parámetros de configuración por defecto para el plugin filter.
	 *
	 *//**
 	* @description Propiedades de configuración del plugin filter del componente RUP Table.
 	*
 	* @name options
 	*
 	* @property {boolean} [showHidden=false] -  Determina si el formulario de filtrado se debe de mostrar inicialmente oculto o no.
 	* @property {string} [url=null] - Url que se va a utilizar para realizar las peticiones de filtrado de la tabla. En caso de no especificarse una concreta, se utilizará por defecto una construida a partir de la url base. (urlBase + /filter).
 	* @property {object} [transitionConfig] - Configuración del efecto de la animación de mostrar/ocultar el formulario defiltrado.
 	* @property {function} [fncSearchCriteria] - Permite especificar una función de callback en la cual es posible modificar la cadena de texto con la que se muestra el resumen de los parámetros de filtrado.
 	*/jQuery.fn.rup_table.plugins.filter={};jQuery.fn.rup_table.plugins.filter.defaults={core:{startOnPage:null},filter:{url:null,showHidden:false,transitionConfig:{duration:'slow',effect:'blind'}}};/* ********* *//* EVENTOS
  /* ********* *//**
   *  Se lanza antes de producirse la petición de filtrado.
   *
   * @event module:rup_table#rupTable_beforeFilter
   * @property {Event} e - Objeto Event correspondiente al evento disparado.
   * @example
   * $("#idComponente").on("rupTable_beforeFilter", function(event){ });
   *//**
    *   El botón de limpiar el formulario, limpia y filtra el formulario. Este evento se lanza antes de limpiar el formulario del filtro pero antes de filtrar con el formulario limpio.
    *
    * @event module:rup_table#rupTable_filter_beforeCleanFilterForm
    * @property {Event} e - Objeto Event correspondiente al evento disparado.
    * @example
    * $("#idComponente").on("rupTable_filter_beforeCleanFilterForm", function(event){ });
    *//**
    *   El botón de limpiar el formulario, limpia y filtra el formulario. Este evento se lanza después de limpiar el formulario del filtro pero antes de filtrar con el formulario limpio.
    *
    * @event module:rup_table#rupTable_filter_afterCleanFilterForm
    * @property {Event} e - Objeto Event correspondiente al evento disparado.
    * @example
    * $("#idComponente").on("rupTable_filter_afterCleanFilterForm", function(event,){ });
    */})(jQuery);/*!
 * Copyright 2013 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 *//*global jQuery *//**
 * Permite al usuario realizar una búsqueda entre el conjunto de resultados que se le muestran. Mediante una serie de criterios de búsqueda permite al usuario posicionarse entre los diferentes registros que se ajustan a dichos criterios.
 *
 * @summary Plugin de search del componente RUP Table.
 * @module rup_table/search
 * @example
 *
 * $("#idComponente").rup_table({
 * 	url: "../jqGridUsuario",
 * 	usePlugins:["search"],
 * 	search:{
 * 		// Propiedades de configuración del plugin search
 * 	}
 * });
 */(function($){/**
	 * Definición de los métodos principales que configuran la inicialización del plugin.
	 *
	 * preConfiguration: Método que se ejecuta antes de la invocación del componente jqGrid.
	 * postConfiguration: Método que se ejecuta después de la invocación del componente jqGrid.
	 *
	 */jQuery.rup_table.registerPlugin('search',{loadOrder:9,preConfiguration:function preConfiguration(settings){var $self=this;return $self.rup_table('preConfigureSearch',settings);},postConfiguration:function postConfiguration(settings){var $self=this;return $self.rup_table('postConfigureSearch',settings);}});//********************************
// DEFINICIÓN DE MÉTODOS PÚBLICOS
//********************************
/**
	 * Extensión del componente rup_table para permitir la gestión de la búsqueda de registros.
	 *
	 * Los métodos implementados son:
	 *
	 * preConfigureSearch(settings): Método que define la preconfiguración necesaria para el correcto funcionamiento del componente.
	 * postConfigureSearch(settings): Método que define la postconfiguración necesaria para el correcto funcionamiento del componente.
	 *
	 */jQuery.fn.rup_table('extend',{/**
		* Metodo que realiza la pre-configuración del plugin search del componente RUP Table.
		* Este método se ejecuta antes de la incialización del plugin.
		*
		* @name preConfigureSearch
		* @function
		* @param {object} settings - Parámetros de configuración del componente.
		*/preConfigureSearch:function preConfigureSearch(settings){// Añadimos la columna por defecto para mostrar la información de registros encontrados
//			settings.colNames = $.merge([""], settings.colNames);
//			settings.colModel = $.merge([settings.search.defaultSearchInfoCol], settings.colModel);
// Se configura la url de filtrado
if(settings.search.url===null){settings.search.url=settings.baseUrl+'/search';}},/**
		* Metodo que realiza la post-configuración del plugin search del componente RUP Table.
		* Este método se ejecuta antes de la incialización del plugin.
		*
		* @name postConfigureSearch
		* @function
		* @param {object} settings - Parámetros de configuración del componente.
		*/postConfigureSearch:function postConfigureSearch(settings){var $self=this;$self.rup_table('createSearchRow',settings);$self._initializeSearchProps(settings);$self.on({'jqGridLoadComplete.rupTable.search':function jqGridLoadCompleteRupTableSearch(data){var page=parseInt($self.rup_table('getGridParam','page'),10);if($self._hasPageMatchedElements(page)){$self.rup_table('highlightMatchedRowsInPage',page);//						// TODO: Generalizar
//						$self.find("td[aria-describedby='"+settings.id+"_infoSearch'] img.ui-icon.ui-icon-search").remove();
//						for (var i=0;i<settings.search.matchedRowsPerPage[page].length;i++){
//							newIndexPos = settings.search.matchedRowsPerPage[page][i];
//							$($self.jqGrid("getInd",newIndexPos, true)).find("td[aria-describedby='"+settings.id+"_infoSearch']").html($("<img/>").addClass("ui-icon ui-icon-search")[0]);
//						}
}$self.rup_table('updateSearchPagination');},'jqGridSelectRow.rupTable.search rupTable_setSelection.search':function jqGridSelectRowRupTableSearchRupTable_setSelectionSearch(event,id,status,obj){$self.rup_table('updateSearchPagination',id);},'jqGridGridComplete.rup_table.search':function jqGridGridCompleteRup_tableSearch(event){var $self=$(this),settings=$self.data('settings');if($self.rup_table('getGridParam','records')===0){settings.search.$searchRow.hide();}else{settings.search.$searchRow.show();}},'rupTable_searchAfterCreateToolbar':function rupTable_searchAfterCreateToolbar(event,$searchRow){var props=$self[0].p,colModel=props.colModel,cellColModel,$elem,editOptions,searchRupType,searchEditOptions;$('th[role=\'columnheader\']',$searchRow).each(function(i){cellColModel=colModel[i];searchRupType=cellColModel.searchoptions!==undefined&&cellColModel.searchoptions.rupType!==undefined?cellColModel.searchoptions.rupType:cellColModel.rupType;colModelName=cellColModel.name;$elem=$('[name=\''+colModelName+'\']',$searchRow);// Se añade el title de los elementos de acuerdo al colname
$elem.attr({'title':props.colNames[i],'class':'editable customelement'}).removeAttr('readOnly');// En caso de tratarse de un componente rup, se inicializa de acuerdo a la configuracón especificada en el colModel
if(searchRupType!==undefined){searchEditOptions=cellColModel.searchoptions||cellColModel.editoptions;/*
							 * PRE Configuración de los componentes RUP
							 */switch(searchRupType){case'combo':searchEditOptions=$.extend({},{menuWidth:$elem.width()},searchEditOptions,{width:'97%'});break;}// Invocación al componente RUP
$elem['rup_'+searchRupType](searchEditOptions);/*
							 * POST Configuración de los componentes RUP
							 */switch(searchRupType){case'date':// TODO: Aplicarlo con estilos
$elem.css('width','86%');break;}}});}});}});/**
	 * Métodos públicos del plugin search.
	 *
	 * Los métodos implementados son:
	 *
	 * toggleSearchForm(): Método que gestiona el mostrar/ocultar el formulario de búsqueda.
	 * createSearchRow(settings): Genera el formulario de búsqueda.
	 * navigateToMatchedRow(matchedRow): Se posiciona en el registro indicado que se corresponde con los criterios de búsqueda.
	 * doSearch(): Realiza la búsqueda de acuerdo a los criterios especificados.
	 * goToFirstMatched(paramPage): Navega hasta el primer resgistro que se corresponde con la búsqueda.
	 * fncGetSearchNavigationParams(buttonType): Devuelve los parámetros de navegación correspondientes al botón de navegación indicado.
	 * doSearchNavigation(arrParams, execute, changePage, index, npos, newPage, newPageIndex): Realiza la navegación entre los resultados de la búsqueda.
	 * clearSearch(): Realiza un borrado de los resultados de la búsqueda.
	 * clearHighlightedMatchedRows(): Elimina el resaltado de los registros
	 * highlightMatchedRowsInPage(page): Realiza el resaltado de los resultados de los registros para la página indicada.
	 * highlightMatchedRow($row): Resalta la línea indicada.
	 * updateSearchPagination(paramRowId): Actualiza los controles de paginación del formulario de búsqueda.
	 * getSearchCurrentRowCount(): Devuelve el resgistro actual en el que se encuentra el registro seleccionado respecto al conjunto de resultados.
	 *
	 */jQuery.fn.rup_table('extend',{/**
     *  Muestra/Oculta el formulario de búsqueda.
     *
     * @function toggleSearchForm
     * @example
     * $("#idTable").rup_table("toggleSearchForm");
     */toggleSearchForm:function toggleSearchForm(){var $self=this,settings=$self.data('settings'),prop=$self[0].p,trow,trow2;if(!settings.search.created){$self.rup_table('createSearchToolbar');settings.search.$collapseIcon.removeClass('ui-icon-triangle-1-e');settings.search.$collapseIcon.addClass('ui-icon-triangle-1-s');jQuery('#searchNavLayer_'+settings.id).show();settings.search.created=true;jQuery('input','table thead tr.ui-search-toolbar').keypress(function(e){var key=e.charCode||e.keyCode||0;if(key==13){$self.rup_table('search');return false;}return this;});}else{trow=jQuery('tr.ui-search-toolbar',$self[0].grid.hDiv);trow2=prop.frozenColumns===true?jQuery('tr.ui-search-toolbar',$self[0].grid.fhDiv):false;if(jQuery('tr.ui-search-toolbar','#gview_'+settings.id).is(':visible')){trow.hide(settings.search.transitionConfig);if(trow2){trow2.hide(settings.search.transitionConfig);}jQuery('#searchNavLayer_'+settings.id).hide(settings.search.transitionConfig);settings.search.$collapseIcon.removeClass('ui-icon-triangle-1-s');settings.search.$collapseIcon.addClass('ui-icon-triangle-1-e');}else{trow.show(settings.search.transitionConfig);if(trow2){trow2.show(settings.search.transitionConfig);}jQuery('#searchNavLayer_'+settings.id).show(settings.search.transitionConfig);settings.search.$collapseIcon.removeClass('ui-icon-triangle-1-e');settings.search.$collapseIcon.addClass('ui-icon-triangle-1-s');}}},/**
     * Genera la barra de controles para gestionar la búsqueda.
     *
     * @function createSearchToolbar
		 * @fires module:rup_table#rupTable_searchAfterCreateToolbar
     * @example
     * $("#idTable").rup_table("createSearchToolbar");
     */createSearchToolbar:function createSearchToolbar(){var $self=this,settings=$self.data('settings'),prop=$self[0].p,$searchRow=jQuery('<tr>').attr({'class':'ui-search-toolbar','role':'rowheader'});if(jQuery('table thead tr:first th[id=\''+settings.id+'_cb\']',$self[0].grid.hDiv).length!==0){$searchRow.append(jQuery('<th>').attr({'role':'columnheader','class':'search_row_header ui-th-column ui-th-'+prop.direction}));}$searchRow.append(jQuery('<th>').attr({'role':'columnheader','class':'search_row_header ui-th-column ui-th-'+prop.direction}));$.each(prop.colModel,function(index,colM){var $searchHeader=jQuery('<th>').attr({'role':'columnheader','class':'search_row_header ui-th-column ui-th-'+prop.direction}),elc,$elc;if(colM.hidden===true){$searchHeader.css('display','none');}colM.search=colM.search===false?false:true;if(colM.stype===undefined){colM.stype=colM.edittype!==undefined?colM.edittype:'text';if(colM.searchoptions!==undefined&&colM.searchoptions.rupType==='combo'){colM.stype='text';}}soptions=$.extend({},colM.searchoptions||colM.editoptions||{},{id:colM.name,name:colM.name});if(colM.search){elc=$.jgrid.createEl.call($self[0],colM.stype!==undefined?colM.stype:colM.edittype,soptions,'',true,$.extend({},$.jgrid.ajaxOptions,soptions.ajaxSelectOptions||{}));$elc=jQuery(elc);$elc.css('width','97%');//					$searchCol.append($elc);
$searchHeader.append($elc);}if(colM.name!==settings.defaultGridInfoCol.name&&colM.name!==settings.defaultGridMultiplePkCol.name&&colM.name!=='cb'){$searchRow.append($searchHeader);}});$('table thead',$self[0].grid.hDiv).append($searchRow);settings.search.$searchRowInputs=jQuery('table thead tr.ui-search-toolbar','#gview_'+settings.id);settings.search.$searchRowInputs.attr({'id':settings.id+'_search_rowInputs','form':settings.id+'_search_rowInputs'});// Configuración de validaciones
if(settings.search.validate!==undefined){settings.search.$searchForm.rup_validate(settings.search.validate);$self.on({'rupTable_beforeSearch.search.validate':function rupTable_beforeSearchSearchValidate(){return settings.search.$searchForm.valid();}});}$self.triggerHandler('rupTable_searchAfterCreateToolbar',[$searchRow]);$self[0].ftoolbar=true;},/**
     * Genera la barra de controles para gestionar la búsqueda.
     *
     * @function createSearchRow
		 * @param {object} settings - Genera la línea de busqueda de acuerdo a las propiedades de configuración especificadas.
     * @example
     * $("#idTable").rup_table("createSearchRow", settings);
     */createSearchRow:function createSearchRow(settings){var $self=this,$gridHead=jQuery('table thead','#gview_'+settings.id),searchForm,// Templates
searchRowHeaderTmpl=jQuery.rup.i18nParse(jQuery.rup.i18n.base,'rup_table.templates.search.searchRowHeader'),collapseLayerTmpl=jQuery.rup.i18nParse(jQuery.rup.i18n.base,'rup_table.templates.search.collapseLayer'),collapseIconTmpl=jQuery.rup.i18nParse(jQuery.rup.i18n.base,'rup_table.templates.search.collapseIcon'),collapseLabelTmpl=jQuery.rup.i18nParse(jQuery.rup.i18n.base,'rup_table.templates.search.collapseLabel'),matchedLayerTmpl=jQuery.rup.i18nParse(jQuery.rup.i18n.base,'rup_table.templates.search.matchedLayer'),matchedLabelTmpl=jQuery.rup.i18nParse(jQuery.rup.i18n.base,'rup_table.templates.search.matchedLabel'),navLayerTmpl=jQuery.rup.i18nParse(jQuery.rup.i18n.base,'rup_table.templates.search.navLayer'),navButtonTmpl=jQuery.rup.i18nParse(jQuery.rup.i18n.base,'rup_table.templates.search.navButton'),navSearchButtonTmpl=jQuery.rup.i18nParse(jQuery.rup.i18n.base,'rup_table.templates.search.navSearchButton'),navClearButtonTmpl=jQuery.rup.i18nParse(jQuery.rup.i18n.base,'rup_table.templates.search.navClearButton'),// Objetos
$searchRow=$(jQuery.rup.i18nParse(jQuery.rup.i18n.base,'rup_table.templates.search.searchRow')),$searchRowHeader=$(jQuery.jgrid.format(searchRowHeaderTmpl,$gridHead.find('th').length-$gridHead.find('th:hidden').length)),// Capa que controla el colapso del formualario
$collapseLayer=$(jQuery.jgrid.format(collapseLayerTmpl,'searchCollapseLayer_'+settings.id)),$collapseIcon=$(jQuery.jgrid.format(collapseIconTmpl,'searchCollapseIcon_'+settings.id)),$collapseLabel=$(jQuery.jgrid.format(collapseLabelTmpl,'searchCollapsLabel_'+settings.id,jQuery.rup.i18nParse(jQuery.rup.i18n.base,'rup_table.plugins.search.searchCriteria'))),// Capa que muestra el número de ocurrencias
$matchedLayer=$(jQuery.jgrid.format(matchedLayerTmpl,'matchedLayer_'+settings.id)),$matchedLabel=$(jQuery.jgrid.format(matchedLabelTmpl,'matchedLabel_'+settings.id,jQuery.jgrid.format(jQuery.rup.i18nParse(jQuery.rup.i18n.base,'rup_table.plugins.search.matchedRecords'),0))),// Capa que controla la navegación entre las diferentes ocurrencias
$navLayer=$(jQuery.jgrid.format(navLayerTmpl,'searchNavLayer_'+settings.id)),$firstNavButton=$(jQuery.jgrid.format(navButtonTmpl,'search_nav_first_'+settings.id,jQuery.rup.i18nParse(jQuery.rup.i18n.base,'rup_table.first'))),$backNavButton=$(jQuery.jgrid.format(navButtonTmpl,'search_nav_back_'+settings.id,jQuery.rup.i18nParse(jQuery.rup.i18n.base,'rup_table.previous'))),$forwardNavButton=$(jQuery.jgrid.format(navButtonTmpl,'search_nav_forward_'+settings.id,jQuery.rup.i18nParse(jQuery.rup.i18n.base,'rup_table.next'))),$lastNavButton=$(jQuery.jgrid.format(navButtonTmpl,'search_nav_last_'+settings.id,jQuery.rup.i18nParse(jQuery.rup.i18n.base,'rup_table.last'))),$navSearchButton=$(jQuery.jgrid.format(navSearchButtonTmpl,'search_nav_button_'+settings.id,jQuery.rup.i18nParse(jQuery.rup.i18n.base,'rup_table.search.Find'))),$navClearButton=$(jQuery.jgrid.format(navClearButtonTmpl,'search_nav_clear_button'+settings.id,jQuery.rup.i18nParse(jQuery.rup.i18n.base,'rup_table.search.Reset')));// Construcción del objeto final
$collapseLayer.append($collapseIcon).append($collapseLabel);$matchedLayer.append($matchedLabel);$navLayer.append($firstNavButton).append($backNavButton).append($forwardNavButton).append($lastNavButton).append($navSearchButton).append($navClearButton);$searchRowHeader.append($collapseLayer);$searchRowHeader.append($matchedLayer);$searchRowHeader.append($navLayer);$searchRow.append($searchRowHeader);$gridHead.append($searchRow);settings.search=settings.search||{};settings.search.created=false;//			settings.search.url = settings.search.url || settings.url+"../search";
settings.search.$collapseIcon=$collapseIcon;settings.search.$searchRow=$searchRow;settings.search.$matchedLabel=$matchedLabel;settings.search.$firstNavButton=$firstNavButton;settings.search.$backNavButton=$backNavButton;settings.search.$forwardNavButton=$forwardNavButton;settings.search.$lastNavButton=$lastNavButton;// Creacion del enlace de mostrar/ocultar el formulario
$collapseIcon.add($collapseLabel).on('click',function(){$self.rup_table('toggleSearchForm');});// Evento de búsqueda asociado al botón
$navSearchButton.on('click',function(){$self.rup_table('search');});// Evento asociado a limpiar el fomulario de búsqueda
$navClearButton.on('click',function(){$self.rup_table('clearSearch');});$navLayer.hide();function doSearchButtonNavigation($button,buttonId){if(!$button.hasClass('ui-state-disabled')){$self.rup_table('navigateToMatchedRow',buttonId);}}// Elemento primero
$firstNavButton.on('click',function(){doSearchButtonNavigation(jQuery(this),'first');});// Elemento anterior
$backNavButton.on('click',function(){doSearchButtonNavigation(jQuery(this),'prev');});// Elemento siguiente
$forwardNavButton.on('click',function(){doSearchButtonNavigation(jQuery(this),'next');});// Elemento ultimo
$lastNavButton.on('click',function(){doSearchButtonNavigation(jQuery(this),'last');});// Se recubre con un form
var $searchForm=jQuery('<form>').attr('id',settings.id+'_search_searchForm');settings.search.$searchRow.parent().parent().wrap($searchForm);settings.search.$searchForm=jQuery('#'+settings.id+'_search_searchForm');settings.search.$searchRow.hide();},/**
     *  Navega hasta el elemento indicado que se ajusta a los criterios de búsqueda indicados.
     *
     * @function navigateToMatchedRow
		 * @param {string} matchedRow - Identificador de la línea a la cual se quiere navegar.
     * @example
     * $("#idTable").rup_table("navigateToMatchedRow", matchedRow);
     */navigateToMatchedRow:function navigateToMatchedRow(matchedRow){var $self=this,retNavParams=$self.rup_table('fncGetSearchNavigationParams',matchedRow);$self.rup_table('doSearchNavigation',retNavParams);},/**
     * Lanza la operación de búsqueda además del evento previo.
     *
     * @function search
		 * @fires module:rup_table#rupTable_beforeSearch
     * @example
     * $("#idTable").rup_table("search");
     */search:function search(){var $self=this,settings=$self.data('settings');var bfr=$self.triggerHandler('rupTable_beforeSearch');if(bfr===false||bfr==='stop'){return;}if($.isFunction(settings.search.beforeSearch)){bfr=settings.search.beforeSearch.call($self);if(bfr===undefined){bfr=true;}if(bfr===false){return;}}$self.rup_table('doSearch');},/**
     *  Lanza la operación de búsqueda.
     *
     * @function navigateToMatchedRow
		 * @fires module:rup_table#rupTable_searchBeforeSubmit.rupTable.masterDetail
     * @example
     * $("#idTable").rup_table("doSearch");
     */doSearch:function doSearch(){var $self=this,settings=$self.data('settings'),ret,jsonData={},page=parseInt($self.rup_table('getGridParam','page'),10),postData=$self.rup_table('getGridParam','postData');//			jsonData.filterParams =$self.rup_table("getGridParam","postData"),
jsonData.filter=$self.rup_table('getFilterParams');jsonData.search=form2object(settings.search.$searchRowInputs[0]);$self._initializeSearchProps(settings);ret=$self.triggerHandler('rupTable_searchBeforeSubmit.rupTable.masterDetail',[postData,jsonData]);if(ret===false){return false;}jQuery.rup_ajax({url:settings.search.url,type:'POST',dataType:'json',data:jQuery.toJSON($.extend(true,{},postData,jsonData)),contentType:'application/json',success:function success(xhr,b,c){rowsPerPage=parseInt($self.rup_table('getGridParam','rowNum'),10);if(xhr.length===0){$self._initializeSearchProps(settings);$self.rup_table('updateSearchPagination');$self.rup_table('clearHighlightedMatchedRows');}else{jQuery.each(xhr,function(index,elem){//							if (settings.primaryKey.length>1){
var retValue='';for(var i=0;i<settings.primaryKey.length;i++){retValue+=elem.pk[settings.primaryKey[i]]+settings.multiplePkToken;}elem['id']=retValue.substr(0,retValue.length-1);//							}
elem.page=Math.ceil(elem.tableLine/rowsPerPage);elem.pageLine=elem.tableLine-(elem.page-1)*rowsPerPage;$self._processMatchedRow(settings,elem);});$self.trigger('rupTableSearchSuccess');$self.rup_table('goToFirstMatched',page);}}});},/**
     * Navega hasta el primer elemento que se ajusta a los criterios de búsqueda. En caso de no existir elementos adecuados en la página actual se navega hasta el primer elemento.
     *
     * @function goToFirstMatched
		 * @param {paramPage} paramPage - En caso de indicarse una página se utilizará en vez de la página actual.
     * @example
     * $("#idTable").rup_table("goToFirstMatched", paramPage);
     */goToFirstMatched:function goToFirstMatched(paramPage){var $self=this,settings=$self.data('settings'),page=typeof paramPage==='string'?parseInt(paramPage,10):paramPage;if($self._hasPageMatchedElements(page)){// TODO: Generalizar
//				$self.find("td[aria-describedby='"+settings.id+"_infoSearch'] img.ui-icon.ui-icon-search").remove();
//				for (var i=0;i<settings.search.matchedRowsPerPage[page].length;i++){
//					newIndexPos = settings.search.matchedRowsPerPage[page][i];
//					$($self.jqGrid("getInd",newIndexPos, true)).find("td[aria-describedby='"+settings.id+"_infoSearch']").html($("<img/>").addClass("ui-icon ui-icon-search")[0]);
//				}
$self.rup_table('setSelection',settings.search.matchedRowsPerPage[page][0],true);$self.rup_table('highlightMatchedRowsInPage',page);}else{$self.rup_table('navigateToMatchedRow','first');}},/**
     * Devuelve los parámetros correspondientes al tipo de enlace de navegación indicado por parámetro.
     *
     * @function fncGetSearchNavigationParams
		 * @param {paramPage} buttonType - Tipo de parámetro first, prev, next o last.-
		 * @return {object} - Parametros de configuración asociados al tipo de enlace.
     * @example
     * $("#idTable").rup_table("fncGetSearchNavigationParams", buttonType);
     */fncGetSearchNavigationParams:function fncGetSearchNavigationParams(buttonType){var $self=this,settings=$self.data('settings'),execute=false,changePage=false,index=0,newPageIndex=0,npos=jQuery.proxy(jQuery.jgrid.getCurrPos,$self[0])(),page=parseInt($self.rup_table('getGridParam','page'),10),newPage=page,activeLineId,//			lastPage = parseInt(Math.ceil($self.rup_table("getGridParam", "records")/$self.rup_table("getGridParam", "rowNum")),10),
currentArrayIndex,selectedLines,pageArrayIndex;$self.trigger('rupTableAfterSearchNav',[buttonType]);npos[0]=parseInt(npos[0],10);activeLineId=$self.rup_table('getActiveLineId');$('#'+settings.formEdit.feedbackId,settings.$detailForm).hide();switch(buttonType){case'first':// Navegar al primer elemento
execute=true;// Si no se han seleccionado todos los elementos
// Se comprueba si la página en la que nos encontramos es la primera en la que se han seleccionado registros
if(settings.search.matchedPages[0]!==page){// Marcamos el flag changePage para indicar que se debe de realizar una paginación
changePage=true;// La nueva página será la primera página en la que se ha realizado una selección de registros
newPage=settings.search.matchedPages[0];}// Recuperamos el primer registro seleccionado del la página
index=settings.search.matchedLinesPerPage[newPage][0];newPageIndex=index;break;case'prev':// Navegar al anterior elemento seleccionado
execute=true;// Obtenemos un array con los index de los registros seleccionados en la página actual
selectedLines=settings.search.matchedLinesPerPage[page]||[];// Obtenemos la posición que ocupa el elemento actual en el array de seleccionados
currentArrayIndex=$.inArray(activeLineId+1,selectedLines);// La línea no se encuentra entre los registros que se corresponden a la búsqueda
if(currentArrayIndex===-1){currentArrayIndex=$.rup_utils.insertSorted($.merge([],selectedLines),activeLineId+1);//						if(currentArrayIndex>1){
//							currentArrayIndex--;
//						}
}// Se comprueba si ocupa el lugar del primer elemento seleccionado
if(currentArrayIndex===0){// En caso de tratarse del primer elemento seleccionado de la página, se deberá de realizar una navegación a la página anterior que disponga de elementos seleccionados
changePage=true;pageArrayIndex=$.inArray(page,settings.search.matchedPages);// En caso de no estar posicionados en una página en la que se encuentran ocurrencias de registros
if(pageArrayIndex===-1){// Se obtiene la posición en la que se encontraría la página
pageArrayIndex=$.rup_utils.insertSorted($.merge([],settings.search.matchedPages),page);}// Recorremos las páginas anteriores
newPage=settings.search.matchedPages[pageArrayIndex-1];// Obtenemos los identificadores de los registros seleccionados de la nueva página
selectedLines=settings.search.matchedLinesPerPage[newPage];// Obtenemos el último registro seleccionado
index=selectedLines[selectedLines.length-1];}else{// En caso de no tratarse del último elemento de la página, recuperamos el elemento anterior que haya sido seleccionado también
index=selectedLines[currentArrayIndex-1];}newPageIndex=index;break;case'next':// Navegar al siguiente elemento seleccionado
execute=true;// Obtenemos un array con los index de los registros seleccionados en la página actual
selectedLines=settings.search.matchedLinesPerPage[page]||[];// Obtenemos la posición que ocupa el elemento actual en el array de seleccionados
currentArrayIndex=$.inArray(activeLineId+1,selectedLines);// La línea no se encuentra entre los registros que se corresponden a la búsqueda
if(currentArrayIndex===-1){currentArrayIndex=$.rup_utils.insertSorted($.merge([],selectedLines),activeLineId+1);currentArrayIndex--;}// Se comprueba si ocupa el lugar del último elemento seleccionado
if(currentArrayIndex===selectedLines.length-1){// En caso de tratarse del primer elemento seleccionado de la página, se deberá de realizar una navegación a la página anterior que disponga de elementos seleccionados
changePage=true;pageArrayIndex=$.inArray(page,settings.search.matchedPages);// En caso de no estar posicionados en una página en la que se encuentran ocurrencias de registros
if(pageArrayIndex===-1){// Se obtiene la posición en la que se encontraría la página
pageArrayIndex=$.rup_utils.insertSorted($.merge([],settings.search.matchedPages),page)-1;}// Recorremos las páginas anteriores
newPage=settings.search.matchedPages[pageArrayIndex+1];// Obtenemos los identificadores de los registros seleccionados de la nueva página
selectedLines=settings.search.matchedLinesPerPage[newPage];// Obtenemos el primer registro de la página
index=selectedLines[0];}else{// En caso de no tratarse del último elemento de la página, recuperamos el elemento anterior que haya sido seleccionado también
index=selectedLines[currentArrayIndex+1];}newPageIndex=index;break;case'last':// Navegar al primer elemento
execute=true;// Si no se han seleccionado todos los elementos
// Se comprueba si la página en la que nos encontramos es la primera en la que se han seleccionado registros
if(settings.search.matchedPages[settings.search.matchedPages.length-1]!==page){// Marcamos el flag changePage para indicar que se debe de realizar una paginación
changePage=true;// La nueva página será la primera página en la que se ha realizado una selección de registros
newPage=settings.search.matchedPages[settings.search.matchedPages.length-1];}// Recuperamos el primer registro seleccionado del la página
index=settings.search.matchedLinesPerPage[newPage][settings.search.matchedLinesPerPage[newPage].length-1];newPageIndex=index;break;}return[buttonType,execute,changePage,index-1,npos,newPage,newPageIndex-1];},/**
     * Realiza la navegación entre los elementos que se ajustan a los criterios de bús
     *
     * @function fncGetSearchNavigationParams
		 * @param {object[]} arrParams - Array de parámetros que determinan la navegación.
     * @example
     * $("#idTable").rup_table("doSearchNavigation", arrParams);
     */doSearchNavigation:function doSearchNavigation(arrParams){var $self=this,settings=$self.data('settings'),execute,changePage,index,newPage,newPageIndex,indexAux,ret,actualRowId,rowId;if($.isArray(arrParams)){buttonType=arrParams[0];execute=arrParams[1];changePage=arrParams[2];index=arrParams[3];npos=arrParams[4];newPage=arrParams[5];newPageIndex=arrParams[6];if(execute){$self.rup_table('hideFormErrors',settings.formEdit.$detailForm);//					$self.triggerHandler("jqGridAddEditClickPgButtons", [buttonType, settings.$detailForm, npos[1][npos[index]]]);
pagePos=jQuery.proxy(jQuery.jgrid.getCurrPos,$self[0])();//					actualRowId = npos[1][npos[0]];
actualRowId=$self.rup_table('getActiveRowId');//					ret = $self.triggerHandler("rupTable_searchNavigation_deselect", actualRowId);
//					if (ret!==false){
$row=jQuery($self.jqGrid('getInd',actualRowId,true));if($row.data('tmp.search.notToDeselect')!=='true'){$self.rup_table('setSelection',actualRowId,false);if($row.data('tmp.search.notToDeselect')!==undefined){delete $row.data('tmp.search.notToDeselect');}}if(changePage){//						$self.jqGrid("setSelection", pagePos[1][pagePos[0]], false);
$self.trigger('reloadGrid',[{page:newPage}]);$self.on('jqGridAfterLoadComplete.rupTable.serach.pagination',function(event,data){indexAux=jQuery.inArray(newPageIndex+1,settings.search.matchedLinesPerPage[newPage]);rowId=settings.search.matchedRowsPerPage[parseInt(data.page,10)][indexAux];$row=jQuery($self.jqGrid('getInd',rowId,true));if($row.attr('aria-selected')==='true'){$row.data('tmp.search.notToDeselect','true');}$self.rup_table('setSelection',rowId,true);$self.off('jqGridAfterLoadComplete.rupTable.serach.pagination');});}else{indexAux=jQuery.inArray(index+1,settings.search.matchedLinesPerPage[newPage]);rowId=settings.search.matchedRowsPerPage[newPage][indexAux];$row=jQuery($self.jqGrid('getInd',rowId,true));if($row.attr('aria-selected')==='true'){$row.data('tmp.search.notToDeselect','true');}$self.rup_table('setSelection',rowId,true);}}}},/**
     * Limpia los criterios de búsqueda introducidos por el usuario.
     *
     * @function clearSearch
     * @example
     * $("#idTable").rup_table("clearSearch");
     */clearSearch:function clearSearch(){var $self=this,settings=$self.data('settings');$self._initializeSearchProps(settings);$self.rup_table('updateSearchPagination');$self.rup_table('clearHighlightedMatchedRows');jQuery('input,textarea','#gview_'+settings.id+' table thead tr.ui-search-toolbar').val('');jQuery('table thead tr.ui-search-toolbar [ruptype=\'combo\']','#gview_'+settings.id).rup_combo('clear');},/**
     * Elimina el resaltado de los registros que se ajustan a los criterios de busqueda.
     *
     * @function clearHighlightedMatchedRows
     * @example
     * $("#idTable").rup_table("clearHighlightedMatchedRows");
     */clearHighlightedMatchedRows:function clearHighlightedMatchedRows(){var $self=this,settings=$self.data('settings');$self.find('td[aria-describedby=\''+settings.id+'_rupInfoCol\'] span.ui-icon.ui-icon-search').removeClass('ui-icon-search');},/**
     * Resalta los registros que se ajustan a los criterios de búsqueda.
     *
     * @function highlightMatchedRowsInPage
		 * @param {string} page - Identificador de la página en la que se desean resaltar los registos.
     * @example
     * $("#idTable").rup_table("highlightMatchedRowsInPage", page);
     */highlightMatchedRowsInPage:function highlightMatchedRowsInPage(page){var $self=this,settings=$self.data('settings'),internalProps=$self[0].p,$row;$self.rup_table('clearHighlightedMatchedRows');for(var i=0;i<settings.search.matchedRowsPerPage[page].length;i++){newIndexPos=settings.search.matchedRowsPerPage[page][i];$row=$($self.jqGrid('getInd',newIndexPos,true));$self.rup_table('highlightMatchedRow',$row);//				if (i==0){
//					internalProps.selarrrow.push($row[0].id);
//					internalProps.selrow = $row[0].id;
//				}
}},/**
     * Resalta como ocurrencia de la búsqueda la línea especificada.
     *
     * @function highlightMatchedRow
		 * @param {string} $row - Objeto jQuery que referencia la línea de la tabla que se quiere resaltar.
     * @example
     * $("#idTable").rup_table("highlightMatchedRow", $("#idRow"));
     */highlightMatchedRow:function highlightMatchedRow($row){var $self=this,settings=$self.data('settings');$row.find('td[aria-describedby=\''+settings.id+'_rupInfoCol\'] span').addClass('ui-icon ui-icon-rupInfoCol ui-icon-search');},/**
     * Actualiza los valores de la navegación entre registros.
     *
     * @function updateSearchPagination
		 * @param {string} paramRowId - Identificador de la página.
     * @example
     * $("#idTable").rup_table("updateSearchPagination", paramRowId);
     */updateSearchPagination:function updateSearchPagination(paramRowId){var $self=this,settings=$self.data('settings'),rowId,pagePos,currentArrayIndex,page=parseInt($self.rup_table('getGridParam','page'),10),numMatched,formatter=$.jgrid.formatter.integer;if(paramRowId!==undefined){rowId=paramRowId;}else{pagePos=jQuery.proxy(jQuery.jgrid.getCurrPos,$self[0])();rowId=pagePos[0]!==-1?pagePos[1][pagePos[0]-1]:-1;}if(settings.search.numMatched===0){settings.search.$firstNavButton.add(settings.search.$backNavButton).add(settings.search.$forwardNavButton).add(settings.search.$lastNavButton).addClass('ui-state-disabled');settings.search.$matchedLabel.html(jQuery.jgrid.format(jQuery.rup.i18nParse(jQuery.rup.i18n.base,'rup_table.plugins.search.matchedRecords'),'0'));}else if(rowId!==-1){// Comprobamos si el registro seleccionado es uno de los resultados de la busqueda
if(jQuery.inArray(rowId,settings.search.matchedRowsPerPage[page])!==-1){// Calculamos el
numMatched=$self.rup_table('getSearchCurrentRowCount',rowId);if(settings.search&&settings.search.numMatched){settings.search.$matchedLabel.html(jQuery.jgrid.format(jQuery.rup.i18nParse(jQuery.rup.i18n.base,'rup_table.plugins.search.matchedRecordsCount'),$.fmatter.util.NumberFormat(numMatched,formatter),$.fmatter.util.NumberFormat(settings.search.numMatched,formatter)));}if(numMatched===1){settings.search.$firstNavButton.addClass('ui-state-disabled');settings.search.$backNavButton.addClass('ui-state-disabled');}else{settings.search.$firstNavButton.removeClass('ui-state-disabled');settings.search.$backNavButton.removeClass('ui-state-disabled');}if(numMatched===settings.search.numMatched){settings.search.$lastNavButton.addClass('ui-state-disabled');settings.search.$forwardNavButton.addClass('ui-state-disabled');}else{settings.search.$lastNavButton.removeClass('ui-state-disabled');settings.search.$forwardNavButton.removeClass('ui-state-disabled');}}else{if(settings.search&&settings.search.numMatched){settings.search.$matchedLabel.html(jQuery.jgrid.format(jQuery.rup.i18nParse(jQuery.rup.i18n.base,'rup_table.plugins.search.matchedRecords'),$.fmatter.util.NumberFormat(settings.search.numMatched,formatter)));}settings.search.$firstNavButton.removeClass('ui-state-disabled');settings.search.$backNavButton.removeClass('ui-state-disabled');settings.search.$forwardNavButton.removeClass('ui-state-disabled');settings.search.$lastNavButton.removeClass('ui-state-disabled');// Miramos a ver si desde la posición actual hay anterior
if(jQuery.inArray(settings.search.matchedPages,page)>0){settings.search.$backNavButton.removeClass('ui-state-disabled');}else if(jQuery.inArray(page,settings.search.matchedPages)===-1&&$.rup_utils.insertSorted($.merge([],settings.search.matchedPages),page)===0){// Anterior a las páginas en las que se han encontrado ocurrencias
settings.search.$backNavButton.addClass('ui-state-disabled');settings.search.$firstNavButton.addClass('ui-state-disabled');}else if(jQuery.inArray(page,settings.search.matchedPages)===-1&&$.rup_utils.insertSorted($.merge([],settings.search.matchedPages),page)>=settings.search.matchedPages.length){// Posterior a las páginas en las que se han encontrado ocurrencias
settings.search.$forwardNavButton.addClass('ui-state-disabled');settings.search.$lastNavButton.addClass('ui-state-disabled');}else{pagePos=$self.rup_table('getActiveLineId');if(settings.search.matchedLinesPerPage[page]!==undefined){currentArrayIndex=$.rup_utils.insertSorted($.merge([],settings.search.matchedLinesPerPage[page]),pagePos+1);}if(currentArrayIndex===0){settings.search.$backNavButton.addClass('ui-state-disabled');}if(settings.search.matchedLinesPerPage[page]!==undefined&&currentArrayIndex===settings.search.matchedLinesPerPage[page].length){settings.search.$forwardNavButton.addClass('ui-state-disabled');}}}}},/**
     *  Devuelve, para una linea determinada, la posición en que se encuentra dentro del total de registros que se ajustan a los criterios de búsqueda
     *
     * @function getSearchCurrentRowCount
		 * @param {string} selectedRowId - Identificador del registro.
     * @example
     * $("#idTable").rup_table("getSearchCurrentRowCount", "05");
     */getSearchCurrentRowCount:function getSearchCurrentRowCount(selectedRowId){var $self=this,settings=$self.data('settings'),page=parseInt($self.rup_table('getGridParam','page'),10),currentPos=jQuery.proxy(jQuery.jgrid.getCurrPos,$self[0])(),selectedRows=$self.rup_table('getSelectedRows'),//			rowsPerPage = parseInt($self.rup_table("getGridParam", "rowNum"),10),
selectedPagesArrayIndex,currentRow=jQuery.inArray(selectedRowId!==undefined?selectedRowId:selectedRows[0],currentPos[1]),cont=0;// En caso de que no se hayan seleccionado
// Se obtiene el indice de la página actual dentro del array de páginas deseleccionadas para
selectedPagesArrayIndex=jQuery.inArray(page,settings.search.matchedPages);for(var i=0;i<selectedPagesArrayIndex;i++){cont+=settings.search.matchedLinesPerPage[settings.search.matchedPages[i]].length;}cont+=$.inArray(currentRow+1,settings.search.matchedLinesPerPage[settings.search.matchedPages[selectedPagesArrayIndex]])+1;return cont;}});/**
	 * Métodos públicos del plugin search.
	 *
	 * Los métodos implementados son:
	 *
	 * _hasPageMatchedElements(paramPage): Devuelve true/false dependiendo si la página tiene registros que coinciden con los criterios de búsqueda o no.
	 * _initializeSearchProps(settings): Se realiza la inicialización de los componentes del plugin search.
	 * _processMatchedRow(settings, matchedElem): Se gestiona el registro indicado.
	 */jQuery.fn.rup_table('extend',{/**
     * Devuelve true/false dependiendo si la página tiene registros que coinciden con los criterios de búsqueda o no.
     *
     * @function _hasPageMatchedElements
		 * @private
		 * @param {string} paramPage - Identificador del registro.
		 * @return {boolean} - true/false dependiendo si la página tiene registros que coinciden con los criterios de búsqueda o no.
     * @example
     * $self._hasPageMatchedElements("1");
     */_hasPageMatchedElements:function _hasPageMatchedElements(paramPage){var $self=this,settings=$self.data('settings'),page=typeof paramPage==='string'?parseInt(paramPage,10):paramPage;// Se comprueba si se han seleccionado todos los registros de la tabla
// Comprobamos si en la página indicada se ha encontrado un elemento
return jQuery.inArray(page,settings.search.matchedPages)!==-1;},/**
     * Se realiza la inicialización de los componentes del plugin search.
     *
     * @function _initializeSearchProps
		 * @private
		 * @param {object} settings - Parámetros de configuración de la página.
		 * @return {boolean} - true/false dependiendo si la página tiene registros que coinciden con los criterios de búsqueda o no.
     * @example
     * $self._initializeSearchProps(settings);
     */_initializeSearchProps:function _initializeSearchProps(settings){// Se almacenan en los settings internos las estructuras de control de los registros seleccionados
if(settings.search===undefined){settings.search={};}// Numero de registros encontrados
settings.search.numMatched=0;// Propiedades
settings.search.matchedRowsPerPage=[];settings.search.matchedLinesPerPage=[];settings.search.matchedRows=[];settings.search.matchedIds=[];settings.search.matchedPages=[];},/**
     * Se gestiona el registro indicado.
     *
     * @function _processMatchedRow
		 * @private
		 * @param {object} settings - Parámetros de configuración de la página.
		 * @param {object} - Referencia al elemento.
     * @example
     * $self._processMatchedRow(settings, matchedElem);
     */_processMatchedRow:function _processMatchedRow(settings,matchedElem){var lineIndex;if(settings.search.matchedRowsPerPage[matchedElem.page]===undefined){settings.search.matchedRowsPerPage[matchedElem.page]=[];settings.search.matchedLinesPerPage[matchedElem.page]=[];}// Se almacena el Id del registro seleccionado
if(jQuery.inArray(matchedElem.id,settings.search.matchedIds)===-1){settings.search.matchedIds.push(matchedElem.id);settings.search.matchedRows.push({id:matchedElem.id,page:matchedElem.page});lineIndex=$.rup_utils.insertSorted(settings.search.matchedLinesPerPage[matchedElem.page],matchedElem.pageLine);settings.search.matchedRowsPerPage[matchedElem.page].splice(lineIndex,0,matchedElem.id);if(settings.search.matchedRowsPerPage[matchedElem.page].length>0&&jQuery.inArray(parseInt(matchedElem.page,10),settings.search.matchedPages)===-1){$.rup_utils.insertSorted(settings.search.matchedPages,parseInt(matchedElem.page,10));}settings.search.numMatched++;}}});//*******************************************************
// DEFINICIÓN DE LA CONFIGURACION POR DEFECTO DEL PATRON
//*******************************************************
/**
 	* @description Propiedades de configuración del plugin search del componente RUP Table.
 	*
 	* @name options
 	*
 	* @property {string} [url=null] - Url que se va a utilizar para realizar las peticiones de filtrado de la tabla. En caso de no especificarse una concreta, se utilizará por defecto una construida a partir de la url base. (urlBase + /search).
	* @property {object} [validate] - Mediante esta propiedad es posible especificar reglas de validación que se especifican en la guía de uso del componente RUP validation.
 	*/jQuery.fn.rup_table.plugins.search={};jQuery.fn.rup_table.plugins.search.defaults={showGridInfoCol:true,search:{url:null,autosearch:false,beforeSearch:function beforeSearch(){return true;},defaultSearchInfoCol:{name:'infoSearch',index:'infoSearch',editable:false,width:'15em',search:false},searchOnEnter:false,transitionConfig:{duration:0}}};/* ********* *//* EVENTOS
  /* ********* *//**
   *  Se lanza al finalizar la creación de la linea de búsqueda de la tabla.
   *
   * @event module:rup_table#rupTable_searchAfterCreateToolbar
   * @property {Event} event - Objeto Event correspondiente al evento disparado.
	 * @property {Event} $searchRow - Linea de la tabla destinada a la búsqueda.
   * @example
   * $("#idComponente").on("rupTable_searchAfterCreateToolbar", function(event, $searchRow){ });
   *//**
    * Evento lanzado antes de realizarse la búsqueda.
    *
    * @event module:rup_table#rupTable_beforeSearch
    * @property {Event} event - Objeto Event correspondiente al evento disparado.
    * @example
    * $("#idComponente").on("rupTable_beforeSearch", function(event){ });
    *//**
    * Evento lanzado antes de realizarse la petición de búsqueda al servidor
    *
    * @event module:rup_table#rupTable_searchBeforeSubmit.rupTable.masterDetail
    * @property {Event} event - Objeto Event correspondiente al evento disparado.
		* @property {object} postData - Objeto data que va a ser enviado en la petición.
		* @property {object} jsonData - Objeto json con los parámetros de búsqueda.
    * @example
    * $("#idComponente").on("rupTable_searchBeforeSubmit.rupTable.masterDetail", function(event, postData, jsonData){ });
    */})(jQuery);/*!
 * Copyright 2013 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 *//*global jQuery *//**
 * Genera una botonera asociada a la tabla con la finalidad de agrupar los controles que permiten realizar acciones sobre los registros de la misma.
 *
 * @summary Plugin de toolbar del componente RUP Table.
 * @module rup_table/toolbar
 * @example
 *
 * $("#idComponente").rup_table({
 * 	url: "../jqGridUsuario",
 * 	usePlugins:["toolbar"],
 * 	toolbar:{
 * 		// Propiedades de configuración del plugin toolbar
 * 	}
 * });
 */(function($){/**
	 * Definición de los métodos principales que configuran la inicialización del plugin.
	 *
	 * preConfiguration: Método que se ejecuta antes de la invocación del componente jqGrid.
	 * postConfiguration: Método que se ejecuta después de la invocación del componente jqGrid.
	 *
	 */jQuery.rup_table.registerPlugin('toolbar',{loadOrder:3,preConfiguration:function preConfiguration(settings){var $self=this;return $self.rup_table('preConfigureToolbar',settings);},postConfiguration:function postConfiguration(settings){var $self=this;return $self.rup_table('postConfigureToolbar',settings);}});//********************************
// DEFINICIÓN DE MÉTODOS PÚBLICOS
//********************************
/**
	 * Extensión del componente rup_table para permitir la gestión de la botonera asociada a la tabla.
	 *
	 * Los métodos implementados son:
	 *
	 * preConfigureToolbar(settings): Método que define la preconfiguración necesaria para el correcto funcionamiento del componente.
	 * postConfigureToolbar(settings): Método que define la postconfiguración necesaria para el correcto funcionamiento del componente.
	 *
	 */jQuery.fn.rup_table('extend',{/**
		* Metodo que realiza la pre-configuración del plugin toolbar del componente RUP Table.
		* Este método se ejecuta antes de la incialización del plugin.
		*
		* @name preConfigureToolbar
		* @function
		* @param {object} settings - Parámetros de configuración del componente.
		*/preConfigureToolbar:function preConfigureToolbar(settings){var $self=this,toolbarSettings=settings.toolbar;/*
			 * Inicialización de los identificadores por defecto de los componentes del toolbar
			 */toolbarSettings.id=toolbarSettings.id!==null?toolbarSettings.id:settings.id+'_toolbar';/*
			 * Inicialización del componente rup_toolbar
			 */if(jQuery('#'+toolbarSettings.id).length>0){settings.$toolbar=toolbarSettings.id[0]==='#'?$(toolbarSettings.id):$('#'+toolbarSettings.id);if(!settings.$toolbar.hasClass('rup-toolbar')){settings.$toolbar.rup_toolbar({width:toolbarSettings.width});}//				toolbarSettings.self=$(toolbarSettings);
}else{// En caso de no indicarse un toolbar, se crea un toolbar por defecto.
// FIXME: Contemplar la posibilidad de no generar una toolbar por defecto
toolbarSettings={};toolbarSettings.id='rup-maint_toolbar-'+settings.id;toolbarSettings.self=$('<div/>').attr('id',toolbarSettings.id);$self.prepend(toolbarSettings.self);toolbarSettings.self.rup_toolbar({width:toolbarSettings.width});}toolbarSettings.$toolbar=settings.$toolbar;// autoAjustToolbar: Realiza el autoajuste del toolbar al tamanyo del grid.
if(toolbarSettings.autoAjustToolbar){settings.$toolbar.css('width',$self.rup_table('getGridParam','width')-5);//-5 para ajustar el ancho
}// createDefaultToolButtons: Determina la creacion de los botones basicos por defecto del toolbar.
// Se unifican los parámetros de configuración de mostrar/ocultar los botones de la toolbar
if(toolbarSettings.createDefaultToolButtons===true){toolbarSettings.showOperations=jQuery.extend(true,{},toolbarSettings.defaultButtons,settings.core.showOperations,toolbarSettings.showOperations);}// Retrocompatibilidad: se mantiene el antiguo parámetro newButtons
toolbarSettings.buttons=jQuery.extend(true,{},toolbarSettings.newButtons,toolbarSettings.buttons);},/**
		* Metodo que realiza la post-configuración del plugin toolbar del componente RUP Table.
		* Este método se ejecuta antes de la incialización del plugin.
		*
		* @name postConfigureToolbar
		* @function
		* @fires module:rup_table#rupTable_feedbackClose
		* @param {object} settings - Parámetros de configuración del componente.
		*/postConfigureToolbar:function postConfigureToolbar(settings){var $self=this,toolbarSettings=settings.toolbar,counter=1;// Se generan los botones de la toolbar en base a las operaciones
jQuery.each(settings.toolbar.showOperations,function(buttonId,value){var operationCfg;if(value===true){operationCfg=settings.core.operations[buttonId];if(operationCfg!==undefined){toolbarSettings['btn'+buttonId.capitalize()]=settings.$toolbar.addButton({id:'btn'+buttonId.capitalize(),i18nCaption:operationCfg.name,css:operationCfg.icon,index:counter++,dropdown:operationCfg.dropdown,right:operationCfg.right},jQuery.rup.i18nParse(jQuery.rup.i18n.base,'rup_table')).bind('click',function(event){jQuery.proxy(operationCfg.callback,$self)($self,event);});}}});//Se comprueba si hay nuevos botones definidos y se ejecuta la función addButton con la parametrizacion de los nuevos botones
if(toolbarSettings.buttons!==undefined&&toolbarSettings.buttons!==null){jQuery.each(toolbarSettings.buttons,function(index,object){if(object.json_i18n===undefined){object.json_i18n={};}//					if (object.obj===undefined)
if(object.obj!==undefined&&object.click!==undefined){settings.$toolbar.addButton(object.obj,object.json_i18n).bind('click',object.click);}else if(object.buttons!==undefined){var mButton=settings.$toolbar.addMButton(object,object.json_i18n).bind('click',settings.$toolbar.showMButton);settings.$toolbar.addButtonsToMButton(object.buttons,mButton,object.json_i18n);}else{$.rup.errorGestor($.rup.i18nParse($.rup.i18n.base,'rup_table.toolbarNewButtonError'));}});}/*
			 * EVENTOS
			 */$self.on({'jqGridSelectRow.rupTable.toolbar jqGridLoadComplete.rupTable.toolbar jqGridInlineEditRow.rupTable.toolbar jqGridInlineAfterRestoreRow.rupTable.toolbar rupTableHighlightRowAsSelected.rupTable.toolbar rupTableSelectedRowNumberUpdated jqGridInlineAfterSaveRow rupTable_toolbarButtonsStateRefresh rupTable_afterDeleteRow.rupTable.toolbar rupTable_coreConfigFinished.toolbar rupTable_deleteAfterComplete.rupTable.toolbar':function jqGridSelectRowRupTableToolbarJqGridLoadCompleteRupTableToolbarJqGridInlineEditRowRupTableToolbarJqGridInlineAfterRestoreRowRupTableToolbarRupTableHighlightRowAsSelectedRupTableToolbarRupTableSelectedRowNumberUpdatedJqGridInlineAfterSaveRowRupTable_toolbarButtonsStateRefreshRupTable_afterDeleteRowRupTableToolbarRupTable_coreConfigFinishedToolbarRupTable_deleteAfterCompleteRupTableToolbar(event,id,status,obj){var $self=jQuery(this),settings=$self.data('settings');// Existe elementos seleccionados para ser editados
function processButton($button,enable){if($button!==undefined){if(enable){$button.button('enable');}else{$button.button('disable');}}}jQuery.each(settings.core.operations,function(buttonId,operationCfg){//						if (value===true){
if(settings.toolbar.showOperations[buttonId]===true){//							operationCfg = settings.core.operations[buttonId];
if(operationCfg!==undefined){processButton(settings.toolbar['btn'+buttonId.capitalize()],jQuery.proxy(operationCfg.enabled,$self)());}}});},'rupTable_internalFeedbackClose':function rupTable_internalFeedbackClose(){var $self=jQuery(this),settings=$self.data('settings');$self.trigger('rupTable_feedbackClose',settings.$internalFeedback);// if ($self.rup_table('isPluginLoaded', 'feedback')){
// 	settings.$internalFeedback.rup_feedback('close');
// }
}});}});//*******************************************************
// DEFINICIÓN DE LA CONFIGURACION POR DEFECTO DEL PATRON
//*******************************************************
/**
	* @description Propiedades de configuración del plugin toolbar del componente RUP Table.
	*
	* @name options
	*
	* @property {string} [id] - En caso de que se vaya a utilizar un identificador diferente al esperado por defecto, se deberá de indicar mediante esta propiedad.
	* @property {boolean} [createDefaultToolButtons=true] - Determina (true/false) si se deben visualizar los botones correspondientes a las operaciones por defecto del componente.
	* @property {object} [showOperations] - Permite indicar que operaciones definidas de manera global van a ser mostradas como botones. Cada operación puede tomar uno de los siguientes valores:  true: Valor por defecto. Se mostrará la operación como opción en la botonera.  true: Valor por defecto. Se mostrará la operación como opción en la  false: La operación no se mostrará como opción en la botonera.
	* @property {object} [deleteOptions] - Propiedades de configuración de la acción de borrado de un registro.
	* @property {object} [buttons] - Permite definir nuevos botones que se mostrarán en la toolbar. Los nuevos botones se especificarán del mismo modo que se describe en el componente rup_toolbar.
	*/jQuery.fn.rup_table.plugins.toolbar={};jQuery.fn.rup_table.plugins.toolbar.defaults={toolbar:{id:null,autoAjustToolbar:true,createDefaultToolButtons:true,defaultAdd:true,defaultEdit:true,defaultSave:true,defaultClone:true,defaultCancel:true,defaultDelete:true,defaultFilter:false,defaultButtons:{},showOperations:{},width:796}};/* ********* *//* EVENTOS
  /* ********* *//**
	*  Evento que se lanza cuando se cierra el feedback.
	*
	* @event module:rup_table#rupTable_feedbackClose
	* @property {Event} event - Objeto Event correspondiente al evento disparado.
	* @property {object} $feedback - Referencia jQuery al feedback interno.
	* @example
	* $("#idComponente").on("rupTable_feedbackClose", function(event, $internalFeedback){ });
	*/})(jQuery);/*!
 * Copyright 2013 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 *//*global jQuery *//**
 * Permite configurar un área para informar al usuario de cómo interactuar con el componente. Mediante el componente feedback se mostraran al usuario mensajes de confirmación, avisos y errores que faciliten y mejoren la interacción del usuario con la aplicación.
 *
 * @summary Plugin de feedback del componente RUP Table.
 * @module rup_table/feedback
 * @example
 *
 * $("#idComponente").rup_table({
 * 	url: "../jqGridUsuario",
 *	usePlugins:["feedback"],
 * 	feedback:{
 * 		// Propiedades de configuración del plugin feedback
 * 	}
 * });
 */(function($){/**
	 * Definición de los métodos principales que configuran la inicialización del plugin.
	 *
	 * preConfiguration: Método que se ejecuta antes de la invocación del componente jqGrid.
	 * postConfiguration: Método que se ejecuta después de la invocación del componente jqGrid.
	 *
	 */jQuery.rup_table.registerPlugin('feedback',{loadOrder:2,preConfiguration:function preConfiguration(settings){var $self=this;return $self.rup_table('preConfigureFeedback',settings);},postConfiguration:function postConfiguration(settings){var $self=this;return $self.rup_table('postConfigureFeedback',settings);}});//********************************
// DEFINICIÓN DE MÉTODOS PÚBLICOS
//********************************
/**
	 * Extensión del componente rup_table para permitir la gestión de la botonera asociada a la tabla.
	 *
	 * Los métodos implementados son:
	 *
	 * preConfigureFeedback(settings): Método que define la preconfiguración necesaria para el correcto funcionamiento del componente.
	 * postConfigureFeedback(settings): Método que define la postconfiguración necesaria para el correcto funcionamiento del componente.
	 *
	 * settings.$feedback : Referencia al componente feedback.
	 * settings.$$internalFeedback : Referencia al feedback interno.
	 *
	 */jQuery.fn.rup_table('extend',{/*
		 * Método que define la preconfiguración necesaria para el correcto funcionamiento del componente.
		 *
		 * TODO: internacionalizar mensajes de error.
		 *//**
			* Metodo que realiza la pre-configuración del plugin feedback del componente RUP Table.
			* Este método se ejecuta antes de la incialización del plugin.
			*
			* @name preConfigureFeedback
			* @function
			* @param {object} settings - Parámetros de configuración del componente.
			*/preConfigureFeedback:function preConfigureFeedback(settings){var $self=this,feedbackId,feedbackSettings=settings.feedback,$feedback;/*
			 * Inicialización de los identificadores por defecto de los componentes del toolbar
			 */feedbackSettings.id=feedbackSettings.id!==null?feedbackSettings.id:settings.id+'_feedback';feedbackId=feedbackSettings.id[0]==='#'?feedbackSettings.id:'#'+feedbackSettings.id;$feedback=jQuery(feedbackId);if($feedback.length===0){alert('El identificador especificado para el feedback no existe.');}else{settings.$feedback=$feedback;settings.$feedback.rup_feedback(feedbackSettings.config).attr('ruptype','feedback');}if(!jQuery.isFunction(settings.loadError)){settings.loadError=function(xhr){$self.rup_table('showFeedback',settings.$feedback,xhr.responseText,'error');};}/*
       * Definición del método serializeGridData para que añada al postData la información relativa a la multiseleccion.
       */$self.on({'rupTable_feedbackClose':function rupTable_feedbackClose(events,$feedback){$($feedback).rup_feedback('close');},'rupTable_feedbackShow':function rupTable_feedbackShow(events,$feedback,msg,type,options){$self.rup_table('showFeedback',$($feedback),msg,type,options);}});},/**
		 * Metodo que realiza la post-configuración del plugin feedback del componente RUP Table.
		 * Este método se ejecuta después de la incialización del plugin.
		 *
		 * @name postConfigureFeedback
		 * @function
		 * @param {object} settings - Parámetros de configuración del componente.
		 */postConfigureFeedback:function postConfigureFeedback(settings){// Definición del feedback interno
settings.$internalFeedback=$('<div/>').attr('id','rup_feedback_'+settings.id).insertBefore('#gbox_'+settings.id);settings.$internalFeedback.rup_feedback(settings.feedback.internalFeedbackConfig);}});jQuery.fn.rup_table('extend',{/**
     * Muestra el feedback indicado con la configuración especificada.
     *
     * @function  showFeedback
     * @param {object} $feedback - Objeto jQuery que referencia al componente feedback.
     * @param {string} msg - : Mensaje a mostrar en el feedback.
		 * @param {string} type -  Clase de feedback a mostrar.
		 * @param {object} options - Propiedades de configuración del feedback
     * @example
     * $("#idTable").rup_table("showFeedback", $("#idFeedback"), "Texto...", "ok"), {};
     */showFeedback:function showFeedback($feedback,msg,type,options){var $self=this,settings=$self.data('settings'),options_backup,default_options;if(options===false){// Muestra el feedback con las opciones con las que se ha creado
$feedback.rup_feedback('set',msg,type);}else if(jQuery.isPlainObject(options)){// Se aplicam las opciones de configuración indicadas sin modificar las del feedback
$feedback.rup_feedback('option',options);$feedback.rup_feedback('set',msg,type);}else{// Se utilizan las opciones de configuración por defecto del componente table
default_options=settings.feedback[type+'FeedbackConfig']!==undefined?settings.feedback[type+'FeedbackConfig']:settings.feedback.okFeedbackConfig;$feedback.rup_feedback('option',default_options);$feedback.rup_feedback('set',msg,type);}}});//*******************************************************
// DEFINICIÓN DE LA CONFIGURACION POR DEFECTO DEL PATRON
//*******************************************************
/**
	 * Parámetros de configuración por defecto para el feedback.
	 *
	 * feedback.config: Configuración por defecto del feedback principal.
	 * feedback.internalFeedbackConfig: Configuración por defecto del feedback interno.
	 *//**
	* @description Propiedades de configuración del plugin feedback del componente RUP Table.
	*
	* @name options
	*
	* @property {string} [id=null] - Nombre del identificador a utilizar en el feedback. Se utiliza en caso de no querer utilizar el por defecto.
	* @property {object} [config] - Determina la configuración por defecto del feedback.
	* @property {object} [okFeedbackConfig] - Determina la configuración por defecto del feedback en los casos de mensajes tipo .
	* @property {object} [errorFeedbackConfig] - Determina la configuración por defecto del feedback en los casos de mensajes tipo ERROR.
	* @property {object} [alertFeedbackConfig] - Determina la configuración por defecto del feedback en los casos de mensajes tipo ALERT.
	* @property {object} [internalFeedbackConfig] - Determina la configuración por defecto del feedback interno de la tabla.
	*/jQuery.fn.rup_table.plugins.feedback={};jQuery.fn.rup_table.plugins.feedback.defaults={loadError:function loadError(xhr,st,err){var $self=$(this),settings=$self.data('settings');$self.rup_table('showFeedback',settings.$feedback,xhr.responseText,'error');},feedback:{okFeedbackConfig:{closeLink:true,gotoTop:false,delay:1000},errorFeedbackConfig:{closeLink:true,gotoTop:false,delay:null},alertFeedbackConfig:{closeLink:true,gotoTop:false,delay:null},id:null,config:{type:'ok',closeLink:true,gotoTop:false,block:true},internalFeedbackConfig:{type:'ok',closeLink:true,gotoTop:false,block:false}}};})(jQuery);/*!
 * Copyright 2013 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 *//*global jQuery *//**
 * Aplica al componente un diseño líquido de modo que se adapte al ancho de la capa en la que está contenido.
 *
 * @summary Plugin de filtrado múltiple del componente RUP Table.
 * @module rup_table/fluid
 * @deprecated
 * @example
 *
 * $("#idComponente").rup_table({
 * 	url: "../jqGridUsuario",
 * 	usePlugins:["fuild"],
 * 	fuild:{
 * 		// Propiedades de configuración del plugin fuild
 * 	}
 * });
 */(function($){/**
	 * Definición de los métodos principales que configuran la inicialización del plugin.
	 *
	 * postConfiguration: Método que se ejecuta después de la invocación del componente jqGrid.
	 *
	 */jQuery.rup_table.registerPlugin('fluid',{loadOrder:5,postConfiguration:function postConfiguration(settings){var $self=this;return $self.rup_table('postConfigureFluid',settings);}});//********************************
// DEFINICIÓN DE MÉTODOS PÚBLICOS
//********************************
/**
	 * Extensión del componente rup_table para permitir la gestión del diseño líquido del componente.
	 *
	 * Los métodos implementados son:
	 *
	 * postConfigureFilter(settings): Método que define la preconfiguración necesaria para el correcto funcionamiento del componente.
	 *
	 * Se almacena la referencia de los diferentes componentes:
	 *
	 * settings.$fluidBaseLayer : Referencia a la capa que se tomará como base para aplicar el diseño líquido.
	 *
	 */jQuery.fn.rup_table('extend',{/*
		 * Realiza la configuración interna necesaria para la gestión correcta de la edición mediante un formulario.
		 *
		 * TODO: internacionalizar mensajes de error.
		 *//**
		* Metodo que realiza la post-configuración del plugin fuild del componente RUP Table.
		* Este método se ejecuta antes de la incialización del plugin.
		*
		* @name postConfigureFluid
		* @function
		* @param {object} settings - Parámetros de configuración del componente.
		*/postConfigureFluid:function postConfigureFluid(settings){var $self=this,$fluidBaseLayer;settings.fluid.baseLayer=$.rup_utils.getJQueryId(settings.fluid.baseLayer!==null?settings.fluid.baseLayer:settings.id+'_div');settings.fluid.$baseLayer=jQuery(settings.fluid.baseLayer);if(settings.fluid.$baseLayer.length===0){alert('El identificador '+settings.baseLayer+' especificado para la capa sobre la que se va a aplicar el diseño líquido no existe.');return;}$fluidBaseLayer=settings.fluid.fluidBaseLayer=settings.fluid.$baseLayer;// Tratamiento del evento de redimiensionado del diseño líquido de la tabla
$self.bind('fluidWidth.resize',function(event,previousWidth,currentWidth){if($self.is(':visible')){var feedBackPaddingLeft,feedBackPaddingRight,toolbarPaddingLeft,toolbarPaddingRight;$self.setGridWidth(currentWidth);// Se redimensionan las capas contenidas en el mantenimiento
$fluidBaseLayer.children().width(currentWidth);//						prop.searchForm.parent().width(currentWidth+3)
// Se redimensiona el feedback
if(settings.$feedback){feedBackPaddingLeft=parseInt(settings.$feedback.css('padding-left'));feedBackPaddingRight=parseInt(settings.$feedback.css('padding-right'));settings.$feedback.width(currentWidth-(feedBackPaddingLeft+feedBackPaddingRight));}// Se redimensiona la toolbar
if(settings.$toolbar){toolbarPaddingLeft=parseInt(settings.$toolbar.css('padding-left'));toolbarPaddingRight=parseInt(settings.$toolbar.css('padding-right'));settings.$toolbar.width(currentWidth-(toolbarPaddingLeft+toolbarPaddingRight));settings.$toolbar.css('width',currentWidth-(toolbarPaddingLeft+toolbarPaddingRight));}}});//			$self.fluidWidth({
//				fluidBaseLayer:settings.fluid.baseLayer,
//				minWidth: 100,
//				maxWidth: 2000,
//				fluidOffset : 0
//			});
$self.fluidWidth(settings.fluid);$self.on('rupTable_fluidUpdate',function(event){$self.fluidWidth(settings.fluid);});}});//*******************************************************
// DEFINICIÓN DE LA CONFIGURACION POR DEFECTO DEL PATRON
//*******************************************************
/**
	 * Parámetros de configuración por defecto para el plugin fluid.
	 *
	 *//**
 	* @description Propiedades de configuración del plugin multifilter del componente RUP Table.
 	*
 	* @name options
 	*
 	* @property {string} [baseLayer] - Identificador de la capa que contiene al componente. Se tomará como base para redimensionar las diferentes partes de la tabla. En caso de no indicarse se tomará por defecto una generada con el patrón identificadorTabla+”_div”.
 	* @property {integer} [minWidth=100] - Determina la anchura máxima a la que se va a redimensionar la capa.
 	* @property {integer} [maxWidth=2000] -  Determina la anchura mínima a la que se va a redimensionar la capa.
 	* @property {integer} [fluidOffset=0] - Desplazamiento que se aplica a la capa redimensionada.
 	*/jQuery.fn.rup_table.plugins.fluid={};jQuery.fn.rup_table.plugins.fluid.defaults={fluid:{baseLayer:null,minWidth:100,maxWidth:2000,fluidOffset:0}};})(jQuery);/*!
 * Copyright 2013 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 *//*global jQuery *//**
 * Permite la edición de los registros de la tabla utilizando un formulario de detalle. El formulario se muestra dentro de un diálogo y ofrece las siguientes funcionalidades:
 * - Añadir un nuevo registro o modificar uno ya existente.
 * - Cancelar la inserción o edición de un registro.
 * - Navegar entre los registros mostrados en la tabla para permitir operar de manera mas ágil sobre losdiferentes elementos.
 *
 * @summary Plugin de edición en formulario del componente RUP Table.
 * @module rup_table/formEdit
 * @example
 *
 * $("#idComponente").rup_table({
 * 	url: "../jqGridUsuario",
 * 	usePlugins:["formEdit"],
 * 	formEdit:{
 * 		// Propiedades de configuración del plugin formEdit
 * 	}
 * });
 */(function($){/**
     * Definición de los métodos principales que configuran la inicialización del plugin.
     *
     * preConfiguration: Método que se ejecuta antes de la invocación del componente jqGrid.
     * postConfiguration: Método que se ejecuta después de la invocación del componente jqGrid.
     *
     */jQuery.rup_table.registerPlugin('formEdit',{loadOrder:6,preConfiguration:function preConfiguration(settings){var $self=this;return $self.rup_table('preConfigureFormEdit',settings);},postConfiguration:function postConfiguration(settings){var $self=this;return $self.rup_table('postConfigureFormEdit',settings);}});//********************************
// DEFINICIÓN DE MÉTODOS PÚBLICOS
//********************************
/**
     * Extensión del componente rup_table para permitir la edición de los registros mediante un formulario.
     *
     * Los métodos implementados son:
     *
     * preConfigureFormEdit(settings): Método que define la preconfiguración necesaria para el correcto funcionamiento del componente.
     * postConfigureFormEdit(settings): Método que define la postconfiguración necesaria para el correcto funcionamiento del componente.
     *
     * Las propiedades de esta extensión almacenadas en el settings son las siguientes:
     *
     * settings.formEdit.$detailForm : Referencia al formulario de detalle mediante el que se realizan las modificaciones e inserciones de registros.
     * settings.formEdit.$detailFormDiv : Referencia al div que arropa el formulario de detalle y sobre el que se inicializa el componente rup_dialog.
     *
     */jQuery.fn.rup_table('extend',{/**
		* Metodo que realiza la pre-configuración del plugin formEdit del componente RUP Table.
		* Este método se ejecuta antes de la incialización del plugin.
		*
		* @name preConfigureFormEdit
		* @function
		* @param {object} settings - Parámetros de configuración del componente.
		*/preConfigureFormEdit:function preConfigureFormEdit(settings){var $self=this,self=this[0],colModel=settings.colModel,colModelObj;settings.formEdit.navigationBarId=settings.formEdit.navigationBarId!==undefined?settings.formEdit.navigationBarId:settings.id+'_detail_navigation';settings.formEdit.saveButtonId=settings.formEdit.saveButtonId!==undefined?settings.formEdit.saveButtonId:settings.id+'_detail_button_save';settings.formEdit.saveRepeatButtonId=settings.formEdit.saveRepeatButtonId!==undefined?settings.formEdit.saveRepeatButtonId:settings.id+'_detail_button_save_repeat';settings.formEdit.cancelButtonId=settings.formEdit.cancelButtonId!==undefined?settings.formEdit.cancelButtonId:settings.id+'_detail_button_cancel';settings.formEdit.feedbackId=settings.formEdit.feedbackId!==undefined?settings.formEdit.feedbackId:settings.id+'_detail_feedback';settings.formEdit.$navigationBar=jQuery('#'+settings.formEdit.navigationBarId);settings.formEdit.$saveButton=jQuery('#'+settings.formEdit.saveButtonId);settings.formEdit.$saveRepeatButton=jQuery('#'+settings.formEdit.saveRepeatButtonId);settings.formEdit.$cancelButton=jQuery('#'+settings.formEdit.cancelButtonId);settings.formEdit.$feedback=jQuery('#'+settings.formEdit.feedbackId);/*
             * Inicialización de propiedades del componente para simplificar su configuración
             */// En caso de no especificarse una url para la edición de un elemento, se utiliza por defecto la indicada en la propiedad url.
if(settings.formEdit.editurl===undefined){settings.formEdit.editurl=settings.baseUrl;settings.formEdit.editOptions.ajaxEditOptions.url=settings.baseUrl;settings.formEdit.addOptions.ajaxEditOptions.url=settings.baseUrl;}if(settings.formEdit.detailOptions.ajaxDetailOptions.url===undefined){settings.formEdit.detailOptions.ajaxDetailOptions.url=settings.baseUrl;}settings.ondblClickRow=function(rowid,iRow,iCol,e){$self.rup_table('editElement',rowid);return false;};settings.formEdit.deleteOptions.ajaxDelOptions=jQuery.extend(true,settings.formEdit.deleteOptions.ajaxDelOptions,{success:function success(data,st,xhr){$self.triggerHandler('rupTableAfterDelete',[data,st,xhr]);$self.rup_table('showFeedback',settings.$feedback,$.rup.i18nParse($.rup.i18n.base,'rup_table.deletedOK'),'ok');}});// Se comprueba si se ha especificado un formulario propio por parte del usuario.
if(settings.formEdit.detailForm===undefined){for(var i=0;i<colModel.length;i++){colModelObj=colModel[i];colModelObj.id='detailForm_'+settings.id+'_'+colModelObj.name.replace(/[.]/g,'_');}}/* DEFINICION DE OPERACIONES BASICAS CON LOS REGISTROS */settings.core.defaultOperations={'add':{name:$.rup.i18nParse($.rup.i18n.base,'rup_table.new'),icon:self._ADAPTER.CONST.core.operations.defaultOperations.add.icon,enabled:function enabled(){return true;},callback:function callback(key,options){$self.rup_table('newElement');}},'edit':{name:$.rup.i18nParse($.rup.i18n.base,'rup_table.modify'),icon:self._ADAPTER.CONST.core.operations.defaultOperations.edit.icon,enabled:function enabled(){var $self=this,settings=$self.data('settings');return jQuery.proxy(settings.fncHasSelectedElements,$self)();},callback:function callback(key,options){$self.rup_table('editElement');}},//				"save": {
//					name: "Guardar",
//					icon: "save",
//					enabled: function(){
//						return false;
//					}},
//					callback: function(key, options){
//						$self.rup_table("newElement");
//					}},
'clone':{name:$.rup.i18nParse($.rup.i18n.base,'rup_table.clone'),icon:self._ADAPTER.CONST.core.operations.defaultOperations.clone.icon,enabled:function enabled(){return jQuery.proxy(settings.fncHasSelectedElements,$self)();},callback:function callback(key,options){$self.rup_table('cloneElement');}},//				"cancel": {
//					name: "Cancel",
//					icon: "cancel",
//					enabled: function(){
//						return false;
//					}},
'delete':{name:$.rup.i18nParse($.rup.i18n.base,'rup_table.delete'),icon:self._ADAPTER.CONST.core.operations.defaultOperations['delete'].icon,enabled:function enabled(){var $self=this,settings=$self.data('settings');return jQuery.proxy(settings.fncHasSelectedElements,$self)();},callback:function callback(key,options){$self.rup_table('deleteElement');}}};$.extend(true,settings.core.operations,settings.core.defaultOperations);// Configuración de edit/add
settings.formEdit.addOptions=$.extend(true,{},settings.formEdit.addEditOptions,settings.formEdit.addOptions);settings.formEdit.editOptions=$.extend(true,{},settings.formEdit.addEditOptions,settings.formEdit.editOptions);},/**
	 * Metodo que realiza la post-configuración del plugin formEdit del componente RUP Table.
	 * Este método se ejecuta antes de la incialización del plugin.
	 *
	 * @name postConfigureFormEdit
	 * @function
	 * @param {object} settings - Parámetros de configuración del componente.
	 */postConfigureFormEdit:function postConfigureFormEdit(settings){var $self=this,$objDetailForm;// Se comprueba si se ha especificado un formulario propio por parte del usuario.
if(settings.formEdit.detailForm){// Se comprueba que el identificador especificado para el diálogo sea válido
if(jQuery(settings.formEdit.detailForm).length===0){alert('El identificador especificado para el fomulario de detalle no existe.');}else{$objDetailForm=$(settings.formEdit.detailForm);if($objDetailForm.is('form')){if($objDetailForm.parent().is('div')){settings.formEdit.$detailFormDiv=$objDetailForm.parent();settings.formEdit.$detailForm=$objDetailForm;}else{alert('El fomrmulario no está incluido dentro de un div');}}else if($objDetailForm.is('div')){var $objFormAux=$objDetailForm.find('form');if($objFormAux.length===1){settings.formEdit.$detailFormDiv=$objDetailForm;settings.formEdit.$detailForm=$objFormAux;}else{alert('El div indicado no contiene un único formulario');}}// Inicialización del componente rup_form sobre del formulario de detalle
settings.formEdit.$detailForm.rup_form(settings.formEdit.editOptions);settings.formEdit.ownFormEdit=true;}}//			else{
// No se configura un formulario de detalle
var beforeSendUserEvent=settings.beforeSend;var defaultBeforeSend=function defaultBeforeSend(jqXHR,ajaxOptions){ajaxOptions.beforeSend=beforeSendUserEvent;ajaxOptions.validate=settings.formEdit.validate;ajaxOptions.feedback=settings.$detailFeedback;// Se elimina el valor de la propiedad contentType para que la gestione automáticamente el componente rup.form
delete ajaxOptions.contentType;if(jQuery.isPlainObject(ajaxOptions.data)){ajaxOptions.data=$.rup_utils.unnestjson(ajaxOptions.data);}ajaxOptions.beforeSubmit=function(a,$form,options){var hasFileInputs=jQuery('input:file',$form).length>0;if(!$.rup.browser.xhrFileUploadSupport&&hasFileInputs||options.iframe===true){options.extraData={};}// TODO : Comprobar si se puede elimianr el delete
a=undefined;//delete a;
};ajaxOptions.propperFormSerialization=false;settings.formEdit.$detailForm.rup_form('ajaxSubmit',ajaxOptions);rp_ge[settings.id].processing=false;return false;};settings.formEdit.editOptions.ajaxEditOptions.beforeSend=defaultBeforeSend;settings.formEdit.addOptions.ajaxEditOptions.beforeSend=defaultBeforeSend;//			}
settings.getDetailTotalRowCount=function(){var $self=this;return $self.rup_table('getGridParam','records');};settings.getDetailCurrentRowCount=function(){var $self=this,page,rowNum,rowId,rowsPerPage,cont;// Obtenemos la pagina actual
page=parseInt($self.rup_table('getGridParam','page'),10);// Obtenemos el identificador del registro seleccionado
rowId=$self.rup_table('getGridParam','selrow');// Obtenemos el numero de linea
//				rowNum = $self.jqGrid("getInd", rowId);
rowNum=jQuery.inArray(rowId,jQuery.proxy(jQuery.jgrid.getCurrPos,$self[0])()[1])+1;// Numero de registros por pagina que se visualizan
rowsPerPage=parseInt($self.rup_table('getGridParam','rowNum'),10);// Flag de todos los registros seleccionados
cont=page*rowsPerPage-rowsPerPage+rowNum;return cont;};settings.getRowForEditing=function(){var $self=this,selrow=$self.jqGrid('getGridParam','selrow');return selrow===null?false:selrow;};settings.fncHasSelectedElements=function(){var $self=this;return jQuery.proxy(settings.getRowForEditing,$self)()!==false;};settings.fncGetNavigationParams=function getNavigationParams(linkType){var $self=this,execute=false,changePage=false,index=0,newPage=0,newPageIndex=0,npos=jQuery.proxy(jQuery.jgrid.getCurrPos,$self[0])(),page=parseInt($self.rup_table('getGridParam','page'),10),rowsPerPage=parseInt($self.rup_table('getGridParam','rowNum'),10),lastPage=parseInt(Math.ceil($self.rup_table('getGridParam','records')/$self.rup_table('getGridParam','rowNum')),10);npos[0]=parseInt(npos[0],10);switch(linkType){case'first':if(!(page===1&&npos[0]===0)){execute=true;index=0;if(page>1){changePage=true;newPage=1;newPageIndex=0;}}break;case'prev':if(!(page===1&&npos[0]===0)){execute=true;index=npos[0]-1;if(index<0){changePage=true;newPage=page-1;newPageIndex=rowsPerPage;}}break;case'next':if(!(page===lastPage&&npos[0]===npos[1].length-1)){execute=true;index=npos[0]+1;if(index>npos[1].length-1){changePage=true;newPage=page+1;newPageIndex=0;}}break;case'last':if(!(page===lastPage&&npos[0]===npos[1].length-1)){execute=true;index=npos[1].length-1;if(page<lastPage){changePage=true;newPage=lastPage;newPageIndex=rowsPerPage;}}break;}return[linkType,execute,changePage,index,npos,newPage,newPageIndex];};settings.doNavigation=function(arrParams,execute,changePage,index,npos,newPage,newPageIndex){var $self=this,settings=$self.data('settings'),props=rp_ge[$self.attr('id')],linkType,execute,changePage,index,npos,newPage,newPageIndex;if($.isArray(arrParams)){linkType=arrParams[0];execute=arrParams[1];changePage=arrParams[2];index=arrParams[3];npos=arrParams[4];newPage=arrParams[5];newPageIndex=arrParams[6];if(execute){$self.rup_table('hideFormErrors',settings.formEdit.$detailForm);$self.triggerHandler('jqGridAddEditClickPgButtons',[linkType,settings.formEdit.$detailForm,npos[1][npos[index]]]);if(changePage){$self.trigger('reloadGrid',[{page:newPage}]);$self.on('jqGridAfterLoadComplete.pagination',function(event,data){var nextPagePos=jQuery.proxy(jQuery.jgrid.getCurrPos,$self[0])(),newIndexPos=newPageIndex<nextPagePos[1].length?newPageIndex:nextPagePos[1].length-1;$self.jqGrid('setSelection',nextPagePos[1][newIndexPos]);jQuery.proxy(jQuery.jgrid.fillData,$self[0])(nextPagePos[1][newIndexPos],$self[0],settings.formEdit.$detailForm.attr('id'),settings.opermode);jQuery.proxy(jQuery.jgrid.updateNav,$self[0])(nextPagePos[1][newIndexPos],npos[1].length-1);$self.off('jqGridAfterLoadComplete.pagination');});}else{jQuery.proxy(jQuery.jgrid.fillData,$self[0])(npos[1][index],$self[0],settings.formEdit.$detailForm.attr('id'),settings.opermode);$self.jqGrid('setSelection',npos[1][index]);jQuery.proxy(jQuery.jgrid.updateNav,$self[0])(npos[1][index],npos[1].length-1);}$self.triggerHandler('jqGridAddEditAfterClickPgButtons',[linkType,settings.formEdit.$detailForm,npos[1][npos[index]]]);if(jQuery.isFunction(props.afterclickPgButtons)){props.afterclickPgButtons.call($self,'next',settings.formEdit.$detailForm,npos[1][npos[index]]);}}}};// Campturador del evento jqGridInlineAfterSaveRow.
$self.on({'jqGridLoadComplete.rupTable.formEditing':function jqGridLoadCompleteRupTableFormEditing(data){var $self=$(this),settings=$self.data('settings'),nPos;if(settings.formEdit.autoselectFirstRecord){nPos=jQuery.proxy(jQuery.jgrid.getCurrPos,$self[0])();$self.jqGrid('setSelection',nPos[1][0],false);}},'jqGridAddEditInitializeForm.rupTable.formEditing':function jqGridAddEditInitializeFormRupTableFormEditing(event,$form,modo){/*
                     * Creación de los componentes rup
                     */var $self=$(this),settings=$self.data('settings'),colModel=settings.colModel;if(settings.formEdit.ownFormEdit===false){jQuery.each(colModel,function(index,colObj){if(colObj.rupType){if(colObj.editoptions&&colObj.editoptions.i18nId===undefined){colObj.editoptions.i18nId=$self.attr('id')+'##'+this.name;}$('#'+(colObj.id!==null?colObj.id:name),$form)['rup_'+colObj.rupType](colObj.editoptions);}});}//Se crea el toolbar de error mediante un componente rup_tooltip
settings.$detailFeedback=settings.formEdit.$feedback.rup_feedback({closeLink:true,gotoTop:false,block:false,fadeSpeed:500//						delay: 1000,
}).attr('ruptype','feedback');},'jqGridAddEditAfterSubmit.rupTable.formEditing':function jqGridAddEditAfterSubmitRupTableFormEditing(event,res,postData,oper){// Una vez se haya realizado el guardado del registro se muestra el mensaje correspondiente en el feedback dependiendo del modo en el que se encuentra.
var settings=$self.data('settings'),formEditSaveType=$self.data('tmp.formEditSaveType'),id,compositeId='',$fieldRupCombo,labelProperty=null,responseJson;$self.removeData('tmp.formEditSaveType');// Tratamiento concreto para los componentes RUP
// Combo
jQuery.each(settings.colModel,function(i,elem){if(elem.rupType==='combo'){$fieldRupCombo=jQuery('[name=\''+elem.name+'\']',settings.$detailForm);if(elem.editoptions.labelProperty!==undefined){labelProperty=elem.editoptions.labelProperty;}else if(elem.editoptions.sourceParam!==undefined){labelProperty=elem.name.substring(0,elem.name.lastIndexOf('.')+1)+elem.editoptions.sourceParam.label;}if(labelProperty!==null){postData[labelProperty]=$fieldRupCombo.rup_combo('label');}}});// Dependiendo del boton de guardado seleccionado se realiza el comportamiento correspondiente
if(formEditSaveType==='SAVE'){if(oper==='edit'){$self.rup_table('showFeedback',settings.$feedback,$.rup.i18nParse($.rup.i18n.base,'rup_table.modifyOK'),'ok');}else{$self.rup_table('showFeedback',settings.$feedback,$.rup.i18nParse($.rup.i18n.base,'rup_table.insertOK'),'ok');}settings.formEdit.$detailFormDiv.rup_dialog('close');}else if(formEditSaveType==='SAVE_REPEAT'){if(oper==='edit'){$self.rup_table('showFeedback',settings.$detailFeedback,$.rup.i18nParse($.rup.i18n.base,'rup_table.modifyOK'),'ok');}else{$self.rup_table('showFeedback',settings.$detailFeedback,$.rup.i18nParse($.rup.i18n.base,'rup_table.insertOK'),'ok');}}// Se obtiene el json de respuesta
try{responseJson=$.parseJSON(res.responseText);}catch(e){responseJson=postData;}// Tratamiento de la primary key compuesta
if(settings.primaryKey&&_typeof(settings.primaryKey)==='object'&&settings.primaryKey.length>1){for(var i=0;i<settings.primaryKey.length;i++){compositeId+=responseJson[settings.primaryKey[i]]+settings.multiplePkToken;}id=compositeId.substr(0,compositeId.length-1);}else{id=responseJson[settings.primaryKey?settings.primaryKey:$self[0].p.prmNames.id];}return[true,'',id];},'jqGridAddEditErrorTextFormat.rupTable.formEditing':function jqGridAddEditErrorTextFormatRupTableFormEditing(event,data,oper){var responseJSON;if(data.status===406&&data.responseText!==''){try{responseJSON=jQuery.parseJSON(data.responseText);if(responseJSON.rupErrorFields){$self.rup_table('showServerValidationFieldErrors',settings.formEdit.$detailForm,responseJSON);}}catch(e){// El mensaje JSON
$self.rup_table('showFeedback',settings.$detailFeedback,data.responseText,'error');}}},//				 "jqGridDblClickRow.rupTable.formEditing": function (event, rowid, iRow, iCol, e){
//					$self.rup_table('editElement', rowid);
//				 },
'jqGridAddEditBeforeShowForm.rupTable.formEditing':function jqGridAddEditBeforeShowFormRupTableFormEditing(event,$detailForm,frmoper){var $self=$(this),settings=$self.data('settings'),$title=jQuery('#ui-dialog-title-'+settings.formEdit.$detailFormDiv.attr('id'),settings.formEdit.$detailFormDiv.parent()),colModel=$self[0].p.colModel;// Se ocultan los errores de validación mostrados en el formulario de detalle
$self.rup_table('hideFormErrors',settings.formEdit.$detailForm);if(frmoper==='add'||frmoper==='clone'||frmoper==='clone_clear'){$($title.context[0]).find(".ui-dialog-titlebar > span").text(rp_ge[$self[0].p.id].addCaption);$('#pagination_'+settings.id+',#pag_'+settings.id).hide();}else{$($title.context[0]).find(".ui-dialog-titlebar > span").text(rp_ge[$self[0].p.id].editCaption);$('#pagination_'+settings.id+',#pag_'+settings.id).show();}},'jqGridAddEditBeforeShowForm.rupTable.formEditing.readOnlyPks':function jqGridAddEditBeforeShowFormRupTableFormEditingReadOnlyPks(event,$detailForm,frmoper){var $self=$(this),settings=$self.data('settings'),colModel=$self[0].p.colModel;// Controlar los campos editables en modo edición
for(var i=0;i<colModel.length;i++){if(settings.formEdit.ownFormEdit!==true||settings.formEdit.ownFormEdit===true&&jQuery.inArray(colModel[i].name,settings.primaryKey)!==-1){if(frmoper==='add'||frmoper==='clone'||frmoper==='clone_clear'){if(colModel[i].editableOnAdd===false){jQuery('[name=\''+colModel[i].name+'\']',settings.formEdit.$detailFormDiv).attr('readonly','readonly');}else{jQuery('[name=\''+colModel[i].name+'\']',settings.formEdit.$detailFormDiv).removeAttr('readonly');}}else{if(colModel[i].editableOnEdit===false){jQuery('[name=\''+colModel[i].name+'\']',settings.formEdit.$detailFormDiv).attr('readonly','readonly');}else{jQuery('[name=\''+colModel[i].name+'\']',settings.formEdit.$detailFormDiv).removeAttr('readonly');}}}}},'jqGridAddEditAfterShowForm.rupTable.formEditing':function jqGridAddEditAfterShowFormRupTableFormEditing(event,$detailForm,frmoper){var $self=$(this),settings=$self.data('settings');// Ubicamos el foco en el primer elemento del formulario
$self.rup_table('hideFormErrors',settings.formEdit.$detailForm);jQuery(':focusable:enabled:not([readonly]):first',$detailForm).focus();}});}});/**
     * Métodos públicos del plugin formEdit.
     *
     * Los métodos implementados son:
     *
     * createDetailNavigation(settings): Crea la barra de navegación del formulario de detalle.
     * deleteElement(rowId, options): Realiza el borrado de un registro determinado.
     * editElement(rowId, options): Lanza la edición de un registro medainte un formulario de detalle.
     * newElement(): Inicia el proceso de inserción de un nuevo registro.
     *
     * s($form): Oculta los mensaje de error visualizado en el
     *
     */jQuery.fn.rup_table('extend',{/**
     * Devuelve la template HTML correspondiente a la capa de navegación del fomulario de filtrado.
     *
     * @function  createDetailNavigation
		 * @return {object} - Template correspondiente a la capa de navegación.
     * @example
     * $("#idTable").rup_table("createDetailNavigation");
     */createDetailNavigation:function createDetailNavigation(){var $self=$(this);return $.proxy($self[0]._ADAPTER.createDetailNavigation,$self)();},/**
		 * Elimina el registro correspondiente al identificador indicado y utilizando las opciones de borrado especificadas.
		 *
		 * @function  deleteElement
		 * @param {string} rowId - Identificador del registro que se desea eliminar.
		 * @param {object} options - Opciones de configuración de la operación de borrado.
		 * @return {object} - Referencia al propio objecto jQuery.
		 * @fires module:rup_table#rupTable_deleteAfterSubmit
		 * @fires module:rup_table#rupTable_afterDeleteRow
		 * @fires module:rup_table#rupTable_beforeDeleteRow
		 * @example
		 * $("#idComponente").rup_table("deleteElement", rowId, options);
		 */deleteElement:function deleteElement(rowId,options){var $self=this,settings=$self.data('settings'),deleteOptions=jQuery.extend(true,{},settings.formEdit.deleteOptions,options),selectedRow=rowId===undefined?$self.rup_table('getSelectedRows'):rowId;// En caso de especificarse el uso del método HTTP DELETE, se anyade el identificador como PathParameter
if(selectedRow.length===1){if(deleteOptions.mtype==='DELETE'){deleteOptions.url=settings.formEdit.editurl+'/'+$self.rup_table('getPkUrl',selectedRow);}}else{deleteOptions.mtype='POST';deleteOptions.ajaxDelOptions.contentType='application/json';deleteOptions.ajaxDelOptions.type='POST';deleteOptions.ajaxDelOptions.dataType='json';deleteOptions.url=settings.formEdit.editurl+'/deleteAll';deleteOptions.serializeDelData=function(ts,postData){return jQuery.toJSON({'core':{'pkToken':settings.multiplePkToken,'pkNames':settings.primaryKey},'multiselection':$self.rup_table('getSelectedIds'),'filter':$self.rup_table('getFilterParams')});};}deleteOptions.afterSubmit=function(){$self.triggerHandler('rupTable_deleteAfterSubmit');return true;};deleteOptions.afterComplete=function(){$self.triggerHandler('rupTable_afterDeleteRow');};if($self.triggerHandler('rupTable_beforeDeleteRow',[deleteOptions,selectedRow])!==false){$self.jqGrid('delGridRow',selectedRow,deleteOptions);}return $self;},/**
		 * Edita el registro correspondiente al identificador indicado y utilizando las opciones de edición especificadas.
		 *
		 * @function  editElement
		 * @param {string} rowId - Identificador del registro que se desea editar.
		 * @param {object} options - Opciones de configuración de la operación de edición.
		 * @return {object} - Referencia al propio objecto jQuery.
		 * @fires module:rup_table#rupTable_beforeEditRow
		 * @example
		 * $("#idComponente").rup_table("editElement", rowId, options);
		 */editElement:function editElement(rowId,options){var $self=this,settings=$self.data('settings'),//				selectedRow = (rowId===undefined?$self.jqGrid('getGridParam','selrow'):rowId);
selectedRow=rowId===undefined?$.proxy(settings.getRowForEditing,$self)():rowId,colModel=$self[0].p.colModel;if(selectedRow!==false){// Controlar los campos editables en modo edición
for(var i=0;i<colModel.length;i++){if(colModel[i].editable===true&&colModel[i].editableOnEdit===false){if(colModel[i].editoptions===undefined){colModel[i].editoptions={};}colModel[i].editoptions.readonly='readonly';}else{if(colModel[i].editoptions!==undefined&&colModel[i].editoptions.readonly!==undefined){delete colModel[i].editoptions.readonly;}}}if($self.triggerHandler('rupTable_beforeEditRow',[settings.formEdit.editOptions,selectedRow])!==false){$self.jqGrid('editGridRow',selectedRow,settings.formEdit.editOptions);}}return $self;},/**
		 * Muestra el formulario de detalle para permitir al usuario insertar un nuevo registro.
		 *
		 * @function  newElement
		 * @param {boolean} addEvent - Determina si se debe lanzar (true) o no (false) el evento rupTable_beforeAddRow.
		 * @return {object} - Referencia al propio objecto jQuery.
		 * @fires module:rup_table#rupTable_beforeAddRow
		 * @example
		 * $("#idComponente").rup_table("newElement", true);
		 */newElement:function newElement(addEvent){var $self=this,settings=$self.data('settings'),colModel=$self[0].p.colModel,eventRet;// Controlar los campos editables en modo edición
for(var i=0;i<colModel.length;i++){if(colModel[i].editable===true&&colModel[i].editableOnAdd!==false){if(colModel[i].editable===true&&colModel[i].editableOnAdd===false){if(colModel[i].editoptions===undefined){colModel[i].editoptions={};}colModel[i].editoptions.readonly='readonly';}else{if(colModel[i].editoptions!==undefined&&colModel[i].editoptions.readonly!==undefined){delete colModel[i].editoptions.readonly;}}}}if(addEvent===false||addEvent!==false&&$self.triggerHandler('rupTable_beforeAddRow',[settings.formEdit.addOptions])!==false){$self.jqGrid('editGridRow','new',settings.formEdit.addOptions);}return $self;},/**
		 * Clona el registro correspondiente al identificador indicado y utilizando las opciones de clonado especificadas.
		 *
		 * @function  cloneElement
		 * @param {string} rowId - Identificador del registro que se desea clonar.
		 * @param {object} options - Opciones de configuración de la operación de clonado.
		 * @param {boolean} cloneEvent - Determina si se debe lanzar (true) o no (false) el evento rupTable_beforeCloneRow.
		 * @return {object} - Referencia al propio objecto jQuery.
		 * @fires module:rup_table#rupTable_beforeCloneRow
		 * @example
		 * $("#idComponente").rup_table("cloneElement", rowId, options, cloneEvent);
		 */cloneElement:function cloneElement(rowId,options,cloneEvent){var $self=this,settings=$self.data('settings'),colModel=$self[0].p.colModel,selectedRow=rowId===undefined?$.proxy(settings.getRowForEditing,$self)():rowId;// Controlar los campos editables en modo edición
for(var i=0;i<colModel.length;i++){if(colModel[i].editable===true&&colModel[i].editableOnAdd!==false){if(colModel[i].editable===true&&colModel[i].editableOnAdd===false){if(colModel[i].editoptions===undefined){colModel[i].editoptions={};}colModel[i].editoptions.readonly='readonly';}else{if(colModel[i].editoptions!==undefined&&colModel[i].editoptions.readonly!==undefined){delete colModel[i].editoptions.readonly;}}}}if(cloneEvent===false||cloneEvent!==false&&$self.triggerHandler('rupTable_beforeCloneRow',[settings,selectedRow])!==false){$self.jqGrid('editGridRow','cloned',settings.formEdit.addOptions);jQuery.proxy(jQuery.jgrid.fillData,$self[0])(selectedRow,$self[0],settings.formEdit.$detailForm,'clone');jQuery('#id_g',settings.formEdit.$detailForm).val('_empty');}return $self;},/**
		 *  Oculta los mensajes de error del formulario indicado.
		 *
		 * @function  hideFormErrors
		 * @param {object} $form - Formulario del que se desea ocultar los mensajes de error.
		 * @example
		 * $("#idComponente").rup_table("hideFormErrors", $form);
		 */hideFormErrors:function hideFormErrors($form){var $self=this,settings=$self.data('settings');// Ocultamos el feedback de error
if(settings.formEdit!==undefined&&settings.formEdit.$feedback!==undefined){settings.formEdit.$feedback.hide();}if($form!==undefined){jQuery('.rup-maint_validateIcon',$form).remove();jQuery('input.error',$form).removeClass('error');if($form.data('validator')){$form.rup_validate('resetElements');}}}});/**
     * Sobreescrituras del componente jqGrid
     */$.extend($.jgrid,{createData:function createData(rowid,obj,tb,maxcols){/*ADD*/var $form=tb.parent();var $t=this,$self=$($t),settings=$self.data('settings'),nmId,nm,hc,trdata,cnt=0,tmp,dc,elc,retpos=[],ind=false,// 			tdtmpl = "<td class='CaptionTD'>&#160;</td><td class='DataTD'>&#160;</td>", tmpl="", i;
/*ADD*/tmpl='<label class=\'CaptionTD\'></label>',i;for(i=1;i<=maxcols;i++){tb.append($('<div>').attr('id','col_'+parseInt((parseInt(i,10)||1)*2,10)).addClass('floating_left_pad_right').width(100/maxcols*0.95+'%'));}if(rowid!='_empty'){ind=$(obj).jqGrid('getInd',rowid);}$(obj.p.colModel).each(function(i){nm=this.name;nmId=this.id;// hidden fields are included in the form
if(this.editrules&&this.editrules.edithidden===true){hc=false;}else{hc=this.hidden===true?true:false;}dc=hc?'style=\'display:none\'':'';if(nm!=='cb'&&nm!=='subgrid'&&this.editable===true&&nm!=='rn'){if(ind===false){tmp='';}else{if(nm==obj.p.ExpandColumn&&obj.p.treeGrid===true){tmp=$('td[role=\'gridcell\']:eq('+i+')',obj.rows[ind]).text();}else{try{tmp=$.unformat.call(obj,$('td[role=\'gridcell\']:eq('+i+')',obj.rows[ind]),{rowId:rowid,colModel:this},i);}catch(_){tmp=this.edittype&&this.edittype=='textarea'?$('td[role=\'gridcell\']:eq('+i+')',obj.rows[ind]).text():$('td[role=\'gridcell\']:eq('+i+')',obj.rows[ind]).html();}if(!tmp||tmp=='&nbsp;'||tmp=='&#160;'||tmp.length==1&&tmp.charCodeAt(0)==160){tmp='';}}}var opt=$.extend({},this.editoptions||{},{id:nmId,name:nm}),frmopt=$.extend({},{elmprefix:'',elmsuffix:'',rowabove:false,rowcontent:''},this.formoptions||{}),rp=parseInt(frmopt.rowpos,10)||cnt+1,cp=parseInt((parseInt(frmopt.colpos,10)||1)*2,10);if(rowid=='_empty'&&opt.defaultValue){tmp=$.isFunction(opt.defaultValue)?opt.defaultValue.call($t):opt.defaultValue;}if(!this.edittype){this.edittype='text';}if($t.p.autoencode){tmp=$.jgrid.htmlDecode(tmp);}elc=$.jgrid.createEl.call($t,this.edittype,opt,tmp,false,$.extend({},$.jgrid.ajaxOptions,obj.p.ajaxSelectOptions||{}));if(tmp===''&&this.edittype=='checkbox'){tmp=$(elc).attr('offval');}if(tmp===''&&this.edittype=='select'){tmp=$('option:eq(0)',elc).text();}/* MODIFICADO */if(this.edittype==='custom'){elc=$(elc).children()[0];}$(elc).addClass('FormElement');/* TODO : Permitir la personalización de los estilos de los campos de texto *///					if( $.inArray(this.edittype, ['text','textarea','password','select']) > -1) {
//						$(elc).addClass("ui-widget-content ui-corner-all");
//					}
trdata=$(tb).find('tr[rowpos='+rp+']');if(frmopt.rowabove){var newdata=$('<div><span class=\'contentinfo\'>'+frmopt.rowcontent+'</span></div>');$(tb).append(newdata);newdata[0].rp=rp;}if(trdata.length===0){/*MOD trdata = $("<tr "+dc+" rowpos='"+rp+"'></tr>").addClass("FormData").attr("id","tr_"+nm);*/trdata=$('<div '+dc+' rowpos=\''+rp+'\'></div>').addClass('FormData floating_left_pad_right one-column').attr('id','tr_'+nm);/*MOD END */$(trdata).append(tmpl);$(tb).find('#col_'+cp).append(trdata);trdata[0].rp=rp;}var $formField=$('label',trdata[0]).attr('for',nmId).html(typeof frmopt.label==='undefined'?obj.p.colNames[i]:frmopt.label);$formField.parent().append(frmopt.elmprefix).append(elc).append(frmopt.elmsuffix);retpos[cnt]=i;cnt++;}});if(cnt>0){/*MOD trdata var idrow = $("<tr class='FormData' style='display:none'><td class='CaptionTD'></td><td colspan='"+ (maxcols*2-1)+"' class='DataTD '><input class='FormElement' id='id_g' type='text' name='"+obj.p.id+"_id' value='"+rowid+"'/></td></tr>");*/var idrow=$('<div class=\'FormData\' style=\'display:none\'><span class=\'CaptionTD\'></span><span class=\'DataTD \'><input class=\'FormElement\' id=\'id_g\' type=\'text\' name=\''+obj.p.id+'_id\' value=\''+rowid+'\'/></span></div>');idrow[0].rp=cnt+999;$(tb).append(idrow);if(rp_ge[$t.p.id].checkOnSubmit||rp_ge[$t.p.id].checkOnUpdate){rp_ge[$t.p.id]._savedData[obj.p.id+'_id']=rowid;}}return retpos;},fillDataClientSide:function fillDataClientSide(rowid,obj,fmid,frmoper){var $t=this,$self=$($t),settings=$self.data('settings'),gID=$t.p.id,frmgr=$.fn.jqGrid.rup.edit.detail.detailFormId+gID,frmtborg=$.fn.jqGrid.rup.edit.detail.detailBodyId+gID,frmtb='#'+$.jgrid.jqID(frmtborg),nm,id,cnt=0,tmp,fld,opt,vl,vlc;if(rp_ge[$t.p.id].checkOnSubmit||rp_ge[$t.p.id].checkOnUpdate){rp_ge[$t.p.id]._savedData={};rp_ge[$t.p.id]._savedData[obj.p.id+'_id']=rowid;}var cm=obj.p.colModel;if(rowid=='_empty'){$self.rup_table('resetForm',settings.formEdit.$detailForm);$(cm).each(function(){nm=this.name;id=this.id!==undefined?this.id:nm;opt=$.extend({},this.editoptions||{});fld=$('#'+$.jgrid.jqID(id),settings.formEdit.$detailForm);if(fld.length===0){fld=$('[name=\''+id+'\']',settings.formEdit.$detailForm);}if(fld&&fld.length&&fld[0]!==null){vl='';if(opt.defaultValue){vl=$.isFunction(opt.defaultValue)?opt.defaultValue.call($t):opt.defaultValue;if(fld[0].type=='checkbox'||fld[0].type=='radio'){vlc=vl.toLowerCase();if(vlc.search(/(false|0|no|off|undefined)/i)<0&&vlc!==''){fld[0].checked=true;fld[0].defaultChecked=true;fld[0].value=vl;}else{fld[0].checked=false;fld[0].defaultChecked=false;}}else{fld.val(vl);}}else{if(fld[0].type=='checkbox'||fld[0].type=='radio'){fld[0].checked=false;fld[0].defaultChecked=false;vl=$(fld).attr('offval');}else if(fld[0].type&&fld[0].type.substr(0,6)=='select'){if(fld.attr('ruptype')==='combo'){fld.rup_combo('reset');}else{fld[0].selectedIndex=0;}}else{fld.val(vl);}}if(rp_ge[$t.p.id].checkOnSubmit===true||rp_ge[$t.p.id].checkOnUpdate){rp_ge[$t.p.id]._savedData[nm]=vl;}}});$('#id_g',settings.formEdit.$detailForm).val(rowid);return;}var tre=$(obj).jqGrid('getInd',rowid,true);if(!tre){return;}$('td[role="gridcell"]',tre).each(function(i){nm=cm[i].name;id=this.id!==undefined?this.id:nm;// hidden fields are included in the form
if(nm!=='cb'&&nm!=='subgrid'&&nm!=='rn'&&cm[i].editable===true){if(nm==obj.p.ExpandColumn&&obj.p.treeGrid===true){tmp=$(this).text();}else{try{tmp=$.unformat.call(obj,$(this),{rowId:rowid,colModel:cm[i]},i);}catch(_){tmp=cm[i].edittype=='textarea'?$(this).text():$(this).html();}}if($t.p.autoencode){tmp=$.jgrid.htmlDecode(tmp);}if(rp_ge[$t.p.id].checkOnSubmit===true||rp_ge[$t.p.id].checkOnUpdate){rp_ge[$t.p.id]._savedData[nm]=tmp;}nm=$.jgrid.jqID(nm);switch(cm[i].edittype){case'password':case'text':case'button':case'image':case'textarea':if(tmp=='&nbsp;'||tmp=='&#160;'||tmp.length==1&&tmp.charCodeAt(0)==160){tmp='';}$('#'+id,'#'+fmid).val(tmp);break;case'select':var opv=tmp.split(',');opv=$.map(opv,function(n){return $.trim(n);});$('#'+id+' option','#'+fmid).each(function(){if(!cm[i].editoptions.multiple&&($.trim(tmp)==$.trim($(this).text())||opv[0]==$.trim($(this).text())||opv[0]==$.trim($(this).val()))){this.selected=true;}else if(cm[i].editoptions.multiple){if($.inArray($.trim($(this).text()),opv)>-1||$.inArray($.trim($(this).val()),opv)>-1){this.selected=true;}else{this.selected=false;}}else{this.selected=false;}});break;case'checkbox':tmp=String(tmp);if(cm[i].editoptions&&cm[i].editoptions.value){var cb=cm[i].editoptions.value.split(':');if(cb[0]==tmp){$('#'+id,'#'+fmid)[$t.p.useProp?'prop':'attr']('checked',true);$('#'+id,'#'+fmid)[$t.p.useProp?'prop':'attr']('defaultChecked',true);//ie
}else{$('#'+id,'#'+fmid)[$t.p.useProp?'prop':'attr']('checked',false);$('#'+id,'#'+fmid)[$t.p.useProp?'prop':'attr']('defaultChecked',false);//ie
}}else{tmp=tmp.toLowerCase();if(tmp.search(/(false|0|no|off|undefined)/i)<0&&tmp!==''){$('#'+id,'#'+fmid)[$t.p.useProp?'prop':'attr']('checked',true);$('#'+id,'#'+fmid)[$t.p.useProp?'prop':'attr']('defaultChecked',true);//ie
}else{$('#'+id,'#'+fmid)[$t.p.useProp?'prop':'attr']('checked',false);$('#'+id,'#'+fmid)[$t.p.useProp?'prop':'attr']('defaultChecked',false);//ie
}}break;case'custom':try{if(cm[i].editoptions&&$.isFunction(cm[i].editoptions.custom_value)){cm[i].editoptions.custom_value.call($t,$('#'+id,'#'+fmid),'set',tmp);}else{throw'e1';}}catch(e){if(e=='e1'){$.jgrid.info_dialog($.jgrid.errors.errcap,'function \'custom_value\' '+$.jgrid.edit.msg.nodefined,$.jgrid.edit.bClose);}else{$.jgrid.info_dialog($.jgrid.errors.errcap,e.message,$.jgrid.edit.bClose);}}break;}cnt++;}});if(cnt>0){$('#id_g',frmtb).val(rowid);}},fillDataServerSide:function fillDataServerSide(rowid,$form,frmoper){var $t=this,$self=$($t),settings=$self.data('settings'),postdata={},$detailFormToPopulate=$form!==undefined?$form:settings.formEdit.$detailForm;if(rowid=='_empty'){$self.rup_table('resetForm',settings.formEdit.$detailForm);$.proxy($.jgrid.getFormData,$t)(postdata,{});rp_ge[$t.p.id]._savedData=$.rup_utils.unnestjson(postdata);if(frmoper!=='clone_clear'){$self.triggerHandler('jqGridAddEditAfterFillData',[$form,frmoper]);}$('#id_g',$form).val(rowid);return;}var ajaxOptions=$.extend({success:function success(xhr,ajaxOptions){var xhrArray;if(xhr.id&&xhr.id instanceof Object){//estamos en JPA
if(xhr.id instanceof Object){//es que estamos en jpa y traemos una clave compuesta
xhr['JPA_ID']=xhr.id;delete xhr.id;}}xhrArray=$.rup_utils.jsontoarray(xhr);$.rup_utils.populateForm(xhrArray,$detailFormToPopulate);rp_ge[$t.p.id]._savedData=$.rup_utils.unnestjson(xhr);rp_ge[$t.p.id]._savedData[settings.id+'_id']=rowid;$('#id_g',$form).val(rowid);$self.triggerHandler('rupTable_afterFormFillDataServerSide',[xhr,$detailFormToPopulate,ajaxOptions]);},error:function error(xhr,ajaxOptions,thrownError){settings.$feedback.rup_feedback('option','delay',null);settings.$feedback.rup_feedback('set',xhr.responseText,'error');settings.$feedback.rup_feedback('option','delay',1000);}},settings.formEdit.detailOptions.ajaxDetailOptions);ajaxOptions.url+='/'+$self.rup_table('getPkUrl',rowid);$.when($.rup_ajax(ajaxOptions)).then(function(success,statusText,xhr){$self.triggerHandler('jqGridAddEditAfterFillData',[$form,frmoper]);});},fillData:function fillData(rowid,obj,fmid,frmoper){var $t=this,$self=$($t),settings=$self.data('settings');//switch ((rowid == '_empty'?"clientSide":settings.formEdit.editOptions.fillDataMethod)){
switch(settings.formEdit.editOptions.fillDataMethod){case'clientSide':$.proxy($.jgrid.fillDataClientSide,$t)(rowid,obj,fmid,frmoper);break;case'serverSide':default:$.proxy($.jgrid.fillDataServerSide,$t)(rowid,settings.formEdit.$detailForm,frmoper);break;}},getFormData:function getFormData(postdata,extpost){var $t=this,$self=$(this),settings=$self.data('settings'),formParams;formParams=form2object(settings.formEdit.$detailForm[0],null,false);jQuery.extend(true,postdata,formParams);return true;},postIt:function postIt(postdata,extpost,frmoper){var $t=this,self=$t,$self=jQuery(self),settings=$self.data('settings'),gID=$t.p.id,frmgr=$.fn.jqGrid.rup.edit.detail.detailFormId+gID,frmtborg=$.fn.jqGrid.rup.edit.detail.detailBodyId+gID,frmtb='#'+$.jgrid.jqID(frmtborg),copydata,ret=[true,'',''],onCS={},opers=$t.p.prmNames,idname,oper,key,selr,i;var retvals=$($t).triggerHandler('jqGridAddEditBeforeCheckValues',[$('#'+frmgr),frmoper]);if(retvals&&(typeof retvals==="undefined"?"undefined":_typeof(retvals))==='object'){postdata=retvals;}if($.isFunction(rp_ge[$t.p.id].beforeCheckValues)){retvals=rp_ge[$t.p.id].beforeCheckValues.call($t,postdata,$('#'+frmgr),postdata[$t.p.id+'_id']=='_empty'?opers.addoper:opers.editoper);if(retvals&&(typeof retvals==="undefined"?"undefined":_typeof(retvals))==='object'){postdata=retvals;}}for(key in postdata){if(postdata.hasOwnProperty(key)){ret=$.jgrid.checkValues.call($t,postdata[key],key,$t);if(ret[0]===false){break;}}}$.proxy($.jgrid.setNulls,$t)();if(ret[0]){onCS=$($t).triggerHandler('jqGridAddEditClickSubmit',[rp_ge[$t.p.id],postdata,frmoper]);if(onCS===undefined&&$.isFunction(rp_ge[$t.p.id].onclickSubmit)){onCS=rp_ge[$t.p.id].onclickSubmit.call($t,rp_ge[$t.p.id],postdata)||{};}ret=$($t).triggerHandler('jqGridAddEditBeforeSubmit',[postdata,$('#'+frmgr),frmoper]);if(ret===undefined){ret=[true,'',''];}if(ret[0]&&$.isFunction(rp_ge[$t.p.id].beforeSubmit)){ret=rp_ge[$t.p.id].beforeSubmit.call($t,postdata,$('#'+frmgr));}}//			if(ret[0] && !rp_ge[$t.p.id].processing) {
if(ret[0]){rp_ge[$t.p.id].processing=true;$('#sData',frmtb+'_2').addClass('ui-state-active');oper=opers.oper;idname=opers.id;// we add to pos data array the action - the name is oper
postdata[oper]=$.trim(postdata[$t.p.id+'_id'])=='_empty'?opers.addoper:opers.editoper;if(postdata[oper]!=opers.addoper){postdata[idname]=postdata[$t.p.id+'_id'];}else{// check to see if we have allredy this field in the form and if yes lieve it
if(postdata[idname]===undefined){postdata[idname]=postdata[$t.p.id+'_id'];}}delete postdata[$t.p.id+'_id'];postdata=$.extend(postdata,rp_ge[$t.p.id].editData,onCS);if($t.p.treeGrid===true){if(postdata[oper]==opers.addoper){selr=$($t).jqGrid('getGridParam','selrow');var tr_par_id=$t.p.treeGridModel=='adjacency'?$t.p.treeReader.parent_id_field:'parent_id';postdata[tr_par_id]=selr;}for(i in $t.p.treeReader){if($t.p.treeReader.hasOwnProperty(i)){var itm=$t.p.treeReader[i];if(postdata.hasOwnProperty(itm)){if(postdata[oper]==opers.addoper&&i==='parent_id_field'){continue;}delete postdata[itm];}}}}postdata[idname]=$.jgrid.stripPref($t.p.idPrefix,postdata[idname]);var ajaxOptions=$.extend({url:rp_ge[$t.p.id].url||$($t).jqGrid('getGridParam','editurl'),type:rp_ge[$t.p.id].mtype,data:$.isFunction(rp_ge[$t.p.id].serializeEditData)?rp_ge[$t.p.id].serializeEditData.call($t,postdata):postdata,complete:function complete(data,status){var key,xhr;postdata[idname]=$t.p.idPrefix+postdata[idname];if(status!='success'){ret[0]=false;ret[1]=$($t).triggerHandler('jqGridAddEditErrorTextFormat',[data,frmoper]);if($.isFunction(rp_ge[$t.p.id].errorTextFormat)){ret[1]=rp_ge[$t.p.id].errorTextFormat.call($t,data);}else{ret[1]=status+' Status: \''+data.statusText+'\'. Error code: '+data.status;}}else{// data is posted successful
// execute aftersubmit with the returned data from server
ret=$($t).triggerHandler('jqGridAddEditAfterSubmit',[data,postdata,frmoper]);if(ret===undefined){ret=[true,'',''];}if(ret[0]&&$.isFunction(rp_ge[$t.p.id].afterSubmit)){ret=rp_ge[$t.p.id].afterSubmit.call($t,data,postdata);}}if(ret[0]===false){$('#'+settings.formEdit.feedbackId+'>td',frmtb).html(ret[1]);$('#'+settings.formEdit.feedbackId,frmtb).show();}else{// remove some values if formattaer select or checkbox
xhr=$.parseJSON(data.responseText);$.each($t.p.colModel,function(){if(extpost[this.name]&&this.formatter&&this.formatter=='select'){try{delete extpost[this.name];}catch(e){}}if(this.formatter=='checkbox'&&postdata[this.name]==undefined){postdata[this.name]=null;}if(this.formatter&&this.formatter!=='checkbox'&&this.formatter!=='select'){if(postdata[this.name]===undefined){postdata[this.name]=this.formatter.call($($t),ret[2],undefined,xhr,postdata[oper]);}}if(this.formatterOnUpdate){postdata[this.name]=this.formatterOnUpdate.call($($t),$('#'+frmgr));}if(this.updateFromDetail){postdata[this.name]=this.updateFromDetail.call($($t),$('#'+frmgr));}});postdata=$.extend(postdata,extpost);if($t.p.autoencode){$.each(postdata,function(n,v){postdata[n]=$.jgrid.htmlDecode(v);});}//rp_ge[$t.p.id].reloadAfterSubmit = rp_ge[$t.p.id].reloadAfterSubmit && $t.p.datatype != "local";
// the action is add
if(postdata[oper]==opers.addoper){//id processing
// user not set the id ret[2]
if(!ret[2]){ret[2]=$.jgrid.randId();}postdata[idname]=ret[2];if(rp_ge[$t.p.id].closeAfterAdd){if(rp_ge[$t.p.id].reloadAfterSubmit){$($t).trigger('reloadGrid');}else{if($t.p.treeGrid===true){$($t).jqGrid('addChildNode',ret[2],selr,postdata);}else{$($t).jqGrid('addRowData',ret[2],postdata,rp_ge[$t.p.id].addedrow);$($t).jqGrid('setSelection',ret[2]);}}$.jgrid.hideModal('#'+$.jgrid.jqID(IDs.themodal),{gb:'#gbox_'+$.jgrid.jqID(gID),jqm:rp_ge[$t.p.id].jqModal,onClose:rp_ge[$t.p.id].onClose});}else if(rp_ge[$t.p.id].clearAfterAdd){if(rp_ge[$t.p.id].reloadAfterSubmit){$($t).trigger('reloadGrid');}else{if($t.p.treeGrid===true){$($t).jqGrid('addChildNode',ret[2],selr,postdata);}else{$($t).jqGrid('addRowData',ret[2],postdata,rp_ge[$t.p.id].addedrow);// TODO : Añadido para que seleccione el registro insertado. Tratar de hacerlo en el evento jqGridAfterInsertRow
$($t).jqGrid('setSelection',ret[2]);}}$.proxy($.jgrid.fillData,$t)('_empty',$t,frmgr);}else{if(rp_ge[$t.p.id].reloadAfterSubmit){$($t).trigger('reloadGrid');}else{if($t.p.treeGrid===true){$($t).jqGrid('addChildNode',ret[2],selr,postdata);}else{$($t).jqGrid('addRowData',ret[2],postdata,rp_ge[$t.p.id].addedrow);}}}}else{// the action is update
if(rp_ge[$t.p.id].reloadAfterSubmit){$($t).trigger('reloadGrid');if(!rp_ge[$t.p.id].closeAfterEdit){setTimeout(function(){$($t).jqGrid('setSelection',postdata[idname]);},1000);}}else{if($t.p.treeGrid===true){$($t).jqGrid('setTreeRow',postdata[idname],postdata);}else{$($t).jqGrid('setRowData',postdata[idname],postdata);}}if(rp_ge[$t.p.id].closeAfterEdit){$.jgrid.hideModal('#'+$.jgrid.jqID(IDs.themodal),{gb:'#gbox_'+$.jgrid.jqID(gID),jqm:rp_ge[$t.p.id].jqModal,onClose:rp_ge[$t.p.id].onClose});}}if($.isFunction(rp_ge[$t.p.id].afterComplete)){copydata=data;setTimeout(function(){$($t).triggerHandler('jqGridAddEditAfterComplete',[copydata,postdata,$('#'+frmgr),frmoper]);rp_ge[$t.p.id].afterComplete.call($t,copydata,postdata,$('#'+frmgr));copydata=null;},500);}if(rp_ge[$t.p.id].checkOnSubmit||rp_ge[$t.p.id].checkOnUpdate){$('#'+frmgr).data('disabled',false);if(rp_ge[$t.p.id]._savedData[$t.p.id+'_id']!='_empty'){for(key in rp_ge[$t.p.id]._savedData){if(rp_ge[$t.p.id]._savedData.hasOwnProperty(key)&&postdata[key]){rp_ge[$t.p.id]._savedData[key]=postdata[key];}}}}}rp_ge[$t.p.id].processing=false;$('#sData',frmtb+'_2').removeClass('ui-state-active');try{$(':input:visible','#'+frmgr)[0].focus();}catch(e){}}},$.jgrid.ajaxOptions,rp_ge[$t.p.id].ajaxEditOptions);if(!ajaxOptions.url&&!rp_ge[$t.p.id].useDataProxy){if($.isFunction($t.p.dataProxy)){rp_ge[$t.p.id].useDataProxy=true;}else{ret[0]=false;ret[1]+=' '+$.jgrid.errors.nourl;}}if(ret[0]){if(rp_ge[$t.p.id].useDataProxy){var dpret=$t.p.dataProxy.call($t,ajaxOptions,'set_'+$t.p.id);if(dpret===undefined){dpret=[true,''];}if(dpret[0]===false){ret[0]=false;ret[1]=dpret[1]||'Error deleting the selected row!';}else{if(ajaxOptions.data.oper==opers.addoper&&rp_ge[$t.p.id].closeAfterAdd){$.jgrid.hideModal('#'+$.jgrid.jqID(IDs.themodal),{gb:'#gbox_'+$.jgrid.jqID(gID),jqm:rp_ge[$t.p.id].jqModal,onClose:rp_ge[$t.p.id].onClose});}if(ajaxOptions.data.oper==opers.editoper&&rp_ge[$t.p.id].closeAfterEdit){$.jgrid.hideModal('#'+$.jgrid.jqID(IDs.themodal),{gb:'#gbox_'+$.jgrid.jqID(gID),jqm:rp_ge[$t.p.id].jqModal,onClose:rp_ge[$t.p.id].onClose});}}}else{$.ajax(ajaxOptions);}}}if(ret[0]===false){$('#'+settings.formEdit.feedbackId+'>td',frmtb).html(ret[1]);$('#'+settings.formEdit.feedbackId,frmtb).show();// return;
}},setNulls:function setNulls(){var $t=this,postdata;$.each($t.p.colModel,function(i,n){if(n.editoptions&&n.editoptions.NullIfEmpty===true){if(postdata.hasOwnProperty(n.name)&&postdata[n.name]===''){postdata[n.name]='null';}}});},compareData:function compareData(nObj,oObj){var ret=false,key,unnestNObj=jQuery.rup_utils.unnestjson(nObj),unnestOObj=jQuery.rup_utils.unnestjson(oObj);for(key in unnestNObj){if(unnestNObj.hasOwnProperty(key)&&String(unnestNObj[key])!==String(unnestOObj[key])){ret=true;// Descomentar para debug
//					console.log(" Compare data: "+ key+ " new: "+String(unnestNObj[key]) + " old: "+String(unnestOObj[key]));
break;}}return ret;},checkUpdates:function checkUpdates(extpost,okCallback){var $self=$(this),settings=$self.data('settings'),postdata,newData,$t=this,gID=$t.p.id,frmgr=$.fn.jqGrid.rup.edit.detail.detailFormId+gID,frmtborg=$.fn.jqGrid.rup.edit.detail.detailBodyId+gID,frmtb='#'+$.jgrid.jqID(frmtborg),stat=true,diff=false;//			$("#"+settings.formEdit.feedbackId,frmtb).hide();
if(rp_ge[$t.p.id].checkOnUpdate){postdata={};extpost={};$.proxy($.jgrid.getFormData,$t)(postdata,extpost);newData=$.extend({},postdata,extpost);if(settings.formEdit.addEditOptions.defaultCompareData===true){diff=$.proxy($.jgrid.compareData,$t)(newData,rp_ge[$t.p.id]._savedData);}var compareDataEvent=jQuery.Event('rupTable_formEditCompareData');compareDataEvent.isDifferent=diff;$self.triggerHandler(compareDataEvent,[rp_ge[$t.p.id]._savedData,newData]);if(compareDataEvent.isDifferent){$.rup_messages('msgConfirm',{message:$.rup.i18nParse($.rup.i18n.base,'rup_table.saveAndContinue'),title:$.rup.i18nParse($.rup.i18n.base,'rup_table.changes'),OKFunction:function OKFunction(){if(jQuery.isFunction(okCallback)){jQuery.proxy(okCallback,$self)();}}});//					$("#"+frmgr).data("disabled",true);
//					$(".confirm","#"+IDs.themodal).show();
stat=false;}}return stat;},restoreInline:function restoreInline(rowid){var $t=this,i;if(rowid!=='_empty'&&typeof $t.p.savedRow!=='undefined'&&$t.p.savedRow.length>0&&$.isFunction($.fn.jqGrid.restoreRow)){for(i=0;i<$t.p.savedRow.length;i++){if($t.p.savedRow[i].id==rowid){$($t).jqGrid('restoreRow',rowid);break;}}}},getCurrPos:function getCurrPos(){var $t=this,$self=$(this),settings=$self.data('settings'),gID=$t.p.id,frmgr=$.fn.jqGrid.rup.edit.detail.detailFormId+gID,frmtborg=$.fn.jqGrid.rup.edit.detail.detailBodyId+gID,frmtb='#'+$.jgrid.jqID(frmtborg),rowsInGrid=$($t).jqGrid('getDataIDs'),idGval=$('#id_g',settings.formEdit.$detailForm).val(),selrow=idGval!==undefined&&idGval!=='_empty'?idGval:$self.jqGrid('getGridParam','selrow'),pos=$.inArray(selrow,rowsInGrid);return[pos,rowsInGrid];},updateNav:function updateNav(cr,posarr){var $self=$(this),totr;if(posarr!==undefined&&posarr[1]!==undefined){totr=posarr[1].length-1;if(cr===0){$('#pData',frmtb+'_2').addClass('ui-state-disabled');}else if(posarr[1][cr-1]!==undefined&&$('#'+$.jgrid.jqID(posarr[1][cr-1])).hasClass('ui-state-disabled')){$('#pData',frmtb+'_2').addClass('ui-state-disabled');}else{$('#pData',frmtb+'_2').removeClass('ui-state-disabled');}if(cr==totr){$('#nData',frmtb+'_2').addClass('ui-state-disabled');}else if(posarr[1][cr+1]!==undefined&&$('#'+$.jgrid.jqID(posarr[1][cr+1])).hasClass('ui-state-disabled')){$('#nData',frmtb+'_2').addClass('ui-state-disabled');}else{$('#nData',frmtb+'_2').removeClass('ui-state-disabled');}}$self.rup_table('updateDetailPagination');}});/*
     * MODIFICACIONES
     * Funciones extendidas (MODIFICADAS) del componente jqGrid.
     *
     * Los métodos aquí indicados han sido extendidos partiendo de la implementación original.
     * Las modificaciones han sido realizadas debido a la incompatibilidad de su implementación con los requisitos exigidos.
     *
     * Los métodos extendidos para su modificación son los siguientes:
     *
     * - editGridRow
     */$.jgrid.extend({editGridRow:function editGridRow(rowid,p){p=$.extend({top:0,left:0,width:300,height:'auto',dataheight:'auto',modal:false,overlay:30,drag:true,resize:true,url:null,mtype:'POST',clearAfterAdd:true,closeAfterEdit:false,reloadAfterSubmit:true,onInitializeForm:null,beforeInitData:null,beforeShowForm:null,afterShowForm:null,beforeSubmit:null,afterSubmit:null,onclickSubmit:null,afterComplete:null,onclickPgButtons:null,afterclickPgButtons:null,editData:{},recreateForm:false,jqModal:true,closeOnEscape:false,addedrow:'first',topinfo:'',bottominfo:'',saveicon:[],closeicon:[],savekey:[false,13],navkeys:[false,38,40],checkOnSubmit:false,checkOnUpdate:false,_savedData:{},processing:false,onClose:null,ajaxEditOptions:{},serializeEditData:null,viewPagerButtons:true},$.jgrid.edit,p||{});rp_ge[$(this)[0].p.id]=p;return this.each(function(){var $t=this,$self=$($t),settings=$self.data('settings');if(!$t.grid||!rowid){return;}var gID=$t.p.id,frmgr=$.fn.jqGrid.rup.edit.detail.detailFormId+gID,frmtborg=$.fn.jqGrid.rup.edit.detail.detailBodyId+gID,frmtb='#'+$.jgrid.jqID(frmtborg),IDs={themodal:$.fn.jqGrid.rup.edit.detail.detailDivId+gID,modalhead:'edithd'+gID,modalcontent:'editcnt'+gID,scrollelm:frmgr},onBeforeShow=$.isFunction(rp_ge[$t.p.id].beforeShowForm)?rp_ge[$t.p.id].beforeShowForm:false,onAfterShow=$.isFunction(rp_ge[$t.p.id].afterShowForm)?rp_ge[$t.p.id].afterShowForm:false,onBeforeInit=$.isFunction(rp_ge[$t.p.id].beforeInitData)?rp_ge[$t.p.id].beforeInitData:false,onInitializeForm=$.isFunction(rp_ge[$t.p.id].onInitializeForm)?rp_ge[$t.p.id].onInitializeForm:false,showFrm=true,maxCols=1,maxRows=0,postdata,extpost,newData,diff,frmoper;frmgr=$.jgrid.jqID(frmgr);if(rowid==='new'){rowid='_empty';frmoper='add';p.caption=rp_ge[$t.p.id].addCaption;}else if(rowid==='cloned'){p.caption=rp_ge[$t.p.id].addCaption;rowid='_empty';frmoper='clone_clear';}else{p.caption=rp_ge[$t.p.id].editCaption;frmoper='edit';}settings.opermode=frmoper;//				if(p.recreateForm===true && $("#"+$.jgrid.jqID(IDs.themodal))[0] !== undefined) {
//					$("#"+$.jgrid.jqID(IDs.themodal)).remove();
//				}
if(p.recreateForm===true&&settings.formEdit.detailFormCreated===true){settings.formEdit.$detailFormDiv.remove();}var closeovrl=true;if(p.checkOnUpdate&&p.jqModal&&!p.modal){closeovrl=false;}if(settings.formEdit.detailFormCreated===true){IDs.themodal=settings.formEdit.$detailFormDiv.attr('id');showFrm=$($t).triggerHandler('jqGridAddEditBeforeInitData',[settings.formEdit.$detailForm?settings.formEdit.$detailForm:$('#'+frmgr),frmoper]);if(showFrm===undefined){showFrm=true;}if(showFrm&&onBeforeInit){showFrm=onBeforeInit.call($t,settings.formEdit.$detailForm?settings.formEdit.$detailForm:$('#'+frmgr));}if(showFrm===false){return;}$.proxy($.jgrid.restoreInline,$t)(rowid);$('.ui-jqdialog-title','#'+$.jgrid.jqID(IDs.modalhead)).html(p.caption);$('#'+settings.formEdit.feedbackId,frmtb).hide();if(rp_ge[$t.p.id].topinfo){$('.topinfo',frmtb).html(rp_ge[$t.p.id].topinfo);$('.tinfo',frmtb).show();}else{$('.tinfo',frmtb).hide();}if(rp_ge[$t.p.id].bottominfo){$('.bottominfo',frmtb+'_2').html(rp_ge[$t.p.id].bottominfo);$('.binfo',frmtb+'_2').show();}else{$('.binfo',frmtb+'_2').hide();}$.proxy($.jgrid.fillData,$t)(rowid,$t,frmgr,frmoper);///
if(rowid=='_empty'||!rp_ge[$t.p.id].viewPagerButtons){$('#pData, #nData',frmtb+'_2').hide();}else{$('#pData, #nData',frmtb+'_2').show();}if(rp_ge[$t.p.id].processing===true){rp_ge[$t.p.id].processing=false;$('#sData',frmtb+'_2').removeClass('ui-state-active');}if((settings.formEdit.$detailForm?settings.formEdit.$detailForm:$('#'+frmgr)).data('disabled')===true){$('.confirm','#'+$.jgrid.jqID(IDs.themodal)).hide();(settings.formEdit.$detailForm?settings.formEdit.$detailForm:$('#'+frmgr)).data('disabled',false);}$($t).triggerHandler('jqGridAddEditBeforeShowForm',[settings.formEdit.$detailForm?settings.formEdit.$detailForm:$('#'+frmgr),frmoper]);if(onBeforeShow){onBeforeShow.call($t,settings.formEdit.$detailForm?settings.formEdit.$detailForm:$('#'+frmgr));}$('#'+$.jgrid.jqID(IDs.themodal)).data('onClose',rp_ge[$t.p.id].onClose);$.jgrid.viewModal('#'+$.jgrid.jqID(IDs.themodal),{gbox:'#gbox_'+$.jgrid.jqID(gID),jqm:p.jqModal,jqM:false,overlay:p.overlay,modal:p.modal});if(!closeovrl){$('.jqmOverlay').click(function(){if(!$.proxy($.jgrid.checkUpdates,$t)(extpost)){return false;}$.jgrid.hideModal('#'+$.jgrid.jqID(IDs.themodal),{gb:'#gbox_'+$.jgrid.jqID(gID),jqm:p.jqModal,onClose:rp_ge[$t.p.id].onClose});return false;});}$($t).triggerHandler('jqGridAddEditAfterShowForm',[settings.formEdit.$detailForm?settings.formEdit.$detailForm:$('#'+frmgr),frmoper]);if(onAfterShow){onAfterShow.call($t,settings.formEdit.$detailForm?settings.formEdit.$detailForm:$('#'+frmgr));}}else{var saveData=function saveData(){postdata={};extpost={};$('#'+settings.formEdit.feedbackId,frmtb).hide();// all depend on ret array
//ret[0] - succes
//ret[1] - msg if not succes
//ret[2] - the id  that will be set if reload after submit false
$.proxy($.jgrid.getFormData,$t)(postdata);if(postdata[$t.p.id+'_id']=='_empty'){$.proxy($.jgrid.postIt,$t)(postdata,extpost,settings.opermode);}else if(p.checkOnSubmit===true){newData=$.extend({},postdata,extpost);diff=compareData(newData,rp_ge[$t.p.id]._savedData);if(diff){$('#'+frmgr).data('disabled',true);$('.confirm','#'+$.jgrid.jqID(IDs.themodal)).show();}else{$.proxy($.jgrid.postIt,$t)(postdata,extpost,settings.opermode);}}else{$.proxy($.jgrid.postIt,$t)(postdata,extpost,settings.opermode);}return false;};var fncSaveButton=function fncSaveButton(){$self.data('tmp.formEditSaveType','SAVE');if(!saveData()){return false;}};var fncSaveAndRepeatButton=function fncSaveAndRepeatButton(){$self.data('tmp.formEditSaveType','SAVE_REPEAT');if(!saveData()){return false;}};var fncCancelLink=function fncCancelLink(){if(!$.proxy($.jgrid.checkUpdates,$t)(extpost,function(){$.jgrid.hideModal('#'+$.jgrid.jqID(IDs.themodal),{gb:'#gbox_'+$.jgrid.jqID(gID),jqm:p.jqModal,onClose:rp_ge[$t.p.id].onClose});})){return false;}$.jgrid.hideModal('#'+$.jgrid.jqID(IDs.themodal),{gb:'#gbox_'+$.jgrid.jqID(gID),jqm:p.jqModal,onClose:rp_ge[$t.p.id].onClose});return false;};var dh=isNaN(p.dataheight)?p.dataheight:p.dataheight+'px',dw=isNaN(p.datawidth)?p.datawidth:p.datawidth+'px',frm=$(jQuery.rup.i18nTemplate(jQuery.rup.i18n.base,'rup_table.templates.detailForm.form',frmgr,dh)).data('disabled',false),tbl=$(jQuery.rup.i18nTemplate(jQuery.rup.i18n.base,'rup_table.templates.detailForm.body',frmtborg)),showFrm=$($t).triggerHandler('jqGridAddEditBeforeInitData',[$('#'+frmgr),frmoper]),flr;if(typeof showFrm=='undefined'){showFrm=true;}if(showFrm&&onBeforeInit){showFrm=onBeforeInit.call($t,$('#'+frmgr));}if(showFrm===false){return;}$.proxy($.jgrid.restoreInline,$t)(rowid);$($t.p.colModel).each(function(){var fmto=this.formoptions;maxCols=Math.max(maxCols,fmto?fmto.colpos||0:0);maxRows=Math.max(maxRows,fmto?fmto.rowpos||0:0);});$(frm).append(tbl);flr=$(jQuery.rup.i18nTemplate(jQuery.rup.i18n.base,'rup_table.templates.detailForm.errorFeedback',settings.formEdit.feedbackId));flr[0].rp=0;$(tbl).append(flr);/* ADD	*/flr=$('<div class=\'tinfo\' style=\'display:none\'><span class=\'topinfo\'>'+rp_ge[$t.p.id].topinfo+'</span></div>');/*MOD END*/flr[0].rp=0;$(tbl).append(flr);// set the id.
// use carefull only to change here colproperties.
// create data
var rtlb=$t.p.direction=='rtl'?true:false,bp=rtlb?'nData':'pData',bn=rtlb?'pData':'nData';/* DEL				createData(rowid,$t,tbl,maxCols); */if(settings.formEdit.$detailForm===undefined){settings.formEdit.$detailForm=tbl.parent();$.proxy($.jgrid.createData,$t)(rowid,$t,tbl,maxCols);}else{settings.formEdit.$detailForm.append($('<div class=\'FormData\' style=\'display:none\'><span class=\'CaptionTD\'></span><span class=\'DataTD \'><input class=\'FormElement\' id=\'id_g\' type=\'text\' name=\''+$t.p.id+'_id\' value=\''+rowid+'\'/></span></div>'));}frm=settings.formEdit.$detailForm[0];$.proxy($.jgrid.fillData,$t)(rowid,$t,frmgr,frmoper);// buttons at footer
var bP='<a href=\'javascript:void(0)\' id=\''+bp+'\' class=\'fm-button ui-state-default ui-corner-left\'><span class=\'ui-icon ui-icon-triangle-1-w\'></span></a>',bN='<a href=\'javascript:void(0)\' id=\''+bn+'\' class=\'fm-button ui-state-default ui-corner-right\'><span class=\'ui-icon ui-icon-triangle-1-e\'></span></a>',bS='<a href=\'javascript:void(0)\' id=\'sData\' class=\'fm-button ui-state-default ui-corner-all\'>'+p.bSubmit+'</a>',bC='<a href=\'javascript:void(0)\' id=\'cData\' class=\'fm-button ui-state-default ui-corner-all\'>'+p.bCancel+'</a>';var bt='<table border=\'0\' cellspacing=\'0\' cellpadding=\'0\' class=\'EditTable\' id=\''+frmtborg+'_2\'><tbody><tr><td colspan=\'2\'><hr class=\'ui-widget-content\' style=\'margin:1px\'/></td></tr><tr id=\'Act_Buttons\'><td class=\'navButton\'>'+(rtlb?bN+bP:bP+bN)+'</td><td class=\'EditButton\'>'+bS+bC+'</td></tr>';bt+='<tr style=\'display:none\' class=\'binfo\'><td class=\'bottominfo\' colspan=\'2\'>'+rp_ge[$t.p.id].bottominfo+'</td></tr>';bt+='</tbody></table>';/*
                     * MODIFICADO POR UDA.
                     * Adaptar la ordenación a la nueva disposición mediante divs en vez de table.
                     */if(settings.formEdit.ownFormEdit===false){if(maxRows>0){for(var i=1;i<=maxCols;i++){// Por cada columna
var $colLayer=tbl.find('#col_'+parseInt((parseInt(i,10)||1)*2,10));var sd=[];$.each($colLayer.find('div'),function(i,r){sd[i]=r;});sd.sort(function(a,b){if(a.rp>b.rp){return 1;}if(a.rp<b.rp){return-1;}return 0;});$.each(sd,function(index,row){$colLayer.append(row);});}}}/*
                     * FIN MODIFICACION
                     */p.gbox='#gbox_'+$.jgrid.jqID(gID);var cle=false;if(p.closeOnEscape===true){p.closeOnEscape=false;cle=true;}/*
                     * MODIFICADO POR UDA
                     * Añadida barra de navegación entre elementos
                     */var barraNavegacion=$self.rup_table('createDetailNavigation'),tms;if(settings.formEdit.ownFormEdit===true){if(!settings.formEdit.$detailFormDiv.is(':visible')){settings.formEdit.$detailFormDiv.show();}/* TODO : Añadir los parametros de configruación que puedan añadirse al rup_dialog. */settings.formEdit.$detailFormDiv.rup_dialog($.extend({},{type:$.rup.dialog.DIV,autoOpen:false,modal:true,resizable:p.resize,title:p.caption,width:p.width},settings.formEdit.dialogOptions));settings.formEdit.detailFormCreated=true;settings.formEdit.$navigationBar.append(barraNavegacion);if(settings.formEdit.$saveButton.length>0){settings.formEdit.$saveButton.button().click(function(){jQuery.proxy(fncSaveButton,$self)();});}if(settings.formEdit.$saveRepeatButton.length>0){settings.formEdit.$saveRepeatButton.button().click(function(){jQuery.proxy(fncSaveAndRepeatButton,$self)();});}if(settings.formEdit.$cancelButton.length>0){settings.formEdit.$cancelButton.on('click',function(){jQuery.proxy(fncCancelLink,$self)();});}if(!jQuery.isFunction(p.onClose)){p.onClose=fncCancelLink;}jQuery('.ui-dialog-titlebar-close, a:has(#closeText_'+settings.formEdit.$detailFormDiv.first()[0].id+')',settings.formEdit.$detailFormDiv.parent()).off('click').on('click',function(event){p.onClose.call(event);});IDs.themodal=settings.formEdit.$detailFormDiv.attr('id');}else{var tms=barraNavegacion.after(frm);var saveButton={text:$.rup.i18nParse($.rup.i18n.base,'rup_global.save'),click:fncSaveButton};var saveAndRepeatButton={text:$.rup.i18nParse($.rup.i18n.base,'rup_global.save_repeat'),click:fncSaveAndRepeatButton};var cancelLink={text:$.rup.i18nParse($.rup.i18n.base,'rup_global.cancel'),btnType:$.rup.dialog.LINK,click:fncCancelLink};p.buttons=[saveButton,saveAndRepeatButton,cancelLink];p.onClose=fncCancelLink;$.jgrid.createModal(IDs,tms,p,'#gview_'+$.jgrid.jqID($t.p.id),$('#gbox_'+$.jgrid.jqID($t.p.id))[0]);settings.formEdit.detailFormCreated=true;}if(settings.formEdit.$detailFormDiv===undefined){settings.formEdit.$detailFormDiv=$('#'+$.jgrid.jqID(IDs.themodal));}/*
                     * Creacion rup_form
                     */if(rtlb){$('#pData, #nData',frmtb+'_2').css('float','right');$('.EditButton',frmtb+'_2').css('text-align','left');}if(rp_ge[$t.p.id].topinfo){$('.tinfo',frmtb).show();}if(rp_ge[$t.p.id].bottominfo){$('.binfo',frmtb+'_2').show();}tms=null;bt=null;$('#'+$.jgrid.jqID(IDs.themodal)).keydown(function(e){var wkey=e.target;if($('#'+frmgr).data('disabled')===true){return false;}//??
if(rp_ge[$t.p.id].savekey[0]===true&&e.which==rp_ge[$t.p.id].savekey[1]){// save
if(wkey.tagName!='TEXTAREA'){$('#sData',frmtb+'_2').trigger('click');return false;}}if(e.which===27){/* DEL 						if(!checkUpdates()) {return false;} *//* ADD */if(!$.proxy($.jgrid.checkUpdates,$t)(extpost)){return false;}if(cle){$.jgrid.hideModal('#'+$.jgrid.jqID(IDs.themodal),{gb:p.gbox,jqm:p.jqModal,onClose:rp_ge[$t.p.id].onClose});}return false;}if(rp_ge[$t.p.id].navkeys[0]===true){if($('#id_g',frmtb).val()=='_empty'){return true;}if(e.which==rp_ge[$t.p.id].navkeys[1]){//up
$('#pData',frmtb+'_2').trigger('click');return false;}if(e.which==rp_ge[$t.p.id].navkeys[2]){//down
$('#nData',frmtb+'_2').trigger('click');return false;}}});if(p.checkOnUpdate){$('a.ui-jqdialog-titlebar-close span','#'+$.jgrid.jqID(IDs.themodal)).removeClass('jqmClose');$('a.ui-jqdialog-titlebar-close','#'+$.jgrid.jqID(IDs.themodal)).unbind('click').click(function(){/* DEL 						if(!checkUpdates()) {return false;} *//* ADD */if(!$.proxy($.jgrid.checkUpdates,$t)(extpost)){return false;}$.jgrid.hideModal('#'+$.jgrid.jqID(IDs.themodal),{gb:'#gbox_'+$.jgrid.jqID(gID),jqm:p.jqModal,onClose:rp_ge[$t.p.id].onClose});return false;});}p.saveicon=$.extend([true,'left','ui-icon-disk'],p.saveicon);p.closeicon=$.extend([true,'left','ui-icon-close'],p.closeicon);// beforeinitdata after creation of the form
if(p.saveicon[0]===true){$('#sData',frmtb+'_2').addClass(p.saveicon[1]=='right'?'fm-button-icon-right':'fm-button-icon-left').append('<span class=\'ui-icon '+p.saveicon[2]+'\'></span>');}if(p.closeicon[0]===true){$('#cData',frmtb+'_2').addClass(p.closeicon[1]=='right'?'fm-button-icon-right':'fm-button-icon-left').append('<span class=\'ui-icon '+p.closeicon[2]+'\'></span>');}// here initform - only once
$($t).triggerHandler('jqGridAddEditInitializeForm',[settings.formEdit.$detailForm,frmoper]);if(onInitializeForm){onInitializeForm.call($t,settings.formEdit.$detailForm);}if(rowid=='_empty'||!rp_ge[$t.p.id].viewPagerButtons){$('#pData,#nData',frmtb+'_2').hide();}else{$('#pData,#nData',frmtb+'_2').show();}$($t).triggerHandler('jqGridAddEditBeforeShowForm',[settings.formEdit.$detailForm,frmoper]);if(onBeforeShow){onBeforeShow.call($t,settings.formEdit.$detailForm);}$('#'+$.jgrid.jqID(IDs.themodal)).data('onClose',rp_ge[$t.p.id].onClose);$.jgrid.viewModal('#'+$.jgrid.jqID(IDs.themodal),{gbox:'#gbox_'+$.jgrid.jqID(gID),jqm:p.jqModal,overlay:p.overlay,modal:p.modal});if(!closeovrl){$('.jqmOverlay').click(function(){/* DEL 						if(!checkUpdates()) {return false;} *//* ADD */if(!$.proxy($.jgrid.checkUpdates,$t)(extpost)){return false;}$.jgrid.hideModal('#'+$.jgrid.jqID(IDs.themodal),{gb:'#gbox_'+$.jgrid.jqID(gID),jqm:p.jqModal,onClose:rp_ge[$t.p.id].onClose});return false;});}$($t).triggerHandler('jqGridAddEditAfterShowForm',[settings.formEdit.$detailForm,frmoper]);if(onAfterShow){onAfterShow.call($t,settings.formEdit.$detailForm);}$('.fm-button','#'+$.jgrid.jqID(IDs.themodal)).hover(function(){$(this).addClass('ui-state-hover');},function(){$(this).removeClass('ui-state-hover');});}var posInit=$.proxy($.jgrid.getCurrPos,$t)();$self.rup_table('updateDetailPagination');$.proxy($.jgrid.updateNav,$t)(posInit[0],posInit[1].length-1);});}});$.fn.jqGrid.rup={};$.fn.jqGrid.rup.edit={detail:{detailDivId:'detailDiv_',detailBodyId:'detailBody_',detailFormId:'detailForm_'},navigation:{forward:{id:'#nData'},back:{id:'#pData'}}};//*******************************************************
// DEFINICIÓN DE LA CONFIGURACION POR DEFECTO DEL PATRON
//*******************************************************
/**
	* @description Propiedades de configuración del plugin formEdit del componente RUP Table.
	* @see Las posibles propiedades que se pueden indicar en cada una de las siguientes propiedades, se especifican con más detalle en la documentación del plugin subyacente jqGrid.
	* @name options
	*
	* @property {object} [addEditOptions] - Propiedades de configuración comunes a las acciones de edición e inserciónde un registro.
	* @property {object} [addOptions] - Propiedades de configuración exclusivas de la acción de inserción de un registro. Sobrescriben las indicadas en la propiedad addEditOptions.
	* @property {object} [editOptions] - Propiedades de configuración exclusivas de la acción de edición de un registro. Sobrescriben las indicadas en la propiedad addEditOptions.
	* @property {object} [deleteOptions] - Propiedades de configuración de la acción de borrado de un registro.
	* @property {object} [detailOptions] - Propiedades de configuración de la acción de mostrar un registro mediante el formulario de detalle.
	* @property {boolean} [defaultCompareData] - Determina si se debe de realizar la comparación por defecto en el control de cambios del formulario de edición. Por defecto a true.
	* @property {object} [dialogOptions] - Permite especificar opciones de configuración para el diálogo que contiene el formulario de detalle. Las opciones de configuración se pueden consultar en la guía de desarrollo del componente RUP Diálogo.
	*/jQuery.fn.rup_table.plugins.formEdit={};jQuery.fn.rup_table.plugins.formEdit.defaults={toolbar:{defaultButtons:{add:true,edit:true,cancel:false,save:false,clone:true,'delete':true,filter:false}},contextMenu:{defaultRowOperations:{add:true,edit:true,cancel:false,save:false,clone:true,'delete':true,filter:false}},formEdit:{autoselectFirstRecord:true,ownFormEdit:false,detailFormCreated:false,dialogOptions:{}}};// Parámetros de configuración por defecto para la acción de eliminar un registro.
jQuery.fn.rup_table.plugins.formEdit.defaults.formEdit.deleteOptions={bSubmit:jQuery.rup.i18nParse(jQuery.rup.i18n.base,'rup_message.aceptar'),cancelicon:[false,'left','icono_cancelar'],delicon:[false],linkStyleButtons:['#eData'],msg:'<div id="rup_msgDIV_msg_icon" class="rup-message_icon-confirm"></div><div id="rup_msgDIV_msg" class="rup-message_msg-confirm white-space-normal">'+jQuery.rup.i18nParse(jQuery.rup.i18n.base,'rup_table.deleteAll')+'</div>',mtype:'DELETE',width:320,reloadAfterSubmit:false,resize:false,useDataProxy:true};// Parámetros de configuración por defecto para la acción de añadir y editar un registro.
jQuery.fn.rup_table.plugins.formEdit.defaults.formEdit.addEditOptions={bSubmit:jQuery.rup.i18nParse(jQuery.rup.i18n.base,'rup_message.aceptar'),closeicon:[false],checkOnUpdate:true,defaultCompareData:true,fillDataMethod:'serverSide',// clientSide || serverSide
saveicon:[false],linkStyleButtons:['#cData'],msg:'<div id="rup_msgDIV_msg_icon" class="rup-message_icon-confirm"></div><div id="rup_msgDIV_msg" class="rup-message_msg-confirm white-space-normal">'+jQuery.rup.i18nParse(jQuery.rup.i18n.base,'rup_table.deleteAll')+'</div>',mtype:'PUT',reloadAfterSubmit:false,resize:false,viewPagerButtons:false,// TODO: no permitir el habilitarlo
width:569,ajaxEditOptions:{type:'PUT',dataType:'json',processData:false}};// Parámetros de configruación específicos para la acción de añadir un registro
jQuery.fn.rup_table.plugins.formEdit.defaults.formEdit.addOptions={mtype:'POST',ajaxEditOptions:{type:'POST'}};// Parámetros de configruación específicos para la acción de editar un registro
jQuery.fn.rup_table.plugins.formEdit.defaults.formEdit.editOptions={mtype:'PUT',ajaxEditOptions:{type:'PUT'}};// Parámetros de configuración por defecto para la obtención del detalle de un registro
jQuery.fn.rup_table.plugins.formEdit.defaults.formEdit.detailOptions={ajaxDetailOptions:{dataType:'json',type:'GET',async:false,contentType:'application/json'}};/* ********* *//* EVENTOS
  /* ********* *//**
	*  Evento que se lanza justo antes de procesarse la petición de borrado de un registro. En caso de devolver false se detiene la ejecución del borrado.
	*
	* @event module:rup_table#rupTable_beforeDeleteRow
	* @property {Event} event - Objeto Event correspondiente al evento disparado.
	* @property {object} deleteOptions - Opciones de configuración de la operación de borrado.
	* @property {string} selectedRow - Identificador de la fila que se desea eliminar.
	* @example
	* $("#idComponente").on("rupTable_beforeDeleteRow", function(event, deleteOptions, selectedRow){ });
	*//**
	*  Evento que se lanza justo antes de procesarse la petición de edición de un registro. En caso de devolver false se detiene la ejecución del borrado.
	*
	* @event module:rup_table#rupTable_beforeEditRow
	* @property {Event} event - Objeto Event correspondiente al evento disparado.
	* @property {object} editOptions - Opciones de configuración de la operación de edición.
	* @property {string} selectedRow - Identificador de la fila que se desea editar.
	* @example
	* $("#idComponente").on("rupTable_beforeEditRow", function(event, editOptions, selectedRow){ });
	*//**
	*  Evento que se lanza justo después de realizarse la petición de borrado de un registro.
	*
	* @event module:rup_table#rupTable_deleteAfterSubmit
	* @property {Event} event - Objeto Event correspondiente al evento disparado.
	* @example
	* $("#idComponente").on("rupTable_deleteAfterSubmit", function(event){ });
	*//**
	*  Evento lanzado antes de ejecutarse el método de inserción de un registro. En caso de retornar false se cancelará la inserción.
	*
	* @event module:rup_table#rupTable_beforeAddRow
	* @property {Event} event - Objeto Event correspondiente al evento disparado.
	* @property {object} addOptions -  Opciones de configuración de la acción de insertar un elemento.
	* @example
	* $("#idComponente").on("rupTable_beforeAddRow", function(event, addOptions){ });
	*//**
	*  Evento lanzado antes de ejecutarse el método de clonado de un registro. En caso de retornar false se cancelará el clonado.
	*
	* @event module:rup_table#rupTable_beforeCloneRow
	* @property {Event} event - Objeto Event correspondiente al evento disparado.
	* @property {object} cloneOptions - Opciones de configuración de la operación de clonado.
	* @property {string} selectedRow - Identificador de la fila que se desea clonar.
	* @example
	* $("#idComponente").on("rupTable_beforeCloneRow", function(event, cloneOptions, selectedRow){ });
	*//**
	*  Evento lanzado antes de ejecutarse el método de clonado de un registro. En caso de retornar false se cancelará el clonado.
	*
	* @event module:rup_table#rupTable_beforeCloneRow
	* @property {Event} event - Objeto Event correspondiente al evento disparado.
	* @property {object} cloneOptions - Opciones de configuración de la operación de clonado.
	* @property {string} selectedRow - Identificador de la fila que se desea clonar.
	* @example
	* $("#idComponente").on("rupTable_beforeCloneRow", function(event, cloneOptions, selectedRow){ });
	*//**
	*  Evento lanzado después de que ha finalizado correctamente el proceso de eliminar un registro..
	*
	* @event module:rup_table#rupTable_afterDeleteRow
	* @property {Event} event - Objeto Event correspondiente al evento disparado.
	* @example
	* $("#idComponente").on("rupTable_afterDeleteRow", function(event){ });
	*//**
	*  Evento lanzado después de que ha finalizado correctamente el proceso de carga de datos en el formulario de edición a partir de una petición al servidor de aplicaciones.
	*
	* @event module:rup_table#rupTable_afterFormFillDataServerSide
	* @property {Event} event - Objeto Event correspondiente al evento disparado.
	* @property {object} xhr - Objeto enviado como respuesta desde el servidor.
	* @property {object} $detailFormToPopulate - Referencia al formulario de detalle.
	* @property {object} ajaxOptions - Opciones de configuración de la petición AJAX.
	* @example
	* $("#idComponente").on("rupTable_afterFormFillDataServerSide", function(event, xhr, $detailFormToPopulate, ajaxOptions){ });
	*//**
	*  : Permite asociar manejadores de eventos para ejecutar
	código que indique al proceso de control de cambios si se han producido modificaciones o no.

	*
	* @event module:rup_table#rupTable_formEditCompareData
	* @property {Event} event - Objeto Event correspondiente al evento disparado.
	* @property {object} savedData - Objeto que contiene los valores iniciales del formulario a partir de la serialización del mismo.
	* @property {object} newData - Objeto que contiene los valores actuales del formulario a partir de la serialización del mismo.
	* @example
	* $("#idComponente").on("rupTable_formEditCompareData ", function(event,	savedData, newData){
	*		// Se realizan las comprobaciones necesarias para determinar si se han producido cambios en el formulario de detalle
	*		event.isDifferent = true; // En caso de que se hayan producido cambios.
	*  	event.isDifferent = false; // En caso de que no hayan producido cambios.
	* });
	*/})(jQuery);/*!
 * Copyright 2013 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 *//*global jQuery */(function($){/**
	 * Definición de los métodos principales que configuran la inicialización del plugin.
	 *
	 * preConfiguration: Método que se ejecuta antes de la invocación del componente jqGrid.
	 * postConfiguration: Método que se ejecuta después de la invocación del componente jqGrid.
	 *
	 *//**
	 * Permite la edición de los registros de la tabla mostrando los campos de edición sobre la propia línea del registro.
	 *
	 * @summary Plugin de edición en línea del componente RUP Table.
	 * @module rup_table/inlineEdit
	 * @example
	 *
	 * $("#idComponente").rup_table({
	 * 	url: "../jqGridUsuario",
	 * 	usePlugins:["inlineEdit"],
	 * 	inlineEdit:{
	 * 		// Propiedades de configuración del plugin inlineEdit
	 * 	}
	 * });
	 */jQuery.rup_table.registerPlugin('inlineEdit',{loadOrder:7,preConfiguration:function preConfiguration(settings){var $self=this;$self.rup_table('preConfigureInlineEdit',settings);},postConfiguration:function postConfiguration(settings){var $self=this;$self.rup_table('postConfigureInlineEdit',settings);}});/**
	 * Extensión del componente rup_table para permitir la edición en línea de los registros visualizados.
	 *
	 * Los métodos implementados son:
	 *
	 * configureInlineEdit(settings): Realiza la configuración interna necesaria para la gestión correcta de la edición en línea.
	 * editRow(rowId, options): Activa el modo edicón en línea para un registro determinado.
	 * saveRow(rowId, options): Realiza el guardado de un registo modificado mediante la edición en línea.
	 *
	 * Las propiedades de esta extensión almacenadas en el settings son las siguientes:
	 *
	 * settings.$inlineForm : Referencia al formulario utilizado para enviar los datos del registro que está siendo editado.
	 *
	 */jQuery.fn.rup_table('extend',{/**
		* Metodo que realiza la pre-configuración del plugin inlineEdit del componente RUP Table.
		* Este método se ejecuta antes de la incialización del plugin.
		*
		* @name preConfigureInlineEdit
		* @function
		* @param {object} settings - Parámetros de configuración del componente.
		*/preConfigureInlineEdit:function preConfigureInlineEdit(settings){var $self=$(this),self=$self[0],//				formId = "inlineForm_" + settings.id,
userBeforeSend;//				$inlineForm =$("<form>").attr({"id":"inlineForm_" + settings.id});
settings.editable=true;//			// Arropamos la estructura de la tabla en un formulario para poder realizar el envío de los campos
//			$self.wrap($inlineForm);
//			// Almacenamos la referencia al formulario.
//			settings.inlineEdit.$inlineForm = $("#"+formId);
if(settings.inlineEdit.addEditOptions.url===undefined){settings.inlineEdit.addEditOptions.url=settings.baseUrl;}settings.inlineEdit.deleteOptions.ajaxDelOptions=$.extend(true,settings.inlineEdit.deleteOptions.ajaxDelOptions,{success:function success(data,st,xhr){$self.triggerHandler('rupTableAfterDelete',[data,st,xhr]);$self.rup_table('showFeedback',settings.$feedback,$.rup.i18nParse($.rup.i18n.base,'rup_table.deletedOK'),'ok');}});/*
			 * Configuración del evetno beforeSend. Se sustituye el existente (en caso de haber)
			 * por el implementado a continuación. El objetivo es realizar la operación AJAX mediante
			 * el componente rup_formulario en vez del sistema por defecto del jqGrid.
			 *
			 * El método beforeSend indicado por el usuario se seguirá ejecutanto de manera normal.
			 */// Se almacena en una variable temporal el método beforeSend especificado por el usuario
userBeforeSend=settings.inlineEdit.beforeSend;settings.inlineEdit.addEditOptions.restoreAfterError=false;settings.inlineEdit.addEditOptions.errorfunc=function(rowid,data,stat,err,o){var responseJSON;if(data.status===406&&data.responseText!==''){try{responseJSON=jQuery.parseJSON(data.responseText);if(responseJSON.rupErrorFields){$self.rup_table('showServerValidationFieldErrors',settings.inlineEdit.$inlineForm,responseJSON);}}catch(e){// El mensaje JSON
$self.rup_table('showFeedback',settings.$feedback,data.responseText,'error');}}};settings.inlineEdit.addEditOptions.ajaxRowOptions.beforeSend=function(jqXHR,ajaxOptions){// Se añade la configuración de validaciones, la función userBeforeSend indicada por el usuario y el feedback utilizado por el componente.
jQuery.extend(true,ajaxOptions,{validate:settings.validate,beforeSend:jQuery.isFunction(userBeforeSend)?userBeforeSend:null,feedback:settings.$feedback});// Handler del evento rupValidate_formValidationError. Se lanza cuando se produce un error de validación en el formulario.
settings.inlineEdit.$inlineForm.on('rupValidate_formValidationError.inlineEditing',function(event,obj){$self.off('rupValidate_formValidationError.inlineEditing');// Se elimina la capa de bloqueo de la tabla.
$('#lui_'+$.jgrid.jqID(settings.id)).hide();});// Se realiza el envío del fomulario
settings.inlineEdit.$inlineForm.rup_form('ajaxSubmit',ajaxOptions);// Se retorna false para evitar que se realice la petición AJAX del plugin subyacente.
return false;};// Fuerza la configuración para que solo se pueda seleccionar mediante el checkbox
settings.multiboxonly=true;settings.getRowForEditing=function(){var $self=this,selrow=$self.jqGrid('getGridParam','selrow');return selrow===null?false:selrow;};/* DEFINICION DE OPERACIONES BASICAS CON LOS REGISTROS */settings.core.defaultOperations={'add':{name:$.rup.i18nParse($.rup.i18n.base,'rup_table.new'),icon:self._ADAPTER.CONST.core.operations.defaultOperations.add.icon,enabled:function enabled(){var $self=this;return jQuery('tr[editable=\'1\']',$self).length===0;},callback:function callback(key,options){var $self=this;$self.rup_table('addRow');}},'edit':{name:$.rup.i18nParse($.rup.i18n.base,'rup_table.modify'),icon:self._ADAPTER.CONST.core.operations.defaultOperations.edit.icon,enabled:function enabled(){var $self=this,selrow=$self.jqGrid('getGridParam','selrow'),newRow;// Existe una fila seleccionada?
selrow=selrow===null?false:selrow;selrow=selrow&&selrow.indexOf('jqg')===-1;// Existe una fila en modo nuevo?
newRow=jQuery('tr[editable=\'1\'].jqgrid-new-row',$self).length===0;return selrow&&newRow;},callback:function callback(key,options){$self.rup_table('editRow',jQuery.proxy(settings.getRowForEditing,$self)());}},'save':{name:$.rup.i18nParse($.rup.i18n.base,'rup_table.save'),icon:self._ADAPTER.CONST.core.operations.defaultOperations.save.icon,enabled:function enabled(){var $self=this;return jQuery('tr[editable=\'1\']',$self).length>0;},callback:function callback(object,event){if(event.type==='click'){$self.rup_table('saveRow');}}},'clone':{name:$.rup.i18nParse($.rup.i18n.base,'rup_table.clone'),icon:self._ADAPTER.CONST.core.operations.defaultOperations.clone.icon,enabled:function enabled(){var $self=this,selrow=$self.jqGrid('getGridParam','selrow'),newRow;// Existe una fila seleccionada?
selrow=selrow===null?false:selrow;selrow=selrow&&selrow.indexOf('jqg')===-1;// Existe una fila en modo nuevo?
newRow=jQuery('tr[editable=\'1\'].jqgrid-new-row',$self).length===0;return selrow&&newRow;//						if (settings.inlineEdit.autoEditRow===true){
//							return $self.rup_table("getSelectedRows").length === 1;
//						}else{
//							return $self.rup_table("getSelectedRows").length === 1 && jQuery("tr[editable='1']", $self).length===0;
//						}
},callback:function callback(key,options){if(jQuery('tr[editable=\'1\']',$self).length>0){$self.rup_table('restoreRow');}$self.rup_table('cloneRow');}},'cancel':{name:$.rup.i18nParse($.rup.i18n.base,'rup_table.cancel'),icon:self._ADAPTER.CONST.core.operations.defaultOperations.cancel.icon,enabled:function enabled(){var $self=this;return jQuery('tr[editable=\'1\']',$self).length>0;},callback:function callback(key,options){$self.rup_table('restoreRow');}},'delete':{name:$.rup.i18nParse($.rup.i18n.base,'rup_table.delete'),icon:self._ADAPTER.CONST.core.operations.defaultOperations['delete'].icon,enabled:function enabled(){var $self=this,selrow=$self.jqGrid('getGridParam','selrow');selrow=selrow===null||selrow.indexOf('jqg')!==-1?false:selrow;return jQuery('tr[editable=\'1\']:not(.jqgrid-new-row)',$self).length>0||selrow;},callback:function callback(key,options){$self.rup_table('deleteRow');}}};$.extend(true,settings.core.operations,settings.core.defaultOperations);// Configuración de edit/add
// Se procede a añadir sobre los settings de configuración los correspondientes a la edición en línea.
settings.inlineEdit.addOptions=$.extend(true,{},settings.inlineEdit.addEditOptions,settings.inlineEdit.addOptions);settings.inlineEdit.editOptions=$.extend(true,{},settings.inlineEdit.addEditOptions,settings.inlineEdit.editOptions);/* =======
			 * EVENTOS
			 * =======
			 */// Campturador del evento jqGridInlineAfterSaveRow.
$self.on({//				"jqGridAfterInsertRow.rupTable.inlineEditing": function(event, rowid, data, data){
//					jQuery($self.getInd(rowid, true)).attr("editmode","add");
//
//				},
'jqGridInlineErrorSaveRow.rupTable.inlineEditing':function jqGridInlineErrorSaveRowRupTableInlineEditing(event,rowid,data){jQuery($self.getInd(rowid,true)).attr('id',settings.inlineEditingRow);$self.rup_table('setSelection',settings.inlineEditingRow);},'jqGridInlineAfterSaveRow.rupTable.inlineEditing':function jqGridInlineAfterSaveRowRupTableInlineEditing(event,rowid,res,tmp,options){// Una vez introducida la fila se elimina el estilo jqgrid-new-row para evitar que se elimine al utilizar el cancelar sobre esa fila.
jQuery('#'+jQuery.jgrid.jqID(rowid)+'.jqgrid-new-row',$self).removeClass('jqgrid-new-row');// Una vez se haya realizado el guardado del registro se muestra el mensaje correspondiente en el feedback dependiendo del modo en el que se encuentra.
if(options.oper==='edit'){$self.rup_table('showFeedback',settings.$feedback,$.rup.i18nParse($.rup.i18n.base,'rup_table.modifyOK'),'ok');}else{$self.rup_table('showFeedback',settings.$feedback,$.rup.i18nParse($.rup.i18n.base,'rup_table.insertOK'),'ok');}},'jqGridInlineEditRow.rupTable.inlineEditing':function oneditfunc_default(event,rowId){var self=this,$self=$(self),settings=$self.data('settings'),colModel=self.p.colModel,ind=$self.jqGrid('getInd',rowId,true),cellColModel,colModelName,editOptions,$elem;// Se procesan las celdas editables
$('td[role=\'gridcell\']',ind).each(function(i){cellColModel=colModel[i];if(cellColModel.editable===true){colModelName=cellColModel.name;$elem=$('[name=\''+colModelName+'\']',ind);// Se añade el title de los elementos de acuerdo al colname
$elem.attr({'oldtitle':self.p.colNames[i],'class':'editable customelement'});// En caso de tratarse de un componente rup, se inicializa de acuerdo a la configuracón especificada en el colModel
if(cellColModel.rupType!==undefined){editOptions=cellColModel.editoptions;/*
								 * PRE Configuración de los componentes RUP
								 */switch(cellColModel.rupType){case'combo':editOptions=$.extend({menuWidth:$elem.width()},editOptions,{width:'100%'});break;}// Invocación al componente RUP
$elem['rup_'+cellColModel.rupType](editOptions);/*
								 * POST Configuración de los componentes RUP
								 */switch(cellColModel.rupType){case'date':// TODO: Aplicarlo con estilos
$elem.css('width','88%');break;}}}});settings.inlineEditingRow=rowId;function addNextRow(rowId,iCol){$self.on('jqGridInlineAfterSaveRow.inlineEditing.addNextRow',function(event){$self.rup_table('addRow');jQuery($self.getInd($self[0].p.selrow,true)).find(':not([readonly]):focusable:first').focus();$self.off('jqGridInlineAfterSaveRow.inlineEditing.addNextRow');});$self.rup_table('saveRow',rowId);return true;}function editNextRow(rowId,iCol){var idsArray,rowIndex,rowsPerPage,page,lastPage,$focusableElem;idsArray=$self.getDataIDs();rowIndex=$self.getInd(rowId)-1;rowsPerPage=parseInt($self.rup_table('getGridParam','rowNum'),10);if(rowIndex===rowsPerPage-1){// Cambio de página
page=parseInt($self.rup_table('getGridParam','page'),10);lastPage=parseInt(Math.ceil($self.rup_table('getGridParam','records')/$self.rup_table('getGridParam','rowNum')),10);if(page<lastPage){$self.trigger('reloadGrid',[{page:page+1}]);$self.on('jqGridAfterLoadComplete.rupTable.inlineEdit',function(event,data){idsArray=$self.getDataIDs();$self.on('jqGridInlineEditRow.rupTable.inlineEditing.tabKeyNav.cellSelected',function(event,rId){if(iCol===undefined||iCol===-1){$focusableElem=jQuery($self.jqGrid('getInd',rId,true)).find('td :not([readonly]):focusable:first');}else{$focusableElem=jQuery($self.jqGrid('getInd',rId,true)).find('td:eq('+iCol+') :not([readonly]):focusable:first');}$focusableElem.trigger('focus');$self.off('jqGridInlineEditRow.rupTable.inlineEditing.tabKeyNav.cellSelected');});jQuery($self.getInd(idsArray[0],true)).trigger('click');$self.off('jqGridAfterLoadComplete.rupTable.inlineEdit');});return false;}}else{$self.on('jqGridInlineEditRow.rupTable.inlineEditing.tabKeyNav.cellSelected',function(event,rId){if(iCol===undefined||iCol===-1){$focusableElem=jQuery($self.jqGrid('getInd',rId,true)).find('td :not([readonly]):focusable:first');}else{$focusableElem=jQuery($self.jqGrid('getInd',rId,true)).find('td:eq('+iCol+') :not([readonly]):focusable:first');}$focusableElem.trigger('focus');$self.off('jqGridInlineEditRow.rupTable.inlineEditing.tabKeyNav.cellSelected');});jQuery($self.getInd(idsArray[rowIndex+1],true)).trigger('click');return false;}return true;}function editPreviousRow(rowId,iCol){var idsArray,rowIndex,page,$focusableElem;idsArray=$self.getDataIDs();rowIndex=$self.getInd(rowId)-1;if(rowIndex===0){// Cambio de página
page=parseInt($self.rup_table('getGridParam','page'),10);if(page>1){$self.trigger('reloadGrid',[{page:page-1}]);$self.on('jqGridAfterLoadComplete.rupTable.inlineEdit',function(event,data){idsArray=$self.getDataIDs();$self.on('jqGridInlineEditRow.rupTable.inlineEditing.tabKeyNav.cellSelected',function(event,rId){if(iCol===undefined||iCol===-1){$focusableElem=jQuery($self.jqGrid('getInd',rId,true)).find('td :not([readonly]):focusable:last');}else{$focusableElem=jQuery($self.jqGrid('getInd',rId,true)).find('td:eq('+iCol+') :not([readonly]):focusable:last');}$focusableElem.trigger('focus');$self.off('jqGridInlineEditRow.rupTable.inlineEditing.tabKeyNav.cellSelected');});jQuery($self.getInd(idsArray[idsArray.length-1],true)).trigger('click');$self.off('jqGridAfterLoadComplete.rupTable.inlineEdit');});return false;}}else{$self.on('jqGridInlineEditRow.rupTable.inlineEditing.tabKeyNav.cellSelected',function(event,rId){if(iCol===undefined||iCol===-1){$focusableElem=jQuery($self.jqGrid('getInd',rId,true)).find('td :not([readonly]):focusable:last');}else{$focusableElem=jQuery($self.jqGrid('getInd',rId,true)).find('td:eq('+iCol+') :not([readonly]):focusable:last');}$focusableElem.trigger('focus');$self.off('jqGridInlineEditRow.rupTable.inlineEditing.tabKeyNav.cellSelected');});jQuery($self.getInd(idsArray[rowIndex-1],true)).trigger('click');return false;}}// Se almacena el contenido del los campos de la línea editable
// TODO: Externalizar la obtención de los datos para comprobar los cambios
$self.data('initialFormData',settings.inlineEdit.$inlineForm.rup_form('formSerialize'));// Se añaden los eventos de teclado
jQuery(ind).on({'keydown':function keydown(event){if(event.keyCode===27){$self.rup_table('restoreRow',$(this).attr('id'),settings.afterrestorefunc);return false;}if(event.keyCode===13){var ta=event.target;if(ta.tagName=='TEXTAREA'){return true;}$self.rup_table('saveRow');return false;}}});jQuery('td',jQuery(ind)).on({'keydown':function keydown(event){var iCol,nameArray;if(event.keyCode===38){nameArray=$.map($self.rup_table('getColModel'),function(elem,index){return elem.name;});iCol=jQuery.inArray($(this).attr('aria-describedby').split(settings.id+'_')[1],nameArray);editPreviousRow($(ind).attr('id'),iCol);return false;}if(event.keyCode===40){nameArray=$.map($self.rup_table('getColModel'),function(elem,index){return elem.name;});iCol=jQuery.inArray($(this).attr('aria-describedby').split(settings.id+'_')[1],nameArray);editNextRow($(ind).attr('id'),iCol);return false;}}});jQuery('input,select',jQuery(ind)).on({'focus':function focus(event){//							var $row = $(this).parent().parent();
//
//							settings.inlineEditingRow  = $row.attr("id");
//							$self.rup_table("setSelection",$row.attr("id"));
}});jQuery('input, textarea, select,a.rup_combo',jQuery(ind)).filter('.editable:visible:last').on({'keydown':function keydown(event){if(event.keyCode==9&&!event.shiftKey){if(jQuery(ind).attr('id').indexOf('jqg')!==-1){if(addNextRow(jQuery(ind).attr('id'))===false){return false;}}else{if(editNextRow(jQuery(ind).attr('id'))===false){return false;}}}}});jQuery('input, textarea, select,a.rup_combo',jQuery(ind)).filter('.editable:visible:first').on({'keydown':function keydown(event){var idsArray,rowIndex,page;if(event.keyCode==9){if(event.shiftKey){idsArray=$self.getDataIDs();rowIndex=$self.getInd(rowId)-1;if(rowIndex===0){// Cambio de página
page=parseInt($self.rup_table('getGridParam','page'),10);if(page>1){$self.trigger('reloadGrid',[{page:page-1}]);$self.on('jqGridAfterLoadComplete.rupTable.inlineEdit',function(event,data){idsArray=$self.getDataIDs();$self.on('jqGridInlineEditRow.rupTable.inlineEditing.tabKeyNav.cellSelected',function(event,rowId){jQuery($self.jqGrid('getInd',rowId,true)).find('td :focusable:last').trigger('focus');$self.off('jqGridInlineEditRow.rupTable.inlineEditing.tabKeyNav.cellSelected');});jQuery($self.getInd(idsArray[idsArray.length-1],true)).trigger('click');$self.off('jqGridAfterLoadComplete.rupTable.inlineEdit');});return false;}}else{$self.on('jqGridInlineEditRow.rupTable.inlineEditing.tabKeyNav.cellSelected',function(event,rowId){jQuery($self.jqGrid('getInd',rowId,true)).find('td :focusable:last').trigger('focus');$self.off('jqGridInlineEditRow.rupTable.inlineEditing.tabKeyNav.cellSelected');});jQuery($self.getInd(idsArray[rowIndex-1],true)).trigger('click');return false;}}}}});},'jqGridDblClickRow.rupTable.inlineEdit':function jqGridDblClickRowRupTableInlineEdit(rowid,iRow,iCol,e){if(!settings.inlineEdit.autoEditRow){$self.rup_table('editRow',iRow);}else{return false;}},'jqGridInlineAfterRestoreRow.inlineEditing.processRupObjects':function jqGridInlineAfterRestoreRowInlineEditingProcessRupObjects(event,rowid){var self=this,$self=$(this),json=self.p.savedRow[0];$self.rup_table('restoreInlineRupFields',rowid,json);},'rupTable_beforeSaveRow.inlineEditing.processRupObjects':function rupTable_beforeSaveRowInlineEditingProcessRupObjects(event,rowid,options){var self=this,$self=$(this),$row,$cell,ruptypeObj;$(self.p.colModel).each(function(i){$row=$(self.rows.namedItem(rowid));$cell=$row.find('td:eq('+i+')');ruptypeObj=$cell.find('[ruptype]:not([autocomplete])');if(ruptypeObj.attr('ruptype')==='combo'){if($self.data('rup.table.formatter')!==undefined){$self.data('rup.table.formatter')[rowid][this.name]['rup_'+ruptypeObj.attr('rupType')]={'label':ruptypeObj.rup_combo('label'),'value':ruptypeObj.rup_combo('getRupValue')};}}else if(ruptypeObj.attr('ruptype')==='autocomplete'&&ruptypeObj.attr('rup_autocomplete_label')){if($self.data('rup.table.formatter')!==undefined){$self.data('rup.table.formatter')[rowid][this.name]['rup_'+ruptypeObj.attr('rupType')]={'label':$('[id="'+ruptypeObj.attr('id')+'_label"]').val(),'value':ruptypeObj.rup_autocomplete('getRupValue')};}}});},'jqGridInlineSuccessSaveRow.rupTable.inlineEditing.processRupObjects':function jqGridInlineSuccessSaveRowRupTableInlineEditingProcessRupObjects(event,res,rowid,o){var json=jQuery.parseJSON(res.responseText),self=this,$self=$(self);$self.rup_table('restoreInlineRupFields',rowid,json);return[true,json,rowid];},'jqGridBeforeSelectRow.rupTable.inlineEditing':function jqGridBeforeSelectRowRupTableInlineEditing(event,rowid,obj){var $self=$(this),settings=$self.data('settings'),editableRows=$('tr[editable=1]',$self);/*
					 * Se comprueba si existen registros que estén siendo editados en línea.
					 * Del mismo modo se comprueba si el registro seleccionado es diferente del que se está editando en ese momento.
					 */if(editableRows.length>0&&settings.inlineEditingRow!==undefined&&settings.inlineEditingRow!==rowid){// Se comprueba si se han realizado cambios en el registro en edición
// TODO: Utilizar un método para comprobar los cambios en el formulario
if($self.data('initialFormData')!==settings.inlineEdit.$inlineForm.rup_form('formSerialize')){// En caso de que se hayan realizado cambios se debera de realizar el guardado de los mismos.
// Se confiura un handler para el evento jqGridInlineSuccessSaveRow que indica que se ha completado con exito el guardado del registro modificado.
$self.on('jqGridInlineSuccessSaveRow.inlineEditing_beforeSelectRow',function(event){// Una vez se haya realizado correctamente el guardado del registo se procede a seleccionar el registro solicitado por el usuario.
$self.rup_table('setSelection',rowid);// Se elimina el handler del evento para evitar duplicidades
$self.off('jqGridInlineSuccessSaveRow.inlineEditing_beforeSelectRow');});// Se procede a realizar el guardado de los registros editados
for(var i=0;i<editableRows.length;i++){$self.rup_table('saveRow',editableRows[0].id);}// Se retorna un false para deterner la selección del registro y permitir que se realice antes la gestión del guardado.
return false;}}// En caso de no necesitarse guardar el registro en edición se continúa con la gestión de la selección de manera normal.
return true;},'jqGridSelectRow.rupTable.inlineEditing':function jqGridSelectRowRupTableInlineEditing(event,rowid,status,obj){var $self=$(this),editableRows;editableRows=$('tr[editable=1]',$self);// En caso de que existan registros en modo edición se restauran
if(editableRows.length>0){jQuery.each($('tr[editable=1]',$self),function(index,elem){if($(elem).attr('id')!==rowid){$self.jqGrid('restoreRow',$(elem).attr('id'));}});}if(settings.inlineEdit.autoEditRow){// Se procede a entrar en modo edición en la línea seleccionada.
$self.rup_table('editRow',rowid);}},'rupTable_checkOutOfGrid.rupTable.inlineEditing':function rupTable_checkOutOfGridRupTableInlineEditing(event,$target){var $self=$(this),settings=$self.data('settings'),operationCfg=settings.core.defaultOperations['save'];if(jQuery.proxy(operationCfg.enabled,$self)()){jQuery.proxy(operationCfg.callback,$self)($self,event);}}});if(settings.inlineEdit.autoEditRow){$self.on({'jqGridCellSelect.rupTable.inlineEditing':function jqGridCellSelectRupTableInlineEditing(event,rowid,iCol,cellcontent,obj){var $self=$(this);if(iCol!==-1){$self.on('jqGridInlineEditRow.rupTable.inlineEditing.cellSelected',function(event,rowId){jQuery($self.jqGrid('getInd',rowid,true)).find('td:eq('+iCol+') :focusable:first').trigger('focus');$self.off('jqGridInlineEditRow.rupTable.inlineEditing.cellSelected');});}}});}},/**
	 * Metodo que realiza la post-configuración del plugin inlineEdit del componente RUP Table.
	 * Este método se ejecuta antes de la incialización del plugin.
	 *
	 * @name postConfigureInlineEdit
	 * @function
	 * @param {object} settings - Parámetros de configuración del componente.
	 */postConfigureInlineEdit:function postConfigureInlineEdit(settings){var $self=this,formId='inlineForm_'+settings.id,$inlineForm=$('<form>').attr({'id':'inlineForm_'+settings.id});// Arropamos la estructura de la tabla en un formulario para poder realizar el envío de los campos
$self.wrap($inlineForm);// Almacenamos la referencia al formulario.
settings.inlineEdit.$inlineForm=$('#'+formId);settings.inlineEdit.$inlineForm.on('rupValidate_formValidationError.inlineEditing',function(event,obj){var rowid=$self.jqGrid('getGridParam','selrow');jQuery($self.getInd(rowid,true)).attr('id',settings.inlineEditingRow);$self.rup_table('setSelection',settings.inlineEditingRow);});$self.on({'jqGridLoadComplete.rupTable.formEditing':function jqGridLoadCompleteRupTableFormEditing(data){var $self=$(this),settings=$self.data('settings'),nPos;if(settings.inlineEdit.autoselectFirstRecord){nPos=jQuery.proxy(jQuery.jgrid.getCurrPos,$self[0])();$self.rup_table('highlightRowAsSelected',jQuery($self.jqGrid('getInd',nPos[1][0],true)));}}});}});/**
	 * Métodos públicos del plugin inlineEdit.
	 *
	 * Los métodos implementados son:
	 *
	 * addRow(options): Muestra una nueva línea para inserción.
	 * editRow(rowId, options): Activa el modo edicón en línea para un registro determinado.
	 * deleteRow(rowId, options): Realiza el borrado de un registro.
	 * saveRow(rowId, options): Realiza el guardado de un registo modificado mediante la edición en línea.
	 * restoreRow(rowId): Restaura la línea indicada
	 *
	 * Las propiedades de esta extensión almacenadas en el settings son las siguientes:
	 *
	 * settings.$inlineForm : Referencia al formulario utilizado para enviar los datos del registro que está siendo editado.
	 *
	 */jQuery.fn.rup_table('extend',{/**
     * Añade una nueva línea en blanco al mantenimiento para permitir introducir los datos del nuevo registro.
     *
     * @function addRow
		 * @param {object} options - Opciones de configuración de la acción de inserción.
		 * @return {object} - Referencia jQuery a la propia tabla.
		 * @fires module:rup_table#rupTable_beforeAddRow
     * @example
     * $("#idTable").rup_table("addRow", options);
     */addRow:function addRow(options){var $self=this,settings=$self.data('settings'),colModel=$self[0].p.colModel;/*
			 * TODO: Ajustar el paso de parámetros
			 */var auxOptions={addRowParams:$.extend({},settings.inlineEdit.addOptions,options)};// Controlar los campos editables en modo nuevo
for(var i=0;i<colModel.length;i++){if(colModel[i].editable===true&&colModel[i].editableOnAdd!==false){if(colModel[i].editable===true&&colModel[i].editableOnAdd===false){if(colModel[i].editoptions===undefined){colModel[i].editoptions={};}colModel[i].editoptions.readonly='readonly';}else{if(colModel[i].editoptions!==undefined&&colModel[i].editoptions.readonly!==undefined){delete colModel[i].editoptions.readonly;}}}}if($self.triggerHandler('rupTable_beforeAddRow',[auxOptions])!==false){$self.jqGrid('addRow',$.extend({},auxOptions));}return $self;},/**
		 * Clona un registro determinado. Añade una nueva línea con el contenido del registro a partir del cual se desea clonar.
     *
     * @function cloneRow
		 * @param {string} rowId -  Identificador del registro a partir del cual se desea realizar el clonado.
		 * @param {object} options - Opciones de configuración de la acción de clonado.
		 * @return {object} - Referencia jQuery a la propia tabla.
		 * @fires module:rup_table#rupTable_beforeCloneRow
     * @example
     * $("#idTable").rup_table("cloneRow", rowId, options);
     */cloneRow:function cloneRow(rowId,options){var $self=this,settings=$self.data('settings'),selectedRow=rowId===undefined?$self.jqGrid('getGridParam','selrow'):rowId,colModel=$self[0].p.colModel,rowdata,clonedRowId;if($self.triggerHandler('rupTable_beforeCloneRow',[settings,rowId])!==false){rowdata=$self.jqGrid('getRowData',selectedRow);$self.rup_table('addRow');clonedRowId=jQuery('tbody:first tr[id*=\'jqg\']',$self).attr('id');$self.jqGrid('setRowData',clonedRowId,rowdata);jQuery($self.jqGrid('getInd',clonedRowId,true)).attr('editable','0');// Controlar los campos editables en modo nuevo
for(var i=0;i<colModel.length;i++){if(colModel[i].editable===true&&colModel[i].editableOnAdd!==false){if(colModel[i].editable===true&&colModel[i].editableOnAdd===false){if(colModel[i].editoptions===undefined){colModel[i].editoptions={};}colModel[i].editoptions.readonly='readonly';}else{if(colModel[i].editoptions!==undefined&&colModel[i].editoptions.readonly!==undefined){delete colModel[i].editoptions.readonly;}}}}$self.rup_table('editRow',clonedRowId,{},true);}},/**
     * Pone el registro indicado en modo edición para permitir la edición de sus datos.
     *
     * @function editRow
		 * @param {string} rowId - Identificador del registro que se desea editar.
		 * @param {object} options - Opciones de configuración de la acción de modificación.
		 * @return {object} - Referencia jQuery a la propia tabla.
		 * @fires module:rup_table#rupTable_beforeEditRow
     * @example
     * $("#idTable").rup_table("editRow", rowId, options, true);
     */editRow:function editRow(rowId,options,skipFieldCheck){var $self=this,settings=$self.data('settings'),selectedRow=rowId===undefined?$self.jqGrid('getGridParam','selrow'):rowId,colModel=$self[0].p.colModel;if(skipFieldCheck!==true){// Controlar los campos editables en modo edición
for(var i=0;i<colModel.length;i++){if(colModel[i].editable===true&&colModel[i].editableOnEdit===false){if(colModel[i].editoptions===undefined){colModel[i].editoptions={};}colModel[i].editoptions.readonly='readonly';}else{if(colModel[i].editoptions!==undefined&&colModel[i].editoptions.readonly!==undefined){delete colModel[i].editoptions.readonly;}}}}if($self.triggerHandler('rupTable_beforeEditRow',[settings.inlineEdit.editOptions,selectedRow])!==false){$self.jqGrid('editRow',selectedRow,$.extend({},settings.inlineEdit.editOptions,options));}return $self;},/**
     * Elimina el registro indicado.
     *
     * @function deleteRow
		 * @param {string} rowId - Identificador del registro que se desea eliminar.
		 * @param {object} options - Opciones de configuración de la acción de borrado..
		 * @return {object} - Referencia jQuery a la propia tabla.
		 * @fires module:rup_table#rupTable_deleteAfterSubmit
		 * @fires module:rup_table#rupTable_deleteAfterComplete
		 * @fires module:rup_table#rupTable_beforeDeleteRow
     * @example
     * $("#idTable").rup_table("deleteRow", rowId, options);
     */deleteRow:function deleteRow(rowId,options){var $self=this,settings=$self.data('settings'),//			deleteOptions = jQuery.extend(true, {}, jQuery.fn.rup_table.defaults.deleteOptions, options),
deleteOptions=jQuery.extend(true,{},settings.inlineEdit.deleteOptions,options),selectedRow=rowId===undefined?$self.rup_table('getSelectedRows'):rowId;// En caso de especificarse el uso del método HTTP DELETE, se anyade el identificador como PathParameter
if(selectedRow.length===1){if(deleteOptions.mtype==='DELETE'){deleteOptions.url=settings.baseUrl+'/'+$self.rup_table('getPkUrl',selectedRow);}}else{deleteOptions.mtype='POST';deleteOptions.ajaxDelOptions.contentType='application/json';deleteOptions.ajaxDelOptions.type='POST';deleteOptions.ajaxDelOptions.dataType='json';deleteOptions.url=settings.baseUrl+'/deleteAll';deleteOptions.serializeDelData=function(ts,postData){//					$self.rup_table("getFilterParams")
return jQuery.toJSON({'core':{'pkToken':settings.multiplePkToken,'pkNames':settings.primaryKey},'multiselection':$self.rup_table('getSelectedIds')});};}deleteOptions.afterSubmit=function(data,postd){$self.triggerHandler('rupTable_deleteAfterSubmit',[data,postd]);return[true];};deleteOptions.afterComplete=function(data,postd){$self.triggerHandler('rupTable_deleteAfterComplete',[data,postd]);};if($self.triggerHandler('rupTable_beforeDeleteRow',[deleteOptions,selectedRow])!==false){$self.jqGrid('delGridRow',selectedRow,deleteOptions);}return $self;},/**
     *  Guarda el registro modificado. Se almacenan los datos introducidos en la línea en modo edición.
     *
     * @function saveRow
		 * @param {string} rowId - Identificador del registro que se desea guardar.
		 * @param {object} options - Opciones de configuración de la acción de guardado..
		 * @return {object} - Referencia jQuery a la propia tabla.
		 * @fires module:rup_table#rupTable_beforeSaveRow
     * @example
     * $("#idTable").rup_table("saveRow", rowId, options);
     */saveRow:function saveRow(rowId,options){var $self=this,settings=$self.data('settings'),selectedRow=rowId===undefined?$self.jqGrid('getGridParam','selrow'):rowId;$self.triggerHandler('rupTable_beforeSaveRow',[selectedRow,options]);if(selectedRow.indexOf('jqg')!==-1){$self[0].p.ajaxRowOptions=settings.inlineEdit.addOptions.ajaxRowOptions;$self.jqGrid('saveRow',selectedRow,settings.inlineEdit.addOptions);}else{$self[0].p.ajaxRowOptions=settings.inlineEdit.editOptions.ajaxRowOptions;$self.jqGrid('saveRow',selectedRow,settings.inlineEdit.editOptions);}return $self;},/**
     * Restaura la fila indicada al estado anterior a habilitarse el modo edición.
     *
     * @function restoreRow
		 * @param {string} rowId - Identificador de la línea que se desea guardar.
		 * @param {function} afterrestorefunc - Función de callback que se ejecuta después de restaurar la fila.
		 * @return {object} - Referencia jQuery a la propia tabla.
		 * @fires module:rup_table#rupTable_beforeRestoreRow
     * @example
     * $("#idTable").rup_table("restoreRow", rowId, function(){});
     */restoreRow:function restoreRow(rowId,afterrestorefunc){var $self=this,rowToRestore=rowId===undefined?$self.jqGrid('getGridParam','selrow'):rowId;$self.triggerHandler('rupTable_beforeRestoreRow',[rowId]);$self.jqGrid('restoreRow',rowToRestore,afterrestorefunc);return $self;},/**
     * Restaura los campos RUP existentes en una fila de edición en línea.
     *
     * @function restoreRow
		 * @param {string} rowId - Identificador de la línea que se desea guardar.
		 * @return {object} - Referencia jQuery a la propia tabla.
     * @example
     * $("#idTable").rup_table("restoreRow", rowId, options);
     */restoreInlineRupFields:function restoreInlineRupFields(rowid){var $self=this,self=this[0],$row,$cell,val;$(self.p.colModel).each(function(i){$row=$(self.rows.namedItem(rowid));$tempRowId=$self.data('settings').inlineEditingRow;$cell=$row.find('td:eq('+i+')');//ruptypeObj = $cell.find("[ruptype]");
//				ruptypeObj = this.editoptions.ruptype;
if(this.rupType){if(this.rupType==='combo'){if($self.data('rup.table.formatter')!==undefined){val=$self.data('rup.table.formatter')[$tempRowId][this.name]['rup_'+this.rupType]['label'];$cell.html(val);}}else if(this.rupType==='autocomplete'){if($self.data('rup.table.formatter')!==undefined){val=$self.data('rup.table.formatter')[$tempRowId][this.name]['rup_'+this.rupType]['label'];$cell.html(val);}}}});return $self;}});//*******************************************************
// DEFINICIÓN DE LA CONFIGURACION POR DEFECTO DEL PATRON
//*******************************************************
/**
	 * Parametros de configuración de los settings para el caso particular de configuración del componente en el caso de funcionar en modo edición en linea.
	 *
	 * Los métodos para los que se proporciona una implementación son los siguientes.
	 *
	 * beforeSelectRow:
	 * onCellSelect:
	 * onSelectRow:
	 *//**
	* @description Propiedades de configuración del plugin inlineEdit del componente RUP Table.
	* @see Las posibles propiedades que se pueden indicar en cada una de las siguientes propiedades, se especifican con más detalle en la documentación del plugin subyacente jqGrid.
	* @name options
	*
	* @property {object} [addEditOptions] - Propiedades de configuración comunes a las acciones de edición e inserciónde un registro.
	* @property {object} [addOptions] - Propiedades de configuración exclusivas de la acción de inserción de un registro. Sobrescriben las indicadas en la propiedad addEditOptions.
	* @property {object} [editOptions] - Propiedades de configuración exclusivas de la acción de edición de un registro. Sobrescriben las indicadas en la propiedad addEditOptions.
	* @property {object} [deleteOptions] - Propiedades de configuración de la acción de borrado de un registro.
	*/jQuery.fn.rup_table.plugins.inlineEdit={};jQuery.fn.rup_table.plugins.inlineEdit.defaults={toolbar:{defaultButtons:{add:true,edit:true,cancel:true,save:true,clone:true,'delete':true,filter:false}},contextMenu:{defaultRowOperations:{add:true,edit:true,cancel:true,save:true,clone:true,'delete':true,filter:false}},inlineEdit:{autoselectFirstRecord:true,autoEditRow:false},formEdit:{}};// Parámetros de configruación comunes para las acciónes de añadir y editar un registro
jQuery.fn.rup_table.plugins.inlineEdit.defaults.inlineEdit.addEditOptions={contentType:'application/json',type:'PUT',dataType:'json',ajaxRowOptions:{contentType:'application/json',dataType:'json',processData:false}};// Parámetros de configruación específicos para la acción de añadir un registro
jQuery.fn.rup_table.plugins.inlineEdit.defaults.inlineEdit.addOptions={mtype:'POST',ajaxRowOptions:{type:'POST'}};// Parámetros de configruación específicos para la acción de editar un registro
jQuery.fn.rup_table.plugins.inlineEdit.defaults.inlineEdit.editOptions={mtype:'PUT',ajaxRowOptions:{type:'PUT'}};// Parámetros de configruación específicos para la acción de eliminar un registro
jQuery.fn.rup_table.plugins.inlineEdit.defaults.inlineEdit.deleteOptions={bSubmit:jQuery.rup.i18nParse(jQuery.rup.i18n.base,'rup_message.aceptar'),cancelicon:[false,'left','icono_cancelar'],delicon:[false],linkStyleButtons:['#eData'],msg:'<div id="rup_msgDIV_msg_icon" class="rup-message_icon-confirm"></div><div id="rup_msgDIV_msg" class="rup-message_msg-confirm white-space-normal">'+jQuery.rup.i18nParse(jQuery.rup.i18n.base,'rup_table.deleteAll')+'</div>',mtype:'DELETE',width:320,reloadAfterSubmit:false,resize:false};/**
	 * Extensión de las propiedades por defecto del jqGrid para el modo de edición en línea
	 */jQuery.jgrid.inlineEdit={keys:false};/* ********* *//* EVENTOS
  /* ********* *//**
	*  Evento que se lanza justo antes de procesarse la petición de borrado de un registro. En caso de devolver false se detiene la ejecución del borrado.
	*
	* @event module:rup_table#rupTable_beforeDeleteRow
	* @property {Event} event - Objeto Event correspondiente al evento disparado.
	* @property {object} deleteOptions - Opciones de configuración de la operación de borrado.
	* @property {string} selectedRow - Identificador de la fila que se desea eliminar.
	* @example
	* $("#idComponente").on("rupTable_beforeDeleteRow", function(event, deleteOptions, selectedRow){ });
	*//**
	*  Evento que se lanza justo antes de procesarse la petición de edición de un registro. En caso de devolver false se detiene la ejecución del borrado.
	*
	* @event module:rup_table#rupTable_beforeEditRow
	* @property {Event} event - Objeto Event correspondiente al evento disparado.
	* @property {object} editOptions - Opciones de configuración de la operación de edición.
	* @property {string} selectedRow - Identificador de la fila que se desea editar.
	* @example
	* $("#idComponente").on("rupTable_beforeEditRow", function(event, editOptions, selectedRow){ });
	*//**
	*  Evento que se lanza justo después de realizarse la petición de borrado de un registro.
	*
	* @event module:rup_table#rupTable_deleteAfterSubmit
	* @property {Event} event - Objeto Event correspondiente al evento disparado.
	* @example
	* $("#idComponente").on("rupTable_deleteAfterSubmit", function(event){ });
	*//**
	*  Evento lanzado antes de ejecutarse el método de inserción de un registro. En caso de retornar false se cancelará la inserción.
	*
	* @event module:rup_table#rupTable_beforeAddRow
	* @property {Event} event - Objeto Event correspondiente al evento disparado.
	* @property {object} addOptions -  Opciones de configuración de la acción de insertar un elemento.
	* @example
	* $("#idComponente").on("rupTable_beforeAddRow", function(event, addOptions){ });
	*//**
	*  Evento lanzado antes de ejecutarse el método de clonado de un registro. En caso de retornar false se cancelará el clonado.
	*
	* @event module:rup_table#rupTable_beforeCloneRow
	* @property {Event} event - Objeto Event correspondiente al evento disparado.
	* @property {object} cloneOptions - Opciones de configuración de la operación de clonado.
	* @property {string} selectedRow - Identificador de la fila que se desea clonar.
	* @example
	* $("#idComponente").on("rupTable_beforeCloneRow", function(event, cloneOptions, selectedRow){ });
	*/})(jQuery);/*!
 * Copyright 2013 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 *//*global jQuery *//**
 * Permite realizar una selección múltiple de los registros que se muestran en la tabla.
 *
 * @summary Plugin de multiselection del componente RUP Table.
 * @module rup_table/multiselection
 * @example
 *
 * $("#idComponente").rup_table({
 * 	url: "../jqGridUsuario",
 * 	usePlugins:["multiselection"],
 * 	multiselection:{
 * 		// Propiedades de configuración del plugin multiselection
 * 	}
 * });
 */(function($){/**
   * Definición de los métodos principales que configuran la inicialización del plugin.
   *
   * preConfiguration: Método que se ejecuta antes de la invocación del componente jqGrid.
   * postConfiguration: Método que se ejecuta después de la invocación del componente jqGrid.
   *
   */jQuery.rup_table.registerPlugin('multiselection',{loadOrder:8,preConfiguration:function preConfiguration(settings){var $self=this;$self.rup_table('preConfigureMultiselection',settings);},postConfiguration:function postConfiguration(settings){var $self=this;if(settings.multiselect===true){$self.rup_table('postConfigureMultiselection',settings);}}});//********************************
// DEFINICIÓN DE MÉTODOS PÚBLICOS
//********************************
/**
   * Extensión del componente rup_table para permitir la gestión de la multiselección.
   *
   * Los métodos implementados son:
   *
   * preConfigureMultiselection(settings): Método que define la preconfiguración necesaria para el correcto funcionamiento del componente.
   * postConfigureMultiselection(settings): Método que define la postconfiguración necesaria para el correcto funcionamiento del componente.
   *
   */jQuery.fn.rup_table('extend',{/**
		* Metodo que realiza la pre-configuración del plugin multiselection del componente RUP Table.
		* Este método se ejecuta antes de la incialización del plugin.
		*
		* @name preConfigureMultiselection
		* @function
		* @param {object} settings - Parámetros de configuración del componente.
		*/preConfigureMultiselection:function preConfigureMultiselection(settings){var $self=this;// Añadimos la columna por defecto para mostrar la información del registro en edición
//			settings.colNames = jQuery.merge([""], settings.colNames);
//			settings.colModel = jQuery.merge([settings.multiselection.defaultEditableInfoCol], settings.colModel);
// Se configura la propiedad multiselecta true para que el plugin subyacente se configure en modo multiseleccion
settings.multiselect=true;settings.multiselectWidth=40;//
//			settings.ondblClickRow=function(){
//				return false;
//			};
$.extend(true,settings.core.operations,{clone:{enabled:function enabled(){return settings.multiselection.numSelected===1;}}});settings.getActiveLineId=function(){var $self=this,settings=$self.data('settings'),npos=jQuery.proxy(jQuery.jgrid.getCurrPos,$self[0])();return jQuery.inArray(settings.multiselection.rowForEditing,npos[1]);};settings.getActiveRowId=function(){var $self=this,settings=$self.data('settings');return settings.multiselection.rowForEditing;};settings.getSelectedRows=function(){var $self=this,settings=$self.data('settings');if(settings.multiselection.selectedAll!==true){return settings.multiselection.selectedIds;}else{return settings.multiselection.deselectedIds;}};settings.getSelectedLines=function(){var $self=this,settings=$self.data('settings'),page=parseInt($self.rup_table('getGridParam','page'),10);if(settings.multiselection.selectedAll!==true){return settings.multiselection.selectedLinesPerPage[page];}else{return settings.multiselection.deselectedLinesPerPage[page];}};/*
       * Definición del método serializeGridData para que añada al postData la información relativa a la multiseleccion.
       */$self.on({'rupTable_serializeGridData.multiselection':function rupTable_serializeGridDataMultiselection(events,postData){var multiselectionObj={},tmpLastSearch;function getLastSearchStr(postData){return postData.rows+postData.sidx+postData.sord+postData.filter!==undefined?jQuery.param(jQuery.extend({},postData.filter,{rows:postData.rows,sidx:postData.sidx,sord:postData.sord})):'';}tmpLastSearch=$self.data('tmp.lastSearch');if(tmpLastSearch!==undefined&&tmpLastSearch!==getLastSearchStr(postData)){if(settings&&settings.multiselection&&settings.multiselection.numSelected>0){multiselectionObj=$self.rup_table('getSelectedIds');jQuery.extend(true,postData,{'multiselection':multiselectionObj});}}$self.data('tmp.lastSearch',getLastSearchStr(postData));},'rupTable_setSelection.multiselection':function rupTable_setSelectionMultiselection(events,selectedRows,status,reorderSelection){var page=parseInt($self.rup_table('getGridParam','page'),10);if(jQuery.isArray(selectedRows)){for(var i=0;i<selectedRows.length;i++){$self._processSelectedRow(settings,selectedRows[i],status);}}else{$self._processSelectedRow(settings,selectedRows,status);}// En caso de que se solicite la reordenación de los identificadores seleccionados
if(reorderSelection===true){$self.on('rupTable_serializeGridData.multiselection.reorderSelection',function(events,postData){$self.off('rupTable_serializeGridData.multiselection.reorderSelection');jQuery.extend(true,postData,{'multiselection':$self.rup_table('getSelectedIds')});});}$self.triggerHandler('rupTable_multiselectionUpdated');$self.triggerHandler('jqGridSelectRow.rupTable.multiselection',[selectedRows,status]);return false;}});},/**
		* Metodo que realiza la post-configuración del plugin multiselection del componente RUP Table.
		* Este método se ejecuta antes de la incialización del plugin.
		*
		* @name postConfigureMultiselection
		* @function
		* @param {object} settings - Parámetros de configuración del componente.
		*/postConfigureMultiselection:function postConfigureMultiselection(settings){var $self=this;// Inicialización de las propiedades asociadas a la gestión de los registros seleccionados
$self._initializeMultiselectionProps(settings);// Se almacena la referencia del check de (de)seleccionar todos los registros
settings.$selectAllCheck=jQuery('#cb_'+settings.id);settings.fncHasSelectedElements=function(){return settings.multiselection.numSelected>0;};settings.getRowForEditing=function(){var $self=this,settings=$self.data('settings'),page=parseInt($self.rup_table('getGridParam','page'),10),nPos=jQuery.proxy(jQuery.jgrid.getCurrPos,$self[0])(),index,retNavParams;if($self._hasPageSelectedElements(page)){if(settings.multiselection.rowForEditing!==undefined){return settings.multiselection.rowForEditing;}index=$self._getSelectedLinesOfPage(page)[0];return nPos[1][index-1];}else{retNavParams=jQuery.proxy(settings.fncGetNavigationParams,$self)('first');execute=retNavParams[1];newPage=retNavParams[5];newPageIndex=retNavParams[6];if(execute){$self.trigger('reloadGrid',[{page:newPage}]);$self.on('jqGridAfterLoadComplete.multiselection.editRow',function(event,data){var nextPagePos=jQuery.proxy(jQuery.jgrid.getCurrPos,$self[0])(),//newIndexPos = nextPagePos[1][$self._getSelectedLinesOfPage(newPage)[0]-1];
newIndexPos=$self.getActiveRowId();$self.jqGrid('editGridRow',newIndexPos,settings.editOptions);$self.off('jqGridAfterLoadComplete.multiselection.editRow');});}return false;}};settings.getDetailTotalRowCount=function(){var $self=this,settings=$self.data('settings');return settings.multiselection.numSelected;};settings.getDetailCurrentRowCount=function(){var $self=this,settings=$self.data('settings'),page=parseInt($self.rup_table('getGridParam','page'),10),currentRow=jQuery.proxy(jQuery.jgrid.getCurrPos,$self[0])(),rowsPerPage=parseInt($self.rup_table('getGridParam','rowNum'),10),selectedPagesArrayIndex,tmpSelectedPage,cont=0;// Comprobamos si se han seleccionado todos los registros de la tabla
if(!settings.multiselection.selectedAll){// En caso de que no se hayan seleccionado
// Se obtiene el indice de la página actual dentro del array de páginas deseleccionadas para
selectedPagesArrayIndex=jQuery.inArray(page,settings.multiselection.selectedPages);tmpSelectedPage=settings.multiselection.selectedPages[selectedPagesArrayIndex];for(var i=1;i<tmpSelectedPage;i++){if(settings.multiselection.selectedLinesPerPage[i]!==undefined){cont+=settings.multiselection.selectedLinesPerPage[i].length;}}cont+=jQuery.inArray(currentRow[0]+1,settings.multiselection.selectedLinesPerPage[tmpSelectedPage])+1;}else{cont=page>1?(page-1-settings.multiselection.deselectedPages.length)*rowsPerPage:0;for(var i=0;i<settings.multiselection.deselectedPages.length&&settings.multiselection.deselectedPages[i]!==page;i++){cont+=rowsPerPage-settings.multiselection.deselectedLinesPerPage[settings.multiselection.deselectedPages[i]].length;}cont+=jQuery.inArray(currentRow[0]+1,$self._getSelectedLinesOfPage(page))+1;}return cont;};settings.fncGetNavigationParams=function getNavigationParams_multiselection(linkType){var $self=this,settings=$self.data('settings'),execute=false,changePage=false,index=0,newPageIndex=0,npos=jQuery.proxy(jQuery.jgrid.getCurrPos,$self[0])(),page=parseInt($self.rup_table('getGridParam','page'),10),newPage=page,lastPage=parseInt(Math.ceil($self.rup_table('getGridParam','records')/$self.rup_table('getGridParam','rowNum')),10),currentArrayIndex,selectedLines;npos[0]=parseInt(npos[0],10);$('#'+settings.formEdit.feedbackId,settings.formEdit.$detailForm).hide();switch(linkType){case'first':// Navegar al primer elemento seleccionado
execute=true;// Si no se han seleccionado todos los elementos
if(!settings.multiselection.selectedAll){// Se comprueba si la página en la que nos encontramos es la primera en la que se han seleccionado registros
if(settings.multiselection.selectedPages[0]!==page){// Marcamos el flag changePage para indicar que se debe de realizar una paginación
changePage=true;// La nueva página será la primera página en la que se ha realizado una selección de registros
newPage=settings.multiselection.selectedPages[0];}}else{// En el caso de que se hayan seleccionado todos los elementos de la tabla
// Recorremos las páginas buscando la primera en la que existan elementos seleccionados
for(var pageAux=1;pageAux<=lastPage;pageAux++){if($self._hasPageSelectedElements(pageAux)){if(pageAux!==page){newPage=pageAux;changePage=true;}break;}}}// Recuperamos el primer registro seleccionado del la página
index=$self._getFirstSelectedElementOfPage(newPage);newPageIndex=index;break;case'prev':// Navegar al anterior elemento seleccionado
execute=true;// Obtenemos un array con los index de los registros seleccionados en la página actual
selectedLines=$self._getSelectedLinesOfPage(page);// Obtenemos la posición que ocupa el elemento actual en el array de seleccionados
currentArrayIndex=jQuery.inArray(npos[0]+1,selectedLines);// Se comprueba si ocupa el lugar del primer elemento seleccionado
if(currentArrayIndex===0){// En caso de tratarse del primer elemento seleccionado de la página, se deberá de realizar una navegación a la página anterior que disponga de elementos seleccionados
changePage=true;// Recorremos las páginas anteriores
for(var pageAux=page-1;pageAux>=0;pageAux--){// En caso de que la página disponga de elementos selecciondados.
if($self._hasPageSelectedElements(pageAux)){newPage=pageAux;// Obtenemos los identificadores de los registros seleccionados de la nueva página
selectedLines=$self._getSelectedLinesOfPage(pageAux);// Obtenemos el último registro seleccionado
index=selectedLines[selectedLines.length-1];break;}}}else{// En caso de no tratarse del último elemento de la página, recuperamos el elemento anterior que haya sido seleccionado también
index=selectedLines[currentArrayIndex-1];}newPageIndex=index;break;case'next':// Navegar al siguiente elemento seleccionado
execute=true;// Obtenemos un array con los index de los registros seleccionados en la página actual
selectedLines=$self._getSelectedLinesOfPage(page);// Obtenemos la posición que ocupa el elemento actual en el array de seleccionados
currentArrayIndex=jQuery.inArray(npos[0]+1,selectedLines);// Se comprueba si ocupa el lugar del último elemento seleccionado
if(currentArrayIndex===selectedLines.length-1){// En caso de tratarse del último elemento seleccionado de la página, se deberá de realizar una navegación a la página siguiente que disponga de elementos seleccionados
changePage=true;// Recorremos las páginas siguientes
for(var pageAux=page+1;pageAux<=lastPage;pageAux++){// En caso de que la página disponga de elementos selecciondados.
if($self._hasPageSelectedElements(pageAux)){newPage=pageAux;// Obtenemos los identificadores de los registros seleccionados de la nueva página
selectedLines=$self._getSelectedLinesOfPage(pageAux);// Obtenemos el primer registro seleccionado
index=selectedLines[0];break;}}}else{// En caso de no tratarse del último elemento de la página, recuperamos el elemento anterior que haya sido seleccionado también
index=selectedLines[currentArrayIndex+1];}newPageIndex=index;break;case'last':// Navegar al ultimo elemento seleccionado
execute=true;// Si no se han seleccionado todos los elementos
if(!settings.multiselection.selectedAll){// Se comprueba si la página en la que nos encontramos es la primera en la que se han seleccionado registros
if(settings.multiselection.selectedPages[settings.multiselection.selectedPages.length-1]!==page){// Marcamos el flag changePage para indicar que se debe de realizar una paginación
changePage=true;// La nueva página será la primera página en la que se ha realizado una selección de registros
newPage=settings.multiselection.selectedPages[settings.multiselection.selectedPages.length-1];}}else{// En el caso de que se hayan seleccionado todos los elementos de la tabla
// Recorremos las páginas buscando la primera en la que existan elementos seleccionados
for(var pageAux=lastPage;pageAux>0;pageAux--){if($self._hasPageSelectedElements(pageAux)){if(pageAux!==page){newPage=pageAux;changePage=true;}break;}}}selectedLines=$self._getSelectedLinesOfPage(newPage);// Recuperamos el último registro seleccionado del la página
index=selectedLines[selectedLines.length-1];newPageIndex=index;}return[linkType,execute,changePage,index-1,npos,newPage,newPageIndex-1];};settings.doNavigation=function(arrParams,execute,changePage,index,npos,newPage,newPageIndex){var $self=this,settings=$self.data('settings'),props=rp_ge[$self.attr('id')],linkType,execute,changePage,index,npos,newPage,newPageIndex,fncAfterclickPgButtons;if(jQuery.isArray(arrParams)){linkType=arrParams[0];execute=arrParams[1];changePage=arrParams[2];index=arrParams[3];npos=arrParams[4];newPage=arrParams[5];newPageIndex=arrParams[6];if(execute){$self.rup_table('hideFormErrors',settings.formEdit.$detailForm);$self.triggerHandler('jqGridAddEditClickPgButtons',[linkType,settings.formEdit.$detailForm,npos[1][npos[index]]]);if(changePage){$self.trigger('reloadGrid',[{page:newPage}]);$self.on('jqGridAfterLoadComplete.pagination',function(event,data){var nextPagePos=jQuery.proxy(jQuery.jgrid.getCurrPos,$self[0])(),newIndexPos=nextPagePos[1][newPageIndex];//								$self.jqGrid("setSelection", nextPagePos[1][newIndexPos]);
jQuery.proxy(jQuery.jgrid.fillData,$self[0])(newIndexPos,$self[0],settings.formEdit.$detailForm.attr('id'),settings.opermode);jQuery.proxy(jQuery.jgrid.updateNav,$self[0])();//								$self.find("td[aria-describedby='"+settings.id+"_infoEditable'] img.ui-icon.ui-icon-pencil").remove();
settings.multiselection.rowForEditing=newIndexPos;$self.rup_table('clearHighlightedEditableRows');$self.rup_table('highlightEditableRow',$self.jqGrid('getInd',newIndexPos,true));//								$($self.jqGrid("getInd",newIndexPos, true)).find("td[aria-describedby='"+settings.id+"_infoEditable']").html($("<img/>").addClass("ui-icon ui-icon-pencil")[0]);
$self.off('jqGridAfterLoadComplete.pagination');});}else{jQuery.proxy(jQuery.jgrid.fillData,$self[0])(npos[1][index],$self[0],settings.formEdit.$detailForm.attr('id'),settings.opermode);//							$self.jqGrid("setSelection", npos[1][index]);
jQuery.proxy(jQuery.jgrid.updateNav,$self[0])();//							$self.find("td[aria-describedby='"+settings.id+"_infoEditable'] img.ui-icon.ui-icon-pencil").remove();
settings.multiselection.rowForEditing=npos[1][index];$self.rup_table('clearHighlightedEditableRows');$self.rup_table('highlightEditableRow',$self.jqGrid('getInd',npos[1][index],true));//							$($self.jqGrid("getInd",npos[1][index], true)).find("td[aria-describedby='"+settings.id+"_infoEditable']").html($("<img/>").addClass("ui-icon ui-icon-pencil")[0]);
}$self.triggerHandler('jqGridAddEditAfterClickPgButtons',[linkType,settings.formEdit.$detailForm,npos[1][npos[index]]]);fncAfterclickPgButtons=props!==undefined?props.afterclickPgButtons:settings.afterclickPgButtons;if(jQuery.isFunction(fncAfterclickPgButtons)){props.fncAfterclickPgButtons.call($self,linkType,settings.formEdit.$detailForm,npos[1][npos[index]]);}}}};// Configuracion de los handler de los eventos
$self.on({/*
         * Capturador del evento jqGridSelectRow.
         * Se ejecuta cuando se selecciona una fila.
         * Realiza la gestión interna sobre la acción de (de)selección del usuario.
         *
         * 	event: Objeto event.
         * 	id: Identificador de la línea.
         *  status: true en caso de selección, false en caso de deselección.
         *  obj: Objeto interno del jqGrid.
         */'jqGridSelectRow.rupTable.multiselection':function jqGridSelectRowRupTableMultiselection(event,id,status,obj){var page,firstSelectedId,firstSelectedLine,activeLineId,selectedLineId,toLine,fromLine,idsArr;if(obj!==false){if(obj!==undefined&&jQuery(obj.target).hasClass('treeclick')){return false;}if(jQuery.rup.isCtrlPressed()===true||jQuery.rup.isShiftPressed()===true){window.getSelection().removeAllRanges();}if(!(jQuery.rup.isCtrlPressed()||jQuery.rup.isShiftPressed())&&settings.multiboxonly===true&&obj!==undefined&&!(obj.originalEvent!==undefined&&jQuery(obj.originalEvent.target).is(':checkbox')&&jQuery(obj.originalEvent.target).attr('id').indexOf('jqg_')!==-1)){$self.rup_table('deselectRemainingRows');}// Shift presed
if(jQuery.rup.isShiftPressed()===true){selectedLineId=$self.jqGrid('getInd',id,false);activeLineId=$self.rup_table('getActiveLineId');if(activeLineId<selectedLineId){toLine=selectedLineId-1;fromLine=activeLineId+1;}else{toLine=activeLineId;fromLine=selectedLineId;}idsArr=$self.jqGrid('getDataIDs');for(var i=fromLine;i<toLine;i++){$self._processSelectedRow(settings,idsArr[i],status);$self.rup_table('highlightRowAsSelected',jQuery($self.jqGrid('getInd',idsArr[i],true)));}}// Se gestiona la selección o deselección del registro indicado
$self._processSelectedRow(settings,id,status);// Actualización del número de registros seleccionados
$self.rup_table('updateSelectedRowNumber');// Se cierra el feedback para (de)seleccionar el resto de registros
$self.trigger('rupTable_feedbackClose',settings.$internalFeedback);// Se gestiona el icono de linea editable
$self.rup_table('clearHighlightedEditableRows');//						$self.find("td[aria-describedby='"+settings.id+"_infoEditable'] img.ui-icon.ui-icon-pencil").remove();
if(status){settings.multiselection.rowForEditing=id;$self.rup_table('highlightEditableRow',$self.jqGrid('getInd',id,true));//							$($self.jqGrid("getInd",id, true)).find("td[aria-describedby='"+settings.id+"_infoEditable']").html($("<img/>").addClass("ui-icon ui-icon-pencil")[0]);
}else{page=parseInt($self.rup_table('getGridParam','page'),10);if($self._hasPageSelectedElements(page)){$self.rup_table('highlightFirstEditableRow');//								firstSelectedLine = $self._getFirstSelectedElementOfPage(page);
//								firstSelectedId = $self.jqGrid("getDataIDs")[firstSelectedLine-1];
//								settings.multiselection.rowForEditing=firstSelectedId;
//								$self.rup_table("highlightEditableRow", $self.jqGrid("getInd",firstSelectedId, true));
}}}},'jqGridDblClickRow.rupTable.multiselection':function jqGridDblClickRowRupTableMultiselection(event,rowid,iRow,iCol,e){$self.rup_table('setSelection',rowid,true);$self.rup_table('clearHighlightedEditableRows');$self.rup_table('highlightEditableRow',$self.jqGrid('getInd',rowid,true));},'jqGridGridComplete.rup_table.multiselection':function jqGridGridCompleteRup_tableMultiselection(event){var $self=$(this),settings=$self.data('settings');if($self.rup_table('getGridParam','records')===0){jQuery(jQuery('#cb_'+$self.attr('id'),settings.core.$tableDiv)[0]).attr('disabled','disabled');}else{jQuery(jQuery('#cb_'+$self.attr('id'),settings.core.$tableDiv)[0]).removeAttr('disabled');}},/*
         * Capturador del evento jqGridLoadComplete.
         * Se ejecuta una vez se haya completado la carga de la tabla.
         *
         * 	data: Objeto que contiene la carga de la tabla.
         *
         */'jqGridLoadComplete.rupTable.multiselection':function jqGridLoadCompleteRupTableMultiselection(data,xhr){var self=$self[0],internalProps=self.p,page=$self.rup_table('getGridParam','page'),rowNum=$self.rup_table('getGridParam','rowNum'),rows,selectedRows=settings.multiselection.selectedRowsPerPage[page],deselectedRows=settings.multiselection.deselectedRowsPerPage[page]||[],reorderedRow,reorderedRowPage,reorderedRowLine,reorderedRowId,arrayAuxRowsPerPage,arrayAuxLinesPerPage,arrayAuxIds,arrayAuxRows,arrayAuxPages,firstSelectedLine,firstSelectedId,indexAux,idAux;/*
           * REORDENAR LA SELECCION
           */if(xhr.reorderedSelection!==undefined&&xhr.reorderedSelection!==null){$self._initializeMultiselectionProps(settings);settings.multiselection.selectedAll=xhr.selectedAll;if(settings.multiselection.selectedAll===true){arrayAuxRowsPerPage=settings.multiselection.deselectedRowsPerPage;arrayAuxLinesPerPage=settings.multiselection.deselectedLinesPerPage;arrayAuxIds=settings.multiselection.deselectedIds;arrayAuxRows=settings.multiselection.deselectedRows;arrayAuxPages=settings.multiselection.deselectedPages;settings.multiselection.numSelected=xhr.records-xhr.reorderedSelection.length;}else{arrayAuxRowsPerPage=settings.multiselection.selectedRowsPerPage;arrayAuxLinesPerPage=settings.multiselection.selectedLinesPerPage;arrayAuxIds=settings.multiselection.selectedIds;arrayAuxRows=settings.multiselection.selectedRows;arrayAuxPages=settings.multiselection.selectedPages;settings.multiselection.numSelected=xhr.reorderedSelection.length;}for(var i=0;i<xhr.reorderedSelection.length;i++){reorderedRow=xhr.reorderedSelection[i];reorderedRowPage=reorderedRow.page;reorderedRowLine=reorderedRow.pageLine;var retValue='';for(var j=0;j<settings.primaryKey.length;j++){retValue+=reorderedRow.pk[settings.primaryKey[j]]+settings.multiplePkToken;}reorderedRowId=retValue.substr(0,retValue.length-1);if(arrayAuxRowsPerPage[reorderedRowPage]===undefined){arrayAuxRowsPerPage[reorderedRowPage]=[];arrayAuxLinesPerPage[reorderedRowPage]=[];}// Se almacena el Id del registro seleccionado
if(jQuery.inArray(reorderedRowId,arrayAuxIds)===-1){arrayAuxIds.push(reorderedRowId);arrayAuxRows.push({id:reorderedRowId,page:reorderedRowPage});//								arrayAuxRowsPerPage[reorderedRowPage].splice(reorderedRowLine,0,reorderedRowId);
arrayAuxRowsPerPage[reorderedRowPage].push(reorderedRowId);arrayAuxLinesPerPage[reorderedRowPage].push(reorderedRowLine);if(arrayAuxRowsPerPage[reorderedRowPage].length>0&&jQuery.inArray(reorderedRowPage,arrayAuxPages)===-1){jQuery.rup_utils.insertSorted(arrayAuxPages,reorderedRowPage);}}}//						$self.rup_table("updateSelectedRowNumber");
}// Se genera el evento que indica la modificación de los elementos seleccionados.
$self.triggerHandler('rupTable_multiselectionUpdated');// Se cierra el feedback para seleccionar/deseleccionar el resto de registros
$self.trigger('rupTable_feedbackClose',settings.$internalFeedback);// Se gestiona el icono de linea editable
if($self._hasPageSelectedElements(page)){if(settings.multiselection.rowForEditing!==undefined&&jQuery.inArray(settings.multiselection.rowForEditing,$self.jqGrid('getDataIDs'))!==-1){$self.rup_table('highlightEditableRow',jQuery($self.jqGrid('getInd',settings.multiselection.rowForEditing,true)),true);}else{$self.rup_table('highlightFirstEditableRow');}//						firstSelectedLine = $self._getFirstSelectedElementOfPage(page);
//						firstSelectedId = $self.jqGrid("getDataIDs")[firstSelectedLine-1];
//						settings.multiselection.rowForEditing=firstSelectedId;
//						$self.rup_table("highlightEditableRow", $self.jqGrid("getInd",firstSelectedId, true));
}/**
           * ARROW
           *///Cabecera
var $checkAllTH=jQuery('[id=\''+settings.id+'_cb\']');if(settings.multiselection.headerContextMenu_enabled&&$checkAllTH.find('a').length===0){//Añadir solo una vez
$checkAllTH.find('input').css('margin-right','1em');$self._addArrow($checkAllTH.find('input'));}//Fila
$self.find('.cbox').css('margin-right','1em');if(settings.multiselection.rowContextMenu_enabled){var isJerarquia=settings.jerarquia!==undefined?true:false,defaultOptions=jQuery.isEmptyObject(settings.multiselection.rowContextMenu.items);//Recorrer todas las filas
$.each($self.find('.cbox'),function(index,value){//Añadir flecha
$self._addArrow(jQuery(value));//Deshabilitar flecha: Jerarquía + solo opciones por defecto + no tiene hijos
if(isJerarquia&&defaultOptions&&$(value).parents('tr').find('.treeclick').hasClass('tree-leaf')){jQuery(this).next('a').addClass('ui-state-disabled').off('click');}});}},/*
         * Capturador del evento jqGridSelectAll.
         * Se ejecuta cuando se realice una selección de todos los elementos de la página.
         *
         * 	event: Objeto event de jQuery
         *  selectedRows: Array con los identificadores de los registros seleccionados en la página
         *  status: true en caso de selección, false en caso de deselección.
         */'jqGridSelectAll.rupTable.multiselection':function jqGridSelectAllRupTableMultiselection(event,selectedRows,status){var page=$self.rup_table('getGridParam','page'),selectMsg,deselectMsg,elementosRestantes,selectRestMsg,remainingSelectButton,remainingDeselectButton,cont;// Se oculta el posible mensaje de feedback que se muestre
$self.triggerHandler('rupTable_internalFeedbackClose');// Se gestiona la selección de todos los registros de la página
cont=0;for(var i=0;i<selectedRows.length;i++){if(selectedRows[i].indexOf(settings.id+'ghead_')===-1){$self._processSelectedRow(settings,selectedRows[i],status);cont++;}}selectMsg=jQuery.rup.i18nTemplate(jQuery.rup.i18n.base,'rup_table.selectMsg','<b>'+cont+'</b>','<b>'+page+'</b>');deselectMsg=jQuery.rup.i18nTemplate(jQuery.rup.i18n.base,'rup_table.deselectMsg','<b>'+cont+'</b>','<b>'+page+'</b>');// Se comprueba el valor de status para determinar si se está seleccionando (true) o deseleccionando (false) todos los registos de la página
if(status){// Se obtienen el número de registros restantes que quedan por seleccionar
elementosRestantes=$self._getRemainingRecordNum(settings,selectedRows);if(elementosRestantes!==0){// En caso de existir registros sin seleccionar se muestra el mensaje junto con un botón para permitir la selecón de dichos elementos
selectRestMsg=jQuery.rup.i18nTemplate(jQuery.rup.i18n.base,'rup_table.selectRestMsg',elementosRestantes);remainingSelectButton=jQuery.rup.i18nTemplate(jQuery.rup.i18n.base,'rup_table.templates.multiselection.selectRemainingRecords',$self[0].id,selectRestMsg,jQuery.rup.i18nParse(jQuery.rup.i18n.base,'rup_table.selectAll'));$self.trigger('rupTable_feedbackShow',[settings.$internalFeedback,selectMsg+remainingSelectButton,'alert']);}else{// Si no hay elementos restantes por seleccionar se muestra solo un mensaje informativo
$self.trigger('rupTable_feedbackShow',[settings.$internalFeedback,selectMsg,'alert']);}// Se asocia el handler al evento click del botón de seleccionar el resto de registros
$('#rup_table_'+$self[0].id+'_selectAll').on('click',function(event){$self.rup_table('selectRemainingRows');});$self.rup_table('highlightFirstEditableRow');}else{$self.rup_table('clearHighlightedEditableRows');// En caso de existir elementos seleccionados se muestra un mensaje que incluye un botón para permitir la deselección del todos los elementos seleccionados
if(settings.multiselection.numSelected>0){selectRestMsg=jQuery.rup.i18nTemplate(jQuery.rup.i18n.base,'rup_table.deselectRestMsg',settings.multiselection.numSelected);remainingDeselectButton=jQuery.rup.i18nTemplate(jQuery.rup.i18n.base,'rup_table.templates.multiselection.deselectRemainingRecords',$self[0].id,selectRestMsg,jQuery.rup.i18nParse(jQuery.rup.i18n.base,'rup_table.deSelectAll'));$self.trigger('rupTable_feedbackShow',[settings.$internalFeedback,deselectMsg+remainingDeselectButton,'alert']);}else{// Si no hay elementos restantes por deseleccionar se muestra solo un mensaje informativo
$self.trigger('rupTable_feedbackShow',[settings.$internalFeedback,deselectMsg,'alert']);}// Se asocia el handler al evento click del botón de deseleccionar el resto de registros
$('#rup_table_'+$self[0].id+'_deselectAll').on('click',function(event){$self.rup_table('deselectRemainingRows');});}// Se actualiza el contador de elementos seleccionados
$self.rup_table('updateSelectedRowNumber');},'rupTableAfterSearchNav.rupTable.multiselection rupTableSearchSuccess.rupTable.multiselection rupTableAfterDelete.rupTable.multiselection':function rupTableAfterSearchNavRupTableMultiselectionRupTableSearchSuccessRupTableMultiselectionRupTableAfterDeleteRupTableMultiselection(){var $self=$(this);$self.rup_table('resetSelection');},'rupTable_multiselectionUpdated.multiselection':function rupTable_multiselectionUpdatedMultiselection(){var $self=$(this),self=$self[0],page=$self.rup_table('getGridParam','page'),settings=$self.data('settings'),internalProps=self.p,rowNum=$self.rup_table('getGridParam','rowNum'),rows,selectedRows=settings.multiselection.selectedRowsPerPage[page],deselectedRows=settings.multiselection.deselectedRowsPerPage[page]||[];// Se oculta el posible mensaje de feedback que se muestre
$self.triggerHandler('rupTable_internalFeedbackClose');/*
           * Gestión de la persistencia de la multiselección entre páginas.
           *
           * El siguiente algoritmo permite mantener la selección de registros mientras se pagina.
           * Los registros seleccionados se mantienen almacenando sus identificadores.
           * En caso de seleccionar todos los elementos de la tabla se trabaja mediante lógica inversa, de modo que se almacenan los registros deseleccionados.
           */// Se comprueba si se han seleccionado todos los registros de la tabla.
if(settings.multiselection.selectedAll){internalProps.selarrrow=[];rows=self.rows;// Para cada línea que muestra la tabla:
for(var i=0;i<rows.length;i++){// Se comprueba si el registro se encuentra en el array de deseleccionados.
if(jQuery.inArray(rows[i].id,deselectedRows)===-1){// En caso de no ser un elemento deseleccionado se marca como seleccionado.
$self.rup_table('highlightRowAsSelected',$(rows[i]));}else{// En caso de ser un elemento deseleccionado se desmarca.
$self.rup_table('clearHighlightedRowAsSelected',$(rows[i]));}}// En caso de estar todos los elementos de la página seleccionados marcamos el check general
if(deselectedRows.length===0){settings.$selectAllCheck[internalProps.useProp?'prop':'attr']('checked',true);}}else{// No se han seleccionado todos los resgistros de la página.
if(selectedRows){rows=self.rows;internalProps.selarrrow=[];// Para cada línea que muestra la tabla:
for(var i=0;i<rows.length;i++){// Se comprueba si el registro se encuentra en el array de seleccionados
if(jQuery.inArray(rows[i].id,selectedRows)!==-1){// En caso de ser un elemento seleccionado, se marca como tal.
$self.rup_table('highlightRowAsSelected',$(rows[i]));}else{// En caso de no ser un elemento seleccionado se desmarca.
$self.rup_table('clearHighlightedRowAsSelected',$(rows[i]));}}// En caso de estar todos los elementos de la página seleccionados marcamos el check general
if(selectedRows.length===rowNum){settings.$selectAllCheck[internalProps.useProp?'prop':'attr']('checked',true);}}}$self.rup_table('updateSelectedRowNumber');},'rupTable_beforeAddRow.multiselection':function rupTable_beforeAddRowMultiselection(event,addCloneOptions){// Si la edición en línea no está activada, no comprobamos los elementos seleccionados y devolvemos true
if($self[0].p.inlineEdit){return true;}$self._checkSelectedElements(function(){$self.jqGrid('editGridRow','new',addCloneOptions);$self.rup_table('resetSelection');$self.rup_table('clearHighlightedEditableRows');});return false;},'jqGridAddEditAfterSubmit.rupTable.formEditing':function jqGridAddEditAfterSubmitRupTableFormEditing(event,res,postData,oper){if(oper!=='edit'){$self.rup_table('resetSelection');$self.rup_table('clearHighlightedEditableRows');}}});if(settings.multiboxonly===true){settings.multiselection.multiboxonly=true;}// Control del uso de Ctrl y Shift
jQuery('body').on({'rup_ctrlKeyDown rup_shiftKeyDown':function rup_ctrlKeyDownRup_shiftKeyDown(){if(settings.multiselection.multiboxonly===true){$self[0].p.multiboxonly=false;}return false;},'rup_ctrlKeyUp rup_shiftKeyUp':function rup_ctrlKeyUpRup_shiftKeyUp(){if(settings.multiselection.multiboxonly===true){$self[0].p.multiboxonly=true;}return false;}});/**
       * MENUS CONTEXTUALES
       */jQuery.contextMenu('destroy','[id=\''+settings.id+'_cb\']');jQuery('[id=\''+settings.id+'_cb\']').rup_contextMenu({trigger:'none',callback:settings.multiselection.headerContextMenu.callback,items:$self._headerContextMenuItems(settings.multiselection.headerContextMenu,settings),position:function position(contextMenu,x,y){var offset=this.offset();contextMenu.$menu.css({top:offset.top+this.height(),left:offset.left});}});if(settings.multiselection.rowContextMenu_enabled){jQuery.contextMenu('destroy','td[aria-describedby=\''+settings.id+'_cb\']');jQuery('td[aria-describedby=\''+settings.id+'_cb\']').rup_contextMenu({trigger:'none',callback:settings.multiselection.rowContextMenu.callback,items:$self._rowContextMenuItems(settings.multiselection.rowContextMenu,settings),position:function position(contextMenu,x,y){var offset=this.offset();contextMenu.$menu.css({top:offset.top+this.height(),left:offset.left});}});}}});/**
   * Métodos públicos del plugin multiselection.
   *
   * Los métodos implementados son:
   *
   * resetSelection(): Limpia a selección realizada por el usuario.
   * updateSelectedRowNumber(): Refresca el identificador de resgistros seleccionados
   */jQuery.fn.rup_table('extend',{getSelectedIds:function getSelectedIds(){var $self=this,settings=$self.data('settings'),multiselectionObj={};if(!settings.multiselection.selectedAll){if(settings.multiselection.selectedIds!=undefined){if(settings.multiselection.selectedIds.length>0){jQuery.extend(true,multiselectionObj,{'selectedIds':settings.multiselection.selectedIds});}}jQuery.extend(true,multiselectionObj,{'selectedAll':false});}else{if(settings.multiselection.deselectedIds.length>0){jQuery.extend(true,multiselectionObj,{'selectedIds':settings.multiselection.deselectedIds});}jQuery.extend(true,multiselectionObj,{'selectedAll':true});}return multiselectionObj;},clearHighlightedEditableRows:function clearHighlightedEditableRows(){var $self=this,settings=$self.data('settings');$self.find('td[aria-describedby=\''+settings.id+'_rupInfoCol\'] span.ui-icon.ui-icon-pencil').removeClass('ui-icon-pencil');},highlightFirstEditableRow:function highlightFirstEditableRow(){var $self=this,settings=$self.data('settings'),page=parseInt($self.rup_table('getGridParam','page'),10),firstSelectedLine,firstSelectedId;$self.rup_table('clearHighlightedEditableRows');if($self._hasPageSelectedElements(page)){firstSelectedLine=$self._getFirstSelectedElementOfPage(page);firstSelectedId=$self.jqGrid('getDataIDs')[firstSelectedLine-1];settings.multiselection.rowForEditing=firstSelectedId;$self.rup_table('highlightEditableRow',$self.jqGrid('getInd',firstSelectedId,true));}},highlightEditableRow:function highlightEditableRow($row){var $self=this,settings=$self.data('settings');$row=jQuery($row);$row.find('td[aria-describedby=\''+settings.id+'_rupInfoCol\'] span').addClass('ui-icon ui-icon-rupInfoCol ui-icon-pencil');},refreshSelection:function refreshSelection(){var $self=this;$self.triggerHandler('rupTable_multiselectionUpdated');},resetSelection:function resetSelection(){var $self=this,settings=$self.data('settings');$self.jqGrid('resetSelection');$self._initializeMultiselectionProps(settings);$self.triggerHandler('rupTable_multiselectionUpdated');},selectAllRows:function selectAllRows(event){var $self=this,settings=$self.data('settings'),arr,$row;$self.rup_table('selectRemainingRows');jQuery('#cb_'+settings.id).attr('checked','checked');// Se marcan los registros de la tabla como marcados
arr=$self.jqGrid('getDataIDs');for(var i=0;i<arr.length;i++){$row=jQuery($self.jqGrid('getInd',arr[i],true));$self.rup_table('highlightRowAsSelected',$row);}$self.rup_table('highlightFirstEditableRow');},selectRemainingRows:function selectRemainingRows(event){var $self=this,settings=$self.data('settings');$self._initializeMultiselectionProps(settings);// Se marca el flag de todos seleccionados a true
settings.multiselection.selectedAll=true;// Numero de registros seleccionados
settings.multiselection.numSelected=$self.rup_table('getGridParam','records');// Se cierra el feedback para seleccionar/deseleccionar el resto de registros
$self.rup_table('updateSelectedRowNumber');$self.trigger('rupTable_feedbackClose',settings.$internalFeedback);},deselectAllRows:function deselectAllRows(event){var $self=this,settings=$self.data('settings'),arr,$row,internalProps=$self[0].p;$self.rup_table('deselectRemainingRows');$self.rup_table('clearHighlightedEditableRows');jQuery('#cb_'+settings.id).removeAttr('checked');// Se marcan los registros de la tabla como marcados
arr=$self.jqGrid('getDataIDs');internalProps.selarrrow=[];for(var i=0;i<arr.length;i++){$row=jQuery($self.jqGrid('getInd',arr[i],true));$self.rup_table('clearHighlightedRowAsSelected',$row);}},deselectRemainingRows:function deselectRemainingRows(event){var $self=this,settings=$self.data('settings');$self._initializeMultiselectionProps(settings);// Se cierra el feedback para seleccionar/deseleccionar el resto de registros
$self.rup_table('updateSelectedRowNumber');$self.trigger('rupTable_feedbackClose',settings.$internalFeedback);},/*
     * Actualiza el contador de la tabla que indica los registros seleccionados.
     */updateSelectedRowNumber:function updateSelectedRowNumber(){var $self=$(this),settings=$self.data('settings');$('div .ui-paging-selected',settings.$pager).html(settings.multiselection.numSelected+' '+jQuery.rup.i18nParse(jQuery.rup.i18n.base,'rup_table.pager.selected'));$self.triggerHandler('rupTableSelectedRowNumberUpdated');}});//*******************************************************
// DEFINICIÓN DE MÉTODOS PRIVADOS
//*******************************************************
/**
   * Métodos privados del plugin multiselection.
   *
   * Los métodos implementados son:
   *
   * _addArrow (object): Añade flecha para desplegar menú contextual.
   * _headerContextMenuItems(options, settings): Configura el menú contextual del check de la cabecera.
   * _rowContextMenuItems(options, settings): Configura el menú contextual del check de cada línea (contiene configuración para Jerarquía).
   * _hasPageSelectedElements(paramPage): Determina (true/false) si la página indicada contiene registros seleccionados.
   * _initializeMultiselectionProps(settings): Inicializa los parámetros internos de control para la multiselección.
   * _getFirstSelectedElementOfPage(paramPage): Devuelve el primer registro seleccionado de la página indicada.
   * _getRemainingRecordNum(settings, selectedRows): Devuelve el número de elementos restantes que pueden ser seleccionados.
   * _getSelectedLinesOfPage(page): Devuelve el número de registros seleccionados de que dispone la página indicada por parámetro.
   * _processSelectedRow(settings, rowId, status): Gestióna la acción de seleción/deselección del registro indicado.
   */jQuery.fn.rup_table('extend',{//Añade flecha contextMenu
_addArrow:function _addArrow(object){jQuery(object).after(jQuery('<a />').attr('href','javascript:void(0)').addClass('ui-icon rup-jerarquia_checkmenu_arrow').on('click',function(e){$(this).parents('th, td').contextMenu();}));},_checkSelectedElements:function _checkSelectedElements(okCallback){var $self=$(this),self=$self[0],page=$self.rup_table('getGridParam','page'),settings=$self.data('settings');//if(prop.showMultiselectAlerts && selectedRows && selectedRows.length>0){
if(settings.multiselection.numSelected>0){$.rup_messages('msgConfirm',{message:$.rup.i18nParse($.rup.i18n.base,'rup_table.checkSelectedElems'),title:$.rup.i18nParse($.rup.i18n.base,'rup_table.changes'),OKFunction:function OKFunction(){okCallback.call();}});}else{okCallback.call();}},//Crear contextMenu cabecera
_headerContextMenuItems:function _headerContextMenuItems(options,settings){var $self=this,items={};if(options.selectAllPage){jQuery.extend(items,{'selectAllPage':{name:$.rup.i18nParse($.rup.i18n.base,'rup_table.plugins.multiselection.selectAllPage'),icon:'check',disabled:function disabled(key,opt){return $self._getSelectedLinesOfPage(parseInt($self.rup_table('getGridParam','page'))).length===$self.jqGrid('getGridParam','reccount');},callback:function callback(key,options){$('[id=\'cb_'+settings.id+'\']').attr('checked','checked').click().attr('checked','checked');}}});}if(options.deselectAllPage){jQuery.extend(items,{'deselectAllPage':{name:$.rup.i18nParse($.rup.i18n.base,'rup_table.plugins.multiselection.deselectAllPage'),icon:'uncheck',disabled:function disabled(key,opt){return $self._getSelectedLinesOfPage(parseInt($self.rup_table('getGridParam','page'))).length===0;},callback:function callback(key,options){$('[id=\'cb_'+settings.id+'\']').removeAttr('checked').click().removeAttr('checked');}}});}if(options.separator){jQuery.extend(items,{'separator':''});}if(options.selectAll){jQuery.extend(items,{'selectAll':{name:$.rup.i18nParse($.rup.i18n.base,'rup_table.plugins.multiselection.selectAll'),icon:'check_all',disabled:function disabled(key,opt){return settings.multiselection.numSelected===$self.rup_table('getGridParam','records');},callback:function callback(key,options){$self.rup_table('selectAllRows');}}});}if(options.deselectAll){jQuery.extend(items,{'deselectAll':{name:$.rup.i18nParse($.rup.i18n.base,'rup_table.plugins.multiselection.deselectAll'),icon:'uncheck_all',disabled:function disabled(key,opt){return settings.multiselection.numSelected===0;},callback:function callback(key,options){$self.rup_table('deselectAllRows');}}});}if(!jQuery.isEmptyObject(options.items)){jQuery.extend(items,options.items);}return items;},_rowContextMenuItems:function _rowContextMenuItems(options,settings){var $self=this,items={};if(settings.jerarquia!==undefined&&settings.jerarquia.contextMenu){if(options.selectChild){jQuery.extend(items,{'selectChild':{name:$.rup.i18nParse($.rup.i18n.base,'rup_table.plugins.jerarquia.selectChild'),icon:'child',callback:function callback(key,options){$self._getJerarquiaChildren(this,key,options);}}});}if(options.selectDescendent){jQuery.extend(items,{'selectDescendent':{name:$.rup.i18nParse($.rup.i18n.base,'rup_table.plugins.jerarquia.selectDescendent'),icon:'descendent',callback:function callback(key,options){$self._getJerarquiaChildren(this,key,options);}}});}if(options.separator){jQuery.extend(items,{'separator':''});}if(options.deselectChild){jQuery.extend(items,{'deselectChild':{name:$.rup.i18nParse($.rup.i18n.base,'rup_table.plugins.jerarquia.deselectChild'),icon:'uncheck',callback:function callback(key,options){$self._getJerarquiaChildren(this,key,options);}}});}if(options.deselectDescendent){jQuery.extend(items,{'deselectDescendent':{name:$.rup.i18nParse($.rup.i18n.base,'rup_table.plugins.jerarquia.deselectDescendent'),icon:'uncheck',callback:function callback(key,options){$self._getJerarquiaChildren(this,key,options);}}});}}if(!jQuery.isEmptyObject(options.items)){jQuery.extend(items,options.items);}return items;},_refreshSelectedElements:function _refreshSelectedElements(settings,status,rowPK,tableRow){//Variables para referenciar selección normal o inversa
var rowsPerPage,linesPerPage,ids,rows,pages;if(settings.multiselection.selectedAll!==true){rowsPerPage=settings.multiselection.selectedRowsPerPage;linesPerPage=settings.multiselection.selectedLinesPerPage;ids=settings.multiselection.selectedIds;rows=settings.multiselection.selectedRows;pages=settings.multiselection.selectedPages;}else{rowsPerPage=settings.multiselection.deselectedRowsPerPage;linesPerPage=settings.multiselection.deselectedLinesPerPage;ids=settings.multiselection.deselectedIds;rows=settings.multiselection.deselectedRows;pages=settings.multiselection.deselectedPages;status=!status;}//Si no estaba seleccionado
if(status){if(jQuery.inArray(rowPK,ids)===-1){//Añadir el elemento a los seleccionados
if(settings.multiselection.selectedAll!==true){settings.multiselection.numSelected++;}else{//Quitar el elemento de los no seleccionados (inversa)
settings.multiselection.numSelected--;}//Controlar si no existe array para la página
if(rowsPerPage[tableRow.page]===undefined){rowsPerPage[tableRow.page]=[];linesPerPage[tableRow.page]=[];}//id
ids.push(rowPK);//PAGINA [líneas]
jQuery.rup_utils.insertSorted(linesPerPage[tableRow.page],tableRow.pageLine);//{ id : PK, page : PAGINA }
rows.push({id:rowPK,page:tableRow.page});//PAGINA [ids]
rowsPerPage[tableRow.page].splice(tableRow.pageLine,0,rowPK);//PAGINA
if(rowsPerPage[tableRow.page].length>0&&jQuery.inArray(tableRow.page,pages)===-1){jQuery.rup_utils.insertSorted(pages,tableRow.page);}}}else{if(jQuery.inArray(rowPK,ids)!==-1){//Quitar el elemento a los seleccionados
if(settings.multiselection.selectedAll!==true){settings.multiselection.numSelected--;}else{//añadir el elemento de los no seleccionados (inversa)
settings.multiselection.numSelected++;}//id
ids.splice(jQuery.inArray(rowPK,ids),1);//PAGINA [líneas]
linesPerPage[tableRow.page].splice(jQuery.inArray(tableRow.pageLine,linesPerPage[tableRow.page]),1);//{ id : PK, page : PAGINA }
var selectedRowObjStr=JSON.stringify({id:rowPK,page:tableRow.page}),indexInArray=null;jQuery.grep(rows,function(element,index){if(JSON.stringify(element)===selectedRowObjStr){indexInArray=index;}});rows.splice(indexInArray,1);//PAGINA [ids]
rowsPerPage[tableRow.page].splice(jQuery.inArray(rowPK,rowsPerPage[tableRow.page]),1);//PAGINA
if(rowsPerPage[tableRow.page].length==0&&jQuery.inArray(tableRow.page,pages)!==-1){pages.splice(jQuery.inArray(tableRow.page,pages),1);}}}},_hasPageSelectedElements:function _hasPageSelectedElements(paramPage){var $self=this,settings=$self.data('settings'),rowsPerPage,page=typeof paramPage==='string'?parseInt(paramPage,10):paramPage;// Se comprueba si se han seleccionado todos los registros de la tabla
if(!settings.multiselection.selectedAll){// En caso de no haberse seleccionado todos los registros de la tabla
// Comprobamos si en la página indicada se ha seleccionado un elemento
return jQuery.inArray(page,settings.multiselection.selectedPages)!==-1;}else{// En caso de haberse seleccionado todos los registros de la tabla
// Generamos un array inicializado con los index de las lineas de las tablas
rowsPerPage=parseInt($self.rup_table('getGridParam','rowNum'),10);// Obtenemos el número de registro por página que se visualizan
// Se comprueba si el número de registros deseleccionados es igual al número de registros por página, en cuyo caso significará que no hay elementos seleccionados
if(jQuery.inArray(page,settings.multiselection.deselectedPages)!==-1&&settings.multiselection.deselectedLinesPerPage[page].length===rowsPerPage){return false;}return true;}},_initializeMultiselectionProps:function _initializeMultiselectionProps(settings){// Se almacenan en los settings internos las estructuras de control de los registros seleccionados
if(settings.multiselection===undefined){settings.multiselection={};}// Flag indicador de selección de todos los registros
settings.multiselection.selectedAll=false;// Numero de registros seleccionados
settings.multiselection.numSelected=0;// Propiedades de selección de registros
settings.multiselection.selectedRowsPerPage=[];settings.multiselection.selectedLinesPerPage=[];settings.multiselection.selectedRows=[];settings.multiselection.selectedIds=[];settings.multiselection.selectedPages=[];// Propiedades de deselección de registros
settings.multiselection.deselectedRowsPerPage=[];settings.multiselection.deselectedLinesPerPage=[];settings.multiselection.deselectedRows=[];settings.multiselection.deselectedIds=[];settings.multiselection.deselectedPages=[];},_getFirstSelectedElementOfPage:function _getFirstSelectedElementOfPage(paramPage){var $self=this,settings=$self.data('settings'),rowsPerPage,page=typeof paramPage==='string'?parseInt(paramPage,10):paramPage;// Se comprueba si se han seleccionado todos los registros de la tabla
if(!settings.multiselection.selectedAll){// En caso de no haberse seleccionado todos los registros de la tabla
// Comprobamos si en la página indicada se ha seleccionado un elemento
if(jQuery.inArray(page,settings.multiselection.selectedPages)===-1){return false;}// En caso de que se haya seleccionado un elemento en la página indicada se devuelve el primero
return settings.multiselection.selectedLinesPerPage[page][0];}else{// En caso de haberse seleccionado todos los registros de la tabla
// Si no se han deseleccionado registros en la página se devuelve el primer indice
if(jQuery.inArray(page,settings.multiselection.deselectedPages)===-1){return 1;}// Obtenemos el número de registro por página que se visualizan
rowsPerPage=parseInt($self.rup_table('getGridParam','rowNum'),10);// Se comprueba si el número de registros deseleccionados es igual al número de registros por página, en cuyo caso significará que no hay eleme
if(settings.multiselection.deselectedLinesPerPage[page].length===rowsPerPage){return false;}// Obtenemos el primer elemento de la página que no ha sido deseleccionado
for(var i=1;i<=rowsPerPage;i++){if(jQuery.inArray(i,settings.multiselection.deselectedLinesPerPage[page])===-1){return i;}}}},_getRemainingRecordNum:function _getRemainingRecordNum(settings,selectedRows){var $self=this,totalRegistros=$self.rup_table('getGridParam','records'),registrosPagina=$self.rup_table('getGridParam','reccount'),registrosSelPagina=selectedRows.length,registrosSelTotal=settings.multiselection.numSelected,elementosRestantes=totalRegistros-registrosPagina!==0?totalRegistros-registrosPagina-(registrosSelTotal-registrosSelPagina):0;return elementosRestantes;},_getSelectedLinesOfPage:function _getSelectedLinesOfPage(page){var $self=this,settings=$self.data('settings'),rowsPerPage,records,lastPage,inverseArray=[];// Se comprueba si se han seleccionado todos los registros de la tabla
if(!settings.multiselection.selectedAll){// En caso de no haberse seleccionado todos los registros de la tabla
// Comprobamos si en la página indicada se ha seleccionado un elemento
if(jQuery.inArray(page,settings.multiselection.selectedPages)===-1){return[];}// En caso de que se haya seleccionado un elemento en la página indicada se devuelve el array de seleccionados
return settings.multiselection.selectedLinesPerPage[page];}else{// En caso de haberse seleccionado todos los registros de la tabla
// Generamos un array inicializado con los index de las lineas de las tablas
rowsPerPage=parseInt($self.rup_table('getGridParam','rowNum'),10);records=$self.rup_table('getGridParam','records');lastPage=parseInt(Math.ceil(records/rowsPerPage,10));// En caso de ser la última página se recalcula el número de elementos que se muestran en ella
if(page===lastPage){rowsPerPage=records-(lastPage-1)*rowsPerPage;}for(var i=1;i<=rowsPerPage;i++){inverseArray[i-1]=i;}// Si no se han deseleccionado registros en la página se devuelve el array al completo
if(jQuery.inArray(page,settings.multiselection.deselectedPages)===-1){return inverseArray;}// Obtenemos el número de registro por página que se visualizan
// Se comprueba si el número de registros deseleccionados es igual al número de registros por página, en cuyo caso significará que no hay elementos seleccionados
if(settings.multiselection.deselectedLinesPerPage[page].length===rowsPerPage){return[];}// Se eliminan del array inicializado con todos los identificadores de las lineas, las que han sido deseleccionadas
return jQuery.grep(inverseArray,function(elem){return jQuery.inArray(elem,settings.multiselection.deselectedLinesPerPage[page])===-1;});}},_processSelectedRow:function _processSelectedRow(settings,rowId,status){var $self=this,page=$self.rup_table('getGridParam','page'),pageInt=parseInt(page),lineIndex,indexInArray,indexAtPage,indexPage;// Se selecciona o deselecciona el elemento en los arrays que almacenan los registros seleccionados.
if(status){if(settings.multiselection.selectedAll){// Se ha deseleccionado un elemento
// Se almacena el Id del registro seleccionado
indexInArray=jQuery.inArray(rowId,settings.multiselection.deselectedIds);if(indexInArray!=-1){settings.multiselection.deselectedIds.splice(indexInArray,1);settings.multiselection.deselectedRows.splice(indexInArray,1);indexAtPage=jQuery.inArray(rowId,settings.multiselection.deselectedRowsPerPage[page]);settings.multiselection.deselectedRowsPerPage[page].splice(indexAtPage,1);settings.multiselection.deselectedLinesPerPage[page].splice(indexAtPage,1);if(settings.multiselection.deselectedRowsPerPage[page].length===0){indexPage=jQuery.inArray(pageInt,settings.multiselection.deselectedPages);if(indexPage!==-1){settings.multiselection.deselectedPages.splice(indexPage,1);}}settings.multiselection.numSelected++;}}else{// Se ha seleccionado un elemento
// Se comprueba si está creado el array correspondiente para la página actual
if(settings.multiselection.selectedRowsPerPage[page]===undefined){settings.multiselection.selectedRowsPerPage[page]=[];settings.multiselection.selectedLinesPerPage[page]=[];}// Se almacena el Id del registro seleccionado
if(jQuery.inArray(rowId,settings.multiselection.selectedIds)===-1){settings.multiselection.selectedIds.push(rowId);settings.multiselection.selectedRows.push({id:rowId,page:page});//						lineIndex = jQuery.rup_utils.insertSorted(settings.multiselection.selectedLinesPerPage[page], $self.jqGrid("getInd",rowId));
lineIndex=jQuery.rup_utils.insertSorted(settings.multiselection.selectedLinesPerPage[page],$self._getLineIndex(rowId));settings.multiselection.selectedRowsPerPage[page].splice(lineIndex,0,rowId);if(settings.multiselection.selectedRowsPerPage[page].length>0&&jQuery.inArray(pageInt,settings.multiselection.selectedPages)===-1){jQuery.rup_utils.insertSorted(settings.multiselection.selectedPages,pageInt);}settings.multiselection.numSelected++;}}}else{if(settings.multiselection.selectedAll){// Se ha seleccionado un elemento
// Se comprueba si está creado el array correspondiente para la página actual
if(settings.multiselection.deselectedRowsPerPage[page]===undefined){settings.multiselection.deselectedRowsPerPage[page]=[];settings.multiselection.deselectedLinesPerPage[page]=[];}// Se almacena el Id del registro seleccionado
if(jQuery.inArray(rowId,settings.multiselection.deselectedIds)===-1){settings.multiselection.deselectedIds.push(rowId);settings.multiselection.deselectedRows.push({id:rowId,page:page});//						lineIndex = jQuery.rup_utils.insertSorted(settings.multiselection.deselectedLinesPerPage[page], $self.jqGrid("getInd",rowId));
lineIndex=jQuery.rup_utils.insertSorted(settings.multiselection.deselectedLinesPerPage[page],$self._getLineIndex(rowId));settings.multiselection.deselectedRowsPerPage[page].splice(lineIndex,0,rowId);if(settings.multiselection.deselectedRowsPerPage[page].length>0&&jQuery.inArray(pageInt,settings.multiselection.deselectedPages)===-1){jQuery.rup_utils.insertSorted(settings.multiselection.deselectedPages,pageInt);}settings.multiselection.numSelected--;}}else{// Se ha deseleccionado un elemento
// Se almacena el Id del registro seleccionado
index=jQuery.inArray(rowId,settings.multiselection.selectedIds);if(index!=-1){settings.multiselection.selectedIds.splice(index,1);settings.multiselection.selectedRows.splice(index,1);indexAtPage=jQuery.inArray(rowId,settings.multiselection.selectedRowsPerPage[page]);settings.multiselection.selectedRowsPerPage[page].splice(indexAtPage,1);settings.multiselection.selectedLinesPerPage[page].splice(indexAtPage,1);if(settings.multiselection.selectedRowsPerPage[page].length===0){indexPage=jQuery.inArray(pageInt,settings.multiselection.selectedPages);if(indexPage!==-1){settings.multiselection.selectedPages.splice(indexPage,1);}}settings.multiselection.numSelected--;}}}$self.rup_table('updateSelectedRowNumber');}});//*******************************************************
// DEFINICIÓN DE LA CONFIGURACION POR DEFECTO DEL PATRON
//*******************************************************
jQuery.fn.rup_table.plugins.multiselection=jQuery.fn.rup_table.plugins.multiselection||{};jQuery.fn.rup_table.plugins.multiselection.defaults={showGridInfoCol:true,formEdit:{autoselectFirstRecord:false},inlineEdit:{autoselectFirstRecord:false},multiselection:{defaultEditableInfoCol:{name:'infoEditable',index:'infoEditable',editable:false,width:'15em',search:false},headerContextMenu_enabled:true,headerContextMenu:{selectAllPage:true,deselectAllPage:true,separator:true,selectAll:true,deselectAll:true,items:{}},rowContextMenu_enabled:false,rowContextMenu:{selectChild:true,selectDescendent:true,separator:true,deselectChild:true,deselectDescendent:true,items:{}}}};jQuery.fn.rup_table.defaults.multiselection={loadBeforeSend:function rup_table_defaults_loadBeforeSend(xhr,settings){// Se modifica la request para incluir las siguientes cabeceras:
// Se añade la cabecera JQGridModel para indicar que la petición ha sido realizada por el componente rup_table
xhr.setRequestHeader('JQGridModel','true');// Se indica que el tipo de contenido enviado en la cabecera es application/jsons
xhr.setRequestHeader('Content-Type','application/json');}};})(jQuery);/*!
 * Copyright 2013 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 *//*global jQuery *//**
 * El objetivo principal del módulo Jerarquía es la presentación de un conjunto de datos (tabla) ordenados jerárquicamente en base a una relación existente entre ellos.
 *
 * @summary Plugin de edición en línea del componente RUP Table.
 * @module rup_table/jerarquia
 * @example
 *
 * $("#idComponente").rup_table({
 * 	url: "../jqGridUsuario",
 * 	usePlugins:["jerarquia"],
 * 	jerarquia:{
 * 		// Propiedades de configuración del plugin jerarquia
 * 	}
 * });
 */(function(jQuery){jQuery.rup_table.registerPlugin('jerarquia',{loadOrder:11,preConfiguration:function preConfiguration(settings){var $self=this;return $self.rup_table('preConfigurejerarquia',settings);},postConfiguration:function postConfiguration(settings){var $self=this;return $self.rup_table('postConfigurejerarquia',settings);}});//********************************
// DEFINICIÓN DE MÉTODOS PÚBLICOS
//********************************
jQuery.fn.rup_table('extend',{/**
		* Metodo que realiza la pre-configuración del plugin jerarquia del componente RUP Table.
		* Este método se ejecuta antes de la incialización del plugin.
		*
		* @name preConfigurejerarquia
		* @function
		* @param {object} settings - Parámetros de configuración del componente.
		*/preConfigurejerarquia:function preConfigurejerarquia(settings){var $self=this,jerarquiaSettings=settings.jerarquia;//Contenedor de parámetros de la jerarquia
$self.jqGrid('setGridParam',{postData:{jerarquia:{}}});//Sobreescribir valores y funciones TREEGRID
settings.treeGrid=true;settings.rowTotal=0;//(avoid default feature)
settings.treeGridModel='adjacency';//default: nested
settings.treeIcons=jerarquiaSettings['icons'];//(avoid default function)
var setTreeGrid_default=$self.jqGrid.setTreeGrid;jQuery.jgrid.extend({setTreeGrid:function setTreeGrid(){setTreeGrid_default.call($self);$self[0].p.altRows=true;//pijama
$self[0].p.pgbuttons=true;//enlaces paginación
$self[0].p.pginput=true;//selector de página
$self[0].p.rowList=settings.rowList;//núm. elementos/página
if(settings.multiselect){$self[0].p.multiselect=true;//multiselección
}}});// Se configura la url de filtrado
if(settings.filter.childrenUrl===null){settings.filter.childrenUrl=settings.baseUrl+'Children';}//Columna de jerarquía
settings.ExpandColumn=jerarquiaSettings['column'];//Si es multiselección se debe de desplazar el puntero de la columna a la siguiente (da igual que sea oculta)
if(settings.multiselect){for(key in settings.colModel){if(settings.colModel[key].name===settings.ExpandColumn){key=parseInt(key)+1;//Si no hay columna siguiente se crea una oculta para esto
if(settings.colModel[key]===undefined){settings.colNames[key]='jerarquia_multiselect';settings.colModel[key]={name:'jerarquia_multiselect',hidden:true};}settings.ExpandColumn=settings.colModel[key].name;break;}}}//Añadir columnas de la jerarquía
settings.colNames=jQuery.merge(['level'],settings.colNames);settings.colModel=jQuery.merge([{name:'level',hidden:true}],settings.colModel);settings.colNames=jQuery.merge(['isLeaf'],settings.colNames);settings.colModel=jQuery.merge([{name:'isLeaf',hidden:true}],settings.colModel);settings.colNames=jQuery.merge(['parentNodes'],settings.colNames);settings.colModel=jQuery.merge([{name:'parentNodes',hidden:true}],settings.colModel);settings.colNames=jQuery.merge(['filter'],settings.colNames);settings.colModel=jQuery.merge([{name:'filter',hidden:true}],settings.colModel);//Inicializar los elementos contraidos
jQuery($self).data('tree',[]);//Sobreescribir evento expandir/contraer
$self.on({'rupTable_serializeGridData.multiselection':function rupTable_serializeGridDataMultiselection(events,postData){//Token para separar los nodos (para tooltip)
jQuery.extend(true,postData,{'jerarquia':{'token':jerarquiaSettings['token']}});if(jQuery.isArray(postData.jerarquia.tree)&&postData.jerarquia.tree.length===0){postData.jerarquia.tree='';}},'jqGridAddEditAfterComplete.rupTable.jerarquia':function jqGridAddEditAfterCompleteRupTableJerarquia(){//Desactivar TREEGRID
$self[0].p.treeGrid=false;//(avoid default feature)
},//				"jqGridAddEditBeforeSubmit.rupTable.jerarquia": function(event, postData, $form, frmoper){
//					var parentProp = jQuery.proxy(settings.getRowForEditing, $self)();
//					if (parentProp!==undefined){
//						postData[settings.jerarquia.parentProp] = parentProp;
//					}
//				},
'jqGridAddEditBeforeSubmit.rupTable.jerarquia jqGridBeforeRequest.rupTable.jerarquia':function jqGridAddEditBeforeSubmitRupTableJerarquiaJqGridBeforeRequestRupTableJerarquia(){//Activar TREEGRID
$self[0].p.treeGrid=true;//(avoid default feature)
},'jqGridLoadComplete.rupTable.jerarquia':function jqGridLoadCompleteRupTableJerarquia(event,data){//Array de elementos contraidos
var collapsedNodes=jQuery($self).data('tree'),collapsedNodes_length=collapsedNodes.length;//ICONOS: contraidos (tree)
for(var i=0;i<collapsedNodes_length;i++){jQuery('[id=\''+collapsedNodes[i]+'\'] .tree-wrap > div').removeClass('tree-leaf '+settings.treeIcons.leaf).addClass('tree-minus '+settings.treeIcons.minus);}//ICONOS: filtrado (filter) y tooltip (parentNodes)
var rows=$self.rup_table('getGridParam','data'),rows_length=rows.length,$filterIcon=jQuery('<div />').addClass('rup-jerarquia_filter ui-icon').addClass(jerarquiaSettings['icons']['filter']).text(jQuery.rup.i18nParse(jQuery.rup.i18n.base,'rup_table.plugins.jerarquia.filtered'));for(var i=0;i<rows_length;i++){var rowId=jQuery.jgrid.getAccessor(rows[i],$self.rup_table('getGridParam','localReader').id),$rowColumn=jQuery('tr[id=\''+rowId+'\'] > td .tree-wrap');//Filtro
if(rows[i].filter){$rowColumn.prepend($filterIcon.clone());}//Tooltip
if(jerarquiaSettings['parentNodesTooltip']){$rowColumn.parent().rup_tooltip({content:{text:$self._parseParentNodes(rows[i].parentNodes)}});}}//EVENTOS: Expandir (plus) - Contraer (minus)
jQuery('.tree-plus, .tree-minus').off('click');jQuery('.tree-plus, .tree-minus').on('click',function(event){var $iconDiv=jQuery(this),rowId=$self.rup_table('getGridParam','_index')[$iconDiv.closest('tr.jqgrow')[0].id],rowData=$self.rup_table('getGridParam','data')[rowId],nodeId=jQuery.jgrid.getAccessor(rowData,$self.rup_table('getGridParam','localReader').id);//Añadir o eliminar elemento para query (y almacenarlo en la tabla)
if($iconDiv.hasClass(settings.treeIcons.plus)){collapsedNodes.push(nodeId);}else{collapsedNodes.splice(jQuery.inArray(nodeId,collapsedNodes),1);}jQuery($self).data('tree',collapsedNodes);//Buscar (añadiendo colapsados)
$self.jqGrid('setGridParam',{postData:{'jerarquia':{'tree':collapsedNodes.toString()}}});$self.trigger('reloadGrid');});//Desactivar TREEGRID
$self[0].p.treeGrid=false;//(avoid default feature)
}});//Eventos que producen reset de los elementos expandidos
jQuery.each(jerarquiaSettings['resetEvents'],function(index,object){var callback=jQuery.isFunction(object[0])?object.shift():null,ids='[id=\''+object.join('\'], [id=\'')+'\']';//Asociar el evento
jQuery(ids).on(index,function(event){if(callback===null||callback.call($self,event)===false){$self.reset();}});//El evento se ejecuta el primero en secuencia
for(var i=0;i<object.length;i++){jQuery._data(jQuery('#'+object[i])[0],'events')[index]=jQuery._data(jQuery('#'+object[i])[0],'events')[index].reverse();}});//Activar contextMenu
settings.multiselection.rowContextMenu_enabled=settings.jerarquia.contextMenu;},/**
		* Metodo que realiza la post-configuración del plugin jerarquia del componente RUP Table.
		* Este método se ejecuta antes de la incialización del plugin.
		*
		* @name postConfigurejerarquia
		* @function
		* @param {object} settings - Parámetros de configuración del componente.
		*/postConfigurejerarquia:function postConfigurejerarquia(settings){var $self=this,jerarquiaSettings=settings.jerarquia;}});/**
   * Métodos públicos del plugin jerarquia.
   *
   * Los métodos implementados son:
   *
   * reset: Reiniciar los elementos expandidos
   */jQuery.fn.rup_table('extend',{//Reiniciar los elementos expandidos
/**
     * Colapsa los nodos que han sido expandidos.
     *
     * @function reset
     * @example
     * $("#idTable").rup_table("reset");
     */reset:function reset(){jQuery(this).data('tree',[]);jQuery(this).jqGrid('setGridParam',{postData:{'jerarquia':{'tree':[]}}});}});/**
   * Métodos privados del plugin jerarquia.
   *
   * Los métodos implementados son:
   *
   * _parseParentNodes(parentNodes): Procesar valores del tooltip
   * _getJerarquiaChildren($trigger, key, options : Obtener los hijos/descendientes para seleccionar/deseleccionar
   */jQuery.fn.rup_table('extend',{/**
     * Colapsa los nodos que han sido expandidos.
     *
     * @function _parseParentNodes
		 * @param {object} parentNodes - Referencia a los nodos padre.
		 * @private
     * @example
     * $self._parseParentNodes(parentNodes);
     */_parseParentNodes:function _parseParentNodes(parentNodes){var parentNodesTooltipFnc=this.data('settings')['jerarquia']['parentNodesTooltipFnc'],nodes=parentNodes.split(this.data('settings')['jerarquia']['token']).slice(1);//filtrar primer separador
if(parentNodesTooltipFnc===null){//Función por defecto
var str='',tab='&nbsp;&nbsp;';for(var i=0;i<nodes.length;i++){if(i!==nodes.length-1){str+=nodes[i]+'<br/>'+tab+'└&nbsp;';tab+='&nbsp;&nbsp;&nbsp;';}else{str+='<b>'+nodes[i]+'</b>';}}return str;}else{return parentNodesTooltipFnc.call(this,nodes);}},//f(x) del contextMenu de multiselect con jerarquia
_getJerarquiaChildren:function _getJerarquiaChildren($trigger,key,options){var $self=this,settings=$self.data('settings'),//        		rowData = $self.rup_table("getGridParam","data")[$trigger.parent().index()-1],
rowData=$self.rup_table('getRowData',$trigger.parent().attr('id')),ajaxData={jerarquia:{//tree : {}, //Obviar elementos contraidos
parentId:jQuery.jgrid.getAccessor(rowData,settings.primaryKeyCol),child:key.toLowerCase().indexOf('child')!=-1//FIXME: Quitar esto
},filter:$self.rup_table('getFilterParams')};jQuery.extend(true,ajaxData,$self.rup_table('getGridParam','postData'));var primaryKey=jQuery.isArray(settings.primaryKey)?settings.primaryKey[0]:settings.primaryKey;jQuery.rup_ajax({url:settings.filter.childrenUrl,dataType:'json',data:jQuery.toJSON(ajaxData),type:'POST',async:false,contentType:'application/json',beforeSend:function beforeSend(xhr){xhr.setRequestHeader('JQGridModel',true);xhr.setRequestHeader('RUP',jQuery.toJSON({primaryKey:primaryKey}));},success:function success(xhr,ajaxOptions){var children=xhr['children'],children_length=children.length,status=key.indexOf('deselect')!=-1?false:true;for(var i=0;i<children_length;i++){var record=children[i];rowPK=record.pk[primaryKey];//FIXME: Generalizar esto
$self._refreshSelectedElements(settings,status,rowPK,record);}//Actualizar datos
$self.triggerHandler('rupTable_multiselectionUpdated');},error:function error(xhr,ajaxOptions,thrownError){},complete:function complete(xhr,textStatus){}});}});//*******************************************************
// DEFINICIÓN DE LA CONFIGURACION POR DEFECTO DEL PATRON
//*******************************************************
// Parámetros de configuración por defecto para la jerarquía
/**
	* @description Propiedades de configuración del plugin jerarquia del componente RUP Table.
	* @name options
	*
	* @property {string} [treedatatype=json] - Determina el tipo de dato empleado para obtener la representación jerárquica.
	* @property {string} [token] - Carácter separador utilizado para concatenar diferentes identificadores de los registros mostrados en la jerarquía. (por defecto “/”).
	* @property {object} [icons] - Estilos utilizados para cada uno de los elementos visuales de la jerarquía.
	* @property {object} icons.plus - Icono para expandir el nodo.
	* @property {object} icons.minus - Icono para contraer el nodo.
	* @property {object} icons.leaf - Icono correspondiente a un nodo hoja.
	* @property {object} icons.filter - Icono para indicar que el nodo satisface los parámetros de filtrado.
	* @property {boolean} [parentNodesTooltip=true] - Determina si se debe de mostrar un tooltip para cada nodo, en el cual se representa la jerarquía que ocupa respecto a los padres.
	* @property {function} [parentNodesTooltipFnc=null] - Función de callback que permite personalizar el tooltip a mostrar.
	* @property {boolean} [contextMenu=true] - Determina si se muestra el menú contextual para cada nodo.
	*/jQuery.fn.rup_table.plugins.jerarquia={};jQuery.fn.rup_table.plugins.jerarquia.defaults={treedatatype:'json',formEdit:{addEditOptions:{reloadAfterSubmit:true}},jerarquia:{token:'/',icons:{plus:'ui-icon-triangle-1-se',minus:'ui-icon-triangle-1-e',leaf:'ui-icon-none',filter:'ui-icon-star'},parentNodesTooltip:true,parentNodesTooltipFnc:null,contextMenu:true}};})(jQuery);/*!
 * Copyright 2013 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 *//*global jQuery *//**
 * Permite relacionar dos tablas de modo que tengan una relación maestro-detalle. De este modo, los resultados de la tabla detalle se muestran a partir del seleccionado en la tabla maestro.
 *
 * @summary Plugin de edición en línea del componente RUP Table.
 * @module rup_table/masterDetail
 * @example
 *
 * $("#idComponenteMaestro").rup_table({
 *	url: "../jqGridUsuarioMaestro",
 * });
 *
 * $("#idComponente").rup_table({
 * 	url: "../jqGridUsuarioDetalle",
 * 	usePlugins:["masterDetail"],
 * 	inlineEdit:{
 * 		master: "#idComponenteMaestro"
 * 		// Propiedades de configuración del plugin inlineEdit
 * 	}
 * });
 */(function($){jQuery.rup_table.registerPlugin('masterDetail',{loadOrder:10,preConfiguration:function preConfiguration(settings){var $self=this;return $self.rup_table('preConfigureMasterDetail',settings);}});//********************************
// DEFINICIÓN DE MÉTODOS PÚBLICOS
//********************************
/**
	 * Extensión del componente rup_table para permitir la edición de los registros mediante un formulario.
	 *
	 * Los métodos implementados son:
	 *
	 * configureDetailForm(settings): Realiza la configuración interna necesaria para la gestión correcta de la edición mediante un formulario.
	 * deleteElement(rowId, options): Realiza el borrado de un registro determinado.
	 * editElement(rowId, options): Lanza la edición de un registro medainte un formulario de detalle.
	 * newElement(): Inicia el proceso de inserción de un nuevo registro.
	 * showServerValidationFieldErrors(errors): Función encargada de mostrar los errores producidos en la gestión de los datos del mantenimiento.
	 *
	 * Las propiedades de esta extensión almacenadas en el settings son las siguientes:
	 *
	 * settings.$detailForm : Referencia al formulario de detalle mediante el que se realizan las modificaciones e inserciones de registros.
	 * settings.$detailFormDiv : Referencia al div que arropa el formulario de detalle y sobre el que se inicializa el componente rup_dialog.
	 *
	 */jQuery.fn.rup_table('extend',{/**
 		* Metodo que realiza la pre-configuración del plugin masterDetail del componente RUP Table.
 		* Este método se ejecuta antes de la incialización del plugin.
 		*
 		* @name preConfigureMasterDetail
 		* @function
 		* @param {object} settings - Parámetros de configuración del componente.
 		*/preConfigureMasterDetail:function preConfigureMasterDetail(settings){var $self=this,$master;// Obtenemos la referencia del maestro
$master=jQuery(settings.masterDetail.master);settings.masterDetail.$master=$master;$self.on({'rupTable_serializeGridData.rupTable.masterDetail':function rupTable_serializeGridDataRupTableMasterDetail(events,postData){var masterPkObject=$self.rup_table('getMasterTablePkObject');if(masterPkObject!==null){jsonParam={'filter':masterPkObject};jQuery.extend(true,postData,jsonParam);}},'jqGridAddEditBeforeSubmit.rupTable.masterDetail':function jqGridAddEditBeforeSubmitRupTableMasterDetail(event,postData,frmoper){var masterPkObject=$self.rup_table('getMasterTablePkObject');if(masterPkObject!==null){jQuery.extend(postData,masterPkObject);}},'rupTable_searchBeforeSubmit.rupTable.masterDetail':function rupTable_searchBeforeSubmitRupTableMasterDetail(event,postData,jsonData){var masterPkObject=$self.rup_table('getMasterTablePkObject');if(masterPkObject!==null){jsonParam={'filter':masterPkObject};jQuery.extend(true,jsonData,jsonParam);}}});$master.on({'jqGridSelectRow.rupTable.masterDetail':function jqGridSelectRowRupTableMasterDetail(event,rowid,status){var lastRowid=$self.data('tmp.masterDetail.lastRowid');if(lastRowid===undefined||lastRowid!==rowid){if(jQuery.inArray('filter',settings.usePlugins)!==-1){$self.data('tmp.masterDetail.lastRowid',rowid);$self.rup_table('showSearchCriteria');$self.rup_table('filter');}else{$self.rup_table('reloadGrid');}}},'jqGridAfterLoadComplete.multiselection.editRow':function jqGridAfterLoadCompleteMultiselectionEditRow(event,data){if(data.rows.length===0){$self.removeData('tmp.masterDetail.lastRowid');$self.jqGrid('clearGridData');}}});}});jQuery.fn.rup_table('extend',{/**
     * Devuelve un objeto json con la clave primaria del registro correspondiente de la tabla maestra.
     *
     * @function getMasterTablePkObject
		 * @param {object} options - Opciones de configuración de la acción de inserción.
		 * @return {object} - Objeto json con la clave primaria del registro correspondiente de la tabla maestra
     * @example
     * $("#idTable").rup_table("getMasterTablePkObject");
     */getMasterTablePkObject:function getMasterTablePkObject(){var $self=this,settings=$self.data('settings'),$master=settings.masterDetail.$master,masterPkValue=$master.rup_table('getSelectedRows'),masterPkName=settings.masterDetail.masterPrimaryKey;function nestJSON(key,value){var retObj={};var splitedKey=key.split('.');if(splitedKey.length===1){retObj[key]=value;return retObj;}else{retObj[splitedKey[0]]=nestJSON(key.substr(key.indexOf('.')+1),value);return retObj;}}//Inicio compatibilidad con masterPrimaryKey compuestas
if($.isArray(masterPkName)&&masterPkName.length>0&&masterPkValue.length===1){var multiplePkToken=$master.rup_table('getGridParam','multiplePkToken');var splitedMasterPkValue=masterPkValue[0].split(multiplePkToken);var retPkObj={};if(splitedMasterPkValue.length===masterPkName.length){$.each(masterPkName,function(index,value){jQuery.extend(true,retPkObj,nestJSON(value,splitedMasterPkValue[index]));});}return retPkObj;//Fin compatibilidad con masterPrimaryKey compuestas
}else{if(masterPkValue.length===1){return nestJSON(masterPkName,masterPkValue[0]);}else if(masterPkValue.length===0){return null;}}}});//*******************************************************
// DEFINICIÓN DE LA CONFIGURACION POR DEFECTO DEL PATRON
//*******************************************************
/**
	* @description Propiedades de configuración del plugin masterDetail del componente RUP Table.
	*
	* @name options
	*
	* @property {string} master - Selector jQuery que referencia al componente maestro.
	* @property {string} masterPrimaryKey -  Clave primaria del componente maestro.
	*/// Parámetros de configuración por defecto para la acción de eliminar un registro.
jQuery.fn.rup_table.plugins.masterDetail={};jQuery.fn.rup_table.plugins.masterDetail.defaults={};})(jQuery);/*!
 * Copyright 2013 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 *//*global jQuery *//**
 * Genera los controles necesarios para permitir al usuario la exportación de los datos mostrados en la tabla.
 *
 * @summary Plugin de reporting del componente RUP Table.
 * @module rup_table/report
 * @example
 *
 * $("#idComponente").rup_table({
 * 	url: "../jqGridUsuario",
 * 	usePlugins:["report"],
 * 	report:{
 * 		// Propiedades de configuración del report inlineEdit
 * 	}
 * });
 */(function($){/**
	 * Definición de los métodos principales que configuran la inicialización del plugin.
	 *
	 * postConfiguration: Método que se ejecuta después de la invocación del componente jqGrid.
	 *
	 */jQuery.rup_table.registerPlugin('report',{loadOrder:11,preConfiguration:function preConfiguration(settings){var $self=this;return $self.rup_table('preConfigureReport',settings);},postConfiguration:function postConfiguration(settings){var $self=this;return $self.rup_table('postConfigureReport',settings);}});//********************************
// DEFINICIÓN DE MÉTODOS PÚBLICOS
//********************************
/**
	 * Extensión del componente rup_table para permitir la gestión de la generaciónd de informes.
	 *
	 * Los métodos implementados son:
	 *
	 * preConfigureReport(settings): Método que define la preconfiguración necesaria para el correcto funcionamiento del componente.
	 *
	 * postConfigureReport(settings): Método que define la preconfiguración necesaria para el correcto funcionamiento del componente.
	 */jQuery.fn.rup_table('extend',{/**
		* Metodo que realiza la pre-configuración del plugin report del componente RUP Table.
		* Este método se ejecuta antes de la incialización del plugin.
		*
		* @name preConfigureReport
		* @function
		* @param {object} settings - Parámetros de configuración del componente.
		*/preConfigureReport:function preConfigureReport(settings){var $self=this;},/**
		* Metodo que realiza la post-configuración del plugin report del componente RUP Table.
		* Este método se ejecuta antes de la incialización del plugin.
		*
		* @name postConfigureReport
		* @function
		* @param {object} settings - Parámetros de configuración del componente.
		* @fires module:rup_table#rupTable_serializeReportData
		*/postConfigureReport:function postConfigureReport(settings){var $self=this,colModel=$self.rup_table('getColModel'),reportsColums,reportSettings=settings.report;reportsColums=$self._getReportColumns(colModel,settings);/*
			 * INICIALIZACION DE VALORES POR DEFECTO
			 */// Inicialización de la toolbar del componente table en caso de que no se especifique
if(reportSettings.appendTo===undefined){reportSettings.appendTo=settings.toolbar.id;}// Se toman los parámetros columns globales como base para los específicos
jQuery.each(reportSettings.buttons[0].buttons,function(index,element){element.columns=$.extend(true,{},reportSettings.columns,element.columns);if(element.columns.grid===undefined){element.columns.grid=settings.id;}if(element.columns.customNames===undefined){element.columns.customNames=reportsColums;}if(element.columns.click===undefined){element.columns.click=function(){};}});reportSettings.fncGetGridParam=function(){var $self=this,settings=$self.data('settings'),data={},filterData={};jQuery.each($self.jqGrid('getGridParam','postData'),function(index,elem){if(jQuery.inArray(index,settings.report.sendPostDataParams)!==-1){data[index]=elem;}});if(settings.filter!==undefined&&settings.filter.$filterContainer!==undefined){filterData=$self.rup_table('getFilterParams');}jQuery.extend(true,data,filterData);$self.triggerHandler('rupTable_serializeReportData',[data]);return $.rup_utils.unnestjson(data);};/*
			 * FIN DE INICIALIZACION DE VALORES POR DEFECTO
			 */jQuery.rup_report(reportSettings);}});jQuery.fn.rup_table('extend',{/**
     * Devuelve las columnas de la tabla para las que se va a generar el informe.
     *
     * @function _processMatchedRow
		 * @private
		 * @param {object} colModel - colModel correspondiente a la tabla.
		 * @param {object} settings - Parámetros de configuración de la página.
		 * @return {string[]} - Array con el nombre de las columnas.
     * @example
     * $self._getReportColumns(colModel, settings);
     */_getReportColumns:function _getReportColumns(colModel,settings){return jQuery.map(colModel,function(elem,index){if(jQuery.inArray(elem.name,settings.report.excludeColumns)===-1){return elem.name;}else{return null;}});}});//*******************************************************
// DEFINICIÓN DE LA CONFIGURACION POR DEFECTO DEL PATRON
//*******************************************************
/**
	* @description Propiedades de configuración del plugin report del componente RUP Table.
	*
	* @name options
	*
	* @property {object} [columns] - Permite especificar mediante un array, los identificadores de las columnas que van a ser mostradas en el informe.
	* @property {string[]} [excludeColumns] - Determina las columnas que van a ser excluidas de la generación del informe.
	* @property {string[]} [sendPostDataParams] - Parámetros del jqGrid que van a ser enviados en la petición de generación del informe.
	*/jQuery.fn.rup_table.plugins.report={};jQuery.fn.rup_table.plugins.report.defaults={report:{columns:{},excludeColumns:['rupInfoCol','cb'],sendPostDataParams:['_search','core','nd','page','rows','sidx','sord']}};/* ********* *//* EVENTOS
  /* ********* *//**
   * Permite asociar un manejador al evento que se produce en el momento en el que se construye el objeto que se envía al servidor para solicitar la generación del informe. Permite la modificación del objeto postData para añadir, modificar o eliminar los parámetros que van a ser enviados.
   *
   * @event module:rup_table#rupTable_serializeReportData
   * @property {Event} event - Objeto Event correspondiente al evento disparado.
	 * @property {Event} dta - Linea de la tabla destinada a la búsqueda.
   * @example
   * $("#idComponente").on("rupTable_serializeReportData", function(event, data){ });
   */})(jQuery);/*!
 * Copyright 2013 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 *//*global jQuery *//**
 * Gestiona las operaciones de filtrado múltiple de datos sobre el origen de datos que utiliza el componente.
 *
 * @summary Plugin de filtrado múltiple del componente RUP Table.
 * @module rup_table/multifilter
 * @example
 *
 * $("#idComponente").rup_table({
 * 	url: "../jqGridUsuario",
 * 	usePlugins:["multifilter"],
 * 	filter:{
 * 		// Propiedades de configuración del plugin multifilter
 * 	}
 * });
 */(function($){/**
	 * Definición de los métodos principales que configuran la inicialización
	 * del plugin.
	 *
	 * postConfiguration: Método que se ejecuta después de la invocación del
	 * componente jqGrid.
	 *
	 */jQuery.rup_table.registerPlugin('multifilter',{loadOrder:15,preConfiguration:function preConfiguration(settings){var $self=this;return $self.rup_table('preConfigureMultifilter',settings);},postConfiguration:function postConfiguration(settings){var $self=this;return $self.rup_table('postConfigureMultifilter',settings);}});// ********************************
// DEFINICIÓN DE MÉTODOS PÚBLICOS
// ********************************
/**
	 * Extensión del componente rup_table para permitir la gestión del filtrado
	 * de registros de la tabla.
	 *
	 * Los métodos implementados son:
	 *
	 * postConfigureFilter(settings): Método que define la preconfiguración
	 * necesaria para el correcto funcionamiento del componente.
	 *
	 * Se almacena la referencia de los diferentes componentes:
	 *
	 * settings.filter.$filterContainer : Contenedor del formulario de filtrado
	 * settings.filter.$filterButton : Botón que realiza el filtrado
	 * settings.filter.$cleanButton : Enlace para limpiar el formulario
	 * settings.filter.$collapsableLayer : Capa que puede ser ocultada/mostrada
	 * settings.filter.$toggleIcon1Id : Control que oculta muestra el fomulario
	 * settings.filter.$filterSummary : Contenedor donde se especifican los
	 * criterios de filtrado
	 *
	 */jQuery.fn.rup_table('extend',{/**
			* Metodo que realiza la pre-configuración del plugin de filtrado múltiple del componente RUP Table.
			* Este método se ejecuta antes de la incialización del plugin.
			*
			* @name preConfigureMultifilter
			* @function
			* @param {object} settings - Parámetros de configuración del componente.
			*/preConfigureMultifilter:function preConfigureMultifilter(settings){var $self=this,tableId=settings.id,multifilterSettings=settings.multifilter,dropdownDialogId,$dropdownDialog,$dropdownDiaglogTemplate;//definicion de variables con los selectores
multifilterSettings.$dropdownDialog=$('#'+settings.id+'_multifilter_dropdownDialog');//definicion de variables con ids
multifilterSettings.dropdownDialogId=settings.id+'_multifilter_dropdownDialog';$dropdownDiaglogTemplate=$self.rup_table('getMultifilterDialogTemplate',settings);settings.filter.$filterContainer.after($dropdownDiaglogTemplate);$self.rup_table('configureMultifilter',settings);// configuracion del resumen del filtro para que
// apareza el nombre del filtro
settings.multifilter.fncFilterName=function(searchString){if(multifilterSettings.$comboLabel==undefined){//&& settings.$firstStartUp  && multifilterSettings.$filterDefaultName!=undefined){
if(multifilterSettings.$filterDefaultName!==undefined)searchString=multifilterSettings.$filterDefaultName+'  {'+searchString+'}   ';}else if(multifilterSettings.$comboLabel!=undefined&&settings.$firstStartUp){if(multifilterSettings.$comboLabel.val()==''&&multifilterSettings.$filterDefaultName!=undefined){if(multifilterSettings.$filterDefaultName!==undefined)searchString=multifilterSettings.$filterDefaultName+'  {'+searchString+'}   ';}}else if(multifilterSettings.$comboLabel.val()!=''&&multifilterSettings.$filterWithName){multifilterSettings.$filterWithName=false;searchString=multifilterSettings.$comboLabel.val()+'  {'+searchString+'}   ';}return searchString;};},/**
			* Metodo que realiza la post-configuración del plugin de filtrado múltiple del componente RUP Table.
			* Este método se ejecuta antes de la incialización del plugin.
			*
			* @name postConfigureMultifilter
			* @function
			* @fires module:rup_table#rupTable_multifilter_fillForm
			* @param {object} settings - Parámetros de configuración del componente.
			*/postConfigureMultifilter:function postConfigureMultifilter(settings){var $self=this,multifilterSettings=settings.multifilter,filterSettings,$dropdownButton,$combo,$comboLabel,$defaultCheck,$feedback,$comboButton,$closeDialog,dropdownButtonConfig;/*
							 * $("#"+settings.id+"_multifilter_combo_label").on("change",
							 * function(){
							 *
							 * if
							 * ($("#"+settings.id+"_multifilter_combo_label").val()==""){
							 * $self._toggleButtons(settings.id,false); }else{
							 * $self._toggleButtons(settings.id,true); } });
							 */dropdownButtonConfig=$self[0]._ADAPTER.multifilter.dropdown;settings.filter.$filterButton.rup_button({dropdown:{dropdownIcon:dropdownButtonConfig.dropdownIcon,dropdownDialog:multifilterSettings.dropdownDialogId,dropdownDialogConfig:{title:dropdownButtonConfig.dropdownDialogConfig.title+$.rup.i18n.base.rup_table.plugins.multifilter.tittle,width:'450px',buttons:[{id:settings.id+'_multifilter_BtnSave',"class":'btn-outline-primary',text:$.rup.i18n.base.rup_table.plugins.multifilter.save,click:function click(){if($self._checkLabel(settings)){// creo objeto Filter con los datos del formulario del filtro
var filter=$self._createFilterFromForm(settings);var bfr=$self.triggerHandler('rupTable_beforeAdd');if(bfr===false||bfr==='stop'){multifilterSettings.$feedback.rup_feedback('set',$.rup.i18n.base.rup_table.plugins.multifilter.errorValidate,'error');return;}// añado el filtro
$self.rup_table('addFilter',filter);}}},{id:settings.id+'_multifilter_BtnApply',"class":'btn-outline-primary',text:$.rup.i18n.base.rup_table.plugins.multifilter.apply,click:function click(){//Deshabilitar el nombre del filtro en el filterSummary una vez que ha terminado el filtro por defecto
if(settings.$firstStartUp){settings.$firstStartUp=false;}if($self._checkLabel(settings)){multifilterSettings.$filterWithName=true;var valorFiltro=$self._searchFilterInCombo(settings);if(valorFiltro!=undefined){//limpiamos el filtro
$self.rup_table('cleanFilterForm');//Cargamos de nuevo el filtro en el formulario del filtro
// rellenar el formulario del filtro
$self.triggerHandler('rupTable_multifilter_fillForm',valorFiltro);$self._fillForm(valorFiltro);$self.rup_table('filter');multifilterSettings.$closeDialog.click();}else{multifilterSettings.$feedback.rup_feedback('set',$.rup.i18n.base.rup_table.plugins.multifilter.errorNoexiste,'error');}//
//$self.rup_table("filter");
// crea el tooptip del resumen del filtro
//var filterCriteria = $self._createTooltip();
}}},{id:settings.id+'_multifilter_BtnRemove',"class":'btn-outline-primary',text:$.rup.i18n.base.rup_table.plugins.multifilter.remove,click:function click(){if($self._checkLabel(settings)){// creo objeto Filter con los datos del formulario del filtro
var filter=$self._createFilterFromForm(settings);// borro el filtro
$self.rup_table('deleteFilter',filter);}}},{text:$.rup.i18n.base.rup_table.plugins.multifilter.cancel,click:function click(){var filtroAnterior=$self.data('filtroAnterior');if(filtroAnterior!=null){//var xhrArray=$.rup_utils.jsontoarray(filtroAnterior);
$self.rup_table('cleanFilterForm');//$.rup_utils.populateForm(filtroAnterior,settings.filter.$filterForm);
$self.triggerHandler('rupTable_multifilter_fillForm',filtroAnterior);$self._fillForm(filtroAnterior);}//limpio el filtro del dropdownDIalog
multifilterSettings.$comboLabel.val('');multifilterSettings.$closeDialog.click();},btnType:$.rup.dialog.LINK}]}}});//Deshabilitar el nombre del filtro en el filterSummary una vez que ha terminado el filtro por defecto
$self.on('rupTable_beforeFilter',function(event){/*if (settings.$firstStartUp){

									settings.$firstStartUp=false;
								}*/});//definincion de variables con los selectores
multifilterSettings.$dropdownButton=$('#'+settings.id+'_filter_filterButton_dropdown');multifilterSettings.$combo=$('#'+settings.id+'_multifilter_combo');multifilterSettings.$comboLabel=$('#'+settings.id+'_multifilter_combo_label');multifilterSettings.$comboButton=$('#'+settings.id+'_multifilter_dropdownDialog .rup-combobox-toggle');multifilterSettings.$defaultCheck=$('#'+settings.id+'_multifilter_defaultFilter');multifilterSettings.$feedback=$('#'+settings.id+'_multifilter_dropdownDialog_feedback');multifilterSettings.$closeDialog=$('#closeText_'+settings.id+'_multifilter_dropdownDialog');// dialog modal para no cambiar el filtro mientras
// se gestionan los mismos
$('#'+multifilterSettings.dropdownDialogId).rup_dialog('setOption','modal',true);$('#'+multifilterSettings.dropdownDialogId).rup_dialog('setOption','draggable',false);$('#'+multifilterSettings.dropdownDialogId).rup_dialog('setOption','resizable',false);// $('#'+multifilterSettings.dropdownDialogId).parent().addClass("rup_multifilter_container");
$('#'+multifilterSettings.dropdownDialogId).parent().css('width','500px');multifilterSettings.$dropdownButton.on('click',function(){//guardo el filtroAnterior
var valorFiltro=form2object(settings.filter.$filterContainer[0]);var xhrArray=$.rup_utils.jsontoarray(valorFiltro);$self.data('filtroAnterior',valorFiltro);//Foco al label al entrar al dialog
multifilterSettings.$comboLabel.focus();});$self._configCombo(settings);multifilterSettings.$feedback.rup_feedback({block:false});//gesión por filtroPorDefecto
//$self.rup_table("showSearchCriteria");
//if(filtroDefault!=null)
//$("#"+settings.id+"_filter_summary").prepend(filtroDefault.filterName +" "+ $("#"+settings.id+"_filter_summary").val() );
//bug IE que al cerrar el dialog con el combo desplegado , la lista del combo sigue abierta
$('.rup-dropdown-dialog').on('dialogclose',function(){multifilterSettings.$comboLabel.autocomplete('widget').hide();});//la primera vez que cancelas el filtroAnterior es el filtroPorDefecto
var valorFiltro=form2object(settings.filter.$filterContainer[0]);xhrArray=$.rup_utils.jsontoarray(valorFiltro);$self.data('filtroAnterior',valorFiltro);//$self.rup_table("filter");
//settings.filter.$filterButton.trigger("click");
//$self.triggerHandler("rupTable_multifilter_fillForm",form2object(settings.filter.$filterContainer[0]));
$self.on({'rupTable_beforeAdd.multifilter.validate':function rupTable_beforeAddMultifilterValidate(){//filterSettings.$filterContainer.rup_validate("resetForm");
if(multifilterSettings!==undefined){if(!settings.$firstStartUp){return settings.filter.$filterContainer.valid();}else{return null;}}else{return settings.filter.$filterContainer.valid();}}});}});// ********************************
// DEFINICIÓN DE MÉTODOS PÚBLICOS
// ********************************
/**
	 * Métodos públicos del plugin filter.
	 *
	 * cleanFilterForm: Realiza una limpieza de los campos del formulario.
	 * filter: Lanza el filtrado de la tabla de acuerdo a los criterios
	 * indicados en el formulario. toggleFilterForm: Método encargado de ocultar
	 * y mostrar el formulario de filtrado.
	 *
	 */jQuery.fn.rup_table('extend',{/**
     * Devuelve la template html empleada para renderizar los controles del formulario de filtrado múltiple.
     *
     * @function  getMultifilterDialogTemplate
		 * @param {object} settings - Propiedades de configuración del componente.
		 * @return {object} - Objeto jQuery con el contenido html de la template.
     * @example
     * $("#idComponente").rup_table("getMultifilterDialogTemplate", settings);
     */getMultifilterDialogTemplate:function getMultifilterDialogTemplate(settings){var $self=this,multifilterSettings=settings.multifilter;var $dropdownDiaglogTemplate=jQuery('<div id="'+multifilterSettings.dropdownDialogId+'" style="display:none" class="rup_multifilter_dropdown">'+'<div id="'+multifilterSettings.dropdownDialogId+'_feedback"></div>'+'<form>'+'<fieldset class="dropdownButton-inputs">'+'<div id="'+multifilterSettings.dropdownDialogId+'_columna_cnt">'+'<div class="form-row">'+'<div id="'+multifilterSettings.dropdownDialogId+'_lineaCombo"  class="form-group fix-align col-sm">'+'<label for="'+settings.id+'_multifilter_combo" class="formulario_linea_label">'+$.rup.i18n.base.rup_table.plugins.multifilter.filters+'</label>'+'<input id="'+settings.id+'_multifilter_combo" class="rup_multifilter_selector" />'+'</div>'+'</div>'+'<div class="form-row">'+'<div id="'+multifilterSettings.dropdownDialogId+'_lineaDefault" class="form-group col-sm">'+'<label for="'+settings.id+'_multifilter_defaultFilter" class="formulario_linea_label">'+$.rup.i18n.base.rup_table.plugins.multifilter.defaultFilter+'</label>'+'<input type="checkbox" id="'+settings.id+'_multifilter_defaultFilter" class="formulario_linea_input form-control"/>'+'</div>'+'</div>'+'</div>'+'</fieldset>'+'</form>'+'</div>');return $dropdownDiaglogTemplate;},/**
     * Realiza la configuración interna del plugin multifilter a partir de las propiedades de configuración indicadas.
     *
     * @function  configureMultifilter
		 * @param {object} settings - Propiedades de configuración del componente.
     * @example
     * $("#idComponente").rup_table("configureMultifilter", settings);
     */configureMultifilter:function configureMultifilter(settings){var $self=this,multifilterSettings=settings.multifilter,$filterForm;$self.data('settings',settings);settings.filter.$filterForm=$('#'+settings.id+'_filter_form');var options_ejie_combo={source:[{label:'Si',value:'0'},{label:'No',value:'1'}],width:120,blank:''};// jQuery("#"+settings.id+"_multifilter_combo").rup_combo(options_ejie_combo);
var selector;if(multifilterSettings.idFilter!=null){selector=multifilterSettings.idFilter;}else{selector=settings.id;}var usuario;if(multifilterSettings.userFilter!=null){usuario=multifilterSettings.userFilter;}else{usuario=LOGGED_USER;}var getDefault;if(multifilterSettings.getDefault!=null){getDefault=multifilterSettings.getDefault;}else{getDefault=true;}jQuery('#'+settings.id+'_multifilter_combo').rup_autocomplete({source:settings.baseUrl+'/multiFilter/getAll?filterSelector='+selector+'&user='+usuario,sourceParam:{label:'filterName',value:'filterDefault',data:'filterValue',category:'filter'},method:'GET',contains:false,combobox:true,menuAppendTo:$('#'+multifilterSettings.dropdownDialogId).parent(),appendTo:$('#'+multifilterSettings.dropdownDialogId).parent(),select:function select(){var valorFiltro=$self._searchFilterInCombo(settings);//limpiar Filtro
//$self.rup_table("resetForm",settings.filter.$filterForm);
$self.rup_table('cleanFilterForm');// rellenar el formulario del filtro
//$.rup_utils.populateForm(xhrArray,settings.filter.$filterForm);
$self.triggerHandler('rupTable_multifilter_fillForm',valorFiltro);$self._fillForm(valorFiltro);//
}});jQuery('#'+settings.id+'_multifilter_combo_label').on('autocompleteopen',function(){$(this).data('uiAutocomplete').menu.element.css('zIndex',Number($('#'+multifilterSettings.dropdownDialogId).parent().css('zIndex'))+1);if($(this).data('tmp.data')!==undefined){var data=$(this).data('tmp.data');var count=-1;var objeto=$.grep(data,function(obj,i){if(obj.filterDefault){count=i;return obj;}});if(objeto!==undefined){var link=$('#'+settings.id+'_multifilter_combo_menu a:eq('+count+')');link.css('font-weight','bold');}}});$('.jstree').on('rup_filter_treeLoaded',function(event,data){$(this).rup_tree('setRupValue',data);//$self.rup_table("showSearchCriteria");
});settings.filter.$cleanButton.on('click',function(){multifilterSettings.$combo.rup_autocomplete('set','','');settings.filter.$filterSummary.html('<i></i>');});},/**
     * Función que añade un filtro al multifiltro
     *
     * @function  addFilter
		 * @param {object} filter - Objeto json con la información del filtro a añadir.
		 * @fires module:rup_table#rupTable_multifilter_beforeAdd
     * @example
     * $("#idComponente").rup_table("addFilter", filter);
     */addFilter:function addFilter(filter){var $self=this;var settings=$self.data('settings');var multifilterSettings=settings.multifilter;// self.data("settings");
if(multifilterSettings.idFilter!=null){filter.filtro.filterSelector=multifilterSettings.idFilter;}// add Filter
$.rup_ajax({url:settings.baseUrl+'/multiFilter/add',type:'POST',data:$.toJSON(filter),dataType:'json',showLoading:false,contentType:'application/json',async:false,beforeSend:function beforeSend(xhr,options){return $self.triggerHandler('rupTable_multifilter_beforeAdd',[xhr,options]);},success:function success(data,status,xhr){multifilterSettings.$savedFilterName=data.filterName;multifilterSettings.$savedFilterValue=data.filterValue;multifilterSettings.$feedback.rup_feedback('set',$.rup.i18n.base.rup_table.plugins.multifilter.ok,'ok');//multifilterSettings.$combo.rup_autocomplete("set","", "");
multifilterSettings.$comboLabel.data('tmp.loadObjects.term',null);multifilterSettings.$comboLabel.data('loadObjects',{});// $("#"+settings.id+"_multifilter_combo_label").data("tmp.loadObjects.term",term);
multifilterSettings.$comboLabel.data('tmp.data',{});if(multifilterSettings.$comboLabel.autocomplete('widget').is(':visible')){multifilterSettings.$comboLabel.autocomplete('widget').hide();}},error:function error(xhr,ajaxOptions,thrownError){multifilterSettings.$feedback.rup_feedback('set',$.rup.i18n.base.rup_table.plugins.multifilter.error,'error');}});},/**
		 * Función que elimina un filtro del multifiltro.
		 *
		 * @function  deleteFilter
		 * @param {object} filter - Objeto json con la información del filtro a eliminar.
		 * @example
		 * $("#idComponente").rup_table("deleteFilter", filter);
		 */deleteFilter:function deleteFilter(filter){var $self=this;var settings=$self.data('settings');var multifilterSettings=settings.multifilter;//reiniciar filter salvado
multifilterSettings.$savedFilterName=undefined;multifilterSettings.$savedFilterValue=undefined;if(multifilterSettings.idFilter!=null){filter.filtro.filterSelector=multifilterSettings.idFilter;}// delete
$.rup_ajax({url:settings.baseUrl+'/multiFilter/delete',type:'POST',data:$.toJSON(filter),dataType:'json',showLoading:false,contentType:'application/json',async:false,success:function success(data,status,xhr){multifilterSettings.$feedback.rup_feedback('set',$.rup.i18n.base.rup_table.plugins.multifilter.ok,'ok');multifilterSettings.$combo.rup_autocomplete('set','','');multifilterSettings.$comboLabel.data('tmp.loadObjects.term',null);multifilterSettings.$comboLabel.data('loadObjects',{});// $("#"+settings.id+"_multifilter_combo_label").data("tmp.loadObjects.term",term);
multifilterSettings.$comboLabel.data('tmp.data',{});if(multifilterSettings.$comboLabel.autocomplete('widget').is(':visible')){multifilterSettings.$comboLabel.autocomplete('widget').hide();}if(data.filterFeedback=='no_records'){multifilterSettings.$feedback.rup_feedback('set',$.rup.i18n.base.rup_table.plugins.multifilter.noRecords,'error');}},error:function error(xhr,ajaxOptions,thrownError){multifilterSettings.$feedback.rup_feedback('set',$.rup.i18n.base.rup_table.plugins.multifilter.error,'error');}});}});// *******************************
// DEFINICIÓN DE MÉTODOS PRIVADOS
// *******************************
jQuery.fn.rup_table('extend',{/**
     * Genera el objeto json de datos de filtrado correspondiente al formulario empleado.
     *
     * @function _createFilterFromForm
		 * @private
		 * @param {object} settings - Propiedades de configuración del componente.
		 * @return {object} - Objeto json con la información de filtrado del formulario.
     * @example
     * $self._createFilterFromForm(settings);
     */_createFilterFromForm:function _createFilterFromForm(settings){var multifilterSettings=settings.multifilter;var dataForm=form2object(settings.filter.$filterContainer[0]);//cambiar la fecha a milisegundos para guardar en bd
var fecha;$.each($('[ruptype=\'date\']',settings.filter.$filterContainer),function(index,item){fecha=$(item).datepicker('getDate');if(fecha!=null)dataForm[item.name]=fecha.getTime().toString();});var dataFormJson=$.toJSON(dataForm);var usuario;if(multifilterSettings.userFilter!=null){usuario=multifilterSettings.userFilter;}else{usuario=LOGGED_USER;}var filter={filtro:{filterSelector:settings.id,filterName:multifilterSettings.$comboLabel.val(),filterValue:dataFormJson,filterDefault:multifilterSettings.$defaultCheck.is(':checked'),filterUser:usuario}};return filter;},/**
     * Inicializa el combo de selección de filtrado a aplicar en el fomulario.
     *
     * @function _configCombo
		 * @private
		 * @param {object} settings - Propiedades de configuración del componente.
     * @example
     * $self._configCombo(settings);
     */_configCombo:function _configCombo(settings){var multifilterSettings=settings.multifilter;multifilterSettings.$comboLabel.on('change',function(){settings.filter.$filterSummary.html('<i></i>');});// si el filtro es el predefinido que aparezca en negrita
multifilterSettings.$comboLabel.data('uiAutocomplete')._renderItem=function(ul,item){return $('<li></li>').data('item.autocomplete',item).append('<a>'+item.label+'</a>').appendTo(ul);};jQuery('#'+settings.id+'_multifilter_combo_label').on('rupAutocomplete_loadComplete',function(event,data){var count=-1;var objeto=$.grep(data,function(obj,i){if(obj.filterDefault){count=i;return obj;}});if(objeto!==undefined){var link=$('#'+settings.id+'_multifilter_combo_menu a:eq('+count+')');link.css('font-weight','bold');}});multifilterSettings.$comboLabel.off('blur click');multifilterSettings.$comboLabel.attr('placeholder',$.rup.i18n.base.rup_table.plugins.multifilter.input);multifilterSettings.$comboLabel.on('blur',function(event){// Obtener datos de si viene de
// seleccionar elemento o si el
// menú de selección está
// desplegado
var selected=multifilterSettings.$combo.data('selected'),isShowingMenu=$('.ui-autocomplete:visible').length>0?true:false;// Borrar índicador de que viene
// de seleccionar elemento
multifilterSettings.$combo.data('selected',false);// Si es un evento de teclado
// pero no es ENTER, omitir esta
// función
if(event.type==='keydown'&&event.keyCode!==13){return true;}if(isShowingMenu===true&&event.type==='keydown'){multifilterSettings.$combo.focus();event.stopPropagation();return true;}var autoCompObject=$(event.currentTarget),loadObjects=multifilterSettings.$comboLabel.data('loadObjects');if(settings.getText==true){if(loadObjects[autoCompObject.val()]!==undefined){multifilterSettings.$combo.val(autoCompObject.val());multifilterSettings.$combo.attr('rup_autocomplete_label',autoCompObject.val());}else{multifilterSettings.$combo.val(autoCompObject.val());multifilterSettings.$combo.attr('rup_autocomplete_label',autoCompObject.val());}}else{if(loadObjects[autoCompObject.val()]!==undefined){multifilterSettings.$combo.val(loadObjects[autoCompObject.val()]);multifilterSettings.$combo.attr('rup_autocomplete_label',loadObjects[autoCompObject.val()]);}else{autoCompObject.autocomplete('close');}}// Si el evento es ENTER y viene
// de seleccionar un elemento o
// el menú se estaba mostrando,
// omitir resto de funciones
// (ej. buscar)
if(event.type==='keydown'&&event.keyCode===13&&(selected||isShowingMenu)){return false;}});multifilterSettings.$comboButton.off('click mousedown');multifilterSettings.$comboButton.on('blur',function(){if(multifilterSettings.$comboLabel.autocomplete('widget').is(':visible')){multifilterSettings.$comboLabel.autocomplete('widget').hide();}});multifilterSettings.$comboButton.on('click',function(){if(multifilterSettings.$comboLabel.autocomplete('widget').is(':visible')){multifilterSettings.$comboLabel.autocomplete('widget').hide();}else{multifilterSettings.$comboLabel.autocomplete('search','');multifilterSettings.$comboLabel.autocomplete('widget').show();multifilterSettings.$comboLabel.autocomplete('widget').trigger('focus');}});},//						_toggleButtons : function(id, visibles) {
//
//							if (visibles == false) {
//								$("#" + id + "_multifilter_BtnSave").button(
//										"disable");
//								$("#" + id + "_multifilter_BtnApply").button(
//										"disable");
//								$("#" + id + "_multifilter_BtnRemove").button(
//										"disable");
//
//							} else {
//								$("#" + id + "_multifilter_BtnSave").button(
//										"enable");
//								$("#" + id + "_multifilter_BtnApply").button(
//										"enable");
//								$("#" + id + "_multifilter_BtnRemove").button(
//										"enable");
//							}
//						},
/**
     * Valida el label que se introduce asociado al filtrado que se va a añadir.
     *
     * @function _checkLabel
		 * @private
		 * @param {object} settings - Propiedades de configuración del componente.
		 * @return {boolean} - Devuelve si es válido o no el nombre introducido para el filtro.
     * @example
     * $self._configCombo(settings);
     */_checkLabel:function _checkLabel(settings){var multifilterSettings=settings.multifilter;if($.trim(multifilterSettings.$comboLabel.val())==''){multifilterSettings.$feedback.rup_feedback('set',$.rup.i18n.base.rup_table.plugins.multifilter.emptyName,'error');return false;}else if(multifilterSettings.$comboLabel.val().length>settings.multifilter.labelSize){multifilterSettings.$feedback.rup_feedback('set',$.rup.i18n.base.rup_table.plugins.multifilter.tooLong,'error');return false;}return true;},/**
     * Devuelve el json de filtrado asociado al filtro seleccionado en el combo.
     *
     * @function _searchFilterInCombo
		 * @private
		 * @param {object} settings - Propiedades de configuración del componente.
		 * @return {object} - Json de filtrado asociado al filtro seleccionado en el combo.
     * @example
     * $self._searchFilterInCombo(settings);
     */_searchFilterInCombo:function _searchFilterInCombo(settings){var multifilterSettings=settings.multifilter;var name=$('#'+settings.id+'_multifilter_combo_label').val();// var listaFiltros = $("#" + this.id+
// "_label").data("tmp.data");
var listaFiltros=$('#'+settings.id+'_multifilter_combo_label').data('tmp.data');// Busco el valor del filtro
var objFiltro=$.grep(listaFiltros,function(obj,i){if(obj.label==name)return obj;});// si es filtro por defecto,
// checkeo el check "Filtro
// por defecto"
if(objFiltro.length!=0){multifilterSettings.$defaultCheck.attr('checked',objFiltro[0].filterDefault);var valorFiltro=$.parseJSON(objFiltro[0].value);var xhrArray=[];// $.map(valorFiltro,function(item) {
// xhrArray[item.name] = item.value;
// });
xhrArray=$.rup_utils.jsontoarray(valorFiltro);}if(valorFiltro==undefined&&multifilterSettings.$savedFilterName!=undefined){if(multifilterSettings.$savedFilterName===name)var valorFiltro=$.parseJSON(multifilterSettings.$savedFilterValue);}return valorFiltro;},/**
		 * Inicializa los campos del formulario con los valores correspondientes al filtro seleccionado.
		 *
		 * @function _fillForm
		 * @private
		 * @param {object} filtroNuevo - Objeto json con los valores de filtrado.
		 * @example
		 * $self._fillForm(data);
		 */_fillForm:function _fillForm(filtroNuevo){var $self=this;var settings=$self.data('settings');//cambiar milisengudos a fecha (el formato de bd del  fecha es milisegundos)
$('[ruptype=\'date\']',settings.filter.$filterContainer).each(function(index,elem){var $campo=jQuery(elem);var fechaString;var jsonFecha=filtroNuevo[elem.name];if(jsonFecha!=undefined){if(jsonFecha.search('/')==-1){var dateFromJson=new Date(parseInt(jsonFecha));var dateFormat=$campo.data('datepicker').settings.dateFormat;if($campo.data('datepicker').settings.datetimepicker){// Cuando es fecha-hora
var dateObj={hour:dateFromJson.getHours(),minute:dateFromJson.getMinutes(),second:dateFromJson.getSeconds()};fechaString=$.datepicker.formatDate(dateFormat,dateFromJson)+' '+$.timepicker._formatTime(dateObj,'hh:mm:ss');}else{// Solo fecha
fechaString=$.datepicker.formatDate(dateFormat,dateFromJson);}filtroNuevo[elem.name]=fechaString;}}});// Formatear datos
// var valorFiltro = $.parseJSON(filtroNuevo);
var xhrArray=$.rup_utils.jsontoarray(filtroNuevo);// evento antes de rellenar el form
// $self.triggerHandler("rupTable_multifilter_fillForm",filtroNuevo);
// rellenar el formulario
$.rup_utils.populateForm(xhrArray,$(this.selector+'_filter_form'));// $self._fillForm(filtroNuevo);
// $self.rup_table("filter");
}});// *******************************************************
// DEFINICIÓN DE LA CONFIGURACION POR DEFECTO DEL PATRON
// *******************************************************
/**
	 * Parámetros de configuración por defecto para el plugin filter.
	 *
	 *//**
	* @description Propiedades de configuración del plugin multifilter del componente RUP Table.
	*
	* @name options
	*
	* @property {string} [idFilter] - Permite asignar un identificador al filtro. Debe ser único para toda la aplicación. En caso de no asignar un id, se asigna el selector del rup_table.
	* @property {string} labelSize - Permite especificar el tamaño máximo permitido para el nombre del filtro. Es una propiedad obligatoria.
	* @property {string} [userFilter] - En caso de que la aplicación donde se tiene que implementar el multifiltro no implemente la variable LOGGED_USER, para conservar el usuario identificado, con este parámetro permite asignar un identificador de usuario alternativo.
	* @property {boolean} [getDefault=true] - Determina si el multifiltro debe de cargar el filtro por defecto al cargar la página.
	*/jQuery.fn.rup_table.plugins.multifilter={};jQuery.fn.rup_table.plugins.multifilter.defaults={multifilter:{}};/* ********* *//* EVENTOS
  /* ********* *//**
   *  Evento lanzado justo antes de añadir un filtro.
   *
   * @event module:rup_table#rupTable_multifilter_beforeAdd
   * @property {Event} event - Objeto Event correspondiente al evento disparado.
	 * @property {Event} xhr - Objecto XHR empleado en la petición AJAX de nuevo filtro.
	 * @property {Event} options - Opciones de comfiguración de la petición AJAX de nuevo filtro.
   * @example
   * $("#idComponente").on("rupTable_multifilter_beforeAdd", function(event, xhr, options){ });
   *//**
		* Evento ejecutado cuando se rellenar el formulario del filtro. Cada vez que se cancela, limpia o se selecciona un filtro se lanza este evento.
		*
		* @event module:rup_table#rupTable_multifilter_fillForm:
		* @property {Event} event - Objeto Event correspondiente al evento disparado.
		* @property {Event} filterData - Valor del filtro.
		* @example
		* $("#idComponente").on("rupTable_multifilter_fillForm:", function(event, filterData){ });
		*/})(jQuery);/*!
 * Copyright 2013 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 *//*global jQuery *//**
 * Proporciona al componente RUP Table ciertas funcionalidades responsive.
 *
 * @summary Plugin de toolbar del componente RUP Table.
 * @module rup_table/responsive
 * @example
 *
 * $("#idComponente").rup_table({
 * 	url: "../jqGridUsuario",
 * 	usePlugins:["responsive"],
 * 	responsive:{
 * 		// Propiedades de configuración del plugin responsive
 * 	}
 * });
 */(function($){/**
   * Definición de los métodos principales que configuran la inicialización del plugin.
   *
   * preConfiguration: Método que se ejecuta antes de la invocación del componente jqGrid.
   * postConfiguration: Método que se ejecuta después de la invocación del componente jqGrid.
   *
   */jQuery.rup_table.registerPlugin('responsive',{loadOrder:20,preConfiguration:function preConfiguration(settings){var $self=this;return $self.rup_table('preConfigureResponsive',settings);},postConfiguration:function postConfiguration(settings){var $self=this;return $self.rup_table('postConfigureResponsive',settings);}});$.extend($.rup,{table:{responsive:{'SCREEN_SM':768,'SCREEN_MD':992,'SCREEN_LG':1200}}});//********************************
// DEFINICIÓN DE MÉTODOS PÚBLICOS
//********************************
/**
   * Extensión del componente rup_table para permitir la gestión de la botonera asociada a la tabla.
   *
   * Los métodos implementados son:
   *
   * preConfigureFeedback(settings): Método que define la preconfiguración necesaria para el correcto funcionamiento del componente.
   * postConfigureFeedback(settings): Método que define la postconfiguración necesaria para el correcto funcionamiento del componente.
   *
   * settings.$feedback : Referencia al componente feedback.
   * settings.$$internalFeedback : Referencia al feedback interno.
   *
   *
   */$.extend($.jgrid,{// 	setGridWidth: function(nwidth, shrink){
// 	debugger;
// 	}
});jQuery.fn.rup_table('extend',{/**
		* Metodo que realiza la pre-configuración del plugin responsive del componente RUP Table.
		* Este método se ejecuta antes de la incialización del plugin.
		*
		* @name preConfigureResponsive
		* @function
		* @param {object} settings - Parámetros de configuración del componente.
		*/preConfigureResponsive:function preConfigureResponsive(settings){var $self=this;},/**
		* Metodo que realiza la post-configuración del plugin responsive del componente RUP Table.
		* Este método se ejecuta antes de la incialización del plugin.
		*
		* @name postConfigureResponsive
		* @function
		* @param {object} settings - Parámetros de configuración del componente.
		*/postConfigureResponsive:function postConfigureResponsive(settings){var $self=this,$fluidBaseLayer,currentDisplay,currentDisplayIndex;settings.fluid.baseLayer=$.rup_utils.getJQueryId(settings.fluid.baseLayer!==null?settings.fluid.baseLayer:settings.id+'_div');settings.fluid.$baseLayer=jQuery(settings.fluid.baseLayer);if(settings.fluid.$baseLayer.length===0){alert('El identificador '+settings.baseLayer+' especificado para la capa sobre la que se va a aplicar el diseño líquido no existe.');return;}$fluidBaseLayer=settings.fluid.fluidBaseLayer=settings.fluid.$baseLayer;// Tratamiento del evento de redimiensionado del diseño líquido de la tabla
$(window).on('resize',function(event,previousWidth,currentWidth){if($self.is(':visible')){var feedBackPaddingLeft,feedBackPaddingRight,toolbarPaddingLeft,toolbarPaddingRight,windowWidth,rwdConfigArray;windowWidth=$(window).width();if(windowWidth>$.rup.table.responsive.SCREEN_LG){currentDisplay='lg';}else if(windowWidth>$.rup.table.responsive.SCREEN_MD){currentDisplay='md';}else if(windowWidth>$.rup.table.responsive.SCREEN_SM){currentDisplay='sm';}else{currentDisplay='xs';}rwdConfigArray=$self.rup_table('getRwdColConfig');$.each(rwdConfigArray,function(i,obj){if(obj[currentDisplay]===true){$self.rup_table('showCol',obj.name);}else{$self.rup_table('hideCol',obj.name);}});//$self.trigger("rupTable_fluidUpdate");
//$self.setGridWidth(currentWidth);
// Se redimensionan las capas contenidas en el mantenimiento
//$fluidBaseLayer.children().width(currentWidth);
//						prop.searchForm.parent().width(currentWidth+3)
// Se redimensiona el feedback
// if (settings.$feedback){
// 	feedBackPaddingLeft = parseInt(settings.$feedback.css("padding-left"));
// 	feedBackPaddingRight = parseInt(settings.$feedback.css("padding-right"));
// 	settings.$feedback.width(currentWidth - (feedBackPaddingLeft+feedBackPaddingRight));
// }
// Se redimensiona la toolbar
// if (settings.$toolbar){
// 	toolbarPaddingLeft = parseInt(settings.$toolbar.css("padding-left"));
// 	toolbarPaddingRight = parseInt(settings.$toolbar.css("padding-right"));
// 	settings.$toolbar.width(currentWidth - (toolbarPaddingLeft+toolbarPaddingRight));
// 	settings.$toolbar.css("width", currentWidth - (toolbarPaddingLeft+toolbarPaddingRight));
// }
}});function intNum(val,defval){val=parseInt(val,10);if(isNaN(val)){return defval||0;}return val;}function reDefineColWidth(){var $self=this;var widthsArr=$self[0].p.colModel.map(function(i,elem){return i.width;});for(var j=0;j<widthsArr.length;j++){$('.ui-jqgrid-labels > th:eq('+j+')').css('width',widthsArr[j]);$self.find('tr').find('td:eq('+j+')').each(function(){$(this).css('width',widthsArr[j]);});}}function setColWidth(){//console.log("entra");
var initwidth=0,ts=this[0],grid=this[0],brd=$.jgrid.cell_width?0:intNum(ts.p.cellLayout,0),vc=0,lvc,scw=intNum(ts.p.scrollOffset,0),cw,hs=false,aw,gw=0,cl=0,cr;$.each(ts.p.colModel,function(){if(this.hidden===undefined){this.hidden=false;}if(ts.p.grouping&&ts.p.autowidth){var ind=$.inArray(this.name,ts.p.groupingView.groupField);if(ind!==-1){this.hidden=!ts.p.groupingView.groupColumnShow[ind];}}this.widthOrg=cw=intNum(this.width,0);if(this.hidden===false){initwidth+=cw+brd;if(this.fixed){gw+=cw+brd;}else{vc++;}cl++;}});if(isNaN(ts.p.width)){ts.p.width=initwidth+(ts.p.shrinkToFit===false&&!isNaN(ts.p.height)?scw:0);}grid.width=ts.p.width;ts.p.tblwidth=initwidth;if(ts.p.shrinkToFit===false&&ts.p.forceFit===true){ts.p.forceFit=false;}if(ts.p.shrinkToFit===true&&vc>0){aw=grid.width-brd*vc-gw;if(!isNaN(ts.p.height)){aw-=scw;hs=true;}initwidth=0;$.each(ts.p.colModel,function(i){if(this.hidden===false&&this.fixed!==true){//console.log("->" + this.name + " - hidden:" + this.hidden + " - fixed: " + this.fixed + " -  tblwidth: " + ts.p.tblwidth + " - width: " + this.width);
cw=Math.round(aw*this.width/(ts.p.tblwidth-brd*vc-gw));this.width=cw;initwidth+=cw;lvc=i;}});cr=0;if(hs){if(grid.width-gw-(initwidth+brd*vc)!==scw){cr=grid.width-gw-(initwidth+brd*vc)-scw;}}else if(!hs&&Math.abs(grid.width-gw-(initwidth+brd*vc))!==1){cr=grid.width-gw-(initwidth+brd*vc);}ts.p.colModel[lvc].width+=cr;ts.p.tblwidth=initwidth+cr+brd*vc+gw;if(ts.p.tblwidth>ts.p.width){ts.p.colModel[lvc].width-=ts.p.tblwidth-parseInt(ts.p.width,10);ts.p.tblwidth=ts.p.width;}}}function resize(){$self.css('width','100%');$self.parents('.ui-jqgrid-bdiv').css('width','100%');$self.parents('.ui-jqgrid-view').css('width','100%');$self.parents('.ui-jqgrid').css('width','100%');$self.parents('.ui-jqgrid').find('.ui-jqgrid-htable').css('width','100%');$self.parents('.ui-jqgrid').find('.ui-jqgrid-htable').parents('.ui-jqgrid-hbox').css('width','100%');$self.parents('.ui-jqgrid').find('.ui-jqgrid-hdiv').css('width','100%');$self.parents('.ui-jqgrid').find('.ui-jqgrid-pager').css('width','100%');if($self.data('settings').$toolbar){$self.data('settings').$toolbar.css('width','100%');}$.proxy(setColWidth,$self)();$.proxy(reDefineColWidth,$self)();}$self.on('jqGridAfterLoadComplete',function(){$.proxy(resize,$self)();});$(window).on('resize',function(){$.proxy(resize,$self)();});// $self.fluidWidth({
// 	fluidBaseLayer:settings.fluid.baseLayer,
// 	minWidth: 100,
// 	maxWidth: 2000,
// 	fluidOffset : 0
// });
//
// // $self.fluidWidth(settings.fluid);
// //
// $self.on("rupTable_fluidUpdate", function(event){
// 	$.proxy(resize,$self)();
// });
}});jQuery.fn.rup_table('extend',{/**
		* Obtiene a partir de la configuración del colModel, la información correspondiente al comportamiento responsive de las columnas.
		*
		* @name getRwdColConfig
		* @function
		* @return {object[]} - Configuración responsive para las columnas de la tabla.
		*/getRwdColConfig:function getRwdColConfig(){var $self=this,rwdCols,retJson={},retArray=[],jsonAux={},colRwdClasses,splitAux,splitAux2;rwdCols=$.grep($self.rup_table('getColModel'),function(obj,i){return obj['rwdClasses'];});$.each(rwdCols,function(i,obj){colRwdClasses=obj.rwdClasses;jsonAux={name:obj.name,xs:true,sm:true,md:true,lg:true};splitAux=colRwdClasses.split(' ');//console.log("name:" + obj.name);
for(var i=0;i<splitAux.length;i++){splitAux2=splitAux[i].split('-');//  console.log("splitAux2:" + splitAux2[0]);
//console.log("splitAux2:" + splitAux2[1]);
if(splitAux2[0]==='hidden'){jsonAux[splitAux2[1]]=false;}}retArray.push(jsonAux);});//console.log(retArray);
return retArray;}});//*******************************************************
// DEFINICIÓN DE LA CONFIGURACION POR DEFECTO DEL PATRON
//*******************************************************
/**
 	* @description Propiedades de configuración del plugin responsive del componente RUP Table.
 	*
 	* @name options
 	*
 	* @property {object} [fluid] - Parametros de configuración
 	* @property {string[]} [excludeColumns] - Determina las columnas que van a ser excluidas de la generación del informe.
 	* @property {string[]} [sendPostDataParams] - Parámetros del jqGrid que van a ser enviados en la petición de generación del informe.
 	*/jQuery.fn.rup_table.plugins.responsive={};jQuery.fn.rup_table.plugins.responsive.defaults={// autowidth:true,
fluid:{baseLayer:null,minWidth:100,maxWidth:2000,fluidOffset:0},toolbar:{autoAjustToolbar:false,width:'87.6%'}};// jQuery.fn.rup_table.plugins.toolbar.defaults = {
// 	toolbar:{
// 		autoAjustToolbar:false
// 	}
// };
})(jQuery);});
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))

/***/ }),
/* 166 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function($) {var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;var _typeof = typeof Symbol === "function" && typeof Symbol.iterator === "symbol" ? function (obj) { return typeof obj; } : function (obj) { return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj; };

/*!
 * Copyright 2013 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 */

/**
 * Permiten dar acceso de forma compacta a grupos de contenidos mutuamente excluyentes pudiendo ser integradas en zonas muy reducidas de la interfaz.
 *
 * @summary Componente RUP Tabs.
 * @module rup_tabs
 * @see El componente está basado en el plugin {@link https://jqueryui.com/tabs/|jQuery UI Tabs}. Para mas información acerca de las funcionalidades y opciones de configuración pinche {@link http://api.jqueryui.com/tabs/|aquí}.
 * @example
 * $("#ejemploArbolDiv").rup_tabs(properties);
 *
 */

/*global define */
/*global jQuery */

(function (factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(3), __webpack_require__(269), __webpack_require__(2)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		factory(jQuery, Rup);
	}
})(function (jQuery, Rup) {

	//*****************************************************************************************************************
	// DEFINICIÓN BASE DEL PATRÓN (definición de la variable privada que contendrá los métodos y la función de jQuery)
	//*****************************************************************************************************************

	var rup_tabs = {};

	//Se configura el arranque de UDA para que alberge el nuevo patrón
	$.extend($.rup.iniRup, $.rup.rupSelectorObjectConstructor('rup_tabs', rup_tabs));

	//********************************
	// DEFINICIÓN DE MÉTODOS PÚBLICOS
	//********************************

	$.fn.rup_tabs('extend', {
		/**
         * Función encargada de deshabilitar una o un conjunto de pestañas de un mismo sub-nivel
         * @function
         * @name disableTabs
         * @param  {string} args.idTab - Selector del componente pestaña
         * @param {integer|object} args.position - Posición de las pestañas a deshabilitar
         * @example
         * //Una única pestaña:
         * $("#tabs").rup_tabs("disableTabs",{
         *    idTab: "tabs",
         *    position: 1
         *    });
         * //Un conjunto de pestañas:
         * $("#tabs").rup_tabs("disableTabs",{
         *    idTab: "tabs",
         *    position: [0,1,2]
         * });
         */
		disableTabs: function disableTabs(args) {
			var tab;

			if (typeof args.position === 'number') {
				$('#' + args.idTab).tabs('disable', args.position);
				this.trigger('disable', null, tab, $('#' + args.idTab));
			} else if (_typeof(args.position) === 'object') {
				for (var i in args.position) {
					$('#' + args.idTab).tabs('disable', args.position[i]);
					this.trigger('disable', null, tab, $('#' + args.idTab));
				}
			} else if (typeof args.position === 'undefined') {
				//deshabilitacion de toda la pestanya del nivel (de momento no se aplica por errores en el plug-in subyacente).
				$('#' + args.idTab).tabs('disable');
				var lengthTab = $('#' + args.idTab).find('.ui-tabs-nav li').size();
				for (var j = 1; j <= lengthTab; j++) {
					tab = $('#' + args.idTab).find('.ui-tabs-nav li:eq(' + j + ')');
					this.trigger('disable', null, tab, $('#' + args.idTab));
				}
			}
		},
		/**
         * Función encargada de habilitar una o un conjunto de pestañas de un mismo subnivel.
         * @function
         * @name enableTabs
         * @param  {string} args.idTab - Selector del componente pestaña
         * @param {integer|object} args.position - Posición de las pestañas a habilitar
         * @example
         * //Una única pestaña:
         * $("#tabs").rup_tabs("enableTabs ",{
         *    idTab: "tabs",
         *    position: 1
         *  });
         * //Un conjunto de pestañas:
         *  $("#tabs").rup_tabs("enableTabs",{
         *    idTab: "tabs",
         *    position: [0,1,2]
         *  });
         */
		enableTabs: function enableTabs(args) {
			var tab;

			if (typeof args.position === 'number') {
				tab = $('#' + args.idTab).find('.ui-tabs-nav li:eq(' + args.position + ')');

				$('#' + args.idTab).tabs('enable', args.position);
				this.trigger('enable', null, tab, $('#' + args.idTab));
			} else if (_typeof(args.position) === 'object') {
				for (var i in args.position) {
					tab = $('#' + args.idTab).find('.ui-tabs-nav li:eq(' + args.position[i] + ')');

					$('#' + args.idTab).tabs('enable', args.position[i]);
					this.trigger('enable', null, tab, $('#' + args.idTab));
				}
			} else if (typeof args.position === 'undefined') {
				//deshabilitacion de toda la pestanya del nivel (de momento no se aplica por errores en el plug-in subyacente).
				$('#' + args.idTab).tabs('enable');
				var lengthTab = $('#' + args.idTab).find('.ui-tabs-nav li').size();
				for (var j = 1; j <= lengthTab; j++) {
					tab = $('#' + args.idTab).find('.ui-tabs-nav li:eq(' + j + ')');
					this.trigger('enable', null, tab, $('#' + args.idTab));
				}
			}
		},
		/**
         * Función que fuerza la recarga de una pestaña. Si se especifica una nueva url, además de recargar la página con la nueva url, se inserta ésta como nueva url de la pestaña
         * @function  Función que fuerza la recarga de una pestaña. Si se especifica una nueva url, además de recargar la página con la nueva url, se inserta ésta como nueva url de la pestaña
         * @name	loadTab
         * @param  {string} args.idTab - Selector del componente pestaña
         * @param {integer} args.position - Posición de la pestaña a recargar
         * @param {string} args.url - Nueva url a cargar.
         * @example
         * //	Recarga simple:
         * $("#tabs").rup_tabs("loadTab",{
         *    idTab: "tabs",
         *    position: 2
         *  });
         * //	Recarga con cambio de url:
         * $("#tabs").rup_tabs("loadTab", {
         *   idTab: "tabs",
         *   position: 2,
         *   url: "/nuevoFragmento" *
         * });
         */
		loadTab: function loadTab(args) {
			$('#' + args.idTab).tabs('load', args.position);
		},
		/**
         *
         *  Función encargada de actualizar la url de invocación de una pestaña determinada
         * @function
         * @name changeUrlTab
         * @param  {string} args.idTab - Selector del componente pestaña
         * @param {integer} args.position - Posición de la pestaña a cambiar
         * @param {string} args.url - Nueva url a cargar.
         * @example
         * $("#tabs").rup_tabs("changeUrlTab",{
         *    idTab: "tabs",
         *     position: 1,
         *    url: "nuevaUrl"
         *  });
         */
		changeUrlTab: function changeUrlTab(args) {
			//$("#" + args.idTab).tabs("url", args.position, $.rup_utils.setNoPortalParam(args.url));

			this._changeUrlTab({
				idTab: args.idTab,
				position: args.position,
				url: $.rup_utils.setNoPortalParam(args.url)
			});
		},
		/**
         * Función encargada de actualizar la capa html, previamente cargada, que se muestra en la pestaña determinada
         * @function
         * @name  changeLayerTab
         * @param {string} args.idTab - Selector del componente pestaña
         * @param {integer} args.position - Posición de la pestaña a cambiar
         * @param {string} args.layer - Selector de la capa a cargar.
         * @example
         * $("#tabs").rup_tabs("changeLayerTab",{
         *    idTab: "tabs",
         *   position: 2,
         *   layer: "nuevaSelector"
         * });
         */
		changeLayerTab: function changeLayerTab(args) {
			this._includeLayer($('#' + args.idTab + ' ul:first-child'), args.layer, $($('#' + args.idTab + ' ul li a').get(args.position)));
		},
		/**
         * Función encargada de seleccionar una pestaña determinada. El comportamiento es idéntico al click con el ratón.
         * @function
         * @name  selectTab
         * @param {string} args.idTab - Selector del componente pestaña
         * @param {integer} args.position - Posición de la pestaña a seleccionar
         * @example
         * $("#tabs").rup_tabs("selectTab",{
         *    idTab: "tabs",
         *    position: 1,
         *  });
         */
		selectTab: function selectTab(args) {
			$('#' + args.idTab).tabs('option', 'active', args.position);
		},

		/**
         * Función encargada de añadir una nueva pestaña cuando el componente ya está creado. Es posible añadir una nueva pestaña al final o entre otras pestañas.
         * @function
         * @name addTab
         * @param {string} args.idTab - Selector del componente pestaña
         * @param {integer} args.position - Posición de las pestaña a añadir
         * @param {string} args.url - la url a añadir a la pestaña.
         * @param {string} args.label - Literal a mostrar en la pestaña.
         * @example
         * $("#tabs").rup_tabs("addTab",{
         *    idTab: "tabs",
         *  position: 2,
         *   label: "nuevaPestaña",
         *   url: "fragmento3"
         *  });
         */
		addTab: function addTab(args) {
			var newTab,
			    auxTabName,
			    nameLiteral = 'rup-tabs-',
			    insertIndex = 0,
			    label,
			    title = '';

			//limitacion de numero de pestañas abiertas
			if (args.maxNumberTabs !== undefined) {
				var numPestanas = $('#' + args.idTab + ' li').size();
				//si sobrepasamos numero de pestañas lanzamos limitTabs
				if (numPestanas + 1 > args.maxNumberTabs) {
					$('#' + args.idTab).trigger('limitTabs');
					return false;
				}
			}
			// para acortar a n caracteres el literalal de la pestana

			if (args.lengthLiteral !== undefined) {
				title = args.label;
				if (args.label.length > args.lengthLiteral) {
					args.label = args.label.substr(0, args.lengthLiteral).concat('...');
				}
			}

			if (args.tabs !== undefined) {
				if (args.idNewTab !== undefined && $('#' + args.idNewTab).length === 0) {
					newTab = $('<div>').attr('id', args.idNewTab);
					newTab.appendTo('body');
					auxTabName = this._includeLayer($('#' + args.idTab + ' > ul:first-child'), '#' + args.idNewTab, null);
					newTab.rup_tabs(args);
					//$("#" + args.idTab).tabs("add", "#" + args.idNewTab, args.label, args.position);
					this._addTab({
						idTab: args.idTab,
						url: args.idNewTab,
						label: args.label,
						position: args.position,
						orientation: args.orientation
					});
					$(auxTabName).remove();
				} else {
					$.rup.errorGestor($.rup.i18nParse($.rup.i18n.base, 'rup_global.parameterError'));
					return false;
				}
			} else if (args.layer !== undefined) {

				//LAYER => Recoge una capa ya cargada de la Jsp
				args.layer = this._includeLayer($('#' + args.idTab + ' > ul:first-child'), args.layer, null);

				//$("#" + args.idTab).tabs("add", args.layer, args.label, args.position);
				this._addTab({
					idTab: args.idTab,
					url: args.layer,
					label: args.label,
					position: args.position,
					orientation: args.orientation
				});
				$.each($('#' + args.idTab + ' div[id*=\'' + nameLiteral + '\']'), function (index, object) {
					if (insertIndex < parseFloat(object.id.split(nameLiteral)[1])) {
						insertIndex = object.id.split(nameLiteral)[1];
					}
				});
				//$("#"+args.idTab+" div[id='rup-tabs-"+insertIndex+"']").addClass("ui-tabs-hide");
			} else {
				//$("#" + args.idTab).tabs("add", $.rup_utils.setNoPortalParam(args.url), args.label, args.position);
				this._addTab({
					idTab: args.idTab,
					url: $.rup_utils.setNoPortalParam(args.url),
					label: args.label,
					position: args.position,
					orientation: args.orientation
				});
				$.each($('#' + args.idTab + ' div[id*=\'' + nameLiteral + '\']'), function (index, object) {
					if (insertIndex < parseFloat(object.id.split(nameLiteral)[1])) {
						insertIndex = object.id.split(nameLiteral)[1];
					}
				});

				$('#' + args.idTab + ' div[id=\'rup-tabs-' + insertIndex + '\']').addClass('ui-tabs-hide');
				//altura fija
				if (undefined !== args.fixedHeight) {
					$('#' + args.idTab + ' div[id=\'rup-tabs-' + insertIndex + '\']').css('height', args.fixedHeight);
				}
			}

			$('#' + args.idTab + ' ul:first li:nth-child(' + (args.position + 1) + ') a').attr('title', title).rup_tooltip({});

			if (args.tabsAtBottom) {
				loadLi = $('#' + args.idTab + ' ul li:last').not('.rup-tabs_loading');
				loadLi.removeClass('ui-corner-top').addClass('ui-corner-botttom');
			}

			var pos = args.position;
			if (args.orientation !== undefined) {
				pos = pos - 1;
			}
			var loadSpan = $('#' + args.idTab + ' ul li a:eq(' + pos + ')');
			if (args.close === true) {
				loadSpan.text('');
				var texto = $.rup.i18nParse($.rup.i18n.app[$(this).attr('id')], args.label);
				if (args.label !== undefined && args.label !== '') {
					texto = args.label;
				}
				loadSpan.append($('<div>').addClass('rup-tabs_title').text(texto)).append($('<span>').addClass('rup-tabs_loading')).append('<span class="ui-icon ui-icon-close" role="presentation">Remove Tab</span>');

				//evento close
				$('span.ui-icon-close').on('click', function () {
					var div = $(this).parent().parent().parent().parent();
					var tabContentId = $(this).parent().attr('href');
					$(this).parent().parent().remove(); //remove li of tab
					$(tabContentId).remove(); //remove respective tab content

					div.tabs('refresh');
				});

				//efecto hover del boton cerrar
				$('span.ui-icon-close').addClass('rup-tabs-close');
				$('span.ui-icon-close').on({
					mouseenter: function mouseenter() {
						$(this).addClass('rup-tabs-close-hover');
					},

					mouseleave: function mouseleave() {
						$(this).removeClass('rup-tabs-close-hover');
					}
				});
			} else {
				loadSpan.text('');
				var textoNoClose = $.rup.i18nParse($.rup.i18n.app[$(this).attr('id')], args.label);
				if (args.label !== undefined && args.label !== '') {
					textoNoClose = args.label;
				}
				loadSpan.append($('<div>').addClass('rup-tabs_title').text(textoNoClose)).append($('<span>').addClass('rup-tabs_loading'));
			}

			//loadSpan.remove();

		},
		/**
         * Función encargada de eliminar una nueva pestaña cuando el componente ya está creado
         * @param {string} args.idTab - Selector del componente pestaña
         * @param {integer} args.position - Posición de las pestaña a eliminar
         */
		removeTab: function removeTab(args) {
			//$("#" + args.idTab).tabs("remove", args.position);
			this._removeTab({
				idTab: args.idTab,
				position: args.position
			});
		},
		selected: 0
	});

	//********************************
	// DEFINICIÓN DE MÉTODOS PRIVADOS
	//********************************

	$.fn.rup_tabs('extend', {
		_init: function _init(args) {

			if (args.length > 1) {
				$.rup.errorGestor($.rup.i18nParse($.rup.i18n.base, 'rup_global.initError') + $(this).attr('id'));
			} else {
				//Se recogen y cruzan las paremetrizaciones del objeto
				var settings = $.extend({}, $.fn.rup_tabs.defaults, args[0]),
				    json_i18n;

				settings.id = $(this).attr('id');
				settings.iniLoad = false;

				//Establecemos el ancho general de las pestañas en caso de venir informado
				if (undefined !== settings.width) {
					$('#' + settings.id).css('width', settings.width).addClass('rup-tabs_overflow');
				}
				//Establecemos la altura general de las pestañas en caso de venir informada
				if (undefined !== settings.height) {
					$('#' + settings.id).css('height', settings.height).addClass('rup-tabs_overflow');
				}

				var structure = settings.tabs,
				    profun = 0;

				while (structure !== undefined) {
					profun = profun + 1;
					structure = structure[0].tabs;
				}

				settings.profun = profun;
				//Generar estructura
				this._parseJSON(settings.tabs, $.rup.i18n.app[settings.id], $('#' + settings.id), '', 1, settings);

				//Una vez creadas todas las pestanyas, se permite la carga normal de las mismas
				settings.iniLoad = true;

				//Convertir en pestanyas
				this._tabify($('#' + settings.id), settings);

				//altura
				if (undefined !== settings.fixedHeight) {
					$('#' + settings.id + '>.ui-tabs-panel').css('height', settings.fixedHeight);
				}

				//Añadir evento de conversión a pestanyas en los enlaces
				//$('#'+settings.id).find("a[rupLevel]").click ({disabled: settings.disabled}, tabClick);

				//evento limite de numero de pestañas
				$('#' + settings.id).on('limitTabs', function () {
					alert('limite de pestañas alcanzado');
				});

				//Deshabilitar las pestanyas indicadas
				if (settings.disabled !== undefined) {
					for (var i in settings.disabled) {
						$('#' + settings.id).rup_tabs('disableTabs', {
							idTab: i,
							position: settings.disabled[i]
						});
					}
				}
			}
		},
		//Funcion encargada de crear los distintos tab's
		_tabify: function _tabify(div, settings) {

			//Se especifica el estilo asociado a la pestanya contenedora de pestanyas
			div.addClass('rup-tabs_container');

			//Se cargan los Setting de cada objeto en su campo "data" correspondiente
			div.data('settings', settings);

			//Se especifica el control del evento "select" por parte del patron
			var select = function select(event, ui) {

				//Se gestiona la primera carga de la primera pestanya de cada tab
				if ($(ui.panel).data('cargado') !== undefined && $(ui.panel).data('cargado') === false && $(ui.panel).length > 0) {
					$(ui.panel).tabs('load', settings.selected);
					$(ui.panel).data('cargado', true);
				}
				if (settings.select !== undefined && settings.select !== null && typeof settings.select === 'function') {
					settings.select(event, ui);
				}
				//Nuevos cargar para la versión jquery 1.12, es la primera vez
				if ($(ui.newPanel).data('cargado') !== undefined) {
					ui.newTab.children('a').attr('href', ui.newTab.children('a').attr('id'));
				}
				$(ui.newPanel).data('cargado', true);
			};

			//se cargan las extensiones de los usuarios en los eventos de las peticiones Ajax
			var ajaxOptions = $.extend({}, settings.ajaxOptions);

			ajaxOptions.beforeSend = function (XMLHttpRequest, sets) {
				if (settings.ajaxOptions.beforeSend !== undefined && settings.ajaxOptions.beforeSend !== null && typeof settings.ajaxOptions.beforeSend === 'function') {
					settings.ajaxOptions.beforeSend.call();
				}

				if (!settings.iniLoad) {
					div.data('cargado', false);
					return false;
				}
			};
			ajaxOptions.complete = function (XMLHttpRequest, textStatus) {
				//se elimina el objeto de visualizacion de carga
				div.find('span.rup-tabs_loading_img').remove();

				if (settings.ajaxOptions.complete !== undefined && settings.ajaxOptions.complete !== null && typeof settings.ajaxOptions.complete === 'function') {
					settings.ajaxOptions.complete(XMLHttpRequest, textStatus);
				}
			};
			ajaxOptions.success = function (data, textStatus, XMLHttpRequest) {
				if (settings.ajaxOptions.success !== undefined && settings.ajaxOptions.success !== null && typeof settings.ajaxOptions.success === 'function') {
					settings.ajaxOptions.success(data, textStatus, XMLHttpRequest);
				}
			};
			ajaxOptions.error = function (xhr, s, t) {
				var userFunction;

				if (settings.ajaxOptions.error !== undefined && settings.ajaxOptions.error !== null && typeof settings.ajaxOptions.error === 'function') {
					userFunction = function userFunction() {
						settings.ajaxOptions.error(xhr, s, t);
					};
				}
				$.rup_messages('msgError', {
					title: $.rup.i18nParse($.rup.i18n.base, 'rup_global.developerError'),
					message: '<p>' + $.rup.i18nParse($.rup.i18n.base, 'rup_tabs.serverError') + '<b> ' + s + ':  ' + xhr.status + ' - ' + xhr.statusText + '.</b>' + '</p>',
					width: '40%',
					beforeClose: userFunction
				});
			};
			//if (settings.navigation!==true){
			$(div).tabs({
				ajaxOptions: settings.cache === false ? $.extend(ajaxOptions, {
					cache: false
				}) : ajaxOptions,
				cache: settings.cache,
				cookie: null,
				//cookie: settings.cookie, //Se deja para una mejora
				//disabled: true, //Bajo funcionalidades
				show: settings.fx ? settings.fx[0] : null, //son los efectos que se aplican al presentar  una pestanya
				hide: settings.fx ? settings.fx[1] : null, //son los efectos que se aplican al ocultar una pestanya
				idPrefix: 'rup-tabs-',
				panelTemplate: settings.panelTemplate,
				active: settings.selected, //deprecado en jquery ui 1.10, ahora es active
				spinner: '<span class=\'rup-tabs_loading_img\' />',
				//eventos
				create: settings.create,
				beforeActivate: select, //deprecado en jquery ui 1.10, ahora es beforeActivate
				load: settings.load,
				activate: settings.show, //deprecated show como evento desde jquery ui 1.10
				add: settings.add,
				remove: settings.remove
				//enable: settings.enable,
				//disable: settings.disable
			});
			//}

			if (settings.scrollable === true) {
				this._scrollable(settings);
			}

			// Tabs at bottoms
			if (settings.tabsAtBottom === true) {
				$(div).addClass('tabs-bottom');
				$(div).find('.tabs-spacer').css('float', 'left').css('height', '200px');
				$('.ui-tabs-nav, .ui-tabs-nav > *', $(div)).removeClass('ui-corner-all ui-corner-top').addClass('ui-corner-bottom');

				$('.ui-tabs-panel.ui-widget-content.ui-corner-bottom', $(div)).removeClass('ui-corner-bottom').addClass('ui-corner-top');

				// move the nav to the bottom
				$('.ui-tabs-nav', $(div)).appendTo('.tabs-bottom');
			}
		},

		_parseJSON: function _parseJSON(json, json_i18n, tabs, pos, profundidad, settings) {
			var $self = this,
			    element,
			    rupLevel,
			    label,
			    title = '';

			// Añadir contenedor de pestanyas
			var $tabsContainer = $(Rup.Templates.rup.tabs.container());
			tabs.append($tabsContainer);
			tabs = $(tabs).children('ul');

			// pestanyas
			for (var i = 0; i < json.length; i++) {
				rupLevel = pos + i; // Indicador de nivel de la pestanya
				element = json[i];
				if (i === 0 && profundidad === settings.profun) {
					settings.iniLoad = true;
				} else {
					settings.iniLoad = false;
				}

				label = $.rup.i18nParse(json_i18n, element.i18nCaption);

				if (settings.lengthLiteral !== undefined) {
					title = label;
					if (label.length > settings.lengthLiteral) {
						label = label.substr(0, settings.lengthLiteral).concat('...');
					}
				}

				if (element.layer !== undefined) {
					// LAYER => Recoge una capa ya cargada de la Jsp
					element.layer = this._includeLayer(tabs, element.layer, null);

					$tabsContainer.append(Rup.Templates.rup.tabs.tab({
						'id': element.i18nCaption,
						'href': element.layer,
						'rupLevel': rupLevel,
						'title': title,
						'aria-controls': title,
						'alt': title,
						'label': label,
						'btnClose': settings.close
					}));

					// evento close
					$('span.ui-icon-close').on('click', function () {

						var tabContentId = $(this).parent().attr('href');
						$(this).parent().parent().remove(); // remove li of
						// tab
						$(tabContentId).remove(); // remove respective tab
						// content

						tabs.parent().tabs('refresh');
					});

					// efecto hover del boton cerrar
					$('span.ui-icon-close').addClass('rup-tabs-close');
					$('span.ui-icon-close').on({
						mouseenter: function mouseenter() {
							$(this).addClass('rup-tabs-close-hover');
						},

						mouseleave: function mouseleave() {
							$(this).removeClass('rup-tabs-close-hover');
						}
					});
				} else if (element.url !== undefined) {
					// URL => Cargar contenido al pulsar
					$tabsContainer.append(Rup.Templates.rup.tabs.tab({
						'id': '#' + element.i18nCaption,
						'href': $.rup_utils.setNoPortalParam(element.url),
						'rupLevel': rupLevel,
						'title': title,
						'aria-controls': title,
						'alt': title,
						'label': label,
						'btnClose': settings.close
					}));
				} else if (element.tabs !== undefined) {
					// TABS => Subpestanyas
					$tabsContainer.append(Rup.Templates.rup.tabs.tab({
						'id': '#' + element.i18nCaption,
						'href': '#' + element.i18nCaption,
						'rupLevel': rupLevel,
						'title': title,
						'aria-controls': title,
						'alt': title,
						'label': label,
						'btnClose': settings.close,
						'tabs': element.tabs
					}));

					// Gestionar capa contenedora subpestanyas
					tabs = $(tabs).parent();
					// Añadir contenedor de capa asociada a pestanya
					var capaId = 'rupRandomLayerId-' + $.rup_utils.autoGenerateIdNum++;
					var $capa = $(Rup.Templates.rup.tabs.subtab({
						'rupRandomLayerId': capaId,
						'id': element.i18nCaption,
						'actualTab': true
					}));
					tabs.append($capa);

					var $subTabsDiv = $('[id=\'' + element.i18nCaption + '\']', $capa);

					// tabs.append(capa); //Añadir contenedor de capa
					// asociada a pestanya
					tabs = $(tabs).children('#' + capaId); //Seleccionar
					// capa contenedora

					// Gestionar capa de la subpestanya
					tabs.prepend($('<div>').attr('id', element.i18nCaption).attr('actualTab', true));
					// //Añadir capa asociada a la pestanya
					tabs = $(tabs).children('div:first-child'); // Seleccionar
					// capa

					// Subpestanyas
					var subsettings = jQuery.extend(true, {}, settings);
					subsettings.selected = element.selected;
					// tabs.append(this._parseJSON(element.tabs, json_i18n,
					// tabs, rupLevel, profundidad+1, subsettings));
					tabs.append(this._parseJSON(element.tabs, json_i18n, tabs, rupLevel, profundidad + 1, subsettings));

					this._tabify(tabs, subsettings); // Si no tiene 1
					// es que es el
					// primer
					// elemento y lo
					// convertimos a
					// pestanyas

				}
			}
		},

		//Funcion encargada de gestionar el objeto definido por el usuario (se parsea el JSon y se actua en consecuencia)
		// _parseJSON : function (json, json_i18n, tabs, pos, profundidad, settings) {
		// 	var element, rupLevel, label, title="";
		//
		// 	tabs.append($('<ul>'));  //Añadir contenedor de pestanyas
		// 	tabs = $(tabs).children('ul'); //Seleccionar pestanya
		//
		// 	//pestanyas
		// 	for (var i = json.length; i--; ) {
		// 		rupLevel = pos+i; //Indicador de nivel de la pestanya
		// 		element = json[i];
		// 		if (i === 0 && profundidad === settings.profun){
		// 			settings.iniLoad = true;
		// 		} else {
		// 			settings.iniLoad = false;
		// 		}
		//
		// 		label = $.rup.i18nParse(json_i18n,element.i18nCaption);
		//
		// 		if (settings.lengthLiteral!==undefined){
		// 			title = label;
		// 			if(label.length>settings.lengthLiteral){
		// 				label = label.substr(0,settings.lengthLiteral).concat("...");
		// 			}
		//
		// 		}
		//
		// 		if (element.layer !== undefined){
		// 			//LAYER => Recoge una capa ya cargada de la Jsp
		// 			element.layer = this._includeLayer(tabs, element.layer, null);
		// 			//si quiero con boton de cerrar pestana
		// 			if (settings.close===true){
		// 				tabs.prepend($('<li>').append(
		// 					$('<a>').attr('href',element.layer)
		// 					.attr({
		// 						'rupLevel':rupLevel,
		// 						'title':title,
		// 						'alt':title
		// 					}).rup_tooltip({})
		// 					.css('padding-left', '1.4em')
		// 					.css('padding-right', '0.3em')
		// 					.append ($('<div>').addClass('rup-tabs_title').text(label))
		// 					.append ($('<span>').addClass('rup-tabs_loading'))
		// 					.append('<span class="ui-icon ui-icon-close" role="presentation">Remove Tab</span>')
		// 			));
		//
		// 			//evento close
		// 			$("span.ui-icon-close").on( "click", function() {
		//
		// 				var tabContentId = $(this).parent().attr("href");
		// 		        $(this).parent().parent().remove(); //remove li of tab
		// 		        $(tabContentId).remove(); //remove respective tab content
		//
		// 				 tabs.tabs( "refresh" );
		// 				 });
		//
		// 			//efecto hover del boton cerrar
		// 			$("span.ui-icon-close").addClass('rup-tabs-close');
		// 			$("span.ui-icon-close").on({
		// 				mouseenter: function () {
		// 					$(this).addClass('rup-tabs-close-hover');
		// 				},
		//
		// 				mouseleave: function () {
		// 					$(this).removeClass('rup-tabs-close-hover');
		// 				}
		// 			});
		//
		// 			}else{
		// 				tabs.prepend($('<li>').append(
		// 						$('<a>').attr('href',element.layer)
		// 						.attr({
		// 							'rupLevel':rupLevel,
		// 							'title':title,
		// 							'alt':title
		// 						}).rup_tooltip({})
		// 						.css('padding-left', '1.4em')
		// 						.css('padding-right', '0.3em')
		// 						.append ($('<div>').addClass('rup-tabs_title').text(label))
		// 						.append ($('<span>').addClass('rup-tabs_loading'))
		// 				));
		// 			}
		//
		// 		} else if (element.url !== undefined){
		// 			//URL => Cargar contenido al pulsar
		// 			tabs.prepend($('<li>').append(
		// 				$('<a>').attr('href',$.rup_utils.setNoPortalParam(element.url))
		// 					.attr({
		// 						'rupLevel':rupLevel,
		// 						'title':title,
		// 						'alt':title
		// 					}).rup_tooltip({})
		// 					.css('padding-left', '1.4em')
		// 					.css('padding-right', '0.3em')
		// 					.append ($('<div>').addClass('rup-tabs_title').text(label))
		// 					.append ($('<span>').addClass('rup-tabs_loading'))
		// 			));
		// 		} else if (element.tabs !== undefined){
		// 			//TABS => Subpestanyas
		// 			tabs.prepend($('<li>').append(
		// 				$('<a>').attr('id','#'+element.i18nCaption)
		// 					.attr('href','#'+element.i18nCaption)
		// 					.attr({
		// 						'rupLevel':rupLevel,
		// 						'title':title,
		// 						'alt':title
		// 					}).rup_tooltip({})
		// 					.css('padding-left', '1.4em')
		// 					.css('padding-right', '0.3em')
		// 					.append ($('<div>').addClass('rup-tabs_title').text(label))
		// 					.append ($('<span>').addClass('rup-tabs_loading'))
		// 			));
		//
		// 			//Gestionar capa contenedora subpestanyas
		// 			tabs = $(tabs).parent();
		//
		// 			var capa = $('<div>'),
		// 				capaId = $.rup_utils.randomIdGenerator(capa);
		// 			tabs.append(capa); 						//Añadir contenedor de capa asociada a pestanya
		// 			tabs = $(tabs).children("#"+capaId); 	//Seleccionar capa contenedora
		//
		// 			//Gestionar capa de la subpestanya
		// 			tabs.prepend($('<div>').attr('id', element.i18nCaption).attr('actualTab',true)); //Añadir capa asociada a la pestanya
		// 			tabs = $(tabs).children('div:first-child'); //Seleccionar capa
		//
		// 			//Subpestanyas
		// 			var subsettings = jQuery.extend(true, {}, settings);
		// 			subsettings.selected = element.selected;
		// 			tabs.append(this._parseJSON(element.tabs, json_i18n, tabs, rupLevel, profundidad+1, subsettings));
		//
		// 			this._tabify(tabs,subsettings); //Si no tiene 1 es que es el primer elemento y lo convertimos a pestanyas
		//
		// 			//Reposicionar 'puntero' para siguiente pasada del bucle
		// 			tabs = $(tabs).parents("div[actualTab=true]").find("ul").first();
		// 			if (tabs.length===0){
		// 				tabs = $("#"+settings.id).find("ul").first();
		// 			}
		//
		// 		}
		// 	}
		// 	$(tabs).parents("div[actualTab=true]").first().removeAttr("actualTab");
		// 	delete tabs;
		// },

		//Función encargada de validar e incluir la capa que contendrá la pestanya. De no tener identificador se le asocia uno.
		_includeLayer: function _includeLayer(tabs, layerSelector, pestanya) {
			var content, selectObject;
			if ($(layerSelector).length > 0) {
				if ($(layerSelector).length === 1) {
					selectObject = $(layerSelector).css('display', '');
				} else {
					selectObject = $('<div>').append($(layerSelector).css('display', ''));
				}

				if (pestanya === null) {
					content = $('<div>').append(selectObject);
					tabs.parent().append(content);
					layerSelector = '#' + $.rup_utils.randomIdGenerator(content);
				} else {
					layerSelector = pestanya.attr('href');
					content = $(pestanya.attr('href'));
					content.children().remove();
					content.append(selectObject);
				}
			} else {

				layerSelector = '#load-tab-error';

				if (pestanya === null) {
					tabs.parent().append($('<div>').attr('id', 'load-tab-error').append($('<div>').addClass('rup-loading_tab_error').append($.rup.i18nParse($.rup.i18n.base, 'rup_global.selectorError'))));
				} else {
					layerSelector = pestanya.attr('href');
					content = $(pestanya.attr('href'));
					content.children().remove();
					content.append($('<div>').attr('id', 'load-tab-error').append($('<div>').addClass('rup-loading_tab_error').append($.rup.i18nParse($.rup.i18n.base, 'rup_global.selectorError'))));
				}
			}
			return layerSelector;
		},
		_scrollable: function _scrollable(settings) {
			var o = $.extend({}, settings),
			    $tabs = $(this),
			    $tabsNav = $tabs.find('.ui-tabs-nav'),
			    $nav; //referencia al wrapper

			//ajuste del css
			$tabs.css({
				'padding': 2,
				'position': 'relative'
			});

			//wrapper del contenido
			$tabs.wrap('<div id="stTabswrapper" class="stTabsMainWrapper" style="position:relative"/>').find('.ui-tabs-nav').css('overflow', 'hidden').wrapInner('<div class="stTabsInnerWrapper" style="width:30000px"><span class="stWidthChecker"/></div>');

			var $widthChecker = $tabs.find('.stWidthChecker'),
			    $itemContainer = $tabs.find('.stTabsInnerWrapper'),
			    $tabsWrapper = $tabs.parents('#stTabswrapper').width($tabs.outerWidth(true));
			//correción de bug en safari
			if ($.browser.safari) {
				$tabsWrapper.width($tabs.width() + 6);
			}
			//alert($tabsWrapper.width());
			if (o.resizable) {
				if ($.fn.resizable) {
					$tabsWrapper.resizable({
						minWidth: $tabsWrapper.width(),
						maxWidth: $tabsWrapper.width() * 2,
						minHeight: $tabsWrapper.height(),
						maxHeight: $tabsWrapper.height() * 2,
						handles: o.resizeHandles,
						alsoResize: $tabs,
						//start : function(){  },
						resize: function resize() {
							$tabs.trigger('resized');
						}
						//stop: function(){ $tabs.trigger('scrollToTab',$tabsNav.find('li.ui-tabs-active')); }
					});
				} else {
					alert('Error:\nCannot be resizable because "jQuery.resizable" plugin is not available.');
				}
			}

			//añade iconos de navegación
			//console.log(parseInt($tabsNav.innerHeight(true)));
			//Total height of nav/2 - total height of arrow/2
			//var arrowsTopMargin = (parseInt(parseInt($tabsNav.innerHeight(true)/2)-8)),
			//	arrowsCommonCss={'cursor':'pointer','z-index':1000,'position':'absolute','top':3,'height':$tabsNav.outerHeight()-($.browser.safari ? 2 : 1)};
			var arrowsTopMargin = parseInt(parseInt($tabsNav.innerHeight() / 2) - 8),
			    arrowsCommonCss = {
				'cursor': 'pointer',
				'z-index': 1000,
				'position': 'absolute',
				'top': 3,
				'height': $tabsNav.outerHeight() - ($.browser.safari ? 2 : 1)
			};
			$tabsWrapper.prepend($nav = $('<div/>').disableSelection().css({
				'position': 'relative',
				'z-index': 3000,
				'display': 'block'
			}).append($('<span/>').disableSelection().attr('title', 'Previous tab').css(arrowsCommonCss).addClass('ui-state-active ui-corner-tl ui-corner-bl stPrev stNav').css('left', 3).append($('<span/>').disableSelection().addClass('ui-icon ui-icon-carat-1-w').html('Previous tab').css('margin-top', arrowsTopMargin)).click(function () {
				//comprueba si esta deshabilitado
				if ($(this).hasClass('ui-state-disabled')) return;
				//selecciona el tab anterior y lanza el evento scrollToTab
				prevIndex = $tabsNav.find('li.ui-tabs-active').prevAll().length - 1;
				//seleeciona el tab
				$tabsNav.find('li').eq(prevIndex).find('a').trigger('click');
				return false;
			}), $('<span/>').disableSelection().attr('title', 'Next tab').css(arrowsCommonCss).addClass('ui-state-active ui-corner-tr ui-corner-br stNext stNav').css({
				'right': 3
			}).append($('<span/>').addClass('ui-icon ui-icon-carat-1-e').html('Next tab').css('margin-top', arrowsTopMargin)).click(function () {
				//selecciona el tab anterior y lanza el evento scrollToTab
				nextIndex = $tabsNav.find('li.ui-tabs-active').prevAll().length + 1;
				//selecciona el tab
				$tabsNav.find('li').eq(nextIndex).find('a').trigger('click');
				return false;
			})));

			//Binding de los eventos con las pestañas
			$tabs.on('navEnabler', function () {
				setTimeout(function () {
					//comprueba si la ultima o la primera  pestaña esta seleccionada y en ese caso deshabilita las flechas
					var isLast = $tabsNav.find('.ui-tabs-active').is(':last-child'),
					    isFirst = $tabsNav.find('.ui-tabs-active').is(':first-child'),
					    $ntNav = $tabsWrapper.find('.stNext'),
					    $pvNav = $tabsWrapper.find('.stPrev');
					//debug('isLast = '+isLast+' - isFirst = '+isFirst);
					if (isLast) {
						$pvNav.removeClass('ui-state-disabled');
						$ntNav.addClass('ui-state-disabled');
					} else if (isFirst) {
						$ntNav.removeClass('ui-state-disabled');
						$pvNav.addClass('ui-state-disabled');
					} else {
						$ntNav.removeClass('ui-state-disabled');
						$pvNav.removeClass('ui-state-disabled');
					}
				}, o.animationSpeed);
			})
			//Comprueba si hace face falta la navegacion (si hay demasiadas pestañas visibles)
			.on('navHandler', function () {
				//Si $widthCheker es mayor tabnav  lo oculto
				//console.log($widthChecker.width());
				//console.log($tabsNav.width());

				//if($widthChecker.width()>$tabsNav.width())
				if ($('.stWidthChecker').children().length > 5) {
					$nav.show();
					//añade cierto margen  a la primera pestaña para hacerla visible si esta seleccionada
					$tabsNav.find('li:first').css('margin-left', $nav.find('.stPrev').outerWidth(true));
				} else {
					$nav.hide();
					//elima el margen del primer elemento
					$tabsNav.find('li:first').css('margin-left', 0);
				}
			})
			//Bind el evento de mover el scroll
			.on('scrollToTab', function (event, $tabToScrollTo, clickedFrom, hiddenOnSide) {
				//Si no se provee una pestaña como parametro ,scroll a la ultima pestaña
				$tabToScrollTo = typeof $tabToScrollTo != 'undefined' ? $($tabToScrollTo) : $tabsNav.find('li.ui-tabs-active');

				var navWidth = $nav.is(':visible') ? $nav.find('.stPrev').outerWidth(true) : 0;
				//debug($tabToScrollTo.prevAll().length)

				offsetLeft = -($tabs.width() - ($tabToScrollTo.outerWidth(true) + navWidth + parseInt($tabsNav.find('li:last').css('margin-right'), 10)));
				offsetLeft = clickedFrom == 'tabClicked' && hiddenOnSide == 'left' ? -navWidth : offsetLeft;
				offsetLeft = clickedFrom == 'tabClicked' && hiddenOnSide == 'right' ? offsetLeft : offsetLeft;
				//debug(offsetLeft);
				var scrollSettings = {
					'axis': 'x',
					'margin': true,
					'offset': {
						'left': offsetLeft
					},
					'easing': o.easing || ''
				};
				//debug(-($tabs.width()-(116+navWidth)));
				$tabsNav.scrollTo($tabToScrollTo, o.animationSpeed, scrollSettings);
			}).on('bindTabClick', function () {
				//Controla el scroll cuando un usuario clickea manualmente en la pestaña
				$tabsNav.find('a').click(function () {
					var $liClicked = $(this).parents('li');
					var navWidth = $nav.find('.stPrev').outerWidth(true);
					//debug('left='+($liClicked.offset().left)+' and tabs width = '+ ($tabs.width()-navWidth));
					if ($liClicked.position().left - navWidth < 0) {
						$tabs.trigger('scrollToTab', [$liClicked, 'tabClicked', 'left']);
					} else if ($liClicked.outerWidth() + $liClicked.position().left > $tabs.width() - navWidth) {
						$tabs.trigger('scrollToTab', [$liClicked, 'tabClicked', 'right']);
					}
					//Des/habilita las flechas de navegacion
					$tabs.trigger('navEnabler');
					return false;
				});
			}).on('resized', function () {
				$tabs.trigger('navHandler');
				$tabs.trigger('scrollToTab', $tabsNav.find('li.ui-tabs-active'));
			})

			//triggers
			.trigger('navHandler').trigger('navEnabler').trigger('bindTabClick');
		},
		/* deprecado el metodo "add" en jquery ui 1.10
             * Este método sustituye su utilidad
             * */
		_addTab: function _addTab(args) {

			if (args.url === undefined) {
				args.url = '#';
			}
			var previousTab = $('#' + args.idTab).find('.ui-tabs-nav li:eq(' + (args.position - 1) + ')');
			if (args.orientation !== undefined) {
				$('<li><a href=\'' + args.url + '\'>' + args.label + '</a></li>').insertBefore(previousTab);
			} else {
				$('<li><a href=\'' + args.url + '\'>' + args.label + '</a></li>').insertAfter(previousTab);
			}

			$('#' + args.idTab).tabs('refresh');
		},
		/* deprecado el metodo "remove" en jquery ui 1.10
             * Este método sustituye su utilidad
             * */
		_removeTab: function _removeTab(args) {
			// Remove the tab
			var tab = $('#' + args.idTab).find('.ui-tabs-nav li:eq(' + (args.position - 1) + ')').remove();

			// Refresh the tabs widget
			$('#' + args.idTab).tabs('refresh');
		},

		/* deprecado el metodo "url" en jquery ui 1.10
             * Este método sustituye su utilidad
             * */
		_changeUrlTab: function _changeUrlTab(args) {
			var tab = $('#' + args.idTab).find('.ui-tabs-nav li:eq(' + args.position + ')');
			$(tab).attr('href', args.url);
		}
	});

	//*******************************************************
	// DEFINICIÓN DE LA CONFIGURACION POR DEFECTO DEL PATRON
	//*******************************************************
	/**
     * @name options
     * @property {object}  disabled - Permite especificar el conjunto de pestañas que, inicialmente, estarán deshabilitadas
     * @property {boolean} [close=false] - Determina si se debe mostrar un icono de cerrar pestaña junto al label de las mismas.
     * @property {integer} 	fixedHeight - Permite especificar una altura fija para el contenedor de las pestañas
     * @property {integer}  [lengthLiteral=undefined] - Permite especificar un número máximo de caracteres a mostrar en el label de la pestaña antes de aplicar ellipsis.
     * @property {integer} maxNumberTabs - Parámetro que determina el número máximo de pestañas que va a permitir el componente que se añadan de manera dinámica
     * @property {boolean} [scrollable=false] - Determina si la pestaña permite el mostrar scroll en la capa contenedora
     * @property {string} layer - Parámetro que permite especificar fragmentos html previamente cargados para el contenido de una pestaña. El parámetro acepta cualquier tipo de selector válido de JQuery para determinar que fragmento html se ubica en la pestaña. En caso de precisarse un selector de JQuery que devuelva más de un elemento, éstos se incluirán en la pestaña correspondiente dispuestos verticalmente (esta forma de trabajar no es muy ortodoxa pero es factible).
     * @property {integer} width - Permite definir la anchura del componente.
     * @property {integer} height - Permite difinir la altura del componente.
     * @property {boolean} [tabsAtBottom=false] - Parámetro que determina si las pestañas se van a mostrar en la parte inferior en vez de en la superior
     *
     *
     */

	$.fn.rup_tabs.defaults = {
		ajaxOptions: {},
		cache: true,
		cookie: null,
		show: null,
		hide: null,
		panelTemplate: '<div></div>',
		profun: 0,
		active: 0, //deprecated selected option, ahora es active
		//eventos
		create: null,
		beforeActivate: null,
		load: null,
		activate: null, //deprecated show event, ahora es activate
		add: null,
		remove: null,
		enable: null,
		disable: null,
		tabsAtBottom: false
	};
	/* **********/
	/* EVENTOS */
	/* **********/

	/**
     * Se lanza cada vez que se crea una pestaña
     * @event module:rup_tabs#create
     * @property {Event} e - Objeto Event correspondiente al evento disparado.
     * @example
     * $(selector).rup_tabs ({ create: function(){...} });
     */

	/**
     * Se lanza el evento cada vez que se hace click sobre una pestaña
     * @event module:rup_tabs#select
     * @property {Event} e - Objeto Event correspondiente al evento disparado.
     * @example
     * $(selector).rup_tabs ({ select: function(){...} });
     */

	/**
     * Este evento se desencadena después de que el contenido de una pestaña se ha cargado.
     * @event module:rup_tabs#load
     * @property {Event} e - Objeto Event correspondiente al evento disparado.
     * @example
     * $(selector).rup_tabs ({ load: function(){...} });
     */

	/**
     * Este evento ocurre cuando una pestaña está preparada para ser mostrada.
     * @event module:rup_tabs#activate
     * @property {Event} e - Objeto Event correspondiente al evento disparado.
     * @example
     * $(selector).rup_tabs ({ activate: function(){...} });
     */

	/**
     * Este evento se desencadena cuando se añade una pestaña
     * @event module:rup_tabs#add
     * @property {Event} e - Objeto Event correspondiente al evento disparado.
     * @example
     * $(selector).rup_tabs ({ add: function(){...} });
     */

	/**
     * Este evento se desencadena cuando se elimina una pestaña
     * @event module:rup_tabs#remove
     * @property {Event} e - Objeto Event correspondiente al evento disparado.
     * @example
     * $(selector).rup_tabs ({ remove: function(){...} });
     */

	/**
     * Este evento se desencadena cuando se habilita una pestaña
     * @event module:rup_tabs#enable
     * @property {Event} e - Objeto Event correspondiente al evento disparado.
     * @example
     * $(selector).rup_tabs ({ enable: function(){...} });
     */

	/**
     * Este evento se desencadena cuando se deshabilita una pestaña
     * @event module:rup_tabs#disable
     * @property {Event} e - Objeto Event correspondiente al evento disparado.
     * @example
     * $(selector).rup_tabs ({ disable: function(){...} });
     */
});
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))

/***/ }),
/* 167 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*!
 * Copyright 2016 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 */

/**
 * El usuario puede introducir y seleccionar una hora tanto de forma manual como visual, moviéndose fácilmente por las horas y los minutos, recibiendo ayudas y sugerencias para minimizar las posibilidades de introducir una hora incorrecta.
 *
 * @summary Componente RUP Time.
 * @module rup_time
 * @example
 * var properties = {
 *   labelMaskId : "hora-mask",
 *   showSecond : true,
 *   timeFormat: 'hh:mm:ss',
 *   showButtonPanel: true
 * };
 *
 * $("#idTime").rup_time(properties);
 */

/*global define */
/*global jQuery */

(function (factory) {
  if (true) {

    // AMD. Register as an anonymous module.
    !(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(2), __webpack_require__(19)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
  } else {

    // Browser globals
    factory(jQuery);
  }
})(function ($) {

  // DEFINICIÓN BASE DEL PATRÓN (definición de la variable privada que contendrá los métodos y la función de jQuery)

  var rup_time = {};

  //Se configura el arranque de UDA para que alberge el nuevo patrón
  $.extend($.rup.iniRup, $.rup.rupSelectorObjectConstructor('rup_time', rup_time));

  // DEFINICIÓN DE MÉTODOS PÚBLICOS
  $.fn.rup_time('extend', {
    /**
       * Método utilizado para obtener el valor del componente. Este método es el utilizado por el resto de componentes RUP para estandarizar la obtención del valor.
       *
       * @name getRupValue
       * @function
       * @return {string} - Devuelve el valor actual del componente seleccionado por el usuario.
       * @example
       * $("#idTime").rup_time("getRupValue");
       */
    getRupValue: function getRupValue() {
      var timeformat, dateObj;
      timeformat = $(this).data('datepicker').settings.timeFormat;
      dateObj = $.datepicker.parseTime(timeformat, $(this).rup_time('getTime'));
      return dateObj ? $.timepicker._formatTime(dateObj, 'hh:mm:ss') : '';
    },
    /**
       * Método utilizado para asignar el valor al componente. Este método es el utilizado por el resto de componentes RUP para estandarizar la asignación del valor.
       *
       * @name setRupValue
       * @function
       * @param {string} param - Valor que se va a asignar al componente. En caso de tratarse de uan configuración en la que se permite seleccionar varias fechas se indicará mediante un array.
       * @example
       * $("#idTime").rup_time("setRupValue", "10:25:16");
       */
    setRupValue: function setRupValue(param) {
      var timeformat, tmpDate, formattedTime;
      timeformat = $(this).data('datepicker').settings.timeFormat;
      tmpDate = $.datepicker.parseTime('hh:mm:ss', param);
      formattedTime = tmpDate ? $.timepicker._formatTime(tmpDate, timeformat) : '';
      $(this).val(formattedTime);
    },
    /**
       * Elimina el componente de la pantalla. En caso de tener máscara también se restaura el label con un texto vacío.
       *
       * @name destroy
       * @function
       * @example
       * $("#idTime").rup_time("destroy");
       */
    destroy: function destroy() {
      //Eliminar máscara
      var labelMaskId = $(this).data('datepicker').settings.labelMaskId;
      if (labelMaskId) {
        $('#' + labelMaskId).text('');
      }
      //Eliminar imagen (reloj)
      $(this).next('img').remove();
      $(this).timepicker('destroy');
    },
    /**
       * Deshabilita el componente en pantalla no pudiendo introducirse ninguna hora ni se despliega el calendario.
       *
       * @name disable
       * @function
       * @example
       * $("#idTime").rup_time("disable");
       */
    disable: function disable() {
      $(this).timepicker('disable');
    },
    /**
       * Habilita el componente permitiendo introducir la hora tanto mediante teclado como mediante el desplegable.
       *
       * @name enable
       * @function
       * @example
       * $("#idTime").rup_time("enable");
       */
    enable: function enable() {
      $(this).timepicker('enable');
    },
    /**
       * Indica si el componente se encuentra deshabilitado o no.
       *
       * @name isDisabled
       * @function
       * @return {boolean} - Determina si el componente está deshabilitado o no.
       * @example
       * $("#idTime").rup_time("isDisabled");
       */
    isDisabled: function isDisabled() {
      return $(this).timepicker('isDisabled');
    },
    /**
       * Oculta el desplegable para seleccionar una hora.
       *
       * @function
       * @name hide
       * @example
       * $("#idTime").rup_time("hide");
       */
    hide: function hide() {
      $(this).timepicker('hide');
    },
    /**
       * Muestra el desplegable para seleccionar una hora.
       *
       * @function
       * @name show
       * @example
       * $("#idTime").rup_time("show");
       */
    show: function show() {
      $(this).timepicker('show');
    },
    /**
       * Devuelve la hora seleccionada, si no se ha seleccionado nada devuelve vacío.
       *
       * @name getTime
       * @function
       * @return {string} - Devuelve la hora seleccionada por el usuario utilizando.
       * @example
       * $("#idTime").rup_time("getTime");
       */
    getTime: function getTime() {
      return $(this).val();
    },
    /**
       * Establece la hora del componente.
       *
       * @name setTime
       * @function
       * @return {date} time - Hora que se desea asignar al componente.
       * @example
       * $("#idTime").rup_time("setTime", time);
       */
    setTime: function setTime(time) {
      $(this).timepicker('refresh'); //Necesario para 'inicializar' el componente
      $.datepicker._setTime($.datepicker._getInst($('#' + $(this).data('datepicker').settings.id)[0]), time);
    },
    /**
       * Refresca el calendario desplegado por si ha habido algún cambio.
       *
       * @name refresh
       * @function
       * @example
       * $("#idTime").rup_time("refresh");
       */
    refresh: function refresh() {
      $(this).timepicker('refresh');
    },
    /**
       * Permite consultar y modificar la configuración del componente.
       *
       * @name option
       * @param {string | object} optionName - Nombre de la propiedad que se desea gestionar o objeto de compuesto de varias propiedades.
       * @param {*} [value] - Corresponde al valor de la propiedad en caso de haberse especificado el nombre de la misma en el primér parámetro.
       * @function
       * @example
       * // Consultar una propiedad
       * $("#idTime").rup_time("option", "showSecond");
       * // Establecer una propiedad
       * $("#idTime").rup_time("option", "showSecond", true);
       * // Establecer varias propiedad
       * $("#idTime").rup_time("option", {showSecond: true, showButtonPanel: true});
       */
    option: function option(optionName, value) {
      $(this).timepicker('option', optionName, value);
    }
    //No soportadas: widget, dialog
  });

  // DEFINICIÓN DE MÉTODOS PRIVADOS
  $.fn.rup_time('extend', {
    /**
       * Método de inicialización del componente
       *
       * @name _init
       * @function
       * @private
       */
    _init: function _init(args) {
      if (args.length > 1) {
        $.rup.errorGestor($.rup.i18nParse($.rup.i18n.base, 'rup_global.initError') + $(this).attr('id'));
      } else {
        //Se recogen y cruzan las paremetrizaciones del objeto
        var $self = $(this),
            self = $self[0],
            settings = $.extend({}, $.fn.rup_time.defaults, args[0]);

        self._ADAPTER = $.rup.adapter[settings.adapter];

        //Se carga el identificador del padre del patron
        settings.id = $self.attr('id');

        $self.attr('ruptype', 'time');

        //Carga de propiedades/literales
        var literales = $.rup.i18n.base['rup_time'];
        for (var key in literales) {
          $.timepicker._defaults[key] = literales[key];
        }

        //Mostrar máscara
        if (settings.labelMaskId) {
          $('#' + settings.labelMaskId).text($.rup.i18nParse($.rup.i18n.base, 'rup_time.mask') + ' ');
        }

        //Mostrar placeholder
        if (settings.placeholderMask) {
          $self.attr('placeholder', $.rup.i18nParse($.rup.i18n.base, 'rup_time.mask'));
        }

        //Imagen del reloj
        settings.buttonImage = $.rup.STATICS + (settings.buttonImage ? settings.buttonImage : '/rup/css/images/clock.png');

        //Atributos NO MODIFICABLES

        //Timepicker
        $self.timepicker(settings);

        //Max-Length
        //$("#"+settings.id).attr("maxlength",literales["mask"].length-2);

        //Añadir imagen
        $.proxy(self._ADAPTER.initIconTrigger, $self)(settings);

        //Ajuste para el comportamiento de portales
        if ($.rup_utils.aplicatioInPortal() && !$self.is('div')) {
          $('.r01gContainer').append($('.ui-datepicker:not(.r01gContainer .ui-datepicker)'));
        }

        //Deshabilitar
        if (settings.disabled) {
          $self.rup_time('disable');
        }

        // Se aplica el tooltip
        $self.parent().find('[title]').rup_tooltip({
          'applyToPortal': true
        });
      }
    }
  });

  // DEFINICIÓN DE LA CONFIGURACION POR DEFECTO DEL PATRON
  $.fn.rup_time.defaults = {
    adapter: 'time_bootstrap',
    placeholderMask: false,
    stepHour: 1,
    stepMinute: 1,
    stepSecond: 1,
    showButtonPanel: false,
    timeOnly: true
  };

  //Sobreescribir EVENTOS
  $.datepicker._timepicker_doKeyPress = $.datepicker._doKeyPress;
  $.datepicker._doKeyPress = function (event) {
    var instance = $.datepicker._get($.datepicker._getInst(event.target), 'timepicker');
    switch (event.keyCode) {
      //Izquierda
      case 37:
        if (event.ctrlKey && !(event.altKey || event.shiftKey)) {
          //Ctrl
          instance.hour_slider.slider('option', 'value', instance.hour_slider.slider('option', 'value') - instance._defaults.stepHour);
        } else if (event.ctrlKey && event.shiftKey && !event.altKey) {
          //Ctrl + Shift
          instance.minute_slider.slider('option', 'value', instance.minute_slider.slider('option', 'value') - instance._defaults.stepMinute);
        } else if (event.ctrlKey && event.shiftKey && event.altKey) {
          //Ctrl + Shfit + Alt
          instance.second_slider.slider('option', 'value', instance.second_slider.slider('option', 'value') - instance._defaults.stepSecond);
        }
        break;
      //Derecha
      case 39:
        if (event.ctrlKey && !(event.altKey || event.shiftKey)) {
          //Ctrl
          instance.hour_slider.slider('option', 'value', instance.hour_slider.slider('option', 'value') + instance._defaults.stepHour);
        } else if (event.ctrlKey && event.shiftKey && !event.altKey) {
          //Ctrl + Shift
          instance.minute_slider.slider('option', 'value', instance.minute_slider.slider('option', 'value') + instance._defaults.stepMinute);
        } else if (event.ctrlKey && event.shiftKey && event.altKey) {
          //Ctrl + Shfit + Alt
          instance.second_slider.slider('option', 'value', instance.second_slider.slider('option', 'value') + instance._defaults.stepSecond);
        }
        break;
    }
    if (instance) {
      instance._onTimeChange();
    }
    return $.datepicker._timepicker_doKeyPress(event);
  };

  /**
    * @description Propiedades de configuración del componente.
    *
    * @name defaults
    *
    * @property {boolean} [disabled=false] - Indica si el componente debe aparecer deshabilitado o no.
    * @property {string} [labelMaskId] - Identificador del label que contendrá la máscara que indica el formato de la hora.
    * @property {string} [timeFormat=hh:mm] - Formato en el que se muestra la hora. Los posibles modificadores son: <ul><li> h: modificador relativo a las horas. En caso de querer que las horas inferiores a 10 muestren el 0 deberá incluirse por duplicado (hh). </li><li> m: modificador relativo a los minutos. En caso de querer que las horas inferiores a 10 muestren el 0 deberá incluirse por duplicado (mm). </li><li>s: modificador relativo a los segundos. En caso de querer que las horas inferiores a 10 muestren el 0 deberá incluirse por duplicado (ss). </li></ul>
    * @property {Integer} [hour=0] - Valor con el que se carga inicialmente las horas del componente..
    * @property {Integer} [minute=0] - Valor con el que se carga inicialmente los minutos del componente.
    * @property {Integer} [second=0] - Valor con el que se carga inicialmente los segundos del componente.
    * @property {Integer} [hourMin=0] - Valor mínimo seleccionable en las horas del componente.
    * @property {Integer} [hourMax=23] - Valor máximo seleccionable en las horas del componente.
    * @property {Integer} [minuteMin=0] - Valor mínimo seleccionable en los minutos del componente.
    * @property {Integer} [minuteMax=59] - Valor máximo seleccionable en los minutos del componente.
    * @property {Integer} [secondMin=0] - Valor mínimo seleccionable en los segundos del componente.
    * @property {Integer} [secondMax=59] - Valor mínimo seleccionable en los segundos del componente.
    * @property {boolean} [showHour=true] - Indica si se muestran o no las horas.
    * @property {boolean} [showMinute=true] - Indica si se muestran o no los minutos.
    * @property {boolean} [showSecond=false] - Indica si se muestran o no los segundos.
    * @property {Integer} [stepHour=1] - Establece el incremento de la barra de scroll relativa a las horas.
    * @property {Integer} [stepMinute=1] - Establece el incremento de la barra de scroll relativa a los minutos.
    * @property {Integer} [stepSecond=1] - establece el incremento de la barra de scroll relativa a los segundos.
    * @property {Integer} [hourGrid=0] - Indica el intervalo de los números que aparecen bajo la barra de scroll relativa a las horas. Al pinchar sobre dichos números se selecciona ese valor.
    * @property {Integer} [minuteGrid=0] - Indica el intervalo de los números que aparecen bajo la barra de scroll relativa a los minutos. Al pinchar sobre dichos números se selecciona ese valor.
    * @property {Integer} [secondGrid=0] - Indica el intervalo de los números que aparecen bajo la barra de scroll relativa a los segundos. Al pinchar sobre dichos números se selecciona ese valor.
    * @property {boolean} [showTime=true] - Determina si se desea mostrar o no la fecha en el desplegable.
    * @property {boolean} [ampm=false] - Determina si en lugar de mostrar la hora en formato 0-24 se muestra con el literal am/pm.
    * @property {boolean} [showButtonPanel=false] - Indica si se muestran los botones de la parte inferior (ahora y cerrar).
    * @property {string} [mask] - Texto empleado para la máscara de la fecha. Su valor por defecto se obtiene del fichero de idioma.
    * @property {string} [buttonText] - Texto alternativo de la imagen que se muestra junto al campo de la fecha. Su valor por defecto se obtiene del fichero de idioma.
    * @property {string} [closeText] - Texto a mostrar en el botón que se muestra en el panel inferior (requiere el activarlo mediante el atributo showButtonPanel) para cerrar el desplegable. Su valor por defecto se obtiene del fichero de idioma..
    * @property {string} [currentText] - Texto a mostrar en el botón que se muestra en el panel inferior (requiere el activarlo mediante el atributo showButtonPanel) para seleccionar la hora actual en el desplegable. Su valor por defecto se obtiene del fichero de idioma.
    * @property {string} [timeOnlyTitle] - Texto que aparece en la cabecera del desplegable. Su valor por defecto se obtiene del fichero de idioma.
    * @property {string} [timeText] - Texto que aparece delante de la hora seleccionada (en caso de que esté activo el atributo showTime). Su valor por defecto se obtiene del fichero de idioma.
    * @property {string} [hourText] - Texto que aparece delante de la barra de scroll de selección de horas. Su valor por defecto se obtiene del fichero de idioma.
    * @property {string} [minuteText] - Texto que aparece delante de la barra de scroll de selección de minutos. Su valor por defecto se obtiene del fichero de idioma.
    * @property {string} [secondText] - Texto que aparece delante de la barra de scroll de selección de segundos. Su valor por defecto se obtiene del fichero de idioma.
    */

  //eventos

  /**
    * Permite asociar una función que se ejecutará cuando se modifique alguno de los valores del desplegable (hora, minutos o segundos). Los parámetros recibidos son la hora seleccionada (texto) y la instancia del componente
    * @event module:rup_time#onSelect
    * @property {Event} e - Objeto Event correspondiente al evento disparado.
    * @example
    * $(selector).rup_time({ onSelect: function(dateText, inst){...} });
    */

  /**
    * Permite asociar una función que se ejecutará cuando se oculte el desplegable. Los parámetros recibidos son la hora seleccionada (texto) y la instancia del componente
    * @event module:rup_time#onClose
    * @property {Event} e - Objeto Event correspondiente al evento disparado.
    * @example
    * $(selector).rup_time({ onClose: function(dateText, inst){...} });
    */
});

/***/ }),
/* 168 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function(jQuery) {var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*!
 * Copyright 2013 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 */

/**
 * Permite al usuario mostrar y ocultar de manera selectiva, información mostrada en una estructura jerárquica.
 *
 * @summary Componente RUP Tree.
 * @module rup_tree
 * @see El componente está basado en el plugin {@link https://www.jstree.com/|jstree}. Para mas información acerca de las funcionalidades y opciones de configuración pinche {@link https://old.jstree.com/documentation|aquí}.
 * @example
 * $("#ejemploArbolDiv").rup_tree(properties);
 *
 */

/*global define */
/*global jQuery */

(function (factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(2), __webpack_require__(199), __webpack_require__(196)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		factory(jQuery);
	}
})(function ($) {

	//*****************************************************************************************************************
	// DEFINICIÓN BASE DEL PATRÓN (definición de la variable privada que contendrá los métodos y la función de jQuery)
	//*****************************************************************************************************************

	var rup_tree = {};

	//Se configura el arranque de UDA para que alberge el nuevo patrón
	jQuery.extend($.rup.iniRup, $.rup.rupSelectorObjectConstructor('rup_tree', rup_tree));

	//********************************
	// DEFINICIÓN DE MÉTODOS PÚBLICOS
	//********************************

	jQuery.fn.rup_tree('extend', {
		/* Metodos publicos del core */

		/**
         * Método utilizado para obtener el valor del componente. Este método es el utilizado por el resto de componentes RUP para estandarizar la  obtención del valor del Autocomplete
         *
         * @function
         * @name getRupValue
         * @return {string | number} - Devuelve el valor actual del componente seleccionado por el usuario.
         * @example
         * $(selector).rup_tree("getRupValue");
         */

		getRupValue: function getRupValue() {
			var $self = this,
			    settings = $self.data('settings'),
			    selectedItems,
			    tmpId,
			    name = $self.attr('name'),
			    wrapObj;

			if (jQuery.inArray('checkbox', settings.plugins) !== -1) {
				selectedItems = $self.rup_tree('get_checked', null, true);
			} else {
				selectedItems = $self.rup_tree('get_selected');
			}

			var returnArray = jQuery.map(selectedItems, function (item, index) {
				var $item = jQuery(item);

				if (jQuery.isFunction(settings.core.getValue)) {
					return jQuery.proxy(settings.core.getValue, $self)($item, $item.data());
				}

				tmpId = $item.attr('id');
				return tmpId ? tmpId : $item.text();
			});

			if (settings.core.submitAsJSON) {
				return jQuery.rup_utils.getRupValueAsJson(name, returnArray);
			} else {

				if (settings.core.submitAsString) {
					return jQuery.rup_utils.getRupValueWrapped(name, returnArray.toString());
				} else {
					return jQuery.rup_utils.getRupValueWrapped(name, returnArray);
				}
			}
		},
		/**
         * Método utilizado para asignar el valor al componente. Este método es el utilizado por
         * el resto de componentes RUP para estandarizar la asignación del valor al Autocomplete.
         *
         * @function
         * @name setRupValue
         * @param {string | number} param - Valor que se va a asignar al componente.
         * @example
         * $("#selector").rup_tree("setRupValue", value);
         */
		setRupValue: function setRupValue(valuesArray) {
			var $self = this,
			    settings = $self.data('settings'),
			    $items,
			    $item,
			    itemValue,
			    tmpId,
			    dataArray;

			$self.rup_tree('uncheck_all');

			$items = $self.get_container_ul().find('li');

			dataArray = settings.core.readAsString === true ? valuesArray.split(',') : valuesArray;

			jQuery.each($items, function (index, item) {
				$item = jQuery(item);

				if (jQuery.isFunction(settings.core.getValue)) {
					itemValue = jQuery.proxy(settings.core.getValue, $self)($item, $item.data());
				} else {
					tmpId = $item.attr('id');
					itemValue = tmpId ? tmpId : $item.text();
				}

				if (jQuery.inArray(itemValue, dataArray) !== -1) {
					$self.rup_tree('check_node', item);
				}
			});
		},
		rollback: function rollback(rollback_object) {
			jQuery.jstree.rollback(rollback_object);
		},
		get_container: function get_container() {
			return $(this).jstree('get_container');
		},
		get_container_ul: function get_container_ul() {
			return $(this).jstree('get_container_ul');
		},
		destroy: function destroy() {
			$(this).jstree('destroy');
		},
		refresh: function refresh(node) {
			$(this).jstree('refresh', node);
		},
		set_focus: function set_focus() {
			$(this).jstree('set_focus');
		},
		unset_focus: function unset_focus() {
			$(this).jstree('unset_focus');
		},
		is_focused: function is_focused() {
			return $(this).jstree('is_focused');
		},
		lock: function lock() {
			$(this).jstree('lock');
		},
		unlock: function unlock() {
			$(this).jstree('unlock');
		},
		is_locked: function is_locked() {
			return $(this).jstree('is_locked');
		},
		get_path: function get_path(node, id_mode) {
			return $(this).jstree('get_path', node, id_mode);
		},
		open_node: function open_node(node, callback, skip_animation) {
			$(this).jstree('open_node', node, callback, skip_animation);
		},
		close_node: function close_node(node, skip_animation) {
			$(this).jstree('close_node', node, skip_animation);
		},
		toggle_node: function toggle_node(node) {
			return $(this).jstree('toggle_node', node);
		},
		open_all: function open_all(node, do_animation) {
			$(this).jstree('open_all', node, do_animation);
		},
		close_all: function close_all(node, do_animation) {
			$(this).jstree('close_all', node, do_animation);
		},
		is_open: function is_open(node) {
			return $(this).jstree('is_open', node);
		},
		is_closed: function is_closed(node) {
			return $(this).jstree('is_closed', node);
		},
		is_leaf: function is_leaf(node) {
			return $(this).jstree('is_leaf', node);
		},
		get_rollback: function get_rollback() {
			return $(this).jstree('get_rollback');
		},
		create_node: function create_node(node, position, js, callback) {
			return $(this).jstree('create_node', node, position, js, callback);
		},
		get_text: function get_text(node) {
			return $(this).jstree('get_text', node);
		},
		rename_node: function rename_node(node, text) {
			$(this).jstree('rename_node', node, text);
		},
		delete_node: function delete_node(node) {
			$(this).jstree('delete_node', node);
		},
		check_move: function check_move() {
			return $(this).jstree('check_move');
		},
		move_node: function move_node(obj, ref, position, is_copy, is_prepared, skip_check) {
			return $(this).jstree('move_node', obj, ref, position, is_copy, is_prepared, skip_check);
		},

		/* Metodos publicos del theme */
		get_theme: function get_theme() {
			var theme = $(this).jstree('get_theme');
			if (typeof theme !== 'string') {
				return 'rup-default';
			} else {
				return theme;
			}
		},
		set_theme: function set_theme(name, url) {
			if (name !== 'rup-default') {
				if ($(this).rup_tree('get_theme') === 'rup-default') {
					$(this).removeClass('jstree-rup-default');
				}
				var settings = this.data('settings');
				settings.actualThemeUrl = url;
				this.data('settings', settings);
				$(this).jstree('set_theme', name, url);
			} else {
				$(this).jstree('set_theme', 'rup-default', this.data('settings').actualThemeUrl);
			}
		},
		show_dots: function show_dots() {
			$(this).jstree('show_dots');
		},
		hide_dots: function hide_dots() {
			$(this).jstree('hide_dots');
		},
		toggle_dots: function toggle_dots() {
			$(this).jstree('toggle_dots');
		},
		show_icons: function show_icons() {
			$(this).jstree('show_icons');
		},
		hide_icons: function hide_icons() {
			$(this).jstree('hide_icons');
		},
		toggle_icons: function toggle_icons() {
			$(this).jstree('toggle_icons');
		},

		/* Metodos publicos de la selección */
		save_selected: function save_selected() {
			$(this).jstree('save_selected');
		},
		reselect: function reselect() {
			$(this).jstree('reselect');
		},
		hover_node: function hover_node(node) {
			$(this).jstree('hover_node', node);
		},
		dehover_node: function dehover_node() {
			$(this).jstree('dehover_node');
		},
		select_node: function select_node(node, check, event) {
			$(this).jstree('select_node', node, check, event);
		},
		deselect_node: function deselect_node(node) {
			$(this).jstree('deselect_node', node);
		},
		toggle_select: function toggle_select(node) {
			$(this).jstree('toggle_select', node);
		},
		deselect_all: function deselect_all(context) {
			$(this).jstree('deselect_all', context);
		},
		get_selected: function get_selected(context) {
			return $(this).jstree('get_selected', context);
		},
		is_selected: function is_selected(node) {
			return $(this).jstree('is_selected', node);
		},

		/* Metodos publicos del hotkeys */
		enable_hotkeys: function enable_hotkeys() {
			$(this).jstree('enable_hotkeys');
		},
		disable_hotkeys: function disable_hotkeys() {
			$(this).jstree('disable_hotkeys');
		},

		/* Metodos  publicos del checkbox */
		change_state: function change_state(node, uncheck) {
			$(this).jstree('change_state', node, uncheck);
		},
		check_node: function check_node(node) {
			$(this).jstree('check_node', node);
		},
		uncheck_node: function uncheck_node(node) {
			$(this).jstree('uncheck_node', node);
		},
		check_all: function check_all() {
			$(this).jstree('check_all');
		},
		uncheck_all: function uncheck_all() {
			$(this).jstree('uncheck_all');
		},
		is_checked: function is_checked(node) {
			return $(this).jstree('is_checked', node);
		},
		get_checked: function get_checked(context, get_all) {
			return $(this).jstree('get_checked', context, get_all);
		},
		get_unchecked: function get_unchecked(context, get_all) {
			return $(this).jstree('is_checked', context, get_all);
		},
		show_checkboxes: function show_checkboxes() {
			$(this).jstree('show_checkboxes');
		},
		hide_checkboxes: function hide_checkboxes() {
			$(this).jstree('hide_checkboxes');
		},

		/* Metodos  publicos del crrm */
		rename: function rename(node) {
			$(this).jstree('rename', node);
		},
		create: function create(node, position, js, callback, skip_rename) {
			return $(this).jstree('create', node, position, js, callback, skip_rename);
		},
		remove: function remove(node) {
			$(this).jstree('remove', node);
		},
		cut: function cut(node) {
			$(this).jstree('cut', node);
		},
		copy: function copy(node) {
			$(this).jstree('copy', node);
		},
		paste: function paste(node) {
			$(this).jstree('paste', node);
		},

		/* Metodos publicos del contextmenu */
		show_contextmenu: function show_contextmenu(node, x, y) {
			$(this).jstree('show_contextmenu', node, x, y);
		},

		/* Metodos publicos de la especificación de types */
		set_type: function set_type(type, node) {
			$(this).jstree('set_type', type, node);
		}
	});

	//********************************
	// DEFINICIÓN DE MÉTODOS PRIVADOS
	//********************************

	jQuery.fn.rup_tree('extend', {
		_init: function _init(args) {
			if (args.length > 1) {
				jQuery.rup.errorGestor(jQuery.rup.i18n.base.rup_global.initError + jQuery(this).attr('id'));
			} else {
				//Se recogen y cruzan las paremetrizaciones del objeto
				if (args.length > 0) {
					if (args[0].select) {
						args[0].ui = args[0].select;
						delete args[0].select;
					}
					if (args[0].jQueryUIStyles) {
						args[0].themeroller = args[0].jQueryUIStyles;
						delete args[0].jQueryUIStyles;
					}
				}

				var settings = jQuery.extend(true, {}, jQuery.fn.rup_tree.defaults, args[0]),
				    self = this[0],
				    selectorSelf = this;

				// Se guarda la referencia al $self
				settings.$self = $(this);
				settings.$self.attr('ruptype', 'tree');

				//validacion de carga por defecto
				if (settings.ui === undefined || settings.ui.enable !== false) {
					settings.plugins[settings.plugins.length] = 'ui';
				}

				if (settings.crrm === undefined || settings.crrm.enable !== false) {
					settings.plugins[settings.plugins.length] = 'crrm';

					//Se añaden los evento para gestionar el objeto cortado
					selectorSelf.bind('cut.jstree', $.proxy(function (event, eventArgs) {
						$(this).find('.rup_tree_cutNode.ui-state-disabled').removeClass('rup_tree_cutNode ui-state-disabled');
						eventArgs.args[0].children('a').addClass('rup_tree_cutNode ui-state-disabled');
					}, this));
					selectorSelf.bind('copy.jstree', $.proxy(function (event, eventArgs) {
						$(this).find('.rup_tree_cutNode.ui-state-disabled').removeClass('rup_tree_cutNode ui-state-disabled');
					}, this));
					selectorSelf.bind('paste.jstree', $.proxy(function (event, eventArgs) {
						$(this).find('.rup_tree_cutNode.ui-state-disabled').removeClass('rup_tree_cutNode ui-state-disabled');
					}, this));
				}

				if (settings.hotkeys === undefined || settings.hotkeys.enable !== false) {
					settings.plugins[settings.plugins.length] = 'hotkeys';

					if (settings.crrm === undefined || settings.crrm.enable !== false) {
						jQuery.jstree.defaults.hotkeys['esc'] = $.proxy(function (event) {
							if (event.target.tagName === 'BODY') {
								$(this).jstree('cleanCut');
								$(this).find('.rup_tree_cutNode.ui-state-disabled').removeClass('rup_tree_cutNode ui-state-disabled');
							}
						}, this);
					}
				}

				//Gestión de los evento para su posterior carga en el orden correcto
				selectorSelf._eventRecollector(settings, selectorSelf);

				//Se tapa la creación del arbol para evitar visualizaciones inapropiadas
				//Se recomienda que el componente, inicialmente, sea invisible. Para ello se dispone del estilo rup_tree
				selectorSelf.addClass('rup_tree');

				//Se determina, a partir de la configuración, el tipo de origen de datos utilizado
				if (settings.xml_data !== undefined) {
					settings.plugins[settings.plugins.length] = 'xml_data';
				} else if (settings.json_data !== undefined) {
					settings.plugins[settings.plugins.length] = 'json_data';
				} else {
					settings.plugins[settings.plugins.length] = 'html_data';
				}

				//Se activa y configura, si fuera necesario, el modulo del menu contextual
				if (settings.contextmenu !== undefined && settings.contextmenu.enable === true) {
					settings.plugins[settings.plugins.length] = 'contextmenu';
				} else {
					delete settings.contextmenu;
				}

				//Se activa, si fuera necesario, el modulo de ordenación
				if (settings.sort !== undefined) {
					if (settings.sort.enable === true) {
						settings.plugins[settings.plugins.length] = 'sort';
						if (settings.sort.sortFunction !== undefined) {
							settings.sort = settings.sort.sortFunction;
						} else {
							delete settings.sort;
						}
					} else {
						delete settings.sort;
					}
				}

				//Se activa, si fuera necesario, el modulo checkbox
				if (settings.checkbox !== undefined && settings.checkbox.enable === true) {
					settings.plugins[settings.plugins.length] = 'checkbox';
					delete settings.checkbox.enable;
				} else {
					delete settings.checkbox;
				}

				//Si fuera necesario, se activa el plugin wholerow (fila entera)
				if (settings.wholerow !== undefined && settings.wholerow === true) {
					settings.plugins[settings.plugins.length] = 'wholerow';
				}

				//Si fuera necesario, se activa el plugin unique
				if (settings.unique !== undefined && settings.unique.enable === true) {
					settings.plugins[settings.plugins.length] = 'unique';
					delete settings.unique.enable;
				} else {
					delete settings.unique;
				}

				//Si fuera necesario, se activa el plugin types
				if (settings.types !== undefined) {
					settings.plugins[settings.plugins.length] = 'types';

					//Se ajusta el jsTree a la convivencia con portales
					if ($.rup_utils.aplicatioInPortal()) {
						this.get_container().bind('loaded.jstree', $.proxy(function () {
							$(this).jstree('types_portal_css');
						}, this));
					}
				}

				//Si fuera necesario, se activa el plugin Drag and Drop
				if (settings.dnd !== undefined && settings.dnd.enable === true) {
					settings.plugins[settings.plugins.length] = 'dnd';
					delete settings.dnd.enable;
				} else {
					delete settings.dnd;
				}

				//Se valora la gestión de estilos. El plugin de themeRoller (estilos jQueryUI) siempre debe ser el ultimo y es excluyente al plugin themes
				if (settings.themeroller !== undefined) {
					if (settings.themeroller.enable === true) {
						settings.plugins[settings.plugins.length] = 'themeroller';
						delete settings.themeroller.enable;
					} else {
						settings.plugins[settings.plugins.length] = 'themes';
						delete settings.themeroller;
					}
				} else {
					settings.plugins[settings.plugins.length] = 'themes';
				}

				//Se almacenan los settings en el data del objeto
				selectorSelf.data('settings', settings);

				//Se crea el árbol
				selectorSelf.jstree(settings);

				//Evento de inicializacion
				selectorSelf.bind('loaded.jstree', $.proxy(function () {
					//Una vez creado, se libera la visualización del componente
					this.removeClass('rup_tree');
				}, this));

				//Se ajustan los estilos por defecto
				if (settings.themeroller === undefined && !settings.themes.theme) {
					selectorSelf.addClass('jstree-rup-default');
					$(this).jstree('set_theme_data', 'rup-default');
				}

				//Se configura, si fuera necesario, el modulo del menu contextual
				if (settings.contextmenu !== undefined && settings.contextmenu.enable === true) {
					delete settings.contextmenu.enable;
					if (settings.contextmenu.defaultOptions !== undefined) {
						var contextmenuItems = this.jstree('get_settings').contextmenu.items;
						var defaultOptions = settings.contextmenu.defaultOptions;
						for (option in defaultOptions) {
							if (defaultOptions[option] === false) {
								contextmenuItems[option] = null;
							} else if (option === 'ccp') {
								var ccpOptions = defaultOptions.ccp;
								for (ccpOption in ccpOptions) {
									if (ccpOptions[ccpOption] === false) {
										contextmenuItems.ccp.submenu[ccpOption] = null;
									}
								}
							}
						}
						$(this).jstree('set_contextmenu_items', contextmenuItems);
						delete settings.contextmenu.defaultOptions;
					}
				} else {
					delete settings.contextmenu;
				}

				/* REVISION (encuentrame) */

				//Se sobreescribe uno de los eventos para hacer reaparecer, una vez creado, el accordion
				//				createUserEvent = settings.create;
				//				settings.create = function (event, ui) {
				//					if (createUserEvent !== undefined) {
				//						if (createUserEvent(event, ui) === false) {
				//							return false;
				//						}
				//					}
				//Comportamiento por defecto del evento
				//					create_default(event, ui);
				//				};

				//				function create_default(event, ui){
				//					$(event.target).addClass("rup_accordion_create");
				//				}

				//Se comprueba la corrección del html con el que se creara el accordion
				//				if(settings.validation){
				//					if(parseInt(elementsNum) !== elementsNum){
				//						$.rup.errorGestor($.rup.i18n.base.rup_accordion.strucPairError);
				//						return false;
				//					} else {
				//						elements.each(function(index,object){
				//							if ((parseInt(index/2) === index/2) && ($(object).find("a").length === 0)){
				//								$.rup.errorGestor($.rup.i18n.base.rup_accordion.headFormatError);
				//								return false;
				//							}
				//						});
				//					}
				//				}

				//Se invoca la creacion del accordion
				//				this.accordion(settings);
			}
		},
		/* revisar funcionamiento */
		_eventRecollector: function _eventRecollector(settings, selectorSelf) {

			var aux;

			for (var i in settings) {
				aux = i.split('_event');
				if (aux.length > 1) {
					this.bind(aux[0] + '.jstree', settings[i]);
				}
			}
		}
	});

	//*******************************************************
	// DEFINICIÓN DE LA CONFIGURACION POR DEFECTO DEL PATRON
	//*******************************************************


	/**
     * @description Propiedades de configuración del componente.
     * @name options
     * @see Para mas información consulte la documentación acerca de las opciones de configuración del plugin {@link https://old.jstree.com/documentation|jstree}.
     * @property {function} [getValue] -Permite especificar una función de callback para implementar el dato a emplear a la hora de ejecutar los métodos getRupValue y setRupValue.
     * @property {boolean} [readAsString=false] - Permite asignar elementos seleccionados indicados mediante un string de identificadores separados por comas.
     * @property {boolean} [submitAsJSON=false] - Determina que los elementos seleccionados se enviarán representados mediante un objeto JSON.
     * @property {boolean} [submitAsString=false] - Determina que los elementos seleccionados se enviarán representados mediante un string de identificadores separados por comas.
     */
	jQuery.fn.rup_tree.defaults = {
		'plugins': ['rup_extend'],
		'actualThemeUrl': '',

		//Pruebas de configuracion (todos los parametros)
		//CORE
		//		"core" : {
		//			"html_titles" : false,
		//			"animation" : 500,
		//			"initially_open" : [],
		//			"open_parents" : true,
		//			"initially_load" : [],
		//			"load_open" : false,
		//			"notify_plugins" : true,
		//			"rtl" : false,
		//			"strings" : { loading : "Loading ...", new_node : "New node" }
		//		},
		//THEMES PLUGIN
		'core': {
			'strings': {
				'loading': $.rup.i18nParse($.rup.i18n.base, 'rup_tree.loading'),
				'new_node': $.rup.i18nParse($.rup.i18n.base, 'rup_tree.new_node')
			},
			'getValue': undefined,
			'submitAsJSON': false,
			'submitAsString': false,
			'readAsString': false
		},
		'themes': {
			'theme': ''
		},
		'checkbox': {
			'override_ui': true
		},
		'crrm': {
			'input_width_limit': 200
		}
	};

	//*************************************************
	// AJUSTES GENERALES DEL FUNCIONAMIENTO DEL PÁTRON
	//*************************************************


	//Gestion de los literales del menu contextual
	jQuery.jstree.defaults.contextmenu.items.create.label = $.rup.i18nParse($.rup.i18n.base, 'rup_tree.create');
	jQuery.jstree.defaults.contextmenu.items.rename.label = $.rup.i18nParse($.rup.i18n.base, 'rup_tree.rename');
	jQuery.jstree.defaults.contextmenu.items.remove.label = $.rup.i18nParse($.rup.i18n.base, 'rup_tree.remove');
	jQuery.jstree.defaults.contextmenu.items.ccp.label = $.rup.i18nParse($.rup.i18n.base, 'rup_tree.ccp.label');
	jQuery.jstree.defaults.contextmenu.items.ccp.submenu.cut.label = $.rup.i18nParse($.rup.i18n.base, 'rup_tree.ccp.cut');
	jQuery.jstree.defaults.contextmenu.items.ccp.submenu.copy.label = $.rup.i18nParse($.rup.i18n.base, 'rup_tree.ccp.copy');
	jQuery.jstree.defaults.contextmenu.items.ccp.submenu.paste.label = $.rup.i18nParse($.rup.i18n.base, 'rup_tree.ccp.paste');

	//Se extienden las funcionalidades del jstree para ajustar prestaciones, de manejo de teclado, que funcionaban erráticamente
	$.compatibility = {
		hotkeys: {
			'ctrl+space': function ctrlSpace(event) {
				delete event.target;
				event.type = 'click';
				if (this.data.ui.hovered) {
					this.data.ui.hovered.children('a:eq(0)').trigger(event);
				}
				return false;
			},
			'shift+space': function shiftSpace(event) {
				delete event.target;
				event.type = 'click';
				if (this.data.ui.hovered) {
					this.data.ui.hovered.children('a:eq(0)').trigger(event);
				}
				return false;
			}
		},
		rup_extend: {
			_fn: {
				'cleanCut': function cleanCut() {
					this.data.crrm.ct_nodes = false;
				},
				'set_contextmenu_items': function set_contextmenu_items(s) {
					var settings = this.get_settings();
					settings.contextmenu.items = s;
					this._set_settings(settings);
				},
				'set_theme_data': function set_theme_data(themeName) {
					this.data.themes['theme'] = themeName;
				},
				'types_portal_css': function types_portal_css() {
					var s = this._get_settings().types;
					var types = s.types,
					    attr = s.type_attr,
					    icons_css = '',
					    _this = this;
					$.each(types, function (i, tp) {
						$.each(tp, function (k, v) {
							if (!/^(max_depth|max_children|icon|valid_children)$/.test(k)) {
								_this.data.types.attach_to.push(k);
							}
						});
						if (!tp.icon) {
							return true;
						}
						if (tp.icon.image || tp.icon.position) {
							icons_css += 'div.r01gContainer ';
							if (i == 'default') {
								icons_css += '.jstree-' + _this.get_index() + ' a > .jstree-icon { ';
							} else {
								icons_css += '.jstree-' + _this.get_index() + ' li[' + attr + '="' + i + '"] > a > .jstree-icon { ';
							}
							if (tp.icon.image) {
								icons_css += ' background-image:url(' + tp.icon.image + '); ';
							}
							if (tp.icon.position) {
								icons_css += ' background-position:' + tp.icon.position + '; ';
							} else {
								icons_css += ' background-position:0 0; ';
							}
							icons_css += '} ';
						}
					});

					var jstreeTypesStylesheet = $('#jstree-types-stylesheet');

					if (jstreeTypesStylesheet !== undefined) {
						jstreeTypesStylesheet.remove();
					}

					if (icons_css !== '') {
						$.vakata.css.add_sheet({
							'str': icons_css,
							title: 'jstree-porta-types'
						});
					}
				}
			}
		}
	};
	jQuery.extend(jQuery.jstree.defaults.hotkeys, $.compatibility.hotkeys);
	$.jstree.plugin('rup_extend', $.compatibility.rup_extend);
});
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))

/***/ }),
/* 169 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function(jQuery) {var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*!
 * Copyright 2016 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 */

/**
 * Permite al usuario seleccionar uno o varios archivos de su equipo y subirlos a la aplicación.
 *
 * @summary Componente RUP Upload.
 * @module rup_upload
 * @see El componente está basado en el plugin {@link https://blueimp.github.io/jQuery-File-Upload/|jQuery File Upload}. Para mas información acerca de las funcionalidades y opciones de configuración pinche {@link https://blueimp.github.io/jQuery-File-Upload/|aquí}.
 * @example
 * $("#idUpload").rup_upload({});
 */

/*global define */
/*global jQuery */

(function (factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(2),
		//'jquery.fileupload/jquery.fileupload.js',
		//'jquery.fileupload/jquery.fileupload-ui.js',
		//'jquery.fileupload/jquery.fileupload-jquery-ui.js',
		//'jquery.fileupload/jquery.fileupload-process.js',
		//'jquery.fileupload/jquery.fileupload-validate.js',
		//'jquery.fileupload/jquery.fileupload-image.js',
		//'jquery.fileupload/jquery.fileupload-audio.js',
		//'jquery.fileupload/jquery.fileupload-process.js',
		//'jquery.fileupload/jquery.fileupload-video.js',
		__webpack_require__(197),

		// 'jquery.fileupload/jquery.fileupload.js'

		__webpack_require__(216)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		factory(jQuery);
	}
})(function ($) {

	$.widget('blueimp.fileupload', $.blueimp.fileupload, {
		options: {
			errorMessages: {
				maxFileSize: $.rup.i18nParse($.rup.i18n.base, 'rup_upload.maxFileSizeError'),
				minFileSize: $.rup.i18nParse($.rup.i18n.base, 'rup_upload.minFileSizeError'),
				acceptFileTypes: $.rup.i18nParse($.rup.i18n.base, 'rup_upload.acceptFileTypesError'),
				maxNumberOfFiles: $.rup.i18nParse($.rup.i18n.base, 'rup_upload.maxNumberOfFilesError')
			},
			// processdone: function (e, data) {
			// 	return $.proxy(data.self._ADAPTER.processdone, this)(e, data);
			//
			// },

			getFilesFromResponse: function getFilesFromResponse(data) {
				if (data.result && $.isArray(data.result)) {
					// return data.result;
					return data.result.map(function (elem, i) {
						return $.extend(elem, {
							deleteType: elem.delete_type,
							deleteUrl: elem.delete_url
						});
					});
				}
				return [];
			}
		},

		// _renderUpload: function (files) {
		//       var that = this,
		//           options = this.options,
		//           tmpl = this._renderUploadTemplate(files),
		//           isValidated = this._validate(files);
		//       if (!(tmpl instanceof $)) {
		//           return $();
		//       }
		//       var settings = $.data(this.element[0], "settings");
		//
		//       tmpl.css('display', 'none');
		//       // .slice(1).remove().end().first() removes all but the first
		//       // element and selects only the first for the jQuery collection:
		//       tmpl.find('.progress div').slice(
		//           isValidated ? 1 : 0
		//       ).remove().end().first()
		//           .progressbar();
		//       tmpl.find('.start button').slice(
		//           this.options.autoUpload || !isValidated ? 0 : 1
		//       ).remove().end().first()
		//           .button({
		//               text: true,
		//               icons: {primary: 'ui-icon-circle-arrow-e'}
		//           });
		//       var cancelButton = tmpl.find('.cancel button').slice(1).remove().end().first()
		//           .button({
		//               text: true,
		//               icons: {primary: 'ui-icon-cancel'}
		//           });
		//
		//       if(settings.submitInForm){
		//         cancelButton.bind("click",function(event){
		//         	var newFileInput;
		//             event.preventDefault();
		//             that.options.fileInput.attr("value","");
		//             newFileInput=that.options.fileInput.clone(true).attr("value","").insertAfter(that.options.fileInput);
		//             that.options.fileInput.remove();
		//             that.options.fileInput=newFileInput;
		//
		//         });
		//       }
		//
		//       tmpl.find('.preview').each(function (index, node) {
		//           that._loadImage(
		//               files[index],
		//               function (img) {
		//                   $(img).hide().appendTo(node).fadeIn();
		//               },
		//               {
		//                   maxWidth: options.previewMaxWidth,
		//                   maxHeight: options.previewMaxHeight,
		//                   fileTypes: options.previewFileTypes,
		//                   canvas: options.previewAsCanvas
		//               }
		//           );
		//       });
		//       return tmpl;
		//   },
		// _renderDownload: function (files) {
		//     var tmpl = this._renderDownloadTemplate(files);
		//     if (!(tmpl instanceof $)) {
		//         return $();
		//     }
		//     tmpl.css('display', 'none');
		//     tmpl.find('.delete button').button({
		//         text: true,
		//         icons: {primary: 'ui-icon-trash'}
		//     });
		//     tmpl.find('a').each(this._enableDragToDesktop);
		//     return tmpl;
		// },
		_renderUploadTemplate: function _renderUploadTemplate(files) {
			var that = this,
			    rows = $();

			var settings = $.data(this.element[0], 'settings');

			$.each(files, function (index, file) {
				// file = that._uploadTemplateHelper(file);
				var row = $('<tr class="template-upload"><td>' + '<div class="formulario_columna_cnt">' + '<span class="izq_float file_icon">&nbsp;</span>' + '<div class="izq_float name"><b></b></div>' + '<div class="formulario_columna_cnt">' + '<div class="izq_float type"></div>' + '<div class="izq_float size"></div>' + (settings.submitInForm ? '<div class="izq_float cancel" style><button>' + $.rup.i18nParse($.rup.i18n.base, 'rup_upload.cancelUpload') + '</button></div>' : '') + '</div>' + (!settings.submitInForm ? '<div class="formulario_columna_cnt">' + (file.error ? '<div class="izq_float error" ></div>' : '<button>' + '<div class="izq_float progress"><div></div></div>' + '<div class="izq_float start fileupload-buttonbar ui-button">' + $.rup.i18nParse($.rup.i18n.base, 'rup_upload.startUpload') + '</button></div>') + '<div class="izq_float cancel"><button>' + $.rup.i18nParse($.rup.i18n.base, 'rup_upload.cancelUpload') + '</button></div>' + '</div>' : '<div class="izq_float start fileupload-buttonbar ui-button" style="display:none"><button>' + $.rup.i18nParse($.rup.i18n.base, 'rup_upload.startUpload') + '</button></div>') + '</td></tr>');
				row.find('.name b').text(file.name);
				row.find('.size').text(file.sizef);
				row.find('.type').text(file.type);
				if (file.error) {
					row.addClass('ui-state-error');
					row.find('.error').text(that.options.errorMessages[file.error] || file.error);
				}

				rows = rows.add(row);
			});
			return rows;
		},
		_renderDownloadTemplate: function _renderDownloadTemplate(files) {
			var that = this,
			    rows = $();
			$.each(files, function (index, file) {
				// file = that._downloadTemplateHelper(file);
				var row = $('<tr class="template-download"><td>' + (file.error ? '<td class="file_icon"></td>' + '<td class="name"></td>' + '<td class="size"></td>' + '<td class="error" colspan="2"></td>' : '<div class="formulario_columna_cnt">' + '<span class="izq_float file_icon">&nbsp;</span>' + '<div class="izq_float name"><a></a></div>' + '</div>' + '<div class="formulario_columna_cnt">' + '<div class="izq_float type"></div>' + '<div class="izq_float size"></div>' + '</div>' + '<div class="formulario_columna_cnt">' + '<a><div class="izq_float">' + '<div class="file_download" >' + '<span class="file_download_icon">&nbsp;</span>' + '<span class="file_download_text">' + $.rup.i18nParse($.rup.i18n.base, 'rup_upload.openUploaded') + '</span></div>' + '</div></a>' + '<div class="izq_float delete"><button>' + $.rup.i18nParse($.rup.i18n.base, 'rup_upload.deleteUploaded') + '</button></div>' + '</div>') + '</td></tr>');

				row.find('.size').text(file.sizef);
				row.find('.type').text(file.type);
				if (file.error) {
					row.find('.name').text(file.name);
					row.addClass('ui-state-error');
					row.find('.error').text(that.options.errorMessages[file.error] || file.error);
				} else {
					row.find('.name a').text(file.name);
					if (file.thumbnail_url) {
						row.find('.preview').append('<a><img></a>').find('img').prop('src', file.thumbnail_url);
						row.find('a').prop('target', '_blank');
					}
					row.find('a').prop('href', $.rup_utils.setNoPortalParam(file.url));
					row.find('.delete button').attr('data-type', file.delete_type).attr('data-url', $.rup_utils.setNoPortalParam(file.delete_url));
				}
				rows = rows.add(row);
			});
			return rows;
		},
		_initFileUploadButtonBar: function _initFileUploadButtonBar() {
			var fileUploadButtonBar = this.element.find('.fileupload-buttonbar'),
			    filesList = this.element.find('.files'),
			    ns = this.options.namespace;
			fileUploadButtonBar.find('.start button').button({
				icons: {
					primary: 'ui-icon-circle-arrow-e'
				}
			}).bind('click.' + ns, function (e) {
				e.preventDefault();
				filesList.find('.start button').click();
			});
			fileUploadButtonBar.find('.cancel').button({
				icons: {
					primary: 'ui-icon-cancel'
				}
			}).bind('click.' + ns, function (e) {
				e.preventDefault();
				filesList.find('.cancel button').click();
			});
			fileUploadButtonBar.find('.delete').button({
				icons: {
					primary: 'ui-icon-trash'
				}
			}).bind('click.' + ns, function (e) {
				e.preventDefault();
				//	                filesList.find('.delete input:checked')
				//	                    .siblings('button').click();
				filesList.find('.delete button').click();
			});
			fileUploadButtonBar.find('.toggle').bind('change.' + ns, function (e) {
				filesList.find('.delete input').prop('checked', $(this).is(':checked'));
			});
		},
		_getAJAXSettings: function _getAJAXSettings(data) {
			var options = $.extend({}, this.options, data);
			this._initFormSettings(options);
			this._initDataSettings(options);
			return options;
		}
		//	    ,_initProgressListener: function (options) {
		//            var that = this,
		//                xhr = options.xhr ? options.xhr() : $.ajaxSettings.xhr();
		//            // Accesss to the native XHR object is required to add event listeners
		//            // for the upload progress event:
		//                if (options.pif ===null && xhr.upload) {
		//    				//-- fix start --
		//    				$( xhr.upload ).bind( "progress", function (e) {
		//    				that._onProgress(e, options);
		//    				});
		//    				options.xhr = function () {
		//                        return xhr;
		//                    };
		//    				//-- fix end --
		//                }
		//        }
		//	    destroy: function (e, data) {
		//            var that = $(this).data('fileupload');
		//            if (data.url) {
		//                $.rup_ajax(data)
		//                    .success(function () {
		//                        that._adjustMaxNumberOfFiles(1);
		//                        $(this).fadeOut(function () {
		//                            $(this).remove();
		//                        });
		//                    });
		//            } else {
		//                that._adjustMaxNumberOfFiles(1);
		//                data.context.fadeOut(function () {
		//                    $(this).remove();
		//                });
		//            }
		//        }

	});

	//*********************************************
	// ESPECIFICACÍON DE LOS TIPOS BASE DEL PATRÓN
	//*********************************************

	//*****************************************************************************************************************
	// DEFINICIÓN BASE DEL PATRÓN (definición de la variable privada que contendrá los métodos y la función de jQuery)
	//*****************************************************************************************************************


	var rup_upload = {};

	//Se configura el arranque de UDA para que alberge el nuevo patrón
	$.extend($.rup.iniRup, $.rup.rupSelectorObjectConstructor('rup_upload', rup_upload));

	//********************************
	// DEFINICIÓN DE MÉTODOS PÚBLICOS
	//********************************

	$.fn.rup_upload('extend', {
		option: function option(args) {
			$(this).fileupload('option', args);
		},
		/**
         * Elimina los objetos jQuery asociados al elemento identificado por el selector, durante el proceso de creación del componente upload
         * @function
         * @name destroy
         * @example
         * $(selector).rup_combo("destroy");
         */
		destroy: function destroy() {
			$(this).fileupload('destroy');
		},
		/**
         *
         * @function Habilita el componente upload
         * @name enable
         * @example
         * $(selector).rup_upload("enable");
         */
		enable: function enable() {
			$(this).fileupload('enable');
		},
		/**
         * Deshabilita el componente upload
         * @function
         * @name disable
         * @example
         * $(selector).rup_upload("disable");
         */
		disable: function disable() {
			$(this).fileupload('disable');
		},
		/**
         * Permite asociar una función que se ejecutará cuando se añada un fichero mediante el componente. muestre el desplegable del combo
         * @function
         * @name add
         * @listens add
         */
		add: function add(data) {
			$(this).fileupload('add', data);
		},
		send: function send(data) {
			$(this).fileupload('send', data);
		}
	});

	//********************************
	// DEFINICIÓN DE MÉTODOS PRIVADOS
	//********************************


	function fileuploadstart() {
		var widget = $(this),
		    progressElement = $('#fileupload-progressbar').fadeIn(),
		    interval = 500,
		    total = 0,
		    loaded = 0,
		    loadedBefore = 0,
		    progressTimer,
		    progressHandler = function progressHandler(e, data) {
			loaded = data.loaded;
			total = data.total;
		},
		    stopHandler = function stopHandler() {
			widget.unbind('fileuploadprogressall', progressHandler).unbind('fileuploadstop', stopHandler);
			window.clearInterval(progressTimer);
			progressElement.fadeOut(function () {
				progressElement.html('');
			});
		},
		    formatTime = function formatTime(seconds) {
			var date = new Date(seconds * 1000);
			return ('0' + date.getUTCHours()).slice(-2) + ':' + ('0' + date.getUTCMinutes()).slice(-2) + ':' + ('0' + date.getUTCSeconds()).slice(-2);
		},
		    formatBytes = function formatBytes(bytes) {
			if (bytes >= 1000000000) {
				return (bytes / 1000000000).toFixed(2) + ' GB';
			}
			if (bytes >= 1000000) {
				return (bytes / 1000000).toFixed(2) + ' MB';
			}
			if (bytes >= 1000) {
				return (bytes / 1000).toFixed(2) + ' KB';
			}
			return bytes + ' B';
		},
		    formatPercentage = function formatPercentage(floatValue) {
			return (floatValue * 100).toFixed(2) + ' %';
		},
		    updateProgressElement = function updateProgressElement(loaded, total, bps) {
			progressElement.html(formatBytes(bps) + 'ps | ' + formatTime((total - loaded) / bps) + ' | ' + formatPercentage(loaded / total) + ' | ' + formatBytes(loaded) + ' / ' + formatBytes(total));
		},
		    intervalHandler = function intervalHandler() {
			var diff = loaded - loadedBefore;
			if (!diff) {
				return;
			}
			loadedBefore = loaded;
			updateProgressElement(loaded, total, diff * (1000 / interval));
		};
		widget.bind('fileuploadprogressall', progressHandler).bind('fileuploadstop', stopHandler);
		progressTimer = window.setInterval(intervalHandler, interval);
	}

	$.fn.rup_upload('extend', {
		_init: function _init(args) {

			var settings = $.extend({}, $.fn.rup_upload.defaults, args[0]),
			    upload = this;

			upload._ADAPTER = $.rup.adapter[settings.adapter];
			settings.self = upload;

			// Se configura el uso del PIF
			if (settings.pif !== null) {
				var url = '',

				//						n38UidSesionCookie = $.rup_utils.readCookie("n38UidSesion"),
				//						n38DominioUidCookie = $.rup_utils.readCookie("n38DominioUid"),
				//						n38UidSesionGlobal = $.rup_utils.readCookie("n38UidSesionGlobal"),
				//						n38UidSistemasXLNetS = $.rup_utils.readCookie("n38UidSistemasXLNetS"),
				pifSettings = jQuery.extend(true, $.fn.rup_upload.pif.defaults, settings.pif);

				//					if (pifSettings.base_url===undefined){
				//						alert("RUP_UPLOAD - No se ha especificado el valor del parámetro base_url para el uso del PIF.");
				//						return -1;
				//					}
				if (pifSettings.userFolder !== true && pifSettings.folderPath === undefined) {
					alert('RUP_UPLOAD - No se ha especificado el valor del parámetro folderPath para el uso del PIF.');
					return -1;
				}

				jQuery.extend(true, settings, {
					formData: {
						base_url: settings.url,
						hadoop_folder_path: pifSettings.folderPath,
						hadoop_preserve_name: pifSettings.preserveName,
						y31_ttl: pifSettings.fileTtl,
						securityToken: pifSettings.securityToken
					}
				});

				//					url += pifSettings.base_url;  // Url base del PIF
				//					url += pifSettings._JANO_PUT_SERVLET; // Servlet PUT
				//					url += "/"+n38UidSesionCookie; // Cookie XLNets n38UidSesionCookie
				//					url += "/"+n38DominioUidCookie; // Cookie XLNets n38DominioUidCookie
				//					url += "/"+n38UidSesionGlobal; // Cookie XLNets n38UidSesionGlobal
				//					url += "/"+n38UidSistemasXLNetS; // Cookie XLNets n38UidSistemasXLNetS

				// Se añaden los parámetros de configuración del PIF a la url

				//					url +="?hadoop_folder_path="+pifSettings.folderPath; // Parámetro folderPath
				//					url +="&hadoop_preserve_name="+pifSettings.preserveName; // Parámetro preserveName
				//					url +="&y31_ttl="+pifSettings.fileTtl; // Parámetro fileTtl


				// Configruamos la url final
				//					settings.url = url;

				//					settings.xhr = function(){
				//
				//					};
			}

			$.data(this[0], 'settings', settings);

			$(this).fileupload(settings);

			// $(this).data('blueimp-fileupload')._formatFileSize = function(size){
			//
			// 	function formatBytes (bytes) {
			// 		if (bytes >= 1000000000) {
			// 			return (bytes / 1000000000).toFixed(2) + ' GB';
			// 		}
			// 		if (bytes >= 1000000) {
			// 			return (bytes / 1000000).toFixed(2) + ' MB';
			// 		}
			// 		if (bytes >= 1000) {
			// 			return (bytes / 1000).toFixed(2) + ' KB';
			// 		}
			// 		return bytes + ' B';
			// 	}
			//
			// 	return formatBytes(size);
			// };

			if (settings.submitInForm) {
				$(this).rup_upload('option', {
					singleFileUploads: false,
					maxNumberOfFiles: 1,
					replaceFileInput: false
				});
			}

			$(this).on({ fileuploadadd: function fileuploadadd(e, data) {
					if (settings.submitInForm) {
						$(this).find('.template-upload').hide();
						$(this).find('.template-upload .cancel button').unbind('click');
						$(this).find('.template-upload .cancel button').click();
					}
				},
				fileuploadsend: function fileuploadsend(e, data) {
					data.url = $.rup_utils.setNoPortalParam(data.url);
					if (!$.rup.browser.xhrFileUploadSupport || settings.forceIframeTransport === true) {
						data.url = data.url + (data.url.match('\\?') === null ? '?' : '&') + '_emulate_iframe_http_status=true';
					}
				},
				fileuploadprocessfail: function fileuploadprocessfail(e, data) {
					data.context.addClass('error');
				}

			});
		},
		_private: function _private(settings) {}
	});

	//*******************************************************
	// DEFINICIÓN DE LA CONFIGURACION POR DEFECTO DEL PATRON
	//*******************************************************

	$.fn.rup_upload.defaults = {
		// label:null,
		// fileInput:null,
		adapter: 'upload_bootstrap',
		submitInForm: false,
		submitFormButton: undefined,
		pif: null,
		//filesContainer: '.files',
		uploadTemplateId: false,
		downloadTemplateId: false,
		uploadTemplate: function uploadTemplate(o) {
			return $.proxy(o.options.self._ADAPTER.uploadTemplate, this)(o);
		},
		downloadTemplate: function downloadTemplate(o) {
			return $.proxy(o.options.self._ADAPTER.downloadTemplate, this)(o);
		}
	};

	$.fn.rup_upload.pif = {};
	$.fn.rup_upload.pif.defaults = {
		fileTtl: 129600,
		preserveName: false,
		_JANO_PUT_SERVLET: '/y31ApiJSWAR/Y31JanoServicePutServlet',
		securityToken: 'app'
	};

	/**
    * @description Propiedades de configuración del componente.
    * @see Para mas información consulte la documentación acerca de las opciones de configuración del plugin {@link https://github.com/blueimp/jQuery-File-Upload/wiki/Options|jQuery File Upload}.
    *
    * @name options
    * @property {string} [namespace] - Se utiliza para asociar el capturador de eventos del dropZone y del fileInpurt. Por defecto toma el valor del widget (“fileupload”).
    * @property {jQuery} [dropZone=$(document)] - Indica el objeto jQuery que representa el área de dropZone. Para deshabilitar el soporte drag & drop se deberá indicar el valor null.
    * @property {jQuery} [fileInput] - Objeto jQuery sobre el cual se monitorizarán los eventos de cambio del mismo. En caso de no especificarse se tomarán los input de tipo file existentes dentro del objeto sobre el que se ha creado el componente upload. Para deshabilitar el capturador de eventos se deberá indicar el valor null.
    * @property {boolean} [replaceFileInput=true] - Determinar si el campo file es reemplazado por un nuevo objeto a partir de un clone.
    * @property {string} [paramName] - Indica el nombre del parámetro de la request mediante el cual se enviará la información del fichero. En caso de no especificarse, se tomará el valor de la propiedad name del campo file. En caso de no especificarse dicha propiedad se tomará el valor files[] por defecto.
    * @property {boolean} [singleFileUploads=true] - Especifica si la subida de ficheros se realizar de manera individual, es decir, si se realiza una petición XHR por cada uno de los ficheros que se deben de enviar.
    * @property {boolean} [limitMultiFileUploads=true] -Especifica el número de ficheros que pueden ser enviados en una única petición XHR.
    * @property {boolean} [sequentialUploads=false] - Especifica si el envío de los ficheros se realizan de manera secuencial en vez de manera simultánea.
    * @property {Integer} [limitConcurrentUploads] - Indica el número máximo de peticiones concurrentes para la
 subida de ficheros.
    * @property {boolean} [forceIframeTransport=false] - Determina si se debe forzar el uso de iframe al realizar la subida de ficheros. Esta opción puede ser útil en caso de subida de ficheros entre diferentes dominios.
    * @property {boolean} [multipart=true] - Indica si la subida de ficheros se realiza como multipart/form-data.
    * @property {boolean} [recalculateProgress=true] - Por defecto, los envíos de ficheros erróneos o cancelados son excluidos del cálculo del progreso global de subida de ficheros. Para evitar el recálculo del progreso global se deberá de especificar esta opción como false.
    * @property {object | object[] | function} [formData] - Información adicional que se desea enviar al realizarse la subida de ficheros. El parámetro acepta lo siguiente: <ul><li>Array de objetos con propiedades</li><li>Objeto simple</li><li>Función que retorna uno de los tipos de datos especificados anteriormente.</li></ul>
    */

	/***********/
	/* EVENTOS */
	/***********/

	/**
     * Permite asociar una función que se ejecutará cuando se añada un fichero mediante el componente.
     *
     * @event module:rup_upload#fileuploadadd
     * @property {Event} e - Objeto Event correspondiente al evento disparado.
     * @property {object} data - Objeto que contiene la información relativa a la subida de los ficheros.
     * @example
     * $("#fileupload").on("fileuploadadd", function (e, data) {
     * });
     */

	/**
     * Permite asociar una función que se ejecutará cuando se añada un fichero mediante el componente.
     *
     * @event module:rup_upload#fileuploadsubmit
     * @property {Event} e - Objeto Event correspondiente al evento disparado.
     * @property {object} data - Objeto que contiene la información relativa a la subida de los ficheros.
     * @return {boolean} - Si la función retorna false el envío no se realiza.
     * @example
     * $("#fileupload").on("fileuploadsubmit", function (e, data) {
     * });
     */

	/**
     * Permite asociar una función que se ejecutará al iniciarse el envío de cada fichero.
     *
     * @event module:rup_upload#fileuploadsend
     * @property {Event} e - Objeto Event correspondiente al evento disparado.
     * @property {object} data - Objeto que contiene la información relativa a la subida de los ficheros.
     * @return {boolean} - Si la función retorna false el envío no se realiza.
     * @example
     * $("#fileupload").on("fileuploadsend", function (e, data) {
     * });
     */

	/**
     * Permite asociar una función que se ejecutará al realizarse de manera satisfactoria el envío de los ficheros.
     *
     * @event module:rup_upload#fileuploaddone
     * @property {Event} e - Objeto Event correspondiente al evento disparado.
     * @property {object} data - Objeto que contiene la información relativa a la subida de los ficheros.
     * @example
     * $("#fileupload").on("fileuploaddone", function (e, data) {
     * });
     */

	/**
     * Permite asociar una función que se ejecutará al producirse un error en el envío de los ficheros o al abortarse el envío.
     *
     * @event module:rup_upload#fileuploadfail
     * @property {Event} e - Objeto Event correspondiente al evento disparado.
     * @property {object} data - Objeto que contiene la información relativa a la subida de los ficheros.
     * @example
     * $("#fileupload").on("fileuploadfail", function (e, data) {
     * });
     */

	/**
     * Permite asociar una función que se ejecutará al producirse un envío correcto, erróneo o se aborte.
     *
     * @event module:rup_upload#fileuploadalways
     * @property {Event} e - Objeto Event correspondiente al evento disparado.
     * @property {object} data - Objeto que contiene la información relativa a la subida de los ficheros.
     * @example
     * $("#fileupload").on("fileuploadalways", function (e, data) {
     * });
     */

	/**
     * Permite asociar una función que se ejecutará al producirse un evento relacionado con el indicador de progreso del envío de ficheros.
     *
     * @event module:rup_upload#fileuploadprogress
     * @property {Event} e - Objeto Event correspondiente al evento disparado.
     * @property {object} data - Objeto que contiene la información relativa a la subida de los ficheros.
     * @example
     * $("#fileupload").on("fileuploadprogress", function (e, data) {
     * });
     */

	/**
     * Permite asociar una función que se ejecutará al producirse un evento relacionado el indicador de progreso global de envío de ficheros.
     *
     * @event module:rup_upload#fileuploadprogressall
     * @property {Event} e - Objeto Event correspondiente al evento disparado.
     * @property {object} data - Objeto que contiene la información relativa a la subida de los ficheros.
     * @example
     * $("#fileupload").on("fileuploadprogressall", function (e, data) {
     * });
     */

	/**
     * Permite asociar una función que se ejecutará al inicio del envío de los ficheros.
     *
     * @event module:rup_upload#fileuploadstart
     * @property {Event} e - Objeto Event correspondiente al evento disparado.
     * @example
     * $("#fileupload").on("fileuploadstart", function (e) {
     * });
     */

	/**
     * Permite asociar una función que se ejecutará al detenerse el proceso de envío de ficheros.
     *
     * @event module:rup_upload#fileuploadstop
     * @property {Event} e - Objeto Event correspondiente al evento disparado.
     * @example
     * $("#fileupload").on("fileuploadstop", function (e) {
     * });
     */
});
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))

/***/ }),
/* 170 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function(jQuery) {var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*!
 * Copyright 2016 E.J.I.E., S.A.
 *
 * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
 * Solo podrá usarse esta obra si se respeta la Licencia.
 * Puede obtenerse una copia de la Licencia en
 *
 *      http://ec.europa.eu/idabc/eupl.html
 *
 * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
 * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
 * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
 * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
 * que establece la Licencia.
 */

/**
 * Permitir guiar al usuario paso a paso a través de un proceso realizando las tareas dentro de un orden señalado.
 *
 * @summary Componente RUP Wizard.
 * @module rup_wizard
 * @example
 * var properties = {};
 * $("#id_form").rup_wizard(properties)
 */

/*global define */
/*global jQuery */

(function (factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(2)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		factory(jQuery);
	}
})(function ($) {

	//****************************************************************************************************************
	// DEFINICIÓN BASE DEL PATRÓN (definición de la variable privada que contendrá los métodos y la función de jQuery)
	//****************************************************************************************************************


	var rup_wizard = {};

	//Se configura el arranque de UDA para que alberge el nuevo patrón
	$.extend($.rup.iniRup, $.rup.rupSelectorObjectConstructor('rup_wizard', rup_wizard));

	//*******************************
	// DEFINICIÓN DE MÉTODOS PÚBLICOS
	//*******************************
	$.fn.rup_wizard('extend', {
		/**
         * Selecciona el paso recibido como parámetro [0..n].
         *
         * @function step
         * @param {Integer} step - Identificador del paso que se desea seleccionar.
         * @example
         * $("#idForm").rup_wizard("step", 1);
         */
		step: function step(stepNumber) {

			//controlar si está deshabilitado
			if ($('#stepDesc' + stepNumber).hasClass('disabled')) {
				return false;
			}

			var currentId = $('#steps li.current').attr('id');

			//Gestionar cabeceras
			$('#steps li').removeClass('current');
			$('#stepDesc' + stepNumber).addClass('current');
			//Estilo flecha paso anterior
			$('#steps li').removeClass('visited');
			if (stepNumber != 0) {
				$('#stepDesc' + (stepNumber - 1)).addClass('visited');
			}

			//Gestionar capas
			$('#step' + currentId.substring(8)).hide();
			$('#step' + stepNumber).show();

			//Gestionar submitButton
			if (!this.rup_wizard('isCurrentStepLast')) {
				$('.rup-wizard_submitButton').hide();
			} else {
				$('.rup-wizard_submitButton').show();
				//Mover botón si no es resumen
				if (!this.rup_wizard('isCurrentStepSummary')) {
					$('#step' + stepNumber).find('p[id$=\'commands\']').append($('.rup-wizard_submitButton'));
				}
			}
		},
		/**
         * Selecciona el primer paso del asistente.
         *
         * @function first
         * @example
         * $("#idForm").rup_wizard("first");
         */
		first: function first() {
			this.rup_wizard('step', 0);
		},
		/**
         * Selecciona el último paso del asistente.
         *
         * @function last
         * @example
         * $("#idForm").rup_wizard("last");
         */
		last: function last() {
			this.rup_wizard('step', $('#steps').children().size() - 1);
		},
		/**
         * Devuelve el número del paso actual.
         *
         * @function getCurrentStep
         * @return {Integer} - Número de paso actual.
         * @example
         * $("#idForm").rup_wizard("getCurrentStep");
         */
		getCurrentStep: function getCurrentStep() {
			return parseInt($('#steps li.current').attr('id').substring(8));
		},
		/**
         * Indica si el paso recibido como parámetro es el activo.
         *
         * @function isCurrentStep
         * @param {Integer} step - Número de paso.
         * @return {boolean} - Devuelve true en caso de que el paso indicado sea el actual y false en caso de que no.
         * @example
         * $("#idForm").rup_wizard("isCurrentStep", 2);
         */
		isCurrentStep: function isCurrentStep(i) {
			return this.rup_wizard('getCurrentStep') === i;
		},
		/**
         * Indica si el paso activo es el primero.
         *
         * @function isCurrentStepFirst
         * @return {boolean} - Devuelve true en caso de que el último paso sea el activo y false en caso de que no.
         * @example
         * $("#idForm").rup_wizard("isCurrentStepFirst");
         */
		isCurrentStepFirst: function isCurrentStepFirst() {
			return this.rup_wizard('isCurrentStep', 0);
		},
		/**
         * Indica si el paso activo es el último.
         *
         * @function isCurrentStepLast
         * @return {boolean} - Devuelve true en caso de que el primer paso sea el activo y false en caso de que no.
         * @example
         * $("#idForm").rup_wizard("isCurrentStepLast");
         */
		isCurrentStepLast: function isCurrentStepLast() {
			return $('#steps').children().size() - 1 === this.rup_wizard('getCurrentStep');
		},
		/**
         * Indica si el paso activo es el resumen.
         *
         * @function isCurrentStepSummary
         * @return {boolean} - Devuelve true en caso de que el paso activo sea el del resumen y false en caso de que no.
         * @example
         * $("#idForm").rup_wizard("isCurrentStepSummary");
         */
		isCurrentStepSummary: function isCurrentStepSummary() {
			return $('#stepDesc' + this.rup_wizard('getCurrentStep')).hasClass('rup-wizard_summary');
		},
		/**
         * Habilita el paso recibido como parámetro.
         *
         * @function enableStep
         * @param {Integer} step - Numero que identifica el paso que deseamos habilitar.
         * @example
         * $("#idForm").rup_wizard("enableStep", 2);
         */
		enableStep: function enableStep(stepNumber) {
			$('#stepDesc' + stepNumber).removeClass('disabled');
		},
		/**
         * Deshabilita el paso recibido como parámetro.
         *
         * @function disableStep
         * @param {Integer} step - Numero que identifica el paso que deseamos deshabilitar.
         * @example
         * $("#idForm").rup_wizard("disableStep", 2);
         */
		disableStep: function disableStep(stepNumber) {
			$('#stepDesc' + stepNumber).addClass('disabled');
		},
		/**
         * Indica si el paso recibido como parámetro está deshabilitado.
         *
         * @function isStepDisabled
         * @param {Integer} step - Numero que identifica el paso que deseamos deshabilitar.
         * @return {boolean} - Devuelve true si el paso indicado está deshabilitado y false en caso de que no.
         * @example
         * $("#idForm").rup_wizard("isStepDisabled", 2);
         */
		isStepDisabled: function isStepDisabled(stepNumber) {
			return $('#stepDesc' + stepNumber).hasClass('disabled');
		}
	});

	//*******************************
	// DEFINICIÓN DE MÉTODOS PRIVADOS
	//*******************************
	$.fn.rup_wizard('extend', {
		_init: function _init(args) {
			if (args.length > 1) {
				$.rup.errorGestor($.rup.i18nParse($.rup.i18n.base, 'rup_global.initError') + $(this).attr('id'));
			} else {
				var settings = $.extend({}, $.fn.rup_wizard.defaults, args[0]),
				    rupWizard = this; //referencia

				this.addClass('rup-wizard');
				this._formToWizard(settings);

				//Contenedor (UL)
				$('#steps').addClass('rup-wizard_stepsDescContainer');

				//Paso (LI)
				$('#steps').children().each(function (index, element) {
					$(element).addClass('rup-wizard_stepDesc') //Estilo paso (LI)
					.click(function (event) {
						//Click en cabecera para cambio de paso
						var step = $(this).attr('id').substring(8);
						if (!rupWizard.isStepDisabled(step)) {
							if (settings.stepFnc[step] !== undefined) {
								if (settings.stepFnc[step].call() === false) {
									event.stopImmediatePropagation();
									return false;
								}
							}
							$(this).rup_wizard('step', step);
						}
					});

					//Eliminar "Step X"
					var span = $(element).children();
					$(span).text(index + 1 + '. ' + $(span).text());
					$(element).text('').append(span);
				});

				//Botones Anterior/Siguiente
				$('p[id$=\'commands\'] .prev')
				//Estilo
				.removeClass('prev').addClass('rup-wizard_prev')
				//Texto
				.text($.rup.i18nParse($.rup.i18n.base, 'rup_wizard.prev'))
				//Evento 'click'
				.unbind('click').click(function (event) {
					//Paso anterior
					rupWizard._gotoPrevStep(rupWizard, settings, event);
				});
				$('p[id$=\'commands\'] .next')
				//Estilo
				.removeClass('next').addClass('rup-wizard_next')
				//Texto
				.text($.rup.i18nParse($.rup.i18n.base, 'rup_wizard.next'))
				//Evento 'click'
				.unbind('click').click(function (event) {
					//Siguiente paso
					rupWizard._gotoNextStep(rupWizard, settings, event);
				});

				//Estilo botón submit (sirve de ID)
				$('#' + settings.submitButton).addClass('rup-wizard_submitButton');
				if (settings.submitFnc) {
					$('#' + settings.submitButton).click(settings.submitFnc);
				}

				//Estilos firstStep y finalStep
				$('#steps li:first').addClass('rup-wizard_firstStepDesc');
				$('#steps li:last').addClass('rup-wizard_lastStepDesc');

				//Paso de RESUMEN
				if (settings.summary) {
					//Cabecera
					$('#steps li:last').removeClass('rup-wizard_lastStepDesc');
					var stepNumber = $('#steps').children().size(),
					    stepDesc = $('<li>').attr('id', 'stepDesc' + stepNumber).addClass('rup-wizard_stepDesc rup-wizard_summary rup-wizard_lastStepDesc').append('<a>' + (stepNumber + 1) + '. ' + $.rup.i18nParse($.rup.i18n.base, 'rup_wizard.summary') + '</a>').click(function (event) {
						//Paso final
						$(this).rup_wizard('step', $(this).attr('id').substring(8));
						//Resumen
						rupWizard._generateSummary(stepNumber, rupWizard, settings);
						event.preventDefault();
					});
					$('#steps').append(stepDesc);

					//Capa
					if (stepNumber > 1) {
						$('div[id=\'step' + (stepNumber - 1) + '\']').after('<div id=\'step' + stepNumber + '\' style=\'display: none;\'/>');

						//Añadir botón siguiente anteúltimo paso
						var nextButton = $('<a>').attr('id', 'step' + (stepNumber - 1) + 'Next').html($.rup.i18nParse($.rup.i18n.base, 'rup_wizard.next')).addClass('rup-wizard_next').unbind('click').click(function (event) {
							//Siguiente paso
							rupWizard._gotoNextStep(rupWizard, settings, event);
							//Resumen
							rupWizard._generateSummary(stepNumber, rupWizard, settings);
							event.preventDefault();
						});
						$('#step' + (stepNumber - 1) + 'commands').append(nextButton);
					}
				}

				//Disabled
				if (settings.disabled !== undefined) {
					$.each(settings.disabled, function (index, element) {
						if (typeof element === 'number') {
							$(this).rup_wizard('disableStep', element);
						} else if (typeof element === 'string') {
							var begin = parseInt(element.substring(0, element.indexOf('-'))),
							    end = parseInt(element.substring(element.indexOf('-') + 1, element.length));
							for (var i = begin; i <= end; i++) {
								$(this).rup_wizard('disableStep', i);
							}
						}
					});
				}
			}

			//Ir al paso inicial
			this.rup_wizard('step', 0);
		},
		_gotoNextStep: function _gotoNextStep(rupWizard, settings, event) {
			// Obtener paso siguiente
			var nextStep = parseInt($('#steps li.current').attr('id').substring(8)) + 1;

			// Comprobar que no está deshabilitado (o buscar el
			// siguiente
			// habilitado)
			if (rupWizard.isStepDisabled(nextStep)) {
				nextStep = $('#stepDesc' + (nextStep - 1)).nextAll('li:not(.disabled)').first().attr('id');
				if (nextStep !== undefined) {
					nextStep = parseInt(nextStep.substring(8));
				} else {
					return false;
				}

				// Si fuera necesario, se generar el resumen
				if (jQuery('#steps').children().size() - 1 === nextStep) {
					rupWizard._generateSummary(nextStep, rupWizard, settings);
				}
			}

			// Invocar f(x) del paso (si existe)
			if (settings.stepFnc[nextStep] !== undefined) {
				if ($('#stepDesc' + nextStep).not('.rup-wizard_summary').length > 0) {
					// Evitar
					// resumen
					// (mala
					// configuracion
					// desarrollador)
					if (settings.stepFnc[nextStep].call() === false) {
						event.stopImmediatePropagation();
						return false;
					}
				}
			}

			// Cambiar de paso
			$('#stepDesc' + nextStep).rup_wizard('step', nextStep);
		},
		_gotoPrevStep: function _gotoPrevStep(rupWizard, settings, event) {

			//Obtener paso anterior
			var prevStep = parseInt($('#steps li.current').attr('id').substring(8)) - 1;

			//Comprobar que no está deshabilitado (o buscar el anterior habilitado)
			if (rupWizard.isStepDisabled(prevStep)) {
				prevStep = $('#stepDesc' + (prevStep + 1)).prevAll('li:not(.disabled)').first().attr('id');
				if (prevStep !== undefined) {
					prevStep = parseInt(prevStep.substring(8));
				} else {
					return false;
				}
			}

			//Invocar f(x) del paso (si existe)
			if (settings.stepFnc[prevStep] !== undefined) {
				if (settings.stepFnc[prevStep].call() === false) {
					event.stopImmediatePropagation();
					return false;
				}
			}

			//Cambiar de paso
			$('#stepDesc' + prevStep).rup_wizard('step', prevStep);
		},
		_generateSummary: function _generateSummary(stepNumber, rupWizard, settings) {

			//controlar si está deshabilitado
			if ($('#stepDesc' + stepNumber).hasClass('disabled')) {
				return false;
			}

			//Devolver botón submit a su lugar
			$('#step' + stepNumber).parent().append($('.rup-wizard_submitButton'));

			/** DEVELOPER SummaryFnc_PRE **/
			if (settings.summaryFnc_PRE && settings.summaryFnc_PRE.call() === false) {
				return false;
			}

			//Reiniciar capa (si hacemos .empty() no funciona accordion la segunda vez)
			$('#step' + stepNumber).remove();
			$('div[id=\'step' + (stepNumber - 1) + '\']').after('<div id=\'step' + stepNumber + '\' style=\'display: none;\'/>');

			//Copiar capas anteriores
			for (var i = 0; i < stepNumber; i++) {
				if (!rupWizard.isStepDisabled(i)) {
					//Comprobar pasos deshabilitados
					$('#step' + stepNumber).append($('#step' + i).children().clone());
				}
			}

			//Eliminar botones
			$('#step' + stepNumber + ' p[id$=\'commands\']').remove();

			//Botón anterior
			$('div[id=\'step' + stepNumber + '\'] fieldset:last').append('<p id=\'step' + stepNumber + 'commands\'></p>');
			var prevButton = $('<a>').attr('id', 'step' + stepNumber + 'Prev').html($.rup.i18nParse($.rup.i18n.base, 'rup_wizard.prev')).addClass('rup-wizard_prev').unbind('click').click(function (event) {
				//Paso anterior
				rupWizard._gotoPrevStep(rupWizard, settings, event);
			});
			$('#step' + stepNumber + 'commands').append(prevButton);

			/** DEVELOPER SummaryFnc_INTER **/
			if (settings.summaryFnc_INTER && settings.summaryFnc_INTER.call() === false) {
				return false;
			}

			//RUP_MULTICOMBO
			$('#step' + stepNumber + ' .ui-multiselect').each(function () {
				var selectObj = $('#' + $(this).prev().attr('id'));
				if (selectObj.data('settings') !== undefined) {
					var seleccionados = selectObj.rup_combo('label');
					if (seleccionados.length > 0) {
						//Existen elementos seleccionados?
						if (selectObj.data('settings')['summaryInline'] == undefined) {
							//Tratamiento por defecto
							var contenedor = $('<div />').addClass('rup-wizard_summaryMultivalue').insertAfter(this);
							for (var i = 0; i < seleccionados.length; i++) {
								$(settings.labelElement, {
									text: '- ' + seleccionados[i],
									'class': 'rup-wizard_summaryValue'
								}).appendTo(contenedor);
								$('<br/>').appendTo(contenedor);
							}
						} else {
							//Tratamiento en línea
							$(settings.labelElement, {
								text: seleccionados.toString().replace(/,/g, ', '),
								'class': 'rup-wizard_summaryValue'
							}).insertAfter(this);
						}
					} else {
						$(settings.labelElement, {
							html: '&nbsp;',
							'class': 'rup-wizard_summaryValue'
						}).insertAfter(this);
					}
					$(this).prev().remove();
					$(this).remove();
				}
			});

			//Gestionar INPUTS
			$('#step' + stepNumber + ' input').each(function () {
				if (this.type === 'text') {
					$(settings.labelElement, {
						text: this.value,
						'class': 'rup-wizard_summaryValue'
					}).insertAfter(this);
				} else if (this.type === 'password') {
					$(settings.labelElement, {
						text: rupWizard._hidePassword(this.value),
						'class': 'rup-wizard_summaryValue'
					}).insertAfter(this);
				} else if (this.type === 'radio') {
					if (this.checked) {
						$(settings.labelElement, {
							text: $('#step' + stepNumber + ' label[for=\'' + this.id + '\']').text(),
							'class': 'rup-wizard_summaryValue'
						}).insertAfter(this);
						$('#' + this.id).attr('checked', 'checked'); //Restablecer selección que se pierde al clonar
					}
					//						if (this.checked){
					//							$(settings.labelElement, { text: "(*) " + $("#step"+stepNumber+" label[for='"+this.id+"']").text(), "class":"rup-wizard_summaryValue" }).insertAfter(this);
					//							$("#"+this.id).attr("checked","checked"); //Restablecer selección que se pierde al clonar
					//						} else {
					//							$(settings.labelElement, { text: "( ) " + $("#step"+stepNumber+" label[for='"+this.id+"']").text(), "class":"rup-wizard_summaryValue" }).insertAfter(this);
					//						}
					$('#step' + stepNumber + ' label[for=\'' + this.id + '\']').remove();
				} else if (this.type === 'checkbox') {
					if (this.checked) {
						$(settings.labelElement, {
							text: '[X] ' + $('#step' + stepNumber + ' label[for=\'' + this.id + '\']').text(),
							'class': 'rup-wizard_summaryValue'
						}).insertAfter(this);
					} else {
						$(settings.labelElement, {
							text: '[ ] ' + $('#step' + stepNumber + ' label[for=\'' + this.id + '\']').text(),
							'class': 'rup-wizard_summaryValue'
						}).insertAfter(this);
					}
					$('#step' + stepNumber + ' label[for=\'' + this.id + '\']').remove();
				}
				$(this).remove();
			});

			//Gestionar TEXTAREAS
			$('#step' + stepNumber + ' textarea').each(function () {
				$(settings.textareaElement, {
					text: $('#' + $(this).attr('id')).val(),
					'class': 'rup-wizard_summaryParagraph'
				}).insertAfter(this);
				$(this).remove();
			});

			//Gestionar SELECTS
			$('#step' + stepNumber + ' select:not(\'.ui-pg-selbox\')').each(function () {
				$(settings.labelElement, {
					text: $('#' + this.id + ' option:selected').text() !== '&nbsp;' ? $('#' + this.id + ' option:selected').text() : '',
					'class': 'rup-wizard_summaryValue'
				}).insertAfter(this);
				$(this).remove();
			});

			//Gestionar LABELS
			$('#step' + stepNumber + ' label').each(function () {
				$(settings.labelSeparatorElement, {
					html: settings.labelSeparatorText,
					'class': 'rup-wizard_separator'
				}).insertAfter(this);
				$(settings.labelElement, {
					text: this.innerHTML,
					'class': 'rup-wizard_summaryLabel'
				}).insertAfter(this);
				$(this).remove();
			});

			//Gestionar componentes RUP
			//rup_accordion
			$('#step' + stepNumber + ' .ui-accordion').each(function () {
				$(this).attr('id', $(this).attr('id') + '_summary');
				$(this).removeAttr('class');
				$(this).children('h1').removeAttr('class');
				$(this).children('h1').children('span.ui-icon').first().remove();
				$(this).children('div').removeAttr('class');
				if ($.isEmptyObject(settings.rupAccordion)) {
					$(this).rup_accordion(settings.accordion);
				} else {
					$(this).rup_accordion(settings.rupAccordion);
				}
			});

			//rup_combo (multicombo se procesa antes)
			$('#step' + stepNumber + ' .rup_combo').each(function () {
				$(this).remove();
			});

			//rup_date
			$('#step' + stepNumber + ' img.ui-datepicker-trigger').each(function () {
				$(this).remove();
			});

			//rup_time
			$('#step' + stepNumber + ' img.ui-timepicker-trigger').each(function () {
				$(this).remove();
			});

			//rup_tabs
			var maxLevel = 0; //Control de estilos cuando las pestañas pasan a accordion
			if (settings.summaryTabs2Accordion) {
				settings.rupTabsElement = '<a />';
			}
			$('#step' + stepNumber + ' > fieldset').children('.rup-tabs_container').each(function () {

				var labelTabs = new Array(),
				    idTabs = new Array(),
				    fieldset = $(this).parent().attr('accordionable', true),
				    //Donde se deben anidar las pestañas
				containerTab = new Array();

				//Obtención de valores/ids de pestañas (labelTabs & idTabs)
				rupWizard._getRupTabs(rupWizard, $(this), labelTabs, idTabs);

				//Procesar pestañas
				var tab = null,
				    pointer = $(fieldset);
				for (var i = 0; i < labelTabs.length; i++) {
					tab = $(settings.rupTabsElement).text(labelTabs[i]); //LABEL pestaña
					if (idTabs[i].indexOf('rupRandomLayerId') !== -1) {
						//Es pestaña
						tab = $(tab).wrap('<div class=\'IE8_fix\'>');
						tab = $(tab).parent().append($(this).find(idTabs[i]).html());
						$(tab).children('div').addClass('rup-wizard_tabLevel-' + containerTab.length);
						tab = $(tab).children().unwrap();
					} else {
						//Es contenedor de pestañas
						tab = $(tab).attr('tabContainer', true);
						tab = $(tab).wrap('<div class=\'IE8_fix\'>');
						tab = $(tab).parent().append($('<div>').attr('id', 'subtab_' + labelTabs[i]).attr('accordionable', true).addClass('rup-wizard_tabContainerLevel-' + containerTab.length));
						tab = $(tab).children().unwrap();
						containerTab.push(labelTabs[i]);
						maxLevel++;
						$(pointer).append(tab);
						pointer = $('#subtab_' + labelTabs[i]);
						continue;
					}

					//Comprobamos si es subelemento
					if ($('#' + containerTab[containerTab.length - 1]).find(idTabs[i]).length === 0) {
						//No es subpestaña, se debe mover el puntero de dónde se deba añadir la capa
						pointer = $(fieldset);
						do {
							containerTab.pop(); //Extraer contenedor de pestañas
							//Comprobar si es subelemento
							if ($('#' + containerTab[containerTab.length - 1]).find(idTabs[i]).length > 0) {
								pointer = $('#subtab_' + containerTab[containerTab.length - 1]);
								break;
							} else {
								//Recalcular estilo (valor del nivel)
								$($(tab).get(1)).removeAttr('class').addClass('rup-wizard_tabLevel-' + containerTab.length);
							}
						} while (containerTab.length > 0);
					}

					//Añadir la capa
					$(pointer).append(tab);
				}

				// rup_table
				$('#step' + stepNumber + ' .rup-table-container').each(function () {
					var $table = $(this);

					$table.fluidWidth({
						fluidBaseLayer: '#' + $table.parent().attr('id')
					});
				});

				//h1 a /h1 para Pesatañas
				if (settings.summaryTabs2Accordion) {
					$(fieldset).find('a').each(function () {
						if (!$(this).hasClass('rup-wizard_prev') && !$(this).hasClass('rup-wizard_next')) {
							//Controlar que no sea botón
							$(this).wrap('<h1>');
						}
					});
				}

				//Eliminar contenedor
				$(this).remove();
			});

			//summaryWithAccordion
			if (settings.summaryWithAccordion) {

				//Convertir estructura
				$('#step' + stepNumber).find('legend').each(function (index, element) {
					//legend -> h1 a /h1
					$('<a />').text(element.innerHTML).insertBefore($(element).parent()).wrap('<h1 />');

					//fieldset -> div
					$(element).parent().replaceWith($('<div />').attr('accordionable', $(element).parent().attr('accordionable') === undefined ? false : true).append($(element).parent().children()));

					//remove legend
					$(element).remove();
				});

				//convertir en rup-accordion
				if ($.isEmptyObject(settings.summaryAccordion)) {
					$('#step' + stepNumber).rup_accordion(settings.accordion);
				} else {
					$('#step' + stepNumber).rup_accordion(settings.summaryAccordion);
				}

				//Botón anterior (sacar de accordion)
				$('<fieldset />').attr('id', 'commands_fieldset').addClass('commands-fieldset').append($('#step' + stepNumber).find('p[id=\'step' + stepNumber + 'commands\']')).appendTo($('#step' + stepNumber));

				//Espacio para separarlo de los pasos
				if (settings.summaryWithAccordionSpaceBefore) {
					$('#step' + stepNumber).prepend('</br>');
				}
				//Espacio para separarlo de los botones
				if (settings.summaryWithAccordionSpaceAfter) {
					$('#commands_fieldset').prepend('</br>');
				}
			}

			//tabs2Accordion
			if (settings.summaryTabs2Accordion) {
				//Eliminar estilos para no accordion
				for (var i = 0; i <= maxLevel; i++) {
					$('.rup-wizard_tabLevel-' + i).removeClass('rup-wizard_tabLevel-' + i);
					$('.rup-wizard_tabContainerLevel-' + i).removeClass('rup-wizard_tabContainerLevel-' + i);
				}

				$('[accordionable=true]').each(function (index, element) {
					if (element.nodeName === 'FIELDSET') {
						var legend = $(element).find('legend')[0],
						    buttons = $(element).find('p[id=\'step' + stepNumber + 'commands\']'),
						    object = $('<div />').attr('accordionable', $(element).attr('accordionable') === undefined ? false : true).append($(element).children());

						//Cambiar estructura
						$(element).replaceWith(object);

						//Eliminar extras (LEGEND y BOTONES)
						$(legend).remove();
						$(buttons).remove();

						//Accordion
						if ($.isEmptyObject(settings.tabAccordion)) {
							$(object).rup_accordion(settings.accordion);
						} else {
							$(object).rup_accordion(settings.tabAccordion);
						}

						//Restablecer extras (LEGEND y BOTONES)
						$(object).prepend(legend);
						$(object).append($('<fieldset />').append(buttons));
					} else {
						if ($.isEmptyObject(settings.tabAccordion)) {
							$(element).rup_accordion(settings.accordion);
						} else {
							$(element).rup_accordion(settings.tabAccordion);
						}
					}
				});
			}

			//Eliminar posibles atributos y estilos extra
			$('[accordionable]').removeAttr('accordionable');

			//Mover botón submit
			$('#step' + stepNumber).find('p[id$=\'commands\']').append($('.rup-wizard_submitButton'));

			//Mostrar paso
			$('#step' + stepNumber).show();

			/** DEVELOPER SummaryFnc_POST **/
			if (settings.summaryFnc_POST) {
				settings.summaryFnc_POST.call();
			}
		},
		_getRupTabs: function _getRupTabs(rupWizard, object, labelTabs, idTabs) {
			//Recorrer los enlaces a pestañas
			$(object).find('.rup-tabs_title').each(function (index, element) {
				//Comprobar que si el elemento ya existe (subpestaña) por recursividad, se omite
				if ($.inArray(element.innerHTML, labelTabs) !== -1) {
					return;
				}

				//Obtener ID y LABEL
				idTabs.push($(element).parent().attr('href'));
				labelTabs.push(element.innerHTML);

				//Es un contenedor de pestañas (llamada recursiva para pre-procesar los hijos)
				if (idTabs[idTabs.length - 1].substring(1) === labelTabs[labelTabs.length - 1]) {
					rupWizard._getRupTabs(rupWizard, $('#' + labelTabs[labelTabs.length - 1]), labelTabs, idTabs);
				}
			});
		},
		_hidePassword: function _hidePassword(password) {
			var value = '';
			for (var i = 0; i < password.length; i++) {
				value += '*';
			}
			return value;
		},
		/* Created by jankoatwarpspeed.com */ //http://www.jankoatwarpspeed.com/post/2009/09/28/webform-wizard-jquery.aspx
		//Modificaciones:
		//	- SPAN por A en los pasos para poder navegar con el tabulador

		_formToWizard: function _formToWizard(options) {
			options = $.extend({
				submitButton: ''
			}, options);

			var element = this;

			var steps = $(element).find('fieldset');
			var count = steps.size();
			var submmitButtonName = '#' + options.submitButton;
			$(submmitButtonName).hide();

			// 2
			$(element).before('<ul id=\'steps\'></ul>');

			steps.each(function (i) {
				$(this).wrap('<div id=\'step' + i + '\'></div>');
				$(this).append('<p id=\'step' + i + 'commands\'></p>');

				// 2
				var name = $(this).find('legend').html();
				$('#steps').append('<li id=\'stepDesc' + i + '\'>Step ' + (i + 1) + '<a>' + name + '</a></li>');

				if (i == 0) {
					createNextButton(i);
					selectStep(i);
				} else if (i == count - 1) {
					$('#step' + i).hide();
					createPrevButton(i);
				} else {
					$('#step' + i).hide();
					createPrevButton(i);
					createNextButton(i);
				}
			});

			function createPrevButton(i) {
				var stepName = 'step' + i;
				$('#' + stepName + 'commands').append('<a id=\'' + stepName + 'Prev\' class=\'prev\'>< Back</a>');

				$('#' + stepName + 'Prev').bind('click', function (e) {
					$('#' + stepName).hide();
					$('#step' + (i - 1)).show();
					$(submmitButtonName).hide();
					selectStep(i - 1);
					e.preventDefault();
				});
			}

			function createNextButton(i) {
				var stepName = 'step' + i;
				$('#' + stepName + 'commands').append('<a id=\'' + stepName + 'Next\' class=\'next\'>Next ></a>');

				$('#' + stepName + 'Next').bind('click', function (e) {
					$('#' + stepName).hide();
					$('#step' + (i + 1)).show();
					if (i + 2 == count) $(submmitButtonName).show();
					selectStep(i + 1);
					e.preventDefault();
				});
			}

			function selectStep(i) {
				$('#steps li').removeClass('current');
				$('#stepDesc' + i).addClass('current');
			}
		}
	});

	//******************************************************
	// DEFINICIÓN DE LA CONFIGURACION POR DEFECTO DEL PATRON
	//******************************************************
	$.fn.rup_wizard.defaults = {
		summary: true,
		summaryWithAccordion: false,
		summaryWithAccordionSpaceBefore: true,
		summaryWithAccordionSpaceAfter: true,
		summaryTabs2Accordion: false,
		stepFnc: {}, //funciones de cada paso
		accordion: {
			animated: 'bounceslide',
			active: false,
			autoHeight: false,
			collapsible: true,
			heightStyle: 'content'
		},
		rupAccordion: {}, //accordion (config) definidos en el formulario
		summaryAccordion: {}, //accordion (config) para generar resumen
		tabAccordion: {}, //accorion (config) para pestañas del resumen
		rupTabsElement: '<h4 />',
		labelElement: '<span />',
		labelSeparatorElement: '<span />',
		labelSeparatorText: '&nbsp;&nbsp;&nbsp;',
		textareaElement: '<p />'
	};

	/**
     * Función de callback que se ejecuta previamente al envío del formulario.
     *
     * @callback module:rup_wizard~onSubmitFnc
     * @example
     * $("#idForm").rup_wizard({
     *   submitFnc: function(){
     *   }
     * });
     */

	/**
     * Función de callback que se invocará previamente a la generación del paso.
     *
     * @callback module:rup_wizard~onSummaryFnc_PRE
     * @return {boolean} - En caso de devolver false no se generaría el resumen.
     * @example
     * $("#idForm").rup_wizard({
     *   summaryFnc_PRE: function(){
     *   }
     * });
     */

	/**
     * Función de callback que se ejecuta una vez ha comenzado la generación del paso resumen.
     *
     * @callback module:rup_wizard~onSummaryFnc_INTER
     * @return {boolean} - En caso de devolver false no se continuaría con el procesado del contenido de los pasos
     * @example
     * $("#idForm").rup_wizard({
     *   summaryFnc_INTER: function(){
     *   }
     * });
     */

	/**
     * Función de callback que se invocará una vez se ha generado el paso resumen.
     *
     * @callback module:rup_wizard~onSummaryFnc_POST
     * @example
     * $("#idForm").rup_wizard({
     *   summaryFnc_POST: function(){
     *   }
     * });
     */

	/**
     * @description Propiedades de configuración del componente.
     *
     * @name options
     *
     * @property {Selector} submitButton - Identificador del botón de envío del formulario. Sirve para que dicho botón solo se muestre en el último paso del asistente.
     * @property {module:rup_validate~onSubmitFnc} [submitFnc] - Función que se ejecuta previamente al envío del formulario.
     * @property {boolean} [summary=true] - Indica si se debe generar o no el paso resumen. Este paso mostrará (como texto plano) los valores seleccionados en los diferentes pasos habilitados. Si un paso se encuentra deshabilitado no se utilizarán sus valores para la generación del resumen. El paso de resumen se genera cuando se navega hacia él.
     * @property {boolean} [summaryWithAccordion=false] - Indica si el paso resumen debe formatear los diferentes pasos del asistente mediante elementos que usan el componente accordion.
     * @property {boolean} [summaryWithAccordionSpaceBefore=true] - Indica si cuando se genera un resumen con los diferentes pasos presentados con accordion, se debe dejar un espacio (</br>) entre el contenido y la barra con los pasos.
     * @property {boolean} [summaryWithAccordionSpaceAfter=true] - Indica si cuando se genera un resumen con los diferentes pasos presentados con accordion, se debe dejar un espacio (</br>) entre el contenido y el contenedor de botones (siguiente y enviar).
     * @property {boolean} [summaryTabs2Accordion=false] - Indica si los componentes rup_tab de los diferentes pasos del wizard se deben convertir en elementos del componente accordion a la hora de generar el paso resumen.
     * @property {module:rup_wizard~onSummaryFnc_PRE} [summaryFnc_PRE] - Función que se invocará previamente a la generación del paso resumen. En caso de devolver false no se generaría el resumen.
     * @property {module:rup_wizard~onSummaryFnc_INTER} [summaryFnc_INTER] -Función que se ejecuta una vez ha comenzado la generación del paso resumen. Se habrá generado la capa contenedora y duplicado el contenido de los pasos anteriores pero sin llegar a procesarse (cambiarse por texto plano). En caso de devolver false no se continuaría con el procesado del contenido de los pasos.
     * @property {module:rup_wizard~onSummaryFnc_POST} [summaryFnc_POST] - Función que se ejecuta una vez se ha generado el paso resumen.
     * @property {object} [stepFnc] - Objeto json que contiene las diferentes funciones a ejecutar al navegar hacia cada uno de los pasos. En caso de devolver false no se continuaría la navegación hacia dicho paso. La clave de cada elemento será el número del paso y el valor será la función a ejecutar.
     * @property {Integer[]} [disabled] - Array que indica los pasos a deshabilitar al inicio. En caso de que el elemento del array sea un número (numeric) se deshabilitará dicho paso y en caso de que sea un literal (string) se procesará como un intervalo que deberá definirse como “X-Y”.
     * @property {object} [accordion] - Define de forma general el funcionamiento del componente rup_accordion en el paso de resumen.
     * @property {object} [rupAccordion] - Define el funcionamiento del patrón rup_accordion en el resumen (de los objetos rup_accordion existentes en los pasos anteriores). No tiene valor por defecto, por lo que en caso de no definirse se toma el valor del parámetro accordion.
     * @property {object} [summaryAccordion] - Define el funcionamiento del patrón rup_accordion en el resumen para cada uno de los pasos que lo componen (si configura la generación de resumen y conversión de pasos en accordion). No tiene valor por defecto, por lo que en caso de no definirse se toma el valor del parámetro accordion.
     * @property {object} [tabAccordion] - Define el funcionamiento del patrón rup_accordion en el resumen, para cada los objetos rup_tab existentes en los pasos anteriores (si configura la generación de resumen y conversión de pestañas en accordion). No tiene valor por defecto, por lo que en caso de no definirse se toma el valor del parámetro accordion.
     * @property {string} [rupTabsElement=<h4/>] - Define el funcionamiento del patrón rup_accordion en el resumen, para cada los objetos rup_tab existentes en los pasos anteriores (si configura la generación de resumen y conversión de pestañas en accordion). No tiene valor por defecto, por lo que en caso de no definirse se toma el valor del parámetro accordion.
     * @property {string} [labelElement=<span/>] - Indica el tipo de objeto HTML en el que se convierten los objetos label en el paso de resumen.
     * @property {string} [labelSeparatorElement=<span/>] - Indica el tipo de objeto HTML que se utilizará para separar los valores de sus correspondientes labels en el paso de resumen.
     * @property {string} [labelSeparatorText=&nbsp;&nbsp;&nbsp;] - Indica el contenido del objeto HTML que se utilizará para separar los valores de sus correspondientes labels en el paso de resumen.
     * @property {string} [textareaElement=<p/>] - Indica el tipo de objeto HTML en el que se convierten los objetos textarea en el paso de resumen.
     */
});
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))

/***/ }),
/* 171 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function(global) {module.exports = global["$"] = __webpack_require__(0);
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(10)))

/***/ }),
/* 172 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function(global) {module.exports = global["jQuery"] = __webpack_require__(0);
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(10)))

/***/ }),
/* 173 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function(jQuery) {/*!
 * jQuery Migrate - v1.4.1 - 2016-05-19
 * Copyright jQuery Foundation and other contributors
 */
(function( jQuery, window, undefined ) {
// See http://bugs.jquery.com/ticket/13335
// "use strict";


jQuery.migrateVersion = "1.4.1";


var warnedAbout = {};

// List of warnings already given; public read only
jQuery.migrateWarnings = [];

// Set to true to prevent console output; migrateWarnings still maintained
// jQuery.migrateMute = false;

// Show a message on the console so devs know we're active
if ( window.console && window.console.log ) {
	window.console.log( "JQMIGRATE: Migrate is installed" +
		( jQuery.migrateMute ? "" : " with logging active" ) +
		", version " + jQuery.migrateVersion );
}

// Set to false to disable traces that appear with warnings
if ( jQuery.migrateTrace === undefined ) {
	jQuery.migrateTrace = true;
}

// Forget any warnings we've already given; public
jQuery.migrateReset = function() {
	warnedAbout = {};
	jQuery.migrateWarnings.length = 0;
};

function migrateWarn( msg) {
	var console = window.console;
	if ( !warnedAbout[ msg ] ) {
		warnedAbout[ msg ] = true;
		jQuery.migrateWarnings.push( msg );
		if ( console && console.warn && !jQuery.migrateMute ) {
			console.warn( "JQMIGRATE: " + msg );
			if ( jQuery.migrateTrace && console.trace ) {
				console.trace();
			}
		}
	}
}

function migrateWarnProp( obj, prop, value, msg ) {
	if ( Object.defineProperty ) {
		// On ES5 browsers (non-oldIE), warn if the code tries to get prop;
		// allow property to be overwritten in case some other plugin wants it
		try {
			Object.defineProperty( obj, prop, {
				configurable: true,
				enumerable: true,
				get: function() {
					migrateWarn( msg );
					return value;
				},
				set: function( newValue ) {
					migrateWarn( msg );
					value = newValue;
				}
			});
			return;
		} catch( err ) {
			// IE8 is a dope about Object.defineProperty, can't warn there
		}
	}

	// Non-ES5 (or broken) browser; just set the property
	jQuery._definePropertyBroken = true;
	obj[ prop ] = value;
}

if ( document.compatMode === "BackCompat" ) {
	// jQuery has never supported or tested Quirks Mode
	migrateWarn( "jQuery is not compatible with Quirks Mode" );
}


var attrFn = jQuery( "<input/>", { size: 1 } ).attr("size") && jQuery.attrFn,
	oldAttr = jQuery.attr,
	valueAttrGet = jQuery.attrHooks.value && jQuery.attrHooks.value.get ||
		function() { return null; },
	valueAttrSet = jQuery.attrHooks.value && jQuery.attrHooks.value.set ||
		function() { return undefined; },
	rnoType = /^(?:input|button)$/i,
	rnoAttrNodeType = /^[238]$/,
	rboolean = /^(?:autofocus|autoplay|async|checked|controls|defer|disabled|hidden|loop|multiple|open|readonly|required|scoped|selected)$/i,
	ruseDefault = /^(?:checked|selected)$/i;

// jQuery.attrFn
migrateWarnProp( jQuery, "attrFn", attrFn || {}, "jQuery.attrFn is deprecated" );

jQuery.attr = function( elem, name, value, pass ) {
	var lowerName = name.toLowerCase(),
		nType = elem && elem.nodeType;

	if ( pass ) {
		// Since pass is used internally, we only warn for new jQuery
		// versions where there isn't a pass arg in the formal params
		if ( oldAttr.length < 4 ) {
			migrateWarn("jQuery.fn.attr( props, pass ) is deprecated");
		}
		if ( elem && !rnoAttrNodeType.test( nType ) &&
			(attrFn ? name in attrFn : jQuery.isFunction(jQuery.fn[name])) ) {
			return jQuery( elem )[ name ]( value );
		}
	}

	// Warn if user tries to set `type`, since it breaks on IE 6/7/8; by checking
	// for disconnected elements we don't warn on $( "<button>", { type: "button" } ).
	if ( name === "type" && value !== undefined && rnoType.test( elem.nodeName ) && elem.parentNode ) {
		migrateWarn("Can't change the 'type' of an input or button in IE 6/7/8");
	}

	// Restore boolHook for boolean property/attribute synchronization
	if ( !jQuery.attrHooks[ lowerName ] && rboolean.test( lowerName ) ) {
		jQuery.attrHooks[ lowerName ] = {
			get: function( elem, name ) {
				// Align boolean attributes with corresponding properties
				// Fall back to attribute presence where some booleans are not supported
				var attrNode,
					property = jQuery.prop( elem, name );
				return property === true || typeof property !== "boolean" &&
					( attrNode = elem.getAttributeNode(name) ) && attrNode.nodeValue !== false ?

					name.toLowerCase() :
					undefined;
			},
			set: function( elem, value, name ) {
				var propName;
				if ( value === false ) {
					// Remove boolean attributes when set to false
					jQuery.removeAttr( elem, name );
				} else {
					// value is true since we know at this point it's type boolean and not false
					// Set boolean attributes to the same name and set the DOM property
					propName = jQuery.propFix[ name ] || name;
					if ( propName in elem ) {
						// Only set the IDL specifically if it already exists on the element
						elem[ propName ] = true;
					}

					elem.setAttribute( name, name.toLowerCase() );
				}
				return name;
			}
		};

		// Warn only for attributes that can remain distinct from their properties post-1.9
		if ( ruseDefault.test( lowerName ) ) {
			migrateWarn( "jQuery.fn.attr('" + lowerName + "') might use property instead of attribute" );
		}
	}

	return oldAttr.call( jQuery, elem, name, value );
};

// attrHooks: value
jQuery.attrHooks.value = {
	get: function( elem, name ) {
		var nodeName = ( elem.nodeName || "" ).toLowerCase();
		if ( nodeName === "button" ) {
			return valueAttrGet.apply( this, arguments );
		}
		if ( nodeName !== "input" && nodeName !== "option" ) {
			migrateWarn("jQuery.fn.attr('value') no longer gets properties");
		}
		return name in elem ?
			elem.value :
			null;
	},
	set: function( elem, value ) {
		var nodeName = ( elem.nodeName || "" ).toLowerCase();
		if ( nodeName === "button" ) {
			return valueAttrSet.apply( this, arguments );
		}
		if ( nodeName !== "input" && nodeName !== "option" ) {
			migrateWarn("jQuery.fn.attr('value', val) no longer sets properties");
		}
		// Does not return so that setAttribute is also used
		elem.value = value;
	}
};


var matched, browser,
	oldInit = jQuery.fn.init,
	oldFind = jQuery.find,
	oldParseJSON = jQuery.parseJSON,
	rspaceAngle = /^\s*</,
	rattrHashTest = /\[(\s*[-\w]+\s*)([~|^$*]?=)\s*([-\w#]*?#[-\w#]*)\s*\]/,
	rattrHashGlob = /\[(\s*[-\w]+\s*)([~|^$*]?=)\s*([-\w#]*?#[-\w#]*)\s*\]/g,
	// Note: XSS check is done below after string is trimmed
	rquickExpr = /^([^<]*)(<[\w\W]+>)([^>]*)$/;

// $(html) "looks like html" rule change
jQuery.fn.init = function( selector, context, rootjQuery ) {
	var match, ret;

	if ( selector && typeof selector === "string" ) {
		if ( !jQuery.isPlainObject( context ) &&
				(match = rquickExpr.exec( jQuery.trim( selector ) )) && match[ 0 ] ) {

			// This is an HTML string according to the "old" rules; is it still?
			if ( !rspaceAngle.test( selector ) ) {
				migrateWarn("$(html) HTML strings must start with '<' character");
			}
			if ( match[ 3 ] ) {
				migrateWarn("$(html) HTML text after last tag is ignored");
			}

			// Consistently reject any HTML-like string starting with a hash (gh-9521)
			// Note that this may break jQuery 1.6.x code that otherwise would work.
			if ( match[ 0 ].charAt( 0 ) === "#" ) {
				migrateWarn("HTML string cannot start with a '#' character");
				jQuery.error("JQMIGRATE: Invalid selector string (XSS)");
			}

			// Now process using loose rules; let pre-1.8 play too
			// Is this a jQuery context? parseHTML expects a DOM element (#178)
			if ( context && context.context && context.context.nodeType ) {
				context = context.context;
			}

			if ( jQuery.parseHTML ) {
				return oldInit.call( this,
						jQuery.parseHTML( match[ 2 ], context && context.ownerDocument ||
							context || document, true ), context, rootjQuery );
			}
		}
	}

	ret = oldInit.apply( this, arguments );

	// Fill in selector and context properties so .live() works
	if ( selector && selector.selector !== undefined ) {
		// A jQuery object, copy its properties
		ret.selector = selector.selector;
		ret.context = selector.context;

	} else {
		ret.selector = typeof selector === "string" ? selector : "";
		if ( selector ) {
			ret.context = selector.nodeType? selector : context || document;
		}
	}

	return ret;
};
jQuery.fn.init.prototype = jQuery.fn;

jQuery.find = function( selector ) {
	var args = Array.prototype.slice.call( arguments );

	// Support: PhantomJS 1.x
	// String#match fails to match when used with a //g RegExp, only on some strings
	if ( typeof selector === "string" && rattrHashTest.test( selector ) ) {

		// The nonstandard and undocumented unquoted-hash was removed in jQuery 1.12.0
		// First see if qS thinks it's a valid selector, if so avoid a false positive
		try {
			document.querySelector( selector );
		} catch ( err1 ) {

			// Didn't *look* valid to qSA, warn and try quoting what we think is the value
			selector = selector.replace( rattrHashGlob, function( _, attr, op, value ) {
				return "[" + attr + op + "\"" + value + "\"]";
			} );

			// If the regexp *may* have created an invalid selector, don't update it
			// Note that there may be false alarms if selector uses jQuery extensions
			try {
				document.querySelector( selector );
				migrateWarn( "Attribute selector with '#' must be quoted: " + args[ 0 ] );
				args[ 0 ] = selector;
			} catch ( err2 ) {
				migrateWarn( "Attribute selector with '#' was not fixed: " + args[ 0 ] );
			}
		}
	}

	return oldFind.apply( this, args );
};

// Copy properties attached to original jQuery.find method (e.g. .attr, .isXML)
var findProp;
for ( findProp in oldFind ) {
	if ( Object.prototype.hasOwnProperty.call( oldFind, findProp ) ) {
		jQuery.find[ findProp ] = oldFind[ findProp ];
	}
}

// Let $.parseJSON(falsy_value) return null
jQuery.parseJSON = function( json ) {
	if ( !json ) {
		migrateWarn("jQuery.parseJSON requires a valid JSON string");
		return null;
	}
	return oldParseJSON.apply( this, arguments );
};

jQuery.uaMatch = function( ua ) {
	ua = ua.toLowerCase();

	var match = /(chrome)[ \/]([\w.]+)/.exec( ua ) ||
		/(webkit)[ \/]([\w.]+)/.exec( ua ) ||
		/(opera)(?:.*version|)[ \/]([\w.]+)/.exec( ua ) ||
		/(msie) ([\w.]+)/.exec( ua ) ||
		ua.indexOf("compatible") < 0 && /(mozilla)(?:.*? rv:([\w.]+)|)/.exec( ua ) ||
		[];

	return {
		browser: match[ 1 ] || "",
		version: match[ 2 ] || "0"
	};
};

// Don't clobber any existing jQuery.browser in case it's different
if ( !jQuery.browser ) {
	matched = jQuery.uaMatch( navigator.userAgent );
	browser = {};

	if ( matched.browser ) {
		browser[ matched.browser ] = true;
		browser.version = matched.version;
	}

	// Chrome is Webkit, but Webkit is also Safari.
	if ( browser.chrome ) {
		browser.webkit = true;
	} else if ( browser.webkit ) {
		browser.safari = true;
	}

	jQuery.browser = browser;
}

// Warn if the code tries to get jQuery.browser
migrateWarnProp( jQuery, "browser", jQuery.browser, "jQuery.browser is deprecated" );

// jQuery.boxModel deprecated in 1.3, jQuery.support.boxModel deprecated in 1.7
jQuery.boxModel = jQuery.support.boxModel = (document.compatMode === "CSS1Compat");
migrateWarnProp( jQuery, "boxModel", jQuery.boxModel, "jQuery.boxModel is deprecated" );
migrateWarnProp( jQuery.support, "boxModel", jQuery.support.boxModel, "jQuery.support.boxModel is deprecated" );

jQuery.sub = function() {
	function jQuerySub( selector, context ) {
		return new jQuerySub.fn.init( selector, context );
	}
	jQuery.extend( true, jQuerySub, this );
	jQuerySub.superclass = this;
	jQuerySub.fn = jQuerySub.prototype = this();
	jQuerySub.fn.constructor = jQuerySub;
	jQuerySub.sub = this.sub;
	jQuerySub.fn.init = function init( selector, context ) {
		var instance = jQuery.fn.init.call( this, selector, context, rootjQuerySub );
		return instance instanceof jQuerySub ?
			instance :
			jQuerySub( instance );
	};
	jQuerySub.fn.init.prototype = jQuerySub.fn;
	var rootjQuerySub = jQuerySub(document);
	migrateWarn( "jQuery.sub() is deprecated" );
	return jQuerySub;
};

// The number of elements contained in the matched element set
jQuery.fn.size = function() {
	migrateWarn( "jQuery.fn.size() is deprecated; use the .length property" );
	return this.length;
};


var internalSwapCall = false;

// If this version of jQuery has .swap(), don't false-alarm on internal uses
if ( jQuery.swap ) {
	jQuery.each( [ "height", "width", "reliableMarginRight" ], function( _, name ) {
		var oldHook = jQuery.cssHooks[ name ] && jQuery.cssHooks[ name ].get;

		if ( oldHook ) {
			jQuery.cssHooks[ name ].get = function() {
				var ret;

				internalSwapCall = true;
				ret = oldHook.apply( this, arguments );
				internalSwapCall = false;
				return ret;
			};
		}
	});
}

jQuery.swap = function( elem, options, callback, args ) {
	var ret, name,
		old = {};

	if ( !internalSwapCall ) {
		migrateWarn( "jQuery.swap() is undocumented and deprecated" );
	}

	// Remember the old values, and insert the new ones
	for ( name in options ) {
		old[ name ] = elem.style[ name ];
		elem.style[ name ] = options[ name ];
	}

	ret = callback.apply( elem, args || [] );

	// Revert the old values
	for ( name in options ) {
		elem.style[ name ] = old[ name ];
	}

	return ret;
};


// Ensure that $.ajax gets the new parseJSON defined in core.js
jQuery.ajaxSetup({
	converters: {
		"text json": jQuery.parseJSON
	}
});


var oldFnData = jQuery.fn.data;

jQuery.fn.data = function( name ) {
	var ret, evt,
		elem = this[0];

	// Handles 1.7 which has this behavior and 1.8 which doesn't
	if ( elem && name === "events" && arguments.length === 1 ) {
		ret = jQuery.data( elem, name );
		evt = jQuery._data( elem, name );
		if ( ( ret === undefined || ret === evt ) && evt !== undefined ) {
			migrateWarn("Use of jQuery.fn.data('events') is deprecated");
			return evt;
		}
	}
	return oldFnData.apply( this, arguments );
};


var rscriptType = /\/(java|ecma)script/i;

// Since jQuery.clean is used internally on older versions, we only shim if it's missing
if ( !jQuery.clean ) {
	jQuery.clean = function( elems, context, fragment, scripts ) {
		// Set context per 1.8 logic
		context = context || document;
		context = !context.nodeType && context[0] || context;
		context = context.ownerDocument || context;

		migrateWarn("jQuery.clean() is deprecated");

		var i, elem, handleScript, jsTags,
			ret = [];

		jQuery.merge( ret, jQuery.buildFragment( elems, context ).childNodes );

		// Complex logic lifted directly from jQuery 1.8
		if ( fragment ) {
			// Special handling of each script element
			handleScript = function( elem ) {
				// Check if we consider it executable
				if ( !elem.type || rscriptType.test( elem.type ) ) {
					// Detach the script and store it in the scripts array (if provided) or the fragment
					// Return truthy to indicate that it has been handled
					return scripts ?
						scripts.push( elem.parentNode ? elem.parentNode.removeChild( elem ) : elem ) :
						fragment.appendChild( elem );
				}
			};

			for ( i = 0; (elem = ret[i]) != null; i++ ) {
				// Check if we're done after handling an executable script
				if ( !( jQuery.nodeName( elem, "script" ) && handleScript( elem ) ) ) {
					// Append to fragment and handle embedded scripts
					fragment.appendChild( elem );
					if ( typeof elem.getElementsByTagName !== "undefined" ) {
						// handleScript alters the DOM, so use jQuery.merge to ensure snapshot iteration
						jsTags = jQuery.grep( jQuery.merge( [], elem.getElementsByTagName("script") ), handleScript );

						// Splice the scripts into ret after their former ancestor and advance our index beyond them
						ret.splice.apply( ret, [i + 1, 0].concat( jsTags ) );
						i += jsTags.length;
					}
				}
			}
		}

		return ret;
	};
}

var eventAdd = jQuery.event.add,
	eventRemove = jQuery.event.remove,
	eventTrigger = jQuery.event.trigger,
	oldToggle = jQuery.fn.toggle,
	oldLive = jQuery.fn.live,
	oldDie = jQuery.fn.die,
	oldLoad = jQuery.fn.load,
	ajaxEvents = "ajaxStart|ajaxStop|ajaxSend|ajaxComplete|ajaxError|ajaxSuccess",
	rajaxEvent = new RegExp( "\\b(?:" + ajaxEvents + ")\\b" ),
	rhoverHack = /(?:^|\s)hover(\.\S+|)\b/,
	hoverHack = function( events ) {
		if ( typeof( events ) !== "string" || jQuery.event.special.hover ) {
			return events;
		}
		if ( rhoverHack.test( events ) ) {
			migrateWarn("'hover' pseudo-event is deprecated, use 'mouseenter mouseleave'");
		}
		return events && events.replace( rhoverHack, "mouseenter$1 mouseleave$1" );
	};

// Event props removed in 1.9, put them back if needed; no practical way to warn them
if ( jQuery.event.props && jQuery.event.props[ 0 ] !== "attrChange" ) {
	jQuery.event.props.unshift( "attrChange", "attrName", "relatedNode", "srcElement" );
}

// Undocumented jQuery.event.handle was "deprecated" in jQuery 1.7
if ( jQuery.event.dispatch ) {
	migrateWarnProp( jQuery.event, "handle", jQuery.event.dispatch, "jQuery.event.handle is undocumented and deprecated" );
}

// Support for 'hover' pseudo-event and ajax event warnings
jQuery.event.add = function( elem, types, handler, data, selector ){
	if ( elem !== document && rajaxEvent.test( types ) ) {
		migrateWarn( "AJAX events should be attached to document: " + types );
	}
	eventAdd.call( this, elem, hoverHack( types || "" ), handler, data, selector );
};
jQuery.event.remove = function( elem, types, handler, selector, mappedTypes ){
	eventRemove.call( this, elem, hoverHack( types ) || "", handler, selector, mappedTypes );
};

jQuery.each( [ "load", "unload", "error" ], function( _, name ) {

	jQuery.fn[ name ] = function() {
		var args = Array.prototype.slice.call( arguments, 0 );

		// If this is an ajax load() the first arg should be the string URL;
		// technically this could also be the "Anything" arg of the event .load()
		// which just goes to show why this dumb signature has been deprecated!
		// jQuery custom builds that exclude the Ajax module justifiably die here.
		if ( name === "load" && typeof args[ 0 ] === "string" ) {
			return oldLoad.apply( this, args );
		}

		migrateWarn( "jQuery.fn." + name + "() is deprecated" );

		args.splice( 0, 0, name );
		if ( arguments.length ) {
			return this.bind.apply( this, args );
		}

		// Use .triggerHandler here because:
		// - load and unload events don't need to bubble, only applied to window or image
		// - error event should not bubble to window, although it does pre-1.7
		// See http://bugs.jquery.com/ticket/11820
		this.triggerHandler.apply( this, args );
		return this;
	};

});

jQuery.fn.toggle = function( fn, fn2 ) {

	// Don't mess with animation or css toggles
	if ( !jQuery.isFunction( fn ) || !jQuery.isFunction( fn2 ) ) {
		return oldToggle.apply( this, arguments );
	}
	migrateWarn("jQuery.fn.toggle(handler, handler...) is deprecated");

	// Save reference to arguments for access in closure
	var args = arguments,
		guid = fn.guid || jQuery.guid++,
		i = 0,
		toggler = function( event ) {
			// Figure out which function to execute
			var lastToggle = ( jQuery._data( this, "lastToggle" + fn.guid ) || 0 ) % i;
			jQuery._data( this, "lastToggle" + fn.guid, lastToggle + 1 );

			// Make sure that clicks stop
			event.preventDefault();

			// and execute the function
			return args[ lastToggle ].apply( this, arguments ) || false;
		};

	// link all the functions, so any of them can unbind this click handler
	toggler.guid = guid;
	while ( i < args.length ) {
		args[ i++ ].guid = guid;
	}

	return this.click( toggler );
};

jQuery.fn.live = function( types, data, fn ) {
	migrateWarn("jQuery.fn.live() is deprecated");
	if ( oldLive ) {
		return oldLive.apply( this, arguments );
	}
	jQuery( this.context ).on( types, this.selector, data, fn );
	return this;
};

jQuery.fn.die = function( types, fn ) {
	migrateWarn("jQuery.fn.die() is deprecated");
	if ( oldDie ) {
		return oldDie.apply( this, arguments );
	}
	jQuery( this.context ).off( types, this.selector || "**", fn );
	return this;
};

// Turn global events into document-triggered events
jQuery.event.trigger = function( event, data, elem, onlyHandlers  ){
	if ( !elem && !rajaxEvent.test( event ) ) {
		migrateWarn( "Global events are undocumented and deprecated" );
	}
	return eventTrigger.call( this,  event, data, elem || document, onlyHandlers  );
};
jQuery.each( ajaxEvents.split("|"),
	function( _, name ) {
		jQuery.event.special[ name ] = {
			setup: function() {
				var elem = this;

				// The document needs no shimming; must be !== for oldIE
				if ( elem !== document ) {
					jQuery.event.add( document, name + "." + jQuery.guid, function() {
						jQuery.event.trigger( name, Array.prototype.slice.call( arguments, 1 ), elem, true );
					});
					jQuery._data( this, name, jQuery.guid++ );
				}
				return false;
			},
			teardown: function() {
				if ( this !== document ) {
					jQuery.event.remove( document, name + "." + jQuery._data( this, name ) );
				}
				return false;
			}
		};
	}
);

jQuery.event.special.ready = {
	setup: function() {
		if ( this === document ) {
			migrateWarn( "'ready' event is deprecated" );
		}
	}
};

var oldSelf = jQuery.fn.andSelf || jQuery.fn.addBack,
	oldFnFind = jQuery.fn.find;

jQuery.fn.andSelf = function() {
	migrateWarn("jQuery.fn.andSelf() replaced by jQuery.fn.addBack()");
	return oldSelf.apply( this, arguments );
};

jQuery.fn.find = function( selector ) {
	var ret = oldFnFind.apply( this, arguments );
	ret.context = this.context;
	ret.selector = this.selector ? this.selector + " " + selector : selector;
	return ret;
};


// jQuery 1.6 did not support Callbacks, do not warn there
if ( jQuery.Callbacks ) {

	var oldDeferred = jQuery.Deferred,
		tuples = [
			// action, add listener, callbacks, .then handlers, final state
			[ "resolve", "done", jQuery.Callbacks("once memory"),
				jQuery.Callbacks("once memory"), "resolved" ],
			[ "reject", "fail", jQuery.Callbacks("once memory"),
				jQuery.Callbacks("once memory"), "rejected" ],
			[ "notify", "progress", jQuery.Callbacks("memory"),
				jQuery.Callbacks("memory") ]
		];

	jQuery.Deferred = function( func ) {
		var deferred = oldDeferred(),
			promise = deferred.promise();

		deferred.pipe = promise.pipe = function( /* fnDone, fnFail, fnProgress */ ) {
			var fns = arguments;

			migrateWarn( "deferred.pipe() is deprecated" );

			return jQuery.Deferred(function( newDefer ) {
				jQuery.each( tuples, function( i, tuple ) {
					var fn = jQuery.isFunction( fns[ i ] ) && fns[ i ];
					// deferred.done(function() { bind to newDefer or newDefer.resolve })
					// deferred.fail(function() { bind to newDefer or newDefer.reject })
					// deferred.progress(function() { bind to newDefer or newDefer.notify })
					deferred[ tuple[1] ](function() {
						var returned = fn && fn.apply( this, arguments );
						if ( returned && jQuery.isFunction( returned.promise ) ) {
							returned.promise()
								.done( newDefer.resolve )
								.fail( newDefer.reject )
								.progress( newDefer.notify );
						} else {
							newDefer[ tuple[ 0 ] + "With" ](
								this === promise ? newDefer.promise() : this,
								fn ? [ returned ] : arguments
							);
						}
					});
				});
				fns = null;
			}).promise();

		};

		deferred.isResolved = function() {
			migrateWarn( "deferred.isResolved is deprecated" );
			return deferred.state() === "resolved";
		};

		deferred.isRejected = function() {
			migrateWarn( "deferred.isRejected is deprecated" );
			return deferred.state() === "rejected";
		};

		if ( func ) {
			func.call( deferred, deferred );
		}

		return deferred;
	};

}

})( jQuery, window );

/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))

/***/ }),
/* 174 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;
/*global jQuery */
/*global define */

(function (root, factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(3)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		root.ButtonBootstrapAdapter = factory(jQuery);
	}
})(undefined, function ($, Rup) {

	function ButtonBootstrapAdapter() {}

	ButtonBootstrapAdapter.prototype.NAME = 'button_bootstrap';

	ButtonBootstrapAdapter.prototype.createDropdownButton = function (settings) {
		var $self = this,
		    dropdownSettings = settings.dropdown;

		return $(Rup.Templates.rup.button.dropdownButton({
			id: $self.prop('id') + '_dropdown'
		}));
	};

	ButtonBootstrapAdapter.prototype.createMButton = function (settings, label) {
		var $self = this,
		    dropdownSettings = settings.dropdown;

		return $(Rup.Templates.rup.button.mbutton({
			id: $self.prop('id'),
			classes: 'rup-toolbar_menuButton ui-button ui-corner-all ui-widget rup-toolbar_menuButtonSlided',
			label: label,
			iconClasses: 'ui-button-icon ui-icon rup-toolbar_menuButtonIcon'
		}));
	};

	ButtonBootstrapAdapter.prototype.createMButtonContainer = function (settings, label) {
		var $self = this,
		    dropdownSettings = settings.dropdown;

		return $(Rup.Templates.rup.button.mbutton - container({
			id: $self.prop('id') + '-container',
			classes: 'ui-widget ui-widget-content rup-toolbar_menuButtonContainer',
			label: label,
			iconClasses: 'ui-button-icon ui-icon rup-toolbar_menuButtonIcon'
		}));
	};

	$.rup = $.rup || {};
	$.rup.adapter = $.rup.adapter || {};

	$.rup.adapter[ButtonBootstrapAdapter.prototype.NAME] = new ButtonBootstrapAdapter();

	return $;
});

/***/ }),
/* 175 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function(jQuery) {var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*global jQuery */
/*global define */

(function (root, factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(2)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		root.ButtonJQueryUIAdapter = factory(jQuery);
	}
})(undefined, function ($) {

	function ButtonJQueryUIAdapter() {}

	ButtonJQueryUIAdapter.prototype.NAME = 'button_jqueryui';

	ButtonJQueryUIAdapter.prototype.createDropdownButton = function (settings) {

		var $self = this,
		    dropdownSettings = settings.dropdown;
		return jQuery('<button>').attr({
			type: 'button',
			id: $self.prop('id') + '_dropdown'

		}).text('Administración de filtros').button({
			icons: {
				primary: dropdownSettings.dropdownIcon
			},
			text: false
		}).addClass('rup-dropdown-button');
	};

	$.rup = $.rup || {};
	$.rup.adapter = $.rup.adapter || {};

	$.rup.adapter[ButtonJQueryUIAdapter.prototype.NAME] = new ButtonJQueryUIAdapter();

	return $;
});
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))

/***/ }),
/* 176 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function(jQuery) {var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*global jQuery */
/*global define */

(function (root, factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(3), __webpack_require__(2)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		root.DatatableBootstrapAdapter = factory(jQuery);
	}
})(undefined, function ($, Rup) {

	function DatatableBootstrapAdapter() {}

	DatatableBootstrapAdapter.prototype.NAME = 'datatable_bootstrap';

	DatatableBootstrapAdapter.prototype.CONST = {
		core: {
			operations: {
				defaultOperations: {
					'add': {
						icon: 'fa fa-plus'
					},
					'edit': {
						icon: 'fa fa-pencil-square-o'
					},
					'clone': {
						icon: 'fa fa-clone'
					},
					'delete': {
						icon: 'fa fa-trash-o'
					},
					'reports': {
						icon: 'fa fa-file-o'
					},
					'copyButton': {
						icon: 'fa fa-clipboard'
					}
				}
			}
		}
	};

	DatatableBootstrapAdapter.prototype.configurePager = function (settings) {
		var $self = this,
		    pagerName,
		    $pagerCenter,
		    pagerLeft,
		    pagerRight,
		    $pagerLeft,
		    $pagerCenter,
		    $pagerRight;

		if (settings.pager !== undefined && settings.pager !== null) {
			settings.$pager = $(settings.pager.indexOf('#') === 0 ? settings.pager : '#' + settings.pager);
			pagerName = settings.$pager.attr('id');

			settings.$pager.css('height', 'auto'); //Posibilitar redimensionar paginador

			//Añadir clase a cada parte del paginador
			$pagerLeft = $('#' + pagerName + '_left');
			$pagerCenter = $('#' + pagerName + '_center');
			$pagerRight = $('#' + pagerName + '_right');

			$pagerLeft.addClass('pager_left');
			$pagerCenter.addClass('pager_center');
			$pagerRight.addClass('pager_right');

			//pager_left
			//**********
			//Quitar posibles botones del paginador (y dejar la parte izquierda vacía)
			$pagerLeft.html('');

			//Contador de seleccionados
			if (settings.multiselect === true) {
				$pagerLeft.append($('<div/>').addClass('ui-paging-selected').html('0 ' + jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.pager.selected')));
			}

			// Pager center
			$pagerCenter.css('white-space', 'inherit');
			jQuery('.pager_center datatable td', settings.$pager).addClass('pagControls');

			// Evento de control de página máxima
			jQuery('.pagControls input.ui-pg-input', $pagerCenter).on('change', function () {
				var pageNum = parseInt($(this).val()),
				    totalNum = parseInt($self.rup_datatable('getGridParam', 'lastpage'));

				if (isNaN(pageNum) === false && pageNum > totalNum) {
					$(this).val(totalNum);
				}
			});

			// Tooltip al combo de selección de número de registros
			jQuery('.pagControls select.ui-pg-selbox', $pagerCenter).attr('title', jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.pager.select')).rup_tooltip();
			// Tooltip al input de selección de página
			jQuery('.pagControls input.ui-pg-input', $pagerCenter).attr('title', jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.pager.input')).rup_tooltip();

			var pagerLinkTemplate = Rup.Templates.rup.datatable.pager.link.bootstrap;

			//Cambiar flechas paginación por literales
			jQuery('#first_' + pagerName, $pagerCenter).html(pagerLinkTemplate({
				label: jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.pager.primPag'),
				icon: 'fa fa-angle-double-left'
			})).removeClass('ui-pg-button');

			jQuery('#prev_' + pagerName, $pagerCenter).html(pagerLinkTemplate({
				label: jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.pager.anterior'),
				icon: 'fa fa-angle-left'
			})).removeClass('ui-pg-button');
			jQuery('#next_' + pagerName, $pagerCenter).html(pagerLinkTemplate({
				label: jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.pager.siguiente'),
				icon: 'fa fa-angle-right'
			})).removeClass('ui-pg-button');
			jQuery('#last_' + pagerName, $pagerCenter).html(pagerLinkTemplate({
				label: jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.pager.ultiPag'),
				icon: 'fa fa-angle-double-right'
			})).removeClass('ui-pg-button');
		}
	};

	DatatableBootstrapAdapter.prototype.createDetailNavigation = function () {

		var $self = $(this),
		    settings = $self.data('settings'),
		    jqGridID = $self.attr('id');
		var $template = $(Rup.Templates.rup.datatable.detail.navigation.bootstrap({
			datatableId: $self.prop('id'),
			resultNumText: jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.numResult'),
			labelFirst: jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.first'),
			labelPrev: jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.previous'),
			labelNext: jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.next'),
			labelLast: jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.last')

		}));

		// var $self = $(this),
		//     settings = $self.data("settings"),
		//     jqGridID = $self.attr("id"),
		//     paginationBarTmpl = jQuery.rup.i18nParse(jQuery.rup.i18n.base, "rup_datatable.templates.detailForm.paginationBar"),
		//     paginationLinkTmpl = jQuery.rup.i18nParse(jQuery.rup.i18n.base, "rup_datatable.templates.detailForm.paginationLink"),
		//     elementCounterTmpl = jQuery.rup.i18nParse(jQuery.rup.i18n.base, "rup_datatable.templates.detailForm.elementCounter"),
		//     $separator = $(jQuery.rup.i18nParse(jQuery.rup.i18n.base, "rup_datatable.templates.detailForm.separator")),
		//     $elementCounter = $(jQuery.jgrid.format(elementCounterTmpl, jqGridID, jQuery.rup.STATICS, jQuery.rup.i18nParse(jQuery.rup.i18n.base, "rup_datatable.numResult"))),
		//     $paginationBar = $(jQuery.jgrid.format(paginationBarTmpl, jqGridID)),
		var $firstPaginationLink = $('#first_' + jqGridID, $template),
		    $backPaginationLink = $('#back_' + jqGridID, $template),
		    $forwardPaginationLink = $('#forward_' + jqGridID, $template),
		    $lastPaginationLink = $('#last_' + jqGridID, $template),
		    extpost = undefined;

		// $paginationBar.append($firstPaginationLink)
		//     .append($backPaginationLink)
		//     .append($forwardPaginationLink)
		//     .append($lastPaginationLink);

		// $pagina

		function doLinkNavigation(linkId, $link) {
			var retNavParams = $.proxy(settings.fncGetNavigationParams, $self)(linkId);
			//Se comprueba el parametro 7 mientras este en convivencia con el rup.datatable el rup.datatable.
			if (retNavParams[7] === undefined && !$link.hasClass('ui-state-disabled')) {
				if ($.proxy($.jgrid.checkUpdates, $self[0])(extpost, function () {
					$.proxy(settings.doNavigation, $self)(retNavParams);
				})) {
					$.proxy(settings.doNavigation, $self)(retNavParams);
				}
			}
		}

		$firstPaginationLink.on('click', function () {
			doLinkNavigation('first', $(this));
		});

		// Elemento anterior
		$backPaginationLink.on('click', function () {
			doLinkNavigation('prev', $(this));
		});

		// Elemento siguiente
		$forwardPaginationLink.on('click', function () {
			doLinkNavigation('next', $(this));
		});

		// Elemento ultimo
		$lastPaginationLink.on('click', function () {
			doLinkNavigation('last', $(this));
		});

		// return $("<div>").append($elementCounter).append($paginationBar).append($separator);
		//
		return $template;
	};

	DatatableBootstrapAdapter.prototype.multifilter = {
		dropdown: {
			dropdownIcon: 'ui-icon-gear',
			dropdownDialogConfig: {
				title: '<i class="fa fa-filter" aria-hidden="true"></i>'
			}
		}

	};

	$.rup = $.rup || {};
	$.rup.adapter = $.rup.adapter || {};

	$.rup.adapter[DatatableBootstrapAdapter.prototype.NAME] = new DatatableBootstrapAdapter();

	return $;
});
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))

/***/ }),
/* 177 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function(jQuery) {var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*global jQuery */
/*global define */

(function (root, factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(2), __webpack_require__(3)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		root.DatatableJQueryUIAdapter = factory(jQuery);
	}
})(undefined, function ($) {

	function DatatableJQueryUIAdapter() {}

	DatatableJQueryUIAdapter.prototype.NAME = 'datatable_jqueryui';

	DatatableJQueryUIAdapter.prototype.CONST = {
		core: {
			operations: {
				defaultOperations: {
					'add': {
						icon: 'fa fa-plus'
					},
					'edit': {
						icon: 'fa fa-pencil-square-o'
					},
					'clone': {
						icon: 'fa fa-clone'
					},
					'delete': {
						icon: 'fa fa-trash-o'
					},
					'reports': {
						icon: 'fa fa-file-o'
					},
					'copyButton': {
						icon: 'fa fa-clipboard'
					}
				}
			}
		}
	};

	DatatableJQueryUIAdapter.prototype.configurePager = function (settings) {
		var $self = this,
		    pagerName,
		    $pagerCenter,
		    pagerLeft,
		    pagerRight;

		if (settings.pager !== undefined && settings.pager !== null) {
			settings.$pager = $(settings.pager.indexOf('#') === 0 ? settings.pager : '#' + settings.pager);
			pagerName = settings.$pager.attr('id');

			settings.$pager.css('height', 'auto'); //Posibilitar redimensionar paginador

			//Añadir clase a cada parte del paginador
			$pagerLeft = $('#' + pagerName + '_left');
			$pagerCenter = $('#' + pagerName + '_center');
			$pagerRight = $('#' + pagerName + '_right');

			$pagerLeft.addClass('pager_left');
			$pagerCenter.addClass('pager_center');
			$pagerRight.addClass('pager_right');

			//pager_left
			//**********
			//Quitar posibles botones del paginador (y dejar la parte izquierda vacía)
			$pagerLeft.html('');

			//Contador de seleccionados
			if (settings.multiselect === true) {
				$pagerLeft.append($('<div/>').addClass('ui-paging-selected').html('0 ' + jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.pager.selected')));
			}

			// Pager center
			jQuery('.pager_center datatable td', settings.$pager).addClass('pagControls');

			// Evento de control de página máxima
			jQuery('.pagControls input.ui-pg-input', $pagerCenter).on('change', function () {
				var pageNum = parseInt($(this).val()),
				    totalNum = parseInt($self.rup_datatable('getGridParam', 'lastpage'));

				if (isNaN(pageNum) === false && pageNum > totalNum) {
					$(this).val(totalNum);
				}
			});

			// Tooltip al combo de selección de número de registros
			jQuery('.pagControls select.ui-pg-selbox', $pagerCenter).attr('title', jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.pager.select')).rup_tooltip();
			// Tooltip al input de selección de página
			jQuery('.pagControls input.ui-pg-input', $pagerCenter).attr('title', jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.pager.input')).rup_tooltip();

			//Cambiar flechas paginación por literales
			jQuery('#first_' + pagerName, $pagerCenter).html($('<a/>').attr('href', 'javascript:void(0)').html(jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.pager.primPag')).addClass('linkPaginacion')).removeClass('ui-pg-button');
			jQuery('#prev_' + pagerName, $pagerCenter).html($('<a/>').attr('href', 'javascript:void(0)').html(jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.pager.anterior')).addClass('linkPaginacion')).removeClass('ui-pg-button');
			jQuery('#next_' + pagerName, $pagerCenter).html($('<a/>').attr('href', 'javascript:void(0)').html(jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.pager.siguiente')).addClass('linkPaginacion')).removeClass('ui-pg-button');
			jQuery('#last_' + pagerName, $pagerCenter).html($('<a/>').attr('href', 'javascript:void(0)').html(jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.pager.ultiPag')).addClass('linkPaginacion')).removeClass('ui-pg-button');
		}
	};

	DatatableJQueryUIAdapter.prototype.createDetailNavigation = function () {
		var $self = $(this),
		    settings = $self.data('settings'),
		    jqGridID = $self.attr('id'),
		    paginationBarTmpl = jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.templates.detailForm.paginationBar'),
		    paginationLinkTmpl = jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.templates.detailForm.paginationLink'),
		    elementCounterTmpl = jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.templates.detailForm.elementCounter'),
		    $separator = $(jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.templates.detailForm.separator')),
		    $elementCounter = $(jQuery.jgrid.format(elementCounterTmpl, jqGridID, jQuery.rup.STATICS, jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.numResult'))),
		    $paginationBar = $(jQuery.jgrid.format(paginationBarTmpl, jqGridID)),
		    $firstPaginationLink = $(jQuery.jgrid.format(paginationLinkTmpl, 'first_' + jqGridID, jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.first'))),
		    $backPaginationLink = $(jQuery.jgrid.format(paginationLinkTmpl, 'back_' + jqGridID, jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.previous'))),
		    $forwardPaginationLink = $(jQuery.jgrid.format(paginationLinkTmpl, 'forward_' + jqGridID, jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.next'))),
		    $lastPaginationLink = $(jQuery.jgrid.format(paginationLinkTmpl, 'last_' + jqGridID, jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.last'))),
		    extpost = undefined;

		$paginationBar.append($firstPaginationLink).append($backPaginationLink).append($forwardPaginationLink).append($lastPaginationLink);

		function doLinkNavigation(linkId, $link) {
			var retNavParams = $.proxy(settings.fncGetNavigationParams, $self)(linkId);
			//Se comprueba el aprametro 7 mientras este en convivencia con el rup.datatable el rup.datatable.
			if (retNavParams[7] !== undefined && !$link.hasClass('ui-state-disabled')) {
				if ($.proxy($.jgrid.checkUpdates, $self[0])(extpost, function () {
					$.proxy(settings.doNavigation, $self)(retNavParams);
				})) {
					$.proxy(settings.doNavigation, $self)(retNavParams);
				}
			}
		}

		// Elemento primero
		$firstPaginationLink.on('click', function () {
			doLinkNavigation('first', $(this));
		});

		// Elemento anterior
		$backPaginationLink.on('click', function () {
			doLinkNavigation('prev', $(this));
		});

		// Elemento siguiente
		$forwardPaginationLink.on('click', function () {
			doLinkNavigation('next', $(this));
		});

		// Elemento ultimo
		$lastPaginationLink.on('click', function () {
			doLinkNavigation('last', $(this));
		});

		return $('<div>').append($elementCounter).append($paginationBar).append($separator);
	};

	DatatableJQueryUIAdapter.prototype.multifilter = {
		dropdown: {
			dropdownIcon: 'ui-icon-gear',
			dropdownDialogConfig: {
				title: '<span class="rup-icon rup-icon-filter"></span>'
			}
		}

	};

	$.rup = $.rup || {};
	$.rup.adapter = $.rup.adapter || {};

	$.rup.adapter[DatatableJQueryUIAdapter.prototype.NAME] = new DatatableJQueryUIAdapter();

	return $;
});
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))

/***/ }),
/* 178 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*global jQuery */
/*global define */

(function (root, factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(2), __webpack_require__(3)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		root.DateBootstrapAdapter = factory(jQuery);
	}
})(undefined, function ($) {

	function DateBootstrapAdapter() {}

	DateBootstrapAdapter.prototype.NAME = 'date_bootstrap';

	DateBootstrapAdapter.prototype.initIconTrigger = function (settings) {
		//Imagen del calendario
		//settings.buttonImage = $.rup.STATICS + (settings.buttonImage ? settings.buttonImage : "/rup/css/images/calendario.png");
		settings.buttonText = '<i class="fa fa-calendar" aria-hidden="true"></i>';
		//Atributos NO MODIFICABLES
		//La imagen no debe ser un botón
		settings.buttonImageOnly = false;
		//Solo permitir caracteres permitidos en la máscara
		settings.constrainInput = true;
		//Mostrar patrón con foco en input y pinchando imagen
		settings.showOn = 'both';
	};

	DateBootstrapAdapter.prototype.postConfigure = function (settings) {
		var $self = this,
		    data = $self.data('datepicker'),
		    $input = data.input,
		    $trigger = data.trigger,
		    $div;

		$div = $('<div>').addClass('rup-date-input-group');
		$input.add($trigger).wrapAll($div);
	};

	$.rup = $.rup || {};
	$.rup.adapter = $.rup.adapter || {};

	$.rup.adapter[DateBootstrapAdapter.prototype.NAME] = new DateBootstrapAdapter();

	return $;
});

/***/ }),
/* 179 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*global jQuery */
/*global define */

(function (root, factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(2), __webpack_require__(3)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		root.FeedbackBootstrapAdapter = factory(jQuery);
	}
})(undefined, function ($) {

	function FeedbackBootstrapAdapter() {}

	FeedbackBootstrapAdapter.prototype.NAME = 'feedback_bootstrap';

	FeedbackBootstrapAdapter.prototype.classComponent = function () {
		return 'rup-bootstrap';
	};

	FeedbackBootstrapAdapter.prototype.closeLiteral = function () {
		return '';
	};

	$.rup = $.rup || {};
	$.rup.adapter = $.rup.adapter || {};

	$.rup.adapter[FeedbackBootstrapAdapter.prototype.NAME] = new FeedbackBootstrapAdapter();

	return $;
});

/***/ }),
/* 180 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*global jQuery */
/*global define */

(function (root, factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(2), __webpack_require__(3)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		root.FeedbackJQueryUIAdapter = factory(jQuery);
	}
})(undefined, function ($) {

	function FeedbackJQueryUIAdapter() {}

	FeedbackJQueryUIAdapter.prototype.NAME = 'feedback_jqueryui';

	FeedbackJQueryUIAdapter.prototype.classComponent = function () {
		return 'rup-jqueryui';
	};

	FeedbackJQueryUIAdapter.prototype.closeLiteral = function () {
		return $.rup.i18nParse($.rup.i18n.base, 'rup_global.cerrar');
	};

	$.rup = $.rup || {};
	$.rup.adapter = $.rup.adapter || {};

	$.rup.adapter[FeedbackJQueryUIAdapter.prototype.NAME] = new FeedbackJQueryUIAdapter();

	return $;
});

/***/ }),
/* 181 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function(jQuery) {var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*global jQuery */
/*global define */

(function (root, factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(3), __webpack_require__(2)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		root.TableBootstrapAdapter = factory(jQuery);
	}
})(undefined, function ($, Rup) {

	function TableBootstrapAdapter() {}

	TableBootstrapAdapter.prototype.NAME = 'table_bootstrap';

	TableBootstrapAdapter.prototype.CONST = {
		core: {
			operations: {
				defaultOperations: {
					'add': {
						icon: 'fa fa-file-o'
					},
					'save': {
						icon: 'fa fa fa-floppy-o'
					},
					'edit': {
						icon: 'fa fa-pencil-square-o'
					},
					'clone': {
						icon: 'fa fa-clone'
					},
					'delete': {
						icon: 'fa fa-trash-o'
					},
					'cancel': {
						icon: 'fa fa-times-circle'
					}
				}
			}
		}
	};

	TableBootstrapAdapter.prototype.configurePager = function (settings) {
		var $self = this,
		    pagerName,
		    $pagerCenter,
		    pagerLeft,
		    pagerRight,
		    $pagerLeft,
		    $pagerCenter,
		    $pagerRight;

		if (settings.pager !== undefined && settings.pager !== null) {
			settings.$pager = $(settings.pager.indexOf('#') === 0 ? settings.pager : '#' + settings.pager);
			pagerName = settings.$pager.attr('id');

			settings.$pager.css('height', 'auto'); //Posibilitar redimensionar paginador

			//Añadir clase a cada parte del paginador
			$pagerLeft = $('#' + pagerName + '_left');
			$pagerCenter = $('#' + pagerName + '_center');
			$pagerRight = $('#' + pagerName + '_right');

			$pagerLeft.addClass('pager_left');
			$pagerCenter.addClass('pager_center');
			$pagerRight.addClass('pager_right');

			//pager_left
			//**********
			//Quitar posibles botones del paginador (y dejar la parte izquierda vacía)
			$pagerLeft.html('');

			//Contador de seleccionados
			if (settings.multiselect === true) {
				$pagerLeft.append($('<div/>').addClass('ui-paging-selected').html('0 ' + jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_table.pager.selected')));
			}

			// Pager center
			$pagerCenter.css('white-space', 'inherit');
			jQuery('.pager_center table td', settings.$pager).addClass('pagControls');

			// Evento de control de página máxima
			jQuery('.pagControls input.ui-pg-input', $pagerCenter).on('change', function () {
				var pageNum = parseInt($(this).val()),
				    totalNum = parseInt($self.rup_table('getGridParam', 'lastpage'));

				if (isNaN(pageNum) === false && pageNum > totalNum) {
					$(this).val(totalNum);
				}
			});

			// Tooltip al combo de selección de número de registros
			jQuery('.pagControls select.ui-pg-selbox', $pagerCenter).attr('title', jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_table.pager.select')).rup_tooltip();
			// Tooltip al input de selección de página
			jQuery('.pagControls input.ui-pg-input', $pagerCenter).attr('title', jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_table.pager.input')).rup_tooltip();

			var pagerLinkTemplate = Rup.Templates.rup.table.pager.link.bootstrap;

			//Cambiar flechas paginación por literales
			jQuery('#first_' + pagerName, $pagerCenter).html(pagerLinkTemplate({
				label: jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_table.pager.primPag'),
				icon: 'fa fa-angle-double-left'
			})).removeClass('ui-pg-button');

			jQuery('#prev_' + pagerName, $pagerCenter).html(pagerLinkTemplate({
				label: jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_table.pager.anterior'),
				icon: 'fa fa-angle-left'
			})).removeClass('ui-pg-button');
			jQuery('#next_' + pagerName, $pagerCenter).html(pagerLinkTemplate({
				label: jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_table.pager.siguiente'),
				icon: 'fa fa-angle-right'
			})).removeClass('ui-pg-button');
			jQuery('#last_' + pagerName, $pagerCenter).html(pagerLinkTemplate({
				label: jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_table.pager.ultiPag'),
				icon: 'fa fa-angle-double-right'
			})).removeClass('ui-pg-button');
		}
	};

	TableBootstrapAdapter.prototype.createDetailNavigation = function () {

		var $self = $(this),
		    settings = $self.data('settings'),
		    jqGridID = $self.attr('id');
		var $template = $(Rup.Templates.rup.table.detail.navigation.bootstrap({
			tableId: $self.prop('id'),
			resultNumText: jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_table.numResult'),
			labelFirst: jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_table.first'),
			labelPrev: jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_table.previous'),
			labelNext: jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_table.next'),
			labelLast: jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_table.last')

		}));

		// var $self = $(this),
		//     settings = $self.data("settings"),
		//     jqGridID = $self.attr("id"),
		//     paginationBarTmpl = jQuery.rup.i18nParse(jQuery.rup.i18n.base, "rup_table.templates.detailForm.paginationBar"),
		//     paginationLinkTmpl = jQuery.rup.i18nParse(jQuery.rup.i18n.base, "rup_table.templates.detailForm.paginationLink"),
		//     elementCounterTmpl = jQuery.rup.i18nParse(jQuery.rup.i18n.base, "rup_table.templates.detailForm.elementCounter"),
		//     $separator = $(jQuery.rup.i18nParse(jQuery.rup.i18n.base, "rup_table.templates.detailForm.separator")),
		//     $elementCounter = $(jQuery.jgrid.format(elementCounterTmpl, jqGridID, jQuery.rup.STATICS, jQuery.rup.i18nParse(jQuery.rup.i18n.base, "rup_table.numResult"))),
		//     $paginationBar = $(jQuery.jgrid.format(paginationBarTmpl, jqGridID)),
		var $firstPaginationLink = $('#first_' + jqGridID, $template),
		    $backPaginationLink = $('#back_' + jqGridID, $template),
		    $forwardPaginationLink = $('#forward_' + jqGridID, $template),
		    $lastPaginationLink = $('#last_' + jqGridID, $template),
		    extpost = undefined;

		// $paginationBar.append($firstPaginationLink)
		//     .append($backPaginationLink)
		//     .append($forwardPaginationLink)
		//     .append($lastPaginationLink);

		// $pagina

		function doLinkNavigation(linkId, $link) {
			var retNavParams = $.proxy(settings.fncGetNavigationParams, $self)(linkId);
			//mientras este en convivencia se mira el parametro para rup.table(entrar) y rup.datatable
			if (retNavParams !== undefined && retNavParams[7] === undefined) {
				if ($.proxy($.jgrid.checkUpdates, $self[0])(extpost, function () {
					$.proxy(settings.doNavigation, $self)(retNavParams);
				})) {
					$.proxy(settings.doNavigation, $self)(retNavParams);
				}
			}
		}

		$firstPaginationLink.on('click', function () {
			doLinkNavigation('first', $(this));
		});

		// Elemento anterior
		$backPaginationLink.on('click', function () {
			doLinkNavigation('prev', $(this));
		});

		// Elemento siguiente
		$forwardPaginationLink.on('click', function () {
			doLinkNavigation('next', $(this));
		});

		// Elemento ultimo
		$lastPaginationLink.on('click', function () {
			doLinkNavigation('last', $(this));
		});

		// return $("<div>").append($elementCounter).append($paginationBar).append($separator);
		//
		return $template;
	};

	TableBootstrapAdapter.prototype.multifilter = {
		dropdown: {
			dropdownIcon: 'ui-icon-gear',
			dropdownDialogConfig: {
				title: '<i class="fa fa-filter" aria-hidden="true"></i>'
			}
		}

	};

	$.rup = $.rup || {};
	$.rup.adapter = $.rup.adapter || {};

	$.rup.adapter[TableBootstrapAdapter.prototype.NAME] = new TableBootstrapAdapter();

	return $;
});
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))

/***/ }),
/* 182 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function(jQuery) {var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*global jQuery */
/*global define */

(function (root, factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(2), __webpack_require__(3)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		root.TableJQueryUIAdapter = factory(jQuery);
	}
})(undefined, function ($) {

	function TableJQueryUIAdapter() {}

	TableJQueryUIAdapter.prototype.NAME = 'table_jqueryui';

	TableJQueryUIAdapter.prototype.CONST = {
		core: {
			operations: {
				defaultOperations: {
					'add': {
						icon: 'ui-icon rup-icon rup-icon-new'
					},
					'save': {
						icon: 'ui-icon rup-icon rup-icon-save'
					},
					'edit': {
						icon: 'ui-icon rup-icon rup-icon-edit'
					},
					'clone': {
						icon: 'ui-icon rup-icon rup-icon-clone'
					},
					'delete': {
						icon: 'ui-icon rup-icon rup-icon-delete'
					},
					'cancel': {
						icon: 'ui-icon rup-icon rup-icon-cancel'
					}
				}
			}
		}
	};

	TableJQueryUIAdapter.prototype.configurePager = function (settings) {
		var $self = this,
		    pagerName,
		    $pagerCenter,
		    pagerLeft,
		    pagerRight;

		if (settings.pager !== undefined && settings.pager !== null) {
			settings.$pager = $(settings.pager.indexOf('#') === 0 ? settings.pager : '#' + settings.pager);
			pagerName = settings.$pager.attr('id');

			settings.$pager.css('height', 'auto'); //Posibilitar redimensionar paginador

			//Añadir clase a cada parte del paginador
			$pagerLeft = $('#' + pagerName + '_left');
			$pagerCenter = $('#' + pagerName + '_center');
			$pagerRight = $('#' + pagerName + '_right');

			$pagerLeft.addClass('pager_left');
			$pagerCenter.addClass('pager_center');
			$pagerRight.addClass('pager_right');

			//pager_left
			//**********
			//Quitar posibles botones del paginador (y dejar la parte izquierda vacía)
			$pagerLeft.html('');

			//Contador de seleccionados
			if (settings.multiselect === true) {
				$pagerLeft.append($('<div/>').addClass('ui-paging-selected').html('0 ' + jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_table.pager.selected')));
			}

			// Pager center
			jQuery('.pager_center table td', settings.$pager).addClass('pagControls');

			// Evento de control de página máxima
			jQuery('.pagControls input.ui-pg-input', $pagerCenter).on('change', function () {
				var pageNum = parseInt($(this).val()),
				    totalNum = parseInt($self.rup_table('getGridParam', 'lastpage'));

				if (isNaN(pageNum) === false && pageNum > totalNum) {
					$(this).val(totalNum);
				}
			});

			// Tooltip al combo de selección de número de registros
			jQuery('.pagControls select.ui-pg-selbox', $pagerCenter).attr('title', jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_table.pager.select')).rup_tooltip();
			// Tooltip al input de selección de página
			jQuery('.pagControls input.ui-pg-input', $pagerCenter).attr('title', jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_table.pager.input')).rup_tooltip();

			//Cambiar flechas paginación por literales
			jQuery('#first_' + pagerName, $pagerCenter).html($('<a/>').attr('href', 'javascript:void(0)').html(jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_table.pager.primPag')).addClass('linkPaginacion')).removeClass('ui-pg-button');
			jQuery('#prev_' + pagerName, $pagerCenter).html($('<a/>').attr('href', 'javascript:void(0)').html(jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_table.pager.anterior')).addClass('linkPaginacion')).removeClass('ui-pg-button');
			jQuery('#next_' + pagerName, $pagerCenter).html($('<a/>').attr('href', 'javascript:void(0)').html(jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_table.pager.siguiente')).addClass('linkPaginacion')).removeClass('ui-pg-button');
			jQuery('#last_' + pagerName, $pagerCenter).html($('<a/>').attr('href', 'javascript:void(0)').html(jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_table.pager.ultiPag')).addClass('linkPaginacion')).removeClass('ui-pg-button');
		}
	};

	TableJQueryUIAdapter.prototype.createDetailNavigation = function () {
		var $self = $(this),
		    settings = $self.data('settings'),
		    jqGridID = $self.attr('id'),
		    paginationBarTmpl = jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_table.templates.detailForm.paginationBar'),
		    paginationLinkTmpl = jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_table.templates.detailForm.paginationLink'),
		    elementCounterTmpl = jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_table.templates.detailForm.elementCounter'),
		    $separator = $(jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_table.templates.detailForm.separator')),
		    $elementCounter = $(jQuery.jgrid.format(elementCounterTmpl, jqGridID, jQuery.rup.STATICS, jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_table.numResult'))),
		    $paginationBar = $(jQuery.jgrid.format(paginationBarTmpl, jqGridID)),
		    $firstPaginationLink = $(jQuery.jgrid.format(paginationLinkTmpl, 'first_' + jqGridID, jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_table.first'))),
		    $backPaginationLink = $(jQuery.jgrid.format(paginationLinkTmpl, 'back_' + jqGridID, jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_table.previous'))),
		    $forwardPaginationLink = $(jQuery.jgrid.format(paginationLinkTmpl, 'forward_' + jqGridID, jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_table.next'))),
		    $lastPaginationLink = $(jQuery.jgrid.format(paginationLinkTmpl, 'last_' + jqGridID, jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_table.last'))),
		    extpost = undefined;

		$paginationBar.append($firstPaginationLink).append($backPaginationLink).append($forwardPaginationLink).append($lastPaginationLink);

		function doLinkNavigation(linkId, $link) {
			var retNavParams = $.proxy(settings.fncGetNavigationParams, $self)(linkId);
			if ($.proxy($.jgrid.checkUpdates, $self[0])(extpost, function () {
				$.proxy(settings.doNavigation, $self)(retNavParams);
			})) {
				$.proxy(settings.doNavigation, $self)(retNavParams);
			}
		}

		// Elemento primero
		$firstPaginationLink.on('click', function () {
			doLinkNavigation('first', $(this));
		});

		// Elemento anterior
		$backPaginationLink.on('click', function () {
			doLinkNavigation('prev', $(this));
		});

		// Elemento siguiente
		$forwardPaginationLink.on('click', function () {
			doLinkNavigation('next', $(this));
		});

		// Elemento ultimo
		$lastPaginationLink.on('click', function () {
			doLinkNavigation('last', $(this));
		});

		return $('<div>').append($elementCounter).append($paginationBar).append($separator);
	};

	TableJQueryUIAdapter.prototype.multifilter = {
		dropdown: {
			dropdownIcon: 'ui-icon-gear',
			dropdownDialogConfig: {
				title: '<span class="rup-icon rup-icon-filter"></span>'
			}
		}

	};

	$.rup = $.rup || {};
	$.rup.adapter = $.rup.adapter || {};

	$.rup.adapter[TableJQueryUIAdapter.prototype.NAME] = new TableJQueryUIAdapter();

	return $;
});
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))

/***/ }),
/* 183 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*global jQuery */
/*global define */

(function (root, factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(2), __webpack_require__(3)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		root.TimeBootstrapAdapter = factory(jQuery);
	}
})(undefined, function ($) {

	function TimeBootstrapAdapter() {}

	TimeBootstrapAdapter.prototype.NAME = 'time_bootstrap';

	TimeBootstrapAdapter.prototype.initIconTrigger = function (settings) {
		var $self = this,
		    $div,
		    $button,
		    $icon;

		if (!$self.is('div')) {

			$div = $('<div>').addClass('rup-time-input-group');
			$button = $('<button>').attr('type', 'button').addClass('ui-timepicker-trigger');
			$icon = $('<i>').attr('aria-hidden', 'true').addClass('fa fa-clock-o');

			$button.append($icon);

			$self.wrap($div);
			$button.insertAfter($self);

			$button.on('click', function () {
				if ($('#ui-datepicker-div').css('display') === 'none') {
					$self.timepicker('show');
				} else {
					$self.timepicker('hide');
				}
			});

			// $("<img>").addClass("ui-timepicker-trigger")
			//   .attr({
			//     "src":settings.buttonImage,
			//     "alt":$.rup.i18nParse($.rup.i18n.base,"rup_time.buttonText"),
			//     "title":$.rup.i18nParse($.rup.i18n.base,"rup_time.buttonText")
			//   })
			// .click(function(){
			//   if ( $("#ui-datepicker-div").css("display")==="none"){
			//     $self.timepicker("show");
			//   } else {
			//     $self.timepicker("hide");
			//   }
			// })
			// .insertAfter($self);
		}
	};

	$.rup = $.rup || {};
	$.rup.adapter = $.rup.adapter || {};

	$.rup.adapter[TimeBootstrapAdapter.prototype.NAME] = new TimeBootstrapAdapter();

	return $;
});

/***/ }),
/* 184 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*global jQuery */
/*global define */

(function (root, factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(2), __webpack_require__(3)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		root.TimeJQueryUIAdapter = factory(jQuery);
	}
})(undefined, function ($) {

	function TimeJQueryUIAdapter() {}

	TimeJQueryUIAdapter.prototype.NAME = 'time_jqueryui';

	TimeJQueryUIAdapter.prototype.initIconTrigger = function (settings) {
		var $self = this;
		if (!$self.is('div')) {

			$('<img>').addClass('ui-timepicker-trigger').attr({
				'src': settings.buttonImage,
				'alt': $.rup.i18nParse($.rup.i18n.base, 'rup_time.buttonText'),
				'title': $.rup.i18nParse($.rup.i18n.base, 'rup_time.buttonText')
			}).click(function () {
				if ($('#ui-datepicker-div').css('display') === 'none') {
					$self.timepicker('show');
				} else {
					$self.timepicker('hide');
				}
			}).insertAfter($self);
		}
	};

	TimeJQueryUIAdapter.prototype.postConfigure = function (settings) {};

	$.rup = $.rup || {};
	$.rup.adapter = $.rup.adapter || {};

	$.rup.adapter[TimeJQueryUIAdapter.prototype.NAME] = new TimeJQueryUIAdapter();

	return $;
});

/***/ }),
/* 185 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*global jQuery */
/*global define */

(function (root, factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(3), __webpack_require__(2)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		root.ToolbarBootstrapAdapter = factory(jQuery);
	}
})(undefined, function ($, Rup) {

	function ToolbarBootstrapAdapter() {}

	ToolbarBootstrapAdapter.prototype.NAME = 'toolbar_bootstrap';

	ToolbarBootstrapAdapter.prototype.addButton = function (obj, json_i18n) {
		var buttonId, rightObjects;

		// Se obtiene el identificador del boton. En caso de no haberse indicado un valor en la propiedad id, se toma el valor de la propiedad i18nCaption.
		if (obj.id) {
			buttonId = obj.id;
		} else {
			buttonId = obj.i18nCaption;
		}

		// Se comprueba si el id del boton contiene el identificador de la botonera. En caso de no existir se añade al principio.
		if (buttonId.indexOf($(this).attr('id')) !== 0) {
			buttonId = $(this).attr('id') + '##' + buttonId;
		}

		// var boton = $("<button type='button'/>").text($.rup.i18nParse(json_i18n,obj.i18nCaption)).addClass("rup-toolbar_button").attr({
		//   "id":buttonId
		// });

		var boton = $(Rup.Templates.rup.toolbar.button.bootstrap({
			id: buttonId,
			css: obj.css,
			label: obj.text ? obj.text : $.rup.i18nParse(json_i18n, obj.i18nCaption)
		}));
		boton.rup_button(obj);
		// boton.button("option", "icons", {primary:obj.css, secondary:null} );

		// if(obj.right !== undefined && obj.right === true){
		//   boton.addClass("rup-button-right");
		// }


		// Si fuera necesario, se añade el estilo para la ubicación derecha y se gestiona su indexado
		if (obj.right !== undefined && obj.right === true) {
			//Añadir botón a la derecha
			var $div_rightObjects = this.children('div:not(.rup-dropdown-btn-group):not(.rup-mbutton )');
			if ($div_rightObjects.length === 0) {
				$div_rightObjects = $('<div />').attr('id', this.attr('id') + '-rightButtons').css('float', 'right');
				this.append($div_rightObjects);
			}
			//				if (boton.parent().is(".rup-dropdown-btn-group")){
			//					boton.parent().prependTo($div_rightObjects);
			//				}else{
			boton.prependTo($div_rightObjects);
			//				}
		} else {
			if (boton.parent().is('.rup-dropdown-btn-group')) {
				$(this).append(boton.parent());
			} else {
				$(this).append(boton);
			}
		}

		//Añadir evento keydown
		this._setKeyDown(boton);

		// Al perder el foco se elimina el estilo de disponer del foco
		boton.bind('focusout', function () {
			$(this).removeClass('ui-state-focus');
		});

		return boton;
	};

	ToolbarBootstrapAdapter.prototype.addMButton = function (obj, json_i18n) {
		//añade a la toolbar un 'mbutton' (sin botones)
		var botonGrp,
		    boton = '',
		    buttonId;
		if (obj.id === undefined) {
			alert('El atributo ID es obligatorio en los MButtons.');
			boton = null;
		} else {
			buttonId = obj.id;
			// Se comprueba si el id del boton contiene el identificador de la botonera. En caso de no existir se añade al principio.
			if (buttonId.indexOf($(this).attr('id')) !== 0) {
				buttonId = $(this).attr('id') + '##' + obj.id;
			}

			botonGrp = $(Rup.Templates.rup.toolbar.mbutton.bootstrap({

				id: buttonId,
				css: obj.css,
				groupClasses: obj.groupClasses,
				label: obj.text ? obj.text : $.rup.i18nParse(json_i18n, obj.i18nCaption)
			}));

			boton = botonGrp.find('[id=\'' + buttonId + '\']');
			//Si no se define un estilo especial se aplica por defecto
			if (obj.css === undefined) {
				obj.css = 'rup-toolbar_menuButtonIcon';
			}
			boton.rup_button();
		}

		// if(obj.right !== undefined && obj.right === true){
		//   botonGrp.addClass("rup-button-right");
		// }

		// Si fuera necesario, se añade el estilo para la ubicación derecha y se gestiona su indexado
		if (obj.right !== undefined && obj.right === true) {
			//Añadir botón a la derecha
			var $div_rightObjects = this.children('div:not(.rup-dropdown-btn-group):not(.rup-mbutton )');
			if ($div_rightObjects.length === 0) {
				$div_rightObjects = $('<div />').attr('id', this.attr('id') + '-rightButtons').css('float', 'right');
				this.append($div_rightObjects);
			}
			botonGrp.prependTo($div_rightObjects);
		} else {
			$(this).append(botonGrp);
		}

		//Añadir evento keydown
		this._setKeyDown(boton);

		if (obj.click) {
			//Añadir eventos
			boton.click({ i18nCaption: obj.i18nCaption }, obj.click);
		}
		return botonGrp;
	};

	ToolbarBootstrapAdapter.prototype.addButtonsToMButton = function (buttons, menuButton, json_i18n) {
		//añade botones al 'mbutton'
		var div,
		    ul,

		//numero de botones a añadir
		length = buttons.length,
		    boton,
		    buttonId;
		//
		// if ($("[id='mbutton_"+menuButton.attr("id")+"']").length === 0){
		//   //Contenedor del menuButton
		//   div = $('<div>')
		//       .addClass("ui-widget ui-widget-content rup-toolbar_menuButtonContainer")
		//       .attr("id","mbutton_"+menuButton[0].id)
		//       .css("display","none");
		//   //Lista no numerada del menuButton
		//   ul = $('<ul>')
		//       .attr("role","menu")
		//       .attr("aria-activedescendant","active-menuitem")
		//       .attr("aria-labelledby","active-menuitem");
		// } else {
		//   div = $("[id='mbutton_"+menuButton.attr("id")+"']");
		//   ul = div.children("ul");
		// }
		//
		// menuButton.attr("href","#");

		//Se añaden cada uno de los botones del menuButton
		ul = menuButton.find('ul');
		for (var i = length; i--;) {

			boton = buttons[i];
			if (boton.id) {
				buttonId = menuButton.attr('id') + '##' + boton.id;
			} else {
				buttonId = menuButton.attr('id') + '##' + boton.i18nCaption;
			}
			buttons[i].id = buttonId;

			ul.prepend($('<li>').append(this.addButton(buttons[i], json_i18n)));
		}

		//Añadir elementos al DOM
		// if(!$.rup_utils.aplicatioInPortal()){
		//   div.appendTo("body");
		//   div.append(ul);
		// } else {
		//   div.append(ul);
		//   $(".r01gContainer").append(div);
		// }

		//Borrar referencias
	};

	$.rup = $.rup || {};
	$.rup.adapter = $.rup.adapter || {};

	$.rup.adapter[ToolbarBootstrapAdapter.prototype.NAME] = new ToolbarBootstrapAdapter();

	return $;
});

/***/ }),
/* 186 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*global jQuery */
/*global define */

(function (root, factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(2), __webpack_require__(3)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		root.ToolbarJQueryUIAdapter = factory(jQuery);
	}
})(undefined, function ($) {

	function ToolbarJQueryUIAdapter() {}

	ToolbarJQueryUIAdapter.prototype.NAME = 'toolbar_jqueryui';

	ToolbarJQueryUIAdapter.prototype.addButton = function (obj, json_i18n) {
		//añade a la toolbar un 'button'

		var buttonId, rightObjects;

		// Se obtiene el identificador del boton. En caso de no haberse indicado un valor en la propiedad id, se toma el valor de la propiedad i18nCaption.
		if (obj.id) {
			buttonId = obj.id;
		} else {
			buttonId = obj.i18nCaption;
		}

		// Se comprueba si el id del boton contiene el identificador de la botonera. En caso de no existir se añade al principio.
		if (buttonId.indexOf($(this).attr('id')) !== 0) {
			buttonId = $(this).attr('id') + '##' + buttonId;
		}

		var boton = $('<button type=\'button\'/>').text($.rup.i18nParse(json_i18n, obj.i18nCaption)).addClass('rup-toolbar_button').attr({
			'id': buttonId
		});

		boton.rup_button(obj);
		boton.button('option', 'icons', { primary: obj.css, secondary: null });

		// Si fuera necesario, se añade el estilo para la ubicación derecha y se gestiona su indexado
		if (obj.right !== undefined && obj.right === true) {
			//Añadir botón a la derecha
			var $div_rightObjects = this.children('div:not(.rup-dropdown-btn-group)');
			if ($div_rightObjects.length === 0) {
				$div_rightObjects = $('<div />').attr('id', this.attr('id') + '-rightButtons').css('float', 'right');
				this.append($div_rightObjects);
			}
			//				if (boton.parent().is(".rup-dropdown-btn-group")){
			//					boton.parent().prependTo($div_rightObjects);
			//				}else{
			boton.prependTo($div_rightObjects);
			//				}
		} else {
			if (boton.parent().is('.rup-dropdown-btn-group')) {
				$(this).append(boton.parent());
			} else {
				$(this).append(boton);
			}
		}

		//Añadir evento keydown
		this._setKeyDown(boton);

		// Al perder el foco se elimina el estilo de disponer del foco
		boton.bind('focusout', function () {
			$(this).removeClass('ui-state-focus');
		});

		return boton;
	};

	ToolbarJQueryUIAdapter.prototype.addMButton = function (obj, json_i18n) {
		//añade a la toolbar un 'mbutton' (sin botones)
		var boton = '',
		    buttonId;
		if (obj.id === undefined) {
			alert('El atributo ID es obligatorio en los MButtons.');
			boton = null;
		} else {
			buttonId = obj.id;
			// Se comprueba si el id del boton contiene el identificador de la botonera. En caso de no existir se añade al principio.
			if (buttonId.indexOf($(this).attr('id')) !== 0) {
				buttonId = $(this).attr('id') + '##' + obj.id;
			}

			boton = $('<a/>').attr('id', buttonId).text($.rup.i18nParse(json_i18n, obj.i18nCaption)).addClass('rup-toolbar_menuButton');
			//Si no se define un estilo especial se aplica por defecto
			if (obj.css === undefined) {
				obj.css = 'rup-toolbar_menuButtonIcon';
			}
			boton.button().button('option', 'icons', { primary: null, secondary: obj.css });
		}

		// Si fuera necesario, se añade el estilo para la ubicación derecha y se gestiona su indexado
		if (obj.right !== undefined && obj.right === true) {
			//Añadir botón a la derecha
			var $div_rightObjects = this.children('div:not(.rup-dropdown-btn-group)');
			if ($div_rightObjects.length === 0) {
				$div_rightObjects = $('<div />').attr('id', this.attr('id') + '-rightButtons').css('float', 'right');
				this.append($div_rightObjects);
			}
			boton.prependTo($div_rightObjects);
		} else {
			$(this).append(boton);
		}

		//Añadir evento keydown
		this._setKeyDown(boton);

		if (obj.click) {
			//Añadir eventos
			boton.click({ i18nCaption: obj.i18nCaption }, obj.click);
		}
		return boton;
	};

	ToolbarJQueryUIAdapter.prototype.addButtonsToMButton = function (buttons, menuButton, json_i18n) {
		//añade botones al 'mbutton'
		var div,
		    ul,

		//numero de botones a añadir
		length = buttons.length,
		    boton,
		    buttonId;

		if ($('[id=\'mbutton_' + menuButton.attr('id') + '\']').length === 0) {
			//Contenedor del menuButton
			div = $('<div>').addClass('ui-widget ui-widget-content rup-toolbar_menuButtonContainer').attr('id', 'mbutton_' + menuButton[0].id).css('display', 'none');
			//Lista no numerada del menuButton
			ul = $('<ul>').attr('role', 'menu').attr('aria-activedescendant', 'active-menuitem').attr('aria-labelledby', 'active-menuitem');
		} else {
			div = $('[id=\'mbutton_' + menuButton.attr('id') + '\']');
			ul = div.children('ul');
		}

		menuButton.attr('href', '#');

		//Se añaden cada uno de los botones del menuButton
		for (var i = length; i--;) {

			boton = buttons[i];
			if (boton.id) {
				buttonId = menuButton.attr('id') + '##' + boton.id;
			} else {
				buttonId = menuButton.attr('id') + '##' + boton.i18nCaption;
			}
			buttons[i].id = buttonId;

			ul.prepend($('<li>').css('display', 'block').append(this.addButton(buttons[i], json_i18n).addClass('rup-toolbar_menuButtonElement')));
		}

		//Añadir elementos al DOM
		if (!$.rup_utils.aplicatioInPortal()) {
			div.appendTo('body');
			div.append(ul);
		} else {
			div.append(ul);
			$('.r01gContainer').append(div);
		}
	};

	$.rup = $.rup || {};
	$.rup.adapter = $.rup.adapter || {};

	$.rup.adapter[ToolbarJQueryUIAdapter.prototype.NAME] = new ToolbarJQueryUIAdapter();

	return $;
});

/***/ }),
/* 187 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*global jQuery */
/*global define */

(function (root, factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(3), __webpack_require__(2)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		root.UploadBootstrapAdapter = factory(jQuery);
	}
})(undefined, function ($, Rup) {

	function UploadBootstrapAdapter() {}

	UploadBootstrapAdapter.prototype.NAME = 'upload_bootstrap';

	UploadBootstrapAdapter.prototype.processdone = function (e, data) {
		//$(e.target).find('.start').removeAttr('disabled');
	};

	UploadBootstrapAdapter.prototype.downloadTemplate = function (o) {
		var that = this,
		    rows = $(),
		    files = o.files,
		    options = o.options;
		rows = $('<ul>').addClass('list-group');

		return Rup.Templates.rup.upload.downloadTemplate({
			files: files
		});
	};

	UploadBootstrapAdapter.prototype.uploadTemplate = function (o) {
		var that = this,
		    rows = $(),
		    files = o.files,
		    options = o.options;

		return Rup.Templates.rup.upload.uploadTemplate({
			files: files,
			submitInForm: options.submitInForm === true ? true : undefined,
			notSubmitInForm: !(options.submitInForm === true ? true : undefined)
		});
	};

	$.rup = $.rup || {};
	$.rup.adapter = $.rup.adapter || {};

	$.rup.adapter[UploadBootstrapAdapter.prototype.NAME] = new UploadBootstrapAdapter();

	return $;
});

/***/ }),
/* 188 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*global jQuery */
/*global define */

(function (root, factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(2)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		root.UploadJQueryUIAdapter = factory(jQuery);
	}
})(undefined, function ($) {

	function UploadJQueryUIAdapter() {}

	UploadJQueryUIAdapter.prototype.NAME = 'upload_jqueryui';

	UploadJQueryUIAdapter.prototype.processdone = function (e, data) {
		$(e.target).find('.start').button('enable');
	};

	UploadJQueryUIAdapter.prototype.downloadTemplate = function (o) {
		var that = this,
		    rows = $(),
		    files = o.files,
		    options = o.options;
		$.each(files, function (index, file) {
			// file = that._downloadTemplateHelper(file);
			var row = $('<tr class="template-download"><td>' + (file.error ? '<td class="file_icon"></td>' + '<td class="name"></td>' + '<td class="size"></td>' + '<td class="error" colspan="2"></td>' : '<div class="formulario_columna_cnt">' + '<span class="izq_float file_icon">&nbsp;</span>' + '<div class="izq_float name"><a></a></div>' + '</div>' + '<div class="formulario_columna_cnt">' + '<div class="izq_float type"></div>' + '<div class="izq_float size"></div>' + '</div>' + '<div class="formulario_columna_cnt">' + '<a><div class="izq_float">' + '<div class="file_download" >' + '<span class="file_download_icon">&nbsp;</span>' + '<span class="file_download_text">' + $.rup.i18nParse($.rup.i18n.base, 'rup_upload.openUploaded') + '</span></div>' + '</div></a>' + '<div class="izq_float delete"><button>' + $.rup.i18nParse($.rup.i18n.base, 'rup_upload.deleteUploaded') + '</button></div>' + '</div>') + '</td></tr>');

			row.find('.size').text(file.sizef);
			row.find('.type').text(file.type);
			if (file.error) {
				row.find('.name').text(file.name);
				row.addClass('ui-state-error');
				row.find('.error').text(options.errorMessages[file.error] || file.error);
			} else {
				row.find('.name a').text(file.name);
				if (file.thumbnail_url) {
					row.find('.preview').append('<a><img></a>').find('img').prop('src', file.thumbnail_url);
					row.find('a').prop('target', '_blank');
				}
				row.find('a').prop('href', $.rup_utils.setNoPortalParam(file.url));
				row.find('.delete button').attr('data-type', file.delete_type).attr('data-url', $.rup_utils.setNoPortalParam(file.delete_url));
			}
			rows = rows.add(row);
		});
		return rows;
	};

	UploadJQueryUIAdapter.prototype.uploadTemplate = function (o) {
		var that = this,
		    rows = $(),
		    files = o.files,
		    options = o.options;

		// var settings = $.data(this.element[0], "settings");


		$.each(files, function (index, file) {
			// file = that._uploadTemplateHelper(file);
			var row = $('<tr class="template-upload"><td>' + '<div class="formulario_columna_cnt">' + '<span class="izq_float file_icon">&nbsp;</span>' + '<div class="izq_float name"><b></b></div>' + '<div class="formulario_columna_cnt">' + '<div class="izq_float type"></div>' + '<div class="izq_float size"></div>' + (options.submitInForm ? '<div class="izq_float cancel" style><button>' + $.rup.i18nParse($.rup.i18n.base, 'rup_upload.cancelUpload') + '</button></div>' : '') + '</div>' + (!options.submitInForm ? '<div class="formulario_columna_cnt">' + (file.error ? '<div class="izq_float error" ></div>' : '<div class="izq_float progress"><div></div></div>' + '<div class="izq_float fileupload-buttonbar"><button class="start">' + $.rup.i18nParse($.rup.i18n.base, 'rup_upload.startUpload') + '</button>') + '<button class="cancel">' + $.rup.i18nParse($.rup.i18n.base, 'rup_upload.cancelUpload') + '</button>' + '</div>' : '<div class="izq_float start fileupload-buttonbar ui-button" style="display:none"><button>' + $.rup.i18nParse($.rup.i18n.base, 'rup_upload.startUpload') + '</button></div>') + '</td></tr>');
			row.find('.name b').text(file.name);
			row.find('.size').text(file.sizef);
			row.find('.type').text(file.type);
			if (file.error) {
				row.addClass('ui-state-error');
				row.find('.error').text(options.errorMessages[file.error] || file.error);
			}

			rows = rows.add(row);
		});
		return rows;
	};

	$.rup = $.rup || {};
	$.rup.adapter = $.rup.adapter || {};

	$.rup.adapter[UploadJQueryUIAdapter.prototype.NAME] = new UploadJQueryUIAdapter();

	return $;
});

/***/ }),
/* 189 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*global jQuery */
/*global define */

(function (root, factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(2), __webpack_require__(3)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		root.ValidateBootstrapAdapter = factory(jQuery);
	}
})(undefined, function ($) {

	function ValidateBootstrapAdapter() {}

	ValidateBootstrapAdapter.prototype.NAME = 'validate_bootstrap';

	ValidateBootstrapAdapter.prototype.forLabelElement = function (contextForm, labelAttributes) {
		if (labelAttributes.labelForTitle !== undefined && labelAttributes.labelForTitle !== '') {
			return $(contextForm).find("input[id='" + labelAttributes.labelForId + "']").attr("oldtitle");
		} else if (labelAttributes.labelForId !== undefined && labelAttributes.labelForId !== '') {
			return $(contextForm).find("label[for='" + labelAttributes.labelForId + "']").text();
		} else {
			return $(contextForm).find("label[for='" + labelAttributes.labelForName + "']").text();
		}
	};

	ValidateBootstrapAdapter.prototype.forInputNameElement = function (contextForm, labelAttributes) {
		return $(contextForm).find("label[for='" + labelAttributes.labelForName + "']");
	};

	ValidateBootstrapAdapter.prototype.forInputIdElement = function (contextForm, labelAttributes) {
		return contextForm.elements[labelAttributes.labelForId];
	};

	ValidateBootstrapAdapter.prototype.highlight = function (element, errorClass) {
		clearValidation(element);
		$(element).addClass('error');
	};

	ValidateBootstrapAdapter.prototype.unhighlight = function (element) {
		clearValidation(element);
		$(element).removeClass('error');
	};

	function clearValidation(element) {
		if ($(element).parent().hasClass('rup-validate-field-error')) {
			$(element).parent().find('.rup-validate-error-icon').remove();
			$(element).unwrap();
			$(element).parent().find('div').remove();
		}
	}
	ValidateBootstrapAdapter.prototype.errorElement = 'div';

	ValidateBootstrapAdapter.prototype.errorPlacement = function (error, element) {

		//limpiar errores previos
		/*  if (element.parent().hasClass("")) {
        element.parent().find(".rup-validate-error-icon").remove();
        element.unwrap();
      }*/

		// var errorElem = error.attr("src",this.errorImage).addClass("rup-maint_validateIcon").html('').rup_tooltip({"applyToPortal": true});
		//
		// if (element.attr("ruptype")==='combo'){
		//   var comboElem = $("#"+element.attr("id")+"-button");
		//   if (comboElem){
		//     errorElem.insertAfter(comboElem);
		//   }
		// }else{
		// var $inputGroup = $("<div>").addClass("form-input-group");
		// var $iconError = $("<i>").addClass("fa fa-times");
		// element.wrap($inputGroup);

		var name = element.prop('name'),
		    labelProp = this.labels ? this.labels[name] : undefined,
		    $labelContainer = $(labelProp),
		    iconProp = this.icons ? this.icons[name] : undefined,
		    $iconContainer = $(iconProp),
		    $icon = $('<i>').addClass('rup-validate-error-icon error fa fa-times').attr('aria-hidden', 'true');

		// Posicionamiento del label
		if ($labelContainer.length > 0) {
			$labelContainer.append(error);
		} else {
			error.insertAfter(element);
		}

		// Posicionamiento del icon
		if ($iconContainer.length > 0) {
			$iconContainer.append($icon);
		} else {
			if (!element.parent().hasClass('rup-validate-field-error')) {
				element.wrap($('<div>').addClass('rup-validate-field-error'));
				$icon.insertAfter(element);
			}
		}

		// $iconError.insertAfter(element);


		// }
	};

	ValidateBootstrapAdapter.prototype.showLabel = function (element, message) {

		var label = this.errorsFor(element),
		    settings = $(this.currentForm).data('settings');
		if (label.length) {
			// refresh error/success class
			label.removeClass(this.settings.validClass).addClass(this.settings.errorClass);

			// check if we have a generated label, replace the message then
			label.attr('generated') && label.html(message);
		} else {
			// create label
			if (this.settings.showFieldErrorAsDefault) {
				label = $('<' + this.settings.errorElement + '/>').attr({
					'for': this.idOrName(element),
					generated: true
				}).addClass(this.settings.errorClass).html(message || '');
			} else {
				label = $('<' + this.settings.errorElement + '/>').attr({
					'for': this.idOrName(element),
					generated: true
				}).addClass(this.settings.errorClass).html(message || '');
			}
			if (this.settings.wrapper) {
				// make sure the element is visible, even in IE
				// actually showing the wrapped element is handled elsewhere
				label = label.hide().show().wrap('<' + this.settings.wrapper + '/>').parent();
			}
			if (!this.labelContainer.append(label).length) this.settings.errorPlacement ? this.settings.errorPlacement(label, $(element)) : label.insertAfter(element);
		}
		if (!message && settings.success) {
			label.text('');
			typeof this.settings.success == 'string' ? label.addClass(this.settings.success) : this.settings.success(label);
		}
		this.toShow = this.toShow.add(label);
	};

	$.rup = $.rup || {};
	$.rup.adapter = $.rup.adapter || {};

	$.rup.adapter[ValidateBootstrapAdapter.prototype.NAME] = new ValidateBootstrapAdapter();

	return $;
});

/***/ }),
/* 190 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*global jQuery */
/*global define */

(function (root, factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(2), __webpack_require__(3)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		root.ValidateJQueryUIAdapter = factory(jQuery);
	}
})(undefined, function ($) {

	function ValidateJQueryUIAdapter() {}

	ValidateJQueryUIAdapter.prototype.NAME = 'validate_jqueryui';

	ValidateJQueryUIAdapter.prototype.forLabelElement = function (fieldTmp, labelAttributes) {
		if (labelAttributes.labelForTitle !== undefined && labelAttributes.labelForTitle !== '') {
			return $(fieldTmp).attr("oldtitle");
		} else if (labelAttributes.labelForId !== undefined && labelAttributes.labelForId !== '') {
			return $("#" + fieldTmp.id).find("label[for='" + labelAttributes.labelForId + "']").text();
		} else {
			return $("#" + fieldTmp.id).find("label[for='" + labelAttributes.labelForName + "']").text();
		}
	};

	ValidateJQueryUIAdapter.prototype.forInputNameElement = function (fieldTmp, labelAttributes) {
		return $("#" + fieldTmp.id).find("label[for='" + labelAttributes.labelForName + "']");
	};

	ValidateJQueryUIAdapter.prototype.forInputIdElement = function (fieldTmp, labelAttributes) {
		return $("#" + fieldTmp.id).find('input[id=\'' + labelAttributes.labelForId + '\']')[0];
	};

	ValidateJQueryUIAdapter.prototype.highlight = function (element, errorClass) {
		$(element).addClass('error');
	};
	ValidateJQueryUIAdapter.prototype.unhighlight = function (element, errorClass) {
		$(element).removeClass('error');
	};

	ValidateJQueryUIAdapter.prototype.errorElement = 'img';

	ValidateJQueryUIAdapter.prototype.errorPlacement = function (error, element) {
		var errorElem = error.attr('src', this.errorImage).addClass('rup-maint_validateIcon').html('').rup_tooltip({
			'applyToPortal': true
		});

		if (element.attr('ruptype') === 'combo') {
			var comboElem = $('#' + element.attr('id') + '-button');
			if (comboElem) {
				errorElem.insertAfter(comboElem);
			}
		} else {
			errorElem.insertAfter(element);
		}
	};

	ValidateJQueryUIAdapter.prototype.showLabel = function (element, message) {

		var label = this.errorsFor(element),
		    settings = $(this.currentForm).data('settings');
		if (label.length) {
			// refresh error/success class
			label.removeClass(this.settings.validClass).addClass(this.settings.errorClass);

			// check if we have a generated label, replace the message then
			label.attr('generated') && label.html(message);
		} else {
			// create label
			if (settings.showFieldErrorAsDefault) {
				label = $('<' + this.settings.errorElement + '/>').attr({
					'for': this.idOrName(element),
					generated: true
				}).addClass(this.settings.errorClass).attr('title', message || '');
			} else {
				label = $('<' + this.settings.errorElement + '/>').attr({
					'for': this.idOrName(element),
					generated: true
				}).addClass(this.settings.errorClass).html(message || '');
			}
			if (this.settings.wrapper) {
				// make sure the element is visible, even in IE
				// actually showing the wrapped element is handled elsewhere
				label = label.hide().show().wrap('<' + this.settings.wrapper + '/>').parent();
			}
			if (!this.labelContainer.append(label).length) this.settings.errorPlacement ? this.settings.errorPlacement(label, $(element)) : label.insertAfter(element);
		}
		if (!message && this.settings.success) {
			label.text('');
			typeof this.settings.success == 'string' ? label.addClass(this.settings.success) : this.settings.success(label);
		}
		this.toShow = this.toShow.add(label);
	};

	$.rup = $.rup || {};
	$.rup.adapter = $.rup.adapter || {};

	$.rup.adapter[ValidateJQueryUIAdapter.prototype.NAME] = new ValidateJQueryUIAdapter();

	return $;
});

/***/ }),
/* 191 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*global jQuery */
/*global define */

(function (factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(178), __webpack_require__(184), __webpack_require__(183), __webpack_require__(188), __webpack_require__(187), __webpack_require__(175), __webpack_require__(174), __webpack_require__(186), __webpack_require__(185), __webpack_require__(177), __webpack_require__(176), __webpack_require__(182), __webpack_require__(181), __webpack_require__(190), __webpack_require__(189), __webpack_require__(180), __webpack_require__(179)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		factory(jQuery);
	}
})(function ($, Templates, DateBootstrapAdapter, TimeJQueryUIAdapter, TimeBootstrapAdapter, UploadJQueryUIAdapter, UploadBootstrapAdapter, ButtonJQueryUIAdapter, ButtonBootstrapAdapter, ToolbarJQueryUIAdapter, ToolbarBootstrapAdapter, DatatableJQueryUIAdapter, DatatableBootstrapAdapter, TableJQueryUIAdapter, TableBootstrapAdapter, ValidateJQueryUIAdapter, ValidateBootstrapAdapter, FeedbackJQueryUIAdapter, FeedbackBootstrapAdapter) {

	return $;
});

/***/ }),
/* 192 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function(jQuery) {var _typeof = typeof Symbol === "function" && typeof Symbol.iterator === "symbol" ? function (obj) { return typeof obj; } : function (obj) { return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj; };

/*
 * MultiDatesPicker v1.4.0
 * http://multidatespickr.sourceforge.net/
 *
 * Copyright 2010, Luca Lauretta
 * Dual licensed under the MIT or GPL Version 2 licenses.
 */
(function ($) {
	$.fn.multiDatesPicker = function (method) {
		var mdp_arguments = arguments;
		var ret = this;
		var today_date = new Date();
		var day_zero = new Date(0);
		var mdp_events = {};

		function datesArraySwitch(type) {
			return type == 'avoided' ? 'avoidedDates' : 'selectedDates';
		};
		function removeDate(index, type) {
			this.multiDatesPicker[datesArraySwitch(type)].splice(index, 1);
		}
		function addDate(date, type) {
			if (methods.gotDate.call(this, date, type) === false) {
				var darr = datesArraySwitch(type);
				this.multiDatesPicker[darr].push(dateConvert(date, 'object'));
				this.multiDatesPicker[darr].sort(methods.compareDates);
			}
		}
		function dateConvert(date, desired_type) {
			return methods.dateConvert(date, desired_type);
		}

		var methods = {
			init: function init(options) {
				$this = $(this);
				this.multiDatesPicker.changed = false;

				if (options) {
					this.multiDatesPicker.originalBeforeShow = options.beforeShow;
					this.multiDatesPicker.originalOnSelect = options.onSelect;
					this.multiDatesPicker.originalBeforeShowDay = options.beforeShowDay;
					this.multiDatesPicker.originalOnClose = options.onClose;

					this.multiDatesPicker.minDate = $.datepicker._determineDate(this, options.minDate, day_zero);
					this.multiDatesPicker.firstAvailableDay = methods.compareDates(this.multiDatesPicker.minDate, day_zero);

					if (options.addDates) methods.addDates.call(this, options.addDates);
					if (options.addAvoidedDates) methods.addDates.call(this, options.addAvoidedDates, 'avoided');

					if (options.mode) methods.setMode.call(this, options.mode);
				}

				$this.datepicker(options);

				mdp_events = {
					beforeShow: function beforeShow(input, inst) {
						this.multiDatesPicker.changed = false;
						if (this.multiDatesPicker.originalBeforeShow) this.multiDatesPicker.originalBeforeShow.call(this, input, inst);
					},
					onSelect: function onSelect(dateText, inst) {
						this.multiDatesPicker.changed = true;

						if (dateText) {
							$(this).multiDatesPicker('toggleDate', dateText);
							var current_date = methods.dateConvert(dateText, 'object');
						}
						var dates_picked = $(this).multiDatesPicker('getDates');
						var datos = this.multiDatesPicker.mode.options;

						if (dates_picked.length > 0) {
							if (this.multiDatesPicker.mode.modeName == 'normal') {
								if (datos.pickableRange) {
									var min_date = methods.compareDates(this.multiDatesPicker.minDate, today_date);
									var max_date = min_date + datos.pickableRangeDelay + pickableRange;

									// min
									var n_min_date = methods.compareDates(dates_picked[0], min_date);

									// max
									var n_max_date = n_min_date + datos.pickableRange;

									// adjust
									if (n_max_date > max_date) min_date = max_date - datos.pickableRange + 1;else {
										max_date = n_max_date;
										min_date = n_min_date;
									}

									// counts the number of avoided dates in the range
									var c_avoided;
									do {
										c_avoided = 0;
										for (var i in this.multiDatesPicker.avoidedDates) {
											if (methods.compareDates(this.multiDatesPicker.avoidedDates[i], min_date) >= 0 && methods.compareDates(this.multiDatesPicker.avoidedDates[i], max_date) <= 0) c_avoided++;
										}
										max_date = max_date + c_avoided;
									} while (c_avoided != 0);

									$(this).datepicker("option", "minDate", min_date);
									$(this).datepicker("option", "maxDate", max_date);
								}
							}
						}

						if (this.tagName == 'INPUT') {
							// for inputs
							$(this).val($(this).multiDatesPicker('getDates', 'string'));
						}

						if (this.multiDatesPicker.originalOnSelect && dateText) this.multiDatesPicker.originalOnSelect.call(this, dateText, inst);
					},
					beforeShowDay: function beforeShowDay(date) {
						var gotThisDate = $(this).multiDatesPicker('gotDate', date) !== false;
						var highlight_class = gotThisDate ? 'ui-state-highlight' : '';

						var isAvoidedDate = $(this).multiDatesPicker('gotDate', date, 'avoided') !== false;
						var allSelected = this.multiDatesPicker.mode.options.maxPicks == $(this).multiDatesPicker('getDates').length;
						var selectable_date = isAvoidedDate || allSelected && !highlight_class ? false : true;

						if (this.multiDatesPicker.originalBeforeShowDay) this.multiDatesPicker.originalBeforeShowDay.call(this, date);

						return [selectable_date, highlight_class];
					},
					onClose: function onClose(dateText, inst) {
						if (this.tagName == 'INPUT' && this.multiDatesPicker.changed) {
							$(inst.dpDiv[0]).stop(false, true);
							setTimeout('$("#' + inst.id + '").datepicker("show")', 50);
						}
						if (this.multiDatesPicker.originalOnClose) this.multiDatesPicker.originalOnClose.call(this, dateText, inst);
					}
				};

				$this.datepicker('option', mdp_events);
			},
			compareDates: function compareDates(date1, date2) {
				var i_dates = [date1, date2];
				var o_dates = new Array();
				var one_day = 1000 * 60 * 60 * 24;

				for (i in i_dates) {
					o_dates.push(dateConvert(i_dates[i], 'object'));
				} // return > 0 means date1 is later than date2 
				// return == 0 means date1 is the same day as date2 
				// return < 0 means date1 is earlier than date2 
				var diff = (o_dates[0].getTime() - o_dates[1].getTime()) / one_day;
				return -1 < diff && diff < 1 ? 0 : diff < 0 ? Math.ceil(diff * -1) * -1 : Math.ceil(diff);
			},
			sumDays: function sumDays(date, n_days) {
				var origDateType = typeof date === 'undefined' ? 'undefined' : _typeof(date);
				obj_date = dateConvert(date, 'object');
				obj_date.setDate(obj_date.getDate() + n_days);
				return dateConvert(obj_date, origDateType);
			},
			dateConvert: function dateConvert(date, desired_format) {
				if (typeof date == 'undefined') date = new Date(0);

				if (desired_format != 'string' && desired_format != 'object') $.error('Date format "' + desired_format + '" not supported on jQuery.multiDatesPicker');

				if ((typeof date === 'undefined' ? 'undefined' : _typeof(date)) == desired_format) return date;

				var conversion = (typeof date === 'undefined' ? 'undefined' : _typeof(date)) + '->' + desired_format;
				switch (conversion) {
					case 'object->string':
						return $.datepicker.formatDate($.datepicker._defaults.dateFormat, date);
					case 'string->object':
						return $.datepicker.parseDate($.datepicker._defaults.dateFormat, date);
					default:
						$.error('Conversion "' + conversion + '" not allowed on jQuery.multiDatesPicker');
				}
			},
			gotDate: function gotDate(date, type) {
				for (var i = 0; i < this.multiDatesPicker[datesArraySwitch(type)].length; i++) {
					if (methods.compareDates(this.multiDatesPicker[datesArraySwitch(type)][i], date) == 0) {
						return i;
					}
				}
				return false;
			},
			getDates: function getDates(format, type) {
				switch (format) {
					case 'object':
						return this.multiDatesPicker[datesArraySwitch(type)];
					default:
						var o_dates = new Array();
						for (i in this.multiDatesPicker[datesArraySwitch(type)]) {
							o_dates.push(dateConvert(this.multiDatesPicker[datesArraySwitch(type)][i], 'string'));
						}return o_dates;
				}
			},
			addDates: function addDates(dates, type) {
				switch (typeof dates === 'undefined' ? 'undefined' : _typeof(dates)) {
					case 'object':
					case 'array':
						if (dates.length) {
							for (i in dates) {
								addDate.call(this, dates[i], type);
							}break;
						} // else does the same as 'string'
					case 'string':
						addDate.call(this, dates, type);
						break;
					default:
						$.error('Date format "' + (typeof dates === 'undefined' ? 'undefined' : _typeof(dates)) + '" not allowed on jQuery.multiDatesPicker');
				}
				$(this).datepicker('refresh');
			},
			removeDates: function removeDates(indexes, type) {
				if (typeof index == 'array') for (i in indexes) {
					removeDate.call(this, i, type);
				} else removeDate.call(this, indexes, type);
				$(this).datepicker('refresh');
			},
			resetDates: function resetDates(type) {
				this.multiDatesPicker[datesArraySwitch(type)] = [];
				$(this).datepicker('refresh');
			},
			toggleDate: function toggleDate(date, type) {
				var index = methods.gotDate.call(this, date);
				var mode = this.multiDatesPicker.mode;

				switch (mode.modeName) {
					case 'daysRange':
						this.multiDatesPicker.selectedDates = []; // deletes all selected dates
						var end = mode.options.autoselectRange[1];
						var begin = mode.options.autoselectRange[0];
						if (end < begin) {
							// switch
							end = mode.options.autoselectRange[0];
							begin = mode.options.autoselectRange[1];
						}
						for (var i = begin; i < end; i++) {
							methods.addDates.call(this, methods.sumDays(date, i));
						}break;
					default:
						if (index === false) // adds dates
							methods.addDates.call(this, date);else // removes dates
							methods.removeDates.call(this, index);
						break;
				}
			},
			setMode: function setMode(mode) {
				this.multiDatesPicker.mode.modeName = mode.modeName;
				switch (mode.modeName) {
					case 'normal':
						for (option in mode.options) {
							switch (option) {
								case 'maxPicks':
								case 'minPicks':
								case 'pickableRange':
								case 'pickableRangeDelay':
								case 'adjustRangeToAvoided':
									this.multiDatesPicker.mode.options[option] = mode.options[option];
									break;
								default:
									$.error('Option ' + option + ' does not exist for setMode on jQuery.multiDatesPicker');
							}
						}break;
					case 'daysRange':
					case 'weeksRange':
						var mandatory = 1;
						for (option in mode.options) {
							switch (option) {
								case 'autoselectRange':
									mandatory--;
								case 'pickableRange':
								case 'pickableRangeDelay':
								case 'adjustRangeToAvoided':
									this.multiDatesPicker.mode.options[option] = mode.options[option];
									break;
								default:
									$.error('Option ' + option + ' does not exist for setMode on jQuery.multiDatesPicker');
							}
						}if (mandatory > 0) $.error('Some mandatory options not specified!');
						break;
				}

				if (mode.options.pickableRange) {
					$(this).datepicker("option", "maxDate", mode.options.pickableRange + (mode.options.pickableRangeDelay || 0));
					$(this).datepicker("option", "minDate", this.multiDatesPicker.minDate);
				}

				if (mdp_events.onSelect) mdp_events.onSelect();
				$(this).datepicker('refresh');
			}
		};

		this.each(function () {
			if (!this.multiDatesPicker) this.multiDatesPicker = {
				selectedDates: [],
				avoidedDates: [],
				mode: {
					modeName: 'normal',
					options: {
						adjustRangeToAvoided: true
					}
				}
			};

			if (methods[method]) {
				var exec_result = methods[method].apply(this, Array.prototype.slice.call(mdp_arguments, 1));
				switch (method) {
					case 'getDates':
					case 'gotDate':
					case 'sumDays':
					case 'compareDates':
					case 'dateConvert':
						ret = exec_result;
				}
				return exec_result;
			} else if ((typeof method === 'undefined' ? 'undefined' : _typeof(method)) === 'object' || !method) {
				return methods.init.apply(this, mdp_arguments);
			} else {
				$.error('Method ' + method + ' does not exist on jQuery.multiDatesPicker');
			}
		});

		return ret;
	};
})(jQuery);
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))

/***/ }),
/* 193 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/* jshint forin:true, noarg:true, noempty:true, eqeqeq:true, boss:true, undef:true, curly:true, browser:true, jquery:true */
/*
 * jQuery MultiSelect UI Widget 1.13
 * Copyright (c) 2012 Eric Hynds
 *
 * http://www.erichynds.com/jquery/jquery-ui-multiselect-widget/
 *
 * Depends:
 *   - jQuery 1.4.2+
 *   - jQuery UI 1.8 widget factory
 *
 * Optional:
 *   - jQuery UI effects
 *   - jQuery UI position utility
 *
 * Dual licensed under the MIT and GPL licenses:
 *   http://www.opensource.org/licenses/mit-license.php
 *   http://www.gnu.org/licenses/gpl.html
 *
*/

/* global define */
/* global jQuery */

(function (factory) {
	if (true) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(11), __webpack_require__(20)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		factory(jQuery);
	}
})(function ($) {

	var multiselectID = 0;

	$.widget('ech.multiselect', {

		// default options
		options: {
			header: true,
			height: 175,
			minWidth: 225,
			classes: '',
			checkAllText: 'Check all',
			uncheckAllText: 'Uncheck all',
			noneSelectedText: 'Select options',
			selectedText: '# selected',
			selectedList: 0,
			show: null,
			hide: null,
			autoOpen: false,
			multiple: true,
			position: {}
		},

		_create: function _create() {
			var el = this.element.hide(),
			    o = this.options;

			this.speed = $.fx.speeds._default; // default speed for effects
			this._isOpen = false; // assume no

			var
			//button = (this.button = $('<button type="button"><span class="ui-icon ui-icon-triangle-2-n-s"></span></button>'))
			button = (this.button = $('<button type="button"><span class="ui-icon ui-icon-triangle-1-s"></span></button>')).addClass('ui-multiselect ui-widget ui-state-default ui-corner-all').addClass(o.classes).attr({ 'title': el.attr('title'), 'aria-haspopup': true, 'tabIndex': el.attr('tabIndex') }).insertAfter(el),
			    buttonlabel = (this.buttonlabel = $('<span />')).html(o.noneSelectedText).appendTo(button),
			    menu = (this.menu = $('<div />')).attr('id', 'rup-multiCombo_' + $(this.element).attr('id')).addClass('ui-multiselect-menu ui-widget ui-widget-content ui-corner-all').addClass(o.classes).appendTo(document.body),
			    header = (this.header = $('<div />')).addClass('ui-widget-header ui-corner-all ui-multiselect-header ui-helper-clearfix').appendTo(menu),
			    headerLinkContainer = (this.headerLinkContainer = $('<ul />')).addClass('ui-helper-reset').html(function () {
				if (o.header === true) {
					return '<li><a class="ui-multiselect-all" href="#"><span class="ui-icon ui-icon-check"></span><span>' + o.checkAllText + '</span></a></li><li><a class="ui-multiselect-none" href="#"><span class="ui-icon ui-icon-closethick"></span><span>' + o.uncheckAllText + '</span></a></li>';
				} else if (typeof o.header === 'string') {
					return '<li>' + o.header + '</li>';
				} else {
					return '';
				}
			}).append('<li class="ui-multiselect-close"><a href="#" class="ui-multiselect-close"><span class="ui-icon ui-icon-circle-close"></span></a></li>').appendTo(header),
			    checkboxContainer = (this.checkboxContainer = $('<ul />')).addClass('ui-multiselect-checkboxes ui-helper-reset').appendTo(menu);

			// perform event bindings
			this._bindEvents();

			// build menu
			this.refresh(true);

			// some addl. logic for single selects
			if (!o.multiple) {
				menu.addClass('ui-multiselect-single');
			}
		},

		_init: function _init() {
			if (this.options.header === false) {
				this.header.hide();
			}
			if (!this.options.multiple) {
				this.headerLinkContainer.find('.ui-multiselect-all, .ui-multiselect-none').hide();
			}
			if (this.options.autoOpen) {
				this.open();
			}
			if (this.element.is(':disabled')) {
				this.disable();
			}
		},

		refresh: function refresh(init) {
			var el = this.element,
			    o = this.options,
			    menu = this.menu,
			    checkboxContainer = this.checkboxContainer,
			    optgroups = [],
			    html = '',
			    id = el.attr('id') || multiselectID++; // unique ID for the label & option tags

			// build items
			el.find('option').each(function (i) {
				var $this = $(this),
				    parent = this.parentNode,
				    title = this.innerHTML,
				    description = this.title,
				    value = this.value,
				    inputID = 'ui-multiselect-' + (this.id || id + '-option-' + i),
				    isDisabled = this.disabled,
				    isSelected = this.selected,
				    labelClasses = ['ui-corner-all'],
				    liClasses = (isDisabled ? 'ui-multiselect-disabled ' : ' ') + this.className,
				    optLabel;

				// is this an optgroup?
				if (parent.tagName === 'OPTGROUP') {
					optLabel = parent.getAttribute('label');

					// has this optgroup been added already?
					if ($.inArray(optLabel, optgroups) === -1) {
						html += '<li class="ui-multiselect-optgroup-label ' + parent.className + '"><a href="#">' + optLabel + '</a></li>';
						optgroups.push(optLabel);
					}
				}

				if (isDisabled) {
					labelClasses.push('ui-state-disabled');
				}

				// browsers automatically select the first option
				// by default with single selects
				if (isSelected && !o.multiple) {
					labelClasses.push('ui-state-active');
				}

				html += '<li class="' + liClasses + '">';

				// create the label
				html += '<label for="' + inputID + '" title="' + description + '" class="' + labelClasses.join(' ') + '">';
				html += '<input id="' + inputID + '" name="multiselect_' + id + '" type="' + (o.multiple ? 'checkbox' : 'radio') + '" value="' + value + '" title="' + title + '"';

				// pre-selected?
				if (isSelected) {
					html += ' checked="checked"';
					html += ' aria-selected="true"';
				}

				// disabled?
				if (isDisabled) {
					html += ' disabled="disabled"';
					html += ' aria-disabled="true"';
				}

				// add the title and close everything off
				html += ' /><span>' + title + '</span></label></li>';
			});

			// insert into the DOM
			checkboxContainer.html(html);

			// cache some moar useful elements
			this.labels = menu.find('label');
			this.inputs = this.labels.children('input');

			// set widths
			this._setButtonWidth();
			this._setMenuWidth();

			// remember default value
			this.button[0].defaultValue = this.update();

			// broadcast refresh event; useful for widgets
			if (!init) {
				this._trigger('refresh');
			}
		},

		// updates the button text. call refresh() to rebuild
		update: function update() {
			var o = this.options,
			    $inputs = this.inputs,
			    $checked = $inputs.filter(':checked'),
			    numChecked = $checked.length,
			    value;

			if (numChecked === 0) {
				value = o.noneSelectedText;
			} else {
				if ($.isFunction(o.selectedText)) {
					value = o.selectedText.call(this, numChecked, $inputs.length, $checked.get());
				} else if (/\d/.test(o.selectedList) && o.selectedList > 0 && numChecked <= o.selectedList) {
					value = $checked.map(function () {
						return $(this).next().html();
					}).get().join(', ');
				} else {
					value = o.selectedText.replace('#', numChecked).replace('#', $inputs.length);
				}
			}

			this.buttonlabel.html(value);
			return value;
		},

		// binds events
		_bindEvents: function _bindEvents() {
			var self = this,
			    button = this.button;

			function clickHandler() {
				self[self._isOpen ? 'close' : 'open']();
				return false;
			}

			// webkit doesn't like it when you click on the span :(
			button.find('span').bind('click.multiselect', clickHandler);

			// button events
			button.bind({
				click: clickHandler,
				keypress: function keypress(e) {
					switch (e.which) {
						case 27: // esc
						case 38: // up
						case 37:
							// left
							self.close();
							break;
						case 39: // right
						case 40:
							// down
							self.open();
							break;
					}
				},
				mouseenter: function mouseenter() {
					if (!button.hasClass('ui-state-disabled')) {
						$(this).addClass('ui-state-hover');
					}
				},
				mouseleave: function mouseleave() {
					$(this).removeClass('ui-state-hover');
				},
				focus: function focus() {
					if (!button.hasClass('ui-state-disabled')) {
						$(this).addClass('ui-state-focus');
					}
				},
				blur: function blur() {
					$(this).removeClass('ui-state-focus');
				}
			});

			// header links
			this.header.delegate('a', 'click.multiselect', function (e) {
				// close link
				if ($(this).hasClass('ui-multiselect-close')) {
					self.close();

					// check all / uncheck all
				} else {
					self[$(this).hasClass('ui-multiselect-all') ? 'checkAll' : 'uncheckAll']();
				}

				e.preventDefault();
			});

			// optgroup label toggle support
			this.menu.delegate('li.ui-multiselect-optgroup-label a', 'click.multiselect', function (e) {
				e.preventDefault();

				var $this = $(this),
				    $inputs = $this.parent().nextUntil('li.ui-multiselect-optgroup-label').find('input:visible:not(:disabled)'),
				    nodes = $inputs.get(),
				    label = $this.parent().text();

				// trigger event and bail if the return is false
				//if( self._trigger('beforeoptgrouptoggle', e, { inputs:nodes, label:label }) === false ){
				//IE Fix: (Select - Disabled option)
				if (self._trigger('beforeoptgrouptoggle', e, { inputs: nodes, label: label }) === false || !nodes.length) {
					return;
				}

				// toggle inputs
				self._toggleChecked($inputs.filter(':checked').length !== $inputs.length, $inputs);

				self._trigger('optgrouptoggle', e, {
					inputs: nodes,
					label: label,
					checked: nodes[0].checked
				});
			}).delegate('label', 'mouseenter.multiselect', function () {
				if (!$(this).hasClass('ui-state-disabled')) {
					self.labels.removeClass('ui-state-hover');
					//$(this).addClass('ui-state-hover').find('input').focus();
					//IE Fix: (Select - Disabled option)
					$(this).addClass('ui-state-hover').find('input:not(:disabled)').focus();
				}
			}).delegate('label', 'keydown.multiselect', function (e) {
				e.preventDefault();

				switch (e.which) {
					case 9: // tab
					case 27:
						// esc
						self.close();
						break;
					case 38: // up
					case 40: // down
					case 37: // left
					case 39:
						// right
						self._traverse(e.which, this);
						break;
					case 13:
						// enter
						$(this).find('input')[0].click();
						break;
				}
			}).delegate('input[type="checkbox"], input[type="radio"]', 'click.multiselect', function (e) {
				var $this = $(this),
				    val = this.value,
				    checked = this.checked,
				    tags = self.element.find('option');

				// bail if this input is disabled or the event is cancelled
				if (this.disabled || self._trigger('click', e, { value: val, text: this.title, checked: checked }) === false) {
					e.preventDefault();
					return;
				}

				// make sure the input has focus. otherwise, the esc key
				// won't close the menu after clicking an item.
				$this.focus();

				// toggle aria state
				$this.attr('aria-selected', checked);

				// change state on the original option tags
				tags.each(function () {
					if (this.value === val) {
						this.selected = checked;
					} else if (!self.options.multiple) {
						this.selected = false;
					}
				});

				// some additional single select-specific logic
				if (!self.options.multiple) {
					self.labels.removeClass('ui-state-active');
					$this.closest('label').toggleClass('ui-state-active', checked);

					// close menu
					self.close();
				}

				// fire change on the select box
				self.element.trigger('change');

				// setTimeout is to fix multiselect issue #14 and #47. caused by jQuery issue #3827
				// http://bugs.jquery.com/ticket/3827
				setTimeout($.proxy(self.update, self), 10);
			});

			// close each widget when clicking on any other element/anywhere else on the page
			$(document).bind('mousedown.multiselect', function (e) {
				if (self._isOpen && !$.contains(self.menu[0], e.target) && !$.contains(self.button[0], e.target) && e.target !== self.button[0]) {
					self.close();
				}
			});

			// deal with form resets.  the problem here is that buttons aren't
			// restored to their defaultValue prop on form reset, and the reset
			// handler fires before the form is actually reset.  delaying it a bit
			// gives the form inputs time to clear.
			$(this.element[0].form).bind('reset.multiselect', function () {
				setTimeout($.proxy(self.refresh, self), 10);
			});
		},

		// set button width
		_setButtonWidth: function _setButtonWidth() {
			var width = this.element.outerWidth(),
			    o = this.options;

			if (/\d/.test(o.minWidth) && width < o.minWidth) {
				width = o.minWidth;
			}

			// set widths
			this.button.width(width);
		},

		// set menu width
		_setMenuWidth: function _setMenuWidth() {
			var m = this.menu,
			    width = this.button.outerWidth() - parseInt(m.css('padding-left'), 10) - parseInt(m.css('padding-right'), 10) - parseInt(m.css('border-right-width'), 10) - parseInt(m.css('border-left-width'), 10);

			m.width(width || this.button.outerWidth());
		},

		// move up or down within the menu
		_traverse: function _traverse(which, start) {
			var $start = $(start),
			    moveToLast = which === 38 || which === 37,


			// select the first li that isn't an optgroup label / disabled
			$next = $start.parent()[moveToLast ? 'prevAll' : 'nextAll']('li:not(.ui-multiselect-disabled, .ui-multiselect-optgroup-label)')[moveToLast ? 'last' : 'first']();

			// if at the first/last element
			if (!$next.length) {
				var $container = this.menu.find('ul').last();

				// move to the first/last
				this.menu.find('label')[moveToLast ? 'last' : 'first']().trigger('mouseover');

				// set scroll position
				$container.scrollTop(moveToLast ? $container.height() : 0);
			} else {
				$next.find('label').trigger('mouseover');
			}
		},

		// This is an internal function to toggle the checked property and
		// other related attributes of a checkbox.
		//
		// The context of this function should be a checkbox; do not proxy it.
		_toggleState: function _toggleState(prop, flag) {
			return function () {
				if (!this.disabled) {
					this[prop] = flag;
				}

				if (flag) {
					this.setAttribute('aria-selected', true);
				} else {
					this.removeAttribute('aria-selected');
				}
			};
		},

		_toggleChecked: function _toggleChecked(flag, group) {
			//var $inputs = (group && group.length) ?  group : this.inputs,
			//	self = this;
			//IE Fix: (Select - Disabled option)
			var $inputs = group && group.length ? group : this.labels.find('input:enabled'),
			    self = this;

			// toggle state on inputs
			$inputs.each(this._toggleState('checked', flag));

			// give the first input focus
			$inputs.eq(0).focus();

			// update button text
			this.update();

			// gather an array of the values that actually changed
			var values = $inputs.map(function () {
				return this.value;
			}).get();

			// toggle state on original option tags
			this.element.find('option').each(function () {
				if (!this.disabled && $.inArray(this.value, values) > -1) {
					self._toggleState('selected', flag).call(this);
				}
			});

			// trigger the change event on the select
			if ($inputs.length) {
				this.element.trigger('change');
			}
		},

		_toggleDisabled: function _toggleDisabled(flag) {
			this.button.attr({ 'disabled': flag, 'aria-disabled': flag })[flag ? 'addClass' : 'removeClass']('ui-state-disabled');

			var inputs = this.menu.find('input');
			var key = 'ech-multiselect-disabled';

			if (flag) {
				// remember which elements this widget disabled (not pre-disabled)
				// elements, so that they can be restored if the widget is re-enabled.
				inputs = inputs.filter(':enabled').data(key, true);
			} else {
				inputs = inputs.filter(function () {
					return $.data(this, key) === true;
				}).removeData(key);
			}

			inputs.attr({ 'disabled': flag, 'arial-disabled': flag }).parent()[flag ? 'addClass' : 'removeClass']('ui-state-disabled');

			this.element.attr({ 'disabled': flag, 'aria-disabled': flag });
		},

		// open the menu
		open: function open(e) {
			var self = this,
			    button = this.button,
			    menu = this.menu,
			    speed = this.speed,
			    o = this.options,
			    args = [];

			// bail if the multiselectopen event returns false, this widget is disabled, or is already open
			if (this._trigger('beforeopen') === false || button.hasClass('ui-state-disabled') || this._isOpen) {
				return;
			}

			var $container = menu.find('ul').last(),
			    effect = o.show,
			    pos = button.offset();

			// figure out opening effects/speeds
			if ($.isArray(o.show)) {
				effect = o.show[0];
				speed = o.show[1] || self.speed;
			}

			// if there's an effect, assume jQuery UI is in use
			// build the arguments to pass to show()
			if (effect) {
				args = [effect, speed];
			}

			// set the scroll of the checkbox container
			$container.scrollTop(0).height(o.height);

			// position and show menu
			if ($.ui.position && !$.isEmptyObject(o.position)) {
				o.position.of = o.position.of || button;

				menu.show().position(o.position).hide();

				// if position utility is not available...
			} else {
				menu.css({
					top: pos.top + button.outerHeight(),
					left: pos.left
				});
			}

			// show the menu, maybe with a speed/effect combo
			//$.fn.show.apply(menu, args);
			menu.show();

			// select the first option
			// triggering both mouseover and mouseover because 1.4.2+ has a bug where triggering mouseover
			// will actually trigger mouseenter.  the mouseenter trigger is there for when it's eventually fixed
			//this.labels.eq(0).trigger('mouseover').trigger('mouseenter').find('input').trigger('focus');
			//IE Fix: (Select - Disabled option)
			this.labels.eq(0).trigger('mouseover').trigger('mouseenter').find('input:enabled').trigger('focus');

			button.addClass('ui-state-active');
			this._isOpen = true;
			this._trigger('open');
		},

		// close the menu
		close: function close() {
			if (this._trigger('beforeclose') === false) {
				return;
			}

			var o = this.options,
			    effect = o.hide,
			    speed = this.speed,
			    args = [];

			// figure out opening effects/speeds
			if ($.isArray(o.hide)) {
				effect = o.hide[0];
				speed = o.hide[1] || this.speed;
			}

			if (effect) {
				args = [effect, speed];
			}

			$.fn.hide.apply(this.menu, args);
			this.button.removeClass('ui-state-active').trigger('blur').trigger('mouseleave');
			this._isOpen = false;
			this._trigger('close');
		},

		enable: function enable() {
			this._toggleDisabled(false);
		},

		disable: function disable() {
			this._toggleDisabled(true);
		},

		checkAll: function checkAll(e) {
			this._toggleChecked(true);
			this._trigger('checkAll');
		},

		uncheckAll: function uncheckAll() {
			this._toggleChecked(false);
			this._trigger('uncheckAll');
		},

		getChecked: function getChecked() {
			return this.menu.find('input').filter(':checked');
		},

		destroy: function destroy() {
			// remove classes + data
			$.Widget.prototype.destroy.call(this);

			this.button.remove();
			this.menu.remove();
			this.element.show();

			return this;
		},

		isOpen: function isOpen() {
			return this._isOpen;
		},

		widget: function widget() {
			return this.menu;
		},

		getButton: function getButton() {
			return this.button;
		},

		// react to option changes after initialization
		_setOption: function _setOption(key, value) {
			var menu = this.menu;

			switch (key) {
				case 'header':
					menu.find('div.ui-multiselect-header')[value ? 'show' : 'hide']();
					break;
				case 'checkAllText':
					menu.find('a.ui-multiselect-all span').eq(-1).text(value);
					break;
				case 'uncheckAllText':
					menu.find('a.ui-multiselect-none span').eq(-1).text(value);
					break;
				case 'height':
					menu.find('ul').last().height(parseInt(value, 10));
					break;
				case 'minWidth':
					this.options[key] = parseInt(value, 10);
					this._setButtonWidth();
					this._setMenuWidth();
					break;
				case 'selectedText':
				case 'selectedList':
				case 'noneSelectedText':
					this.options[key] = value; // these all needs to update immediately for the update() call
					this.update();
					break;
				case 'classes':
					menu.add(this.button).removeClass(this.options.classes).addClass(value);
					break;
				case 'multiple':
					menu.toggleClass('ui-multiselect-single', !value);
					this.options.multiple = value;
					this.element[0].multiple = value;
					this.refresh();
			}

			$.Widget.prototype._setOption.apply(this, arguments);
		}
	});
});

/***/ }),
/* 194 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function(jQuery) {/*
* jQuery File Download Plugin v1.3.3
*
* http://www.johnculviner.com
*
* Copyright (c) 2012 - John Culviner
*
* Licensed under the MIT license:
* http://www.opensource.org/licenses/mit-license.php
*/

var $ = jQuery.noConflict();

$.extend({
            //
            //$.fileDownload('/path/to/url/', options)
            // see directly below for possible 'options'
            fileDownload: function fileDownload(fileUrl, options) {

                        var defaultFailCallback = function defaultFailCallback(responseHtml, url) {
                                    alert("A file download error has occurred, please try again.");
                        };

                        //provide some reasonable defaults to any unspecified options below
                        var settings = $.extend({

                                    //
                                    //Requires jQuery UI: provide a message to display to the user when the file download is being prepared before the browser's dialog appears
                                    //
                                    preparingMessageHtml: null,

                                    //
                                    //Requires jQuery UI: provide a message to display to the user when a file download fails
                                    //
                                    failMessageHtml: null,

                                    //
                                    //the stock android browser straight up doesn't support file downloads initiated by a non GET: http://code.google.com/p/android/issues/detail?id=1780
                                    //specify a message here to display if a user tries with an android browser
                                    //if jQuery UI is installed this will be a dialog, otherwise it will be an alert
                                    //
                                    androidPostUnsupportedMessageHtml: "Unfortunately your Android browser doesn't support this type of file download. Please try again with a different browser.",

                                    //
                                    //Requires jQuery UI: options to pass into jQuery UI Dialog
                                    //
                                    dialogOptions: { modal: true },

                                    //
                                    //a function to call after a file download dialog/ribbon has appeared
                                    //Args:
                                    // url - the original url attempted
                                    //
                                    successCallback: function successCallback(url) {},

                                    //
                                    //a function to call after a file download dialog/ribbon has appeared
                                    //Args:
                                    // responseHtml - the html that came back in response to the file download. this won't necessarily come back depending on the browser.
                                    // in less than IE9 a cross domain error occurs because 500+ errors cause a cross domain issue due to IE subbing out the
                                    // server's error message with a "helpful" IE built in message
                                    // url - the original url attempted
                                    //
                                    failCallback: defaultFailCallback,

                                    //
                                    // the HTTP method to use. Defaults to "GET".
                                    //
                                    httpMethod: "GET",

                                    //
                                    // if specified will perform a "httpMethod" request to the specified 'fileUrl' using the specified data.
                                    // data must be an object (which will be $.param serialized) or already a key=value param string
                                    //
                                    data: null,

                                    //
                                    //a period in milliseconds to poll to determine if a successful file download has occured or not
                                    //
                                    checkInterval: 100,

                                    //
                                    //the cookie name to indicate if a file download has occured
                                    //
                                    cookieName: "fileDownload",

                                    //
                                    //the cookie value for the above name to indicate that a file download has occured
                                    //
                                    cookieValue: "true",

                                    //
                                    //the cookie path for above name value pair
                                    //
                                    cookiePath: "/",

                                    //
                                    //the title for the popup second window as a download is processing in the case of a mobile browser
                                    //
                                    popupWindowTitle: "Initiating file download...",

                                    //
                                    //Functionality to encode HTML entities for a POST, need this if data is an object with properties whose values contains strings with quotation marks.
                                    //HTML entity encoding is done by replacing all &,<,>,',",\r,\n characters.
                                    //Note that some browsers will POST the string htmlentity-encoded whilst others will decode it before POSTing.
                                    //It is recommended that on the server, htmlentity decoding is done irrespective.
                                    //
                                    encodeHTMLEntities: true
                        }, options);

                        //Setup mobile browser detection: Partial credit: http://detectmobilebrowser.com/
                        var userAgent = (navigator.userAgent || navigator.vendor || window.opera).toLowerCase();

                        var isIos = false; //has full support of features in iOS 4.0+, uses a new window to accomplish this.
                        var isAndroid = false; //has full support of GET features in 4.0+ by using a new window. Non-GET is completely unsupported by the browser. See above for specifying a message.
                        var isOtherMobileBrowser = false; //there is no way to reliably guess here so all other mobile devices will GET and POST to the current window.

                        if (/ip(ad|hone|od)/.test(userAgent)) {

                                    isIos = true;
                        } else if (userAgent.indexOf('android') != -1) {

                                    isAndroid = true;
                        } else {

                                    isOtherMobileBrowser = /avantgo|bada\/|blackberry|blazer|compal|elaine|fennec|hiptop|playbook|silk|iemobile|iris|kindle|lge |maemo|midp|mmp|netfront|opera m(ob|in)i|palm( os)?|phone|p(ixi|re)\/|plucker|pocket|psp|symbian|treo|up\.(browser|link)|vodafone|wap|windows (ce|phone)|xda|xiino/i.test(userAgent) || /1207|6310|6590|3gso|4thp|50[1-6]i|770s|802s|a wa|abac|ac(er|oo|s\-)|ai(ko|rn)|al(av|ca|co)|amoi|an(ex|ny|yw)|aptu|ar(ch|go)|as(te|us)|attw|au(di|\-m|r |s )|avan|be(ck|ll|nq)|bi(lb|rd)|bl(ac|az)|br(e|v)w|bumb|bw\-(n|u)|c55\/|capi|ccwa|cdm\-|cell|chtm|cldc|cmd\-|co(mp|nd)|craw|da(it|ll|ng)|dbte|dc\-s|devi|dica|dmob|do(c|p)o|ds(12|\-d)|el(49|ai)|em(l2|ul)|er(ic|k0)|esl8|ez([4-7]0|os|wa|ze)|fetc|fly(\-|_)|g1 u|g560|gene|gf\-5|g\-mo|go(\.w|od)|gr(ad|un)|haie|hcit|hd\-(m|p|t)|hei\-|hi(pt|ta)|hp( i|ip)|hs\-c|ht(c(\-| |_|a|g|p|s|t)|tp)|hu(aw|tc)|i\-(20|go|ma)|i230|iac( |\-|\/)|ibro|idea|ig01|ikom|im1k|inno|ipaq|iris|ja(t|v)a|jbro|jemu|jigs|kddi|keji|kgt( |\/)|klon|kpt |kwc\-|kyo(c|k)|le(no|xi)|lg( g|\/(k|l|u)|50|54|e\-|e\/|\-[a-w])|libw|lynx|m1\-w|m3ga|m50\/|ma(te|ui|xo)|mc(01|21|ca)|m\-cr|me(di|rc|ri)|mi(o8|oa|ts)|mmef|mo(01|02|bi|de|do|t(\-| |o|v)|zz)|mt(50|p1|v )|mwbp|mywa|n10[0-2]|n20[2-3]|n30(0|2)|n50(0|2|5)|n7(0(0|1)|10)|ne((c|m)\-|on|tf|wf|wg|wt)|nok(6|i)|nzph|o2im|op(ti|wv)|oran|owg1|p800|pan(a|d|t)|pdxg|pg(13|\-([1-8]|c))|phil|pire|pl(ay|uc)|pn\-2|po(ck|rt|se)|prox|psio|pt\-g|qa\-a|qc(07|12|21|32|60|\-[2-7]|i\-)|qtek|r380|r600|raks|rim9|ro(ve|zo)|s55\/|sa(ge|ma|mm|ms|ny|va)|sc(01|h\-|oo|p\-)|sdk\/|se(c(\-|0|1)|47|mc|nd|ri)|sgh\-|shar|sie(\-|m)|sk\-0|sl(45|id)|sm(al|ar|b3|it|t5)|so(ft|ny)|sp(01|h\-|v\-|v )|sy(01|mb)|t2(18|50)|t6(00|10|18)|ta(gt|lk)|tcl\-|tdg\-|tel(i|m)|tim\-|t\-mo|to(pl|sh)|ts(70|m\-|m3|m5)|tx\-9|up(\.b|g1|si)|utst|v400|v750|veri|vi(rg|te)|vk(40|5[0-3]|\-v)|vm40|voda|vulc|vx(52|53|60|61|70|80|81|83|85|98)|w3c(\-| )|webc|whit|wi(g |nc|nw)|wmlb|wonu|x700|xda(\-|2|g)|yas\-|your|zeto|zte\-/i.test(userAgent.substr(0, 4));
                        }

                        var httpMethodUpper = settings.httpMethod.toUpperCase();

                        if (isAndroid && httpMethodUpper != "GET") {
                                    //the stock android browser straight up doesn't support file downloads initiated by non GET requests: http://code.google.com/p/android/issues/detail?id=1780

                                    if ($().dialog) {
                                                $("<div>").html(settings.androidPostUnsupportedMessageHtml).dialog(settings.dialogOptions);
                                    } else {
                                                alert(settings.androidPostUnsupportedMessageHtml);
                                    }

                                    return;
                        }

                        //wire up a jquery dialog to display the preparing message if specified
                        var $preparingDialog = null;
                        if (settings.preparingMessageHtml) {

                                    $preparingDialog = $("<div>").html(settings.preparingMessageHtml).dialog(settings.dialogOptions);
                        }

                        var internalCallbacks = {

                                    onSuccess: function onSuccess(url) {

                                                //remove the perparing message if it was specified
                                                if ($preparingDialog) {
                                                            $preparingDialog.dialog('close');
                                                };

                                                settings.successCallback(url);
                                    },

                                    onFail: function onFail(responseHtml, url) {

                                                //remove the perparing message if it was specified
                                                if ($preparingDialog) {
                                                            $preparingDialog.dialog('close');
                                                };

                                                //wire up a jquery dialog to display the fail message if specified
                                                if (settings.failMessageHtml) {

                                                            $("<div>").html(settings.failMessageHtml).dialog(settings.dialogOptions);

                                                            //only run the fallcallback if the developer specified something different than default
                                                            //otherwise we would see two messages about how the file download failed
                                                            if (settings.failCallback != defaultFailCallback) {
                                                                        settings.failCallback(responseHtml, url);
                                                            }
                                                } else {

                                                            settings.failCallback(responseHtml, url);
                                                }
                                    }
                        };

                        //make settings.data a param string if it exists and isn't already
                        if (settings.data !== null && typeof settings.data !== "string") {
                                    settings.data = $.param(settings.data);
                        }

                        var $iframe, downloadWindow, formDoc, $form;

                        if (httpMethodUpper === "GET") {

                                    if (settings.data !== null) {
                                                //need to merge any fileUrl params with the data object

                                                var qsStart = fileUrl.indexOf('?');

                                                if (qsStart != -1) {
                                                            //we have a querystring in the url

                                                            if (fileUrl.substring(fileUrl.length - 1) !== "&") {
                                                                        fileUrl = fileUrl + "&";
                                                            }
                                                } else {

                                                            fileUrl = fileUrl + "?";
                                                }

                                                fileUrl = fileUrl + settings.data;
                                    }

                                    if (isIos || isAndroid) {

                                                downloadWindow = window.open(fileUrl);
                                                downloadWindow.document.title = settings.popupWindowTitle;
                                                window.focus();
                                    } else if (isOtherMobileBrowser) {

                                                window.location(fileUrl);
                                    } else {

                                                //create a temporary iframe that is used to request the fileUrl as a GET request
                                                $iframe = $("<iframe>").hide().attr("src", fileUrl).appendTo("body");
                                    }
                        } else {

                                    var formInnerHtml = "";

                                    if (settings.data !== null) {

                                                $.each(settings.data.replace(/\+/g, ' ').split("&"), function () {

                                                            var kvp = this.split("=");

                                                            var key = settings.encodeHTMLEntities ? htmlSpecialCharsEntityEncode(decodeURIComponent(kvp[0])) : decodeURIComponent(kvp[0]);
                                                            if (!key) return;
                                                            var value = kvp[1] || '';
                                                            value = settings.encodeHTMLEntities ? htmlSpecialCharsEntityEncode(decodeURIComponent(kvp[1])) : decodeURIComponent(kvp[1]);

                                                            formInnerHtml += '<input type="hidden" name="' + key + '" value="' + value + '" />';
                                                });
                                    }

                                    if (isOtherMobileBrowser) {

                                                $form = $("<form>").appendTo("body");
                                                $form.hide().attr('method', settings.httpMethod).attr('action', fileUrl).html(formInnerHtml);
                                    } else {

                                                if (isIos) {

                                                            downloadWindow = window.open("about:blank");
                                                            downloadWindow.document.title = settings.popupWindowTitle;
                                                            formDoc = downloadWindow.document;
                                                            window.focus();
                                                } else {

                                                            $iframe = $("<iframe style='display: none' src='about:blank'></iframe>").appendTo("body");
                                                            formDoc = getiframeDocument($iframe);
                                                }

                                                formDoc.write("<html><head></head><body><form method='" + settings.httpMethod + "' action='" + fileUrl + "'>" + formInnerHtml + "</form>" + settings.popupWindowTitle + "</body></html>");
                                                $form = $(formDoc).find('form');
                                    }

                                    $form.submit();
                        }

                        //check if the file download has completed every checkInterval ms
                        setTimeout(checkFileDownloadComplete, settings.checkInterval);

                        function checkFileDownloadComplete() {

                                    //has the cookie been written due to a file download occuring?
                                    if (document.cookie.indexOf(settings.cookieName + "=" + settings.cookieValue) != -1) {

                                                //execute specified callback
                                                internalCallbacks.onSuccess(fileUrl);

                                                //remove the cookie and iframe
                                                var date = new Date(1000);
                                                document.cookie = settings.cookieName + "=; expires=" + date.toUTCString() + "; path=" + settings.cookiePath;

                                                cleanUp(false);

                                                return;
                                    }

                                    //has an error occured?
                                    //if neither containers exist below then the file download is occuring on the current window
                                    if (downloadWindow || $iframe) {

                                                //has an error occured?
                                                try {

                                                            var formDoc;
                                                            if (downloadWindow) {
                                                                        formDoc = downloadWindow.document;
                                                            } else {
                                                                        formDoc = getiframeDocument($iframe);
                                                            }

                                                            if (formDoc && formDoc.body != null && formDoc.body.innerHTML.length > 0) {

                                                                        var isFailure = true;

                                                                        if ($form && $form.length > 0) {
                                                                                    var $contents = $(formDoc.body).contents().first();

                                                                                    if ($contents.length > 0 && $contents[0] === $form[0]) {
                                                                                                isFailure = false;
                                                                                    }
                                                                        }

                                                                        if (isFailure) {
                                                                                    internalCallbacks.onFail(formDoc.body.innerHTML, fileUrl);

                                                                                    cleanUp(true);

                                                                                    return;
                                                                        }
                                                            }
                                                } catch (err) {

                                                            //500 error less than IE9
                                                            internalCallbacks.onFail('', fileUrl);

                                                            cleanUp(true);

                                                            return;
                                                }
                                    }

                                    //keep checking...
                                    setTimeout(checkFileDownloadComplete, settings.checkInterval);
                        }

                        //gets an iframes document in a cross browser compatible manner
                        function getiframeDocument($iframe) {
                                    var iframeDoc = $iframe[0].contentWindow || $iframe[0].contentDocument;
                                    if (iframeDoc.document) {
                                                iframeDoc = iframeDoc.document;
                                    }
                                    return iframeDoc;
                        }

                        function cleanUp(isFailure) {

                                    setTimeout(function () {

                                                if (downloadWindow) {

                                                            if (isAndroid) {
                                                                        downloadWindow.close();
                                                            }

                                                            if (isIos) {
                                                                        if (isFailure) {
                                                                                    downloadWindow.focus(); //ios safari bug doesn't allow a window to be closed unless it is focused
                                                                                    downloadWindow.close();
                                                                        } else {
                                                                                    downloadWindow.focus();
                                                                        }
                                                            }
                                                }
                                    }, 0);
                        }

                        function htmlSpecialCharsEntityEncode(str) {
                                    return str.replace(/&/gm, '&amp;').replace(/\n/gm, "&#10;").replace(/\r/gm, "&#13;").replace(/</gm, '&lt;').replace(/>/gm, '&gt;').replace(/"/gm, '&quot;').replace(/'/gm, '&apos;'); //single quotes just to be safe
                        }
            }
});
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))

/***/ }),
/* 195 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function(jQuery) {var _typeof = typeof Symbol === "function" && typeof Symbol.iterator === "symbol" ? function (obj) { return typeof obj; } : function (obj) { return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj; };

/*!
 * jQuery Form Plugin
 * version: 2.93 (30-NOV-2011)
 * @requires jQuery v1.3.2 or later
 *
 * Examples and documentation at: http://malsup.com/jquery/form/
 * Dual licensed under the MIT and GPL licenses:
 *	http://www.opensource.org/licenses/mit-license.php
 *	http://www.gnu.org/licenses/gpl.html
 */
(function ($) {

	/*
 	Usage Note:
 	-----------
 	Do not use both ajaxSubmit and ajaxForm on the same form.  These
 	functions are intended to be exclusive.  Use ajaxSubmit if you want
 	to bind your own submit handler to the form.  For example,
 
 	$(document).ready(function() {
 		$('#myForm').bind('submit', function(e) {
 			e.preventDefault(); // <-- important
 			$(this).ajaxSubmit({
 				target: '#output'
 			});
 		});
 	});
 
 	Use ajaxForm when you want the plugin to manage all the event binding
 	for you.  For example,
 
 	$(document).ready(function() {
 		$('#myForm').ajaxForm({
 			target: '#output'
 		});
 	});
 
 	When using ajaxForm, the ajaxSubmit function will be invoked for you
 	at the appropriate time.
 */

	/**
  * ajaxSubmit() provides a mechanism for immediately submitting
  * an HTML form using AJAX.
  */
	$.fn.ajaxSubmit = function (options) {
		// fast fail if nothing selected (http://dev.jquery.com/ticket/2752)
		if (!this.length) {
			log('ajaxSubmit: skipping submit process - no element selected');
			return this;
		}

		var method,
		    action,
		    url,
		    $form = this;

		if (typeof options == 'function') {
			options = { success: options };
		}

		method = this.attr('method');
		action = this.attr('action');
		url = typeof action === 'string' ? $.trim(action) : '';
		url = url || window.location.href || '';
		if (url) {
			// clean url (don't include hash vaue)
			url = (url.match(/^([^#]+)/) || [])[1];
		}

		options = $.extend(true, {
			url: url,
			success: $.ajaxSettings.success,
			type: method || 'GET',
			iframeSrc: /^https/i.test(window.location.href || '') ? 'javascript:false' : 'about:blank'
		}, options);

		// hook for manipulating the form data before it is extracted;
		// convenient for use with rich editors like tinyMCE or FCKEditor
		var veto = {};
		this.trigger('form-pre-serialize', [this, options, veto]);
		if (veto.veto) {
			log('ajaxSubmit: submit vetoed via form-pre-serialize trigger');
			return this;
		}

		// provide opportunity to alter form data before it is serialized
		if (options.beforeSerialize && options.beforeSerialize(this, options) === false) {
			log('ajaxSubmit: submit aborted via beforeSerialize callback');
			return this;
		}

		var traditional = options.traditional;
		if (traditional === undefined) {
			traditional = $.ajaxSettings.traditional;
		}

		var qx,
		    n,
		    v,
		    a = options.propperFormSerialization !== false ? this.formToArray(options.semantic) : [];
		if (options.data) {
			options.extraData = options.data;
			qx = $.param(options.data, traditional);
		}

		// give pre-submit callback an opportunity to abort the submit
		if (options.beforeSubmit && options.beforeSubmit(a, this, options) === false) {
			log('ajaxSubmit: submit aborted via beforeSubmit callback');
			return this;
		}

		// fire vetoable 'validate' event
		this.trigger('form-submit-validate', [a, this, options, veto]);
		if (veto.veto) {
			log('ajaxSubmit: submit vetoed via form-submit-validate trigger');
			return this;
		}

		var q = $.param(a, traditional);
		if (qx) {
			q = q ? q + '&' + qx : qx;
		}
		if (options.type.toUpperCase() == 'GET') {
			options.url += (options.url.indexOf('?') >= 0 ? '&' : '?') + q;
			options.data = null; // data is null for 'get'
		} else {
			options.data = q; // data is the query string for 'post'
		}

		var callbacks = [];
		if (options.resetForm) {
			callbacks.push(function () {
				$form.resetForm();
			});
		}
		if (options.clearForm) {
			callbacks.push(function () {
				$form.clearForm(options.includeHidden);
			});
		}

		// perform a load on the target only if dataType is not provided
		if (!options.dataType && options.target) {
			var oldSuccess = options.success || function () {};
			callbacks.push(function (data) {
				var fn = options.replaceTarget ? 'replaceWith' : 'html';
				$(options.target)[fn](data).each(oldSuccess, arguments);
			});
		} else if (options.success) {
			callbacks.push(options.success);
		}

		options.success = function (data, status, xhr) {
			// jQuery 1.4+ passes xhr as 3rd arg
			var context = options.context || options; // jQuery 1.4+ supports scope context
			for (var i = 0, max = callbacks.length; i < max; i++) {
				callbacks[i].apply(context, [data, status, xhr || $form, $form]);
			}
		};

		// are there files to upload?
		var fileInputs = $('input:file:enabled[value]', this); // [value] (issue #113)
		var hasFileInputs = fileInputs.length > 0;
		var mp = 'multipart/form-data';
		var multipart = $form.attr('enctype') == mp || $form.attr('encoding') == mp;

		var fileAPI = !!(hasFileInputs && fileInputs.get(0).files && window.FormData);
		log('fileAPI :' + fileAPI);
		var shouldUseFrame = (hasFileInputs || multipart) && !fileAPI;

		// options.iframe allows user to force iframe mode
		// 06-NOV-09: now defaulting to iframe mode if file input is detected
		if (options.iframe !== false && (options.iframe || shouldUseFrame)) {
			// hack to fix Safari hang (thanks to Tim Molendijk for this)
			// see:  http://groups.google.com/group/jquery-dev/browse_thread/thread/36395b7ab510dd5d
			if (options.closeKeepAlive) {
				$.get(options.closeKeepAlive, function () {
					fileUploadIframe(a);
				});
			} else {
				fileUploadIframe(a);
			}
		} else if ((hasFileInputs || multipart) && fileAPI) {
			options.progress = options.progress || $.noop;
			fileUploadXhr(a);
		} else {
			$.ajax(options);
		}

		// fire 'notify' event
		this.trigger('form-submit-notify', [this, options]);
		return this;

		// XMLHttpRequest Level 2 file uploads (big hat tip to francois2metz)
		function fileUploadXhr(a) {
			var formdata = new FormData();

			for (var i = 0; i < a.length; i++) {
				if (a[i].type == 'file') continue;
				formdata.append(a[i].name, a[i].value);
			}

			$form.find('input:file:enabled').each(function () {
				var name = $(this).attr('name'),
				    files = this.files;
				if (name) {
					for (var i = 0; i < files.length; i++) {
						formdata.append(name, files[i]);
					}
				}
			});

			if (options.extraData) {
				for (var k in options.extraData) {
					formdata.append(k, options.extraData[k]);
				}
			}

			options.data = null;
			var _beforeSend = options.beforeSend;
			options.beforeSend = function (xhr, options) {
				options.data = formdata;
				if (xhr.upload) {
					// unfortunately, jQuery doesn't expose this prop (http://bugs.jquery.com/ticket/10190)
					xhr.upload.onprogress = function (event) {
						options.progress(event.position, event.total);
					};
				}
				if (_beforeSend) _beforeSend.call(options, xhr, options);
			};
			$.ajax(options);
		}

		// private function for handling file uploads (hat tip to YAHOO!)
		function fileUploadIframe(a) {
			var form = $form[0],
			    el,
			    i,
			    s,
			    g,
			    id,
			    $io,
			    io,
			    xhr,
			    sub,
			    n,
			    timedOut,
			    timeoutHandle;
			var useProp = !!$.fn.prop;

			if (a) {
				if (useProp) {
					// ensure that every serialized input is still enabled
					for (i = 0; i < a.length; i++) {
						el = $(form[a[i].name]);
						el.prop('disabled', false);
					}
				} else {
					for (i = 0; i < a.length; i++) {
						el = $(form[a[i].name]);
						el.removeAttr('disabled');
					}
				}
			}

			if ($(':input[name=submit],:input[id=submit]', form).length) {
				// if there is an input with a name or id of 'submit' then we won't be
				// able to invoke the submit fn on the form (at least not x-browser)
				alert('Error: Form elements must not have name or id of "submit".');
				return;
			}

			s = $.extend(true, {}, $.ajaxSettings, options);
			s.context = s.context || s;
			id = 'jqFormIO' + new Date().getTime();
			if (s.iframeTarget) {
				$io = $(s.iframeTarget);
				n = $io.attr('name');
				if (n == null) $io.attr('name', id);else id = n;
			} else {
				$io = $('<iframe name="' + id + '" src="' + s.iframeSrc + '" />');
				$io.css({ position: 'absolute', top: '-1000px', left: '-1000px' });
			}
			io = $io[0];

			xhr = { // mock object
				aborted: 0,
				responseText: null,
				responseXML: null,
				status: 0,
				statusText: 'n/a',
				getAllResponseHeaders: function getAllResponseHeaders() {},
				getResponseHeader: function getResponseHeader() {},
				setRequestHeader: function setRequestHeader() {},
				abort: function abort(status) {
					var e = status === 'timeout' ? 'timeout' : 'aborted';
					log('aborting upload... ' + e);
					this.aborted = 1;
					$io.attr('src', s.iframeSrc); // abort op in progress
					xhr.error = e;
					s.error && s.error.call(s.context, xhr, e, status);
					g && $.event.trigger('ajaxError', [xhr, s, e]);
					s.complete && s.complete.call(s.context, xhr, e);
				}
			};

			g = s.global;
			// trigger ajax global events so that activity/block indicators work like normal
			if (g && !$.active++) {
				$.event.trigger('ajaxStart');
			}
			if (g) {
				$.event.trigger('ajaxSend', [xhr, s]);
			}

			if (s.beforeSend && s.beforeSend.call(s.context, xhr, s) === false) {
				if (s.global) {
					$.active--;
				}
				return;
			}
			if (xhr.aborted) {
				return;
			}

			// add submitting element to data if we know it
			sub = form.clk;
			if (sub) {
				n = sub.name;
				if (n && !sub.disabled) {
					s.extraData = s.extraData || {};
					s.extraData[n] = sub.value;
					if (sub.type == 'image') {
						s.extraData[n + '.x'] = form.clk_x;
						s.extraData[n + '.y'] = form.clk_y;
					}
				}
			}

			var CLIENT_TIMEOUT_ABORT = 1;
			var SERVER_ABORT = 2;

			function getDoc(frame) {
				var doc = frame.contentWindow ? frame.contentWindow.document : frame.contentDocument ? frame.contentDocument : frame.document;
				return doc;
			}

			// Rails CSRF hack (thanks to Yvan BARTHƒLEMY)
			var csrf_token = $('meta[name=csrf-token]').attr('content');
			var csrf_param = $('meta[name=csrf-param]').attr('content');
			if (csrf_param && csrf_token) {
				s.extraData = s.extraData || {};
				s.extraData[csrf_param] = csrf_token;
			}

			// take a breath so that pending repaints get some cpu time before the upload starts
			function doSubmit() {
				// make sure form attrs are set
				var t = $form.attr('target'),
				    a = $form.attr('action');

				// update form attrs in IE friendly way
				form.setAttribute('target', id);
				if (!method) {
					form.setAttribute('method', 'POST');
				}
				if (a != s.url) {
					form.setAttribute('action', s.url);
				}

				// ie borks in some cases when setting encoding
				if (!s.skipEncodingOverride && (!method || /post/i.test(method))) {
					$form.attr({
						encoding: 'multipart/form-data',
						enctype: 'multipart/form-data'
					});
				}

				// support timout
				if (s.timeout) {
					timeoutHandle = setTimeout(function () {
						timedOut = true;cb(CLIENT_TIMEOUT_ABORT);
					}, s.timeout);
				}

				// look for server aborts
				function checkState() {
					try {
						var state = getDoc(io).readyState;
						log('state = ' + state);
						if (state.toLowerCase() == 'uninitialized') setTimeout(checkState, 50);
					} catch (e) {
						log('Server abort: ', e, ' (', e.name, ')');
						cb(SERVER_ABORT);
						timeoutHandle && clearTimeout(timeoutHandle);
						timeoutHandle = undefined;
					}
				}

				// add "extra" data to form if provided in options
				var extraInputs = [];
				try {
					if (s.extraData) {
						for (var n in s.extraData) {
							extraInputs.push($('<input type="hidden" name="' + n + '">').attr('value', s.extraData[n]).appendTo(form)[0]);
						}
					}

					if (!s.iframeTarget) {
						// add iframe to doc and submit the form
						$io.appendTo('body');
						io.attachEvent ? io.attachEvent('onload', cb) : io.addEventListener('load', cb, false);
					}
					setTimeout(checkState, 15);
					form.submit();
				} finally {
					// reset attrs and remove "extra" input elements
					form.setAttribute('action', a);
					if (t) {
						form.setAttribute('target', t);
					} else {
						$form.removeAttr('target');
					}
					$(extraInputs).remove();
				}
			}

			if (s.forceSync) {
				doSubmit();
			} else {
				setTimeout(doSubmit, 10); // this lets dom updates render
			}

			var data,
			    doc,
			    domCheckCount = 50,
			    callbackProcessed;

			function cb(e) {
				if (xhr.aborted || callbackProcessed) {
					return;
				}
				try {
					doc = getDoc(io);
				} catch (ex) {
					log('cannot access response document: ', ex);
					e = SERVER_ABORT;
				}
				if (e === CLIENT_TIMEOUT_ABORT && xhr) {
					xhr.abort('timeout');
					return;
				} else if (e == SERVER_ABORT && xhr) {
					xhr.abort('server abort');
					return;
				}

				if (!doc || doc.location.href == s.iframeSrc) {
					// response not received yet
					if (!timedOut) return;
				}
				io.detachEvent ? io.detachEvent('onload', cb) : io.removeEventListener('load', cb, false);

				var status = 'success',
				    errMsg;
				try {
					if (timedOut) {
						throw 'timeout';
					}

					var isXml = s.dataType == 'xml' || doc.XMLDocument || $.isXMLDoc(doc);
					log('isXml=' + isXml);
					if (!isXml && window.opera && (doc.body == null || doc.body.innerHTML == '')) {
						if (--domCheckCount) {
							// in some browsers (Opera) the iframe DOM is not always traversable when
							// the onload callback fires, so we loop a bit to accommodate
							log('requeing onLoad callback, DOM not available');
							setTimeout(cb, 250);
							return;
						}
						// let this fall through because server response could be an empty document
						//log('Could not access iframe DOM after mutiple tries.');
						//throw 'DOMException: not available';
					}

					//log('response detected');
					var docRoot = doc.body ? doc.body : doc.documentElement;
					xhr.responseText = docRoot ? docRoot.innerHTML : null;
					xhr.responseXML = doc.XMLDocument ? doc.XMLDocument : doc;
					if (isXml) s.dataType = 'xml';
					xhr.getResponseHeader = function (header) {
						var headers = { 'content-type': s.dataType };
						return headers[header];
					};
					// support for XHR 'status' & 'statusText' emulation :
					if (docRoot) {
						xhr.status = Number(docRoot.getAttribute('status')) || xhr.status;
						xhr.statusText = docRoot.getAttribute('statusText') || xhr.statusText;
					}

					var dt = (s.dataType || '').toLowerCase();
					var scr = /(json|script|text)/.test(dt);
					if (scr || s.textarea) {

						var documentContent, isTextArea;
						// see if user embedded response in textarea
						try {
							documentContent = $($(doc).text());
							isTextArea = documentContent.is('textarea');
						} catch (e) {
							isTextArea = false;
						}

						//					var ta = doc.getElementsByTagName('textarea')[0];
						if (isTextArea) {
							xhr.responseText = documentContent.text();
							// support for XHR 'status' & 'statusText' emulation :
							xhr.status = Number(documentContent.attr('status')) || xhr.status;
							xhr.statusText = documentContent.attr('statusText') || xhr.statusText;
						} else if (scr) {
							// account for browsers injecting pre around json response
							var pre = doc.getElementsByTagName('pre')[0];
							var b = doc.getElementsByTagName('body')[0];
							if (pre) {
								xhr.responseText = pre.textContent ? pre.textContent : pre.innerText;
							} else if (b) {
								xhr.responseText = b.textContent ? b.textContent : b.innerText;
							}
						}
					} else if (dt == 'xml' && !xhr.responseXML && xhr.responseText != null) {
						xhr.responseXML = toXml(xhr.responseText);
					}

					try {
						data = httpData(xhr, dt, s);
					} catch (e) {
						status = 'parsererror';
						xhr.error = errMsg = e || status;
					}
				} catch (e) {
					log('error caught: ', e);
					status = 'error';
					xhr.error = errMsg = e || status;
				}

				if (xhr.aborted) {
					log('upload aborted');
					status = null;
				}

				if (xhr.status) {
					// we've set xhr.status
					status = xhr.status >= 200 && xhr.status < 300 || xhr.status === 304 ? 'success' : 'error';
				}

				// ordering of these callbacks/triggers is odd, but that's how $.ajax does it
				if (status === 'success') {
					s.success && s.success.call(s.context, data, 'success', xhr);
					g && $.event.trigger('ajaxSuccess', [xhr, s]);
				} else if (status) {
					if (errMsg == undefined) errMsg = xhr.statusText;
					s.error && s.error.call(s.context, xhr, status, errMsg);
					g && $.event.trigger('ajaxError', [xhr, s, errMsg]);
				}

				g && $.event.trigger('ajaxComplete', [xhr, s]);

				if (g && ! --$.active) {
					$.event.trigger('ajaxStop');
				}

				s.complete && s.complete.call(s.context, xhr, status);

				callbackProcessed = true;
				if (s.timeout) clearTimeout(timeoutHandle);

				// clean up
				setTimeout(function () {
					if (!s.iframeTarget) $io.remove();
					xhr.responseXML = null;
				}, 100);
			}

			var toXml = $.parseXML || function (s, doc) {
				// use parseXML if available (jQuery 1.5+)
				if (window.ActiveXObject) {
					doc = new ActiveXObject('Microsoft.XMLDOM');
					doc.async = 'false';
					doc.loadXML(s);
				} else {
					doc = new DOMParser().parseFromString(s, 'text/xml');
				}
				return doc && doc.documentElement && doc.documentElement.nodeName != 'parsererror' ? doc : null;
			};
			var parseJSON = $.parseJSON || function (s) {
				return window['eval']('(' + s + ')');
			};

			var httpData = function httpData(xhr, type, s) {
				// mostly lifted from jq1.4.4

				var ct = xhr.getResponseHeader('content-type') || '',
				    xml = type === 'xml' || !type && ct.indexOf('xml') >= 0,
				    data = xml ? xhr.responseXML : xhr.responseText;

				if (xml && data.documentElement.nodeName === 'parsererror') {
					$.error && $.error('parsererror');
				}
				if (s && s.dataFilter) {
					data = s.dataFilter(data, type);
				}
				if (typeof data === 'string') {
					if (type === 'json' || !type && ct.indexOf('json') >= 0) {
						data = parseJSON(data);
					} else if (type === 'script' || !type && ct.indexOf('javascript') >= 0) {
						$.globalEval(data);
					}
				}
				return data;
			};
		}
	};

	/**
 * ajaxForm() provides a mechanism for fully automating form submission.
 *
 * The advantages of using this method instead of ajaxSubmit() are:
 *
 * 1: This method will include coordinates for <input type="image" /> elements (if the element
 *	is used to submit the form).
 * 2. This method will include the submit element's name/value data (for the element that was
 *	used to submit the form).
 * 3. This method binds the submit() method to the form for you.
 *
 * The options argument for ajaxForm works exactly as it does for ajaxSubmit.  ajaxForm merely
 * passes the options argument along after properly binding events for submit elements and
 * the form itself.
 */
	$.fn.ajaxForm = function (options) {
		// in jQuery 1.3+ we can fix mistakes with the ready state
		if (this.length === 0) {
			var o = { s: this.selector, c: this.context };
			if (!$.isReady && o.s) {
				log('DOM not ready, queuing ajaxForm');
				$(function () {
					$(o.s, o.c).ajaxForm(options);
				});
				return this;
			}
			// is your DOM ready?  http://docs.jquery.com/Tutorials:Introducing_$(document).ready()
			log('terminating; zero elements found by selector' + ($.isReady ? '' : ' (DOM not ready)'));
			return this;
		}

		return this.ajaxFormUnbind().bind('submit.form-plugin', function (e) {
			if (!e.isDefaultPrevented()) {
				// if event has been canceled, don't proceed
				e.preventDefault();
				$(this).ajaxSubmit(options);
			}
		}).bind('click.form-plugin', function (e) {
			var target = e.target;
			var $el = $(target);
			if (!$el.is(':submit,input:image')) {
				// is this a child element of the submit el?  (ex: a span within a button)
				var t = $el.closest(':submit');
				if (t.length == 0) {
					return;
				}
				target = t[0];
			}
			var form = this;
			form.clk = target;
			if (target.type == 'image') {
				if (e.offsetX != undefined) {
					form.clk_x = e.offsetX;
					form.clk_y = e.offsetY;
				} else if (typeof $.fn.offset == 'function') {
					// try to use dimensions plugin
					var offset = $el.offset();
					form.clk_x = e.pageX - offset.left;
					form.clk_y = e.pageY - offset.top;
				} else {
					form.clk_x = e.pageX - target.offsetLeft;
					form.clk_y = e.pageY - target.offsetTop;
				}
			}
			// clear form vars
			setTimeout(function () {
				form.clk = form.clk_x = form.clk_y = null;
			}, 100);
		});
	};

	// ajaxFormUnbind unbinds the event handlers that were bound by ajaxForm
	$.fn.ajaxFormUnbind = function () {
		return this.unbind('submit.form-plugin click.form-plugin');
	};

	/**
 * formToArray() gathers form element data into an array of objects that can
 * be passed to any of the following ajax functions: $.get, $.post, or load.
 * Each object in the array has both a 'name' and 'value' property.  An example of
 * an array for a simple login form might be:
 *
 * [ { name: 'username', value: 'jresig' }, { name: 'password', value: 'secret' } ]
 *
 * It is this array that is passed to pre-submit callback functions provided to the
 * ajaxSubmit() and ajaxForm() methods.
 */
	$.fn.formToArray = function (semantic) {
		var a = [];
		if (this.length === 0) {
			return a;
		}

		var form = this[0];
		var els = semantic ? form.getElementsByTagName('*') : form.elements;
		if (!els) {
			return a;
		}

		var i, j, n, v, el, max, jmax;
		for (i = 0, max = els.length; i < max; i++) {
			el = els[i];
			n = el.name;
			if (!n) {
				continue;
			}

			if (semantic && form.clk && el.type == 'image') {
				// handle image inputs on the fly when semantic == true
				if (!el.disabled && form.clk == el) {
					a.push({ name: n, value: $(el).val(), type: el.type });
					a.push({ name: n + '.x', value: form.clk_x }, { name: n + '.y', value: form.clk_y });
				}
				continue;
			}

			v = $.fieldValue(el, true);
			if (v && v.constructor == Array) {
				for (j = 0, jmax = v.length; j < jmax; j++) {
					a.push({ name: n, value: v[j] });
				}
			} else if (v !== null && typeof v != 'undefined') {
				a.push({ name: n, value: v, type: el.type });
			}
		}

		if (!semantic && form.clk) {
			// input type=='image' are not found in elements array! handle it here
			var $input = $(form.clk),
			    input = $input[0];
			n = input.name;
			if (n && !input.disabled && input.type == 'image') {
				a.push({ name: n, value: $input.val() });
				a.push({ name: n + '.x', value: form.clk_x }, { name: n + '.y', value: form.clk_y });
			}
		}
		return a;
	};

	/**
 * Serializes form data into a 'submittable' string. This method will return a string
 * in the format: name1=value1&amp;name2=value2
 */
	$.fn.formSerialize = function (semantic) {
		//hand off to jQuery.param for proper encoding
		return $.param(this.formToArray(semantic));
	};

	/**
 * Serializes all field elements in the jQuery object into a query string.
 * This method will return a string in the format: name1=value1&amp;name2=value2
 */
	$.fn.fieldSerialize = function (successful) {
		var a = [];
		this.each(function () {
			var n = this.name;
			if (!n) {
				return;
			}
			var v = $.fieldValue(this, successful);
			if (v && v.constructor == Array) {
				for (var i = 0, max = v.length; i < max; i++) {
					a.push({ name: n, value: v[i] });
				}
			} else if (v !== null && typeof v != 'undefined') {
				a.push({ name: this.name, value: v });
			}
		});
		//hand off to jQuery.param for proper encoding
		return $.param(a);
	};

	/**
 * Returns the value(s) of the element in the matched set.  For example, consider the following form:
 *
 *  <form><fieldset>
 *	  <input name="A" type="text" />
 *	  <input name="A" type="text" />
 *	  <input name="B" type="checkbox" value="B1" />
 *	  <input name="B" type="checkbox" value="B2"/>
 *	  <input name="C" type="radio" value="C1" />
 *	  <input name="C" type="radio" value="C2" />
 *  </fieldset></form>
 *
 *  var v = $(':text').fieldValue();
 *  // if no values are entered into the text inputs
 *  v == ['','']
 *  // if values entered into the text inputs are 'foo' and 'bar'
 *  v == ['foo','bar']
 *
 *  var v = $(':checkbox').fieldValue();
 *  // if neither checkbox is checked
 *  v === undefined
 *  // if both checkboxes are checked
 *  v == ['B1', 'B2']
 *
 *  var v = $(':radio').fieldValue();
 *  // if neither radio is checked
 *  v === undefined
 *  // if first radio is checked
 *  v == ['C1']
 *
 * The successful argument controls whether or not the field element must be 'successful'
 * (per http://www.w3.org/TR/html4/interact/forms.html#successful-controls).
 * The default value of the successful argument is true.  If this value is false the value(s)
 * for each element is returned.
 *
 * Note: This method *always* returns an array.  If no valid value can be determined the
 *	array will be empty, otherwise it will contain one or more values.
 */
	$.fn.fieldValue = function (successful) {
		for (var val = [], i = 0, max = this.length; i < max; i++) {
			var el = this[i];
			var v = $.fieldValue(el, successful);
			if (v === null || typeof v == 'undefined' || v.constructor == Array && !v.length) {
				continue;
			}
			v.constructor == Array ? $.merge(val, v) : val.push(v);
		}
		return val;
	};

	/**
 * Returns the value of the field element.
 */
	$.fieldValue = function (el, successful) {
		var n = el.name,
		    t = el.type,
		    tag = el.tagName.toLowerCase();
		if (successful === undefined) {
			successful = true;
		}

		if (successful && (!n || el.disabled || t == 'reset' || t == 'button' || (t == 'checkbox' || t == 'radio') && !el.checked || (t == 'submit' || t == 'image') && el.form && el.form.clk != el || tag == 'select' && el.selectedIndex == -1)) {
			return null;
		}

		if (tag == 'select') {
			var index = el.selectedIndex;
			if (index < 0) {
				return null;
			}
			var a = [],
			    ops = el.options;
			var one = t == 'select-one';
			var max = one ? index + 1 : ops.length;
			for (var i = one ? index : 0; i < max; i++) {
				var op = ops[i];
				if (op.selected) {
					var v = op.value;
					if (!v) {
						// extra pain for IE...
						v = op.attributes && op.attributes['value'] && !op.attributes['value'].specified ? op.text : op.value;
					}
					if (one) {
						return v;
					}
					a.push(v);
				}
			}
			return a;
		}
		return $(el).val();
	};

	/**
 * Clears the form data.  Takes the following actions on the form's input fields:
 *  - input text fields will have their 'value' property set to the empty string
 *  - select elements will have their 'selectedIndex' property set to -1
 *  - checkbox and radio inputs will have their 'checked' property set to false
 *  - inputs of type submit, button, reset, and hidden will *not* be effected
 *  - button elements will *not* be effected
 */
	$.fn.clearForm = function (includeHidden) {
		return this.each(function () {
			$('input,select,textarea', this).clearFields(includeHidden);
		});
	};

	/**
 * Clears the selected form elements.
 */
	$.fn.clearFields = $.fn.clearInputs = function (includeHidden) {
		var re = /^(?:color|date|datetime|email|month|number|password|range|search|tel|text|time|url|week)$/i; // 'hidden' is not in this list
		return this.each(function () {
			var t = this.type,
			    tag = this.tagName.toLowerCase();
			if (re.test(t) || tag == 'textarea' || includeHidden && /hidden/.test(t)) {
				this.value = '';
			} else if (t == 'checkbox' || t == 'radio') {
				this.checked = false;
			} else if (tag == 'select') {
				this.selectedIndex = -1;
			}
		});
	};

	/**
 * Resets the form data.  Causes all form elements to be reset to their original value.
 */
	$.fn.resetForm = function () {
		return this.each(function () {
			// guard against an input with the name of 'reset'
			// note that IE reports the reset function as an 'object'
			if (typeof this.reset == 'function' || _typeof(this.reset) == 'object' && !this.reset.nodeType) {
				this.reset();
			}
		});
	};

	/**
 * Enables or disables any matching elements.
 */
	$.fn.enable = function (b) {
		if (b === undefined) {
			b = true;
		}
		return this.each(function () {
			this.disabled = !b;
		});
	};

	/**
 * Checks/unchecks any matching checkboxes or radio buttons and
 * selects/deselects and matching option elements.
 */
	$.fn.selected = function (select) {
		if (select === undefined) {
			select = true;
		}
		return this.each(function () {
			var t = this.type;
			if (t == 'checkbox' || t == 'radio') {
				this.checked = select;
			} else if (this.tagName.toLowerCase() == 'option') {
				var $sel = $(this).parent('select');
				if (select && $sel[0] && $sel[0].type == 'select-one') {
					// deselect all other options
					$sel.find('option').selected(false);
				}
				this.selected = select;
			}
		});
	};

	// expose debug var
	$.fn.ajaxSubmit.debug = false;

	// helper fn for console logging
	function log() {
		if (!$.fn.ajaxSubmit.debug) return;
		var msg = '[jquery.form] ' + Array.prototype.join.call(arguments, '');
		if (window.console && window.console.log) {
			window.console.log(msg);
		} else if (window.opera && window.opera.postError) {
			window.opera.postError(msg);
		}
	}
})(jQuery);
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))

/***/ }),
/* 196 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function(jQuery) {/*
 * jQuery Hotkeys Plugin
 * Copyright 2010, John Resig
 * Dual licensed under the MIT or GPL Version 2 licenses.
 *
 * Based upon the plugin by Tzury Bar Yochay:
 * http://github.com/tzuryby/hotkeys
 *
 * Original idea by:
 * Binny V A, http://www.openjs.com/scripts/events/keyboard_shortcuts/
*/

(function (jQuery) {

	jQuery.hotkeys = {
		version: "0.8",

		specialKeys: {
			8: "backspace", 9: "tab", 13: "return", 16: "shift", 17: "ctrl", 18: "alt", 19: "pause",
			20: "capslock", 27: "esc", 32: "space", 33: "pageup", 34: "pagedown", 35: "end", 36: "home",
			37: "left", 38: "up", 39: "right", 40: "down", 45: "insert", 46: "del",
			96: "0", 97: "1", 98: "2", 99: "3", 100: "4", 101: "5", 102: "6", 103: "7",
			104: "8", 105: "9", 106: "*", 107: "+", 109: "-", 110: ".", 111: "/",
			112: "f1", 113: "f2", 114: "f3", 115: "f4", 116: "f5", 117: "f6", 118: "f7", 119: "f8",
			120: "f9", 121: "f10", 122: "f11", 123: "f12", 144: "numlock", 145: "scroll", 191: "/", 224: "meta"
		},

		shiftNums: {
			"`": "~", "1": "!", "2": "@", "3": "#", "4": "$", "5": "%", "6": "^", "7": "&",
			"8": "*", "9": "(", "0": ")", "-": "_", "=": "+", ";": ": ", "'": "\"", ",": "<",
			".": ">", "/": "?", "\\": "|"
		}
	};

	function keyHandler(handleObj) {
		// Only care when a possible input has been specified
		if (typeof handleObj.data !== "string") {
			return;
		}

		var origHandler = handleObj.handler,
		    keys = handleObj.data.toLowerCase().split(" ");

		handleObj.handler = function (event) {
			// Don't fire in text-accepting inputs that we didn't directly bind to
			if (this !== event.target && (/textarea|select/i.test(event.target.nodeName) || event.target.type === "text")) {
				return;
			}

			// Keypress represents characters, not special keys
			var special = event.type !== "keypress" && jQuery.hotkeys.specialKeys[event.which],
			    character = String.fromCharCode(event.which).toLowerCase(),
			    key,
			    modif = "",
			    possible = {};

			// check combinations (alt|ctrl|shift+anything)
			if (event.altKey && special !== "alt") {
				modif += "alt+";
			}

			if (event.ctrlKey && special !== "ctrl") {
				modif += "ctrl+";
			}

			// TODO: Need to make sure this works consistently across platforms
			if (event.metaKey && !event.ctrlKey && special !== "meta") {
				modif += "meta+";
			}

			if (event.shiftKey && special !== "shift") {
				modif += "shift+";
			}

			if (special) {
				possible[modif + special] = true;
			} else {
				possible[modif + character] = true;
				possible[modif + jQuery.hotkeys.shiftNums[character]] = true;

				// "$" can be triggered as "Shift+4" or "Shift+$" or just "$"
				if (modif === "shift+") {
					possible[jQuery.hotkeys.shiftNums[character]] = true;
				}
			}

			for (var i = 0, l = keys.length; i < l; i++) {
				if (possible[keys[i]]) {
					return origHandler.apply(this, arguments);
				}
			}
		};
	}

	jQuery.each(["keydown", "keyup", "keypress"], function () {
		jQuery.event.special[this] = { add: keyHandler };
	});
})(jQuery);
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))

/***/ }),
/* 197 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function(jQuery) {/*
 * jQuery Iframe Transport Plugin 1.2.4
 * https://github.com/blueimp/jQuery-File-Upload
 *
 * Copyright 2011, Sebastian Tschan
 * https://blueimp.net
 *
 * Licensed under the MIT license:
 * http://creativecommons.org/licenses/MIT/
 */

/*jslint unparam: true, nomen: true */
/*global jQuery, document */

(function ($) {
	'use strict';

	// Helper variable to create unique names for the transport iframes:

	var counter = 0;

	// The iframe transport accepts three additional options:
	// options.fileInput: a jQuery collection of file input fields
	// options.paramName: the parameter name for the file form data,
	//  overrides the name property of the file input field(s)
	// options.formData: an array of objects with name and value properties,
	//  equivalent to the return data of .serializeArray(), e.g.:
	//  [{name: 'a', value: 1}, {name: 'b', value: 2}]
	$.ajaxTransport('iframe', function (options) {
		if (options.async && (options.type === 'POST' || options.type === 'GET')) {
			var form, iframe;
			return {
				send: function send(_, completeCallback) {
					form = $('<form style="display:none;"></form>');
					// javascript:false as initial iframe src
					// prevents warning popups on HTTPS in IE6.
					// IE versions below IE8 cannot set the name property of
					// elements that have already been added to the DOM,
					// so we set the name along with the iframe HTML markup:

					if (options.url.indexOf('emulate_iframe_http_status') !== -1 && options.dataType.indexOf('iframe') !== -1) {
						options.dataType = options.dataType.split(' ')[1];
						options.dataTypes = options.dataTypes.slice(1);
					}

					var xhr = { // mock object
						aborted: 0,
						responseText: null,
						responseXML: null,
						status: 200,
						statusText: 'success',
						getAllResponseHeaders: function getAllResponseHeaders() {},
						getResponseHeader: function getResponseHeader() {},
						setRequestHeader: function setRequestHeader() {},
						abort: function abort(status) {
							var e = status === 'timeout' ? 'timeout' : 'aborted';
							log('aborting upload... ' + e);
							this.aborted = 1;
							$io.attr('src', s.iframeSrc); // abort op in progress
							xhr.error = e;
							s.error && s.error.call(s.context, xhr, e, status);
							g && $.event.trigger('ajaxError', [xhr, s, e]);
							s.complete && s.complete.call(s.context, xhr, e);
						}
					};

					iframe = $('<iframe src="javascript:false;" name="iframe-transport-' + (counter += 1) + '"></iframe>').bind('load', function () {
						var fileInputClones;
						iframe.unbind('load').bind('load', function () {
							var response;
							// Wrap in a try/catch block to catch exceptions thrown
							// when trying to access cross-domain iframe contents:
							try {

								response = iframe.contents();

								var frame = response;

								var doc = frame;
								var docRoot = $(document).find('body');
								var documentContent, isTextArea;
								// see if user embedded response in textarea
								try {
									documentContent = $($(doc).text());
									isTextArea = documentContent.is('textarea');
								} catch (e) {
									isTextArea = false;
								}
								if (isTextArea) {
									//                						xhr.responseText = documentContent.text();
									// support for XHR 'status' & 'statusText' emulation :
									xhr.status = Number(documentContent.attr('status')) || xhr.status;

									xhr.statusText = documentContent.attr('statusText') || xhr.statusText;

									xhr.responseText = { 'json': documentContent.text() };
								} else {

									xhr.responseText = { 'iframe': response };
									// Google Chrome and Firefox do not throw an
									// exception when calling iframe.contents() on
									// cross-domain requests, so we unify the response:
									if (!response.length || !response[0].firstChild) {
										throw new Error();
									}
								}
							} catch (e) {
								response = undefined;
							}
							// The complete callback returns the
							// iframe content document as response object:
							completeCallback(xhr.status, xhr.statusText, xhr.responseText);
							// Fix for IE endless progress bar activity bug
							// (happens on form submits to iframe targets):
							$('<iframe src="javascript:false;"></iframe>').appendTo(form);
							form.remove();
						});
						form.prop('target', iframe.prop('name')).prop('action', options.url).prop('method', options.type);
						if (options.formData) {
							$.each(options.formData, function (index, field) {
								$('<input type="hidden"/>').prop('name', field.name).val(field.value).appendTo(form);
							});
						}
						if (options.fileInput && options.fileInput.length && options.type === 'POST') {
							fileInputClones = options.fileInput.clone();
							// Insert a clone for each file input field:
							options.fileInput.after(function (index) {
								return fileInputClones[index];
							});
							if (options.paramName) {
								options.fileInput.each(function () {
									$(this).prop('name', options.paramName);
								});
							}
							// Appending the file input fields to the hidden form
							// removes them from their original location:
							form.append(options.fileInput).prop('enctype', 'multipart/form-data')
							// enctype must be set as encoding for IE:
							.prop('encoding', 'multipart/form-data');
						}
						form.submit();
						// Insert the file input fields at their original location
						// by replacing the clones with the originals:
						if (fileInputClones && fileInputClones.length) {
							options.fileInput.each(function (index, input) {
								var clone = $(fileInputClones[index]);
								$(input).prop('name', clone.prop('name'));
								clone.replaceWith(input);
							});
						}
					});
					form.append(iframe).appendTo(document.body);
				},
				abort: function abort() {
					if (iframe) {
						// javascript:false as iframe src aborts the request
						// and prevents warning popups on HTTPS in IE6.
						// concat is used to avoid the "Script URL" JSLint error:
						iframe.unbind('load').prop('src', 'javascript'.concat(':false;'));
					}
					if (form) {
						form.remove();
					}
				}
			};
		}
	});

	// The iframe transport returns the iframe content document as response.
	// The following adds converters from iframe to text, json, html, and script:
	$.ajaxSetup({
		converters: {
			'iframe text': function iframeText(iframe) {
				return iframe.find('body').text();
			},
			'iframe json': function iframeJson(iframe) {
				return $.parseJSON(iframe.find('body').text());
			},
			'iframe html': function iframeHtml(iframe) {
				return iframe.find('body').html();
			},
			'iframe script': function iframeScript(iframe) {
				return $.globalEval(iframe.find('body').text());
			}
		}
	});
})(jQuery);
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))

/***/ }),
/* 198 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;var _typeof = typeof Symbol === "function" && typeof Symbol.iterator === "symbol" ? function (obj) { return typeof obj; } : function (obj) { return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj; };

/*
 * jQuery JSON Plugin
 * version: 2.1 (2009-08-14)
 *
 * This document is licensed as free software under the terms of the
 * MIT License: http://www.opensource.org/licenses/mit-license.php
 *
 * Brantley Harris wrote this plugin. It is based somewhat on the JSON.org
 * website's http://www.json.org/json2.js, which proclaims:
 * "NO WARRANTY EXPRESSED OR IMPLIED. USE AT YOUR OWN RISK.", a sentiment that
 * I uphold.
 *
 * It is also influenced heavily by MochiKit's serializeJSON, which is
 * copyrighted 2005 by Bob Ippolito.
 */

;(function (factory) {
    if (true) {

        // AMD. Register as an anonymous module.
        !(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
    } else {

        // Browser globals
        factory(jQuery);
    }
})(function ($) {
    /** jQuery.toJSON( json-serializble )
        Converts the given argument into a JSON respresentation.
          If an object has a "toJSON" function, that will be used to get the representation.
        Non-integer/string keys are skipped in the object, as are keys that point to a function.
          json-serializble:
            The *thing* to be converted.
     **/
    $.toJSON = function (o) {
        if ((typeof JSON === "undefined" ? "undefined" : _typeof(JSON)) == 'object' && JSON.stringify) return JSON.stringify(o);

        var type = typeof o === "undefined" ? "undefined" : _typeof(o);

        if (o === null) return "null";

        if (type == "undefined") return undefined;

        if (type == "number" || type == "boolean") return o + "";

        if (type == "string") return $.quoteString(o);

        if (type == 'object') {
            if (typeof o.toJSON == "function") return $.toJSON(o.toJSON());

            if (o.constructor === Date) {
                var month = o.getUTCMonth() + 1;
                if (month < 10) month = '0' + month;

                var day = o.getUTCDate();
                if (day < 10) day = '0' + day;

                var year = o.getUTCFullYear();

                var hours = o.getUTCHours();
                if (hours < 10) hours = '0' + hours;

                var minutes = o.getUTCMinutes();
                if (minutes < 10) minutes = '0' + minutes;

                var seconds = o.getUTCSeconds();
                if (seconds < 10) seconds = '0' + seconds;

                var milli = o.getUTCMilliseconds();
                if (milli < 100) milli = '0' + milli;
                if (milli < 10) milli = '0' + milli;

                return '"' + year + '-' + month + '-' + day + 'T' + hours + ':' + minutes + ':' + seconds + '.' + milli + 'Z"';
            }

            if (o.constructor === Array) {
                var ret = [];
                for (var i = 0; i < o.length; i++) {
                    ret.push($.toJSON(o[i]) || "null");
                }return "[" + ret.join(",") + "]";
            }

            var pairs = [];
            for (var k in o) {
                var name;
                var type = typeof k === "undefined" ? "undefined" : _typeof(k);

                if (type == "number") name = '"' + k + '"';else if (type == "string") name = $.quoteString(k);else continue; //skip non-string or number keys

                if (typeof o[k] == "function") continue; //skip pairs where the value is a function.

                var val = $.toJSON(o[k]);

                pairs.push(name + ":" + val);
            }

            return "{" + pairs.join(", ") + "}";
        }
    };

    /** jQuery.evalJSON(src)
        Evaluates a given piece of json source.
     **/
    $.evalJSON = function (src) {
        if ((typeof JSON === "undefined" ? "undefined" : _typeof(JSON)) == 'object' && JSON.parse) return JSON.parse(src);
        return eval("(" + src + ")");
    };

    /** jQuery.secureEvalJSON(src)
        Evals JSON in a way that is *more* secure.
    **/
    $.secureEvalJSON = function (src) {
        if ((typeof JSON === "undefined" ? "undefined" : _typeof(JSON)) == 'object' && JSON.parse) return JSON.parse(src);

        var filtered = src;
        filtered = filtered.replace(/\\["\\\/bfnrtu]/g, '@');
        filtered = filtered.replace(/"[^"\\\n\r]*"|true|false|null|-?\d+(?:\.\d*)?(?:[eE][+\-]?\d+)?/g, ']');
        filtered = filtered.replace(/(?:^|:|,)(?:\s*\[)+/g, '');

        if (/^[\],:{}\s]*$/.test(filtered)) return eval("(" + src + ")");else throw new SyntaxError("Error parsing JSON, source is not valid.");
    };

    /** jQuery.quoteString(string)
        Returns a string-repr of a string, escaping quotes intelligently.
        Mostly a support function for toJSON.
          Examples:
            >>> jQuery.quoteString("apple")
            "apple"
              >>> jQuery.quoteString('"Where are we going?", she asked.')
            "\"Where are we going?\", she asked."
     **/
    $.quoteString = function (string) {
        if (string.match(_escapeable)) {
            return '"' + string.replace(_escapeable, function (a) {
                var c = _meta[a];
                if (typeof c === 'string') return c;
                c = a.charCodeAt();
                return "\\u00" + Math.floor(c / 16).toString(16) + (c % 16).toString(16);
            }) + '"';
        }
        return '"' + string + '"';
    };

    var _escapeable = /["\\\x00-\x1f\x7f-\x9f]/g;

    var _meta = {
        '\b': '\\b',
        '\t': '\\t',
        '\n': '\\n',
        '\f': '\\f',
        '\r': '\\r',
        '"': '\\"',
        '\\': '\\\\'
    };
});

/***/ }),
/* 199 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function(jQuery) {

// top wrapper to prevent multiple inclusion (is this OK?)
(function () {
	if (jQuery && jQuery.jstree) {
		return;
	}
	var is_ie6 = false,
	    is_ie7 = false,
	    is_ff2 = false;

	/* 
  * jsTree core
  */
	(function ($) {
		// Common functions not related to jsTree 
		// decided to move them to a `vakata` "namespace"
		$.vakata = {};
		// CSS related functions
		$.vakata.css = {
			get_css: function get_css(rule_name, delete_flag, sheet) {
				rule_name = rule_name.toLowerCase();
				var css_rules = sheet.cssRules || sheet.rules,
				    j = 0;
				do {
					if (css_rules.length && j > css_rules.length + 5) {
						return false;
					}
					if (css_rules[j].selectorText && css_rules[j].selectorText.toLowerCase() == rule_name) {
						if (delete_flag === true) {
							if (sheet.removeRule) {
								sheet.removeRule(j);
							}
							if (sheet.deleteRule) {
								sheet.deleteRule(j);
							}
							return true;
						} else {
							return css_rules[j];
						}
					}
				} while (css_rules[++j]);
				return false;
			},
			add_css: function add_css(rule_name, sheet) {
				if ($.jstree.css.get_css(rule_name, false, sheet)) {
					return false;
				}
				if (sheet.insertRule) {
					sheet.insertRule(rule_name + ' { }', 0);
				} else {
					sheet.addRule(rule_name, null, 0);
				}
				return $.vakata.css.get_css(rule_name);
			},
			remove_css: function remove_css(rule_name, sheet) {
				return $.vakata.css.get_css(rule_name, true, sheet);
			},
			add_sheet: function add_sheet(opts) {
				var tmp = false,
				    is_new = true;
				if (opts.str) {
					if (opts.title) {
						tmp = $("style[id='" + opts.title + "-stylesheet']")[0];
					}
					if (tmp) {
						is_new = false;
					} else {
						tmp = document.createElement("style");
						tmp.setAttribute('type', "text/css");
						if (opts.title) {
							tmp.setAttribute("id", opts.title + "-stylesheet");
						}
					}
					if (tmp.styleSheet) {
						if (is_new) {
							document.getElementsByTagName("head")[0].appendChild(tmp);
							tmp.styleSheet.cssText = opts.str;
						} else {
							tmp.styleSheet.cssText = tmp.styleSheet.cssText + " " + opts.str;
						}
					} else {
						tmp.appendChild(document.createTextNode(opts.str));
						document.getElementsByTagName("head")[0].appendChild(tmp);
					}
					return tmp.sheet || tmp.styleSheet;
				}
				if (opts.url) {
					if (document.createStyleSheet) {
						try {
							tmp = document.createStyleSheet(opts.url);
						} catch (e) {}
					} else {
						tmp = document.createElement('link');
						tmp.rel = 'stylesheet';
						tmp.type = 'text/css';
						tmp.media = "all";
						tmp.href = opts.url;
						document.getElementsByTagName("head")[0].appendChild(tmp);
						return tmp.styleSheet;
					}
				}
			}
		};

		// private variables 
		var instances = [],
		    // instance array (used by $.jstree.reference/create/focused)
		focused_instance = -1,
		    // the index in the instance array of the currently focused instance
		plugins = {},
		    // list of included plugins
		prepared_move = {}; // for the move_node function

		// jQuery plugin wrapper (thanks to jquery UI widget function)
		$.fn.jstree = function (settings) {
			var isMethodCall = typeof settings == 'string',
			    // is this a method call like $().jstree("open_node")
			args = Array.prototype.slice.call(arguments, 1),
			    returnValue = this;

			// if a method call execute the method on all selected instances
			if (isMethodCall) {
				if (settings.substring(0, 1) == '_') {
					return returnValue;
				}
				this.each(function () {
					var instance = instances[$.data(this, "jstree_instance_id")],
					    methodValue = instance && $.isFunction(instance[settings]) ? instance[settings].apply(instance, args) : instance;
					if (typeof methodValue !== "undefined" && (settings.indexOf("is_") === 0 || methodValue !== true && methodValue !== false)) {
						returnValue = methodValue;return false;
					}
				});
			} else {
				this.each(function () {
					// extend settings and allow for multiple hashes and $.data
					var instance_id = $.data(this, "jstree_instance_id"),
					    a = [],
					    b = settings ? $.extend({}, true, settings) : {},
					    c = $(this),
					    s = false,
					    t = [];
					a = a.concat(args);
					if (c.data("jstree")) {
						a.push(c.data("jstree"));
					}
					b = a.length ? $.extend.apply(null, [true, b].concat(a)) : b;

					// if an instance already exists, destroy it first
					if (typeof instance_id !== "undefined" && instances[instance_id]) {
						instances[instance_id].destroy();
					}
					// push a new empty object to the instances array
					instance_id = parseInt(instances.push({}), 10) - 1;
					// store the jstree instance id to the container element
					$.data(this, "jstree_instance_id", instance_id);
					// clean up all plugins
					b.plugins = $.isArray(b.plugins) ? b.plugins : $.jstree.defaults.plugins.slice();
					b.plugins.unshift("core");
					// only unique plugins
					b.plugins = b.plugins.sort().join(",,").replace(/(,|^)([^,]+)(,,\2)+(,|$)/g, "$1$2$4").replace(/,,+/g, ",").replace(/,$/, "").split(",");

					// extend defaults with passed data
					s = $.extend(true, {}, $.jstree.defaults, b);
					s.plugins = b.plugins;
					$.each(plugins, function (i, val) {
						if ($.inArray(i, s.plugins) === -1) {
							s[i] = null;delete s[i];
						} else {
							t.push(i);
						}
					});
					s.plugins = t;

					// push the new object to the instances array (at the same time set the default classes to the container) and init
					instances[instance_id] = new $.jstree._instance(instance_id, $(this).addClass("jstree jstree-" + instance_id), s);
					// init all activated plugins for this instance
					$.each(instances[instance_id]._get_settings().plugins, function (i, val) {
						instances[instance_id].data[val] = {};
					});
					$.each(instances[instance_id]._get_settings().plugins, function (i, val) {
						if (plugins[val]) {
							plugins[val].__init.apply(instances[instance_id]);
						}
					});
					// initialize the instance
					setTimeout(function () {
						if (instances[instance_id]) {
							instances[instance_id].init();
						}
					}, 0);
				});
			}
			// return the jquery selection (or if it was a method call that returned a value - the returned value)
			return returnValue;
		};
		// object to store exposed functions and objects
		$.jstree = {
			defaults: {
				plugins: []
			},
			_focused: function _focused() {
				return instances[focused_instance] || null;
			},
			_reference: function _reference(needle) {
				// get by instance id
				if (instances[needle]) {
					return instances[needle];
				}
				// get by DOM (if still no luck - return null
				var o = $(needle);
				if (!o.length && typeof needle === "string") {
					o = $("#" + needle);
				}
				if (!o.length) {
					return null;
				}
				return instances[o.closest(".jstree").data("jstree_instance_id")] || null;
			},
			_instance: function _instance(index, container, settings) {
				// for plugins to store data in
				this.data = { core: {} };
				this.get_settings = function () {
					return $.extend(true, {}, settings);
				};
				this._get_settings = function () {
					return settings;
				};
				this.get_index = function () {
					return index;
				};
				this.get_container = function () {
					return container;
				};
				this.get_container_ul = function () {
					return container.children("ul:eq(0)");
				};
				this._set_settings = function (s) {
					settings = $.extend(true, {}, settings, s);
				};
			},
			_fn: {},
			plugin: function plugin(pname, pdata) {
				pdata = $.extend({}, {
					__init: $.noop,
					__destroy: $.noop,
					_fn: {},
					defaults: false
				}, pdata);
				plugins[pname] = pdata;

				$.jstree.defaults[pname] = pdata.defaults;
				$.each(pdata._fn, function (i, val) {
					val.plugin = pname;
					val.old = $.jstree._fn[i];
					$.jstree._fn[i] = function () {
						var rslt,
						    func = val,
						    args = Array.prototype.slice.call(arguments),
						    evnt = new $.Event("before.jstree"),
						    rlbk = false;

						if (this.data.core.locked === true && i !== "unlock" && i !== "is_locked") {
							return;
						}

						// Check if function belongs to the included plugins of this instance
						do {
							if (func && func.plugin && $.inArray(func.plugin, this._get_settings().plugins) !== -1) {
								break;
							}
							func = func.old;
						} while (func);
						if (!func) {
							return;
						}

						// context and function to trigger events, then finally call the function
						if (i.indexOf("_") === 0) {
							rslt = func.apply(this, args);
						} else {
							rslt = this.get_container().triggerHandler(evnt, { "func": i, "inst": this, "args": args, "plugin": func.plugin });
							if (rslt === false) {
								return;
							}
							if (typeof rslt !== "undefined") {
								args = rslt;
							}

							rslt = func.apply($.extend({}, this, {
								__callback: function __callback(data) {
									this.get_container().triggerHandler(i + '.jstree', { "inst": this, "args": args, "rslt": data, "rlbk": rlbk });
								},
								__rollback: function __rollback() {
									rlbk = this.get_rollback();
									return rlbk;
								},
								__call_old: function __call_old(replace_arguments) {
									return func.old.apply(this, replace_arguments ? Array.prototype.slice.call(arguments, 1) : args);
								}
							}), args);
						}

						// return the result
						return rslt;
					};
					$.jstree._fn[i].old = val.old;
					$.jstree._fn[i].plugin = pname;
				});
			},
			rollback: function rollback(rb) {
				if (rb) {
					if (!$.isArray(rb)) {
						rb = [rb];
					}
					$.each(rb, function (i, val) {
						instances[val.i].set_rollback(val.h, val.d);
					});
				}
			}
		};
		// set the prototype for all instances
		$.jstree._fn = $.jstree._instance.prototype = {};

		// load the css when DOM is ready
		$(function () {
			// code is copied from jQuery ($.browser is deprecated + there is a bug in IE)
			var u = navigator.userAgent.toLowerCase(),
			    v = (u.match(/.+?(?:rv|it|ra|ie)[\/: ]([\d.]+)/) || [0, '0'])[1],
			    css_string = '' + '.jstree ul, .jstree li { display:block; margin:0 0 0 0; padding:0 0 0 0; list-style-type:none; } ' + '.jstree li { display:block; min-height:18px; line-height:18px; white-space:nowrap; margin-left:18px; min-width:18px; } ' + '.jstree-rtl li { margin-left:0; margin-right:18px; } ' + '.jstree > ul > li { margin-left:0px; } ' + '.jstree-rtl > ul > li { margin-right:0px; } ' + '.jstree ins { display:inline-block; text-decoration:none; width:18px; height:18px; margin:0 0 0 0; padding:0; } ' + '.jstree a { display:inline-block; line-height:16px; height:16px; color:black; white-space:nowrap; text-decoration:none; padding:1px 2px; margin:0; } ' + '.jstree a:focus { outline: none; } ' + '.jstree a > ins { height:16px; width:16px; } ' + '.jstree a > .jstree-icon { margin-right:3px; } ' + '.jstree-rtl a > .jstree-icon { margin-left:3px; margin-right:0; } ' + 'li.jstree-open > ul { display:block; } ' + 'li.jstree-closed > ul { display:none; } ';
			// Correct IE 6 (does not support the > CSS selector)
			if (/msie/.test(u) && parseInt(v, 10) == 6) {
				is_ie6 = true;

				// fix image flicker and lack of caching
				try {
					document.execCommand("BackgroundImageCache", false, true);
				} catch (err) {}

				css_string += '' + '.jstree li { height:18px; margin-left:0; margin-right:0; } ' + '.jstree li li { margin-left:18px; } ' + '.jstree-rtl li li { margin-left:0px; margin-right:18px; } ' + 'li.jstree-open ul { display:block; } ' + 'li.jstree-closed ul { display:none !important; } ' + '.jstree li a { display:inline; border-width:0 !important; padding:0px 2px !important; } ' + '.jstree li a ins { height:16px; width:16px; margin-right:3px; } ' + '.jstree-rtl li a ins { margin-right:0px; margin-left:3px; } ';
			}
			// Correct IE 7 (shifts anchor nodes onhover)
			if (/msie/.test(u) && parseInt(v, 10) == 7) {
				is_ie7 = true;
				css_string += '.jstree li a { border-width:0 !important; padding:0px 2px !important; } ';
			}
			// correct ff2 lack of display:inline-block
			if (!/compatible/.test(u) && /mozilla/.test(u) && parseFloat(v, 10) < 1.9) {
				is_ff2 = true;
				css_string += '' + '.jstree ins { display:-moz-inline-box; } ' + '.jstree li { line-height:12px; } ' + // WHY??
				'.jstree a { display:-moz-inline-box; } ' + '.jstree .jstree-no-icons .jstree-checkbox { display:-moz-inline-stack !important; } ';
				/* this shouldn't be here as it is theme specific */
			}
			// the default stylesheet
			$.vakata.css.add_sheet({ str: css_string, title: "jstree" });
		});

		// core functions (open, close, create, update, delete)
		$.jstree.plugin("core", {
			__init: function __init() {
				this.data.core.locked = false;
				this.data.core.to_open = this.get_settings().core.initially_open;
				this.data.core.to_load = this.get_settings().core.initially_load;
			},
			defaults: {
				html_titles: false,
				animation: 500,
				initially_open: [],
				initially_load: [],
				open_parents: true,
				notify_plugins: true,
				rtl: false,
				load_open: false,
				strings: {
					loading: "Loading ...",
					new_node: "New node",
					multiple_selection: "Multiple selection"
				}
			},
			_fn: {
				init: function init() {
					this.set_focus();
					if (this._get_settings().core.rtl) {
						this.get_container().addClass("jstree-rtl").css("direction", "rtl");
					}
					this.get_container().html("<ul><li class='jstree-last jstree-leaf'><ins>&#160;</ins><a class='jstree-loading' href='#'><ins class='jstree-icon'>&#160;</ins>" + this._get_string("loading") + "</a></li></ul>");
					this.data.core.li_height = this.get_container_ul().find("li.jstree-closed, li.jstree-leaf").eq(0).height() || 18;

					this.get_container().delegate("li > ins", "click.jstree", $.proxy(function (event) {
						var trgt = $(event.target);
						// if(trgt.is("ins") && event.pageY - trgt.offset().top < this.data.core.li_height) { this.toggle_node(trgt); }
						this.toggle_node(trgt);
					}, this)).bind("mousedown.jstree", $.proxy(function () {
						this.set_focus(); // This used to be setTimeout(set_focus,0) - why?
					}, this)).bind("dblclick.jstree", function (event) {
						var sel;
						if (document.selection && document.selection.empty) {
							document.selection.empty();
						} else {
							if (window.getSelection) {
								sel = window.getSelection();
								try {
									sel.removeAllRanges();
									sel.collapse();
								} catch (err) {}
							}
						}
					});
					if (this._get_settings().core.notify_plugins) {
						this.get_container().bind("load_node.jstree", $.proxy(function (e, data) {
							var o = this._get_node(data.rslt.obj),
							    t = this;
							if (o === -1) {
								o = this.get_container_ul();
							}
							if (!o.length) {
								return;
							}
							o.find("li").each(function () {
								var th = $(this);
								if (th.data("jstree")) {
									$.each(th.data("jstree"), function (plugin, values) {
										if (t.data[plugin] && $.isFunction(t["_" + plugin + "_notify"])) {
											t["_" + plugin + "_notify"].call(t, th, values);
										}
									});
								}
							});
						}, this));
					}
					if (this._get_settings().core.load_open) {
						this.get_container().bind("load_node.jstree", $.proxy(function (e, data) {
							var o = this._get_node(data.rslt.obj),
							    t = this;
							if (o === -1) {
								o = this.get_container_ul();
							}
							if (!o.length) {
								return;
							}
							o.find("li.jstree-open:not(:has(ul))").each(function () {
								t.load_node(this, $.noop, $.noop);
							});
						}, this));
					}
					this.__callback();
					this.load_node(-1, function () {
						this.loaded();this.reload_nodes();
					});
				},
				destroy: function destroy() {
					var i,
					    n = this.get_index(),
					    s = this._get_settings(),
					    _this = this;

					$.each(s.plugins, function (i, val) {
						try {
							plugins[val].__destroy.apply(_this);
						} catch (err) {}
					});
					this.__callback();
					// set focus to another instance if this one is focused
					if (this.is_focused()) {
						for (i in instances) {
							if (instances.hasOwnProperty(i) && i != n) {
								instances[i].set_focus();
								break;
							}
						}
					}
					// if no other instance found
					if (n === focused_instance) {
						focused_instance = -1;
					}
					// remove all traces of jstree in the DOM (only the ones set using jstree*) and cleans all events
					this.get_container().unbind(".jstree").undelegate(".jstree").removeData("jstree_instance_id").find("[class^='jstree']").andSelf().attr("class", function () {
						return this.className.replace(/jstree[^ ]*|$/ig, '');
					});
					$(document).unbind(".jstree-" + n).undelegate(".jstree-" + n);
					// remove the actual data
					instances[n] = null;
					delete instances[n];
				},

				_core_notify: function _core_notify(n, data) {
					if (data.opened) {
						this.open_node(n, false, true);
					}
				},

				lock: function lock() {
					this.data.core.locked = true;
					this.get_container().children("ul").addClass("jstree-locked").css("opacity", "0.7");
					this.__callback({});
				},
				unlock: function unlock() {
					this.data.core.locked = false;
					this.get_container().children("ul").removeClass("jstree-locked").css("opacity", "1");
					this.__callback({});
				},
				is_locked: function is_locked() {
					return this.data.core.locked;
				},
				save_opened: function save_opened() {
					var _this = this;
					this.data.core.to_open = [];
					this.get_container_ul().find("li.jstree-open").each(function () {
						if (this.id) {
							_this.data.core.to_open.push("#" + this.id.toString().replace(/^#/, "").replace(/\\\//g, "/").replace(/\//g, "\\\/").replace(/\\\./g, ".").replace(/\./g, "\\.").replace(/\:/g, "\\:"));
						}
					});
					this.__callback(_this.data.core.to_open);
				},
				save_loaded: function save_loaded() {},
				reload_nodes: function reload_nodes(is_callback) {
					var _this = this,
					    done = true,
					    current = [],
					    remaining = [];
					if (!is_callback) {
						this.data.core.reopen = false;
						this.data.core.refreshing = true;
						this.data.core.to_open = $.map($.makeArray(this.data.core.to_open), function (n) {
							return "#" + n.toString().replace(/^#/, "").replace(/\\\//g, "/").replace(/\//g, "\\\/").replace(/\\\./g, ".").replace(/\./g, "\\.").replace(/\:/g, "\\:");
						});
						this.data.core.to_load = $.map($.makeArray(this.data.core.to_load), function (n) {
							return "#" + n.toString().replace(/^#/, "").replace(/\\\//g, "/").replace(/\//g, "\\\/").replace(/\\\./g, ".").replace(/\./g, "\\.").replace(/\:/g, "\\:");
						});
						if (this.data.core.to_open.length) {
							this.data.core.to_load = this.data.core.to_load.concat(this.data.core.to_open);
						}
					}
					if (this.data.core.to_load.length) {
						$.each(this.data.core.to_load, function (i, val) {
							if (val == "#") {
								return true;
							}
							if ($(val).length) {
								current.push(val);
							} else {
								remaining.push(val);
							}
						});
						if (current.length) {
							this.data.core.to_load = remaining;
							$.each(current, function (i, val) {
								if (!_this._is_loaded(val)) {
									_this.load_node(val, function () {
										_this.reload_nodes(true);
									}, function () {
										_this.reload_nodes(true);
									});
									done = false;
								}
							});
						}
					}
					if (this.data.core.to_open.length) {
						$.each(this.data.core.to_open, function (i, val) {
							_this.open_node(val, false, true);
						});
					}
					if (done) {
						// TODO: find a more elegant approach to syncronizing returning requests
						if (this.data.core.reopen) {
							clearTimeout(this.data.core.reopen);
						}
						this.data.core.reopen = setTimeout(function () {
							_this.__callback({}, _this);
						}, 50);
						this.data.core.refreshing = false;
						this.reopen();
					}
				},
				reopen: function reopen() {
					var _this = this;
					if (this.data.core.to_open.length) {
						$.each(this.data.core.to_open, function (i, val) {
							_this.open_node(val, false, true);
						});
					}
					this.__callback({});
				},
				refresh: function refresh(obj) {
					var _this = this;
					this.save_opened();
					if (!obj) {
						obj = -1;
					}
					obj = this._get_node(obj);
					if (!obj) {
						obj = -1;
					}
					if (obj !== -1) {
						obj.children("UL").remove();
					} else {
						this.get_container_ul().empty();
					}
					this.load_node(obj, function () {
						_this.__callback({ "obj": obj });_this.reload_nodes();
					});
				},
				// Dummy function to fire after the first load (so that there is a jstree.loaded event)
				loaded: function loaded() {
					this.__callback();
				},
				// deal with focus
				set_focus: function set_focus() {
					if (this.is_focused()) {
						return;
					}
					var f = $.jstree._focused();
					if (f) {
						f.unset_focus();
					}

					this.get_container().addClass("jstree-focused");
					focused_instance = this.get_index();
					this.__callback();
				},
				is_focused: function is_focused() {
					return focused_instance == this.get_index();
				},
				unset_focus: function unset_focus() {
					if (this.is_focused()) {
						this.get_container().removeClass("jstree-focused");
						focused_instance = -1;
					}
					this.__callback();
				},

				// traverse
				_get_node: function _get_node(obj) {
					var $obj = $(obj, this.get_container());
					if ($obj.is(".jstree") || obj == -1) {
						return -1;
					}
					$obj = $obj.closest("li", this.get_container());
					return $obj.length ? $obj : false;
				},
				_get_next: function _get_next(obj, strict) {
					obj = this._get_node(obj);
					if (obj === -1) {
						return this.get_container().find("> ul > li:first-child");
					}
					if (!obj.length) {
						return false;
					}
					if (strict) {
						return obj.nextAll("li").size() > 0 ? obj.nextAll("li:eq(0)") : false;
					}

					if (obj.hasClass("jstree-open")) {
						return obj.find("li:eq(0)");
					} else if (obj.nextAll("li").size() > 0) {
						return obj.nextAll("li:eq(0)");
					} else {
						return obj.parentsUntil(".jstree", "li").next("li").eq(0);
					}
				},
				_get_prev: function _get_prev(obj, strict) {
					obj = this._get_node(obj);
					if (obj === -1) {
						return this.get_container().find("> ul > li:last-child");
					}
					if (!obj.length) {
						return false;
					}
					if (strict) {
						return obj.prevAll("li").length > 0 ? obj.prevAll("li:eq(0)") : false;
					}

					if (obj.prev("li").length) {
						obj = obj.prev("li").eq(0);
						while (obj.hasClass("jstree-open")) {
							obj = obj.children("ul:eq(0)").children("li:last");
						}
						return obj;
					} else {
						var o = obj.parentsUntil(".jstree", "li:eq(0)");return o.length ? o : false;
					}
				},
				_get_parent: function _get_parent(obj) {
					obj = this._get_node(obj);
					if (obj == -1 || !obj.length) {
						return false;
					}
					var o = obj.parentsUntil(".jstree", "li:eq(0)");
					return o.length ? o : -1;
				},
				_get_children: function _get_children(obj) {
					obj = this._get_node(obj);
					if (obj === -1) {
						return this.get_container().children("ul:eq(0)").children("li");
					}
					if (!obj.length) {
						return false;
					}
					return obj.children("ul:eq(0)").children("li");
				},
				get_path: function get_path(obj, id_mode) {
					var p = [],
					    _this = this;
					obj = this._get_node(obj);
					if (obj === -1 || !obj || !obj.length) {
						return false;
					}
					obj.parentsUntil(".jstree", "li").each(function () {
						p.push(id_mode ? this.id : _this.get_text(this));
					});
					p.reverse();
					p.push(id_mode ? obj.attr("id") : this.get_text(obj));
					return p;
				},

				// string functions
				_get_string: function _get_string(key) {
					return this._get_settings().core.strings[key] || key;
				},

				is_open: function is_open(obj) {
					obj = this._get_node(obj);return obj && obj !== -1 && obj.hasClass("jstree-open");
				},
				is_closed: function is_closed(obj) {
					obj = this._get_node(obj);return obj && obj !== -1 && obj.hasClass("jstree-closed");
				},
				is_leaf: function is_leaf(obj) {
					obj = this._get_node(obj);return obj && obj !== -1 && obj.hasClass("jstree-leaf");
				},
				correct_state: function correct_state(obj) {
					obj = this._get_node(obj);
					if (!obj || obj === -1) {
						return false;
					}
					obj.removeClass("jstree-closed jstree-open").addClass("jstree-leaf").children("ul").remove();
					this.__callback({ "obj": obj });
				},
				// open/close
				open_node: function open_node(obj, callback, skip_animation) {
					obj = this._get_node(obj);
					if (!obj.length) {
						return false;
					}
					if (!obj.hasClass("jstree-closed")) {
						if (callback) {
							callback.call();
						}return false;
					}
					var s = skip_animation || is_ie6 ? 0 : this._get_settings().core.animation,
					    t = this;
					if (!this._is_loaded(obj)) {
						obj.children("a").addClass("jstree-loading");
						this.load_node(obj, function () {
							t.open_node(obj, callback, skip_animation);
						}, callback);
					} else {
						if (this._get_settings().core.open_parents) {
							obj.parentsUntil(".jstree", ".jstree-closed").each(function () {
								t.open_node(this, false, true);
							});
						}
						if (s) {
							obj.children("ul").css("display", "none");
						}
						obj.removeClass("jstree-closed").addClass("jstree-open").children("a").removeClass("jstree-loading");
						if (s) {
							obj.children("ul").stop(true, true).slideDown(s, function () {
								this.style.display = "";t.after_open(obj);
							});
						} else {
							t.after_open(obj);
						}
						this.__callback({ "obj": obj });
						if (callback) {
							callback.call();
						}
					}
				},
				after_open: function after_open(obj) {
					this.__callback({ "obj": obj });
				},
				close_node: function close_node(obj, skip_animation) {
					obj = this._get_node(obj);
					var s = skip_animation || is_ie6 ? 0 : this._get_settings().core.animation,
					    t = this;
					if (!obj.length || !obj.hasClass("jstree-open")) {
						return false;
					}
					if (s) {
						obj.children("ul").attr("style", "display:block !important");
					}
					obj.removeClass("jstree-open").addClass("jstree-closed");
					if (s) {
						obj.children("ul").stop(true, true).slideUp(s, function () {
							this.style.display = "";t.after_close(obj);
						});
					} else {
						t.after_close(obj);
					}
					this.__callback({ "obj": obj });
				},
				after_close: function after_close(obj) {
					this.__callback({ "obj": obj });
				},
				toggle_node: function toggle_node(obj) {
					obj = this._get_node(obj);
					if (obj.hasClass("jstree-closed")) {
						return this.open_node(obj);
					}
					if (obj.hasClass("jstree-open")) {
						return this.close_node(obj);
					}
				},
				open_all: function open_all(obj, do_animation, original_obj) {
					obj = obj ? this._get_node(obj) : -1;
					if (!obj || obj === -1) {
						obj = this.get_container_ul();
					}
					if (original_obj) {
						obj = obj.find("li.jstree-closed");
					} else {
						original_obj = obj;
						if (obj.is(".jstree-closed")) {
							obj = obj.find("li.jstree-closed").andSelf();
						} else {
							obj = obj.find("li.jstree-closed");
						}
					}
					var _this = this;
					obj.each(function () {
						var __this = this;
						if (!_this._is_loaded(this)) {
							_this.open_node(this, function () {
								_this.open_all(__this, do_animation, original_obj);
							}, !do_animation);
						} else {
							_this.open_node(this, false, !do_animation);
						}
					});
					// so that callback is fired AFTER all nodes are open
					if (original_obj.find('li.jstree-closed').length === 0) {
						this.__callback({ "obj": original_obj });
					}
				},
				close_all: function close_all(obj, do_animation) {
					var _this = this;
					obj = obj ? this._get_node(obj) : this.get_container();
					if (!obj || obj === -1) {
						obj = this.get_container_ul();
					}
					obj.find("li.jstree-open").andSelf().each(function () {
						_this.close_node(this, !do_animation);
					});
					this.__callback({ "obj": obj });
				},
				clean_node: function clean_node(obj) {
					obj = obj && obj != -1 ? $(obj) : this.get_container_ul();
					obj = obj.is("li") ? obj.find("li").andSelf() : obj.find("li");
					obj.removeClass("jstree-last").filter("li:last-child").addClass("jstree-last").end().filter(":has(li)").not(".jstree-open").removeClass("jstree-leaf").addClass("jstree-closed");
					obj.not(".jstree-open, .jstree-closed").addClass("jstree-leaf").children("ul").remove();
					this.__callback({ "obj": obj });
				},
				// rollback
				get_rollback: function get_rollback() {
					this.__callback();
					return { i: this.get_index(), h: this.get_container().children("ul").clone(true), d: this.data };
				},
				set_rollback: function set_rollback(html, data) {
					this.get_container().empty().append(html);
					this.data = data;
					this.__callback();
				},
				// Dummy functions to be overwritten by any datastore plugin included
				load_node: function load_node(obj, s_call, e_call) {
					this.__callback({ "obj": obj });
				},
				_is_loaded: function _is_loaded(obj) {
					return true;
				},

				// Basic operations: create
				create_node: function create_node(obj, position, js, callback, is_loaded) {
					obj = this._get_node(obj);
					position = typeof position === "undefined" ? "last" : position;
					var d = $("<li />"),
					    s = this._get_settings().core,
					    tmp;

					if (obj !== -1 && !obj.length) {
						return false;
					}
					if (!is_loaded && !this._is_loaded(obj)) {
						this.load_node(obj, function () {
							this.create_node(obj, position, js, callback, true);
						});return false;
					}

					this.__rollback();

					if (typeof js === "string") {
						js = { "data": js };
					}
					if (!js) {
						js = {};
					}
					if (js.attr) {
						d.attr(js.attr);
					}
					if (js.metadata) {
						d.data(js.metadata);
					}
					if (js.state) {
						d.addClass("jstree-" + js.state);
					}
					if (!js.data) {
						js.data = this._get_string("new_node");
					}
					if (!$.isArray(js.data)) {
						tmp = js.data;js.data = [];js.data.push(tmp);
					}
					$.each(js.data, function (i, m) {
						tmp = $("<a />");
						if ($.isFunction(m)) {
							m = m.call(this, js);
						}
						if (typeof m == "string") {
							tmp.attr('href', '#')[s.html_titles ? "html" : "text"](m);
						} else {
							if (!m.attr) {
								m.attr = {};
							}
							if (!m.attr.href) {
								m.attr.href = '#';
							}
							tmp.attr(m.attr)[s.html_titles ? "html" : "text"](m.title);
							if (m.language) {
								tmp.addClass(m.language);
							}
						}
						tmp.prepend("<ins class='jstree-icon'>&#160;</ins>");
						if (!m.icon && js.icon) {
							m.icon = js.icon;
						}
						if (m.icon) {
							if (m.icon.indexOf("/") === -1) {
								tmp.children("ins").addClass(m.icon);
							} else {
								tmp.children("ins").css("background", "url('" + m.icon + "') center center no-repeat");
							}
						}
						d.append(tmp);
					});
					d.prepend("<ins class='jstree-icon'>&#160;</ins>");
					if (obj === -1) {
						obj = this.get_container();
						if (position === "before") {
							position = "first";
						}
						if (position === "after") {
							position = "last";
						}
					}
					switch (position) {
						case "before":
							obj.before(d);tmp = this._get_parent(obj);break;
						case "after":
							obj.after(d);tmp = this._get_parent(obj);break;
						case "inside":
						case "first":
							if (!obj.children("ul").length) {
								obj.append("<ul />");
							}
							obj.children("ul").prepend(d);
							tmp = obj;
							break;
						case "last":
							if (!obj.children("ul").length) {
								obj.append("<ul />");
							}
							obj.children("ul").append(d);
							tmp = obj;
							break;
						default:
							if (!obj.children("ul").length) {
								obj.append("<ul />");
							}
							if (!position) {
								position = 0;
							}
							tmp = obj.children("ul").children("li").eq(position);
							if (tmp.length) {
								tmp.before(d);
							} else {
								obj.children("ul").append(d);
							}
							tmp = obj;
							break;
					}
					if (tmp === -1 || tmp.get(0) === this.get_container().get(0)) {
						tmp = -1;
					}
					this.clean_node(tmp);
					this.__callback({ "obj": d, "parent": tmp });
					if (callback) {
						callback.call(this, d);
					}
					return d;
				},
				// Basic operations: rename (deal with text)
				get_text: function get_text(obj) {
					obj = this._get_node(obj);
					if (!obj.length) {
						return false;
					}
					var s = this._get_settings().core.html_titles;
					obj = obj.children("a:eq(0)");
					if (s) {
						obj = obj.clone();
						obj.children("INS").remove();
						return obj.html();
					} else {
						obj = obj.contents().filter(function () {
							return this.nodeType == 3;
						})[0];
						return obj.nodeValue;
					}
				},
				set_text: function set_text(obj, val) {
					obj = this._get_node(obj);
					if (!obj.length) {
						return false;
					}
					obj = obj.children("a:eq(0)");
					if (this._get_settings().core.html_titles) {
						var tmp = obj.children("INS").clone();
						obj.html(val).prepend(tmp);
						this.__callback({ "obj": obj, "name": val });
						return true;
					} else {
						obj = obj.contents().filter(function () {
							return this.nodeType == 3;
						})[0];
						this.__callback({ "obj": obj, "name": val });
						return obj.nodeValue = val;
					}
				},
				rename_node: function rename_node(obj, val) {
					obj = this._get_node(obj);
					this.__rollback();
					if (obj && obj.length && this.set_text.apply(this, Array.prototype.slice.call(arguments))) {
						this.__callback({ "obj": obj, "name": val });
					}
				},
				// Basic operations: deleting nodes
				delete_node: function delete_node(obj) {
					obj = this._get_node(obj);
					if (!obj.length) {
						return false;
					}
					this.__rollback();
					var p = this._get_parent(obj),
					    prev = $([]),
					    t = this;
					obj.each(function () {
						prev = prev.add(t._get_prev(this));
					});
					obj = obj.detach();
					if (p !== -1 && p.find("> ul > li").length === 0) {
						p.removeClass("jstree-open jstree-closed").addClass("jstree-leaf");
					}
					this.clean_node(p);
					this.__callback({ "obj": obj, "prev": prev, "parent": p });
					return obj;
				},
				prepare_move: function prepare_move(o, r, pos, cb, is_cb) {
					var p = {};

					p.ot = $.jstree._reference(o) || this;
					p.o = p.ot._get_node(o);
					p.r = r === -1 ? -1 : this._get_node(r);
					p.p = typeof pos === "undefined" || pos === false ? "last" : pos; // TODO: move to a setting
					if (!is_cb && prepared_move.o && prepared_move.o[0] === p.o[0] && prepared_move.r[0] === p.r[0] && prepared_move.p === p.p) {
						this.__callback(prepared_move);
						if (cb) {
							cb.call(this, prepared_move);
						}
						return;
					}
					p.ot = $.jstree._reference(p.o) || this;
					p.rt = $.jstree._reference(p.r) || this; // r === -1 ? p.ot : $.jstree._reference(p.r) || this
					if (p.r === -1 || !p.r) {
						p.cr = -1;
						switch (p.p) {
							case "first":
							case "before":
							case "inside":
								p.cp = 0;
								break;
							case "after":
							case "last":
								p.cp = p.rt.get_container().find(" > ul > li").length;
								break;
							default:
								p.cp = p.p;
								break;
						}
					} else {
						if (!/^(before|after)$/.test(p.p) && !this._is_loaded(p.r)) {
							return this.load_node(p.r, function () {
								this.prepare_move(o, r, pos, cb, true);
							});
						}
						switch (p.p) {
							case "before":
								p.cp = p.r.index();
								p.cr = p.rt._get_parent(p.r);
								break;
							case "after":
								p.cp = p.r.index() + 1;
								p.cr = p.rt._get_parent(p.r);
								break;
							case "inside":
							case "first":
								p.cp = 0;
								p.cr = p.r;
								break;
							case "last":
								p.cp = p.r.find(" > ul > li").length;
								p.cr = p.r;
								break;
							default:
								p.cp = p.p;
								p.cr = p.r;
								break;
						}
					}
					p.np = p.cr == -1 ? p.rt.get_container() : p.cr;
					p.op = p.ot._get_parent(p.o);
					p.cop = p.o.index();
					if (p.op === -1) {
						p.op = p.ot ? p.ot.get_container() : this.get_container();
					}
					if (!/^(before|after)$/.test(p.p) && p.op && p.np && p.op[0] === p.np[0] && p.o.index() < p.cp) {
						p.cp++;
					}
					//if(p.p === "before" && p.op && p.np && p.op[0] === p.np[0] && p.o.index() < p.cp) { p.cp--; }
					p.or = p.np.find(" > ul > li:nth-child(" + (p.cp + 1) + ")");
					prepared_move = p;
					this.__callback(prepared_move);
					if (cb) {
						cb.call(this, prepared_move);
					}
				},
				check_move: function check_move() {
					var obj = prepared_move,
					    ret = true,
					    r = obj.r === -1 ? this.get_container() : obj.r;
					if (!obj || !obj.o || obj.or[0] === obj.o[0]) {
						return false;
					}
					if (!obj.cy) {
						if (obj.op && obj.np && obj.op[0] === obj.np[0] && obj.cp - 1 === obj.o.index()) {
							return false;
						}
						obj.o.each(function () {
							if (r.parentsUntil(".jstree", "li").andSelf().index(this) !== -1) {
								ret = false;return false;
							}
						});
					}
					return ret;
				},
				move_node: function move_node(obj, ref, position, is_copy, is_prepared, skip_check) {
					if (!is_prepared) {
						return this.prepare_move(obj, ref, position, function (p) {
							this.move_node(p, false, false, is_copy, true, skip_check);
						});
					}
					if (is_copy) {
						prepared_move.cy = true;
					}
					if (!skip_check && !this.check_move()) {
						return false;
					}

					this.__rollback();
					var o = false;
					if (is_copy) {
						o = obj.o.clone(true);
						o.find("*[id]").andSelf().each(function () {
							if (this.id) {
								this.id = "copy_" + this.id;
							}
						});
					} else {
						o = obj.o;
					}

					if (obj.or.length) {
						obj.or.before(o);
					} else {
						if (!obj.np.children("ul").length) {
							$("<ul />").appendTo(obj.np);
						}
						obj.np.children("ul:eq(0)").append(o);
					}

					try {
						obj.ot.clean_node(obj.op);
						obj.rt.clean_node(obj.np);
						if (!obj.op.find("> ul > li").length) {
							obj.op.removeClass("jstree-open jstree-closed").addClass("jstree-leaf").children("ul").remove();
						}
					} catch (e) {}

					if (is_copy) {
						prepared_move.cy = true;
						prepared_move.oc = o;
					}
					this.__callback(prepared_move);
					return prepared_move;
				},
				_get_move: function _get_move() {
					return prepared_move;
				}
			}
		});
	})(jQuery);
	//*/

	/* 
  * jsTree ui plugin
  * This plugins handles selecting/deselecting/hovering/dehovering nodes
  */
	(function ($) {
		var scrollbar_width, e1, e2;
		$(function () {
			if (/msie/.test(navigator.userAgent.toLowerCase())) {
				e1 = $('<textarea cols="10" rows="2"></textarea>').css({ position: 'absolute', top: -1000, left: 0 }).appendTo('body');
				e2 = $('<textarea cols="10" rows="2" style="overflow: hidden;"></textarea>').css({ position: 'absolute', top: -1000, left: 0 }).appendTo('body');
				scrollbar_width = e1.width() - e2.width();
				e1.add(e2).remove();
			} else {
				e1 = $('<div />').css({ width: 100, height: 100, overflow: 'auto', position: 'absolute', top: -1000, left: 0 }).prependTo('body').append('<div />').find('div').css({ width: '100%', height: 200 });
				scrollbar_width = 100 - e1.width();
				e1.parent().remove();
			}
		});
		$.jstree.plugin("ui", {
			__init: function __init() {
				this.data.ui.selected = $();
				this.data.ui.last_selected = false;
				this.data.ui.hovered = null;
				this.data.ui.to_select = this.get_settings().ui.initially_select;

				this.get_container().delegate("a", "click.jstree", $.proxy(function (event) {
					event.preventDefault();
					event.currentTarget.blur();
					if (!$(event.currentTarget).hasClass("jstree-loading")) {
						this.select_node(event.currentTarget, true, event);
					}
				}, this)).delegate("a", "mouseenter.jstree", $.proxy(function (event) {
					if (!$(event.currentTarget).hasClass("jstree-loading")) {
						this.hover_node(event.target);
					}
				}, this)).delegate("a", "mouseleave.jstree", $.proxy(function (event) {
					if (!$(event.currentTarget).hasClass("jstree-loading")) {
						this.dehover_node(event.target);
					}
				}, this)).bind("reopen.jstree", $.proxy(function () {
					this.reselect();
				}, this)).bind("get_rollback.jstree", $.proxy(function () {
					this.dehover_node();
					this.save_selected();
				}, this)).bind("set_rollback.jstree", $.proxy(function () {
					this.reselect();
				}, this)).bind("close_node.jstree", $.proxy(function (event, data) {
					var s = this._get_settings().ui,
					    obj = this._get_node(data.rslt.obj),
					    clk = obj && obj.length ? obj.children("ul").find("a.jstree-clicked") : $(),
					    _this = this;
					if (s.selected_parent_close === false || !clk.length) {
						return;
					}
					clk.each(function () {
						_this.deselect_node(this);
						if (s.selected_parent_close === "select_parent") {
							_this.select_node(obj);
						}
					});
				}, this)).bind("delete_node.jstree", $.proxy(function (event, data) {
					var s = this._get_settings().ui.select_prev_on_delete,
					    obj = this._get_node(data.rslt.obj),
					    clk = obj && obj.length ? obj.find("a.jstree-clicked") : [],
					    _this = this;
					clk.each(function () {
						_this.deselect_node(this);
					});
					if (s && clk.length) {
						data.rslt.prev.each(function () {
							if (this.parentNode) {
								_this.select_node(this);return false; /* if return false is removed all prev nodes will be selected */
							}
						});
					}
				}, this)).bind("move_node.jstree", $.proxy(function (event, data) {
					if (data.rslt.cy) {
						data.rslt.oc.find("a.jstree-clicked").removeClass("jstree-clicked");
					}
				}, this));
			},
			defaults: {
				select_limit: -1, // 0, 1, 2 ... or -1 for unlimited
				select_multiple_modifier: "ctrl", // on, or ctrl, shift, alt
				select_range_modifier: "shift",
				selected_parent_close: "select_parent", // false, "deselect", "select_parent"
				selected_parent_open: true,
				select_prev_on_delete: true,
				disable_selecting_children: false,
				initially_select: []
			},
			_fn: {
				_get_node: function _get_node(obj, allow_multiple) {
					if (typeof obj === "undefined" || obj === null) {
						return allow_multiple ? this.data.ui.selected : this.data.ui.last_selected;
					}
					var $obj = $(obj, this.get_container());
					if ($obj.is(".jstree") || obj == -1) {
						return -1;
					}
					$obj = $obj.closest("li", this.get_container());
					return $obj.length ? $obj : false;
				},
				_ui_notify: function _ui_notify(n, data) {
					if (data.selected) {
						this.select_node(n, false);
					}
				},
				save_selected: function save_selected() {
					var _this = this;
					this.data.ui.to_select = [];
					this.data.ui.selected.each(function () {
						if (this.id) {
							_this.data.ui.to_select.push("#" + this.id.toString().replace(/^#/, "").replace(/\\\//g, "/").replace(/\//g, "\\\/").replace(/\\\./g, ".").replace(/\./g, "\\.").replace(/\:/g, "\\:"));
						}
					});
					this.__callback(this.data.ui.to_select);
				},
				reselect: function reselect() {
					var _this = this,
					    s = this.data.ui.to_select;
					s = $.map($.makeArray(s), function (n) {
						return "#" + n.toString().replace(/^#/, "").replace(/\\\//g, "/").replace(/\//g, "\\\/").replace(/\\\./g, ".").replace(/\./g, "\\.").replace(/\:/g, "\\:");
					});
					// this.deselect_all(); WHY deselect, breaks plugin state notifier?
					$.each(s, function (i, val) {
						if (val && val !== "#") {
							_this.select_node(val);
						}
					});
					this.data.ui.selected = this.data.ui.selected.filter(function () {
						return this.parentNode;
					});
					this.__callback();
				},
				refresh: function refresh(obj) {
					this.save_selected();
					return this.__call_old();
				},
				hover_node: function hover_node(obj) {
					obj = this._get_node(obj);
					if (!obj.length) {
						return false;
					}
					//if(this.data.ui.hovered && obj.get(0) === this.data.ui.hovered.get(0)) { return; }
					if (!obj.hasClass("jstree-hovered")) {
						this.dehover_node();
					}
					this.data.ui.hovered = obj.children("a").addClass("jstree-hovered").parent();
					this._fix_scroll(obj);
					this.__callback({ "obj": obj });
				},
				dehover_node: function dehover_node() {
					var obj = this.data.ui.hovered,
					    p;
					if (!obj || !obj.length) {
						return false;
					}
					p = obj.children("a").removeClass("jstree-hovered").parent();
					if (this.data.ui.hovered[0] === p[0]) {
						this.data.ui.hovered = null;
					}
					this.__callback({ "obj": obj });
				},
				select_node: function select_node(obj, check, e) {
					obj = this._get_node(obj);
					if (obj == -1 || !obj || !obj.length) {
						return false;
					}
					var s = this._get_settings().ui,
					    is_multiple = s.select_multiple_modifier == "on" || s.select_multiple_modifier !== false && e && e[s.select_multiple_modifier + "Key"],
					    is_range = s.select_range_modifier !== false && e && e[s.select_range_modifier + "Key"] && this.data.ui.last_selected && this.data.ui.last_selected[0] !== obj[0] && this.data.ui.last_selected.parent()[0] === obj.parent()[0],
					    is_selected = this.is_selected(obj),
					    proceed = true,
					    t = this;
					if (check) {
						if (s.disable_selecting_children && is_multiple && (obj.parentsUntil(".jstree", "li").children("a.jstree-clicked").length || obj.children("ul").find("a.jstree-clicked:eq(0)").length)) {
							return false;
						}
						proceed = false;
						switch (!0) {
							case is_range:
								this.data.ui.last_selected.addClass("jstree-last-selected");
								obj = obj[obj.index() < this.data.ui.last_selected.index() ? "nextUntil" : "prevUntil"](".jstree-last-selected").andSelf();
								if (s.select_limit == -1 || obj.length < s.select_limit) {
									this.data.ui.last_selected.removeClass("jstree-last-selected");
									this.data.ui.selected.each(function () {
										if (this !== t.data.ui.last_selected[0]) {
											t.deselect_node(this);
										}
									});
									is_selected = false;
									proceed = true;
								} else {
									proceed = false;
								}
								break;
							case is_selected && !is_multiple:
								this.deselect_all();
								is_selected = false;
								proceed = true;
								break;
							case !is_selected && !is_multiple:
								if (s.select_limit == -1 || s.select_limit > 0) {
									this.deselect_all();
									proceed = true;
								}
								break;
							case is_selected && is_multiple:
								this.deselect_node(obj);
								break;
							case !is_selected && is_multiple:
								if (s.select_limit == -1 || this.data.ui.selected.length + 1 <= s.select_limit) {
									proceed = true;
								}
								break;
						}
					}
					if (proceed && !is_selected) {
						if (!is_range) {
							this.data.ui.last_selected = obj;
						}
						obj.children("a").addClass("jstree-clicked");
						if (s.selected_parent_open) {
							obj.parents(".jstree-closed").each(function () {
								t.open_node(this, false, true);
							});
						}
						this.data.ui.selected = this.data.ui.selected.add(obj);
						this._fix_scroll(obj.eq(0));
						this.__callback({ "obj": obj, "e": e });
					}
				},
				_fix_scroll: function _fix_scroll(obj) {
					var c = this.get_container()[0],
					    t;
					if (c.scrollHeight > c.offsetHeight) {
						obj = this._get_node(obj);
						if (!obj || obj === -1 || !obj.length || !obj.is(":visible")) {
							return;
						}
						t = obj.offset().top - this.get_container().offset().top;
						if (t < 0) {
							c.scrollTop = c.scrollTop + t - 1;
						}
						if (t + this.data.core.li_height + (c.scrollWidth > c.offsetWidth ? scrollbar_width : 0) > c.offsetHeight) {
							c.scrollTop = c.scrollTop + (t - c.offsetHeight + this.data.core.li_height + 1 + (c.scrollWidth > c.offsetWidth ? scrollbar_width : 0));
						}
					}
				},
				deselect_node: function deselect_node(obj) {
					obj = this._get_node(obj);
					if (!obj.length) {
						return false;
					}
					if (this.is_selected(obj)) {
						obj.children("a").removeClass("jstree-clicked");
						this.data.ui.selected = this.data.ui.selected.not(obj);
						if (this.data.ui.last_selected.get(0) === obj.get(0)) {
							this.data.ui.last_selected = this.data.ui.selected.eq(0);
						}
						this.__callback({ "obj": obj });
					}
				},
				toggle_select: function toggle_select(obj) {
					obj = this._get_node(obj);
					if (!obj.length) {
						return false;
					}
					if (this.is_selected(obj)) {
						this.deselect_node(obj);
					} else {
						this.select_node(obj);
					}
				},
				is_selected: function is_selected(obj) {
					return this.data.ui.selected.index(this._get_node(obj)) >= 0;
				},
				get_selected: function get_selected(context) {
					return context ? $(context).find("a.jstree-clicked").parent() : this.data.ui.selected;
				},
				deselect_all: function deselect_all(context) {
					var ret = context ? $(context).find("a.jstree-clicked").parent() : this.get_container().find("a.jstree-clicked").parent();
					ret.children("a.jstree-clicked").removeClass("jstree-clicked");
					this.data.ui.selected = $([]);
					this.data.ui.last_selected = false;
					this.__callback({ "obj": ret });
				}
			}
		});
		// include the selection plugin by default
		$.jstree.defaults.plugins.push("ui");
	})(jQuery);
	//*/

	/* 
  * jsTree CRRM plugin
  * Handles creating/renaming/removing/moving nodes by user interaction.
  */
	(function ($) {
		$.jstree.plugin("crrm", {
			__init: function __init() {
				this.get_container().bind("move_node.jstree", $.proxy(function (e, data) {
					if (this._get_settings().crrm.move.open_onmove) {
						var t = this;
						data.rslt.np.parentsUntil(".jstree").andSelf().filter(".jstree-closed").each(function () {
							t.open_node(this, false, true);
						});
					}
				}, this));
			},
			defaults: {
				input_width_limit: 200,
				move: {
					always_copy: false, // false, true or "multitree"
					open_onmove: true,
					default_position: "last",
					check_move: function check_move(m) {
						return true;
					}
				}
			},
			_fn: {
				_show_input: function _show_input(obj, callback) {
					obj = this._get_node(obj);
					var rtl = this._get_settings().core.rtl,
					    w = this._get_settings().crrm.input_width_limit,
					    w1 = obj.children("ins").width(),
					    w2 = obj.find("> a:visible > ins").width() * obj.find("> a:visible > ins").length,
					    t = this.get_text(obj),
					    h1 = $("<div />", { css: { "position": "absolute", "top": "-200px", "left": rtl ? "0px" : "-1000px", "visibility": "hidden" } }).appendTo("body"),
					    h2 = obj.css("position", "relative").append($("<input />", {
						"value": t,
						"class": "jstree-rename-input",
						// "size" : t.length,
						"css": {
							"padding": "0",
							"border": "1px solid silver",
							"position": "absolute",
							"left": rtl ? "auto" : w1 + w2 + 4 + "px",
							"right": rtl ? w1 + w2 + 4 + "px" : "auto",
							"top": "0px",
							"height": this.data.core.li_height - 2 + "px",
							"lineHeight": this.data.core.li_height - 2 + "px",
							"width": "150px" // will be set a bit further down
						},
						"blur": $.proxy(function () {
							var i = obj.children(".jstree-rename-input"),
							    v = i.val();
							if (v === "") {
								v = t;
							}
							h1.remove();
							i.remove(); // rollback purposes
							this.set_text(obj, t); // rollback purposes
							this.rename_node(obj, v);
							callback.call(this, obj, v, t);
							obj.css("position", "");
						}, this),
						"keyup": function keyup(event) {
							var key = event.keyCode || event.which;
							if (key == 27) {
								this.value = t;this.blur();return;
							} else if (key == 13) {
								this.blur();return;
							} else {
								h2.width(Math.min(h1.text("pW" + this.value).width(), w));
							}
						},
						"keypress": function keypress(event) {
							var key = event.keyCode || event.which;
							if (key == 13) {
								return false;
							}
						}
					})).children(".jstree-rename-input");
					this.set_text(obj, "");
					h1.css({
						fontFamily: h2.css('fontFamily') || '',
						fontSize: h2.css('fontSize') || '',
						fontWeight: h2.css('fontWeight') || '',
						fontStyle: h2.css('fontStyle') || '',
						fontStretch: h2.css('fontStretch') || '',
						fontVariant: h2.css('fontVariant') || '',
						letterSpacing: h2.css('letterSpacing') || '',
						wordSpacing: h2.css('wordSpacing') || ''
					});
					h2.width(Math.min(h1.text("pW" + h2[0].value).width(), w))[0].select();
				},
				rename: function rename(obj) {
					obj = this._get_node(obj);
					this.__rollback();
					var f = this.__callback;
					this._show_input(obj, function (obj, new_name, old_name) {
						f.call(this, { "obj": obj, "new_name": new_name, "old_name": old_name });
					});
				},
				create: function create(obj, position, js, callback, skip_rename) {
					var t,
					    _this = this;
					obj = this._get_node(obj);
					if (!obj) {
						obj = -1;
					}
					this.__rollback();
					t = this.create_node(obj, position, js, function (t) {
						var p = this._get_parent(t),
						    pos = $(t).index();
						if (callback) {
							callback.call(this, t);
						}
						if (p.length && p.hasClass("jstree-closed")) {
							this.open_node(p, false, true);
						}
						if (!skip_rename) {
							this._show_input(t, function (obj, new_name, old_name) {
								_this.__callback({ "obj": obj, "name": new_name, "parent": p, "position": pos });
							});
						} else {
							_this.__callback({ "obj": t, "name": this.get_text(t), "parent": p, "position": pos });
						}
					});
					return t;
				},
				remove: function remove(obj) {
					obj = this._get_node(obj, true);
					var p = this._get_parent(obj),
					    prev = this._get_prev(obj);
					this.__rollback();
					obj = this.delete_node(obj);
					if (obj !== false) {
						this.__callback({ "obj": obj, "prev": prev, "parent": p });
					}
				},
				check_move: function check_move() {
					if (!this.__call_old()) {
						return false;
					}
					var s = this._get_settings().crrm.move;
					if (!s.check_move.call(this, this._get_move())) {
						return false;
					}
					return true;
				},
				move_node: function move_node(obj, ref, position, is_copy, is_prepared, skip_check) {
					var s = this._get_settings().crrm.move;
					if (!is_prepared) {
						if (typeof position === "undefined") {
							position = s.default_position;
						}
						if (position === "inside" && !s.default_position.match(/^(before|after)$/)) {
							position = s.default_position;
						}
						return this.__call_old(true, obj, ref, position, is_copy, false, skip_check);
					}
					// if the move is already prepared
					if (s.always_copy === true || s.always_copy === "multitree" && obj.rt.get_index() !== obj.ot.get_index()) {
						is_copy = true;
					}
					this.__call_old(true, obj, ref, position, is_copy, true, skip_check);
				},

				cut: function cut(obj) {
					obj = this._get_node(obj, true);
					if (!obj || !obj.length) {
						return false;
					}
					this.data.crrm.cp_nodes = false;
					this.data.crrm.ct_nodes = obj;
					this.__callback({ "obj": obj });
				},
				copy: function copy(obj) {
					obj = this._get_node(obj, true);
					if (!obj || !obj.length) {
						return false;
					}
					this.data.crrm.ct_nodes = false;
					this.data.crrm.cp_nodes = obj;
					this.__callback({ "obj": obj });
				},
				paste: function paste(obj) {
					obj = this._get_node(obj);
					if (!obj || !obj.length) {
						return false;
					}
					var nodes = this.data.crrm.ct_nodes ? this.data.crrm.ct_nodes : this.data.crrm.cp_nodes;
					if (!this.data.crrm.ct_nodes && !this.data.crrm.cp_nodes) {
						return false;
					}
					if (this.data.crrm.ct_nodes) {
						this.move_node(this.data.crrm.ct_nodes, obj);this.data.crrm.ct_nodes = false;
					}
					if (this.data.crrm.cp_nodes) {
						this.move_node(this.data.crrm.cp_nodes, obj, false, true);
					}
					this.__callback({ "obj": obj, "nodes": nodes });
				}
			}
		});
		// include the crr plugin by default
		// $.jstree.defaults.plugins.push("crrm");
	})(jQuery);
	//*/

	/* 
  * jsTree themes plugin
  * Handles loading and setting themes, as well as detecting path to themes, etc.
  */
	(function ($) {
		var themes_loaded = [];
		// this variable stores the path to the themes folder - if left as false - it will be autodetected
		$.jstree._themes = false;
		$.jstree.plugin("themes", {
			__init: function __init() {
				this.get_container().bind("init.jstree", $.proxy(function () {
					var s = this._get_settings().themes;
					this.data.themes.dots = s.dots;
					this.data.themes.icons = s.icons;
					this.set_theme(s.theme, s.url);
				}, this)).bind("loaded.jstree", $.proxy(function () {
					// bound here too, as simple HTML tree's won't honor dots & icons otherwise
					if (!this.data.themes.dots) {
						this.hide_dots();
					} else {
						this.show_dots();
					}
					if (!this.data.themes.icons) {
						this.hide_icons();
					} else {
						this.show_icons();
					}
				}, this));
			},
			defaults: {
				theme: "default",
				url: false,
				dots: true,
				icons: true
			},
			_fn: {
				set_theme: function set_theme(theme_name, theme_url) {
					if (!theme_name) {
						return false;
					}
					if (!theme_url) {
						theme_url = $.jstree._themes + theme_name + '/style.css';
					}
					if ($.inArray(theme_url, themes_loaded) == -1) {
						$.vakata.css.add_sheet({ "url": theme_url });
						themes_loaded.push(theme_url);
					}
					if (this.data.themes.theme != theme_name) {
						this.get_container().removeClass('jstree-' + this.data.themes.theme);
						this.data.themes.theme = theme_name;
					}
					this.get_container().addClass('jstree-' + theme_name);
					if (!this.data.themes.dots) {
						this.hide_dots();
					} else {
						this.show_dots();
					}
					if (!this.data.themes.icons) {
						this.hide_icons();
					} else {
						this.show_icons();
					}
					this.__callback();
				},
				get_theme: function get_theme() {
					return this.data.themes.theme;
				},

				show_dots: function show_dots() {
					this.data.themes.dots = true;this.get_container().children("ul").removeClass("jstree-no-dots");
				},
				hide_dots: function hide_dots() {
					this.data.themes.dots = false;this.get_container().children("ul").addClass("jstree-no-dots");
				},
				toggle_dots: function toggle_dots() {
					if (this.data.themes.dots) {
						this.hide_dots();
					} else {
						this.show_dots();
					}
				},

				show_icons: function show_icons() {
					this.data.themes.icons = true;this.get_container().children("ul").removeClass("jstree-no-icons");
				},
				hide_icons: function hide_icons() {
					this.data.themes.icons = false;this.get_container().children("ul").addClass("jstree-no-icons");
				},
				toggle_icons: function toggle_icons() {
					if (this.data.themes.icons) {
						this.hide_icons();
					} else {
						this.show_icons();
					}
				}
			}
		});
		// autodetect themes path
		$(function () {
			if ($.jstree._themes === false) {
				$("script").each(function () {
					if (this.src.toString().match(/jquery\.jstree[^\/]*?\.js(\?.*)?$/)) {
						$.jstree._themes = this.src.toString().replace(/jquery\.jstree[^\/]*?\.js(\?.*)?$/, "") + 'themes/';
						return false;
					}
				});
			}
			if ($.jstree._themes === false) {
				$.jstree._themes = "themes/";
			}
		});
		// include the themes plugin by default
		$.jstree.defaults.plugins.push("themes");
	})(jQuery);
	//*/

	/*
  * jsTree hotkeys plugin
  * Enables keyboard navigation for all tree instances
  * Depends on the jstree ui & jquery hotkeys plugins
  */
	(function ($) {
		var bound = [];
		function exec(i, event) {
			var f = $.jstree._focused(),
			    tmp;
			if (f && f.data && f.data.hotkeys && f.data.hotkeys.enabled) {
				tmp = f._get_settings().hotkeys[i];
				if (tmp) {
					return tmp.call(f, event);
				}
			}
		}
		$.jstree.plugin("hotkeys", {
			__init: function __init() {
				if (typeof $.hotkeys === "undefined") {
					throw "jsTree hotkeys: jQuery hotkeys plugin not included.";
				}
				if (!this.data.ui) {
					throw "jsTree hotkeys: jsTree UI plugin not included.";
				}
				$.each(this._get_settings().hotkeys, function (i, v) {
					if (v !== false && $.inArray(i, bound) == -1) {
						$(document).bind("keydown", i, function (event) {
							return exec(i, event);
						});
						bound.push(i);
					}
				});
				this.get_container().bind("lock.jstree", $.proxy(function () {
					if (this.data.hotkeys.enabled) {
						this.data.hotkeys.enabled = false;this.data.hotkeys.revert = true;
					}
				}, this)).bind("unlock.jstree", $.proxy(function () {
					if (this.data.hotkeys.revert) {
						this.data.hotkeys.enabled = true;
					}
				}, this));
				this.enable_hotkeys();
			},
			defaults: {
				"up": function up() {
					var o = this.data.ui.hovered || this.data.ui.last_selected || -1;
					this.hover_node(this._get_prev(o));
					return false;
				},
				"ctrl+up": function ctrlUp() {
					var o = this.data.ui.hovered || this.data.ui.last_selected || -1;
					this.hover_node(this._get_prev(o));
					return false;
				},
				"shift+up": function shiftUp() {
					var o = this.data.ui.hovered || this.data.ui.last_selected || -1;
					this.hover_node(this._get_prev(o));
					return false;
				},
				"down": function down() {
					var o = this.data.ui.hovered || this.data.ui.last_selected || -1;
					this.hover_node(this._get_next(o));
					return false;
				},
				"ctrl+down": function ctrlDown() {
					var o = this.data.ui.hovered || this.data.ui.last_selected || -1;
					this.hover_node(this._get_next(o));
					return false;
				},
				"shift+down": function shiftDown() {
					var o = this.data.ui.hovered || this.data.ui.last_selected || -1;
					this.hover_node(this._get_next(o));
					return false;
				},
				"left": function left() {
					var o = this.data.ui.hovered || this.data.ui.last_selected;
					if (o) {
						if (o.hasClass("jstree-open")) {
							this.close_node(o);
						} else {
							this.hover_node(this._get_prev(o));
						}
					}
					return false;
				},
				"ctrl+left": function ctrlLeft() {
					var o = this.data.ui.hovered || this.data.ui.last_selected;
					if (o) {
						if (o.hasClass("jstree-open")) {
							this.close_node(o);
						} else {
							this.hover_node(this._get_prev(o));
						}
					}
					return false;
				},
				"shift+left": function shiftLeft() {
					var o = this.data.ui.hovered || this.data.ui.last_selected;
					if (o) {
						if (o.hasClass("jstree-open")) {
							this.close_node(o);
						} else {
							this.hover_node(this._get_prev(o));
						}
					}
					return false;
				},
				"right": function right() {
					var o = this.data.ui.hovered || this.data.ui.last_selected;
					if (o && o.length) {
						if (o.hasClass("jstree-closed")) {
							this.open_node(o);
						} else {
							this.hover_node(this._get_next(o));
						}
					}
					return false;
				},
				"ctrl+right": function ctrlRight() {
					var o = this.data.ui.hovered || this.data.ui.last_selected;
					if (o && o.length) {
						if (o.hasClass("jstree-closed")) {
							this.open_node(o);
						} else {
							this.hover_node(this._get_next(o));
						}
					}
					return false;
				},
				"shift+right": function shiftRight() {
					var o = this.data.ui.hovered || this.data.ui.last_selected;
					if (o && o.length) {
						if (o.hasClass("jstree-closed")) {
							this.open_node(o);
						} else {
							this.hover_node(this._get_next(o));
						}
					}
					return false;
				},
				"space": function space() {
					if (this.data.ui.hovered) {
						this.data.ui.hovered.children("a:eq(0)").click();
					}
					return false;
				},
				"ctrl+space": function ctrlSpace(event) {
					event.type = "click";
					if (this.data.ui.hovered) {
						this.data.ui.hovered.children("a:eq(0)").trigger(event);
					}
					return false;
				},
				"shift+space": function shiftSpace(event) {
					event.type = "click";
					if (this.data.ui.hovered) {
						this.data.ui.hovered.children("a:eq(0)").trigger(event);
					}
					return false;
				},
				"f2": function f2() {
					this.rename(this.data.ui.hovered || this.data.ui.last_selected);
				},
				"del": function del() {
					this.remove(this.data.ui.hovered || this._get_node(null));
				}
			},
			_fn: {
				enable_hotkeys: function enable_hotkeys() {
					this.data.hotkeys.enabled = true;
				},
				disable_hotkeys: function disable_hotkeys() {
					this.data.hotkeys.enabled = false;
				}
			}
		});
	})(jQuery);
	//*/

	/* 
  * jsTree JSON plugin
  * The JSON data store. Datastores are build by overriding the `load_node` and `_is_loaded` functions.
  */
	(function ($) {
		$.jstree.plugin("json_data", {
			__init: function __init() {
				var s = this._get_settings().json_data;
				if (s.progressive_unload) {
					this.get_container().bind("after_close.jstree", function (e, data) {
						data.rslt.obj.children("ul").remove();
					});
				}
			},
			defaults: {
				// `data` can be a function:
				//  * accepts two arguments - node being loaded and a callback to pass the result to
				//  * will be executed in the current tree's scope & ajax won't be supported
				data: false,
				ajax: false,
				correct_state: true,
				progressive_render: false,
				progressive_unload: false
			},
			_fn: {
				load_node: function load_node(obj, s_call, e_call) {
					var _this = this;this.load_node_json(obj, function () {
						_this.__callback({ "obj": _this._get_node(obj) });s_call.call(this);
					}, e_call);
				},
				_is_loaded: function _is_loaded(obj) {
					var s = this._get_settings().json_data;
					obj = this._get_node(obj);
					return obj == -1 || !obj || !s.ajax && !s.progressive_render && !$.isFunction(s.data) || obj.is(".jstree-open, .jstree-leaf") || obj.children("ul").children("li").length > 0;
				},
				refresh: function refresh(obj) {
					obj = this._get_node(obj);
					var s = this._get_settings().json_data;
					if (obj && obj !== -1 && s.progressive_unload && ($.isFunction(s.data) || !!s.ajax)) {
						obj.removeData("jstree_children");
					}
					return this.__call_old();
				},
				load_node_json: function load_node_json(obj, s_call, e_call) {
					var s = this.get_settings().json_data,
					    d,
					    error_func = function error_func() {},
					    success_func = function success_func() {};
					obj = this._get_node(obj);

					if (obj && obj !== -1 && (s.progressive_render || s.progressive_unload) && !obj.is(".jstree-open, .jstree-leaf") && obj.children("ul").children("li").length === 0 && obj.data("jstree_children")) {
						d = this._parse_json(obj.data("jstree_children"), obj);
						if (d) {
							obj.append(d);
							if (!s.progressive_unload) {
								obj.removeData("jstree_children");
							}
						}
						this.clean_node(obj);
						if (s_call) {
							s_call.call(this);
						}
						return;
					}

					if (obj && obj !== -1) {
						if (obj.data("jstree_is_loading")) {
							return;
						} else {
							obj.data("jstree_is_loading", true);
						}
					}
					switch (!0) {
						case !s.data && !s.ajax:
							throw "Neither data nor ajax settings supplied.";
						// function option added here for easier model integration (also supporting async - see callback)
						case $.isFunction(s.data):
							s.data.call(this, obj, $.proxy(function (d) {
								d = this._parse_json(d, obj);
								if (!d) {
									if (obj === -1 || !obj) {
										if (s.correct_state) {
											this.get_container().children("ul").empty();
										}
									} else {
										obj.children("a.jstree-loading").removeClass("jstree-loading");
										obj.removeData("jstree_is_loading");
										if (s.correct_state) {
											this.correct_state(obj);
										}
									}
									if (e_call) {
										e_call.call(this);
									}
								} else {
									if (obj === -1 || !obj) {
										this.get_container().children("ul").empty().append(d.children());
									} else {
										obj.append(d).children("a.jstree-loading").removeClass("jstree-loading");obj.removeData("jstree_is_loading");
									}
									this.clean_node(obj);
									if (s_call) {
										s_call.call(this);
									}
								}
							}, this));
							break;
						case !!s.data && !s.ajax || !!s.data && !!s.ajax && (!obj || obj === -1):
							if (!obj || obj == -1) {
								d = this._parse_json(s.data, obj);
								if (d) {
									this.get_container().children("ul").empty().append(d.children());
									this.clean_node();
								} else {
									if (s.correct_state) {
										this.get_container().children("ul").empty();
									}
								}
							}
							if (s_call) {
								s_call.call(this);
							}
							break;
						case !s.data && !!s.ajax || !!s.data && !!s.ajax && obj && obj !== -1:
							error_func = function error_func(x, t, e) {
								var ef = this.get_settings().json_data.ajax.error;
								if (ef) {
									ef.call(this, x, t, e);
								}
								if (obj != -1 && obj.length) {
									obj.children("a.jstree-loading").removeClass("jstree-loading");
									obj.removeData("jstree_is_loading");
									if (t === "success" && s.correct_state) {
										this.correct_state(obj);
									}
								} else {
									if (t === "success" && s.correct_state) {
										this.get_container().children("ul").empty();
									}
								}
								if (e_call) {
									e_call.call(this);
								}
							};
							success_func = function success_func(d, t, x) {
								var sf = this.get_settings().json_data.ajax.success;
								if (sf) {
									d = sf.call(this, d, t, x) || d;
								}
								if (d === "" || d && d.toString && d.toString().replace(/^[\s\n]+$/, "") === "" || !$.isArray(d) && !$.isPlainObject(d)) {
									return error_func.call(this, x, t, "");
								}
								d = this._parse_json(d, obj);
								if (d) {
									if (obj === -1 || !obj) {
										this.get_container().children("ul").empty().append(d.children());
									} else {
										obj.append(d).children("a.jstree-loading").removeClass("jstree-loading");obj.removeData("jstree_is_loading");
									}
									this.clean_node(obj);
									if (s_call) {
										s_call.call(this);
									}
								} else {
									if (obj === -1 || !obj) {
										if (s.correct_state) {
											this.get_container().children("ul").empty();
											if (s_call) {
												s_call.call(this);
											}
										}
									} else {
										obj.children("a.jstree-loading").removeClass("jstree-loading");
										obj.removeData("jstree_is_loading");
										if (s.correct_state) {
											this.correct_state(obj);
											if (s_call) {
												s_call.call(this);
											}
										}
									}
								}
							};
							s.ajax.context = this;
							s.ajax.error = error_func;
							s.ajax.success = success_func;
							if (!s.ajax.dataType) {
								s.ajax.dataType = "json";
							}
							if ($.isFunction(s.ajax.url)) {
								s.ajax.url = s.ajax.url.call(this, obj);
							}
							if ($.isFunction(s.ajax.data)) {
								s.ajax.data = s.ajax.data.call(this, obj);
							}
							$.ajax(s.ajax);
							break;
					}
				},
				_parse_json: function _parse_json(js, obj, is_callback) {
					var d = false,
					    p = this._get_settings(),
					    s = p.json_data,
					    t = p.core.html_titles,
					    tmp,
					    i,
					    j,
					    ul1,
					    ul2;

					if (!js) {
						return d;
					}
					if (s.progressive_unload && obj && obj !== -1) {
						obj.data("jstree_children", d);
					}
					if ($.isArray(js)) {
						d = $();
						if (!js.length) {
							return false;
						}
						for (i = 0, j = js.length; i < j; i++) {
							tmp = this._parse_json(js[i], obj, true);
							if (tmp.length) {
								d = d.add(tmp);
							}
						}
					} else {
						if (typeof js == "string") {
							js = { data: js };
						}
						if (!js.data && js.data !== "") {
							return d;
						}
						d = $("<li />");
						if (js.attr) {
							d.attr(js.attr);
						}
						if (js.metadata) {
							d.data(js.metadata);
						}
						if (js.state) {
							d.addClass("jstree-" + js.state);
						}
						if (!$.isArray(js.data)) {
							tmp = js.data;js.data = [];js.data.push(tmp);
						}
						$.each(js.data, function (i, m) {
							tmp = $("<a />");
							if ($.isFunction(m)) {
								m = m.call(this, js);
							}
							if (typeof m == "string") {
								tmp.attr('href', '#')[t ? "html" : "text"](m);
							} else {
								if (!m.attr) {
									m.attr = {};
								}
								if (!m.attr.href) {
									m.attr.href = '#';
								}
								tmp.attr(m.attr)[t ? "html" : "text"](m.title);
								if (m.language) {
									tmp.addClass(m.language);
								}
							}
							tmp.prepend("<ins class='jstree-icon'>&#160;</ins>");
							if (!m.icon && js.icon) {
								m.icon = js.icon;
							}
							if (m.icon) {
								if (m.icon.indexOf("/") === -1) {
									tmp.children("ins").addClass(m.icon);
								} else {
									tmp.children("ins").css("background", "url('" + m.icon + "') center center no-repeat");
								}
							}
							d.append(tmp);
						});
						d.prepend("<ins class='jstree-icon'>&#160;</ins>");
						if (js.children) {
							if (s.progressive_render && js.state !== "open") {
								d.addClass("jstree-closed").data("jstree_children", js.children);
							} else {
								if (s.progressive_unload) {
									d.data("jstree_children", js.children);
								}
								if ($.isArray(js.children) && js.children.length) {
									tmp = this._parse_json(js.children, obj, true);
									if (tmp.length) {
										ul2 = $("<ul />");
										ul2.append(tmp);
										d.append(ul2);
									}
								}
							}
						}
					}
					if (!is_callback) {
						ul1 = $("<ul />");
						ul1.append(d);
						d = ul1;
					}
					return d;
				},
				get_json: function get_json(obj, li_attr, a_attr, is_callback) {
					var result = [],
					    s = this._get_settings(),
					    _this = this,
					    tmp1,
					    tmp2,
					    li,
					    a,
					    t,
					    lang;
					obj = this._get_node(obj);
					if (!obj || obj === -1) {
						obj = this.get_container().find("> ul > li");
					}
					li_attr = $.isArray(li_attr) ? li_attr : ["id", "class"];
					if (!is_callback && this.data.types) {
						li_attr.push(s.types.type_attr);
					}
					a_attr = $.isArray(a_attr) ? a_attr : [];

					obj.each(function () {
						li = $(this);
						tmp1 = { data: [] };
						if (li_attr.length) {
							tmp1.attr = {};
						}
						$.each(li_attr, function (i, v) {
							tmp2 = li.attr(v);
							if (tmp2 && tmp2.length && tmp2.replace(/jstree[^ ]*/ig, '').length) {
								tmp1.attr[v] = (" " + tmp2).replace(/ jstree[^ ]*/ig, '').replace(/\s+$/ig, " ").replace(/^ /, "").replace(/ $/, "");
							}
						});
						if (li.hasClass("jstree-open")) {
							tmp1.state = "open";
						}
						if (li.hasClass("jstree-closed")) {
							tmp1.state = "closed";
						}
						if (li.data()) {
							tmp1.metadata = li.data();
						}
						a = li.children("a");
						a.each(function () {
							t = $(this);
							if (a_attr.length || $.inArray("languages", s.plugins) !== -1 || t.children("ins").get(0).style.backgroundImage.length || t.children("ins").get(0).className && t.children("ins").get(0).className.replace(/jstree[^ ]*|$/ig, '').length) {
								lang = false;
								if ($.inArray("languages", s.plugins) !== -1 && $.isArray(s.languages) && s.languages.length) {
									$.each(s.languages, function (l, lv) {
										if (t.hasClass(lv)) {
											lang = lv;
											return false;
										}
									});
								}
								tmp2 = { attr: {}, title: _this.get_text(t, lang) };
								$.each(a_attr, function (k, z) {
									tmp2.attr[z] = (" " + (t.attr(z) || "")).replace(/ jstree[^ ]*/ig, '').replace(/\s+$/ig, " ").replace(/^ /, "").replace(/ $/, "");
								});
								if ($.inArray("languages", s.plugins) !== -1 && $.isArray(s.languages) && s.languages.length) {
									$.each(s.languages, function (k, z) {
										if (t.hasClass(z)) {
											tmp2.language = z;return true;
										}
									});
								}
								if (t.children("ins").get(0).className.replace(/jstree[^ ]*|$/ig, '').replace(/^\s+$/ig, "").length) {
									tmp2.icon = t.children("ins").get(0).className.replace(/jstree[^ ]*|$/ig, '').replace(/\s+$/ig, " ").replace(/^ /, "").replace(/ $/, "");
								}
								if (t.children("ins").get(0).style.backgroundImage.length) {
									tmp2.icon = t.children("ins").get(0).style.backgroundImage.replace("url(", "").replace(")", "");
								}
							} else {
								tmp2 = _this.get_text(t);
							}
							if (a.length > 1) {
								tmp1.data.push(tmp2);
							} else {
								tmp1.data = tmp2;
							}
						});
						li = li.find("> ul > li");
						if (li.length) {
							tmp1.children = _this.get_json(li, li_attr, a_attr, true);
						}
						result.push(tmp1);
					});
					return result;
				}
			}
		});
	})(jQuery);
	//*/

	/* 
  * jsTree languages plugin
  * Adds support for multiple language versions in one tree
  * This basically allows for many titles coexisting in one node, but only one of them being visible at any given time
  * This is useful for maintaining the same structure in many languages (hence the name of the plugin)
  */
	(function ($) {
		var sh = false;
		$.jstree.plugin("languages", {
			__init: function __init() {
				this._load_css();
			},
			defaults: [],
			_fn: {
				set_lang: function set_lang(i) {
					var langs = this._get_settings().languages,
					    st = false,
					    selector = ".jstree-" + this.get_index() + ' a';
					if (!$.isArray(langs) || langs.length === 0) {
						return false;
					}
					if ($.inArray(i, langs) == -1) {
						if (!!langs[i]) {
							i = langs[i];
						} else {
							return false;
						}
					}
					if (i == this.data.languages.current_language) {
						return true;
					}
					st = $.vakata.css.get_css(selector + "." + this.data.languages.current_language, false, sh);
					if (st !== false) {
						st.style.display = "none";
					}
					st = $.vakata.css.get_css(selector + "." + i, false, sh);
					if (st !== false) {
						st.style.display = "";
					}
					this.data.languages.current_language = i;
					this.__callback(i);
					return true;
				},
				get_lang: function get_lang() {
					return this.data.languages.current_language;
				},
				_get_string: function _get_string(key, lang) {
					var langs = this._get_settings().languages,
					    s = this._get_settings().core.strings;
					if ($.isArray(langs) && langs.length) {
						lang = lang && $.inArray(lang, langs) != -1 ? lang : this.data.languages.current_language;
					}
					if (s[lang] && s[lang][key]) {
						return s[lang][key];
					}
					if (s[key]) {
						return s[key];
					}
					return key;
				},
				get_text: function get_text(obj, lang) {
					obj = this._get_node(obj) || this.data.ui.last_selected;
					if (!obj.size()) {
						return false;
					}
					var langs = this._get_settings().languages,
					    s = this._get_settings().core.html_titles;
					if ($.isArray(langs) && langs.length) {
						lang = lang && $.inArray(lang, langs) != -1 ? lang : this.data.languages.current_language;
						obj = obj.children("a." + lang);
					} else {
						obj = obj.children("a:eq(0)");
					}
					if (s) {
						obj = obj.clone();
						obj.children("INS").remove();
						return obj.html();
					} else {
						obj = obj.contents().filter(function () {
							return this.nodeType == 3;
						})[0];
						return obj.nodeValue;
					}
				},
				set_text: function set_text(obj, val, lang) {
					obj = this._get_node(obj) || this.data.ui.last_selected;
					if (!obj.size()) {
						return false;
					}
					var langs = this._get_settings().languages,
					    s = this._get_settings().core.html_titles,
					    tmp;
					if ($.isArray(langs) && langs.length) {
						lang = lang && $.inArray(lang, langs) != -1 ? lang : this.data.languages.current_language;
						obj = obj.children("a." + lang);
					} else {
						obj = obj.children("a:eq(0)");
					}
					if (s) {
						tmp = obj.children("INS").clone();
						obj.html(val).prepend(tmp);
						this.__callback({ "obj": obj, "name": val, "lang": lang });
						return true;
					} else {
						obj = obj.contents().filter(function () {
							return this.nodeType == 3;
						})[0];
						this.__callback({ "obj": obj, "name": val, "lang": lang });
						return obj.nodeValue = val;
					}
				},
				_load_css: function _load_css() {
					var langs = this._get_settings().languages,
					    str = "/* languages css */",
					    selector = ".jstree-" + this.get_index() + ' a',
					    ln;
					if ($.isArray(langs) && langs.length) {
						this.data.languages.current_language = langs[0];
						for (ln = 0; ln < langs.length; ln++) {
							str += selector + "." + langs[ln] + " {";
							if (langs[ln] != this.data.languages.current_language) {
								str += " display:none; ";
							}
							str += " } ";
						}
						sh = $.vakata.css.add_sheet({ 'str': str, 'title': "jstree-languages" });
					}
				},
				create_node: function create_node(obj, position, js, callback) {
					var t = this.__call_old(true, obj, position, js, function (t) {
						var langs = this._get_settings().languages,
						    a = t.children("a"),
						    ln;
						if ($.isArray(langs) && langs.length) {
							for (ln = 0; ln < langs.length; ln++) {
								if (!a.is("." + langs[ln])) {
									t.append(a.eq(0).clone().removeClass(langs.join(" ")).addClass(langs[ln]));
								}
							}
							a.not("." + langs.join(", .")).remove();
						}
						if (callback) {
							callback.call(this, t);
						}
					});
					return t;
				}
			}
		});
	})(jQuery);
	//*/

	/*
  * jsTree cookies plugin
  * Stores the currently opened/selected nodes in a cookie and then restores them
  * Depends on the jquery.cookie plugin
  */
	(function ($) {
		$.jstree.plugin("cookies", {
			__init: function __init() {
				if (typeof $.cookie === "undefined") {
					throw "jsTree cookie: jQuery cookie plugin not included.";
				}

				var s = this._get_settings().cookies,
				    tmp;
				if (!!s.save_loaded) {
					tmp = $.cookie(s.save_loaded);
					if (tmp && tmp.length) {
						this.data.core.to_load = tmp.split(",");
					}
				}
				if (!!s.save_opened) {
					tmp = $.cookie(s.save_opened);
					if (tmp && tmp.length) {
						this.data.core.to_open = tmp.split(",");
					}
				}
				if (!!s.save_selected) {
					tmp = $.cookie(s.save_selected);
					if (tmp && tmp.length && this.data.ui) {
						this.data.ui.to_select = tmp.split(",");
					}
				}
				this.get_container().one((this.data.ui ? "reselect" : "reopen") + ".jstree", $.proxy(function () {
					this.get_container().bind("open_node.jstree close_node.jstree select_node.jstree deselect_node.jstree", $.proxy(function (e) {
						if (this._get_settings().cookies.auto_save) {
							this.save_cookie((e.handleObj.namespace + e.handleObj.type).replace("jstree", ""));
						}
					}, this));
				}, this));
			},
			defaults: {
				save_loaded: "jstree_load",
				save_opened: "jstree_open",
				save_selected: "jstree_select",
				auto_save: true,
				cookie_options: {}
			},
			_fn: {
				save_cookie: function save_cookie(c) {
					if (this.data.core.refreshing) {
						return;
					}
					var s = this._get_settings().cookies;
					if (!c) {
						// if called manually and not by event
						if (s.save_loaded) {
							this.save_loaded();
							$.cookie(s.save_loaded, this.data.core.to_load.join(","), s.cookie_options);
						}
						if (s.save_opened) {
							this.save_opened();
							$.cookie(s.save_opened, this.data.core.to_open.join(","), s.cookie_options);
						}
						if (s.save_selected && this.data.ui) {
							this.save_selected();
							$.cookie(s.save_selected, this.data.ui.to_select.join(","), s.cookie_options);
						}
						return;
					}
					switch (c) {
						case "open_node":
						case "close_node":
							if (!!s.save_opened) {
								this.save_opened();
								$.cookie(s.save_opened, this.data.core.to_open.join(","), s.cookie_options);
							}
							if (!!s.save_loaded) {
								this.save_loaded();
								$.cookie(s.save_loaded, this.data.core.to_load.join(","), s.cookie_options);
							}
							break;
						case "select_node":
						case "deselect_node":
							if (!!s.save_selected && this.data.ui) {
								this.save_selected();
								$.cookie(s.save_selected, this.data.ui.to_select.join(","), s.cookie_options);
							}
							break;
					}
				}
			}
		});
		// include cookies by default
		// $.jstree.defaults.plugins.push("cookies");
	})(jQuery);
	//*/

	/*
  * jsTree sort plugin
  * Sorts items alphabetically (or using any other function)
  */
	(function ($) {
		$.jstree.plugin("sort", {
			__init: function __init() {
				this.get_container().bind("load_node.jstree", $.proxy(function (e, data) {
					var obj = this._get_node(data.rslt.obj);
					obj = obj === -1 ? this.get_container().children("ul") : obj.children("ul");
					this.sort(obj);
				}, this)).bind("rename_node.jstree create_node.jstree create.jstree", $.proxy(function (e, data) {
					this.sort(data.rslt.obj.parent());
				}, this)).bind("move_node.jstree", $.proxy(function (e, data) {
					var m = data.rslt.np == -1 ? this.get_container() : data.rslt.np;
					this.sort(m.children("ul"));
				}, this));
			},
			defaults: function defaults(a, b) {
				return this.get_text(a) > this.get_text(b) ? 1 : -1;
			},
			_fn: {
				sort: function sort(obj) {
					var s = this._get_settings().sort,
					    t = this;
					obj.append($.makeArray(obj.children("li")).sort($.proxy(s, t)));
					obj.find("> li > ul").each(function () {
						t.sort($(this));
					});
					this.clean_node(obj);
				}
			}
		});
	})(jQuery);
	//*/

	/*
  * jsTree DND plugin
  * Drag and drop plugin for moving/copying nodes
  */
	(function ($) {
		var o = false,
		    r = false,
		    m = false,
		    ml = false,
		    sli = false,
		    sti = false,
		    dir1 = false,
		    dir2 = false,
		    last_pos = false;
		$.vakata.dnd = {
			is_down: false,
			is_drag: false,
			helper: false,
			scroll_spd: 10,
			init_x: 0,
			init_y: 0,
			threshold: 5,
			helper_left: 5,
			helper_top: 10,
			user_data: {},

			drag_start: function drag_start(e, data, html) {
				if ($.vakata.dnd.is_drag) {
					$.vakata.drag_stop({});
				}
				try {
					e.currentTarget.unselectable = "on";
					e.currentTarget.onselectstart = function () {
						return false;
					};
					if (e.currentTarget.style) {
						e.currentTarget.style.MozUserSelect = "none";
					}
				} catch (err) {}
				$.vakata.dnd.init_x = e.pageX;
				$.vakata.dnd.init_y = e.pageY;
				$.vakata.dnd.user_data = data;
				$.vakata.dnd.is_down = true;
				$.vakata.dnd.helper = $("<div id='vakata-dragged' />").html(html); //.fadeTo(10,0.25);
				$(document).bind("mousemove", $.vakata.dnd.drag);
				$(document).bind("mouseup", $.vakata.dnd.drag_stop);
				return false;
			},
			drag: function drag(e) {
				if (!$.vakata.dnd.is_down) {
					return;
				}
				if (!$.vakata.dnd.is_drag) {
					if (Math.abs(e.pageX - $.vakata.dnd.init_x) > 5 || Math.abs(e.pageY - $.vakata.dnd.init_y) > 5) {
						$.vakata.dnd.helper.appendTo("body");
						$.vakata.dnd.is_drag = true;
						$(document).triggerHandler("drag_start.vakata", { "event": e, "data": $.vakata.dnd.user_data });
					} else {
						return;
					}
				}

				// maybe use a scrolling parent element instead of document?
				if (e.type === "mousemove") {
					// thought of adding scroll in order to move the helper, but mouse poisition is n/a
					var d = $(document),
					    t = d.scrollTop(),
					    l = d.scrollLeft();
					if (e.pageY - t < 20) {
						if (sti && dir1 === "down") {
							clearInterval(sti);sti = false;
						}
						if (!sti) {
							dir1 = "up";sti = setInterval(function () {
								$(document).scrollTop($(document).scrollTop() - $.vakata.dnd.scroll_spd);
							}, 150);
						}
					} else {
						if (sti && dir1 === "up") {
							clearInterval(sti);sti = false;
						}
					}
					if ($(window).height() - (e.pageY - t) < 20) {
						if (sti && dir1 === "up") {
							clearInterval(sti);sti = false;
						}
						if (!sti) {
							dir1 = "down";sti = setInterval(function () {
								$(document).scrollTop($(document).scrollTop() + $.vakata.dnd.scroll_spd);
							}, 150);
						}
					} else {
						if (sti && dir1 === "down") {
							clearInterval(sti);sti = false;
						}
					}

					if (e.pageX - l < 20) {
						if (sli && dir2 === "right") {
							clearInterval(sli);sli = false;
						}
						if (!sli) {
							dir2 = "left";sli = setInterval(function () {
								$(document).scrollLeft($(document).scrollLeft() - $.vakata.dnd.scroll_spd);
							}, 150);
						}
					} else {
						if (sli && dir2 === "left") {
							clearInterval(sli);sli = false;
						}
					}
					if ($(window).width() - (e.pageX - l) < 20) {
						if (sli && dir2 === "left") {
							clearInterval(sli);sli = false;
						}
						if (!sli) {
							dir2 = "right";sli = setInterval(function () {
								$(document).scrollLeft($(document).scrollLeft() + $.vakata.dnd.scroll_spd);
							}, 150);
						}
					} else {
						if (sli && dir2 === "right") {
							clearInterval(sli);sli = false;
						}
					}
				}

				$.vakata.dnd.helper.css({ left: e.pageX + $.vakata.dnd.helper_left + "px", top: e.pageY + $.vakata.dnd.helper_top + "px" });
				$(document).triggerHandler("drag.vakata", { "event": e, "data": $.vakata.dnd.user_data });
			},
			drag_stop: function drag_stop(e) {
				if (sli) {
					clearInterval(sli);
				}
				if (sti) {
					clearInterval(sti);
				}
				$(document).unbind("mousemove", $.vakata.dnd.drag);
				$(document).unbind("mouseup", $.vakata.dnd.drag_stop);
				$(document).triggerHandler("drag_stop.vakata", { "event": e, "data": $.vakata.dnd.user_data });
				$.vakata.dnd.helper.remove();
				$.vakata.dnd.init_x = 0;
				$.vakata.dnd.init_y = 0;
				$.vakata.dnd.user_data = {};
				$.vakata.dnd.is_down = false;
				$.vakata.dnd.is_drag = false;
			}
		};
		$(function () {
			var css_string = '#vakata-dragged { display:block; margin:0 0 0 0; padding:4px 4px 4px 24px; position:absolute; top:-2000px; line-height:16px; z-index:10000; } ';
			$.vakata.css.add_sheet({ str: css_string, title: "vakata" });
		});

		$.jstree.plugin("dnd", {
			__init: function __init() {
				this.data.dnd = {
					active: false,
					after: false,
					inside: false,
					before: false,
					off: false,
					prepared: false,
					w: 0,
					to1: false,
					to2: false,
					cof: false,
					cw: false,
					ch: false,
					i1: false,
					i2: false,
					mto: false
				};
				this.get_container().bind("mouseenter.jstree", $.proxy(function (e) {
					if ($.vakata.dnd.is_drag && $.vakata.dnd.user_data.jstree) {
						if (this.data.themes) {
							m.attr("class", "jstree-" + this.data.themes.theme);
							if (ml) {
								ml.attr("class", "jstree-" + this.data.themes.theme);
							}
							$.vakata.dnd.helper.attr("class", "jstree-dnd-helper jstree-" + this.data.themes.theme);
						}
						//if($(e.currentTarget).find("> ul > li").length === 0) {
						if (e.currentTarget === e.target && $.vakata.dnd.user_data.obj && $($.vakata.dnd.user_data.obj).length && $($.vakata.dnd.user_data.obj).parents(".jstree:eq(0)")[0] !== e.target) {
							// node should not be from the same tree
							var tr = $.jstree._reference(e.target),
							    dc;
							if (tr.data.dnd.foreign) {
								dc = tr._get_settings().dnd.drag_check.call(this, { "o": o, "r": tr.get_container(), is_root: true });
								if (dc === true || dc.inside === true || dc.before === true || dc.after === true) {
									$.vakata.dnd.helper.children("ins").attr("class", "jstree-ok");
								}
							} else {
								tr.prepare_move(o, tr.get_container(), "last");
								if (tr.check_move()) {
									$.vakata.dnd.helper.children("ins").attr("class", "jstree-ok");
								}
							}
						}
					}
				}, this)).bind("mouseup.jstree", $.proxy(function (e) {
					//if($.vakata.dnd.is_drag && $.vakata.dnd.user_data.jstree && $(e.currentTarget).find("> ul > li").length === 0) {
					if ($.vakata.dnd.is_drag && $.vakata.dnd.user_data.jstree && e.currentTarget === e.target && $.vakata.dnd.user_data.obj && $($.vakata.dnd.user_data.obj).length && $($.vakata.dnd.user_data.obj).parents(".jstree:eq(0)")[0] !== e.target) {
						// node should not be from the same tree
						var tr = $.jstree._reference(e.currentTarget),
						    dc;
						if (tr.data.dnd.foreign) {
							dc = tr._get_settings().dnd.drag_check.call(this, { "o": o, "r": tr.get_container(), is_root: true });
							if (dc === true || dc.inside === true || dc.before === true || dc.after === true) {
								tr._get_settings().dnd.drag_finish.call(this, { "o": o, "r": tr.get_container(), is_root: true });
							}
						} else {
							tr.move_node(o, tr.get_container(), "last", e[tr._get_settings().dnd.copy_modifier + "Key"]);
						}
					}
				}, this)).bind("mouseleave.jstree", $.proxy(function (e) {
					if (e.relatedTarget && e.relatedTarget.id && e.relatedTarget.id === "jstree-marker-line") {
						return false;
					}
					if ($.vakata.dnd.is_drag && $.vakata.dnd.user_data.jstree) {
						if (this.data.dnd.i1) {
							clearInterval(this.data.dnd.i1);
						}
						if (this.data.dnd.i2) {
							clearInterval(this.data.dnd.i2);
						}
						if (this.data.dnd.to1) {
							clearTimeout(this.data.dnd.to1);
						}
						if (this.data.dnd.to2) {
							clearTimeout(this.data.dnd.to2);
						}
						if ($.vakata.dnd.helper.children("ins").hasClass("jstree-ok")) {
							$.vakata.dnd.helper.children("ins").attr("class", "jstree-invalid");
						}
					}
				}, this)).bind("mousemove.jstree", $.proxy(function (e) {
					if ($.vakata.dnd.is_drag && $.vakata.dnd.user_data.jstree) {
						var cnt = this.get_container()[0];

						// Horizontal scroll
						if (e.pageX + 24 > this.data.dnd.cof.left + this.data.dnd.cw) {
							if (this.data.dnd.i1) {
								clearInterval(this.data.dnd.i1);
							}
							this.data.dnd.i1 = setInterval($.proxy(function () {
								this.scrollLeft += $.vakata.dnd.scroll_spd;
							}, cnt), 100);
						} else if (e.pageX - 24 < this.data.dnd.cof.left) {
							if (this.data.dnd.i1) {
								clearInterval(this.data.dnd.i1);
							}
							this.data.dnd.i1 = setInterval($.proxy(function () {
								this.scrollLeft -= $.vakata.dnd.scroll_spd;
							}, cnt), 100);
						} else {
							if (this.data.dnd.i1) {
								clearInterval(this.data.dnd.i1);
							}
						}

						// Vertical scroll
						if (e.pageY + 24 > this.data.dnd.cof.top + this.data.dnd.ch) {
							if (this.data.dnd.i2) {
								clearInterval(this.data.dnd.i2);
							}
							this.data.dnd.i2 = setInterval($.proxy(function () {
								this.scrollTop += $.vakata.dnd.scroll_spd;
							}, cnt), 100);
						} else if (e.pageY - 24 < this.data.dnd.cof.top) {
							if (this.data.dnd.i2) {
								clearInterval(this.data.dnd.i2);
							}
							this.data.dnd.i2 = setInterval($.proxy(function () {
								this.scrollTop -= $.vakata.dnd.scroll_spd;
							}, cnt), 100);
						} else {
							if (this.data.dnd.i2) {
								clearInterval(this.data.dnd.i2);
							}
						}
					}
				}, this)).bind("scroll.jstree", $.proxy(function (e) {
					if ($.vakata.dnd.is_drag && $.vakata.dnd.user_data.jstree && m && ml) {
						m.hide();
						ml.hide();
					}
				}, this)).delegate("a", "mousedown.jstree", $.proxy(function (e) {
					if (e.which === 1) {
						this.start_drag(e.currentTarget, e);
						return false;
					}
				}, this)).delegate("a", "mouseenter.jstree", $.proxy(function (e) {
					if ($.vakata.dnd.is_drag && $.vakata.dnd.user_data.jstree) {
						this.dnd_enter(e.currentTarget);
					}
				}, this)).delegate("a", "mousemove.jstree", $.proxy(function (e) {
					if ($.vakata.dnd.is_drag && $.vakata.dnd.user_data.jstree) {
						if (!r || !r.length || r.children("a")[0] !== e.currentTarget) {
							this.dnd_enter(e.currentTarget);
						}
						if (typeof this.data.dnd.off.top === "undefined") {
							this.data.dnd.off = $(e.target).offset();
						}
						this.data.dnd.w = (e.pageY - (this.data.dnd.off.top || 0)) % this.data.core.li_height;
						if (this.data.dnd.w < 0) {
							this.data.dnd.w += this.data.core.li_height;
						}
						this.dnd_show();
					}
				}, this)).delegate("a", "mouseleave.jstree", $.proxy(function (e) {
					if ($.vakata.dnd.is_drag && $.vakata.dnd.user_data.jstree) {
						if (e.relatedTarget && e.relatedTarget.id && e.relatedTarget.id === "jstree-marker-line") {
							return false;
						}
						if (m) {
							m.hide();
						}
						if (ml) {
							ml.hide();
						}
						/*
      var ec = $(e.currentTarget).closest("li"), 
      	er = $(e.relatedTarget).closest("li");
      if(er[0] !== ec.prev()[0] && er[0] !== ec.next()[0]) {
      	if(m) { m.hide(); }
      	if(ml) { ml.hide(); }
      }
      */
						this.data.dnd.mto = setTimeout(function (t) {
							return function () {
								t.dnd_leave(e);
							};
						}(this), 0);
					}
				}, this)).delegate("a", "mouseup.jstree", $.proxy(function (e) {
					if ($.vakata.dnd.is_drag && $.vakata.dnd.user_data.jstree) {
						this.dnd_finish(e);
					}
				}, this));

				$(document).bind("drag_stop.vakata", $.proxy(function () {
					if (this.data.dnd.to1) {
						clearTimeout(this.data.dnd.to1);
					}
					if (this.data.dnd.to2) {
						clearTimeout(this.data.dnd.to2);
					}
					if (this.data.dnd.i1) {
						clearInterval(this.data.dnd.i1);
					}
					if (this.data.dnd.i2) {
						clearInterval(this.data.dnd.i2);
					}
					this.data.dnd.after = false;
					this.data.dnd.before = false;
					this.data.dnd.inside = false;
					this.data.dnd.off = false;
					this.data.dnd.prepared = false;
					this.data.dnd.w = false;
					this.data.dnd.to1 = false;
					this.data.dnd.to2 = false;
					this.data.dnd.i1 = false;
					this.data.dnd.i2 = false;
					this.data.dnd.active = false;
					this.data.dnd.foreign = false;
					if (m) {
						m.css({ "top": "-2000px" });
					}
					if (ml) {
						ml.css({ "top": "-2000px" });
					}
				}, this)).bind("drag_start.vakata", $.proxy(function (e, data) {
					if (data.data.jstree) {
						var et = $(data.event.target);
						if (et.closest(".jstree").hasClass("jstree-" + this.get_index())) {
							this.dnd_enter(et);
						}
					}
				}, this));
				/*
    .bind("keydown.jstree-" + this.get_index() + " keyup.jstree-" + this.get_index(), $.proxy(function(e) {
    		if($.vakata.dnd.is_drag && $.vakata.dnd.user_data.jstree && !this.data.dnd.foreign) {
    			var h = $.vakata.dnd.helper.children("ins");
    			if(e[this._get_settings().dnd.copy_modifier + "Key"] && h.hasClass("jstree-ok")) {
    				h.parent().html(h.parent().html().replace(/ \(Copy\)$/, "") + " (Copy)");
    			} 
    			else {
    				h.parent().html(h.parent().html().replace(/ \(Copy\)$/, ""));
    			}
    		}
    	}, this)); */

				var s = this._get_settings().dnd;
				if (s.drag_target) {
					$(document).delegate(s.drag_target, "mousedown.jstree-" + this.get_index(), $.proxy(function (e) {
						o = e.target;
						$.vakata.dnd.drag_start(e, { jstree: true, obj: e.target }, "<ins class='jstree-icon'></ins>" + $(e.target).text());
						if (this.data.themes) {
							if (m) {
								m.attr("class", "jstree-" + this.data.themes.theme);
							}
							if (ml) {
								ml.attr("class", "jstree-" + this.data.themes.theme);
							}
							$.vakata.dnd.helper.attr("class", "jstree-dnd-helper jstree-" + this.data.themes.theme);
						}
						$.vakata.dnd.helper.children("ins").attr("class", "jstree-invalid");
						var cnt = this.get_container();
						this.data.dnd.cof = cnt.offset();
						this.data.dnd.cw = parseInt(cnt.width(), 10);
						this.data.dnd.ch = parseInt(cnt.height(), 10);
						this.data.dnd.foreign = true;
						e.preventDefault();
					}, this));
				}
				if (s.drop_target) {
					$(document).delegate(s.drop_target, "mouseenter.jstree-" + this.get_index(), $.proxy(function (e) {
						if (this.data.dnd.active && this._get_settings().dnd.drop_check.call(this, { "o": o, "r": $(e.target), "e": e })) {
							$.vakata.dnd.helper.children("ins").attr("class", "jstree-ok");
						}
					}, this)).delegate(s.drop_target, "mouseleave.jstree-" + this.get_index(), $.proxy(function (e) {
						if (this.data.dnd.active) {
							$.vakata.dnd.helper.children("ins").attr("class", "jstree-invalid");
						}
					}, this)).delegate(s.drop_target, "mouseup.jstree-" + this.get_index(), $.proxy(function (e) {
						if (this.data.dnd.active && $.vakata.dnd.helper.children("ins").hasClass("jstree-ok")) {
							this._get_settings().dnd.drop_finish.call(this, { "o": o, "r": $(e.target), "e": e });
						}
					}, this));
				}
			},
			defaults: {
				copy_modifier: "ctrl",
				check_timeout: 100,
				open_timeout: 500,
				drop_target: ".jstree-drop",
				drop_check: function drop_check(data) {
					return true;
				},
				drop_finish: $.noop,
				drag_target: ".jstree-draggable",
				drag_finish: $.noop,
				drag_check: function drag_check(data) {
					return { after: false, before: false, inside: true };
				}
			},
			_fn: {
				dnd_prepare: function dnd_prepare() {
					if (!r || !r.length) {
						return;
					}
					this.data.dnd.off = r.offset();
					if (this._get_settings().core.rtl) {
						this.data.dnd.off.right = this.data.dnd.off.left + r.width();
					}
					if (this.data.dnd.foreign) {
						var a = this._get_settings().dnd.drag_check.call(this, { "o": o, "r": r });
						this.data.dnd.after = a.after;
						this.data.dnd.before = a.before;
						this.data.dnd.inside = a.inside;
						this.data.dnd.prepared = true;
						return this.dnd_show();
					}
					this.prepare_move(o, r, "before");
					this.data.dnd.before = this.check_move();
					this.prepare_move(o, r, "after");
					this.data.dnd.after = this.check_move();
					if (this._is_loaded(r)) {
						this.prepare_move(o, r, "inside");
						this.data.dnd.inside = this.check_move();
					} else {
						this.data.dnd.inside = false;
					}
					this.data.dnd.prepared = true;
					return this.dnd_show();
				},
				dnd_show: function dnd_show() {
					if (!this.data.dnd.prepared) {
						return;
					}
					var o = ["before", "inside", "after"],
					    r = false,
					    rtl = this._get_settings().core.rtl,
					    pos;
					if (this.data.dnd.w < this.data.core.li_height / 3) {
						o = ["before", "inside", "after"];
					} else if (this.data.dnd.w <= this.data.core.li_height * 2 / 3) {
						o = this.data.dnd.w < this.data.core.li_height / 2 ? ["inside", "before", "after"] : ["inside", "after", "before"];
					} else {
						o = ["after", "inside", "before"];
					}
					$.each(o, $.proxy(function (i, val) {
						if (this.data.dnd[val]) {
							$.vakata.dnd.helper.children("ins").attr("class", "jstree-ok");
							r = val;
							return false;
						}
					}, this));
					if (r === false) {
						$.vakata.dnd.helper.children("ins").attr("class", "jstree-invalid");
					}

					pos = rtl ? this.data.dnd.off.right - 18 : this.data.dnd.off.left + 10;
					switch (r) {
						case "before":
							m.css({ "left": pos + "px", "top": this.data.dnd.off.top - 6 + "px" }).show();
							if (ml) {
								ml.css({ "left": pos + 8 + "px", "top": this.data.dnd.off.top - 1 + "px" }).show();
							}
							break;
						case "after":
							m.css({ "left": pos + "px", "top": this.data.dnd.off.top + this.data.core.li_height - 6 + "px" }).show();
							if (ml) {
								ml.css({ "left": pos + 8 + "px", "top": this.data.dnd.off.top + this.data.core.li_height - 1 + "px" }).show();
							}
							break;
						case "inside":
							m.css({ "left": pos + (rtl ? -4 : 4) + "px", "top": this.data.dnd.off.top + this.data.core.li_height / 2 - 5 + "px" }).show();
							if (ml) {
								ml.hide();
							}
							break;
						default:
							m.hide();
							if (ml) {
								ml.hide();
							}
							break;
					}
					last_pos = r;
					return r;
				},
				dnd_open: function dnd_open() {
					this.data.dnd.to2 = false;
					this.open_node(r, $.proxy(this.dnd_prepare, this), true);
				},
				dnd_finish: function dnd_finish(e) {
					if (this.data.dnd.foreign) {
						if (this.data.dnd.after || this.data.dnd.before || this.data.dnd.inside) {
							this._get_settings().dnd.drag_finish.call(this, { "o": o, "r": r, "p": last_pos });
						}
					} else {
						this.dnd_prepare();
						this.move_node(o, r, last_pos, e[this._get_settings().dnd.copy_modifier + "Key"]);
					}
					o = false;
					r = false;
					m.hide();
					if (ml) {
						ml.hide();
					}
				},
				dnd_enter: function dnd_enter(obj) {
					if (this.data.dnd.mto) {
						clearTimeout(this.data.dnd.mto);
						this.data.dnd.mto = false;
					}
					var s = this._get_settings().dnd;
					this.data.dnd.prepared = false;
					r = this._get_node(obj);
					if (s.check_timeout) {
						// do the calculations after a minimal timeout (users tend to drag quickly to the desired location)
						if (this.data.dnd.to1) {
							clearTimeout(this.data.dnd.to1);
						}
						this.data.dnd.to1 = setTimeout($.proxy(this.dnd_prepare, this), s.check_timeout);
					} else {
						this.dnd_prepare();
					}
					if (s.open_timeout) {
						if (this.data.dnd.to2) {
							clearTimeout(this.data.dnd.to2);
						}
						if (r && r.length && r.hasClass("jstree-closed")) {
							// if the node is closed - open it, then recalculate
							this.data.dnd.to2 = setTimeout($.proxy(this.dnd_open, this), s.open_timeout);
						}
					} else {
						if (r && r.length && r.hasClass("jstree-closed")) {
							this.dnd_open();
						}
					}
				},
				dnd_leave: function dnd_leave(e) {
					this.data.dnd.after = false;
					this.data.dnd.before = false;
					this.data.dnd.inside = false;
					$.vakata.dnd.helper.children("ins").attr("class", "jstree-invalid");
					m.hide();
					if (ml) {
						ml.hide();
					}
					if (r && r[0] === e.target.parentNode) {
						if (this.data.dnd.to1) {
							clearTimeout(this.data.dnd.to1);
							this.data.dnd.to1 = false;
						}
						if (this.data.dnd.to2) {
							clearTimeout(this.data.dnd.to2);
							this.data.dnd.to2 = false;
						}
					}
				},
				start_drag: function start_drag(obj, e) {
					o = this._get_node(obj);
					if (this.data.ui && this.is_selected(o)) {
						o = this._get_node(null, true);
					}
					var dt = o.length > 1 ? this._get_string("multiple_selection") : this.get_text(o),
					    cnt = this.get_container();
					if (!this._get_settings().core.html_titles) {
						dt = dt.replace(/</ig, "&lt;").replace(/>/ig, "&gt;");
					}
					$.vakata.dnd.drag_start(e, { jstree: true, obj: o }, "<ins class='jstree-icon'></ins>" + dt);
					if (this.data.themes) {
						if (m) {
							m.attr("class", "jstree-" + this.data.themes.theme);
						}
						if (ml) {
							ml.attr("class", "jstree-" + this.data.themes.theme);
						}
						$.vakata.dnd.helper.attr("class", "jstree-dnd-helper jstree-" + this.data.themes.theme);
					}
					this.data.dnd.cof = cnt.offset();
					this.data.dnd.cw = parseInt(cnt.width(), 10);
					this.data.dnd.ch = parseInt(cnt.height(), 10);
					this.data.dnd.active = true;
				}
			}
		});
		$(function () {
			var css_string = '' + '#vakata-dragged ins { display:block; text-decoration:none; width:16px; height:16px; margin:0 0 0 0; padding:0; position:absolute; top:4px; left:4px; ' + ' -moz-border-radius:4px; border-radius:4px; -webkit-border-radius:4px; ' + '} ' + '#vakata-dragged .jstree-ok { background:green; } ' + '#vakata-dragged .jstree-invalid { background:red; } ' + '#jstree-marker { padding:0; margin:0; font-size:12px; overflow:hidden; height:12px; width:8px; position:absolute; top:-30px; z-index:10001; background-repeat:no-repeat; display:none; background-color:transparent; text-shadow:1px 1px 1px white; color:black; line-height:10px; } ' + '#jstree-marker-line { padding:0; margin:0; line-height:0%; font-size:1px; overflow:hidden; height:1px; width:100px; position:absolute; top:-30px; z-index:10000; background-repeat:no-repeat; display:none; background-color:#456c43; ' + ' cursor:pointer; border:1px solid #eeeeee; border-left:0; -moz-box-shadow: 0px 0px 2px #666; -webkit-box-shadow: 0px 0px 2px #666; box-shadow: 0px 0px 2px #666; ' + ' -moz-border-radius:1px; border-radius:1px; -webkit-border-radius:1px; ' + '}' + '';
			$.vakata.css.add_sheet({ str: css_string, title: "jstree" });
			m = $("<div />").attr({ id: "jstree-marker" }).hide().html("&raquo;").bind("mouseleave mouseenter", function (e) {
				m.hide();
				ml.hide();
				e.preventDefault();
				e.stopImmediatePropagation();
				return false;
			}).appendTo("body");
			ml = $("<div />").attr({ id: "jstree-marker-line" }).hide().bind("mouseup", function (e) {
				if (r && r.length) {
					r.children("a").trigger(e);
					e.preventDefault();
					e.stopImmediatePropagation();
					return false;
				}
			}).bind("mouseleave", function (e) {
				var rt = $(e.relatedTarget);
				if (rt.is(".jstree") || rt.closest(".jstree").length === 0) {
					if (r && r.length) {
						r.children("a").trigger(e);
						m.hide();
						ml.hide();
						e.preventDefault();
						e.stopImmediatePropagation();
						return false;
					}
				}
			}).appendTo("body");
			$(document).bind("drag_start.vakata", function (e, data) {
				if (data.data.jstree) {
					m.show();if (ml) {
						ml.show();
					}
				}
			});
			$(document).bind("drag_stop.vakata", function (e, data) {
				if (data.data.jstree) {
					m.hide();if (ml) {
						ml.hide();
					}
				}
			});
		});
	})(jQuery);
	//*/

	/*
  * jsTree checkbox plugin
  * Inserts checkboxes in front of every node
  * Depends on the ui plugin
  * DOES NOT WORK NICELY WITH MULTITREE DRAG'N'DROP
  */
	(function ($) {
		$.jstree.plugin("checkbox", {
			__init: function __init() {
				this.data.checkbox.noui = this._get_settings().checkbox.override_ui;
				if (this.data.ui && this.data.checkbox.noui) {
					this.select_node = this.deselect_node = this.deselect_all = $.noop;
					this.get_selected = this.get_checked;
				}

				this.get_container().bind("open_node.jstree create_node.jstree clean_node.jstree refresh.jstree", $.proxy(function (e, data) {
					this._prepare_checkboxes(data.rslt.obj);
				}, this)).bind("loaded.jstree", $.proxy(function (e) {
					this._prepare_checkboxes();
				}, this)).delegate(this.data.ui && this.data.checkbox.noui ? "a" : "ins.jstree-checkbox", "click.jstree", $.proxy(function (e) {
					e.preventDefault();
					if (this._get_node(e.target).hasClass("jstree-checked")) {
						this.uncheck_node(e.target);
					} else {
						this.check_node(e.target);
					}
					if (this.data.ui && this.data.checkbox.noui) {
						this.save_selected();
						if (this.data.cookies) {
							this.save_cookie("select_node");
						}
					} else {
						e.stopImmediatePropagation();
						return false;
					}
				}, this));
			},
			defaults: {
				override_ui: false,
				two_state: false,
				real_checkboxes: false,
				checked_parent_open: true,
				real_checkboxes_names: function real_checkboxes_names(n) {
					return ["check_" + (n[0].id || Math.ceil(Math.random() * 10000)), 1];
				}
			},
			__destroy: function __destroy() {
				this.get_container().find("input.jstree-real-checkbox").removeClass("jstree-real-checkbox").end().find("ins.jstree-checkbox").remove();
			},
			_fn: {
				_checkbox_notify: function _checkbox_notify(n, data) {
					if (data.checked) {
						this.check_node(n, false);
					}
				},
				_prepare_checkboxes: function _prepare_checkboxes(obj) {
					obj = !obj || obj == -1 ? this.get_container().find("> ul > li") : this._get_node(obj);
					if (obj === false) {
						return;
					} // added for removing root nodes
					var c,
					    _this = this,
					    t,
					    ts = this._get_settings().checkbox.two_state,
					    rc = this._get_settings().checkbox.real_checkboxes,
					    rcn = this._get_settings().checkbox.real_checkboxes_names;
					obj.each(function () {
						t = $(this);
						c = t.is("li") && (t.hasClass("jstree-checked") || rc && t.children(":checked").length) ? "jstree-checked" : "jstree-unchecked";
						t.find("li").andSelf().each(function () {
							var $t = $(this),
							    nm;
							$t.children("a" + (_this.data.languages ? "" : ":eq(0)")).not(":has(.jstree-checkbox)").prepend("<ins class='jstree-checkbox'>&#160;</ins>").parent().not(".jstree-checked, .jstree-unchecked").addClass(ts ? "jstree-unchecked" : c);
							if (rc) {
								if (!$t.children(":checkbox").length) {
									nm = rcn.call(_this, $t);
									$t.prepend("<input type='checkbox' class='jstree-real-checkbox' id='" + nm[0] + "' name='" + nm[0] + "' value='" + nm[1] + "' />");
								} else {
									$t.children(":checkbox").addClass("jstree-real-checkbox");
								}
							}
							if (!ts) {
								if (c === "jstree-checked" || $t.hasClass("jstree-checked") || $t.children(':checked').length) {
									$t.find("li").andSelf().addClass("jstree-checked").children(":checkbox").prop("checked", true);
								}
							} else {
								if ($t.hasClass("jstree-checked") || $t.children(':checked').length) {
									$t.addClass("jstree-checked").children(":checkbox").prop("checked", true);
								}
							}
						});
					});
					if (!ts) {
						obj.find(".jstree-checked").parent().parent().each(function () {
							_this._repair_state(this);
						});
					}
				},
				change_state: function change_state(obj, state) {
					obj = this._get_node(obj);
					var coll = false,
					    rc = this._get_settings().checkbox.real_checkboxes;
					if (!obj || obj === -1) {
						return false;
					}
					state = state === false || state === true ? state : obj.hasClass("jstree-checked");
					if (this._get_settings().checkbox.two_state) {
						if (state) {
							obj.removeClass("jstree-checked").addClass("jstree-unchecked");
							if (rc) {
								obj.children(":checkbox").prop("checked", false);
							}
						} else {
							obj.removeClass("jstree-unchecked").addClass("jstree-checked");
							if (rc) {
								obj.children(":checkbox").prop("checked", true);
							}
						}
					} else {
						if (state) {
							coll = obj.find("li").andSelf();
							if (!coll.filter(".jstree-checked, .jstree-undetermined").length) {
								return false;
							}
							coll.removeClass("jstree-checked jstree-undetermined").addClass("jstree-unchecked");
							if (rc) {
								coll.children(":checkbox").prop("checked", false);
							}
						} else {
							coll = obj.find("li").andSelf();
							if (!coll.filter(".jstree-unchecked, .jstree-undetermined").length) {
								return false;
							}
							coll.removeClass("jstree-unchecked jstree-undetermined").addClass("jstree-checked");
							if (rc) {
								coll.children(":checkbox").prop("checked", true);
							}
							if (this.data.ui) {
								this.data.ui.last_selected = obj;
							}
							this.data.checkbox.last_selected = obj;
						}
						obj.parentsUntil(".jstree", "li").each(function () {
							var $this = $(this);
							if (state) {
								if ($this.children("ul").children("li.jstree-checked, li.jstree-undetermined").length) {
									$this.parentsUntil(".jstree", "li").andSelf().removeClass("jstree-checked jstree-unchecked").addClass("jstree-undetermined");
									if (rc) {
										$this.parentsUntil(".jstree", "li").andSelf().children(":checkbox").prop("checked", false);
									}
									return false;
								} else {
									$this.removeClass("jstree-checked jstree-undetermined").addClass("jstree-unchecked");
									if (rc) {
										$this.children(":checkbox").prop("checked", false);
									}
								}
							} else {
								if ($this.children("ul").children("li.jstree-unchecked, li.jstree-undetermined").length) {
									$this.parentsUntil(".jstree", "li").andSelf().removeClass("jstree-checked jstree-unchecked").addClass("jstree-undetermined");
									if (rc) {
										$this.parentsUntil(".jstree", "li").andSelf().children(":checkbox").prop("checked", false);
									}
									return false;
								} else {
									$this.removeClass("jstree-unchecked jstree-undetermined").addClass("jstree-checked");
									if (rc) {
										$this.children(":checkbox").prop("checked", true);
									}
								}
							}
						});
					}
					if (this.data.ui && this.data.checkbox.noui) {
						this.data.ui.selected = this.get_checked();
					}
					this.__callback(obj);
					return true;
				},
				check_node: function check_node(obj) {
					if (this.change_state(obj, false)) {
						obj = this._get_node(obj);
						if (this._get_settings().checkbox.checked_parent_open) {
							var t = this;
							obj.parents(".jstree-closed").each(function () {
								t.open_node(this, false, true);
							});
						}
						this.__callback({ "obj": obj });
					}
				},
				uncheck_node: function uncheck_node(obj) {
					if (this.change_state(obj, true)) {
						this.__callback({ "obj": this._get_node(obj) });
					}
				},
				check_all: function check_all() {
					var _this = this,
					    coll = this._get_settings().checkbox.two_state ? this.get_container_ul().find("li") : this.get_container_ul().children("li");
					coll.each(function () {
						_this.change_state(this, false);
					});
					this.__callback();
				},
				uncheck_all: function uncheck_all() {
					var _this = this,
					    coll = this._get_settings().checkbox.two_state ? this.get_container_ul().find("li") : this.get_container_ul().children("li");
					coll.each(function () {
						_this.change_state(this, true);
					});
					this.__callback();
				},

				is_checked: function is_checked(obj) {
					obj = this._get_node(obj);
					return obj.length ? obj.is(".jstree-checked") : false;
				},
				get_checked: function get_checked(obj, get_all) {
					obj = !obj || obj === -1 ? this.get_container() : this._get_node(obj);
					return get_all || this._get_settings().checkbox.two_state ? obj.find(".jstree-checked") : obj.find("> ul > .jstree-checked, .jstree-undetermined > ul > .jstree-checked");
				},
				get_unchecked: function get_unchecked(obj, get_all) {
					obj = !obj || obj === -1 ? this.get_container() : this._get_node(obj);
					return get_all || this._get_settings().checkbox.two_state ? obj.find(".jstree-unchecked") : obj.find("> ul > .jstree-unchecked, .jstree-undetermined > ul > .jstree-unchecked");
				},

				show_checkboxes: function show_checkboxes() {
					this.get_container().children("ul").removeClass("jstree-no-checkboxes");
				},
				hide_checkboxes: function hide_checkboxes() {
					this.get_container().children("ul").addClass("jstree-no-checkboxes");
				},

				_repair_state: function _repair_state(obj) {
					obj = this._get_node(obj);
					if (!obj.length) {
						return;
					}
					if (this._get_settings().checkbox.two_state) {
						obj.find('li').andSelf().not('.jstree-checked').removeClass('jstree-undetermined').addClass('jstree-unchecked').children(':checkbox').prop('checked', true);
						return;
					}
					var rc = this._get_settings().checkbox.real_checkboxes,
					    a = obj.find("> ul > .jstree-checked").length,
					    b = obj.find("> ul > .jstree-undetermined").length,
					    c = obj.find("> ul > li").length;
					if (c === 0) {
						if (obj.hasClass("jstree-undetermined")) {
							this.change_state(obj, false);
						}
					} else if (a === 0 && b === 0) {
						this.change_state(obj, true);
					} else if (a === c) {
						this.change_state(obj, false);
					} else {
						obj.parentsUntil(".jstree", "li").andSelf().removeClass("jstree-checked jstree-unchecked").addClass("jstree-undetermined");
						if (rc) {
							obj.parentsUntil(".jstree", "li").andSelf().children(":checkbox").prop("checked", false);
						}
					}
				},
				reselect: function reselect() {
					if (this.data.ui && this.data.checkbox.noui) {
						var _this = this,
						    s = this.data.ui.to_select;
						s = $.map($.makeArray(s), function (n) {
							return "#" + n.toString().replace(/^#/, "").replace(/\\\//g, "/").replace(/\//g, "\\\/").replace(/\\\./g, ".").replace(/\./g, "\\.").replace(/\:/g, "\\:");
						});
						this.deselect_all();
						$.each(s, function (i, val) {
							_this.check_node(val);
						});
						this.__callback();
					} else {
						this.__call_old();
					}
				},
				save_loaded: function save_loaded() {
					var _this = this;
					this.data.core.to_load = [];
					this.get_container_ul().find("li.jstree-closed.jstree-undetermined").each(function () {
						if (this.id) {
							_this.data.core.to_load.push("#" + this.id);
						}
					});
				}
			}
		});
		$(function () {
			var css_string = '.jstree .jstree-real-checkbox { display:none; } ';
			$.vakata.css.add_sheet({ str: css_string, title: "jstree" });
		});
	})(jQuery);
	//*/

	/* 
  * jsTree XML plugin
  * The XML data store. Datastores are build by overriding the `load_node` and `_is_loaded` functions.
  */
	(function ($) {
		$.vakata.xslt = function (xml, xsl, callback) {
			var r = false,
			    p,
			    q,
			    s;
			// IE9
			if (r === false && window.ActiveXObject) {
				try {
					r = new ActiveXObject("Msxml2.XSLTemplate");
					q = new ActiveXObject("Msxml2.DOMDocument");
					q.loadXML(xml);
					s = new ActiveXObject("Msxml2.FreeThreadedDOMDocument");
					s.loadXML(xsl);
					r.stylesheet = s;
					p = r.createProcessor();
					p.input = q;
					p.transform();
					r = p.output;
				} catch (e) {}
			}
			xml = $.parseXML(xml);
			xsl = $.parseXML(xsl);
			// FF, Chrome
			if (r === false && typeof XSLTProcessor !== "undefined") {
				p = new XSLTProcessor();
				p.importStylesheet(xsl);
				r = p.transformToFragment(xml, document);
				r = $('<div />').append(r).html();
			}
			// OLD IE
			if (r === false && typeof xml.transformNode !== "undefined") {
				r = xml.transformNode(xsl);
			}
			callback.call(null, r);
		};
		var xsl = {
			'nest': '<' + '?xml version="1.0" encoding="utf-8" ?>' + '<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" >' + '<xsl:output method="html" encoding="utf-8" omit-xml-declaration="yes" standalone="no" indent="no" media-type="text/html" />' + '<xsl:template match="/">' + '	<xsl:call-template name="nodes">' + '		<xsl:with-param name="node" select="/root" />' + '	</xsl:call-template>' + '</xsl:template>' + '<xsl:template name="nodes">' + '	<xsl:param name="node" />' + '	<ul>' + '	<xsl:for-each select="$node/item">' + '		<xsl:variable name="children" select="count(./item) &gt; 0" />' + '		<li>' + '			<xsl:attribute name="class">' + '				<xsl:if test="position() = last()">jstree-last </xsl:if>' + '				<xsl:choose>' + '					<xsl:when test="@state = \'open\'">jstree-open </xsl:when>' + '					<xsl:when test="$children or @hasChildren or @state = \'closed\'">jstree-closed </xsl:when>' + '					<xsl:otherwise>jstree-leaf </xsl:otherwise>' + '				</xsl:choose>' + '				<xsl:value-of select="@class" />' + '			</xsl:attribute>' + '			<xsl:for-each select="@*">' + '				<xsl:if test="name() != \'class\' and name() != \'state\' and name() != \'hasChildren\'">' + '					<xsl:attribute name="{name()}"><xsl:value-of select="." /></xsl:attribute>' + '				</xsl:if>' + '			</xsl:for-each>' + '	<ins class="jstree-icon"><xsl:text>&#xa0;</xsl:text></ins>' + '			<xsl:for-each select="content/name">' + '				<a>' + '				<xsl:attribute name="href">' + '					<xsl:choose>' + '					<xsl:when test="@href"><xsl:value-of select="@href" /></xsl:when>' + '					<xsl:otherwise>#</xsl:otherwise>' + '					</xsl:choose>' + '				</xsl:attribute>' + '				<xsl:attribute name="class"><xsl:value-of select="@lang" /> <xsl:value-of select="@class" /></xsl:attribute>' + '				<xsl:attribute name="style"><xsl:value-of select="@style" /></xsl:attribute>' + '				<xsl:for-each select="@*">' + '					<xsl:if test="name() != \'style\' and name() != \'class\' and name() != \'href\'">' + '						<xsl:attribute name="{name()}"><xsl:value-of select="." /></xsl:attribute>' + '					</xsl:if>' + '				</xsl:for-each>' + '					<ins>' + '						<xsl:attribute name="class">jstree-icon ' + '							<xsl:if test="string-length(attribute::icon) > 0 and not(contains(@icon,\'/\'))"><xsl:value-of select="@icon" /></xsl:if>' + '						</xsl:attribute>' + '						<xsl:if test="string-length(attribute::icon) > 0 and contains(@icon,\'/\')"><xsl:attribute name="style">background:url(<xsl:value-of select="@icon" />) center center no-repeat;</xsl:attribute></xsl:if>' + '						<xsl:text>&#xa0;</xsl:text>' + '					</ins>' + '					<xsl:copy-of select="./child::node()" />' + '				</a>' + '			</xsl:for-each>' + '			<xsl:if test="$children or @hasChildren"><xsl:call-template name="nodes"><xsl:with-param name="node" select="current()" /></xsl:call-template></xsl:if>' + '		</li>' + '	</xsl:for-each>' + '	</ul>' + '</xsl:template>' + '</xsl:stylesheet>',

			'flat': '<' + '?xml version="1.0" encoding="utf-8" ?>' + '<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" >' + '<xsl:output method="html" encoding="utf-8" omit-xml-declaration="yes" standalone="no" indent="no" media-type="text/xml" />' + '<xsl:template match="/">' + '	<ul>' + '	<xsl:for-each select="//item[not(@parent_id) or @parent_id=0 or not(@parent_id = //item/@id)]">' + /* the last `or` may be removed */
			'		<xsl:call-template name="nodes">' + '			<xsl:with-param name="node" select="." />' + '			<xsl:with-param name="is_last" select="number(position() = last())" />' + '		</xsl:call-template>' + '	</xsl:for-each>' + '	</ul>' + '</xsl:template>' + '<xsl:template name="nodes">' + '	<xsl:param name="node" />' + '	<xsl:param name="is_last" />' + '	<xsl:variable name="children" select="count(//item[@parent_id=$node/attribute::id]) &gt; 0" />' + '	<li>' + '	<xsl:attribute name="class">' + '		<xsl:if test="$is_last = true()">jstree-last </xsl:if>' + '		<xsl:choose>' + '			<xsl:when test="@state = \'open\'">jstree-open </xsl:when>' + '			<xsl:when test="$children or @hasChildren or @state = \'closed\'">jstree-closed </xsl:when>' + '			<xsl:otherwise>jstree-leaf </xsl:otherwise>' + '		</xsl:choose>' + '		<xsl:value-of select="@class" />' + '	</xsl:attribute>' + '	<xsl:for-each select="@*">' + '		<xsl:if test="name() != \'parent_id\' and name() != \'hasChildren\' and name() != \'class\' and name() != \'state\'">' + '		<xsl:attribute name="{name()}"><xsl:value-of select="." /></xsl:attribute>' + '		</xsl:if>' + '	</xsl:for-each>' + '	<ins class="jstree-icon"><xsl:text>&#xa0;</xsl:text></ins>' + '	<xsl:for-each select="content/name">' + '		<a>' + '		<xsl:attribute name="href">' + '			<xsl:choose>' + '			<xsl:when test="@href"><xsl:value-of select="@href" /></xsl:when>' + '			<xsl:otherwise>#</xsl:otherwise>' + '			</xsl:choose>' + '		</xsl:attribute>' + '		<xsl:attribute name="class"><xsl:value-of select="@lang" /> <xsl:value-of select="@class" /></xsl:attribute>' + '		<xsl:attribute name="style"><xsl:value-of select="@style" /></xsl:attribute>' + '		<xsl:for-each select="@*">' + '			<xsl:if test="name() != \'style\' and name() != \'class\' and name() != \'href\'">' + '				<xsl:attribute name="{name()}"><xsl:value-of select="." /></xsl:attribute>' + '			</xsl:if>' + '		</xsl:for-each>' + '			<ins>' + '				<xsl:attribute name="class">jstree-icon ' + '					<xsl:if test="string-length(attribute::icon) > 0 and not(contains(@icon,\'/\'))"><xsl:value-of select="@icon" /></xsl:if>' + '				</xsl:attribute>' + '				<xsl:if test="string-length(attribute::icon) > 0 and contains(@icon,\'/\')"><xsl:attribute name="style">background:url(<xsl:value-of select="@icon" />) center center no-repeat;</xsl:attribute></xsl:if>' + '				<xsl:text>&#xa0;</xsl:text>' + '			</ins>' + '			<xsl:copy-of select="./child::node()" />' + '		</a>' + '	</xsl:for-each>' + '	<xsl:if test="$children">' + '		<ul>' + '		<xsl:for-each select="//item[@parent_id=$node/attribute::id]">' + '			<xsl:call-template name="nodes">' + '				<xsl:with-param name="node" select="." />' + '				<xsl:with-param name="is_last" select="number(position() = last())" />' + '			</xsl:call-template>' + '		</xsl:for-each>' + '		</ul>' + '	</xsl:if>' + '	</li>' + '</xsl:template>' + '</xsl:stylesheet>'
		},
		    escape_xml = function escape_xml(string) {
			return string.toString().replace(/&/g, '&amp;').replace(/</g, '&lt;').replace(/>/g, '&gt;').replace(/"/g, '&quot;').replace(/'/g, '&apos;');
		};
		$.jstree.plugin("xml_data", {
			defaults: {
				data: false,
				ajax: false,
				xsl: "flat",
				clean_node: false,
				correct_state: true,
				get_skip_empty: false,
				get_include_preamble: true
			},
			_fn: {
				load_node: function load_node(obj, s_call, e_call) {
					var _this = this;this.load_node_xml(obj, function () {
						_this.__callback({ "obj": _this._get_node(obj) });s_call.call(this);
					}, e_call);
				},
				_is_loaded: function _is_loaded(obj) {
					var s = this._get_settings().xml_data;
					obj = this._get_node(obj);
					return obj == -1 || !obj || !s.ajax && !$.isFunction(s.data) || obj.is(".jstree-open, .jstree-leaf") || obj.children("ul").children("li").size() > 0;
				},
				load_node_xml: function load_node_xml(obj, s_call, e_call) {
					var s = this.get_settings().xml_data,
					    error_func = function error_func() {},
					    success_func = function success_func() {};

					obj = this._get_node(obj);
					if (obj && obj !== -1) {
						if (obj.data("jstree_is_loading")) {
							return;
						} else {
							obj.data("jstree_is_loading", true);
						}
					}
					switch (!0) {
						case !s.data && !s.ajax:
							throw "Neither data nor ajax settings supplied.";
						case $.isFunction(s.data):
							s.data.call(this, obj, $.proxy(function (d) {
								this.parse_xml(d, $.proxy(function (d) {
									if (d) {
										d = d.replace(/ ?xmlns="[^"]*"/ig, "");
										if (d.length > 10) {
											d = $(d);
											if (obj === -1 || !obj) {
												this.get_container().children("ul").empty().append(d.children());
											} else {
												obj.children("a.jstree-loading").removeClass("jstree-loading");obj.append(d);obj.removeData("jstree_is_loading");
											}
											if (s.clean_node) {
												this.clean_node(obj);
											}
											if (s_call) {
												s_call.call(this);
											}
										} else {
											if (obj && obj !== -1) {
												obj.children("a.jstree-loading").removeClass("jstree-loading");
												obj.removeData("jstree_is_loading");
												if (s.correct_state) {
													this.correct_state(obj);
													if (s_call) {
														s_call.call(this);
													}
												}
											} else {
												if (s.correct_state) {
													this.get_container().children("ul").empty();
													if (s_call) {
														s_call.call(this);
													}
												}
											}
										}
									}
								}, this));
							}, this));
							break;
						case !!s.data && !s.ajax || !!s.data && !!s.ajax && (!obj || obj === -1):
							if (!obj || obj == -1) {
								this.parse_xml(s.data, $.proxy(function (d) {
									if (d) {
										d = d.replace(/ ?xmlns="[^"]*"/ig, "");
										if (d.length > 10) {
											d = $(d);
											this.get_container().children("ul").empty().append(d.children());
											if (s.clean_node) {
												this.clean_node(obj);
											}
											if (s_call) {
												s_call.call(this);
											}
										}
									} else {
										if (s.correct_state) {
											this.get_container().children("ul").empty();
											if (s_call) {
												s_call.call(this);
											}
										}
									}
								}, this));
							}
							break;
						case !s.data && !!s.ajax || !!s.data && !!s.ajax && obj && obj !== -1:
							error_func = function error_func(x, t, e) {
								var ef = this.get_settings().xml_data.ajax.error;
								if (ef) {
									ef.call(this, x, t, e);
								}
								if (obj !== -1 && obj.length) {
									obj.children("a.jstree-loading").removeClass("jstree-loading");
									obj.removeData("jstree_is_loading");
									if (t === "success" && s.correct_state) {
										this.correct_state(obj);
									}
								} else {
									if (t === "success" && s.correct_state) {
										this.get_container().children("ul").empty();
									}
								}
								if (e_call) {
									e_call.call(this);
								}
							};
							success_func = function success_func(d, t, x) {
								d = x.responseText;
								var sf = this.get_settings().xml_data.ajax.success;
								if (sf) {
									d = sf.call(this, d, t, x) || d;
								}
								if (d === "" || d && d.toString && d.toString().replace(/^[\s\n]+$/, "") === "") {
									return error_func.call(this, x, t, "");
								}
								this.parse_xml(d, $.proxy(function (d) {
									if (d) {
										d = d.replace(/ ?xmlns="[^"]*"/ig, "");
										if (d.length > 10) {
											d = $(d);
											if (obj === -1 || !obj) {
												this.get_container().children("ul").empty().append(d.children());
											} else {
												obj.children("a.jstree-loading").removeClass("jstree-loading");obj.append(d);obj.removeData("jstree_is_loading");
											}
											if (s.clean_node) {
												this.clean_node(obj);
											}
											if (s_call) {
												s_call.call(this);
											}
										} else {
											if (obj && obj !== -1) {
												obj.children("a.jstree-loading").removeClass("jstree-loading");
												obj.removeData("jstree_is_loading");
												if (s.correct_state) {
													this.correct_state(obj);
													if (s_call) {
														s_call.call(this);
													}
												}
											} else {
												if (s.correct_state) {
													this.get_container().children("ul").empty();
													if (s_call) {
														s_call.call(this);
													}
												}
											}
										}
									}
								}, this));
							};
							s.ajax.context = this;
							s.ajax.error = error_func;
							s.ajax.success = success_func;
							if (!s.ajax.dataType) {
								s.ajax.dataType = "xml";
							}
							if ($.isFunction(s.ajax.url)) {
								s.ajax.url = s.ajax.url.call(this, obj);
							}
							if ($.isFunction(s.ajax.data)) {
								s.ajax.data = s.ajax.data.call(this, obj);
							}
							$.ajax(s.ajax);
							break;
					}
				},
				parse_xml: function parse_xml(xml, callback) {
					var s = this._get_settings().xml_data;
					$.vakata.xslt(xml, xsl[s.xsl], callback);
				},
				get_xml: function get_xml(tp, obj, li_attr, a_attr, is_callback) {
					var result = "",
					    s = this._get_settings(),
					    _this = this,
					    tmp1,
					    tmp2,
					    li,
					    a,
					    lang;
					if (!tp) {
						tp = "flat";
					}
					if (!is_callback) {
						is_callback = 0;
					}
					obj = this._get_node(obj);
					if (!obj || obj === -1) {
						obj = this.get_container().find("> ul > li");
					}
					li_attr = $.isArray(li_attr) ? li_attr : ["id", "class"];
					if (!is_callback && this.data.types && $.inArray(s.types.type_attr, li_attr) === -1) {
						li_attr.push(s.types.type_attr);
					}

					a_attr = $.isArray(a_attr) ? a_attr : [];

					if (!is_callback) {
						if (s.xml_data.get_include_preamble) {
							result += '<' + '?xml version="1.0" encoding="UTF-8"?' + '>';
						}
						result += "<root>";
					}
					obj.each(function () {
						result += "<item";
						li = $(this);
						$.each(li_attr, function (i, v) {
							var t = li.attr(v);
							if (!s.xml_data.get_skip_empty || typeof t !== "undefined") {
								result += " " + v + "=\"" + escape_xml((" " + (t || "")).replace(/ jstree[^ ]*/ig, '').replace(/\s+$/ig, " ").replace(/^ /, "").replace(/ $/, "")) + "\"";
							}
						});
						if (li.hasClass("jstree-open")) {
							result += " state=\"open\"";
						}
						if (li.hasClass("jstree-closed")) {
							result += " state=\"closed\"";
						}
						if (tp === "flat") {
							result += " parent_id=\"" + escape_xml(is_callback) + "\"";
						}
						result += ">";
						result += "<content>";
						a = li.children("a");
						a.each(function () {
							tmp1 = $(this);
							lang = false;
							result += "<name";
							if ($.inArray("languages", s.plugins) !== -1) {
								$.each(s.languages, function (k, z) {
									if (tmp1.hasClass(z)) {
										result += " lang=\"" + escape_xml(z) + "\"";lang = z;return false;
									}
								});
							}
							if (a_attr.length) {
								$.each(a_attr, function (k, z) {
									var t = tmp1.attr(z);
									if (!s.xml_data.get_skip_empty || typeof t !== "undefined") {
										result += " " + z + "=\"" + escape_xml((" " + t || "").replace(/ jstree[^ ]*/ig, '').replace(/\s+$/ig, " ").replace(/^ /, "").replace(/ $/, "")) + "\"";
									}
								});
							}
							if (tmp1.children("ins").get(0).className.replace(/jstree[^ ]*|$/ig, '').replace(/^\s+$/ig, "").length) {
								result += ' icon="' + escape_xml(tmp1.children("ins").get(0).className.replace(/jstree[^ ]*|$/ig, '').replace(/\s+$/ig, " ").replace(/^ /, "").replace(/ $/, "")) + '"';
							}
							if (tmp1.children("ins").get(0).style.backgroundImage.length) {
								result += ' icon="' + escape_xml(tmp1.children("ins").get(0).style.backgroundImage.replace("url(", "").replace(")", "").replace(/'/ig, "").replace(/"/ig, "")) + '"';
							}
							result += ">";
							result += "<![CDATA[" + _this.get_text(tmp1, lang) + "]]>";
							result += "</name>";
						});
						result += "</content>";
						tmp2 = li[0].id || true;
						li = li.find("> ul > li");
						if (li.length) {
							tmp2 = _this.get_xml(tp, li, li_attr, a_attr, tmp2);
						} else {
							tmp2 = "";
						}
						if (tp == "nest") {
							result += tmp2;
						}
						result += "</item>";
						if (tp == "flat") {
							result += tmp2;
						}
					});
					if (!is_callback) {
						result += "</root>";
					}
					return result;
				}
			}
		});
	})(jQuery);
	//*/

	/*
  * jsTree search plugin
  * Enables both sync and async search on the tree
  * DOES NOT WORK WITH JSON PROGRESSIVE RENDER
  */
	(function ($) {
		if ($().jquery.split('.')[1] >= 8) {
			$.expr[':'].jstree_contains = $.expr.createPseudo(function (search) {
				return function (a) {
					return (a.textContent || a.innerText || "").toLowerCase().indexOf(search.toLowerCase()) >= 0;
				};
			});
			$.expr[':'].jstree_title_contains = $.expr.createPseudo(function (search) {
				return function (a) {
					return (a.getAttribute("title") || "").toLowerCase().indexOf(search.toLowerCase()) >= 0;
				};
			});
		} else {
			$.expr[':'].jstree_contains = function (a, i, m) {
				return (a.textContent || a.innerText || "").toLowerCase().indexOf(m[3].toLowerCase()) >= 0;
			};
			$.expr[':'].jstree_title_contains = function (a, i, m) {
				return (a.getAttribute("title") || "").toLowerCase().indexOf(m[3].toLowerCase()) >= 0;
			};
		}
		$.jstree.plugin("search", {
			__init: function __init() {
				this.data.search.str = "";
				this.data.search.result = $();
				if (this._get_settings().search.show_only_matches) {
					this.get_container().bind("search.jstree", function (e, data) {
						$(this).children("ul").find("li").hide().removeClass("jstree-last");
						data.rslt.nodes.parentsUntil(".jstree").andSelf().show().filter("ul").each(function () {
							$(this).children("li:visible").eq(-1).addClass("jstree-last");
						});
					}).bind("clear_search.jstree", function () {
						$(this).children("ul").find("li").css("display", "").end().end().jstree("clean_node", -1);
					});
				}
			},
			defaults: {
				ajax: false,
				search_method: "jstree_contains", // for case insensitive - jstree_contains
				show_only_matches: false
			},
			_fn: {
				search: function search(str, skip_async) {
					if ($.trim(str) === "") {
						this.clear_search();return;
					}
					var s = this.get_settings().search,
					    t = this,
					    error_func = function error_func() {},
					    success_func = function success_func() {};
					this.data.search.str = str;

					if (!skip_async && s.ajax !== false && this.get_container_ul().find("li.jstree-closed:not(:has(ul)):eq(0)").length > 0) {
						this.search.supress_callback = true;
						error_func = function error_func() {};
						success_func = function success_func(d, t, x) {
							var sf = this.get_settings().search.ajax.success;
							if (sf) {
								d = sf.call(this, d, t, x) || d;
							}
							this.data.search.to_open = d;
							this._search_open();
						};
						s.ajax.context = this;
						s.ajax.error = error_func;
						s.ajax.success = success_func;
						if ($.isFunction(s.ajax.url)) {
							s.ajax.url = s.ajax.url.call(this, str);
						}
						if ($.isFunction(s.ajax.data)) {
							s.ajax.data = s.ajax.data.call(this, str);
						}
						if (!s.ajax.data) {
							s.ajax.data = { "search_string": str };
						}
						if (!s.ajax.dataType || /^json/.exec(s.ajax.dataType)) {
							s.ajax.dataType = "json";
						}
						$.ajax(s.ajax);
						return;
					}
					if (this.data.search.result.length) {
						this.clear_search();
					}
					this.data.search.result = this.get_container().find("a" + (this.data.languages ? "." + this.get_lang() : "") + ":" + s.search_method + "(" + this.data.search.str + ")");
					this.data.search.result.addClass("jstree-search").parent().parents(".jstree-closed").each(function () {
						t.open_node(this, false, true);
					});
					this.__callback({ nodes: this.data.search.result, str: str });
				},
				clear_search: function clear_search(str) {
					this.data.search.result.removeClass("jstree-search");
					this.__callback(this.data.search.result);
					this.data.search.result = $();
				},
				_search_open: function _search_open(is_callback) {
					var _this = this,
					    done = true,
					    current = [],
					    remaining = [];
					if (this.data.search.to_open.length) {
						$.each(this.data.search.to_open, function (i, val) {
							if (val == "#") {
								return true;
							}
							if ($(val).length && $(val).is(".jstree-closed")) {
								current.push(val);
							} else {
								remaining.push(val);
							}
						});
						if (current.length) {
							this.data.search.to_open = remaining;
							$.each(current, function (i, val) {
								_this.open_node(val, function () {
									_this._search_open(true);
								});
							});
							done = false;
						}
					}
					if (done) {
						this.search(this.data.search.str, true);
					}
				}
			}
		});
	})(jQuery);
	//*/

	/* 
  * jsTree contextmenu plugin
  */
	(function ($) {
		$.vakata.context = {
			hide_on_mouseleave: false,

			cnt: $("<div id='vakata-contextmenu' />"),
			vis: false,
			tgt: false,
			par: false,
			func: false,
			data: false,
			rtl: false,
			show: function show(s, t, x, y, d, p, rtl) {
				$.vakata.context.rtl = !!rtl;
				var html = $.vakata.context.parse(s),
				    h,
				    w;
				if (!html) {
					return;
				}
				$.vakata.context.vis = true;
				$.vakata.context.tgt = t;
				$.vakata.context.par = p || t || null;
				$.vakata.context.data = d || null;
				$.vakata.context.cnt.html(html).css({ "visibility": "hidden", "display": "block", "left": 0, "top": 0 });

				if ($.vakata.context.hide_on_mouseleave) {
					$.vakata.context.cnt.one("mouseleave", function (e) {
						$.vakata.context.hide();
					});
				}

				h = $.vakata.context.cnt.height();
				w = $.vakata.context.cnt.width();
				if (x + w > $(document).width()) {
					x = $(document).width() - (w + 5);
					$.vakata.context.cnt.find("li > ul").addClass("right");
				}
				if (y + h > $(document).height()) {
					y = y - (h + t[0].offsetHeight);
					$.vakata.context.cnt.find("li > ul").addClass("bottom");
				}

				$.vakata.context.cnt.css({ "left": x, "top": y }).find("li:has(ul)").bind("mouseenter", function (e) {
					var w = $(document).width(),
					    h = $(document).height(),
					    ul = $(this).children("ul").show();
					if (w !== $(document).width()) {
						ul.toggleClass("right");
					}
					if (h !== $(document).height()) {
						ul.toggleClass("bottom");
					}
				}).bind("mouseleave", function (e) {
					$(this).children("ul").hide();
				}).end().css({ "visibility": "visible" }).show();
				$(document).triggerHandler("context_show.vakata");
			},
			hide: function hide() {
				$.vakata.context.vis = false;
				$.vakata.context.cnt.attr("class", "").css({ "visibility": "hidden" });
				$(document).triggerHandler("context_hide.vakata");
			},
			parse: function parse(s, is_callback) {
				if (!s) {
					return false;
				}
				var str = "",
				    tmp = false,
				    was_sep = true;
				if (!is_callback) {
					$.vakata.context.func = {};
				}
				str += "<ul>";
				$.each(s, function (i, val) {
					if (!val) {
						return true;
					}
					$.vakata.context.func[i] = val.action;
					if (!was_sep && val.separator_before) {
						str += "<li class='vakata-separator vakata-separator-before'></li>";
					}
					was_sep = false;
					str += "<li class='" + (val._class || "") + (val._disabled ? " jstree-contextmenu-disabled " : "") + "'><ins ";
					if (val.icon && val.icon.indexOf("/") === -1) {
						str += " class='" + val.icon + "' ";
					}
					if (val.icon && val.icon.indexOf("/") !== -1) {
						str += " style='background:url(" + val.icon + ") center center no-repeat;' ";
					}
					str += ">&#160;</ins><a href='#' rel='" + i + "'>";
					if (val.submenu) {
						str += "<span style='float:" + ($.vakata.context.rtl ? "left" : "right") + ";'>&raquo;</span>";
					}
					str += val.label + "</a>";
					if (val.submenu) {
						tmp = $.vakata.context.parse(val.submenu, true);
						if (tmp) {
							str += tmp;
						}
					}
					str += "</li>";
					if (val.separator_after) {
						str += "<li class='vakata-separator vakata-separator-after'></li>";
						was_sep = true;
					}
				});
				str = str.replace(/<li class\='vakata-separator vakata-separator-after'\><\/li\>$/, "");
				str += "</ul>";
				$(document).triggerHandler("context_parse.vakata");
				return str.length > 10 ? str : false;
			},
			exec: function exec(i) {
				if ($.isFunction($.vakata.context.func[i])) {
					// if is string - eval and call it!
					$.vakata.context.func[i].call($.vakata.context.data, $.vakata.context.par);
					return true;
				} else {
					return false;
				}
			}
		};
		$(function () {
			var css_string = '' + '#vakata-contextmenu { display:block; visibility:hidden; left:0; top:-200px; position:absolute; margin:0; padding:0; min-width:180px; background:#ebebeb; border:1px solid silver; z-index:10000; *width:180px; } ' + '#vakata-contextmenu ul { min-width:180px; *width:180px; } ' + '#vakata-contextmenu ul, #vakata-contextmenu li { margin:0; padding:0; list-style-type:none; display:block; } ' + '#vakata-contextmenu li { line-height:20px; min-height:20px; position:relative; padding:0px; } ' + '#vakata-contextmenu li a { padding:1px 6px; line-height:17px; display:block; text-decoration:none; margin:1px 1px 0 1px; } ' + '#vakata-contextmenu li ins { float:left; width:16px; height:16px; text-decoration:none; margin-right:2px; } ' + '#vakata-contextmenu li a:hover, #vakata-contextmenu li.vakata-hover > a { background:gray; color:white; } ' + '#vakata-contextmenu li ul { display:none; position:absolute; top:-2px; left:100%; background:#ebebeb; border:1px solid gray; } ' + '#vakata-contextmenu .right { right:100%; left:auto; } ' + '#vakata-contextmenu .bottom { bottom:-1px; top:auto; } ' + '#vakata-contextmenu li.vakata-separator { min-height:0; height:1px; line-height:1px; font-size:1px; overflow:hidden; margin:0 2px; background:silver; /* border-top:1px solid #fefefe; */ padding:0; } ';
			$.vakata.css.add_sheet({ str: css_string, title: "vakata" });
			$.vakata.context.cnt.delegate("a", "click", function (e) {
				e.preventDefault();
			}).delegate("a", "mouseup", function (e) {
				if (!$(this).parent().hasClass("jstree-contextmenu-disabled") && $.vakata.context.exec($(this).attr("rel"))) {
					$.vakata.context.hide();
				} else {
					$(this).blur();
				}
			}).delegate("a", "mouseover", function () {
				$.vakata.context.cnt.find(".vakata-hover").removeClass("vakata-hover");
			}).appendTo("body");
			$(document).bind("mousedown", function (e) {
				if ($.vakata.context.vis && !$.contains($.vakata.context.cnt[0], e.target)) {
					$.vakata.context.hide();
				}
			});
			if (typeof $.hotkeys !== "undefined") {
				$(document).bind("keydown", "up", function (e) {
					if ($.vakata.context.vis) {
						var o = $.vakata.context.cnt.find("ul:visible").last().children(".vakata-hover").removeClass("vakata-hover").prevAll("li:not(.vakata-separator)").first();
						if (!o.length) {
							o = $.vakata.context.cnt.find("ul:visible").last().children("li:not(.vakata-separator)").last();
						}
						o.addClass("vakata-hover");
						e.stopImmediatePropagation();
						e.preventDefault();
					}
				}).bind("keydown", "down", function (e) {
					if ($.vakata.context.vis) {
						var o = $.vakata.context.cnt.find("ul:visible").last().children(".vakata-hover").removeClass("vakata-hover").nextAll("li:not(.vakata-separator)").first();
						if (!o.length) {
							o = $.vakata.context.cnt.find("ul:visible").last().children("li:not(.vakata-separator)").first();
						}
						o.addClass("vakata-hover");
						e.stopImmediatePropagation();
						e.preventDefault();
					}
				}).bind("keydown", "right", function (e) {
					if ($.vakata.context.vis) {
						$.vakata.context.cnt.find(".vakata-hover").children("ul").show().children("li:not(.vakata-separator)").removeClass("vakata-hover").first().addClass("vakata-hover");
						e.stopImmediatePropagation();
						e.preventDefault();
					}
				}).bind("keydown", "left", function (e) {
					if ($.vakata.context.vis) {
						$.vakata.context.cnt.find(".vakata-hover").children("ul").hide().children(".vakata-separator").removeClass("vakata-hover");
						e.stopImmediatePropagation();
						e.preventDefault();
					}
				}).bind("keydown", "esc", function (e) {
					$.vakata.context.hide();
					e.preventDefault();
				}).bind("keydown", "space", function (e) {
					$.vakata.context.cnt.find(".vakata-hover").last().children("a").click();
					e.preventDefault();
				});
			}
		});

		$.jstree.plugin("contextmenu", {
			__init: function __init() {
				this.get_container().delegate("a", "contextmenu.jstree", $.proxy(function (e) {
					e.preventDefault();
					if (!$(e.currentTarget).hasClass("jstree-loading")) {
						this.show_contextmenu(e.currentTarget, e.pageX, e.pageY);
					}
				}, this)).delegate("a", "click.jstree", $.proxy(function (e) {
					if (this.data.contextmenu) {
						$.vakata.context.hide();
					}
				}, this)).bind("destroy.jstree", $.proxy(function () {
					// TODO: move this to descruct method
					if (this.data.contextmenu) {
						$.vakata.context.hide();
					}
				}, this));
				$(document).bind("context_hide.vakata", $.proxy(function () {
					this.data.contextmenu = false;
				}, this));
			},
			defaults: {
				select_node: false, // requires UI plugin
				show_at_node: true,
				items: { // Could be a function that should return an object like this one
					"create": {
						"separator_before": false,
						"separator_after": true,
						"label": "Create",
						"action": function action(obj) {
							this.create(obj);
						}
					},
					"rename": {
						"separator_before": false,
						"separator_after": false,
						"label": "Rename",
						"action": function action(obj) {
							this.rename(obj);
						}
					},
					"remove": {
						"separator_before": false,
						"icon": false,
						"separator_after": false,
						"label": "Delete",
						"action": function action(obj) {
							if (this.is_selected(obj)) {
								this.remove();
							} else {
								this.remove(obj);
							}
						}
					},
					"ccp": {
						"separator_before": true,
						"icon": false,
						"separator_after": false,
						"label": "Edit",
						"action": false,
						"submenu": {
							"cut": {
								"separator_before": false,
								"separator_after": false,
								"label": "Cut",
								"action": function action(obj) {
									this.cut(obj);
								}
							},
							"copy": {
								"separator_before": false,
								"icon": false,
								"separator_after": false,
								"label": "Copy",
								"action": function action(obj) {
									this.copy(obj);
								}
							},
							"paste": {
								"separator_before": false,
								"icon": false,
								"separator_after": false,
								"label": "Paste",
								"action": function action(obj) {
									this.paste(obj);
								}
							}
						}
					}
				}
			},
			_fn: {
				show_contextmenu: function show_contextmenu(obj, x, y) {
					obj = this._get_node(obj);
					var s = this.get_settings().contextmenu,
					    a = obj.children("a:visible:eq(0)"),
					    o = false,
					    i = false;
					if (s.select_node && this.data.ui && !this.is_selected(obj)) {
						this.deselect_all();
						this.select_node(obj, true);
					}
					if (s.show_at_node || typeof x === "undefined" || typeof y === "undefined") {
						o = a.offset();
						x = o.left;
						y = o.top + this.data.core.li_height;
					}
					i = obj.data("jstree") && obj.data("jstree").contextmenu ? obj.data("jstree").contextmenu : s.items;
					if ($.isFunction(i)) {
						i = i.call(this, obj);
					}
					this.data.contextmenu = true;
					$.vakata.context.show(i, a, x, y, this, obj, this._get_settings().core.rtl);
					if (this.data.themes) {
						$.vakata.context.cnt.attr("class", "jstree-" + this.data.themes.theme + "-context");
					}
				}
			}
		});
	})(jQuery);
	//*/

	/* 
  * jsTree types plugin
  * Adds support types of nodes
  * You can set an attribute on each li node, that represents its type.
  * According to the type setting the node may get custom icon/validation rules
  */
	(function ($) {
		$.jstree.plugin("types", {
			__init: function __init() {
				var s = this._get_settings().types;
				this.data.types.attach_to = [];
				this.get_container().bind("init.jstree", $.proxy(function () {
					var types = s.types,
					    attr = s.type_attr,
					    icons_css = "",
					    _this = this;

					$.each(types, function (i, tp) {
						$.each(tp, function (k, v) {
							if (!/^(max_depth|max_children|icon|valid_children)$/.test(k)) {
								_this.data.types.attach_to.push(k);
							}
						});
						if (!tp.icon) {
							return true;
						}
						if (tp.icon.image || tp.icon.position) {
							if (i == "default") {
								icons_css += '.jstree-' + _this.get_index() + ' a > .jstree-icon { ';
							} else {
								icons_css += '.jstree-' + _this.get_index() + ' li[' + attr + '="' + i + '"] > a > .jstree-icon { ';
							}
							if (tp.icon.image) {
								icons_css += ' background-image:url(' + tp.icon.image + '); ';
							}
							if (tp.icon.position) {
								icons_css += ' background-position:' + tp.icon.position + '; ';
							} else {
								icons_css += ' background-position:0 0; ';
							}
							icons_css += '} ';
						}
					});
					if (icons_css !== "") {
						$.vakata.css.add_sheet({ 'str': icons_css, title: "jstree-types" });
					}
				}, this)).bind("before.jstree", $.proxy(function (e, data) {
					var s,
					    t,
					    o = this._get_settings().types.use_data ? this._get_node(data.args[0]) : false,
					    d = o && o !== -1 && o.length ? o.data("jstree") : false;
					if (d && d.types && d.types[data.func] === false) {
						e.stopImmediatePropagation();return false;
					}
					if ($.inArray(data.func, this.data.types.attach_to) !== -1) {
						if (!data.args[0] || !data.args[0].tagName && !data.args[0].jquery) {
							return;
						}
						s = this._get_settings().types.types;
						t = this._get_type(data.args[0]);
						if ((s[t] && typeof s[t][data.func] !== "undefined" || s["default"] && typeof s["default"][data.func] !== "undefined") && this._check(data.func, data.args[0]) === false) {
							e.stopImmediatePropagation();
							return false;
						}
					}
				}, this));
				if (is_ie6) {
					this.get_container().bind("load_node.jstree set_type.jstree", $.proxy(function (e, data) {
						var r = data && data.rslt && data.rslt.obj && data.rslt.obj !== -1 ? this._get_node(data.rslt.obj).parent() : this.get_container_ul(),
						    c = false,
						    s = this._get_settings().types;
						$.each(s.types, function (i, tp) {
							if (tp.icon && (tp.icon.image || tp.icon.position)) {
								c = i === "default" ? r.find("li > a > .jstree-icon") : r.find("li[" + s.type_attr + "='" + i + "'] > a > .jstree-icon");
								if (tp.icon.image) {
									c.css("backgroundImage", "url(" + tp.icon.image + ")");
								}
								c.css("backgroundPosition", tp.icon.position || "0 0");
							}
						});
					}, this));
				}
			},
			defaults: {
				// defines maximum number of root nodes (-1 means unlimited, -2 means disable max_children checking)
				max_children: -1,
				// defines the maximum depth of the tree (-1 means unlimited, -2 means disable max_depth checking)
				max_depth: -1,
				// defines valid node types for the root nodes
				valid_children: "all",

				// whether to use $.data
				use_data: false,
				// where is the type stores (the rel attribute of the LI element)
				type_attr: "rel",
				// a list of types
				types: {
					// the default type
					"default": {
						"max_children": -1,
						"max_depth": -1,
						"valid_children": "all"

						// Bound functions - you can bind any other function here (using boolean or function)
						//"select_node"	: true
					}
				}
			},
			_fn: {
				_types_notify: function _types_notify(n, data) {
					if (data.type && this._get_settings().types.use_data) {
						this.set_type(data.type, n);
					}
				},
				_get_type: function _get_type(obj) {
					obj = this._get_node(obj);
					return !obj || !obj.length ? false : obj.attr(this._get_settings().types.type_attr) || "default";
				},
				set_type: function set_type(str, obj) {
					obj = this._get_node(obj);
					var ret = !obj.length || !str ? false : obj.attr(this._get_settings().types.type_attr, str);
					if (ret) {
						this.__callback({ obj: obj, type: str });
					}
					return ret;
				},
				_check: function _check(rule, obj, opts) {
					obj = this._get_node(obj);
					var v = false,
					    t = this._get_type(obj),
					    d = 0,
					    _this = this,
					    s = this._get_settings().types,
					    data = false;
					if (obj === -1) {
						if (!!s[rule]) {
							v = s[rule];
						} else {
							return;
						}
					} else {
						if (t === false) {
							return;
						}
						data = s.use_data ? obj.data("jstree") : false;
						if (data && data.types && typeof data.types[rule] !== "undefined") {
							v = data.types[rule];
						} else if (!!s.types[t] && typeof s.types[t][rule] !== "undefined") {
							v = s.types[t][rule];
						} else if (!!s.types["default"] && typeof s.types["default"][rule] !== "undefined") {
							v = s.types["default"][rule];
						}
					}
					if ($.isFunction(v)) {
						v = v.call(this, obj);
					}
					if (rule === "max_depth" && obj !== -1 && opts !== false && s.max_depth !== -2 && v !== 0) {
						// also include the node itself - otherwise if root node it is not checked
						obj.children("a:eq(0)").parentsUntil(".jstree", "li").each(function (i) {
							// check if current depth already exceeds global tree depth
							if (s.max_depth !== -1 && s.max_depth - (i + 1) <= 0) {
								v = 0;return false;
							}
							d = i === 0 ? v : _this._check(rule, this, false);
							// check if current node max depth is already matched or exceeded
							if (d !== -1 && d - (i + 1) <= 0) {
								v = 0;return false;
							}
							// otherwise - set the max depth to the current value minus current depth
							if (d >= 0 && (d - (i + 1) < v || v < 0)) {
								v = d - (i + 1);
							}
							// if the global tree depth exists and it minus the nodes calculated so far is less than `v` or `v` is unlimited
							if (s.max_depth >= 0 && (s.max_depth - (i + 1) < v || v < 0)) {
								v = s.max_depth - (i + 1);
							}
						});
					}
					return v;
				},
				check_move: function check_move() {
					if (!this.__call_old()) {
						return false;
					}
					var m = this._get_move(),
					    s = m.rt._get_settings().types,
					    mc = m.rt._check("max_children", m.cr),
					    md = m.rt._check("max_depth", m.cr),
					    vc = m.rt._check("valid_children", m.cr),
					    ch = 0,
					    d = 1,
					    t;

					if (vc === "none") {
						return false;
					}
					if ($.isArray(vc) && m.ot && m.ot._get_type) {
						m.o.each(function () {
							if ($.inArray(m.ot._get_type(this), vc) === -1) {
								d = false;return false;
							}
						});
						if (d === false) {
							return false;
						}
					}
					if (s.max_children !== -2 && mc !== -1) {
						ch = m.cr === -1 ? this.get_container().find("> ul > li").not(m.o).length : m.cr.find("> ul > li").not(m.o).length;
						if (ch + m.o.length > mc) {
							return false;
						}
					}
					if (s.max_depth !== -2 && md !== -1) {
						d = 0;
						if (md === 0) {
							return false;
						}
						if (typeof m.o.d === "undefined") {
							// TODO: deal with progressive rendering and async when checking max_depth (how to know the depth of the moved node)
							t = m.o;
							while (t.length > 0) {
								t = t.find("> ul > li");
								d++;
							}
							m.o.d = d;
						}
						if (md - m.o.d < 0) {
							return false;
						}
					}
					return true;
				},
				create_node: function create_node(obj, position, js, callback, is_loaded, skip_check) {
					if (!skip_check && (is_loaded || this._is_loaded(obj))) {
						var p = typeof position == "string" && position.match(/^before|after$/i) && obj !== -1 ? this._get_parent(obj) : this._get_node(obj),
						    s = this._get_settings().types,
						    mc = this._check("max_children", p),
						    md = this._check("max_depth", p),
						    vc = this._check("valid_children", p),
						    ch;
						if (typeof js === "string") {
							js = { data: js };
						}
						if (!js) {
							js = {};
						}
						if (vc === "none") {
							return false;
						}
						if ($.isArray(vc)) {
							if (!js.attr || !js.attr[s.type_attr]) {
								if (!js.attr) {
									js.attr = {};
								}
								js.attr[s.type_attr] = vc[0];
							} else {
								if ($.inArray(js.attr[s.type_attr], vc) === -1) {
									return false;
								}
							}
						}
						if (s.max_children !== -2 && mc !== -1) {
							ch = p === -1 ? this.get_container().find("> ul > li").length : p.find("> ul > li").length;
							if (ch + 1 > mc) {
								return false;
							}
						}
						if (s.max_depth !== -2 && md !== -1 && md - 1 < 0) {
							return false;
						}
					}
					return this.__call_old(true, obj, position, js, callback, is_loaded, skip_check);
				}
			}
		});
	})(jQuery);
	//*/

	/* 
  * jsTree HTML plugin
  * The HTML data store. Datastores are build by replacing the `load_node` and `_is_loaded` functions.
  */
	(function ($) {
		$.jstree.plugin("html_data", {
			__init: function __init() {
				// this used to use html() and clean the whitespace, but this way any attached data was lost
				this.data.html_data.original_container_html = this.get_container().find(" > ul > li").clone(true);
				// remove white space from LI node - otherwise nodes appear a bit to the right
				this.data.html_data.original_container_html.find("li").andSelf().contents().filter(function () {
					return this.nodeType == 3;
				}).remove();
			},
			defaults: {
				data: false,
				ajax: false,
				correct_state: true
			},
			_fn: {
				load_node: function load_node(obj, s_call, e_call) {
					var _this = this;this.load_node_html(obj, function () {
						_this.__callback({ "obj": _this._get_node(obj) });s_call.call(this);
					}, e_call);
				},
				_is_loaded: function _is_loaded(obj) {
					obj = this._get_node(obj);
					return obj == -1 || !obj || !this._get_settings().html_data.ajax && !$.isFunction(this._get_settings().html_data.data) || obj.is(".jstree-open, .jstree-leaf") || obj.children("ul").children("li").size() > 0;
				},
				load_node_html: function load_node_html(obj, s_call, e_call) {
					var d,
					    s = this.get_settings().html_data,
					    error_func = function error_func() {},
					    success_func = function success_func() {};
					obj = this._get_node(obj);
					if (obj && obj !== -1) {
						if (obj.data("jstree_is_loading")) {
							return;
						} else {
							obj.data("jstree_is_loading", true);
						}
					}
					switch (!0) {
						case $.isFunction(s.data):
							s.data.call(this, obj, $.proxy(function (d) {
								if (d && d !== "" && d.toString && d.toString().replace(/^[\s\n]+$/, "") !== "") {
									d = $(d);
									if (!d.is("ul")) {
										d = $("<ul />").append(d);
									}
									if (obj == -1 || !obj) {
										this.get_container().children("ul").empty().append(d.children()).find("li, a").filter(function () {
											return !this.firstChild || !this.firstChild.tagName || this.firstChild.tagName !== "INS";
										}).prepend("<ins class='jstree-icon'>&#160;</ins>").end().filter("a").children("ins:first-child").not(".jstree-icon").addClass("jstree-icon");
									} else {
										obj.children("a.jstree-loading").removeClass("jstree-loading");obj.append(d).children("ul").find("li, a").filter(function () {
											return !this.firstChild || !this.firstChild.tagName || this.firstChild.tagName !== "INS";
										}).prepend("<ins class='jstree-icon'>&#160;</ins>").end().filter("a").children("ins:first-child").not(".jstree-icon").addClass("jstree-icon");obj.removeData("jstree_is_loading");
									}
									this.clean_node(obj);
									if (s_call) {
										s_call.call(this);
									}
								} else {
									if (obj && obj !== -1) {
										obj.children("a.jstree-loading").removeClass("jstree-loading");
										obj.removeData("jstree_is_loading");
										if (s.correct_state) {
											this.correct_state(obj);
											if (s_call) {
												s_call.call(this);
											}
										}
									} else {
										if (s.correct_state) {
											this.get_container().children("ul").empty();
											if (s_call) {
												s_call.call(this);
											}
										}
									}
								}
							}, this));
							break;
						case !s.data && !s.ajax:
							if (!obj || obj == -1) {
								this.get_container().children("ul").empty().append(this.data.html_data.original_container_html).find("li, a").filter(function () {
									return !this.firstChild || !this.firstChild.tagName || this.firstChild.tagName !== "INS";
								}).prepend("<ins class='jstree-icon'>&#160;</ins>").end().filter("a").children("ins:first-child").not(".jstree-icon").addClass("jstree-icon");
								this.clean_node();
							}
							if (s_call) {
								s_call.call(this);
							}
							break;
						case !!s.data && !s.ajax || !!s.data && !!s.ajax && (!obj || obj === -1):
							if (!obj || obj == -1) {
								d = $(s.data);
								if (!d.is("ul")) {
									d = $("<ul />").append(d);
								}
								this.get_container().children("ul").empty().append(d.children()).find("li, a").filter(function () {
									return !this.firstChild || !this.firstChild.tagName || this.firstChild.tagName !== "INS";
								}).prepend("<ins class='jstree-icon'>&#160;</ins>").end().filter("a").children("ins:first-child").not(".jstree-icon").addClass("jstree-icon");
								this.clean_node();
							}
							if (s_call) {
								s_call.call(this);
							}
							break;
						case !s.data && !!s.ajax || !!s.data && !!s.ajax && obj && obj !== -1:
							obj = this._get_node(obj);
							error_func = function error_func(x, t, e) {
								var ef = this.get_settings().html_data.ajax.error;
								if (ef) {
									ef.call(this, x, t, e);
								}
								if (obj != -1 && obj.length) {
									obj.children("a.jstree-loading").removeClass("jstree-loading");
									obj.removeData("jstree_is_loading");
									if (t === "success" && s.correct_state) {
										this.correct_state(obj);
									}
								} else {
									if (t === "success" && s.correct_state) {
										this.get_container().children("ul").empty();
									}
								}
								if (e_call) {
									e_call.call(this);
								}
							};
							success_func = function success_func(d, t, x) {
								var sf = this.get_settings().html_data.ajax.success;
								if (sf) {
									d = sf.call(this, d, t, x) || d;
								}
								if (d === "" || d && d.toString && d.toString().replace(/^[\s\n]+$/, "") === "") {
									return error_func.call(this, x, t, "");
								}
								if (d) {
									d = $(d);
									if (!d.is("ul")) {
										d = $("<ul />").append(d);
									}
									if (obj == -1 || !obj) {
										this.get_container().children("ul").empty().append(d.children()).find("li, a").filter(function () {
											return !this.firstChild || !this.firstChild.tagName || this.firstChild.tagName !== "INS";
										}).prepend("<ins class='jstree-icon'>&#160;</ins>").end().filter("a").children("ins:first-child").not(".jstree-icon").addClass("jstree-icon");
									} else {
										obj.children("a.jstree-loading").removeClass("jstree-loading");obj.append(d).children("ul").find("li, a").filter(function () {
											return !this.firstChild || !this.firstChild.tagName || this.firstChild.tagName !== "INS";
										}).prepend("<ins class='jstree-icon'>&#160;</ins>").end().filter("a").children("ins:first-child").not(".jstree-icon").addClass("jstree-icon");obj.removeData("jstree_is_loading");
									}
									this.clean_node(obj);
									if (s_call) {
										s_call.call(this);
									}
								} else {
									if (obj && obj !== -1) {
										obj.children("a.jstree-loading").removeClass("jstree-loading");
										obj.removeData("jstree_is_loading");
										if (s.correct_state) {
											this.correct_state(obj);
											if (s_call) {
												s_call.call(this);
											}
										}
									} else {
										if (s.correct_state) {
											this.get_container().children("ul").empty();
											if (s_call) {
												s_call.call(this);
											}
										}
									}
								}
							};
							s.ajax.context = this;
							s.ajax.error = error_func;
							s.ajax.success = success_func;
							if (!s.ajax.dataType) {
								s.ajax.dataType = "html";
							}
							if ($.isFunction(s.ajax.url)) {
								s.ajax.url = s.ajax.url.call(this, obj);
							}
							if ($.isFunction(s.ajax.data)) {
								s.ajax.data = s.ajax.data.call(this, obj);
							}
							$.ajax(s.ajax);
							break;
					}
				}
			}
		});
		// include the HTML data plugin by default
		$.jstree.defaults.plugins.push("html_data");
	})(jQuery);
	//*/

	/* 
  * jsTree themeroller plugin
  * Adds support for jQuery UI themes. Include this at the end of your plugins list, also make sure "themes" is not included.
  */
	(function ($) {
		$.jstree.plugin("themeroller", {
			__init: function __init() {
				var s = this._get_settings().themeroller;
				this.get_container().addClass("ui-widget-content").addClass("jstree-themeroller").delegate("a", "mouseenter.jstree", function (e) {
					if (!$(e.currentTarget).hasClass("jstree-loading")) {
						$(this).addClass(s.item_h);
					}
				}).delegate("a", "mouseleave.jstree", function () {
					$(this).removeClass(s.item_h);
				}).bind("init.jstree", $.proxy(function (e, data) {
					data.inst.get_container().find("> ul > li > .jstree-loading > ins").addClass("ui-icon-refresh");
					this._themeroller(data.inst.get_container().find("> ul > li"));
				}, this)).bind("open_node.jstree create_node.jstree", $.proxy(function (e, data) {
					this._themeroller(data.rslt.obj);
				}, this)).bind("loaded.jstree refresh.jstree", $.proxy(function (e) {
					this._themeroller();
				}, this)).bind("close_node.jstree", $.proxy(function (e, data) {
					this._themeroller(data.rslt.obj);
				}, this)).bind("delete_node.jstree", $.proxy(function (e, data) {
					this._themeroller(data.rslt.parent);
				}, this)).bind("correct_state.jstree", $.proxy(function (e, data) {
					data.rslt.obj.children("ins.jstree-icon").removeClass(s.opened + " " + s.closed + " ui-icon").end().find("> a > ins.ui-icon").filter(function () {
						return this.className.toString().replace(s.item_clsd, "").replace(s.item_open, "").replace(s.item_leaf, "").indexOf("ui-icon-") === -1;
					}).removeClass(s.item_open + " " + s.item_clsd).addClass(s.item_leaf || "jstree-no-icon");
				}, this)).bind("select_node.jstree", $.proxy(function (e, data) {
					data.rslt.obj.children("a").addClass(s.item_a);
				}, this)).bind("deselect_node.jstree deselect_all.jstree", $.proxy(function (e, data) {
					this.get_container().find("a." + s.item_a).removeClass(s.item_a).end().find("a.jstree-clicked").addClass(s.item_a);
				}, this)).bind("dehover_node.jstree", $.proxy(function (e, data) {
					data.rslt.obj.children("a").removeClass(s.item_h);
				}, this)).bind("hover_node.jstree", $.proxy(function (e, data) {
					this.get_container().find("a." + s.item_h).not(data.rslt.obj).removeClass(s.item_h);
					data.rslt.obj.children("a").addClass(s.item_h);
				}, this)).bind("move_node.jstree", $.proxy(function (e, data) {
					this._themeroller(data.rslt.o);
					this._themeroller(data.rslt.op);
				}, this));
			},
			__destroy: function __destroy() {
				var s = this._get_settings().themeroller,
				    c = ["ui-icon"];
				$.each(s, function (i, v) {
					v = v.split(" ");
					if (v.length) {
						c = c.concat(v);
					}
				});
				this.get_container().removeClass("ui-widget-content").find("." + c.join(", .")).removeClass(c.join(" "));
			},
			_fn: {
				_themeroller: function _themeroller(obj) {
					var s = this._get_settings().themeroller;
					obj = !obj || obj == -1 ? this.get_container_ul() : this._get_node(obj);
					obj = !obj || obj == -1 ? this.get_container_ul() : obj.parent();
					obj.find("li.jstree-closed").children("ins.jstree-icon").removeClass(s.opened).addClass("ui-icon " + s.closed).end().children("a").addClass(s.item).children("ins.jstree-icon").addClass("ui-icon").filter(function () {
						return this.className.toString().replace(s.item_clsd, "").replace(s.item_open, "").replace(s.item_leaf, "").indexOf("ui-icon-") === -1;
					}).removeClass(s.item_leaf + " " + s.item_open).addClass(s.item_clsd || "jstree-no-icon").end().end().end().end().find("li.jstree-open").children("ins.jstree-icon").removeClass(s.closed).addClass("ui-icon " + s.opened).end().children("a").addClass(s.item).children("ins.jstree-icon").addClass("ui-icon").filter(function () {
						return this.className.toString().replace(s.item_clsd, "").replace(s.item_open, "").replace(s.item_leaf, "").indexOf("ui-icon-") === -1;
					}).removeClass(s.item_leaf + " " + s.item_clsd).addClass(s.item_open || "jstree-no-icon").end().end().end().end().find("li.jstree-leaf").children("ins.jstree-icon").removeClass(s.closed + " ui-icon " + s.opened).end().children("a").addClass(s.item).children("ins.jstree-icon").addClass("ui-icon").filter(function () {
						return this.className.toString().replace(s.item_clsd, "").replace(s.item_open, "").replace(s.item_leaf, "").indexOf("ui-icon-") === -1;
					}).removeClass(s.item_clsd + " " + s.item_open).addClass(s.item_leaf || "jstree-no-icon");
				}
			},
			defaults: {
				"opened": "ui-icon-triangle-1-se",
				"closed": "ui-icon-triangle-1-e",
				"item": "ui-state-default",
				"item_h": "ui-state-hover",
				"item_a": "ui-state-active",
				"item_open": "ui-icon-folder-open",
				"item_clsd": "ui-icon-folder-collapsed",
				"item_leaf": "ui-icon-document"
			}
		});
		$(function () {
			var css_string = '' + '.jstree-themeroller .ui-icon { overflow:visible; } ' + '.jstree-themeroller a { padding:0 2px; } ' + '.jstree-themeroller .jstree-no-icon { display:none; }';
			$.vakata.css.add_sheet({ str: css_string, title: "jstree" });
		});
	})(jQuery);
	//*/

	/* 
  * jsTree unique plugin
  * Forces different names amongst siblings (still a bit experimental)
  * NOTE: does not check language versions (it will not be possible to have nodes with the same title, even in different languages)
  */
	(function ($) {
		$.jstree.plugin("unique", {
			__init: function __init() {
				this.get_container().bind("before.jstree", $.proxy(function (e, data) {
					var nms = [],
					    res = true,
					    p,
					    t;
					if (data.func == "move_node") {
						// obj, ref, position, is_copy, is_prepared, skip_check
						if (data.args[4] === true) {
							if (data.args[0].o && data.args[0].o.length) {
								data.args[0].o.children("a").each(function () {
									nms.push($(this).text().replace(/^\s+/g, ""));
								});
								res = this._check_unique(nms, data.args[0].np.find("> ul > li").not(data.args[0].o), "move_node");
							}
						}
					}
					if (data.func == "create_node") {
						// obj, position, js, callback, is_loaded
						if (data.args[4] || this._is_loaded(data.args[0])) {
							p = this._get_node(data.args[0]);
							if (data.args[1] && (data.args[1] === "before" || data.args[1] === "after")) {
								p = this._get_parent(data.args[0]);
								if (!p || p === -1) {
									p = this.get_container();
								}
							}
							if (typeof data.args[2] === "string") {
								nms.push(data.args[2]);
							} else if (!data.args[2] || !data.args[2].data) {
								nms.push(this._get_string("new_node"));
							} else {
								nms.push(data.args[2].data);
							}
							res = this._check_unique(nms, p.find("> ul > li"), "create_node");
						}
					}
					if (data.func == "rename_node") {
						// obj, val
						nms.push(data.args[1]);
						t = this._get_node(data.args[0]);
						p = this._get_parent(t);
						if (!p || p === -1) {
							p = this.get_container();
						}
						res = this._check_unique(nms, p.find("> ul > li").not(t), "rename_node");
					}
					if (!res) {
						e.stopPropagation();
						return false;
					}
				}, this));
			},
			defaults: {
				error_callback: $.noop
			},
			_fn: {
				_check_unique: function _check_unique(nms, p, func) {
					var cnms = [],
					    ok = true;
					p.children("a").each(function () {
						cnms.push($(this).text().replace(/^\s+/g, ""));
					});
					if (!cnms.length || !nms.length) {
						return true;
					}
					$.each(nms, function (i, v) {
						if ($.inArray(v, cnms) !== -1) {
							ok = false;
							return false;
						}
					});
					if (!ok) {
						this._get_settings().unique.error_callback.call(null, nms, p, func);
					}
					return ok;
				},
				check_move: function check_move() {
					if (!this.__call_old()) {
						return false;
					}
					var p = this._get_move(),
					    nms = [];
					if (p.o && p.o.length) {
						p.o.children("a").each(function () {
							nms.push($(this).text().replace(/^\s+/g, ""));
						});
						return this._check_unique(nms, p.np.find("> ul > li").not(p.o), "check_move");
					}
					return true;
				}
			}
		});
	})(jQuery);
	//*/

	/*
  * jsTree wholerow plugin
  * Makes select and hover work on the entire width of the node
  * MAY BE HEAVY IN LARGE DOM
  */
	(function ($) {
		$.jstree.plugin("wholerow", {
			__init: function __init() {
				if (!this.data.ui) {
					throw "jsTree wholerow: jsTree UI plugin not included.";
				}
				this.data.wholerow.html = false;
				this.data.wholerow.to = false;
				this.get_container().bind("init.jstree", $.proxy(function (e, data) {
					this._get_settings().core.animation = 0;
				}, this)).bind("open_node.jstree create_node.jstree clean_node.jstree loaded.jstree", $.proxy(function (e, data) {
					this._prepare_wholerow_span(data && data.rslt && data.rslt.obj ? data.rslt.obj : -1);
				}, this)).bind("search.jstree clear_search.jstree reopen.jstree after_open.jstree after_close.jstree create_node.jstree delete_node.jstree clean_node.jstree", $.proxy(function (e, data) {
					if (this.data.to) {
						clearTimeout(this.data.to);
					}
					this.data.to = setTimeout(function (t, o) {
						return function () {
							t._prepare_wholerow_ul(o);
						};
					}(this, data && data.rslt && data.rslt.obj ? data.rslt.obj : -1), 0);
				}, this)).bind("deselect_all.jstree", $.proxy(function (e, data) {
					this.get_container().find(" > .jstree-wholerow .jstree-clicked").removeClass("jstree-clicked " + (this.data.themeroller ? this._get_settings().themeroller.item_a : ""));
				}, this)).bind("select_node.jstree deselect_node.jstree ", $.proxy(function (e, data) {
					data.rslt.obj.each(function () {
						var ref = data.inst.get_container().find(" > .jstree-wholerow li:visible:eq(" + parseInt(($(this).offset().top - data.inst.get_container().offset().top + data.inst.get_container()[0].scrollTop) / data.inst.data.core.li_height, 10) + ")");
						// ref.children("a")[e.type === "select_node" ? "addClass" : "removeClass"]("jstree-clicked");
						ref.children("a").attr("class", data.rslt.obj.children("a").attr("class"));
					});
				}, this)).bind("hover_node.jstree dehover_node.jstree", $.proxy(function (e, data) {
					this.get_container().find(" > .jstree-wholerow .jstree-hovered").removeClass("jstree-hovered " + (this.data.themeroller ? this._get_settings().themeroller.item_h : ""));
					if (e.type === "hover_node") {
						var ref = this.get_container().find(" > .jstree-wholerow li:visible:eq(" + parseInt((data.rslt.obj.offset().top - this.get_container().offset().top + this.get_container()[0].scrollTop) / this.data.core.li_height, 10) + ")");
						// ref.children("a").addClass("jstree-hovered");
						ref.children("a").attr("class", data.rslt.obj.children(".jstree-hovered").attr("class"));
					}
				}, this)).delegate(".jstree-wholerow-span, ins.jstree-icon, li", "click.jstree", function (e) {
					var n = $(e.currentTarget);
					if (e.target.tagName === "A" || e.target.tagName === "INS" && n.closest("li").is(".jstree-open, .jstree-closed")) {
						return;
					}
					n.closest("li").children("a:visible:eq(0)").click();
					e.stopImmediatePropagation();
				}).delegate("li", "mouseover.jstree", $.proxy(function (e) {
					e.stopImmediatePropagation();
					if ($(e.currentTarget).children(".jstree-hovered, .jstree-clicked").length) {
						return false;
					}
					this.hover_node(e.currentTarget);
					return false;
				}, this)).delegate("li", "mouseleave.jstree", $.proxy(function (e) {
					if ($(e.currentTarget).children("a").hasClass("jstree-hovered").length) {
						return;
					}
					this.dehover_node(e.currentTarget);
				}, this));
				if (is_ie7 || is_ie6) {
					$.vakata.css.add_sheet({ str: ".jstree-" + this.get_index() + " { position:relative; } ", title: "jstree" });
				}
			},
			defaults: {},
			__destroy: function __destroy() {
				this.get_container().children(".jstree-wholerow").remove();
				this.get_container().find(".jstree-wholerow-span").remove();
			},
			_fn: {
				_prepare_wholerow_span: function _prepare_wholerow_span(obj) {
					obj = !obj || obj == -1 ? this.get_container().find("> ul > li") : this._get_node(obj);
					if (obj === false) {
						return;
					} // added for removing root nodes
					obj.each(function () {
						$(this).find("li").andSelf().each(function () {
							var $t = $(this);
							if ($t.children(".jstree-wholerow-span").length) {
								return true;
							}
							$t.prepend("<span class='jstree-wholerow-span' style='width:" + $t.parentsUntil(".jstree", "li").length * 18 + "px;'>&#160;</span>");
						});
					});
				},
				_prepare_wholerow_ul: function _prepare_wholerow_ul() {
					var o = this.get_container().children("ul").eq(0),
					    h = o.html();
					o.addClass("jstree-wholerow-real");
					if (this.data.wholerow.last_html !== h) {
						this.data.wholerow.last_html = h;
						this.get_container().children(".jstree-wholerow").remove();
						this.get_container().append(o.clone().removeClass("jstree-wholerow-real").wrapAll("<div class='jstree-wholerow' />").parent().width(o.parent()[0].scrollWidth).css("top", (o.height() + (is_ie7 ? 5 : 0)) * -1).find("li[id]").each(function () {
							this.removeAttribute("id");
						}).end());
					}
				}
			}
		});
		$(function () {
			var css_string = '' + '.jstree .jstree-wholerow-real { position:relative; z-index:1; } ' + '.jstree .jstree-wholerow-real li { cursor:pointer; } ' + '.jstree .jstree-wholerow-real a { border-left-color:transparent !important; border-right-color:transparent !important; } ' + '.jstree .jstree-wholerow { position:relative; z-index:0; height:0; } ' + '.jstree .jstree-wholerow ul, .jstree .jstree-wholerow li { width:100%; } ' + '.jstree .jstree-wholerow, .jstree .jstree-wholerow ul, .jstree .jstree-wholerow li, .jstree .jstree-wholerow a { margin:0 !important; padding:0 !important; } ' + '.jstree .jstree-wholerow, .jstree .jstree-wholerow ul, .jstree .jstree-wholerow li { background:transparent !important; }' + '.jstree .jstree-wholerow ins, .jstree .jstree-wholerow span, .jstree .jstree-wholerow input { display:none !important; }' + '.jstree .jstree-wholerow a, .jstree .jstree-wholerow a:hover { text-indent:-9999px; !important; width:100%; padding:0 !important; border-right-width:0px !important; border-left-width:0px !important; } ' + '.jstree .jstree-wholerow-span { position:absolute; left:0; margin:0px; padding:0; height:18px; border-width:0; padding:0; z-index:0; }';
			if (is_ff2) {
				css_string += '' + '.jstree .jstree-wholerow a { display:block; height:18px; margin:0; padding:0; border:0; } ' + '.jstree .jstree-wholerow-real a { border-color:transparent !important; } ';
			}
			if (is_ie7 || is_ie6) {
				css_string += '' + '.jstree .jstree-wholerow, .jstree .jstree-wholerow li, .jstree .jstree-wholerow ul, .jstree .jstree-wholerow a { margin:0; padding:0; line-height:18px; } ' + '.jstree .jstree-wholerow a { display:block; height:18px; line-height:18px; overflow:hidden; } ';
			}
			$.vakata.css.add_sheet({ str: css_string, title: "jstree" });
		});
	})(jQuery);
	//*/

	/*
 * jsTree model plugin
 * This plugin gets jstree to use a class model to retrieve data, creating great dynamism
 */
	(function ($) {
		var nodeInterface = ["getChildren", "getChildrenCount", "getAttr", "getName", "getProps"],
		    validateInterface = function validateInterface(obj, inter) {
			var valid = true;
			obj = obj || {};
			inter = [].concat(inter);
			$.each(inter, function (i, v) {
				if (!$.isFunction(obj[v])) {
					valid = false;return false;
				}
			});
			return valid;
		};
		$.jstree.plugin("model", {
			__init: function __init() {
				if (!this.data.json_data) {
					throw "jsTree model: jsTree json_data plugin not included.";
				}
				this._get_settings().json_data.data = function (n, b) {
					var obj = n == -1 ? this._get_settings().model.object : n.data("jstree_model");
					if (!validateInterface(obj, nodeInterface)) {
						return b.call(null, false);
					}
					if (this._get_settings().model.async) {
						obj.getChildren($.proxy(function (data) {
							this.model_done(data, b);
						}, this));
					} else {
						this.model_done(obj.getChildren(), b);
					}
				};
			},
			defaults: {
				object: false,
				id_prefix: false,
				async: false
			},
			_fn: {
				model_done: function model_done(data, callback) {
					var ret = [],
					    s = this._get_settings(),
					    _this = this;

					if (!$.isArray(data)) {
						data = [data];
					}
					$.each(data, function (i, nd) {
						var r = nd.getProps() || {};
						r.attr = nd.getAttr() || {};
						if (nd.getChildrenCount()) {
							r.state = "closed";
						}
						r.data = nd.getName();
						if (!$.isArray(r.data)) {
							r.data = [r.data];
						}
						if (_this.data.types && $.isFunction(nd.getType)) {
							r.attr[s.types.type_attr] = nd.getType();
						}
						if (r.attr.id && s.model.id_prefix) {
							r.attr.id = s.model.id_prefix + r.attr.id;
						}
						if (!r.metadata) {
							r.metadata = {};
						}
						r.metadata.jstree_model = nd;
						ret.push(r);
					});
					callback.call(null, ret);
				}
			}
		});
	})(jQuery);
	//*/
})();
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))

/***/ }),
/* 200 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function(jQuery) {/*
	xBreadcrumbs (Extended Breadcrums) jQuery Plugin
	(c) 2009 ajaxBlender.com
	For any questions please visit www.ajaxblender.com 
	or email us at support@ajaxblender.com
*/

;(function ($) {
	/*  Variables  */
	$.fn.xBreadcrumbs = function (settings) {
		var element = $(this);
		var settings = $.extend({}, $.fn.xBreadcrumbs.defaults, settings);

		function _build() {
			if (settings.collapsible) {
				var sz = element.children('LI').length;
				element.children('LI').children('A').css('white-space', 'nowrap').css('float', 'left');
				element.children('LI').children('A').each(function (i, el) {
					if (i != sz - 1) {
						$(this).css('overflow', 'hidden');
						$(this).attr('init-width', $(this).width());
						$(this).width(settings.collapsedWidth);
					}
				});
			}

			element.children('LI').mouseenter(function () {
				if ($(this).hasClass('hover')) {
					return;
				}

				_hideAllSubLevels();
				if (!_subLevelExists($(this))) {
					return;
				}

				// Show sub-level
				var subLevel = $(this).children('UL');
				_showHideSubLevel(subLevel, true);

				if (settings.collapsible && !$(this).hasClass('current')) {
					var initWidth = $(this).children('A').attr('init-width');
					$(this).children('A').animate({ width: initWidth }, 'normal');
				}
			});

			element.children('LI').mouseleave(function () {
				var subLevel = $(this).children('UL');
				_showHideSubLevel(subLevel, false);

				if (settings.collapsible && !$(this).hasClass('current')) {
					$(this).children('A').animate({ width: settings.collapsedWidth }, 'fast');
				}
			});
		};

		function _hideAllSubLevels() {
			element.children('LI').children('UL').each(function () {
				$(this).hide();
				$(this).parent().removeClass('hover');
			});
		};

		function _showHideSubLevel(subLevel, isShow) {
			if (isShow) {
				subLevel.parent().addClass('hover');
				if ($.browser.msie) {
					var pos = subLevel.parent().position();
					subLevel.css('left', parseInt(pos['left']));
				}
				if (settings.showSpeed != '') {
					subLevel.fadeIn(settings.showSpeed);
				} else {
					subLevel.show();
				}
			} else {
				subLevel.parent().removeClass('hover');
				if (settings.hideSpeed != '') {
					subLevel.fadeOut(settings.hideSpeed);
				} else {
					subLevel.hide();
				}
			}
		};

		function _subLevelExists(obj) {
			return obj.children('UL').length > 0;
		};

		//    Entry point
		_build();
	};

	/*  Default Settings  */
	$.fn.xBreadcrumbs.defaults = {
		showSpeed: 'fast',
		hideSpeed: '',
		collapsible: false,
		collapsedWidth: 10
	};
})(jQuery);
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))

/***/ }),
/* 201 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;var _typeof = typeof Symbol === "function" && typeof Symbol.iterator === "symbol" ? function (obj) { return typeof obj; } : function (obj) { return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj; };

/**
  * Genera los botones del datatable
  *
  * @summary 		Extensión del componente RUP Datatable
  * @module			"rup.table.buttons"
  * @version     1.5.1
  * @license
  * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
  * Solo podrá usarse esta obra si se respeta la Licencia.
  * Puede obtenerse una copia de la Licencia en
  *
  *      http://ec.europa.eu/idabc/eupl.html
  *
  * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
  * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
  * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
  * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
  * que establece la Licencia.
  * @copyright   Copyright 2018 E.J.I.E., S.A.
  *
  */

(function (factory) {
	if (true) {
		// AMD
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(4)], __WEBPACK_AMD_DEFINE_RESULT__ = function ($) {
			return factory($, window, document);
		}.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else if ((typeof exports === 'undefined' ? 'undefined' : _typeof(exports)) === 'object') {
		// CommonJS
		module.exports = function (root, $) {
			if (!root) {
				root = window;
			}

			if (!$ || !$.fn.dataTable) {
				$ = require('datatables.net')(root, $).$;
			}

			return factory($, root, root.document);
		};
	} else {
		// Browser
		factory(jQuery, window, document);
	}
})(function ($, window, document, undefined) {
	'use strict';

	var DataTable = $.fn.dataTable;

	// Used for namespacing events added to the document by each instance, so they
	// can be removed on destroy
	var _instCounter = 0;

	// Button namespacing counter for namespacing events on individual buttons
	var _buttonCounter = 0;

	// Default ID naming counter
	var _buttonIdCounter = 1;

	var _dtButtons = DataTable.ext.buttons;

	/**
   * Botones
   *
   * @name Buttons
   * @function
   * @since UDA 3.4.0 // Datatable 1.0.0
   *
   * @param {object} dt
   * @param {object} config
   *
   */
	var Buttons = function Buttons(dt, config) {
		var idTable = dt.context[0].sTableId;
		var ctx = dt.context[0];
		ctx.ext = DataTable.ext;
		ctx.ext.buttons = {};
		ctx.ext.buttons.copyButton = {
			text: function text(dt) {
				return $.rup.i18nParse($.rup.i18n.base, 'rup_datatable.toolbar.reports.copyButton');
			},
			id: idTable + 'copyButton_1', // Campo obligatorio si se quiere usar desde el contextMenu
			className: 'buttons-copyButton',
			displayRegex: /^[1-9][0-9]*$/, // Se muestra siempre que sea un numero mayor a 0
			insideContextMenu: true, // Independientemente de este valor, sera 'false' si no tiene un id definido
			type: 'copyButton',
			init: function init(dt, node, config) {
				ctx.ext.buttons.copyButton.eventDT = dt;
			},
			action: function action(e, dt, button, config) {
				// Si es llamado desde el contextMenu este paso es innecesario y la condicion
				// del if evita un error
				if (this.processing !== undefined) {
					this.processing(true);
				}
				var that = this;
				$('#' + ctx.sTableId).triggerHandler('tableButtonsBeforeCopyClick');
				_reportsCopyData(dt, that, config);
				$('#' + ctx.sTableId).triggerHandler('tableButtonsAfterCopyClick');
			}
		};

		ctx.ext.buttons.addButton = {
			text: function text(dt) {
				return $.rup.i18nParse($.rup.i18n.base, 'rup_datatable.toolbar.add');
			},
			id: idTable + 'addButton_1', // Campo obligatorio si se quiere usar desde el contextMenu
			className: 'datatable_toolbar_btnAdd',
			displayRegex: /^\d+$/, // Se muestra siempre que sea un numero positivo o neutro
			insideContextMenu: true, // Independientemente de este valor, sera 'false' si no tiene un id definido
			type: 'add',
			init: function init(dt, node, config) {
				ctx.ext.buttons.addButton.eventDT = dt;
			},
			action: function action(e, dt, node, config) {
				$('#' + ctx.sTableId).triggerHandler('tableButtonsBeforeAddClick');
				DataTable.Api().buttons.actions(dt, config);
				$('#' + ctx.sTableId).triggerHandler('tableButtonsAfterAddClick');
			}
		};

		ctx.ext.buttons.editButton = {
			text: function text(dt) {
				return $.rup.i18nParse($.rup.i18n.base, 'rup_datatable.toolbar.edit');
			},
			id: idTable + 'editButton_1', // Campo obligatorio si se quiere usar desde el contextMenu
			className: 'datatable_toolbar_btnEdit',
			displayRegex: /^[1-9][0-9]*$/, // Se muestra siempre que sea un numero mayor a 0
			insideContextMenu: true, // Independientemente de este valor, sera 'false' si no tiene un id definido
			type: 'edit',
			init: function init(dt, node, config) {
				ctx.ext.buttons.editButton.eventDT = dt;
			},
			action: function action(e, dt, node, config) {
				$('#' + ctx.sTableId).triggerHandler('tableButtonsBeforeEditClick');
				DataTable.Api().buttons.actions(dt, config);
				$('#' + ctx.sTableId).triggerHandler('tableButtonsAfterEditClick');
			}
		};

		ctx.ext.buttons.cloneButton = {
			text: function text(dt) {
				return $.rup.i18nParse($.rup.i18n.base, 'rup_datatable.toolbar.clone');
			},
			id: idTable + 'cloneButton_1', // Campo obligatorio si se quiere usar desde el contextMenu
			className: 'datatable_toolbar_btnClone',
			displayRegex: /^1$/, // Se muestra solo cuando sea igual a 1
			insideContextMenu: true, // Independientemente de este valor, sera 'false' si no tiene un id definido
			type: 'clone',
			init: function init(dt, node, config) {
				ctx.ext.buttons.cloneButton.eventDT = dt;
			},
			action: function action(e, dt, node, config) {
				$('#' + ctx.sTableId).triggerHandler('tableButtonsBeforeCloneClick');
				DataTable.Api().buttons.actions(dt, config);
				$('#' + ctx.sTableId).triggerHandler('tableButtonsAfterCloneClick');
			}
		};

		ctx.ext.buttons.deleteButton = {
			text: function text(dt) {
				return $.rup.i18nParse($.rup.i18n.base, 'rup_datatable.toolbar.delete');
			},
			id: idTable + 'deleteButton_1', // Campo obligatorio si se quiere usar desde el contextMenu
			className: 'datatable_toolbar_btnDelete',
			displayRegex: /^[1-9][0-9]*$/, // Se muestra siempre que sea un numero mayor a 0
			insideContextMenu: true, // Independientemente de este valor, sera 'false' si no tiene un id definido
			type: 'delete',
			init: function init(dt, node, config) {
				ctx.ext.buttons.deleteButton.eventDT = dt;
			},
			action: function action(e, dt, node, config) {
				$('#' + ctx.sTableId).triggerHandler('tableButtonsBeforeDeleteClick');
				DataTable.Api().buttons.actions(dt, config);
				$('#' + ctx.sTableId).triggerHandler('tableButtonsAfterDeleteClick');
			}
		};

		ctx.ext.buttons.reportsButton = {
			extend: 'collection',
			text: function text(dt) {
				return $.rup.i18nParse($.rup.i18n.base, 'rup_datatable.toolbar.reports.main');
			},
			id: idTable + 'informes_01',
			className: 'align-right',
			displayRegex: /^[1-9][0-9]*$/, // Se muestra siempre que sea un numero mayor a 0
			autoClose: true,
			type: 'reports',
			buttons: ['copyButton']
		};
		// If there is no config set it to an empty object
		if (typeof config === 'undefined') {
			config = {};
		}

		// Allow a boolean true for defaults
		if (config === true) {
			config = {};
		}

		// For easy configuration of buttons an array can be given
		if ($.isArray(config)) {
			config = { buttons: config };
		}

		this.c = $.extend(true, {}, Buttons.defaults, config);

		// Don't want a deep copy for the buttons
		if (config.buttons) {
			this.c.buttons = config.buttons;
		}

		this.s = {
			dt: new DataTable.Api(dt),
			buttons: [],
			listenKeys: '',
			namespace: 'dtb' + _instCounter++
		};

		this.dom = {
			container: $('<' + this.c.dom.container.tag + '/>').addClass(this.c.dom.container.className)
		};

		this._constructor();
	};

	$.extend(Buttons.prototype, {
		/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
   * Public methods
   */

		/**
   * Get the action of a button
   *
   * @name action
    * @function
    * @since UDA 3.4.0 // Datatable 1.0.0
   *
   * @param  {int|string} Button index
   * @return {function}
   *
   */
		/**
   * Set the action of a button
   *
   * @name action
    * @function
    * @since UDA 3.4.0 // Datatable 1.0.0
   *
   * @param  {node} node Button element
   * @param  {function} action Function to set
   * @return {Buttons} Self for chaining
   *
   */
		action: function action(node, _action) {
			var button = this._nodeToButton(node);

			if (_action === undefined) {
				return button.conf.action;
			}

			button.conf.action = _action;

			return this;
		},

		/**
   * Add an active class to the button to make to look active or get current
   * active state.
   *
   * @name active
    * @function
    * @since UDA 3.4.0 // Datatable 1.0.0
   *
   * @param  {node} node Button element
   * @param  {boolean} [flag] Enable / disable flag
   * @return {Buttons} Self for chaining or boolean for getter
   *
   */
		active: function active(node, flag) {
			var button = this._nodeToButton(node);
			var klass = this.c.dom.button.active;
			var jqNode = $(button.node);

			if (flag === undefined) {
				return jqNode.hasClass(klass);
			}

			jqNode.toggleClass(klass, flag === undefined ? true : flag);

			return this;
		},

		/**
   * Add a new button
   *
   * @name add
    * @function
    * @since UDA 3.4.0 // Datatable 1.0.0
   *
   * @param {object} config Button configuration object, base string name or function
   * @param {int|string} [idx] Button index for where to insert the button
   * @return {Buttons} Self for chaining
   *
   */
		add: function add(config, idx) {
			var buttons = this.s.buttons;

			if (typeof idx === 'string') {
				var split = idx.split('-');
				var base = this.s;

				for (var i = 0, ien = split.length - 1; i < ien; i++) {
					base = base.buttons[split[i] * 1];
				}

				buttons = base.buttons;
				idx = split[split.length - 1] * 1;
			}

			this._expandButton(buttons, config, false, idx);
			this._draw();

			return this;
		},

		/**
   * Get the container node for the buttons
   *
   * @name container
    * @function
    * @since UDA 3.4.0 // Datatable 1.0.0
   *
   * @return {jQuery} Buttons node
   *
   */
		container: function container() {
			return this.dom.container;
		},

		/**
   * Disable a button
   *
   * @name disable
    * @function
    * @since UDA 3.4.0 // Datatable 1.0.0
   *
   * @param  {node} node Button node
   * @return {Buttons} Self for chaining
   *
   */
		disable: function disable(node) {
			var button = this._nodeToButton(node);

			$(button.node).addClass(this.c.dom.button.disabled);

			return this;
		},

		/**
   * Destroy the instance, cleaning up event handlers and removing DOM
   * elements
   *
   * @name destroy
    * @function
    * @since UDA 3.4.0 // Datatable 1.0.0
   *
   * @return {Buttons} Self for chaining
   *
   */
		destroy: function destroy() {
			// Key event listener
			$('body').off('keyup.' + this.s.namespace);

			// Individual button destroy (so they can remove their own events if
			// needed). Take a copy as the array is modified by `remove`
			var buttons = this.s.buttons.slice();
			var i, ien;

			for (i = 0, ien = buttons.length; i < ien; i++) {
				this.remove(buttons[i].node);
			}

			// Container
			this.dom.container.remove();

			// Remove from the settings object collection
			var buttonInsts = this.s.dt.settings()[0];

			for (i = 0, ien = buttonInsts.length; i < ien; i++) {
				if (buttonInsts.inst === this) {
					buttonInsts.splice(i, 1);
					break;
				}
			}

			return this;
		},

		/**
   * Enable / disable a button
   *
   * @name enable
    * @function
    * @since UDA 3.4.0 // Datatable 1.0.0
   *
   * @param  {node} node Button node
   * @param  {boolean} [flag=true] Enable / disable flag
   * @return {Buttons} Self for chaining
   *
   */
		enable: function enable(node, flag) {
			if (flag === false) {
				return this.disable(node);
			}

			var button = this._nodeToButton(node);
			$(button.node).removeClass(this.c.dom.button.disabled);

			return this;
		},

		/**
   * Get the instance name for the button set selector
   *
   * @name name
    * @function
    * @since UDA 3.4.0 // Datatable 1.0.0
   *
   * @return {string} Instance name
   *
   */
		name: function name() {
			return this.c.name;
		},

		/**
   * Get a button's node
   *
   * @name node
    * @function
    * @since UDA 3.4.0 // Datatable 1.0.0
   *
   * @param  {node} node Button node
   * @return {jQuery} Button element
   *
   */
		node: function node(_node) {
			var button = this._nodeToButton(_node);
			return $(button.node);
		},

		/**
   * Set / get a processing class on the selected button
   *
   * @name processing
    * @function
    * @since UDA 3.4.0 // Datatable 1.0.0
   *
   * @param  {boolean} flag true to add, false to remove, undefined to get
   * @return {boolean|Buttons} Getter value or this if a setter.
   *
   */
		processing: function processing(node, flag) {
			var button = this._nodeToButton(node);

			if (flag === undefined) {
				return $(button.node).hasClass('processing');
			}

			$(button.node).toggleClass('processing', flag);

			return this;
		},

		/**
   * Remove a button.
   *
   * @name remove
    * @function
    * @since UDA 3.4.0 // Datatable 1.0.0
   *
   * @param  {node} node Button node
   * @return {Buttons} Self for chaining
   *
   */
		remove: function remove(node) {
			var button = this._nodeToButton(node);
			var host = this._nodeToHost(node);
			var dt = this.s.dt;

			// Remove any child buttons first
			if (button.buttons.length) {
				for (var i = button.buttons.length - 1; i >= 0; i--) {
					this.remove(button.buttons[i].node);
				}
			}

			// Allow the button to remove event handlers, etc
			if (button.conf.destroy) {
				button.conf.destroy.call(dt.button(node), dt, $(node), button.conf);
			}

			this._removeKey(button.conf);

			$(button.node).remove();

			var idx = $.inArray(button, host);
			host.splice(idx, 1);

			return this;
		},

		/**
   * Get the text for a button
   *
   * @name text
    * @function
    * @since UDA 3.4.0 // Datatable 1.0.0
   *
   * @param  {int|string} node Button index
   * @return {string} Button text
   *
   */
		/**
   * Set the text for a button
   *
   * @name text
    * @function
    * @since UDA 3.4.0 // Datatable 1.0.0
   *
   * @param  {int|string|function} node Button index
   * @param  {string} label Text
   * @return {Buttons} Self for chaining
   *
   */
		text: function text(node, label) {
			var button = this._nodeToButton(node);
			var buttonLiner = this.c.dom.collection.buttonLiner;
			var linerTag = button.inCollection && buttonLiner && buttonLiner.tag ? buttonLiner.tag : this.c.dom.buttonLiner.tag;
			var dt = this.s.dt;
			var jqNode = $(button.node);
			var text = function text(opt) {
				return typeof opt === 'function' ? opt(dt, jqNode, button.conf) : opt;
			};

			if (label === undefined) {
				return text(button.conf.text);
			}

			button.conf.text = label;

			if (linerTag) {
				jqNode.children(linerTag).html(text(label));
			} else {
				jqNode.html(text(label));
			}

			return this;
		},

		/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
   * Constructor
   */

		/**
   * Buttons constructor
   *
   * @name _constructor
    * @function
    * @since UDA 3.4.0 // Datatable 1.0.0
   *
   */
		_constructor: function _constructor() {
			var that = this;
			var dt = this.s.dt;
			var dtSettings = dt.settings()[0];
			var buttons = this.c.buttons;

			if (!dtSettings._buttons) {
				dtSettings._buttons = [];
			}

			dtSettings._buttons.push({
				inst: this,
				name: this.c.name
			});

			for (var i = 0, ien = buttons.length; i < ien; i++) {
				this.add(buttons[i]);
			}

			dt.on('destroy', function () {
				that.destroy();
			});

			// Global key event binding to listen for button keys
			$('body').on('keyup.' + this.s.namespace, function (e) {
				if (!document.activeElement || document.activeElement === document.body) {
					// SUse a string of characters for fast lookup of if we need to
					// handle this
					var character = String.fromCharCode(e.keyCode).toLowerCase();

					if (that.s.listenKeys.toLowerCase().indexOf(character) !== -1) {
						that._keypress(character, e);
					}
				}
			});
		},

		/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
   * Private methods
   */

		/**
   * Add a new button to the key press listener
   *
   * @name _addKey
    * @function
    * @since UDA 3.4.0 // Datatable 1.0.0
   *
   * @param {object} conf Resolved button configuration object
   *
   */
		_addKey: function _addKey(conf) {
			if (conf.key) {
				this.s.listenKeys += $.isPlainObject(conf.key) ? conf.key.key : conf.key;
			}
		},

		/**
   * Insert the buttons into the container. Call without parameters!
   *
   * @name _draw
    * @function
    * @since UDA 3.4.0 // Datatable 1.0.0
   *
   * @param  {node} [container] Recursive only - Insert point
   * @param  {array} [buttons] Recursive only - Buttons array
   *
   */
		_draw: function _draw(container, buttons) {
			if (!container) {
				container = this.dom.container;
				buttons = this.s.buttons;
			}

			container.children().detach();

			for (var i = 0, ien = buttons.length; i < ien; i++) {
				container.append(buttons[i].inserter);
				container.append(' ');

				if (buttons[i].buttons && buttons[i].buttons.length) {
					this._draw(buttons[i].collection, buttons[i].buttons);
				}
			}
		},

		/**
   * Create buttons from an array of buttons
   *
   * @name _expandButton
    * @function
    * @since UDA 3.4.0 // Datatable 1.0.0
   *
   * @param  {array} attachTo Buttons array to attach to
   * @param  {object} button Button definition
   * @param  {boolean} inCollection true if the button is in a collection
   *
   */
		_expandButton: function _expandButton(attachTo, button, inCollection, attachPoint) {
			var dt = this.s.dt;
			var buttonCounter = 0;
			var buttons = !$.isArray(button) ? [button] : button;

			for (var i = 0, ien = buttons.length; i < ien; i++) {
				var conf = this._resolveExtends(buttons[i]);

				if (!conf) {
					continue;
				}

				// If the configuration is an array, then expand the buttons at this
				// point
				if ($.isArray(conf)) {
					this._expandButton(attachTo, conf, inCollection, attachPoint);
					continue;
				}

				var built = this._buildButton(conf, inCollection);
				if (!built) {
					continue;
				}

				if (attachPoint !== undefined) {
					attachTo.splice(attachPoint, 0, built);
					attachPoint++;
				} else {
					attachTo.push(built);
				}

				if (built.conf.buttons) {
					var collectionDom = this.c.dom.collection;
					built.collection = $('<' + collectionDom.tag + '/>').addClass(collectionDom.className).attr('role', 'menu');
					built.conf._collection = built.collection;

					this._expandButton(built.buttons, built.conf.buttons, true, attachPoint);
				}

				// init call is made here, rather than buildButton as it needs to
				// be selectable, and for that it needs to be in the buttons array
				if (conf.init) {
					conf.init.call(dt.button(built.node), dt, $(built.node), conf);
				}

				buttonCounter++;
			}
		},

		/**
   * Create an individual button
   *
   * @name _buildButton
    * @function
    * @since UDA 3.4.0 // Datatable 1.0.0
   *
   * @param  {object} config            Resolved button configuration
   * @param  {boolean} inCollection `true` if a collection button
   * @return {jQuery} Created button node (jQuery)
   *
   */
		_buildButton: function _buildButton(config, inCollection) {
			var buttonDom = this.c.dom.button;
			var linerDom = this.c.dom.buttonLiner;
			var collectionDom = this.c.dom.collection;
			var dt = this.s.dt;
			var ctx = dt.settings()[0];
			var text = function text(opt) {
				return typeof opt === 'function' ? opt(dt, button, config) : opt;
			};

			if (inCollection && collectionDom.button) {
				buttonDom = collectionDom.button;
			}

			if (inCollection && collectionDom.buttonLiner) {
				linerDom = collectionDom.buttonLiner;
			}

			// Make sure that the button is available based on whatever requirements
			// it has. For example, Flash buttons require Flash
			if (config.available && !config.available(dt, config)) {
				return false;
			}

			var action = function action(e, dt, button, config) {
				config.action.call(dt.button(button), e, dt, button, config);

				$(dt.table().node()).triggerHandler('buttons-action.dt', [dt.button(button), dt, button, config]);
			};

			var button = $('<' + buttonDom.tag + '/>').addClass(buttonDom.className).attr('tabindex', this.s.dt.settings()[0].iTabIndex).attr('aria-controls', this.s.dt.table().node().id).on('click.dtb', function (e) {
				e.preventDefault();

				if (!button.hasClass(buttonDom.disabled) && config.action) {
					action(e, dt, button, config);
				}

				button.blur();
			}).on('keyup.dtb', function (e) {
				if (e.keyCode === 13) {
					if (!button.hasClass(buttonDom.disabled) && config.action) {
						action(e, dt, button, config);
					}
				}
			});

			// Make `a` tags act like a link
			if (buttonDom.tag.toLowerCase() === 'a') {
				button.attr('href', '#');
			}

			if (linerDom.tag) {
				var liner = $('<' + linerDom.tag + '/>').html(text(config.text)).addClass(linerDom.className);

				if (linerDom.tag.toLowerCase() === 'a') {
					liner.attr('href', '#');
				}

				button.append(liner);
			} else {
				button.html(text(config.text));
			}

			if (config.id) {
				button.attr('id', config.id);
			} else {
				// Se desactiva el acceso desde el contextMenu por no tener un id establecido
				config.insideContextMenu = false;
				// Se asigna un id dinamico en funcion del nombre del datatable al que pertenece
				config.id = ctx.sTableId + '_button_' + _buttonIdCounter++;
				button.attr('id', config.id);
			}

			if (config.className) {
				button.addClass(config.className);
			}

			if (config.titleAttr) {
				button.attr('title', text(config.titleAttr));
			}

			if (config.attr) {
				button.attr(config.attr);
			}

			if (!config.namespace) {
				config.namespace = '.dt-button-' + _buttonCounter++;
			}

			if (!config.icon) {
				// Comprueba si es alguno de los botones con iconos definidos por defecto
				switch (config.type) {
					case 'add':
						config.icon = "fa-plus";
						break;
					case 'edit':
						config.icon = "fa-pencil-square-o";
						break;
					case 'clone':
						config.icon = "fa-clone";
						break;
					case 'delete':
						config.icon = "fa-trash-o";
						break;
					case 'reports':
						config.icon = "fa-file-o";
						break;
					case 'copyButton':
						config.icon = "fa-clipboard";
						break;
					default:
						config.icon = "fa-cog";
				}
			}

			var buttonContainer = this.c.dom.buttonContainer;
			var inserter;
			if (buttonContainer && buttonContainer.tag) {
				inserter = $('<' + buttonContainer.tag + '/>').addClass(buttonContainer.className).append(button);
			} else {
				inserter = button;
			}

			this._addKey(config);

			return {
				conf: config,
				node: button.get(0),
				inserter: inserter,
				buttons: [],
				inCollection: inCollection,
				collection: null
			};
		},

		/**
   * Get the button object from a node (recursive)
   *
   * @name _nodeToButton
    * @function
    * @since UDA 3.4.0 // Datatable 1.0.0
   *
   * @param  {node} node Button node
   * @param  {array} [buttons] Button array, uses base if not defined
   * @return {object} Button object
   *
   */
		_nodeToButton: function _nodeToButton(node, buttons) {
			if (!buttons) {
				buttons = this.s.buttons;
			}

			for (var i = 0, ien = buttons.length; i < ien; i++) {
				if (buttons[i].node === node) {
					return buttons[i];
				}

				if (buttons[i].buttons.length) {
					var ret = this._nodeToButton(node, buttons[i].buttons);

					if (ret) {
						return ret;
					}
				}
			}
		},

		/**
   * Get container array for a button from a button node (recursive)
   *
   * @name _nodeToHost
    * @function
    * @since UDA 3.4.0 // Datatable 1.0.0
   *
   * @param  {node} node Button node
   * @param  {array} [buttons] Button array, uses base if not defined
   * @return {array} Button's host array
   *
   */
		_nodeToHost: function _nodeToHost(node, buttons) {
			if (!buttons) {
				buttons = this.s.buttons;
			}

			for (var i = 0, ien = buttons.length; i < ien; i++) {
				if (buttons[i].node === node) {
					return buttons;
				}

				if (buttons[i].buttons.length) {
					var ret = this._nodeToHost(node, buttons[i].buttons);

					if (ret) {
						return ret;
					}
				}
			}
		},

		/**
   * Handle a key press - determine if any button's key configured matches
   * what was typed and trigger the action if so.
   *
   * @name _keypress
    * @function
    * @since UDA 3.4.0 // Datatable 1.0.0
   *
   * @param  {string} character The character pressed
   * @param  {object} e Key event that triggered this call
   *
   */
		_keypress: function _keypress(character, e) {
			// Check if this button press already activated on another instance of Buttons
			if (e._buttonsHandled) {
				return;
			}

			var run = function run(conf, node) {
				if (!conf.key) {
					return;
				}

				if (conf.key === character) {
					e._buttonsHandled = true;
					$(node).click();
				} else if ($.isPlainObject(conf.key)) {
					if (conf.key.key !== character) {
						return;
					}

					if (conf.key.shiftKey && !e.shiftKey) {
						return;
					}

					if (conf.key.altKey && !e.altKey) {
						return;
					}

					if (conf.key.ctrlKey && !e.ctrlKey) {
						return;
					}

					if (conf.key.metaKey && !e.metaKey) {
						return;
					}

					// Made it this far - it is good
					e._buttonsHandled = true;
					$(node).click();
				}
			};

			var recurse = function recurse(a) {
				for (var i = 0, ien = a.length; i < ien; i++) {
					run(a[i].conf, a[i].node);

					if (a[i].buttons.length) {
						recurse(a[i].buttons);
					}
				}
			};

			recurse(this.s.buttons);
		},

		/**
   * Remove a key from the key listener for this instance (to be used when a
   * button is removed)
   *
   * @name _removeKey
    * @function
    * @since UDA 3.4.0 // Datatable 1.0.0
   *
   * @param  {object} conf Button configuration
   *
   */
		_removeKey: function _removeKey(conf) {
			if (conf.key) {
				var character = $.isPlainObject(conf.key) ? conf.key.key : conf.key;

				// Remove only one character, as multiple buttons could have the
				// same listening key
				var a = this.s.listenKeys.split('');
				var idx = $.inArray(character, a);
				a.splice(idx, 1);
				this.s.listenKeys = a.join('');
			}
		},

		/**
   * Resolve a button configuration
   *
   * @name _resolveExtends
    * @function
    * @since UDA 3.4.0 // Datatable 1.0.0
   *
   * @param  {string|function|object} conf Button config to resolve
   * @return {object} Button configuration
   *
   */
		_resolveExtends: function _resolveExtends(conf) {
			var dt = this.s.dt;
			var i, ien;
			var ctx = dt.context[0];
			var _dtButtonsTable = ctx.ext.buttons;
			_dtButtonsTable.collection = _dtButtons.collection;
			var toConfObject = function toConfObject(base) {
				var loop = 0;

				// Loop until we have resolved to a button configuration, or an
				// array of button configurations (which will be iterated
				// separately)
				while (!$.isPlainObject(base) && !$.isArray(base)) {
					if (base === undefined) {
						return;
					}

					if (typeof base === 'function') {
						base = base(dt, conf);

						if (!base) {
							return false;
						}
					} else if (typeof base === 'string') {
						if (!_dtButtonsTable[base]) {
							throw 'Unknown button type: ' + base;
						}

						base = _dtButtonsTable[base];
					}

					loop++;
					if (loop > 30) {
						// Protect against misconfiguration killing the browser
						throw 'Buttons: Too many iterations';
					}
				}

				return $.isArray(base) ? base : $.extend({}, base);
			};

			conf = toConfObject(conf);

			while (conf && conf.extend) {
				// Use `toConfObject` in case the button definition being extended
				// is itself a string or a function
				if (!_dtButtonsTable[conf.extend]) {
					throw 'Cannot extend unknown button type: ' + conf.extend;
				}

				var objArray = toConfObject(_dtButtonsTable[conf.extend]);
				if ($.isArray(objArray)) {
					return objArray;
				} else if (!objArray) {
					// This is a little brutal as it might be possible to have a
					// valid button without the extend, but if there is no extend
					// then the host button would be acting in an undefined state
					return false;
				}

				// Stash the current class name
				var originalClassName = objArray.className;

				conf = $.extend({}, objArray, conf);

				// The extend will have overwritten the original class name if the
				// `conf` object also assigned a class, but we want to concatenate
				// them so they are list that is combined from all extended buttons
				if (originalClassName && conf.className !== originalClassName) {
					conf.className = originalClassName + ' ' + conf.className;
				}

				// Buttons to be added to a collection  -gives the ability to define
				// if buttons should be added to the start or end of a collection
				var postfixButtons = conf.postfixButtons;
				if (postfixButtons) {
					if (!conf.buttons) {
						conf.buttons = [];
					}

					for (i = 0, ien = postfixButtons.length; i < ien; i++) {
						conf.buttons.push(postfixButtons[i]);
					}

					conf.postfixButtons = null;
				}

				var prefixButtons = conf.prefixButtons;
				if (prefixButtons) {
					if (!conf.buttons) {
						conf.buttons = [];
					}

					for (i = 0, ien = prefixButtons.length; i < ien; i++) {
						conf.buttons.splice(i, 0, prefixButtons[i]);
					}

					conf.prefixButtons = null;
				}

				// Although we want the `conf` object to overwrite almost all of
				// the properties of the object being extended, the `extend`
				// property should come from the object being extended
				conf.extend = objArray.extend;
			}

			return conf;
		}
	});

	/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  * Statics
  */

	/**
  * Show / hide a background layer behind a collection
  *
  * @name Buttons.background
  * @function
  * @since UDA 3.4.0 // Datatable 1.0.0
  *
  * @param  {boolean} Flag to indicate if the background should be shown or
  *   hidden
  * @param  {string} Class to assign to the background
  *
  * @static
  *
  */
	Buttons.background = function (show, className, fade) {
		if (fade === undefined) {
			fade = 400;
		}

		if (show) {
			$('<div/>').addClass(className).css('display', 'none').appendTo('body').fadeIn(fade);
		} else {
			$('body > div.' + className).fadeOut(fade, function () {
				$(this).removeClass(className).remove();
			});
		}
	};

	/**
  * Instance selector - select Buttons instances based on an instance selector
  * value from the buttons assigned to a DataTable. This is only useful if
  * multiple instances are attached to a DataTable.
  *
  * @name Buttons.instanceSelector
  * @function
  * @since UDA 3.4.0 // Datatable 1.0.0
  *
  * @param  {string|int|array} Instance selector - see `instance-selector`
  *   documentation on the DataTables site
  * @param  {array} Button instance array that was attached to the DataTables
  *   settings object
  * @return {array} Buttons instances
  *
  * @static
  *
  */
	Buttons.instanceSelector = function (group, buttons) {
		if (!group) {
			return $.map(buttons, function (v) {
				return v.inst;
			});
		}

		var ret = [];
		var names = $.map(buttons, function (v) {
			return v.name;
		});

		// Flatten the group selector into an array of single options
		var process = function process(input) {
			if ($.isArray(input)) {
				for (var i = 0, ien = input.length; i < ien; i++) {
					process(input[i]);
				}
				return;
			}

			if (typeof input === 'string') {
				if (input.indexOf(',') !== -1) {
					// String selector, list of names
					process(input.split(','));
				} else {
					// String selector individual name
					var idx = $.inArray($.trim(input), names);

					if (idx !== -1) {
						ret.push(buttons[idx].inst);
					}
				}
			} else if (typeof input === 'number') {
				// Index selector
				ret.push(buttons[input].inst);
			}
		};

		process(group);

		return ret;
	};

	/**
  * Button selector - select one or more buttons from a selector input so some
  * operation can be performed on them.
  *
  * @name Buttons.buttonSelector
  * @function
  * @since UDA 3.4.0 // Datatable 1.0.0
  *
  * @param  {array} Button instances array that the selector should operate on
  * @param  {string|int|node|jQuery|array} Button selector - see
  *   `button-selector` documentation on the DataTables site
  * @return {array} Array of objects containing `inst` and `idx` properties of
  *   the selected buttons so you know which instance each button belongs to.
  *
  * @static
  *
  */
	Buttons.buttonSelector = function (insts, selector) {
		var ret = [];
		var nodeBuilder = function nodeBuilder(a, buttons, baseIdx) {
			var button;
			var idx;

			for (var i = 0, ien = buttons.length; i < ien; i++) {
				button = buttons[i];

				if (button) {
					idx = baseIdx !== undefined ? baseIdx + i : i + '';

					a.push({
						node: button.node,
						name: button.conf.name,
						idx: idx
					});

					if (button.buttons) {
						nodeBuilder(a, button.buttons, idx + '-');
					}
				}
			}
		};

		var run = function run(selector, inst) {
			var i, ien;
			var buttons = [];
			nodeBuilder(buttons, inst.s.buttons);

			var nodes = $.map(buttons, function (v) {
				return v.node;
			});

			if ($.isArray(selector) || selector instanceof $) {
				for (i = 0, ien = selector.length; i < ien; i++) {
					run(selector[i], inst);
				}
				return;
			}

			if (selector === null || selector === undefined || selector === '*') {
				// Select all
				for (i = 0, ien = buttons.length; i < ien; i++) {
					ret.push({
						inst: inst,
						node: buttons[i].node
					});
				}
			} else if (typeof selector === 'number') {
				// Main button index selector
				ret.push({
					inst: inst,
					node: inst.s.buttons[selector].node
				});
			} else if (typeof selector === 'string') {
				if (selector.indexOf(',') !== -1) {
					// Split
					var a = selector.split(',');

					for (i = 0, ien = a.length; i < ien; i++) {
						run($.trim(a[i]), inst);
					}
				} else if (selector.match(/^\d+(\-\d+)*$/)) {
					// Sub-button index selector
					var indexes = $.map(buttons, function (v) {
						return v.idx;
					});

					ret.push({
						inst: inst,
						node: buttons[$.inArray(selector, indexes)].node
					});
				} else if (selector.indexOf(':name') !== -1) {
					// Button name selector
					var name = selector.replace(':name', '');

					for (i = 0, ien = buttons.length; i < ien; i++) {
						if (buttons[i].name === name) {
							ret.push({
								inst: inst,
								node: buttons[i].node
							});
						}
					}
				} else {
					// jQuery selector on the nodes
					$(nodes).filter(selector).each(function () {
						ret.push({
							inst: inst,
							node: this
						});
					});
				}
			} else if ((typeof selector === 'undefined' ? 'undefined' : _typeof(selector)) === 'object' && selector.nodeName) {
				// Node selector
				var idx = $.inArray(selector, nodes);

				if (idx !== -1) {
					ret.push({
						inst: inst,
						node: nodes[idx]
					});
				}
			}
		};

		for (var i = 0, ien = insts.length; i < ien; i++) {
			var inst = insts[i];

			run(selector, inst);
		}

		return ret;
	};

	/**
  * Buttons defaults. For full documentation, please refer to the docs/option
  * directory or the DataTables site. Contiene los botones expuestos en el toolbar.
  *
  * @name Buttons.defaults
  * @function
  * @since UDA 3.4.0 // Datatable 1.0.0
  *
  * @type {Object}
  *
  * @static
  *
  */
	Buttons.defaults = {
		buttons: ['addButton', 'editButton', 'cloneButton', 'deleteButton', 'reportsButton'],
		name: 'main',
		tabIndex: 0,
		dom: {
			container: {
				tag: 'div',
				className: 'dt-buttons'
			},
			collection: {
				tag: 'div',
				className: 'dt-button-collection'
			},
			button: {
				tag: 'button',
				className: 'btn btn-primary',
				active: 'active',
				disabled: 'disabled'
			},
			buttonLiner: {
				tag: 'span',
				className: ''
			}
		}
	};

	/**
  * Version information
  *
  * @name Buttons.version
  * @function
  * @since UDA 3.4.0 // Datatable 1.0.0
  *
  * @type {string}
  *
  * @static
  *
  */
	Buttons.version = '1.5.1';

	$.extend(_dtButtons, {
		collection: {
			text: function text(dt) {
				return $.rup.i18nParse($.rup.i18n.base, 'rup.datatable.collection');
			},
			className: 'buttons-collection',
			action: function action(e, dt, button, config) {
				var host = button;
				var collectionParent = $(button).parents('div.dt-button-collection');
				var hostPosition = host.position();
				var tableContainer = $(dt.table().container());
				var multiLevel = false;
				var insertPoint = host;

				// Remove any old collection
				if (collectionParent.length) {
					multiLevel = $('.dt-button-collection').position();
					insertPoint = collectionParent;
					$('body').trigger('click.dtb-collection');
				}

				config._collection.addClass(config.collectionLayout).css('display', 'none').insertAfter(insertPoint).fadeIn(config.fade);

				var position = config._collection.css('position');

				if (multiLevel && position === 'absolute') {
					config._collection.css({
						top: multiLevel.top,
						left: multiLevel.left
					});
				} else if (position === 'absolute') {
					config._collection.css({
						top: hostPosition.top + host.outerHeight(),
						left: hostPosition.left
					});

					// calculate overflow when positioned beneath
					var tableBottom = tableContainer.offset().top + tableContainer.height();
					var listBottom = hostPosition.top + host.outerHeight() + config._collection.outerHeight();
					var bottomOverflow = listBottom - tableBottom;

					// calculate overflow when positioned above
					var listTop = hostPosition.top - config._collection.outerHeight();
					var tableTop = tableContainer.offset().top;
					var topOverflow = tableTop - listTop;

					// if bottom overflow is larger, move to the top because it fits better
					if (bottomOverflow > topOverflow) {
						config._collection.css('top', hostPosition.top - config._collection.outerHeight() - 5);
					}

					var listRight = hostPosition.left + config._collection.outerWidth();
					var tableRight = tableContainer.offset().left + tableContainer.width();
					if (listRight > tableRight) {
						config._collection.css('left', hostPosition.left - (listRight - tableRight));
					}
				} else {
					// Fix position - centre on screen
					var top = config._collection.height() / 2;
					if (top > $(window).height() / 2) {
						top = $(window).height() / 2;
					}

					config._collection.css('marginTop', top * -1);
				}

				if (config.background) {
					Buttons.background(true, config.backgroundClassName, config.fade);
				}

				// Need to break the 'thread' for the collection button being
				// activated by a click - it would also trigger this event
				setTimeout(function () {
					// This is bonkers, but if we don't have a click listener on the
					// background element, iOS Safari will ignore the body click
					// listener below. An empty function here is all that is
					// required to make it work...
					$('div.dt-button-background').on('click.dtb-collection', function () {});

					$('body').on('click.dtb-collection', function (e) {
						// andSelf is deprecated in jQ1.8, but we want 1.7 compat
						var back = $.fn.addBack ? 'addBack' : 'andSelf';

						if (!$(e.target).parents()[back]().filter(config._collection).length) {
							config._collection.fadeOut(config.fade, function () {
								config._collection.detach();
							});

							$('div.dt-button-background').off('click.dtb-collection');
							Buttons.background(false, config.backgroundClassName, config.fade);

							$('body').off('click.dtb-collection');
							dt.off('buttons-action.b-internal');
						}
					});
				}, 10);

				if (config.autoClose) {
					dt.on('buttons-action.b-internal', function () {
						$('div.dt-button-background').click();
					});
				}
			},
			background: true,
			collectionLayout: '',
			backgroundClassName: 'dt-button-background',
			autoClose: false,
			fade: 400,
			attr: {
				'aria-haspopup': true
			}
		},
		addButton: function addButton(dt, conf) {
			var ctx = dt.context[0];
			var collection = _dtButtons['collection'];
			_dtButtons = ctx.ext.buttons;
			_dtButtons.collection = collection;
			if (_dtButtons.addButton) {
				return 'addButton';
			}
		},
		editButton: function editButton(dt, conf) {
			if (_dtButtons.editButton) {
				return 'editButton';
			}
		},
		cloneButton: function cloneButton(dt, conf) {
			if (_dtButtons.cloneButton) {
				return 'cloneButton';
			}
		},
		deleteButton: function deleteButton(dt, conf) {
			if (_dtButtons.deleteButton) {
				return 'deleteButton';
			}
		},
		reportsButton: function reportsButton(dt, conf) {
			if (_dtButtons.reportsButton) {
				return 'reportsButton';
			}
		},
		pageLength: function pageLength(dt) {
			var lengthMenu = dt.settings()[0].aLengthMenu;
			var vals = $.isArray(lengthMenu[0]) ? lengthMenu[0] : lengthMenu;
			var lang = $.isArray(lengthMenu[0]) ? lengthMenu[1] : lengthMenu;
			var text = function text(dt) {
				return dt.i18n('rup_datatable.pageLength', {
					"-1": 'Show all rows',
					_: 'Show %d rows'
				}, dt.page.len());
			};

			return {
				extend: 'collection',
				text: text,
				className: 'buttons-page-length',
				autoClose: true,
				buttons: $.map(vals, function (val, i) {
					return {
						text: lang[i],
						className: 'button-page-length',
						action: function action(e, dt) {
							dt.page.len(val).draw();
						},
						init: function init(dt, node, conf) {
							var that = this;
							var fn = function fn() {
								that.active(dt.page.len() === val);
							};

							dt.on('length.dt' + conf.namespace, fn);
							fn();
						},
						destroy: function destroy(dt, node, conf) {
							dt.off('length.dt' + conf.namespace);
						}
					};
				}),
				init: function init(dt, node, conf) {
					var that = this;
					dt.on('length.dt' + conf.namespace, function () {
						that.text(text(dt));
					});
				},
				destroy: function destroy(dt, node, conf) {
					dt.off('length.dt' + conf.namespace);
				}
			};
		}
	});

	/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  * DataTables API
  *
  * For complete documentation, please refer to the docs/api directory or the
  * DataTables site
  */

	// Buttons group and individual button selector
	DataTable.Api.register('buttons()', function (group, selector) {
		// Argument shifting
		if (selector === undefined) {
			selector = group;
			group = undefined;
		}

		this.selector.buttonGroup = group;

		var res = this.iterator(true, 'table', function (ctx) {
			if (ctx._buttons) {
				return Buttons.buttonSelector(Buttons.instanceSelector(group, ctx._buttons), selector);
			}
		}, true);

		res._groupSelector = group;
		return res;
	});

	// Individual button selector
	DataTable.Api.register('button()', function (group, selector) {
		// just run buttons() and truncate
		var buttons = this.buttons(group, selector);

		if (buttons.length > 1) {
			buttons.splice(1, buttons.length);
		}

		return buttons;
	});

	// Active buttons
	DataTable.Api.registerPlural('buttons().active()', 'button().active()', function (flag) {
		if (flag === undefined) {
			return this.map(function (set) {
				return set.inst.active(set.node);
			});
		}

		return this.each(function (set) {
			set.inst.active(set.node, flag);
		});
	});

	// Get / set button action
	DataTable.Api.registerPlural('buttons().action()', 'button().action()', function (action) {
		if (action === undefined) {
			return this.map(function (set) {
				return set.inst.action(set.node);
			});
		}

		return this.each(function (set) {
			set.inst.action(set.node, action);
		});
	});

	// Enable / disable buttons
	DataTable.Api.register(['buttons().enable()', 'button().enable()'], function (flag) {
		return this.each(function (set) {
			set.inst.enable(set.node, flag);
		});
	});

	// Disable buttons
	DataTable.Api.register(['buttons().disable()', 'button().disable()'], function () {
		return this.each(function (set) {
			set.inst.disable(set.node);
		});
	});

	// Get button nodes
	DataTable.Api.registerPlural('buttons().nodes()', 'button().node()', function () {
		var jq = $();

		// jQuery will automatically reduce duplicates to a single entry
		$(this.each(function (set) {
			jq = jq.add(set.inst.node(set.node));
		}));

		return jq;
	});

	// Get / set button processing state
	DataTable.Api.registerPlural('buttons().processing()', 'button().processing()', function (flag) {
		if (flag === undefined) {
			return this.map(function (set) {
				return set.inst.processing(set.node);
			});
		}

		return this.each(function (set) {
			set.inst.processing(set.node, flag);
		});
	});

	// Get / set button text (i.e. the button labels)
	DataTable.Api.registerPlural('buttons().text()', 'button().text()', function (label) {
		if (label === undefined) {
			return this.map(function (set) {
				return set.inst.text(set.node);
			});
		}

		return this.each(function (set) {
			set.inst.text(set.node, label);
		});
	});

	// Trigger a button's action
	DataTable.Api.registerPlural('buttons().trigger()', 'button().trigger()', function () {
		return this.each(function (set) {
			set.inst.node(set.node).trigger('click');
		});
	});

	// Get the container elements
	DataTable.Api.registerPlural('buttons().containers()', 'buttons().container()', function () {
		var jq = $();
		var groupSelector = this._groupSelector;

		// We need to use the group selector directly, since if there are no buttons
		// the result set will be empty
		this.iterator(true, 'table', function (ctx) {
			if (ctx._buttons) {
				var insts = Buttons.instanceSelector(groupSelector, ctx._buttons);

				for (var i = 0, ien = insts.length; i < ien; i++) {
					jq = jq.add(insts[i].container());
				}
			}
		});

		return jq;
	});

	// Add a new button
	DataTable.Api.register('button().add()', function (idx, conf) {
		var ctx = this.context;

		// Don't use `this` as it could be empty - select the instances directly
		if (ctx.length) {
			var inst = Buttons.instanceSelector(this._groupSelector, ctx[0]._buttons);

			if (inst.length) {
				inst[0].add(conf, idx);
			}
		}

		return this.button(this._groupSelector, idx);
	});

	// Destroy the button sets selected
	DataTable.Api.register('buttons().destroy()', function () {
		this.pluck('inst').unique().each(function (inst) {
			inst.destroy();
		});

		return this;
	});

	// Remove a button
	DataTable.Api.registerPlural('buttons().remove()', 'buttons().remove()', function () {
		this.each(function (set) {
			set.inst.remove(set.node);
		});

		return this;
	});

	// Information box that can be used by buttons
	var _infoTimer;
	DataTable.Api.register('buttons.info()', function (title, message, time) {
		var that = this;

		if (title === false) {
			$('#datatables_buttons_info').fadeOut(function () {
				$(this).remove();
			});
			clearTimeout(_infoTimer);
			_infoTimer = null;

			return this;
		}

		if (_infoTimer) {
			clearTimeout(_infoTimer);
		}

		if ($('#datatables_buttons_info').length) {
			$('#datatables_buttons_info').remove();
		}

		title = title ? '<h2>' + title + '</h2>' : '';

		$('<div id="datatables_buttons_info" class="dt-button-info"/>').html(title).append($('<div/>')[typeof message === 'string' ? 'html' : 'append'](message)).css('display', 'none').appendTo('body').fadeIn();

		if (time !== undefined && time !== 0) {
			_infoTimer = setTimeout(function () {
				that.buttons.info(false);
			}, time);
		}

		return this;
	});

	// Get data from the table for export - this is common to a number of plug-in
	// buttons so it is included in the Buttons core library
	DataTable.Api.register('buttons.exportData()', function (options) {
		if (this.context.length) {
			return _exportData(new DataTable.Api(this.context[0]), options);
		}
	});

	// Get information about the export that is common to many of the export data
	// types (DRY)
	DataTable.Api.register('buttons.exportInfo()', function (conf) {
		if (!conf) {
			conf = {};
		}

		return {
			filename: _filename(conf),
			title: _title(conf),
			messageTop: _message(this, conf.message || conf.messageTop, 'top'),
			messageBottom: _message(this, conf.messageBottom, 'bottom')
		};
	});

	// Gestiona las acciones de los botones
	DataTable.Api.register('buttons.actions()', function (dt, config) {
		var ctx = dt.settings()[0];
		// Añade aquí las funciones de tus botones
		switch (config.type) {
			case 'add':
				var idTableDetail = ctx.oInit.formEdit.detailForm;
				// Limpiamos el formulario
				$(idTableDetail).find('form')[0].reset();
				if (ctx.multiselection.numSelected > 0) {
					$.rup_messages('msgConfirm', {
						message: $.rup.i18nParse($.rup.i18n.base, 'rup_datatable.checkSelectedElems'),
						title: $.rup.i18nParse($.rup.i18n.base, 'rup_datatable.changes'),
						OKFunction: function OKFunction() {
							// Abrimos el formulario
							if (ctx.oInit.seeker !== undefined) {
								DataTable.Api().seeker.limpiarSeeker(dt, ctx); // Y deselecionamos los checks y seekers
							} else {
								if (ctx.oInit.multiSelect !== undefined) {
									DataTable.Api().multiSelect.deselectAll(dt); // Y deselecionamos los checks y seekers
								} else if (ctx.oInit.select !== undefined) {
									DataTable.Api().select.deselect(ctx); // Y deselecionamos los checks y seekers
								}
							}
							DataTable.Api().editForm.openSaveDialog('POST', dt, null);
						}
					});
				} else {
					DataTable.Api().editForm.openSaveDialog('POST', dt, null);
				}
				break;
			case 'edit':
				// Abrimos el formulario
				//Se busca el idRow con el ultimó seleccionado en caso de no existir será el primero.
				var idRow = DataTable.Api().editForm.getRowSelected(dt, 'PUT').line;
				DataTable.Api().editForm.openSaveDialog('PUT', dt, idRow);
				break;
			case 'clone':
				// Abrimos el formulario
				var idRow = DataTable.Api().editForm.getRowSelected(dt, 'CLONE').line;
				DataTable.Api().editForm.openSaveDialog('CLONE', dt, idRow);
				break;
			case 'delete':
				// borramos todos los seleccionados.
				DataTable.Api().editForm.deleteAllSelects(dt);
				break;
		}
	});

	// Detecta el numero de filas seleccionadas y en funcion a eso muestra u oculta
	// los botones
	DataTable.Api.register('buttons.displayRegex()', function (ctx) {
		var opts = ctx._buttons[0].inst.s.buttons;
		var numOfSelectedRows = ctx.multiselection.numSelected;
		var collectionObject;
		$.each(opts, function (i) {
			collectionObject = null;
			_manageButtonsAndButtonsContextMenu(opts[i], numOfSelectedRows, collectionObject, ctx);
			// Comprueba si tiene botones hijos
			if (this.buttons.length > 0) {
				collectionObject = this;
				_manageButtonsAndButtonsContextMenu(opts[i], numOfSelectedRows, collectionObject, ctx);
			}
		});
	});

	/**
  * Get the file name for an exported file.
  *
  * @name _filename
  * @function
  * @since UDA 3.4.0 // Datatable 1.0.0
  *
  * @param {object}	config Button configuration
  * @param {boolean} incExtension Include the file name extension
  *
  */
	var _filename = function _filename(config) {
		// Backwards compatibility
		var filename = config.filename === '*' && config.title !== '*' && config.title !== undefined && config.title !== null && config.title !== '' ? config.title : config.filename;

		if (typeof filename === 'function') {
			filename = filename();
		}

		if (filename === undefined || filename === null) {
			return null;
		}

		if (filename.indexOf('*') !== -1) {
			filename = $.trim(filename.replace('*', $('head > title').text()));
		}

		// Strip characters which the OS will object to
		filename = filename.replace(/[^a-zA-Z0-9_\u00A1-\uFFFF\.,\-_ !\(\)]/g, "");

		var extension = _stringOrFunction(config.extension);
		if (!extension) {
			extension = '';
		}

		return filename + extension;
	};

	/**
  * Simply utility method to allow parameters to be given as a function
  *
  * @name _stringOrFunction
  * @function
  * @since UDA 3.4.0 // Datatable 1.0.0
  *
  * @param {undefined|string|function} option Option
  *
  * @return {null|string} Resolved value
  *
  */
	var _stringOrFunction = function _stringOrFunction(option) {
		if (option === null || option === undefined) {
			return null;
		} else if (typeof option === 'function') {
			return option();
		}
		return option;
	};

	/**
  * Get the title for an exported file.
  *
  * @name _title
  * @function
  * @since UDA 3.4.0 // Datatable 1.0.0
  *
  * @param {object} config	Button configuration
  *
  */
	var _title = function _title(config) {
		var title = _stringOrFunction(config.title);

		return title === null ? null : title.indexOf('*') !== -1 ? title.replace('*', $('head > title').text() || 'Exported data') : title;
	};

	var _message = function _message(dt, option, position) {
		var message = _stringOrFunction(option);
		if (message === null) {
			return null;
		}

		var caption = $('caption', dt.table().container()).eq(0);
		if (message === '*') {
			var side = caption.css('caption-side');
			if (side !== position) {
				return null;
			}

			return caption.length ? caption.text() : '';
		}

		return message;
	};

	var _exportTextarea = $('<textarea/>')[0];
	var _exportData = function _exportData(dt, inOpts) {
		var config = $.extend(true, {}, {
			rows: null,
			columns: '',
			modifier: {
				search: 'applied',
				order: 'applied'
			},
			orthogonal: 'display',
			stripHtml: true,
			stripNewlines: true,
			decodeEntities: true,
			trim: true,
			format: {
				header: function header(d) {
					return strip(d);
				},
				footer: function footer(d) {
					return strip(d);
				},
				body: function body(d) {
					return strip(d);
				}
			}
		}, inOpts);

		var strip = function strip(str) {
			if (typeof str !== 'string') {
				return str;
			}

			// Always remove script tags
			str = str.replace(/<script\b[^<]*(?:(?!<\/script>)<[^<]*)*<\/script>/gi, '');

			if (config.stripHtml) {
				str = str.replace(/<[^>]*>/g, '');
			}

			if (config.trim) {
				str = str.replace(/^\s+|\s+$/g, '');
			}

			if (config.stripNewlines) {
				str = str.replace(/\n/g, ' ');
			}

			if (config.decodeEntities) {
				_exportTextarea.innerHTML = str;
				str = _exportTextarea.value;
			}

			return str;
		};

		var header = dt.columns(config.columns).indexes().map(function (idx) {
			var el = dt.column(idx).header();
			return config.format.header(el.innerHTML, idx, el);
		}).toArray();

		var footer = dt.table().footer() ? dt.columns(config.columns).indexes().map(function (idx) {
			var el = dt.column(idx).footer();
			return config.format.footer(el ? el.innerHTML : '', idx, el);
		}).toArray() : null;

		// If Select is available on this table, and any rows are selected, limit the export
		// to the selected rows. If no rows are selected, all rows will be exported. Specify
		// a `selected` modifier to control directly.
		var modifier = $.extend({}, config.modifier);
		if (dt.select && typeof dt.select.info === 'function' && modifier.selected === undefined) {
			if (dt.rows(config.rows, $.extend({ selected: true }, modifier)).any()) {
				$.extend(modifier, { selected: true });
			}
		}

		var rowIndexes = dt.rows(config.rows, modifier).indexes().toArray();
		var selectedCells = dt.cells(rowIndexes, config.columns);
		var cells = selectedCells.render(config.orthogonal).toArray();
		var cellNodes = selectedCells.nodes().toArray();

		var columns = header.length;
		var rows = columns > 0 ? cells.length / columns : 0;
		var body = [rows];
		var cellCounter = 0;

		for (var i = 0, ien = rows; i < ien; i++) {
			var row = [columns];

			for (var j = 0; j < columns; j++) {
				row[j] = config.format.body(cells[cellCounter], i, j, cellNodes[cellCounter]);
				cellCounter++;
			}

			body[i] = row;
		}

		return {
			header: header,
			footer: footer,
			body: body
		};
	};

	/**
  * Activa la coleccion
  *
  * @name _enableCollection
  * @function
  * @since UDA 3.4.0 // Datatable 1.0.0
  *
  * @param {string} id	Id of the button
  *
  */
	var _enableCollection = function _enableCollection(id) {
		$('#' + id).removeClass('disabledDatatable');
	};

	/**
  * Desactiva la coleccion
  *
  * @name _disableCollection
  * @function
  * @since UDA 3.4.0 // Datatable 1.0.0
  *
  * @param {string} id	Id of the button
  *
  */
	var _disableCollection = function _disableCollection(id) {
		$('#' + id).addClass('disabledDatatable');
	};

	/**
  * Activa el boton y su opcion dentro del context menu
  *
  * @name _enableButtonAndContextMenuOption
  * @function
  * @since UDA 3.4.0 // Datatable 1.0.0
  *
  * @param {string} id	Id of the button
  *
  */
	var _enableButtonAndContextMenuOption = function _enableButtonAndContextMenuOption(id) {
		$('#' + id + ', #' + id + '_contextMenuToolbar').removeClass('disabledDatatable');
	};

	/**
  * Desactiva el boton y su opcion dentro del context menu
  *
  * @name _disableButtonAndContextMenuOption
  * @function
  * @since UDA 3.4.0 // Datatable 1.0.0
  *
  * @param {string} id	Id of the button
  *
  */
	var _disableButtonAndContextMenuOption = function _disableButtonAndContextMenuOption(id) {
		$('#' + id + '_contextMenuToolbar, #' + id).addClass('disabledDatatable');
	};

	/**
  * Gestiona la propiedad de activado/desactivado de los botones y de sus opciones
  * dentro del context menu.
  *
  * @name _manageButtonsAndButtonsContextMenu
  * @function
  * @since UDA 3.4.0 // Datatable 1.0.0
  *
  * @param {object} opts	Buttons properties
  * @param {int} numOfSelectedRows	Number of selected rows
  * @param {null|object} collectionObject	Collection button properties
  *
  */
	var _manageButtonsAndButtonsContextMenu = function _manageButtonsAndButtonsContextMenu(opts, numOfSelectedRows, collectionObject, ctx) {
		// Si pertenece a un collection o es un collection
		if (opts.collection !== null && collectionObject) {
			var collectionId = collectionObject.conf.id;
			var collectionDisplayRegex = collectionObject.conf.displayRegex;
			var alreadyExecuted = false;
			// Recorre todos los botones dentro del collection
			$.each(collectionObject.buttons, function (key, value) {
				// Activa/desactiva en funcion de la propiedad 'displayRegex' del padre y los hijos
				if (collectionDisplayRegex !== undefined && value.conf.displayRegex !== undefined) {
					if (collectionDisplayRegex.test(numOfSelectedRows) && value.conf.displayRegex.test(numOfSelectedRows)) {
						_enableButtonAndContextMenuOption(value.conf.id);
					} else {
						_disableButtonAndContextMenuOption(value.conf.id);
					}
				}
				// Activa/desactiva en funcion de la propiedad 'displayRegex' de sus hijos
				else if (collectionDisplayRegex === undefined && value.conf.displayRegex !== undefined) {
						// Habilita la coleccion si cumple el regex (solo se ejecuta una vez como
						// maximo gracias al booleano 'alreadyExecuted')
						if (value.conf.displayRegex.test(numOfSelectedRows) && !alreadyExecuted) {
							_enableCollection(collectionId);
							alreadyExecuted = true;
						}
						// Habilita el boton si cumple el displayRegex
						if (value.conf.displayRegex.test(numOfSelectedRows)) {
							_enableButtonAndContextMenuOption(value.conf.id);
						}
						// Como este boton no cumple el 'displayRegex' para ser habilitado, se deshabilitan
						// tanto el boton como su opcion en el contextMenu
						else {
								_disableButtonAndContextMenuOption(value.conf.id);
							}
						// En caso de que ningun regex cumpliese, se fuerza la deshabilitacion
						if (!alreadyExecuted) {
							_disableCollection(collectionId);
						}
					}
					// Desactiva todo si ni el collection ni los hijos tienen la propiedad 'displayRegex'
					// o simplemente si los hijos no tienen la propiedad
					else {
							_disableButtonAndContextMenuOption(value.conf.id);
							if (!alreadyExecuted) {
								_disableCollection(collectionId);
								alreadyExecuted = true;
							}
						}
			});
			// Genera un evento encargado de ocultar los botones dentro del collection.
			// Se comprueba mediante una clase si ya tiene o no el evento, mejorando asi
			// el rendimiento
			$('#' + collectionId + ':not(.listening)').addClass('listening').on('click', function (e) {
				// Se establece el valor de 'numOfSelectedRows' porque sino siempre tendria
				// el valor recibido cuando se creo el evento
				var numOfSelectedRows = ctx.multiselection.numSelected;
				$.each(collectionObject.buttons, function (key, value) {
					// Habilita el boton dentro del collection
					if (value.conf.displayRegex.test(numOfSelectedRows)) {
						_enableButtonAndContextMenuOption(value.conf.id);
					}
					// Deshabilita el boton dentro del collection
					else {
							_disableButtonAndContextMenuOption(value.conf.id);
						}
				});
			});
		}
		// Si el boton no tiene un regex definido, permanecera siempre desactivado
		else if (opts.conf.displayRegex === undefined) {
				// Deshabilita el boton y su opcion dentro del context menu
				_disableButtonAndContextMenuOption(opts.conf.id);
			}
			// Si tiene un regex definido, lo activa y desactiva en funcion de este
			else if (opts.conf.displayRegex !== undefined) {
					// Si el regex recibido de cada boton cumple la sentencia al probarlo contra
					// el numero de filas seleccionadas, se mostrara, en caso contrario, permanecera
					// oculto
					if (opts.conf.displayRegex.test(numOfSelectedRows)) {
						// Habilita el boton y su opcion dentro del context menu
						_enableButtonAndContextMenuOption(opts.conf.id);
					} else {
						// Deshabilita el boton y su opcion dentro del context menu
						_disableButtonAndContextMenuOption(opts.conf.id);
					}
				}
	};

	/**
 * Establece el tipo de llamada necesario para obtener los datos según lo seleccionado
 * e inicia la gestión para finalmente obtenerlos
 *
 * @name _reportsCopyData
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 *
 * @param {object} dt Instancia del datatable
 * @param {object} that Objeto del boton
 * @param {object} config Configuracion del boton
 *
 */
	var _reportsCopyData = function _reportsCopyData(dt, that, config) {
		var ctx = dt.settings()[0];
		var info = dt.buttons.exportInfo(config);
		var type;
		var multiselection = ctx.multiselection;
		var selectedAll = multiselection.selectedAll;
		var deselectedIds = multiselection.deselectedIds;

		if (selectedAll) {
			if (deselectedIds.length > 0) {
				// Este caso es para cuando se selecciona todo y despues se
				// deseleccionan algunos registros
				type = "all-deselected";
			} else {
				// Este caso es para cuando se seleccionan todos los registros
				type = "all";
			}
		} else {
			// Este caso para cuando hay determinados registros seleccionados manualmente
			type = "selected";
		}

		$.when(_reportsTypeOfCopy(dt, type, multiselection, selectedAll, deselectedIds)).then(function (exportData) {
			var exportDataRows = exportData.length;
			var exportDataParsed = JSON.stringify(exportData);

			var hiddenDiv = $('<div/>').css({
				height: 1,
				width: 1,
				overflow: 'hidden',
				position: 'fixed',
				top: 0,
				left: 0
			});

			exportDataParsed = _convertToTabulador(exportDataParsed, true);
			var textarea = $('<textarea readonly/>').val(exportDataParsed).appendTo(hiddenDiv);

			_reportsOpenMessage(dt, ctx, that, exportDataRows, hiddenDiv, textarea);
		});
	};

	/**
 * Se encarga de mapear los datos de json a datos separados por el tabulador.
 *
 * @name ConvertToTabulador
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 *
 * @param {object} objArray Objeto que contiene los datos a exportar
 * @param {boolean} true en caso de querer que se mueste la cabecera
 *
 * @return {object}
 *
 */
	var _convertToTabulador = function _convertToTabulador(objArray, showLabel) {
		var array = (typeof objArray === 'undefined' ? 'undefined' : _typeof(objArray)) !== 'object' ? JSON.parse(objArray) : objArray;
		var str = '';

		if (showLabel) {
			var row = "";

			// Se asignan los nombres de las columnas
			$.each(array[0], function (key, value) {
				// Comprobar si es un objeto, en caso afirmativo lo recorremos y lo concatenamos
				if ($.isPlainObject(value)) {
					var objectName = key;
					$.each(this, function (key, value) {
						var keyToCamelKeys = key.substring(0, 1).toLocaleUpperCase() + key.substring(1);
						row += objectName + keyToCamelKeys + ';';
					});
				} else {
					row += key + ';';
				}
			});
			row = row.slice(0, -1);
			str += row + '\r\n';
		}

		// Se asignan los valores
		$.each(array, function () {
			var line = '';
			$.each(this, function (key, value) {
				// Comprobar si es un objeto, en caso afirmativo lo recorremos y lo concatenamos
				if ($.isPlainObject(value)) {
					$.each(this, function (key, value) {
						line += value + ';';
					});
				} else {
					line += value + ';';
				}
			});
			line = line.slice(0, -1);
			str += line + '\r\n';
		});

		return str;
	};

	/**
 * Según el tipo de función de copia solicitada, realiza unas u otras comprobaciones
 * antes de solicitar los datos al servidor
 *
 * @name _reportsTypeOfCopy
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 *
 * @param {object} dt Instancia del datatable
 * @param {string} type Tipo de funcion de copia a ejecutar
 * @param {object} multiselection Propiedades de la multiseleccion
 * @param {boolean} selectedAll Cuando es true significa que todas las filas estan marcadas
 * @param {array} [deselectedIds] ID's de las filas deseleccionadas
 *
 * @return {object}
 *
 */
	var _reportsTypeOfCopy = function _reportsTypeOfCopy(dt, type, multiselection, selectedAll, deselectedIds) {
		var ctx = dt.settings()[0];
		var deferred = $.Deferred();
		var exportData;
		var selectedIds = multiselection.selectedIds;
		var selectedRows = multiselection.selectedRowsPerPage;
		var ajaxOptions = {};
		var urlAjax;
		var typeAjax;
		var contentTypeAjax = 'application/json';
		var dataTypeAjax = 'json';

		switch (type) {
			case 'selected':
				var localAccess = true;
				var exportData = [];

				// Comprueba si todos los valores seleccionados estan en la misma pagina
				$.each(selectedRows, function (key, value) {
					if (ctx.json.page != value.page) {
						localAccess = false;
						return false;
					}
				});
				if (localAccess) {
					// Puede acceder a los valores seleccionados localmente
					$.each(selectedRows, function (key, value) {
						var idPadre = value.id;
						$.each(ctx.json.rows, function (key, value) {
							if (DataTable.Api().rupTable.getIdPk(value) === idPadre) {
								exportData.push(value);
							}
						});
					});
					deferred.resolve(exportData);
				} else {
					// Accede a los datos mediante el servidor ya que se ha hecho uso de la paginacion
					// Parametros necesarios para configurar la llamada AJAX
					urlAjax = '/clipboardReport';
					typeAjax = 'POST';
					ajaxOptions = _reportsPrepareRequestData(ajaxOptions, urlAjax, typeAjax, contentTypeAjax, dataTypeAjax, ctx, selectedAll, deselectedIds, selectedIds);

					$.when(_reportsRequestData(ajaxOptions, ctx)).then(function (data) {
						exportData = data;
						deferred.resolve(exportData);
					});
				}
				break;
			case 'all':
				// Parametros necesarios para configurar la llamada AJAX
				typeAjax = 'GET';
				ajaxOptions = _reportsPrepareRequestData(ajaxOptions, urlAjax, typeAjax, contentTypeAjax, dataTypeAjax, ctx, selectedAll, deselectedIds, selectedIds);

				$.when(_reportsRequestData(ajaxOptions, ctx)).then(function (data) {
					ctx.ext.buttons.allData = data;
					exportData = ctx.ext.buttons.allData;
					deferred.resolve(exportData);
				});
				break;
			case 'all-deselected':
				// Parametros necesarios para configurar la llamada AJAX
				urlAjax = '/clipboardReport';
				typeAjax = 'POST';
				ajaxOptions = _reportsPrepareRequestData(ajaxOptions, urlAjax, typeAjax, contentTypeAjax, dataTypeAjax, ctx, selectedAll, deselectedIds, selectedIds);

				$.when(_reportsRequestData(ajaxOptions, ctx)).then(function (data) {
					exportData = data;
					deferred.resolve(exportData);
				});
				break;
		}

		return deferred.promise();
	};

	/**
 * Se encarga de generar las opciones de configuración con las que se llamara a la API
 *
 * @name _reportsPrepareRequestData
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 *
 * @param {object} ajaxOptions Parametros de la llamada Ajax
 * @param {string} urlAjax Parametro para la URL
 * @param {string} typeAjax Tipo de llamada a la API
 * @param {string} contentTypeAjax Formato de datos enviados
 * @param {string} dataTypeAjax Formato de datos esperados
 * @param {object} ctx Contexto
 * @param {boolean} selectedAll Cuando es true significa que todas las filas estan marcadas
 * @param {array} [deselectedIds] ID's de las filas deseleccionadas
 * @param {array} [selectedIds] ID's de las filas seleccionadas
 *
 * @return {object}
 *
 */
	var _reportsPrepareRequestData = function _reportsPrepareRequestData(ajaxOptions, urlAjax, typeAjax, contentTypeAjax, dataTypeAjax, ctx, selectedAll, deselectedIds, selectedIds) {
		var row = {};
		row.core = {
			'pkToken': ctx.oInit.multiplePkToken,
			'pkNames': ctx.oInit.primaryKey
		};
		row.multiselection = {};
		row.multiselection.selectedAll = selectedAll;
		if (row.multiselection.selectedAll) {
			row.multiselection.selectedIds = deselectedIds;
		} else {
			row.multiselection.selectedIds = selectedIds;
		}
		// Completa el objeto 'ajaxOptions' con los parametros necesarios para la
		// llamada que se realizara al servidor
		ajaxOptions.contentType = contentTypeAjax;
		ajaxOptions.dataType = dataTypeAjax;
		if (urlAjax !== undefined) {
			ajaxOptions.url = ctx.oInit.urlBase + urlAjax;
		} else {
			ajaxOptions.url = ctx.oInit.urlBase;
		}
		ajaxOptions.type = typeAjax;
		if (typeAjax === 'POST') {
			ajaxOptions.data = JSON.stringify(row);
		}

		return ajaxOptions;
	};

	/**
 * Se encarga de llamar a la API y de devolver los datos recibidos
 *
 * @name _reportsRequestData
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 *
 * @param {object} ajaxOptions Parametros de la llamada Ajax
 * @param {object} ctx Contexto
 *
 * @return {object}
 *
 */
	var _reportsRequestData = function _reportsRequestData(ajaxOptions, ctx) {
		var deferred = $.Deferred();
		$.ajax(ajaxOptions).done(function (data) {
			deferred.resolve(data);
			$('#' + ctx.sTableId).triggerHandler('tableButtonsSuccessReportsRequestData');
		}).complete(function () {
			$('#' + ctx.sTableId).triggerHandler('tableButtonsCompleteReportsRequestData');
		}).error(function () {
			$('#' + ctx.sTableId).triggerHandler('tableButtonsErrorReportsRequestData');
		});
		return deferred.promise();
	};

	/**
 * Gestiona la apertura/cierre del mensaje de confirmación de copia
 *
 * @name _reportsOpenMessage
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 *
 * @param {object} dt Instancia del datatable
 * @param {object} ctx Contexto
 * @param {object} that Objeto del boton
 * @param {int} exportDataRows Numero de filas a ser exportadas
 * @param {object} hiddenDiv Elemento del DOM
 * @param {object} textarea Elemento del DOM
 *
 */
	var _reportsOpenMessage = function _reportsOpenMessage(dt, ctx, that, exportDataRows, hiddenDiv, textarea) {
		$.rup_messages('msgConfirm', {
			title: dt.i18n('rup_datatable.copyButton.changes', 'Copia de registros en clipboard'),
			message: dt.i18n('rup_datatable.copyButton.saveAndContinue', {
				_: '¿Desea copiar %d registros?',
				1: '¿Desea copiar un registro?'
			}, exportDataRows),
			OKFunction: function OKFunction() {
				ctx.oInit.formEdit.okCallBack = true;
				_reportsCopyDataToClipboard(dt, that, exportDataRows, hiddenDiv, textarea);
				ctx.oInit.formEdit.detailForm.rup_dialog("close");
			},
			beforeClose: function beforeClose() {
				ctx.oInit.formEdit.okCallBack = false;
				// Si es llamado desde el contextMenu este paso es innecesario y la condicion
				// del if evita un error
				if (that.processing !== undefined) {
					that.processing(false);
				}
			}
		});
	};

	/**
 * Copia los datos recibidos al portapapeles
 *
 * @name _reportsCopyDataToClipboard
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 *
 * @param {object} dt Instancia del datatable
 * @param {object} that Objeto del boton
 * @param {int} exportDataRows Numero de filas a ser exportadas
 * @param {object} hiddenDiv Elemento del DOM
 * @param {object} textarea Elemento del DOM
 *
 */
	var _reportsCopyDataToClipboard = function _reportsCopyDataToClipboard(dt, that, exportDataRows, hiddenDiv, textarea) {
		// Para los navegadores que soportan el comando de copia 'execCommand'
		if (document.queryCommandSupported('copy')) {
			hiddenDiv.appendTo(dt.table().container());
			textarea[0].focus();
			textarea[0].select();

			try {
				var successful = document.execCommand('copy');
				hiddenDiv.remove();

				if (successful) {
					dt.buttons.info(dt.i18n('rup_datatable.copyButton.changes', 'Copia de registros en portapapeles'), dt.i18n('rup_datatable.copyButton.saved', {
						_: 'Copiados %d registros al portapapeles',
						1: 'Copiado un registro al portapapeles'
					}, exportDataRows), 2000);
					// Si es llamado desde el contextMenu este paso es innecesario y la condicion
					// del if evita un error
					if (that.processing !== undefined) {
						that.processing(false);
					}
					return;
				}
			} catch (t) {}
		}

		// Si no soportan la copia mediante 'execCommand', se mostrara un text box
		// con las instrucciones de como copiar los elementos seleccionados
		var message = $('<span>' + dt.i18n('rup_datatable.copyButton.copyKeys', 'Presiona ctrl o ⌘ + C para copiar los datos de la tabla al portapapeles.' + 'Para cancelar, haz click sobre este mensaje o pulsa el botón escape.') + '</span>').append(hiddenDiv);

		dt.buttons.info(dt.i18n('rup_datatable.copyButton.copyTitle', 'Copiar al portapapeles'), message, 0);

		// Selecciona el texto para cuando el usuario accione la copia al portapapeles
		// se le pegue ese texto
		textarea[0].focus();
		textarea[0].select();

		// Evento que oculta el mensaje cuando el usuario ha terminado con la copia
		var container = $(message).closest('.dt-button-info');
		var close = function close() {
			container.off('click.buttons-copy');
			$(document).off('.buttons-copy');
			dt.buttons.info(false);
			// Si es llamado desde el contextMenu este paso es innecesario y la condicion
			// del if evita un error
			if (that.processing !== undefined) {
				that.processing(false);
			}
		};

		container.on('click.buttons-copy', close);
		$(document).on('keydown.buttons-copy', function (e) {
			if (e.keyCode === 27) {
				// esc
				close();
			}
		}).on('copy.buttons-copy cut.buttons-copy', function () {
			close();
			// Si es llamado desde el contextMenu este paso es innecesario y la condicion
			// del if evita un error
			if (that.processing !== undefined) {
				that.processing(false);
			}
		});
	};

	/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  * DataTables interface
  */

	// Attach to DataTables objects for global access
	$.fn.dataTable.Buttons = Buttons;
	$.fn.DataTable.Buttons = Buttons;

	function inicio(ctx) {
		var opts = ctx._buttons[0].inst.s.buttons;
		var numOfSelectedRows = ctx.multiselection.numSelected;
		var collectionObject;

		$.each(opts, function (i) {
			// Activa/desactiva los botones en el inicio en funcion de la propiedad
			// 'displayRegex' que tengan asociada
			collectionObject = null;
			_manageButtonsAndButtonsContextMenu(opts[i], numOfSelectedRows, collectionObject, ctx);
			// Comprueba si tiene botones hijos
			if (this.buttons.length > 0) {
				collectionObject = this;
				_manageButtonsAndButtonsContextMenu(opts[i], numOfSelectedRows, collectionObject, ctx);
			}
			// Comprueba si tiene un icono asociado
			if (this.conf.icon !== undefined) {
				// Establece el icono de los botones
				$('#' + this.conf.id).prepend('<i class="fa ' + this.conf.icon + ' right-separator" aria-hidden="true"></i>');
				// Comprueba si tiene botones hijos
				if (this.buttons.length > 0 && $('#' + this.conf.id).length > 0) {
					// Añadimos un evento para cuando se pulse sobre el boton padre, se le
					// asignen los iconos a los hijos
					$('#' + this.conf.id)[0].addEventListener('click', function eventHandler() {
						var that = this;
						$.each(opts[i].buttons, function (i) {
							var selectorCollection = $('#' + this.conf.id);
							// Establece el icono de los botones hijos
							selectorCollection.prepend('<i class="fa ' + this.conf.icon + ' right-separator" aria-hidden="true"></i>');
							that.removeEventListener('click', eventHandler);
						});
					}, false);
				}
			}
		});

		// Detecta cuando se selecciona o se deselecciona una fila en el datatable
		$('#' + ctx.sTableId).DataTable().on('select deselect contextmenu', function (event) {
			DataTable.Api().buttons.displayRegex(ctx);
			if (event.type === 'contextmenu' && event.srcElement) {
				$(event.srcElement.parentElement).triggerHandler('tableButtonsOpenContextMenu');
			}
		});
	};

	// DataTables `dom` feature option
	DataTable.ext.feature.push({
		fnInit: function fnInit(settings) {
			var api = new DataTable.Api(settings);
			var opts = api.init().buttons || DataTable.defaults.buttons;

			return new Buttons(api, opts).container();
		},
		cFeature: "B"
	});

	//DataTables creation - check if the buttons have been defined for this table,
	//they will have been if the `B` option was used in `dom`, otherwise we should
	//create the buttons instance here so they can be inserted into the document
	//using the API. Listen for `init` for compatibility with pre 1.10.10, but to
	//be removed in future.
	$(document).on('plugin-init.dt', function (e, settings) {
		if (e.namespace !== 'dt') {
			return;
		}

		if (settings.oInit.buttons !== undefined && settings._buttons) {
			inicio(settings);
		}
	});

	return Buttons;
});

/***/ }),
/* 202 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;var _typeof = typeof Symbol === "function" && typeof Symbol.iterator === "symbol" ? function (obj) { return typeof obj; } : function (obj) { return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj; };

/*! ColReorder 1.4.1
 * ©2010-2017 SpryMedia Ltd - datatables.net/license
 */

/**
 * @summary     ColReorder
 * @description Provide the ability to reorder columns in a DataTable
 * @version     1.4.1
 * @file        rup.table.colReorder.js
 *  
 * @contact     www.sprymedia.co.uk/contact
 * @copyright   Copyright 2010-2017 SpryMedia Ltd.
 *
 * This source file is free software, available under the following license:
 *   MIT license - http://datatables.net/license/mit
 *
 * This source file is distributed in the hope that it will be useful, but
 * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
 * or FITNESS FOR A PARTICULAR PURPOSE. See the license files for details.
 *
 * For details please refer to: http://www.datatables.net
 */
(function (factory) {
	if (true) {
		// AMD
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(4)], __WEBPACK_AMD_DEFINE_RESULT__ = function ($) {
			return factory($, window, document);
		}.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else if ((typeof exports === 'undefined' ? 'undefined' : _typeof(exports)) === 'object') {
		// CommonJS
		module.exports = function (root, $) {
			if (!root) {
				root = window;
			}

			if (!$ || !$.fn.dataTable) {
				$ = require('datatables.net')(root, $).$;
			}

			return factory($, root, root.document);
		};
	} else {
		// Browser
		factory(jQuery, window, document);
	}
})(function ($, window, document, undefined) {
	'use strict';

	var DataTable = $.fn.dataTable;

	/**
  * Switch the key value pairing of an index array to be value key (i.e. the old value is now the
  * key). For example consider [ 2, 0, 1 ] this would be returned as [ 1, 2, 0 ].
  *  @method  fnInvertKeyValues
  *  @param   array aIn Array to switch around
  *  @returns array
  */
	function fnInvertKeyValues(aIn) {
		var aRet = [];
		for (var i = 0, iLen = aIn.length; i < iLen; i++) {
			aRet[aIn[i]] = i;
		}
		return aRet;
	}

	/**
  * Modify an array by switching the position of two elements
  *  @method  fnArraySwitch
  *  @param   array aArray Array to consider, will be modified by reference (i.e. no return)
  *  @param   int iFrom From point
  *  @param   int iTo Insert point
  *  @returns void
  */
	function fnArraySwitch(aArray, iFrom, iTo) {
		var mStore = aArray.splice(iFrom, 1)[0];
		aArray.splice(iTo, 0, mStore);
	}

	/**
  * Switch the positions of nodes in a parent node (note this is specifically designed for
  * table rows). Note this function considers all element nodes under the parent!
  *  @method  fnDomSwitch
  *  @param   string sTag Tag to consider
  *  @param   int iFrom Element to move
  *  @param   int Point to element the element to (before this point), can be null for append
  *  @returns void
  */
	function fnDomSwitch(nParent, iFrom, iTo) {
		var anTags = [];
		for (var i = 0, iLen = nParent.childNodes.length; i < iLen; i++) {
			if (nParent.childNodes[i].nodeType == 1) {
				anTags.push(nParent.childNodes[i]);
			}
		}
		var nStore = anTags[iFrom];

		if (iTo !== null) {
			nParent.insertBefore(nStore, anTags[iTo]);
		} else {
			nParent.appendChild(nStore);
		}
	}

	/**
  * Plug-in for DataTables which will reorder the internal column structure by taking the column
  * from one position (iFrom) and insert it into a given point (iTo).
  *  @method  $.fn.dataTableExt.oApi.fnColReorder
  *  @param   object oSettings DataTables settings object - automatically added by DataTables!
  *  @param   int iFrom Take the column to be repositioned from this point
  *  @param   int iTo and insert it into this point
  *  @param   bool drop Indicate if the reorder is the final one (i.e. a drop)
  *    not a live reorder
  *  @param   bool invalidateRows speeds up processing if false passed
  *  @returns void
  */
	$.fn.dataTableExt.oApi.fnColReorder = function (oSettings, iFrom, iTo, drop, invalidateRows) {
		var i,
		    iLen,
		    j,
		    jLen,
		    jen,
		    iCols = oSettings.aoColumns.length,
		    nTrs,
		    oCol;
		var attrMap = function attrMap(obj, prop, mapping) {
			if (!obj[prop] || typeof obj[prop] === 'function') {
				return;
			}

			var a = obj[prop].split('.');
			var num = a.shift();

			if (isNaN(num * 1)) {
				return;
			}

			obj[prop] = mapping[num * 1] + '.' + a.join('.');
		};

		/* Sanity check in the input */
		if (iFrom == iTo) {
			/* Pointless reorder */
			return;
		}

		if (iFrom < 0 || iFrom >= iCols) {
			this.oApi._fnLog(oSettings, 1, "ColReorder 'from' index is out of bounds: " + iFrom);
			return;
		}

		if (iTo < 0 || iTo >= iCols) {
			this.oApi._fnLog(oSettings, 1, "ColReorder 'to' index is out of bounds: " + iTo);
			return;
		}

		/*
   * Calculate the new column array index, so we have a mapping between the old and new
   */
		var aiMapping = [];
		for (i = 0, iLen = iCols; i < iLen; i++) {
			aiMapping[i] = i;
		}
		fnArraySwitch(aiMapping, iFrom, iTo);
		var aiInvertMapping = fnInvertKeyValues(aiMapping);

		/*
   * Convert all internal indexing to the new column order indexes
   */
		/* Sorting */
		for (i = 0, iLen = oSettings.aaSorting.length; i < iLen; i++) {
			oSettings.aaSorting[i][0] = aiInvertMapping[oSettings.aaSorting[i][0]];
		}

		/* Fixed sorting */
		if (oSettings.aaSortingFixed !== null) {
			for (i = 0, iLen = oSettings.aaSortingFixed.length; i < iLen; i++) {
				oSettings.aaSortingFixed[i][0] = aiInvertMapping[oSettings.aaSortingFixed[i][0]];
			}
		}

		/* Data column sorting (the column which the sort for a given column should take place on) */
		for (i = 0, iLen = iCols; i < iLen; i++) {
			oCol = oSettings.aoColumns[i];
			for (j = 0, jLen = oCol.aDataSort.length; j < jLen; j++) {
				oCol.aDataSort[j] = aiInvertMapping[oCol.aDataSort[j]];
			}

			// Update the column indexes
			oCol.idx = aiInvertMapping[oCol.idx];
		}

		// Update 1.10 optimised sort class removal variable
		$.each(oSettings.aLastSort, function (i, val) {
			oSettings.aLastSort[i].src = aiInvertMapping[val.src];
		});

		/* Update the Get and Set functions for each column */
		for (i = 0, iLen = iCols; i < iLen; i++) {
			oCol = oSettings.aoColumns[i];

			if (typeof oCol.mData == 'number') {
				oCol.mData = aiInvertMapping[oCol.mData];
			} else if ($.isPlainObject(oCol.mData)) {
				// HTML5 data sourced
				attrMap(oCol.mData, '_', aiInvertMapping);
				attrMap(oCol.mData, 'filter', aiInvertMapping);
				attrMap(oCol.mData, 'sort', aiInvertMapping);
				attrMap(oCol.mData, 'type', aiInvertMapping);
			}
		}

		/*
   * Move the DOM elements
   */
		if (oSettings.aoColumns[iFrom].bVisible) {
			/* Calculate the current visible index and the point to insert the node before. The insert
    * before needs to take into account that there might not be an element to insert before,
    * in which case it will be null, and an appendChild should be used
    */
			var iVisibleIndex = this.oApi._fnColumnIndexToVisible(oSettings, iFrom);
			var iInsertBeforeIndex = null;

			i = iTo < iFrom ? iTo : iTo + 1;
			while (iInsertBeforeIndex === null && i < iCols) {
				iInsertBeforeIndex = this.oApi._fnColumnIndexToVisible(oSettings, i);
				i++;
			}

			/* Header */
			nTrs = oSettings.nTHead.getElementsByTagName('tr');
			for (i = 0, iLen = nTrs.length; i < iLen; i++) {
				fnDomSwitch(nTrs[i], iVisibleIndex, iInsertBeforeIndex);
			}

			/* Footer */
			if (oSettings.nTFoot !== null) {
				nTrs = oSettings.nTFoot.getElementsByTagName('tr');
				//Se empieza siempre a partir del segundo tr que lleva el filtro.
				for (i = 1, iLen = nTrs.length; i < iLen; i++) {
					fnDomSwitch(nTrs[i], iVisibleIndex, iInsertBeforeIndex);
				}
			}

			/* Body */
			for (i = 0, iLen = oSettings.aoData.length; i < iLen; i++) {
				if (oSettings.aoData[i].nTr !== null) {
					fnDomSwitch(oSettings.aoData[i].nTr, iVisibleIndex, iInsertBeforeIndex);
				}
			}
		}

		/*
   * Move the internal array elements
   */
		/* Columns */
		fnArraySwitch(oSettings.aoColumns, iFrom, iTo);

		// regenerate the get / set functions
		for (i = 0, iLen = iCols; i < iLen; i++) {
			oSettings.oApi._fnColumnOptions(oSettings, i, {});
		}

		/* Search columns */
		fnArraySwitch(oSettings.aoPreSearchCols, iFrom, iTo);

		/* Array array - internal data anodes cache */
		for (i = 0, iLen = oSettings.aoData.length; i < iLen; i++) {
			var data = oSettings.aoData[i];
			var cells = data.anCells;

			if (cells) {
				fnArraySwitch(cells, iFrom, iTo);

				// Longer term, should this be moved into the DataTables' invalidate
				// methods?
				for (j = 0, jen = cells.length; j < jen; j++) {
					if (cells[j] && cells[j]._DT_CellIndex) {
						cells[j]._DT_CellIndex.column = j;
					}
				}
			}

			// For DOM sourced data, the invalidate will reread the cell into
			// the data array, but for data sources as an array, they need to
			// be flipped
			if (data.src !== 'dom' && $.isArray(data._aData)) {
				fnArraySwitch(data._aData, iFrom, iTo);
			}
		}

		/* Reposition the header elements in the header layout array */
		for (i = 0, iLen = oSettings.aoHeader.length; i < iLen; i++) {
			fnArraySwitch(oSettings.aoHeader[i], iFrom, iTo);
		}

		if (oSettings.aoFooter !== null) {
			for (i = 0, iLen = oSettings.aoFooter.length; i < iLen; i++) {
				fnArraySwitch(oSettings.aoFooter[i], iFrom, iTo);
			}
		}

		if (invalidateRows || invalidateRows === undefined) {
			$.fn.dataTable.Api(oSettings).rows().invalidate();
		}

		/*
   * Update DataTables' event handlers
   */

		/* Sort listener */
		for (i = 0, iLen = iCols; i < iLen; i++) {
			$(oSettings.aoColumns[i].nTh).off('click.DT');
			this.oApi._fnSortAttachListener(oSettings, oSettings.aoColumns[i].nTh, i);
		}

		/* Fire an event so other plug-ins can update */
		$(oSettings.oInstance).trigger('column-reorder.dt', [oSettings, {
			from: iFrom,
			to: iTo,
			mapping: aiInvertMapping,
			drop: drop,

			// Old style parameters for compatibility
			iFrom: iFrom,
			iTo: iTo,
			aiInvertMapping: aiInvertMapping
		}]);
	};

	/**
  * ColReorder provides column visibility control for DataTables
  * @class ColReorder
  * @constructor
  * @param {object} dt DataTables settings object
  * @param {object} opts ColReorder options
  */
	var ColReorder = function ColReorder(dt, opts) {
		var settings = new $.fn.dataTable.Api(dt).settings()[0];

		// Ensure that we can't initialise on the same table twice
		if (settings._colReorder) {
			return settings._colReorder;
		}

		// Allow the options to be a boolean for defaults
		if (opts === true) {
			opts = {};
		}

		// Convert from camelCase to Hungarian, just as DataTables does
		var camelToHungarian = $.fn.dataTable.camelToHungarian;
		if (camelToHungarian) {
			camelToHungarian(ColReorder.defaults, ColReorder.defaults, true);
			camelToHungarian(ColReorder.defaults, opts || {});
		}

		/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
   * Public class variables
   * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */

		/**
   * @namespace Settings object which contains customisable information for ColReorder instance
   */
		this.s = {
			/**
    * DataTables settings object
    *  @property dt
    *  @type     Object
    *  @default  null
    */
			"dt": null,

			/**
    * Initialisation object used for this instance
    *  @property init
    *  @type     object
    *  @default  {}
    */
			"init": $.extend(true, {}, ColReorder.defaults, opts),

			/**
    * Number of columns to fix (not allow to be reordered)
    *  @property fixed
    *  @type     int
    *  @default  0
    */
			"fixed": 0,

			/**
    * Number of columns to fix counting from right (not allow to be reordered)
    *  @property fixedRight
    *  @type     int
    *  @default  0
    */
			"fixedRight": 0,

			/**
    * Callback function for once the reorder has been done
    *  @property reorderCallback
    *  @type     function
    *  @default  null
    */
			"reorderCallback": null,

			/**
    * @namespace Information used for the mouse drag
    */
			"mouse": {
				"startX": -1,
				"startY": -1,
				"offsetX": -1,
				"offsetY": -1,
				"target": -1,
				"targetIndex": -1,
				"fromIndex": -1
			},

			/**
    * Information which is used for positioning the insert cusor and knowing where to do the
    * insert. Array of objects with the properties:
    *   x: x-axis position
    *   to: insert point
    *  @property aoTargets
    *  @type     array
    *  @default  []
    */
			"aoTargets": []
		};

		/**
   * @namespace Common and useful DOM elements for the class instance
   */
		this.dom = {
			/**
    * Dragging element (the one the mouse is moving)
    *  @property drag
    *  @type     element
    *  @default  null
    */
			"drag": null,

			/**
    * The insert cursor
    *  @property pointer
    *  @type     element
    *  @default  null
    */
			"pointer": null
		};

		/* Constructor logic */
		this.s.dt = settings;
		this.s.dt._colReorder = this;
		this._fnConstruct();

		return this;
	};

	$.extend(ColReorder.prototype, {
		/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
   * Public methods
   * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */

		/**
   * Reset the column ordering to the original ordering that was detected on
   * start up.
   *  @return {this} Returns `this` for chaining.
   *
   *  @example
   *    // DataTables initialisation with ColReorder
   *    var table = $('#example').dataTable( {
   *        "sDom": 'Rlfrtip'
   *    } );
   *
   *    // Add click event to a button to reset the ordering
   *    $('#resetOrdering').click( function (e) {
   *        e.preventDefault();
   *        $.fn.dataTable.ColReorder( table ).fnReset();
   *    } );
   */
		"fnReset": function fnReset() {
			this._fnOrderColumns(this.fnOrder());

			return this;
		},

		/**
   * `Deprecated` - Get the current order of the columns, as an array.
   *  @return {array} Array of column identifiers
   *  @deprecated `fnOrder` should be used in preference to this method.
   *      `fnOrder` acts as a getter/setter.
   */
		"fnGetCurrentOrder": function fnGetCurrentOrder() {
			return this.fnOrder();
		},

		/**
   * Get the current order of the columns, as an array. Note that the values
   * given in the array are unique identifiers for each column. Currently
   * these are the original ordering of the columns that was detected on
   * start up, but this could potentially change in future.
   *  @return {array} Array of column identifiers
   *
   *  @example
   *    // Get column ordering for the table
   *    var order = $.fn.dataTable.ColReorder( dataTable ).fnOrder();
   */ /**
      * Set the order of the columns, from the positions identified in the
      * ordering array given. Note that ColReorder takes a brute force approach
      * to reordering, so it is possible multiple reordering events will occur
      * before the final order is settled upon.
      *  @param {array} [set] Array of column identifiers in the new order. Note
      *    that every column must be included, uniquely, in this array.
      *  @return {this} Returns `this` for chaining.
      *
      *  @example
      *    // Swap the first and second columns
      *    $.fn.dataTable.ColReorder( dataTable ).fnOrder( [1, 0, 2, 3, 4] );
      *
      *  @example
      *    // Move the first column to the end for the table `#example`
      *    var curr = $.fn.dataTable.ColReorder( '#example' ).fnOrder();
      *    var first = curr.shift();
      *    curr.push( first );
      *    $.fn.dataTable.ColReorder( '#example' ).fnOrder( curr );
      *
      *  @example
      *    // Reverse the table's order
      *    $.fn.dataTable.ColReorder( '#example' ).fnOrder(
      *      $.fn.dataTable.ColReorder( '#example' ).fnOrder().reverse()
      *    );
      */
		"fnOrder": function fnOrder(set, original) {
			var a = [],
			    i,
			    ien,
			    j,
			    jen;
			var columns = this.s.dt.aoColumns;

			if (set === undefined) {
				for (i = 0, ien = columns.length; i < ien; i++) {
					a.push(columns[i]._ColReorder_iOrigCol);
				}

				return a;
			}

			// The order given is based on the original indexes, rather than the
			// existing ones, so we need to translate from the original to current
			// before then doing the order
			if (original) {
				var order = this.fnOrder();

				for (i = 0, ien = set.length; i < ien; i++) {
					a.push($.inArray(set[i], order));
				}

				set = a;
			}

			this._fnOrderColumns(fnInvertKeyValues(set));

			return this;
		},

		/**
   * Convert from the original column index, to the original
   *
   * @param  {int|array} idx Index(es) to convert
   * @param  {string} dir Transpose direction - `fromOriginal` / `toCurrent`
   *   or `'toOriginal` / `fromCurrent`
   * @return {int|array}     Converted values
   */
		fnTranspose: function fnTranspose(idx, dir) {
			if (!dir) {
				dir = 'toCurrent';
			}

			var order = this.fnOrder();
			var columns = this.s.dt.aoColumns;

			if (dir === 'toCurrent') {
				// Given an original index, want the current
				return !$.isArray(idx) ? $.inArray(idx, order) : $.map(idx, function (index) {
					return $.inArray(index, order);
				});
			} else {
				// Given a current index, want the original
				return !$.isArray(idx) ? columns[idx]._ColReorder_iOrigCol : $.map(idx, function (index) {
					return columns[index]._ColReorder_iOrigCol;
				});
			}
		},

		/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
   * Private methods (they are of course public in JS, but recommended as private)
   * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */

		/**
   * Constructor logic
   *  @method  _fnConstruct
   *  @returns void
   *  @private
   */
		"_fnConstruct": function _fnConstruct() {
			var that = this;
			var iLen = this.s.dt.aoColumns.length;
			var table = this.s.dt.nTable;
			var i;

			/* Columns discounted from reordering - counting left to right */
			if (this.s.init.iFixedColumns) {
				this.s.fixed = this.s.init.iFixedColumns;
			}

			if (this.s.init.iFixedColumnsLeft) {
				this.s.fixed = this.s.init.iFixedColumnsLeft;
			}

			/* Columns discounted from reordering - counting right to left */
			this.s.fixedRight = this.s.init.iFixedColumnsRight ? this.s.init.iFixedColumnsRight : 0;

			/* Drop callback initialisation option */
			if (this.s.init.fnReorderCallback) {
				this.s.reorderCallback = this.s.init.fnReorderCallback;
			}

			/* Add event handlers for the drag and drop, and also mark the original column order */
			for (i = 0; i < iLen; i++) {
				if (i > this.s.fixed - 1 && i < iLen - this.s.fixedRight) {
					this._fnMouseListener(i, this.s.dt.aoColumns[i].nTh);
				}

				/* Mark the original column order for later reference */
				this.s.dt.aoColumns[i]._ColReorder_iOrigCol = i;
			}

			/* State saving */
			this.s.dt.oApi._fnCallbackReg(this.s.dt, 'aoStateSaveParams', function (oS, oData) {
				that._fnStateSave.call(that, oData);
			}, "ColReorder_State");

			/* An initial column order has been specified */
			var aiOrder = null;
			if (this.s.init.aiOrder) {
				aiOrder = this.s.init.aiOrder.slice();
			}

			/* State loading, overrides the column order given */
			if (this.s.dt.oLoadedState && typeof this.s.dt.oLoadedState.ColReorder != 'undefined' && this.s.dt.oLoadedState.ColReorder.length == this.s.dt.aoColumns.length) {
				aiOrder = this.s.dt.oLoadedState.ColReorder;
			}

			/* If we have an order to apply - do so */
			if (aiOrder) {
				/* We might be called during or after the DataTables initialisation. If before, then we need
     * to wait until the draw is done, if after, then do what we need to do right away
     */
				if (!that.s.dt._bInitComplete) {
					var bDone = false;
					$(table).on('draw.dt.colReorder', function () {
						if (!that.s.dt._bInitComplete && !bDone) {
							bDone = true;
							var resort = fnInvertKeyValues(aiOrder);
							that._fnOrderColumns.call(that, resort);
						}
					});
				} else {
					var resort = fnInvertKeyValues(aiOrder);
					that._fnOrderColumns.call(that, resort);
				}
			} else {
				this._fnSetColumnIndexes();
			}

			// Destroy clean up
			$(table).on('destroy.dt.colReorder', function () {
				$(table).off('destroy.dt.colReorder draw.dt.colReorder');
				$(that.s.dt.nTHead).find('*').off('.ColReorder');

				$.each(that.s.dt.aoColumns, function (i, column) {
					$(column.nTh).removeAttr('data-column-index');
				});

				that.s.dt._colReorder = null;
				that.s = null;
			});
		},

		/**
   * Set the column order from an array
   *  @method  _fnOrderColumns
   *  @param   array a An array of integers which dictate the column order that should be applied
   *  @returns void
   *  @private
   */
		"_fnOrderColumns": function _fnOrderColumns(a) {
			var changed = false;

			if (a.length != this.s.dt.aoColumns.length) {
				this.s.dt.oInstance.oApi._fnLog(this.s.dt, 1, "ColReorder - array reorder does not " + "match known number of columns. Skipping.");
				return;
			}

			for (var i = 0, iLen = a.length; i < iLen; i++) {
				var currIndex = $.inArray(i, a);
				if (i != currIndex) {
					/* Reorder our switching array */
					fnArraySwitch(a, currIndex, i);

					/* Do the column reorder in the table */
					this.s.dt.oInstance.fnColReorder(currIndex, i, true, false);

					changed = true;
				}
			}

			$.fn.dataTable.Api(this.s.dt).rows().invalidate();

			this._fnSetColumnIndexes();

			// Has anything actually changed? If not, then nothing else to do
			if (!changed) {
				return;
			}

			/* When scrolling we need to recalculate the column sizes to allow for the shift */
			if (this.s.dt.oScroll.sX !== "" || this.s.dt.oScroll.sY !== "") {
				this.s.dt.oInstance.fnAdjustColumnSizing(false);
			}

			/* Save the state */
			this.s.dt.oInstance.oApi._fnSaveState(this.s.dt);

			if (this.s.reorderCallback !== null) {
				this.s.reorderCallback.call(this);
			}
		},

		/**
   * Because we change the indexes of columns in the table, relative to their starting point
   * we need to reorder the state columns to what they are at the starting point so we can
   * then rearrange them again on state load!
   *  @method  _fnStateSave
   *  @param   object oState DataTables state
   *  @returns string JSON encoded cookie string for DataTables
   *  @private
   */
		"_fnStateSave": function _fnStateSave(oState) {
			var i, iLen, aCopy, iOrigColumn;
			var oSettings = this.s.dt;
			var columns = oSettings.aoColumns;

			oState.ColReorder = [];

			/* Sorting */
			if (oState.aaSorting) {
				// 1.10.0-
				for (i = 0; i < oState.aaSorting.length; i++) {
					oState.aaSorting[i][0] = columns[oState.aaSorting[i][0]]._ColReorder_iOrigCol;
				}

				var aSearchCopy = $.extend(true, [], oState.aoSearchCols);

				for (i = 0, iLen = columns.length; i < iLen; i++) {
					iOrigColumn = columns[i]._ColReorder_iOrigCol;

					/* Column filter */
					oState.aoSearchCols[iOrigColumn] = aSearchCopy[i];

					/* Visibility */
					oState.abVisCols[iOrigColumn] = columns[i].bVisible;

					/* Column reordering */
					oState.ColReorder.push(iOrigColumn);
				}
			} else if (oState.order) {
				// 1.10.1+
				for (i = 0; i < oState.order.length; i++) {
					oState.order[i][0] = columns[oState.order[i][0]]._ColReorder_iOrigCol;
				}

				var stateColumnsCopy = $.extend(true, [], oState.columns);

				for (i = 0, iLen = columns.length; i < iLen; i++) {
					iOrigColumn = columns[i]._ColReorder_iOrigCol;

					/* Columns */
					oState.columns[iOrigColumn] = stateColumnsCopy[i];

					/* Column reordering */
					oState.ColReorder.push(iOrigColumn);
				}
			}
		},

		/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
   * Mouse drop and drag
   */

		/**
   * Add a mouse down listener to a particluar TH element
   *  @method  _fnMouseListener
   *  @param   int i Column index
   *  @param   element nTh TH element clicked on
   *  @returns void
   *  @private
   */
		"_fnMouseListener": function _fnMouseListener(i, nTh) {
			var that = this;
			$(nTh).on('mousedown.ColReorder', function (e) {
				that._fnMouseDown.call(that, e, nTh);
			}).on('touchstart.ColReorder', function (e) {
				that._fnMouseDown.call(that, e, nTh);
			});
		},

		/**
   * Mouse down on a TH element in the table header
   *  @method  _fnMouseDown
   *  @param   event e Mouse event
   *  @param   element nTh TH element to be dragged
   *  @returns void
   *  @private
   */
		"_fnMouseDown": function _fnMouseDown(e, nTh) {
			var that = this;

			/* Store information about the mouse position */
			var target = $(e.target).closest('th, td');
			var offset = target.offset();
			var idx = parseInt($(nTh).attr('data-column-index'), 10);

			if (idx === undefined) {
				return;
			}

			this.s.mouse.startX = this._fnCursorPosition(e, 'pageX');
			this.s.mouse.startY = this._fnCursorPosition(e, 'pageY');
			this.s.mouse.offsetX = this._fnCursorPosition(e, 'pageX') - offset.left;
			this.s.mouse.offsetY = this._fnCursorPosition(e, 'pageY') - offset.top;
			this.s.mouse.target = this.s.dt.aoColumns[idx].nTh; //target[0];
			this.s.mouse.targetIndex = idx;
			this.s.mouse.fromIndex = idx;

			this._fnRegions();

			/* Add event handlers to the document */
			$(document).on('mousemove.ColReorder touchmove.ColReorder', function (e) {
				that._fnMouseMove.call(that, e);
			}).on('mouseup.ColReorder touchend.ColReorder', function (e) {
				that._fnMouseUp.call(that, e);
			});
		},

		/**
   * Deal with a mouse move event while dragging a node
   *  @method  _fnMouseMove
   *  @param   event e Mouse event
   *  @returns void
   *  @private
   */
		"_fnMouseMove": function _fnMouseMove(e) {
			var that = this;

			if (this.dom.drag === null) {
				/* Only create the drag element if the mouse has moved a specific distance from the start
     * point - this allows the user to make small mouse movements when sorting and not have a
     * possibly confusing drag element showing up
     */
				if (Math.pow(Math.pow(this._fnCursorPosition(e, 'pageX') - this.s.mouse.startX, 2) + Math.pow(this._fnCursorPosition(e, 'pageY') - this.s.mouse.startY, 2), 0.5) < 5) {
					return;
				}
				this._fnCreateDragNode();
			}

			/* Position the element - we respect where in the element the click occured */
			this.dom.drag.css({
				left: this._fnCursorPosition(e, 'pageX') - this.s.mouse.offsetX,
				top: this._fnCursorPosition(e, 'pageY') - this.s.mouse.offsetY
			});

			/* Based on the current mouse position, calculate where the insert should go */
			var bSet = false;
			var lastToIndex = this.s.mouse.toIndex;

			for (var i = 1, iLen = this.s.aoTargets.length; i < iLen; i++) {
				if (this._fnCursorPosition(e, 'pageX') < this.s.aoTargets[i - 1].x + (this.s.aoTargets[i].x - this.s.aoTargets[i - 1].x) / 2) {
					this.dom.pointer.css('left', this.s.aoTargets[i - 1].x);
					this.s.mouse.toIndex = this.s.aoTargets[i - 1].to;
					bSet = true;
					break;
				}
			}

			// The insert element wasn't positioned in the array (less than
			// operator), so we put it at the end
			if (!bSet) {
				this.dom.pointer.css('left', this.s.aoTargets[this.s.aoTargets.length - 1].x);
				this.s.mouse.toIndex = this.s.aoTargets[this.s.aoTargets.length - 1].to;
			}

			// Perform reordering if realtime updating is on and the column has moved
			if (this.s.init.bRealtime && lastToIndex !== this.s.mouse.toIndex) {
				this.s.dt.oInstance.fnColReorder(this.s.mouse.fromIndex, this.s.mouse.toIndex, false);
				this.s.mouse.fromIndex = this.s.mouse.toIndex;
				this._fnRegions();
			}
		},

		/**
   * Finish off the mouse drag and insert the column where needed
   *  @method  _fnMouseUp
   *  @param   event e Mouse event
   *  @returns void
   *  @private
   */
		"_fnMouseUp": function _fnMouseUp(e) {
			var that = this;

			$(document).off('.ColReorder');

			if (this.dom.drag !== null) {
				/* Remove the guide elements */
				this.dom.drag.remove();
				this.dom.pointer.remove();
				this.dom.drag = null;
				this.dom.pointer = null;

				/* Actually do the reorder */
				this.s.dt.oInstance.fnColReorder(this.s.mouse.fromIndex, this.s.mouse.toIndex, true);
				this._fnSetColumnIndexes();

				/* When scrolling we need to recalculate the column sizes to allow for the shift */
				if (this.s.dt.oScroll.sX !== "" || this.s.dt.oScroll.sY !== "") {
					this.s.dt.oInstance.fnAdjustColumnSizing(false);
				}

				/* Save the state */
				this.s.dt.oInstance.oApi._fnSaveState(this.s.dt);

				if (this.s.reorderCallback !== null) {
					this.s.reorderCallback.call(this);
				}
			}
		},

		/**
   * Calculate a cached array with the points of the column inserts, and the
   * 'to' points
   *  @method  _fnRegions
   *  @returns void
   *  @private
   */
		"_fnRegions": function _fnRegions() {
			var aoColumns = this.s.dt.aoColumns;

			this.s.aoTargets.splice(0, this.s.aoTargets.length);

			this.s.aoTargets.push({
				"x": $(this.s.dt.nTable).offset().left,
				"to": 0
			});

			var iToPoint = 0;
			var total = this.s.aoTargets[0].x;

			for (var i = 0, iLen = aoColumns.length; i < iLen; i++) {
				/* For the column / header in question, we want it's position to remain the same if the
     * position is just to it's immediate left or right, so we only increment the counter for
     * other columns
     */
				if (i != this.s.mouse.fromIndex) {
					iToPoint++;
				}

				if (aoColumns[i].bVisible && aoColumns[i].nTh.style.display !== 'none') {
					total += $(aoColumns[i].nTh).outerWidth();

					this.s.aoTargets.push({
						"x": total,
						"to": iToPoint
					});
				}
			}

			/* Disallow columns for being reordered by drag and drop, counting right to left */
			if (this.s.fixedRight !== 0) {
				this.s.aoTargets.splice(this.s.aoTargets.length - this.s.fixedRight);
			}

			/* Disallow columns for being reordered by drag and drop, counting left to right */
			if (this.s.fixed !== 0) {
				this.s.aoTargets.splice(0, this.s.fixed);
			}
		},

		/**
   * Copy the TH element that is being drags so the user has the idea that they are actually
   * moving it around the page.
   *  @method  _fnCreateDragNode
   *  @returns void
   *  @private
   */
		"_fnCreateDragNode": function _fnCreateDragNode() {
			var scrolling = this.s.dt.oScroll.sX !== "" || this.s.dt.oScroll.sY !== "";

			var origCell = this.s.dt.aoColumns[this.s.mouse.targetIndex].nTh;
			var origTr = origCell.parentNode;
			var origThead = origTr.parentNode;
			var origTable = origThead.parentNode;
			var cloneCell = $(origCell).clone();

			// This is a slightly odd combination of jQuery and DOM, but it is the
			// fastest and least resource intensive way I could think of cloning
			// the table with just a single header cell in it.
			this.dom.drag = $(origTable.cloneNode(false)).addClass('DTCR_clonedTable').append($(origThead.cloneNode(false)).append($(origTr.cloneNode(false)).append(cloneCell[0]))).css({
				position: 'absolute',
				top: 0,
				left: 0,
				width: $(origCell).outerWidth(),
				height: $(origCell).outerHeight()
			}).appendTo('body');

			this.dom.pointer = $('<div></div>').addClass('DTCR_pointer').css({
				position: 'absolute',
				top: scrolling ? $('div.dataTables_scroll', this.s.dt.nTableWrapper).offset().top : $(this.s.dt.nTable).offset().top,
				height: scrolling ? $('div.dataTables_scroll', this.s.dt.nTableWrapper).height() : $(this.s.dt.nTable).height()
			}).appendTo('body');
		},

		/**
   * Add a data attribute to the column headers, so we know the index of
   * the row to be reordered. This allows fast detection of the index, and
   * for this plug-in to work with FixedHeader which clones the nodes.
   *  @private
   */
		"_fnSetColumnIndexes": function _fnSetColumnIndexes() {
			$.each(this.s.dt.aoColumns, function (i, column) {
				$(column.nTh).attr('data-column-index', i);
			});
		},

		/**
   * Get cursor position regardless of mouse or touch input
   * @param  {Event}  e    jQuery Event
   * @param  {string} prop Property to get
   * @return {number}      Value
   */
		_fnCursorPosition: function _fnCursorPosition(e, prop) {
			if (e.type.indexOf('touch') !== -1) {
				return e.originalEvent.touches[0][prop];
			}
			return e[prop];
		}
	});

	/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  * Static parameters
  * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */

	/**
  * ColReorder default settings for initialisation
  *  @namespace
  *  @static
  */
	ColReorder.defaults = {
		/**
   * Predefined ordering for the columns that will be applied automatically
   * on initialisation. If not specified then the order that the columns are
   * found to be in the HTML is the order used.
   *  @type array
   *  @default null
   *  @static
   */
		aiOrder: null,

		/**
   * Redraw the table's column ordering as the end user draws the column
   * (`true`) or wait until the mouse is released (`false` - default). Note
   * that this will perform a redraw on each reordering, which involves an
   * Ajax request each time if you are using server-side processing in
   * DataTables.
   *  @type boolean
   *  @default false
   *  @static
   */
		bRealtime: true,

		/**
   * Indicate how many columns should be fixed in position (counting from the
   * left). This will typically be 1 if used, but can be as high as you like.
   *  @type int
   *  @default 0
   *  @static
   */
		iFixedColumnsLeft: 0,

		/**
   * As `iFixedColumnsRight` but counting from the right.
   *  @type int
   *  @default 0
   *  @static
   */
		iFixedColumnsRight: 0,

		/**
   * Callback function that is fired when columns are reordered. The `column-
   * reorder` event is preferred over this callback
   *  @type function():void
   *  @default null
   *  @static
   */
		fnReorderCallback: null
	};

	/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  * Constants
  * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */

	/**
  * ColReorder version
  *  @constant  version
  *  @type      String
  *  @default   As code
  */
	ColReorder.version = "1.4.1";

	/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  * DataTables interfaces
  * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */

	// Expose
	$.fn.dataTable.ColReorder = ColReorder;
	$.fn.DataTable.ColReorder = ColReorder;

	// Register a new feature with DataTables
	if (typeof $.fn.dataTable == "function" && typeof $.fn.dataTableExt.fnVersionCheck == "function" && $.fn.dataTableExt.fnVersionCheck('1.10.8')) {
		$.fn.dataTableExt.aoFeatures.push({
			"fnInit": function fnInit(settings) {
				var table = settings.oInstance;

				if (!settings._colReorder) {
					var dtInit = settings.oInit;
					var opts = dtInit.colReorder || dtInit.oColReorder || {};

					new ColReorder(settings, opts);
				} else {
					table.oApi._fnLog(settings, 1, "ColReorder attempted to initialise twice. Ignoring second");
				}

				return null; /* No node for DataTables to insert */
			},
			"cFeature": "R",
			"sFeature": "ColReorder"
		});
	} else {
		alert("Warning: ColReorder requires DataTables 1.10.8 or greater - www.datatables.net/download");
	}

	// Attach a listener to the document which listens for DataTables initialisation
	// events so we can automatically initialise
	$(document).on('preInit.dt.colReorder', function (e, settings) {
		if (e.namespace !== 'dt') {
			return;
		}

		var init = settings.oInit.colReorder;
		var defaults = DataTable.defaults.colReorder;

		if (init || defaults) {
			var opts = $.extend({}, init, defaults);

			if (init !== false) {
				new ColReorder(settings, opts);
			}
		}
	});

	// API augmentation
	$.fn.dataTable.Api.register('colReorder.reset()', function () {
		return this.iterator('table', function (ctx) {
			ctx._colReorder.fnReset();
		});
	});

	$.fn.dataTable.Api.register('colReorder.order()', function (set, original) {
		if (set) {
			return this.iterator('table', function (ctx) {
				ctx._colReorder.fnOrder(set, original);
			});
		}

		return this.context.length ? this.context[0]._colReorder.fnOrder() : null;
	});

	$.fn.dataTable.Api.register('colReorder.transpose()', function (idx, dir) {
		return this.context.length && this.context[0]._colReorder ? this.context[0]._colReorder.fnTranspose(idx, dir) : idx;
	});

	$.fn.dataTable.Api.register('colReorder.move()', function (from, to, drop, invalidateRows) {
		if (this.context.length) {
			this.context[0]._colReorder.s.dt.oInstance.fnColReorder(from, to, drop, invalidateRows);
		}
		return this;
	});

	return ColReorder;
});

/***/ }),
/* 203 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function(jQuery) {var __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;var _typeof = typeof Symbol === "function" && typeof Symbol.iterator === "symbol" ? function (obj) { return typeof obj; } : function (obj) { return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj; };

/**
  * Módulo que habilita la edicción mediante un formulario.
  *
  * @summary 		Extensión del componente RUP Datatable
  * @module			"rup.table.editForm"
  * @version     1.0.0
  * @license
  * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
  * Solo podrá usarse esta obra si se respeta la Licencia.
  * Puede obtenerse una copia de la Licencia en
  *
  *      http://ec.europa.eu/idabc/eupl.html
  *
  * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
  * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
  * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
  * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
  * que establece la Licencia.
  * @copyright   Copyright 2018 E.J.I.E., S.A.
  *
  */

(function (factory) {
	if (true) {
		// AMD
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(4)], __WEBPACK_AMD_DEFINE_RESULT__ = function ($) {
			return factory($, window, document);
		}.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else if ((typeof exports === 'undefined' ? 'undefined' : _typeof(exports)) === 'object') {
		// CommonJS
		module.exports = function (root, $) {
			if (!root) {
				root = window;
			}

			if (!$ || !$.fn.dataTable) {
				$ = require('datatables.net')(root, $).$;
			}

			return factory($, root, root.document);
		};
	} else {
		// Browser
		factory(jQuery, window, document);
	}
})(function ($, window, document, undefined) {
	'use strict';

	var DataTable = $.fn.dataTable;

	// Version information for debugger
	DataTable.editForm = {};

	DataTable.editForm.version = '1.2.4';

	/**
 * Se inicializa el componente editForm
 *
 * @name init
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 *
 * @param {object} dt - Es el objeto datatable.
 *
 */
	DataTable.editForm.init = function (dt) {
		var ctx = dt.settings()[0];
		var init = ctx.oInit.multiSelect;
		var defaults = DataTable.defaults.multiSelect;
		var opts = init === undefined ? defaults : init;

		//DetailForm se convierte en function
		//Se inicializan los botones
		ctx.oInit.formEdit.detailForm = $(ctx.oInit.formEdit.detailForm);
		ctx.oInit.formEdit.idForm = ctx.oInit.formEdit.detailForm.find('form');
		ctx.oInit.formEdit.id = ctx.oInit.formEdit.detailForm[0].id.replace('_detail_div', '');

		//Se coge el adapter, y se crea la barra de navegación
		if (ctx.oInit.multiSelect === undefined) {
			// si es de select
			_callNavigationSelectBar(dt);
		} else {
			//si es de multiselect
			_callNavigationBar(dt);
		}
		//Se inicializa el editFrom la info
		_updateDetailPagination(ctx, 1, 1);

		//se añade el boton de cancelar
		ctx.oInit.formEdit.buttoCancel = ctx.oInit.formEdit.detailForm.find('#' + ctx.sTableId + '_detail_button_cancel');
		ctx.oInit.formEdit.buttoCancel.bind('click', function () {
			ctx.oInit.formEdit.okCallBack = false;
			var feedback = ctx.oInit.formEdit.detailForm.find('#' + ctx.sTableId + '_detail_feedback');

			//Despues de cerrar
			//Se limpia los elementos.
			if (ctx.oInit.formEdit.idForm.find('.error').length > 0) {
				ctx.oInit.formEdit.idForm.rup_validate("resetElements");
			}

			//Se cierra el dialog
			ctx.oInit.formEdit.detailForm.rup_dialog("close");
			//Se cierran los mensajes del feedback
			if (feedback[0].className !== '') {
				feedback.rup_feedback('hide');
			}
		});
		var idRow;
		var rowsBody = $(ctx.nTBody);
		//Se edita el row/fila.
		if (ctx.oInit.multiSelect !== undefined || ctx.oInit.select !== undefined) {
			rowsBody.on('dblclick.DT', 'tr[role="row"]', function () {
				idRow = this._DT_RowIndex;
				//Añadir la seleccion del mismo.
				if (ctx.oInit.multiSelect !== undefined) {
					dt['row'](idRow).multiSelect();
				} else {
					$('tr', rowsBody).removeClass('selected tr-highlight');
					DataTable.Api().select.selectRowIndex(dt, idRow, true);
				}
				_getRowSelected(dt, 'PUT');
				DataTable.editForm.fnOpenSaveDialog('PUT', dt, idRow);
				$('#' + ctx.sTableId).triggerHandler('tableEditFormClickRow');
			});
		}

		// Creacion del Context Menu
		if (ctx.oInit.buttons !== undefined) {
			var botonesToolbar = ctx._buttons[0].inst.s.buttons;
			var items = {};
			$.when($.each(botonesToolbar, function (i) {
				// Entra si tiene marcada la opcion para habilitarlo dentro del contextMenu
				if (this.conf.insideContextMenu) {
					// Poblamos el objeto 'items' con los botones habilitados
					items[this.conf.id] = {
						id: this.conf.id + '_contextMenuToolbar',
						name: this.conf.text(dt),
						inCollection: this.inCollection,
						idCollection: undefined
					};
				}
				// Comprueba si tiene botones hijos
				if (this.buttons.length > 0) {
					var idCollection = this.conf.id;
					$.each(this.buttons, function (i) {
						// Entra si tiene marcada la opcion para habilitarlo dentro del contextMenu
						if (this.conf.insideContextMenu) {
							// Poblamos el objeto 'items' con los botones habilitados
							items[this.conf.id] = {
								id: this.conf.id + '_contextMenuToolbar',
								name: this.conf.text(dt),
								inCollection: this.inCollection,
								idCollection: idCollection
							};
						}
					});
				}
			})).done(function () {
				var tableTr = $('#' + ctx.sTableId + ' > tbody > tr');
				tableTr.rup_contextMenu({
					callback: function callback(key, options) {
						var selector = items[key];
						// Recogemos el id de la accion pulsada en el context menu
						var contextMenuActionId = selector.id;
						// Le quitamos la extension '_contextMenuToolbar' para tener asi
						// el id del boton que queremos accionar
						var buttonId = contextMenuActionId.replace('_contextMenuToolbar', '');
						// Variable que nos dira si esta dentro de una coleccion
						var inCollection = selector.inCollection;
						// Variable que almacena el id de la coleccion (si no pertenece a una
						// siempre sera 'undefined')
						var idCollection = selector.idCollection;
						// Comprobamos si existe el elemento con este id
						if (inCollection && idCollection !== undefined) {
							// Obtenemos la info necesaria del boton y la guardamos en variables
							var buttonName;
							var eventDT;
							var eventConfig;

							$.each(ctx.ext.buttons, function (key) {
								var buttonObject = ctx.ext.buttons[key];
								if (buttonObject.id === buttonId) {
									buttonName = key;
									eventDT = buttonObject.eventDT;
									eventConfig = buttonObject;
								}
							});

							// Llamamos directamente al action para no hacer aparecer y desaparecer
							// el boton, empeorando la UX
							ctx.ext.buttons[buttonName].action(undefined, eventDT, undefined, eventConfig);
						} else {
							$('#' + buttonId).trigger('click');
						}
					},
					items: items
				});
			});
		}

		//Se captura evento de cierre
		ctx.oInit.formEdit.detailForm.on("dialogbeforeclose", function (event, ui) {
			// si es igual no hacer nada.
			var formSerializado = _editFormSerialize(ctx.oInit.formEdit.idForm);
			if (ctx.oInit.formEdit.dataOrigin === formSerializado) {
				return true;
			}
			if (ctx.oInit.formEdit.dataOrigin !== formSerializado && !ctx.oInit.formEdit.okCallBack) {

				$.rup_messages('msgConfirm', {
					message: $.rup.i18nParse($.rup.i18n.base, 'rup_datatable.saveAndContinue'),
					title: $.rup.i18nParse($.rup.i18n.base, 'rup_datatable.changes'),
					OKFunction: function OKFunction() {
						ctx.oInit.formEdit.okCallBack = true;
						ctx.oInit.formEdit.detailForm.rup_dialog("close");
					},
					CANCELFunction: function CANCELFunction() {
						ctx.oInit.formEdit.okCallBack = false;
					}
				});
			}
			//En caso de aceptar se cierrar y se limpia.
			if (!ctx.oInit.formEdit.okCallBack || ctx.oInit.formEdit.okCallBack === undefined) {
				return false;
			}
		});
		ctx.oInit.formEdit.detailForm.settings = { type: $.rup.dialog.DIV };
	};

	/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  * Local functions
  */

	/**
  * Initialisation of a new table. Attach event handlers and callbacks to allow
  * Select to operate correctly.
  *
  * This will occur _after_ the initial DataTables initialisation, although
  * before Ajax data is rendered, if there is ajax data
  *
  * @name init
  * @function
  * @since UDA 3.4.0 // Datatable 1.0.0
  *
  * @param  {DataTable.settings} ctx Settings object to operate on
  *
  */
	function init(ctx) {
		var api = new DataTable.Api(ctx);

		// Row callback so that classes can be added to rows and cells if the item
		// was selected before the element was created. This will happen with the
		// `deferRender` option enabled.
		//
		// This method of attaching to `aoRowCreatedCallback` is a hack until
		// DataTables has proper events for row manipulation If you are reviewing
		// this code to create your own plug-ins, please do not do this!
		ctx.aoRowCreatedCallback.push({
			fn: function fn(row, data, index) {
				var i, ien;
				var d = ctx.aoData[index];

				// Row
				if (d._multiSelect_selected) {
					$(row).addClass(ctx._multiSelect.className);
				}

				// Cells and columns - if separated out, we would need to do two
				// loops, so it makes sense to combine them into a single one
				for (i = 0, ien = ctx.aoColumns.length; i < ien; i++) {
					if (ctx.aoColumns[i]._multiSelect_selected || d._selected_cells && d._selected_cells[i]) {
						$(d.anCells[i]).addClass(ctx._multiSelect.className);
					}
				}
			},
			sName: 'select-deferRender'
		});

		// On Ajax reload we want to reselect all rows which are currently selected,
		// if there is an rowId (i.e. a unique value to identify each row with)
		api.on('preXhr.dt.dtSelect', function () {
			// note that column selection doesn't need to be cached and then
			// reselected, as they are already selected
			var rows = api.rows({ selected: true }).ids(true).filter(function (d) {
				return d !== undefined;
			});

			var cells = api.cells({ selected: true }).eq(0).map(function (cellIdx) {
				var id = api.row(cellIdx.row).id(true);
				return id ? { row: id, column: cellIdx.column } : undefined;
			}).filter(function (d) {
				return d !== undefined;
			});

			// On the next draw, reselect the currently selected items
			api.one('draw.dt.dtSelect', function () {
				api.rows(rows).multiSelect();

				// `cells` is not a cell index selector, so it needs a loop
				if (cells.any()) {
					cells.each(function (id) {
						api.cells(id.row, id.column).multiSelect();
					});
				}
			});
		});

		// Clean up and release
		api.on('destroy.dtSelect', function () {
			disableMouseSelection(api);
			api.off('.dtSelect');
		});
	}

	function eventTrigger(api, type, args, any) {
		if (any && !api.flatten().length) {
			return;
		}

		if (typeof type === 'string') {
			type = type + '.dt';
		}

		args.unshift(api);

		$(api.table().node()).trigger(type, args);
	}

	/**
 * Función que lleva todo el comportamiento para abrir el dialog y editar un registro.
 *
 * @name openSaveDialog
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 *
 * @param {string} actionType - Es la acción que se va a ajecutar en el formulario para ir al controller, basado en rest.
 * @param {object} dt - Es el objeto datatable.
 * @param {integer} idRow - Número con la posición de la fila que hay que obtener.
 *
 */
	DataTable.editForm.fnOpenSaveDialog = function _openSaveDialog(actionType, dt, idRow) {
		var ctx = dt.settings()[0];
		var idForm = ctx.oInit.formEdit.idForm;

		//Se limpia los errores. Si hubiese
		var feed = ctx.oInit.formEdit.detailForm.find('#' + ctx.sTableId + '_detail_feedback');
		var divErrorFeedback = ctx.oInit.formEdit.detailForm.find('#' + feed[0].id + '_ok');
		if (divErrorFeedback.length > 0) {
			divErrorFeedback.hide();
		}

		//se añade el boton de guardar
		var button = ctx.oInit.formEdit.detailForm.find('#' + ctx.sTableId + '_detail_button_save');
		//se añade el boton de guardar y continuar
		var buttonContinue = ctx.oInit.formEdit.detailForm.find('#' + ctx.sTableId + '_detail_button_save_repeat');

		if (actionType === 'CLONE') {
			//En caso de ser clonado, solo se debe guardar.
			actionType = 'POST';
			buttonContinue.hide();
		} else {
			buttonContinue.show();
		}

		if (idRow < 0) {
			idRow = 1;
		}
		$('#' + ctx.sTableId).triggerHandler('tableEditFormAddEditBeforeInitData');
		var row = ctx.json.rows[idRow];
		var rowArray = $.rup_utils.jsontoarray(row);
		var title;

		if (actionType === 'PUT') {
			$.rup_utils.populateForm(rowArray, idForm);
			var multiselection = ctx.multiselection;
			var indexInArray = jQuery.inArray(DataTable.Api().rupTable.getIdPk(row), multiselection.selectedIds);
			if (ctx.multiselection.selectedAll) {
				//Si es selecAll recalcular el numero de los selects.,solo la primera vez es necesario.
				indexInArray = ctx.oInit.formEdit.$navigationBar.numPosition;
			}
			if (indexInArray === undefined) {
				indexInArray = 0;
				ctx.oInit.formEdit.$navigationBar.numPosition = 0;
			}
			var numTotal = multiselection.numSelected;
			if (ctx.oInit.multiSelect === undefined) {
				numTotal = ctx.json.recordsTotal;
				indexInArray = (Number(ctx.json.page) - 1) * 10;
				indexInArray = indexInArray + idRow;
			}
			$('#' + ctx.sTableId).triggerHandler('tableEditFormAfterFillData');
			_updateDetailPagination(ctx, indexInArray + 1, numTotal);
			DataTable.Api().rupTable.selectPencil(ctx, idRow);
			//Se guarda el ultimo id editado.
			ctx.multiselection.lastSelectedId = DataTable.Api().rupTable.getIdPk(row);
			//Se muestra el dialog.
			ctx.oInit.formEdit.$navigationBar.show();
			// Asignamos un valor a la variable del título del formulario
			title = $.rup.i18nParse($.rup.i18n.base, 'rup_datatable.edit.editCaption');
			// Comprobamos si se desea bloquear la edicion de las claves primarias
			if (ctx.oInit.blockPKeditForm) {
				$.each(ctx.oInit.primaryKey, function (key, id) {
					$(idForm[0]).find("input[name=" + id + "]").prop("readOnly", true);
				});
			}
		} else if (actionType === 'POST') {
			$.rup_utils.populateForm(rowArray, idForm);
			ctx.oInit.formEdit.$navigationBar.hide();
			// Asignamos un valor a la variable del título del formulario
			title = $.rup.i18nParse($.rup.i18n.base, 'rup_datatable.edit.addCaption');
		}

		$('#' + ctx.sTableId).triggerHandler('tableEditFormAddEditBeforeShowForm');
		// Establecemos el título del formulario
		ctx.oInit.formEdit.detailForm.rup_dialog("setOption", "title", title);

		ctx.oInit.formEdit.detailForm.rup_dialog(ctx.oInit.formEdit.detailForm.settings);
		ctx.oInit.formEdit.detailForm.rup_dialog("open");

		// Establecemos el foco al primer elemento input o select que se
		// encuentre habilitado en el formulario
		$(idForm[0]).find('input,select').filter(':not([readonly]):first').focus();

		//Se guardan los datos originales
		ctx.oInit.formEdit.dataOrigin = _editFormSerialize(idForm);
		ctx.oInit.formEdit.okCallBack = false;

		button.unbind("click");
		button.bind('click', function () {
			//Comprobar si row ha sido modificada
			//Se serializa el formulario con los cambios
			row = _editFormSerialize(idForm);

			//Verificar los checkbox vacíos.
			row = _returnCheckEmpty(idForm, _editFormSerialize(idForm));

			//Se transforma
			row = $.rup_utils.queryStringToJson(row);
			ctx.oInit.formEdit.okCallBack = true;

			_callSaveAjax(actionType, dt, row, idRow, false, ctx.oInit.formEdit.detailForm, '');
		});

		ctx.oInit.formEdit.detailForm.buttonSaveContinue = buttonContinue;
		ctx.oInit.formEdit.detailForm.buttonSaveContinue.actionType = actionType;
		buttonContinue.unbind("click");
		buttonContinue.bind('click', function () {
			var actionSaveContinue = ctx.oInit.formEdit.detailForm.buttonSaveContinue.actionType;
			//Comprobar si row ha sido modificada
			//Se serializa el formulario con los cambios
			row = _editFormSerialize(idForm);

			//Verificar los checkbox vacíos.
			row = _returnCheckEmpty(idForm, _editFormSerialize(idForm));

			//Se transforma
			row = $.rup_utils.queryStringToJson(row);

			_callSaveAjax(actionSaveContinue, dt, row, idRow, true, ctx.oInit.formEdit.detailForm, '');
		});

		$('#' + ctx.sTableId).triggerHandler('tableEditFormAddEditAfterShowForm');
	};

	/**
 * Llamada al servidor con los datos de edición.
 *
 * @name _callSaveAjax
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 *
 * @param {string} actionType - Es la acción que se va a ajecutar en el formulario para ir al controller, basado en rest.
 * @param {object} dt - Es el objeto datatable.
 * @param {object} row - Son los datos que se cargan.
 * @param {integer} idRow - Número con la posición de la fila que hay que obtener.
 * @param {boolean} continuar - Si es true guarda la pagina y se queda en el dialog , si es false guarda y cierra el dialog.
 * @param {string} idTableDetail - Identificdor del detail de la table.
 * @param {string} url - Url que se añade para llamar  al controller.
 *
 */
	function _callSaveAjax(actionType, dt, row, idRow, continuar, idTableDetail, url) {
		var ctx = dt.settings()[0];
		$('#' + ctx.sTableId).triggerHandler('tableEditFormBeforeCallAjax');
		// add Filter
		var feed = idTableDetail.find('#' + ctx.sTableId + '_detail_feedback');
		var msgFeedBack = $.rup.i18nParse($.rup.i18n.base, 'rup_datatable.modifyOK');
		if (url === '/deleteAll' || actionType === 'DELETE') {
			msgFeedBack = $.rup.i18nParse($.rup.i18n.base, 'rup_datatable.deletedOK');
		}
		var ajaxOptions = {
			url: ctx.oInit.urlBase + url,
			accepts: { '*': '*/*', 'html': 'text/html', 'json': 'application/json, text/javascript',
				'script': 'text/javascript, application/javascript, application/ecmascript, application/x-ecmascript',
				'text': 'text/plain', 'xml': 'application/xml, text/xml' },
			type: actionType,
			data: row,
			dataType: 'json',
			showLoading: false,
			contentType: 'application/json',
			async: true,
			success: function success(data, status, xhr) {

				if (url !== '/deleteAll' && actionType !== 'DELETE') {
					if (continuar) {
						//Se crea un feddback_ok,para que no se pise con el de los errores
						var divOkFeedback = idTableDetail.find('#' + feed[0].id + '_ok');
						if (divOkFeedback.length === 0) {
							divOkFeedback = $('<div/>').attr('id', feed[0].id + '_ok').insertBefore(feed);
						}
						_callFeedbackOk(ctx, divOkFeedback, msgFeedBack, 'ok'); //Se informa,feedback del formulario
					} else {
						ctx.oInit.formEdit.detailForm.rup_dialog("close");
						_callFeedbackOk(ctx, ctx.multiselection.internalFeedback, msgFeedBack, 'ok'); //Se informa feedback de la tabla
					}

					if (actionType === 'PUT') {
						//Modificar
						dt.row(idRow).data(row); // se actualiza al editar
						ctx.json.rows[idRow] = row;
						// Actualizamos el ultimo id seleccionado (por si ha sido editado)
						var posicion = 0;
						$.each(ctx.multiselection.selectedRowsPerPage, function (index, p) {
							if (p.id === ctx.multiselection.lastSelectedId) {
								posicion = index;
								return;
							}
						});
						if (ctx.seeker !== undefined && !jQuery.isEmptyObject(ctx.seeker.ajaxOption.data.search) && ctx.seeker.search.funcionParams.length > 0) {
							_comprobarSeeker(row, ctx, idRow);
						}
						ctx.multiselection.lastSelectedId = DataTable.Api().rupTable.getIdPk(row);
						ctx.multiselection.selectedRowsPerPage[posicion].id = DataTable.Api().rupTable.getIdPk(row);
					} else {
						//Se actualiza la tabla temporalmente. y deja de ser post para pasar a put(edicion)
						if (ctx.oInit.select !== undefined) {
							DataTable.Api().select.deselect(ctx);
						}
						var rowAux = row;
						$.each(ctx.json.rows, function (index, r) {
							var rowNext = r;
							dt.row(index).data(rowAux);
							rowAux = rowNext;
						});
						ctx.json.rows.pop();
						ctx.json.rows.splice(0, 0, row);
						//Se guardan los datos para pasar de nuevo a editable.
						ctx.oInit.formEdit.detailForm.buttonSaveContinue.actionType = 'PUT';
						ctx.oInit.formEdit.dataOrigin = _editFormSerialize(ctx.oInit.formEdit.idForm);
						if (ctx.oInit.multiSelect !== undefined) {
							ctx.multiselection.internalFeedback.type = "noBorrar";
							dt['row']().multiSelect();
						}
						//Se actualiza la linea
						if (ctx.json.reorderedSelection !== null && ctx.json.reorderedSelection !== undefined) {
							ctx.multiselection.selectedRowsPerPage[0].line = ctx.json.reorderedSelection[0].pageLine;
						}
						$('#' + ctx.sTableId).triggerHandler('tableEditFormAfterInsertRow');
					}
				} else {
					// Eliminar
					ctx.multiselection.internalFeedback.type = 'eliminar';
					ctx.multiselection.internalFeedback.msgFeedBack = msgFeedBack;
					if (ctx.oInit.multiSelect !== undefined) {
						DataTable.Api().multiSelect.deselectAll(dt);
					} else if (ctx.oInit.select !== undefined) {
						DataTable.Api().select.deselect(ctx);
					}
					$('#' + ctx.sTableId).triggerHandler('tableEditFormAfterDelete');
				}
				// Recargar datos
				dt.ajax.reload();
				$('#' + ctx.sTableId).triggerHandler('tableEditFormSuccessCallSaveAjax');
			},
			complete: function complete() {
				$('#' + ctx.sTableId).triggerHandler('tableEditFormCompleteCallSaveAjax');
			},
			error: function error(xhr, ajaxOptions, thrownError) {
				var divErrorFeedback = idTableDetail.find('#' + feed[0].id + '_ok');
				if (divErrorFeedback.length === 0) {
					divErrorFeedback = $('<div/>').attr('id', feed[0].id + '_ok').insertBefore(feed);
				}
				_callFeedbackOk(ctx, divErrorFeedback, xhr.responseText, 'error');
				$('#' + ctx.sTableId).triggerHandler('tableEditFormErrorCallSaveAjax');
			},
			validate: ctx.oInit.formEdit.validate,
			feedback: feed.rup_feedback({ type: "ok", block: false })
		};

		ctx.oInit.formEdit.idForm.rup_form('ajaxSubmit', ajaxOptions);
	}

	/**
 * Llamada para crear el feedback dentro del dialog.
 *
 * @name callFeedbackOk
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 *
 * @param {object} ctx - Settings object to operate on.
 * @param {object} feedback - Div donde se va ejecutar el feedback.
 * @param {string} msgFeedBack - Mensaje para el feedback.
 * @param {string} type - Tipos del feedback, mirar en el rup.feedback..
 *
 */
	function _callFeedbackOk(ctx, feedback, msgFeedBack, type) {
		$('#' + ctx.sTableId).triggerHandler('tableEditFormFeedbackShow');
		var confDelay = ctx.oInit.feedback.okFeedbackConfig.delay;
		feedback.rup_feedback({ message: msgFeedBack, type: type, block: false });
		feedback.rup_feedback('set', msgFeedBack);
		//Aseguramos que el estilo es correcto.
		if (type === 'ok') {
			setTimeout(function () {
				feedback.rup_feedback('destroy');
				feedback.css('width', '100%');
				$('#' + ctx.sTableId).triggerHandler('tableEditFormInternalFeedbackClose');
			}, confDelay);
		}
	}

	/**
 * Se verifican los check vacios dentro de un formulario.
 *
 * @name returnCheckEmpty
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 *
 * @param {object} idForm - Identificador del formulario.
 * @param {string} values - Values ya añadidos al formulario.
 *
 */
	function _returnCheckEmpty(idForm, values) {
		var maps = jQuery(idForm.selector + ' input[type=checkbox]:not(:checked)').map(function () {
			return "&" + this.name + "=0";
		}).get().toString();
		return values + maps;
	}

	/**
 * Actualiza la navegación del dialogo.
 *
 * @name updateDetailPagination
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 *
 * @param {object} ctx - Settings object to operate on.
 * @param {integer} currentRowNum - Número de la posción actual del registro selecionado.
 * @param {integer} totalRowNum - Número total de registros seleccionados.
 *
 */
	function _updateDetailPagination(ctx, currentRowNum, totalRowNum) {
		var formId = ctx.oInit.formEdit.id;
		var tableId = ctx.oInit.formEdit.$navigationBar[0].id;
		if (currentRowNum === 1) {
			$('#first_' + tableId + ', #back_' + tableId, ctx.oInit.formEdit.detailForm).addClass('ui-state-disabled');
		} else {
			$('#first_' + tableId + ', #back_' + tableId, ctx.oInit.formEdit.detailForm).removeClass('ui-state-disabled');
		}
		if (currentRowNum === totalRowNum) {
			$('#forward_' + tableId + ', #last_' + tableId, ctx.oInit.formEdit.detailForm).addClass('ui-state-disabled');
		} else {
			$('#forward_' + tableId + ', #last_' + tableId, ctx.oInit.formEdit.detailForm).removeClass('ui-state-disabled');
		}

		$('#rup_table_selectedElements_' + tableId).text(jQuery.jgrid.format(jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.defaults.detailForm_pager'), currentRowNum, totalRowNum));
	}

	/**
 * Constructor de la barra de navegación.
 *
 * @name callNavigatorBar
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 *
 * @param {object} dt - Es el objeto datatable.
 *
 */
	function _callNavigationBar(dt) {
		var ctx = dt.settings()[0];
		ctx.oInit._ADAPTER = $.rup.adapter[jQuery.fn.rup_table.plugins.core.defaults.adapter];
		ctx.oInit.formEdit.$navigationBar = ctx.oInit.formEdit.detailForm.find('#' + ctx.sTableId + '_detail_navigation');
		var settings = {};
		//Funcion para obtener los parametros de navegacion.
		settings.fncGetNavigationParams = function getNavigationParams_multiselection(linkType) {
			var execute = false,
			    changePage = false,
			    index = 0,
			    newPageIndex = 0,
			    npos = ctx.oInit.formEdit.$navigationBar.currentPos,
			    page = dt.page() + 1,
			    newPage = page,
			    lastPage = ctx.json.total;
			var multiselection = ctx.multiselection;
			var rowSelected;

			switch (linkType) {
				case 'first':
					// Si no se han seleccionado todos los elementos
					if (!multiselection.selectedAll) {
						rowSelected = multiselection.selectedRowsPerPage[0];
						rowSelected.indexSelected = 0;
					} else {
						// En el caso de que se hayan seleccionado todos los elementos de la tabla
						// Recorremos las páginas buscando la primera en la que existan elementos seleccionados
						ctx.oInit.formEdit.$navigationBar.numPosition = 0;
						rowSelected = ctx.oInit.formEdit.$navigationBar.currentPos;
						rowSelected.page = _getNextPageSelected(ctx, 1, 'next');
						if (Number(rowSelected.page) === page) {
							//Si es la misma pagina.buscar la linea
							rowSelected.line = _getLineByPageSelected(ctx, -1);
						} else {
							rowSelected.line = 0; // luego hay que buscar la linea
						}
					}
					break;
				case 'prev':
					// Si no se han seleccionado todos los elementos
					if (!multiselection.selectedAll) {
						var indexPrev = ctx.oInit.formEdit.$navigationBar.currentPos.indexSelected - 1;
						rowSelected = multiselection.selectedRowsPerPage[indexPrev];
						rowSelected.indexSelected = indexPrev;
					} else {
						ctx.oInit.formEdit.$navigationBar.numPosition--;
						var linea = _getLineByPageSelectedReverse(ctx, ctx.oInit.formEdit.$navigationBar.currentPos.line);
						if (linea === -1) {
							//Es que hay que cambiar de pagina.
							//buscarPAgina.
							rowSelected = ctx.oInit.formEdit.$navigationBar.currentPos;
							rowSelected.page = _getPrevPageSelected(ctx, page - 1);
						} else {
							rowSelected = ctx.oInit.formEdit.$navigationBar.currentPos;
						}
					}

					break;
				case 'next':
					// Si no se han seleccionado todos los elementos
					if (!multiselection.selectedAll) {
						var indexNext = ctx.oInit.formEdit.$navigationBar.currentPos.indexSelected + 1;
						rowSelected = multiselection.selectedRowsPerPage[indexNext];
						rowSelected.indexSelected = indexNext;
					} else {
						ctx.oInit.formEdit.$navigationBar.numPosition++;
						//2 casos: Si hay que navegar o no.
						var lineaNext = _getLineByPageSelected(ctx, ctx.oInit.formEdit.$navigationBar.currentPos.line);
						if (lineaNext === -1) {
							//Es que hay que cambiar de pagina.
							//buscarPAgina.
							rowSelected = ctx.oInit.formEdit.$navigationBar.currentPos;
							rowSelected.page = _getNextPageSelected(ctx, page + 1, 'next');
							rowSelected.line = 0; // luego hay que buscar la linea
						} else {
							rowSelected = ctx.oInit.formEdit.$navigationBar.currentPos;
						}
					}

					break;
				case 'last':
					// Si no se han seleccionado todos los elementos
					if (!multiselection.selectedAll) {
						var indexLast = multiselection.selectedRowsPerPage.length - 1;
						rowSelected = multiselection.selectedRowsPerPage[indexLast];
						rowSelected.indexSelected = indexLast;
					} else {
						ctx.oInit.formEdit.$navigationBar.numPosition = ctx.multiselection.numSelected - 1;
						rowSelected = ctx.oInit.formEdit.$navigationBar.currentPos;
						rowSelected.page = _getPrevPageSelected(ctx, lastPage);
						if (Number(rowSelected.page) === page) {
							//Si es la misma pagina.buscar la linea
							rowSelected.line = _getLineByPageSelectedReverse(ctx, -1);
						}
					}

			}
			if (Number(rowSelected.page) !== page) {
				var table = $('#' + ctx.sTableId).DataTable();
				table.page(rowSelected.page - 1).draw('page');
				//Se añaden los parametros para luego ejecutar, la funcion del dialog.
				ctx.oInit.formEdit.$navigationBar.funcionParams = ['PUT', dt, rowSelected.line, linkType];
			} else {
				//Si nose pagina se abre directamente la funcion.
				DataTable.editForm.fnOpenSaveDialog('PUT', dt, rowSelected.line);
			}
			//Se actualiza la ultima posicion movida.
			ctx.oInit.formEdit.$navigationBar.currentPos = rowSelected;
			//Se añade un parametro respecto el rup.table para permitir la convivencia.
			return [linkType, execute, changePage, index - 1, npos, newPage, newPageIndex - 1, ''];
		};

		ctx.oInit.formEdit.$navigationBar.data('settings', settings);
		//var barraNavegacion = $.proxy(ctx.oInit.adapter.createDetailNavigation,ctx.oInit.formEdit.$navigationBar);
		var barraNavegacion = $.proxy(ctx.oInit._ADAPTER.createDetailNavigation, ctx.oInit.formEdit.$navigationBar);
		ctx.oInit.formEdit.$navigationBar.append(barraNavegacion);
	}

	/**
 * Constructor de la barra de navegación.
 *
 * @name callNavigatorSelectBar
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 *
 * @param {object} dt - Es el objeto datatable.
 *
 */
	function _callNavigationSelectBar(dt) {
		var ctx = dt.settings()[0];
		ctx.oInit._ADAPTER = $.rup.adapter[jQuery.fn.rup_table.plugins.core.defaults.adapter];
		ctx.oInit.formEdit.$navigationBar = ctx.oInit.formEdit.detailForm.find('#' + ctx.sTableId + '_detail_navigation');
		var settings = {};

		//Funcion para obtener los parametros de navegacion.
		settings.fncGetNavigationParams = function getNavigationParams_multiselection(linkType) {
			var execute = false,
			    changePage = false,
			    index = 0,
			    newPageIndex = 0,
			    npos = ctx.oInit.formEdit.$navigationBar.currentPos,
			    page = dt.page() + 1,
			    newPage = page,
			    lastPage = ctx.json.total;
			var futurePage = page;

			switch (linkType) {
				case 'first':
					futurePage = 1;
					ctx.multiselection.selectedRowsPerPage[0].line = 0;
					break;
				case 'prev':
					ctx.multiselection.selectedRowsPerPage[0].line = ctx.multiselection.selectedRowsPerPage[0].line - 1;
					if (ctx.json.rows[ctx.multiselection.selectedRowsPerPage[0].line] === undefined) {
						futurePage = futurePage - 1;
					}
					break;
				case 'next':
					ctx.multiselection.selectedRowsPerPage[0].line = ctx.multiselection.selectedRowsPerPage[0].line + 1;
					if (ctx.json.rows[ctx.multiselection.selectedRowsPerPage[0].line] === undefined) {
						futurePage = futurePage + 1;
					}
					break;
				case 'last':
					futurePage = lastPage;
					ctx.multiselection.selectedRowsPerPage[0].line = ctx.json.rows.length - 1;

			}
			//Cambio de pagina
			if (Number(futurePage) !== page) {
				var table = $('#' + ctx.sTableId).DataTable();
				ctx.select.selectedRowsPerPage = {};
				ctx.select.selectedRowsPerPage.cambio = linkType;
				ctx.select.selectedRowsPerPage.page = futurePage;
				table.page(futurePage - 1).draw('page');
			} else {
				//Si nose pagina se abre directamente la funcion.
				DataTable.editForm.fnOpenSaveDialog('PUT', dt, ctx.multiselection.selectedRowsPerPage[0].line);
				var rowSelectAux = ctx.json.rows[ctx.multiselection.selectedRowsPerPage[0].line];
				ctx.multiselection.selectedRowsPerPage[0].id = DataTable.Api().rupTable.getIdPk(rowSelectAux);
				DataTable.Api().select.deselect(ctx);
				DataTable.Api().select.drawSelectId(ctx);
			}
		};

		ctx.oInit.formEdit.$navigationBar.data('settings', settings);
		//var barraNavegacion = $.proxy(ctx.oInit.adapter.createDetailNavigation,ctx.oInit.formEdit.$navigationBar);
		var barraNavegacion = $.proxy(ctx.oInit._ADAPTER.createDetailNavigation, ctx.oInit.formEdit.$navigationBar);
		ctx.oInit.formEdit.$navigationBar.append(barraNavegacion);
	}

	/**
 * Metodo que obtiene la fila siguiente seleccionada.
 *
 * @name getRowSelected
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 *
 * @param {object} dt - Es el objeto datatable.
 * @param {string} actionType - Es el objeto datatable.
 *
 * @return {object} que contiene  el identificador, la pagina y la linea de la fila seleccionada
 *
 */
	function _getRowSelected(dt, actionType) {
		var ctx = dt.settings()[0];
		var rowDefault = { id: 0, page: 1, line: 0 };
		var lastSelectedId = ctx.multiselection.lastSelectedId;
		if (!ctx.multiselection.selectedAll) {
			//Si no hay un ultimo señalado se coge el ultimo;

			if (lastSelectedId === undefined || lastSelectedId === '') {
				ctx.multiselection.lastSelectedId = ctx.multiselection.selectedRowsPerPage[0].id;
			}
			$.each(ctx.multiselection.selectedRowsPerPage, function (index, p) {
				if (p.id === ctx.multiselection.lastSelectedId) {
					rowDefault.id = p.id;
					rowDefault.page = p.page;
					rowDefault.line = p.line;
					rowDefault.indexSelected = index;
					ctx.oInit.formEdit.$navigationBar.currentPos = rowDefault;
					return false;
				}
			});
		} else {
			ctx.oInit.formEdit.$navigationBar.numPosition = 0; //variable para indicar los mostrados cuando es selectAll y no se puede calcular,El inicio es 0.
			if (lastSelectedId === undefined || lastSelectedId === '') {
				rowDefault.page = _getNextPageSelected(ctx, 1, 'next'); //Como arranca de primeras la pagina es la 1.
				rowDefault.line = _getLineByPageSelected(ctx, -1);
			} else {
				//buscar la posicion y pagina
				var result = $.grep(ctx.multiselection.selectedRowsPerPage, function (v) {
					return v.id === ctx.multiselection.lastSelectedId;
				});
				rowDefault.page = result[0].page;
				rowDefault.line = result[0].line;
				var index = ctx._iDisplayLength * (Number(rowDefault.page) - 1);
				index = index + 1 + rowDefault.line;
				//Hay que restar los deselecionados.
				result = $.grep(ctx.multiselection.deselectedRowsPerPage, function (v) {
					return Number(v.page) < Number(rowDefault.page) || Number(rowDefault.page) === Number(v.page) && Number(v.line) < Number(rowDefault.line);
				});
				rowDefault.indexSelected = index - result.length; //Buscar indice
				ctx.oInit.formEdit.$navigationBar.numPosition = rowDefault.indexSelected - 1;
			}

			ctx.oInit.formEdit.$navigationBar.currentPos = rowDefault;
		}

		//En caso de estar en una pagina distinta , navegamos a ella
		if (dt.page() + 1 !== Number(rowDefault.page)) {
			var table = $('#' + ctx.sTableId).DataTable();
			table.page(rowDefault.page - 1).draw('page');
			ctx.oInit.formEdit.$navigationBar.funcionParams = [actionType, dt, rowDefault.line];
		}

		return rowDefault;
	}

	/**
 * Metodo que obtiene la página siguiente donde esta el primer elemento o elemento seleccionado.
 *
 * @name getNextPageSelected
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 *
 * @param {object} ctx - Settings object to operate on.
 * @param {integer} pageInit - Página a partir de la cual hay que mirar, en general serà la 1.
 * @param {string} orden - Pueder ser pre o next, en función de si necesitar ir hacia adelante o hacia atrás.
 *
 * @return integer - devuele la página
 *
 */
	function _getNextPageSelected(ctx, pageInit, orden) {
		var pagina = pageInit;
		var pageTotals = ctx.json.total;
		if (orden === 'prev') {
			//Si es previo se resta.
			pageTotals = 1;
		}
		if (ctx.multiselection.deselectedRowsPerPage.length > 0) {
			var maxPagina = ctx.json.rows.length;
			var count = 0;
			//Buscar la pagina donde va estar el seleccionado.
			for (var page = pageInit; page < pageTotals;) {
				$.each(ctx.multiselection.deselectedRowsPerPage, function (index, p) {
					if (page === Number(p.page)) {
						count++;
					}
					if (count === maxPagina) {
						return false;
					}
				});
				if (count < maxPagina) {
					pagina = page;
					page = ctx.json.total; //Se pone el total para salir del bucle.
				}
				count = 0;
				if (orden === 'next') {
					page++;
				} else if (orden === 'prev') {
					page--;
				}
			}
		}
		return pagina;
	}

	/**
 * Metodo que obtiene la página siguiente donde esta el primer elemento o elemento seleccionado.
 *
 * @name getPrevPageSelected
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 *
 * @param {object} ctx - Settings object to operate on.
 * @param {integer} pageInit - Página a partir de la cual hay que mirar, en general serà la 1.
 *
 * @return integer - devuele la página
 *
 */
	function _getPrevPageSelected(ctx, pageInit) {
		var pagina = pageInit;
		var pageTotals = 1;
		if (ctx.multiselection.deselectedRowsPerPage.length > 0) {
			var maxPagina = ctx.json.rows.length;
			if (ctx.json.total === pagina) {
				//Es ultima pagina, calcular los registros{
				maxPagina = ctx.json.records % ctx._iDisplayLength;
			}
			var count = 0;
			//Buscar la pagina donde va estar el seleccionado.
			for (var page = pageInit; pageTotals <= page;) {
				$.each(ctx.multiselection.deselectedRowsPerPage, function (index, p) {
					if (Number(page) === Number(p.page)) {
						count++;
					}
					if (count === maxPagina) {
						return false;
					}
				});
				if (count < maxPagina) {
					pagina = page;
					pageTotals = ctx.json.total; //Se pone el total para salir del bucle.
				}
				count = 0;
				page--;
			}
		}
		return pagina;
	}

	/**
 * Metodo que obtiene la linea siguiente donde esta el primer elemento o elemento seleccionado.
 *
 * @name getLineByPageSelected
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 *
 * @param {object} ctx - Settings object to operate on.
 * @param {integer} lineInit - Linea a partir de la cual hay que mirar, en general será la 1.
 *
 * @return integer - devuele la linea
 *
 */
	function _getLineByPageSelected(ctx, lineInit) {
		var line = -1;
		var rows = ctx.json.rows;

		$.each(rows, function (index, row) {
			if (index > lineInit) {
				var indexInArray = jQuery.inArray(DataTable.Api().rupTable.getIdPk(row), ctx.multiselection.deselectedIds);
				if (indexInArray === -1) {
					line = index;
					var arra = { id: DataTable.Api().rupTable.getIdPk(row), page: ctx.json.page, line: index };
					ctx.oInit.formEdit.$navigationBar.currentPos = arra;
					return false;
				}
			}
		});
		return line;
	}

	/**
 * Metodo que obtiene la última linea siguiente donde esta el primer elemento o elemento seleccionado.
 *
 * @name getLineByPageSelectedReverse
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 *
 * @param {object} ctx - Settings object to operate on.
 * @param {integer} lineInit - Linea a partir de la cual hay que mirar.
 *
 * @return integer - devuele la linea
 *
 */
	function _getLineByPageSelectedReverse(ctx, lineInit) {
		var line = -1;
		var rows = ctx.json.rows;

		for (var index = rows.length - 1; index >= 0; index--) {
			var row = rows[index];
			if (index < lineInit) {
				var indexInArray = jQuery.inArray(DataTable.Api().rupTable.getIdPk(row), ctx.multiselection.deselectedIds);
				if (indexInArray === -1) {
					line = index;
					var arra = { id: DataTable.Api().rupTable.getIdPk(row), page: ctx.json.page, line: index };
					ctx.oInit.formEdit.$navigationBar.currentPos = arra;
					index = -1;
				}
			}
		};
		return line;
	}

	/**
 * Metodo que elimina todos los registros seleccionados.
 *
 * @name deleteAllSelects
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 *
 * @param {object} dt - Es el objeto datatable.
 *
 */
	function _deleteAllSelects(dt) {
		var ctx = dt.settings()[0];
		var row = ctx.multiselection.selectedIds;
		var idRow = 0;
		$.rup_messages('msgConfirm', {
			message: $.rup.i18nParse($.rup.i18n.base, 'rup_datatable.deleteAll'),
			title: $.rup.i18nParse($.rup.i18n.base, 'rup_datatable.delete'),
			OKFunction: function OKFunction() {
				if (ctx.multiselection.selectedIds.length > 1) {
					var row = {};
					row.core = { 'pkToken': ctx.oInit.multiplePkToken, 'pkNames': ctx.oInit.primaryKey };
					row.multiselection = {};
					row.multiselection.selectedAll = ctx.multiselection.selectedAll;
					if (row.multiselection.selectedAll) {
						row.multiselection.selectedIds = ctx.multiselection.deselectedIds;
					} else {
						row.multiselection.selectedIds = ctx.multiselection.selectedIds;
					}
					_callSaveAjax('POST', dt, row, idRow, false, ctx.oInit.formEdit.detailForm, '/deleteAll');
				} else {
					row = ctx.multiselection.selectedIds[0];
					row = row.replace(ctx.oInit.multiplePkToken, '/');
					_callSaveAjax('DELETE', dt, '', idRow, false, ctx.oInit.formEdit.detailForm, '/' + row);
				}
			}
		});
	}

	/**
 * Metodo que serializa los datos del formulario.
 *
 * @name _editFormSerialize
 * @function
 * @since UDA 3.6.0 // Datatable 1.2.0
 *
 * @param {object} idForm - Formulario que alberga los datos.
 *
 * @return {string} - Devuelve los datos del formulario serializados
 *
 */
	function _editFormSerialize(idForm) {
		var serializedForm = '';
		var idFormArray = idForm.formToArray();
		var length = idFormArray.length;

		$.each(idFormArray, function (key, obj) {
			serializedForm += obj.name + "=" + obj.value;

			if (key < length - 1) {
				serializedForm += "&";
			}
		});

		return serializedForm;
	}

	function _comprobarSeeker(row, ctx, idRow) {
		var cumple = true;
		$.each(ctx.seeker.ajaxOption.data.search, function (key, obj) {
			if (row[key].indexOf(obj) === -1) {
				cumple = false;
				return false;
			}
		});
		if (!cumple) {
			// eliminar del seeker, por pagina y linea		
			ctx.seeker.search.funcionParams = jQuery.grep(ctx.seeker.search.funcionParams, function (search) {
				return search.page !== Number(ctx.json.page) || search.pageLine !== idRow + 1;
			});
			// se borra el icono

			$('#' + ctx.sTableId + ' tbody tr:eq(' + idRow + ') td.select-checkbox span.ui-icon-search').remove();
			$('#' + ctx.sTableId + ' tbody tr:eq(' + idRow + ') td span.ui-icon-search').remove();
			DataTable.Api().seeker.updateDetailSeekPagination(1, ctx.seeker.search.funcionParams.length, ctx);
		}
	}
	/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  * DataTables API
  *
  * For complete documentation, please refer to the docs/api directory or the
  * DataTables site
  */

	// Local variables to improve compression
	var apiRegister = DataTable.Api.register;

	apiRegister('editForm.openSaveDialog()', function (actionType, dt, idRow) {
		//Se declara la variable del editForm para que puede ser invocada desde cualquier sitio.
		DataTable.editForm.fnOpenSaveDialog(actionType, dt, idRow);
	});

	apiRegister('editForm.updateDetailPagination()', function (ctx, currentRowNum, totalRowNum) {
		_updateDetailPagination(ctx, currentRowNum, totalRowNum);
	});

	apiRegister('editForm.getRowSelected()', function (dt, actionType) {
		return _getRowSelected(dt, actionType);
	});

	apiRegister('editForm.deleteAllSelects()', function (dt) {
		return _deleteAllSelects(dt);
	});

	apiRegister('editForm.getLineByPageSelected()', function (ctx, linea) {
		return _getLineByPageSelected(ctx, linea);
	});

	apiRegister('editForm.getLineByPageSelectedReverse()', function (ctx, linea) {
		return _getLineByPageSelectedReverse(ctx, linea);
	});

	/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  * Initialisation
  */

	// DataTables creation - check if select has been defined in the options. Note
	// this required that the table be in the document! If it isn't then something
	// needs to trigger this method unfortunately. The next major release of
	// DataTables will rework the events and address this.
	$(document).on('plugin-init.dt', function (e, ctx) {
		if (e.namespace !== 'dt') {
			return;
		}

		if (ctx.oInit.formEdit !== undefined) {
			DataTable.editForm.init(new DataTable.Api(ctx));
			$(ctx.oInit.formEdit.detailForm).rup_dialog($.extend({}, {
				type: $.rup.dialog.DIV,
				autoOpen: false,
				modal: true,
				resizable: '',
				width: 569
			}, {}));
		}
	});

	return DataTable.editForm;
});
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))

/***/ }),
/* 204 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;var _typeof = typeof Symbol === "function" && typeof Symbol.iterator === "symbol" ? function (obj) { return typeof obj; } : function (obj) { return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj; };

/**
  * Módulo que permite toda la seleción simple
  *
  * @summary 		Extensión del componente RUP Datatable
  * @module			"rup.table.masterDetail"
  * @version     1.0.0
  * @license
  * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
  * Solo podrá usarse esta obra si se respeta la Licencia.
  * Puede obtenerse una copia de la Licencia en
  *
  *      http://ec.europa.eu/idabc/eupl.html
  *
  * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
  * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
  * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
  * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
  * que establece la Licencia.
  * @copyright   Copyright 2018 E.J.I.E., S.A.
  *
  */

(function (factory) {
	if (true) {
		// AMD
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(4)], __WEBPACK_AMD_DEFINE_RESULT__ = function ($) {
			return factory($, window, document);
		}.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else if ((typeof exports === 'undefined' ? 'undefined' : _typeof(exports)) === 'object') {
		// CommonJS
		module.exports = function (root, $) {
			if (!root) {
				root = window;
			}

			if (!$ || !$.fn.dataTable) {
				$ = require('datatables.net')(root, $).$;
			}

			return factory($, root, root.document);
		};
	} else {
		// Browser
		factory(jQuery, window, document);
	}
})(function ($, window, document, undefined) {
	'use strict';

	var DataTable = $.fn.dataTable;

	// Version information for debugger
	DataTable.masterDetail = {};

	DataTable.masterDetail.version = '1.2.4';

	/**
 * Se inicializa el componente select
 *
 * @name init
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 * 
 * @param {object} dt - Es el objeto datatable.
 *
 */
	DataTable.masterDetail.init = function (dt) {
		var ctx = dt.settings()[0];
		//se crear el hidden en el formulario. 
		var idHidden = ctx.oInit.masterDetail.master + '_selector_' + ctx.sTableId;
		idHidden = idHidden.replace("#", "");
		$('<input>').val('-1').attr({
			type: 'hidden',
			id: idHidden,
			name: ctx.oInit.masterDetail.masterPrimaryKey
		}).appendTo(ctx.oInit.$filterForm);
		var rowsBody = $(ctx.oInit.masterDetail.master + " > tbody");
		//Se edita el row/fila.
		rowsBody.on('click.DT', 'tr[role="row"]', function () {
			var tableMaster = $(ctx.oInit.masterDetail.master).DataTable();
			var rowSelected = tableMaster.rows('.selected').indexes();
			if (rowSelected[0] !== undefined) {
				//Se ha deseleccionado, no entrar.
				var row = tableMaster.rows(rowSelected).data();
				var id = DataTable.Api().rupTable.getIdPk(row[0]);
				$("#" + idHidden).val("" + id);
				$('#' + ctx.sTableId + '_filter_filterButton').click();
			}
		});
	};

	/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  * Local functions
  */

	/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  * DataTables selectors
  */

	/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  * DataTables API
  *
  * For complete documentation, please refer to the docs/api directory or the
  * DataTables site
  */

	// Local variables to improve compression
	var apiRegister = DataTable.Api.register;

	apiRegister('masterDetail()', function () {
		return this.iterator('table', function (ctx) {
			DataTable.masterDetail.init(new DataTable.Api(ctx));
		});
	});

	// Common events with suitable namespaces
	function namespacedEvents(config) {
		var unique = config._eventNamespace;

		return 'draw.dt.DT' + unique + ' select.dt.DT' + unique + ' deselect.dt.DT' + unique;
	}

	/* * * ** * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  * Initialisation
  */

	// DataTables creation - check if select has been defined in the options. Note
	// this required that the table be in the document! If it isn't then something
	// needs to trigger this method unfortunately. The next major release of
	// DataTables will rework the events and address this.
	$(document).on('preInit.dt.dtSelect', function (e, ctx) {
		if (e.namespace !== 'dt') {
			return;
		}
		if (ctx.oInit.masterDetail !== undefined) {
			DataTable.masterDetail.init(new DataTable.Api(ctx));
		}
	});

	return DataTable.masterDetail;
});

/***/ }),
/* 205 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function(jQuery) {var __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;var _typeof = typeof Symbol === "function" && typeof Symbol.iterator === "symbol" ? function (obj) { return typeof obj; } : function (obj) { return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj; };

/**
  * Módulo que permite toda multiFilter
  *
  * @summary 		Extensión del componente RUP Datatable
  * @module			"rup.table.multiFilter"
  * @version     1.0.0
  * @license
  * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
  * Solo podrá usarse esta obra si se respeta la Licencia.
  * Puede obtenerse una copia de la Licencia en
  *
  *      http://ec.europa.eu/idabc/eupl.html
  *
  * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
  * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
  * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
  * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
  * que establece la Licencia.
  * @copyright   Copyright 2018 E.J.I.E., S.A.
  *
  */

(function (factory) {
	if (true) {
		// AMD
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(4)], __WEBPACK_AMD_DEFINE_RESULT__ = function ($) {
			return factory($, window, document);
		}.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else if ((typeof exports === 'undefined' ? 'undefined' : _typeof(exports)) === 'object') {
		// CommonJS
		module.exports = function (root, $) {
			if (!root) {
				root = window;
			}

			if (!$ || !$.fn.dataTable) {
				$ = require('datatables.net')(root, $).$;
			}

			return factory($, root, root.document);
		};
	} else {
		// Browser
		factory(jQuery, window, document);
	}
})(function ($, window, document, undefined) {
	'use strict';

	var DataTable = $.fn.dataTable;

	// Version information for debugger
	DataTable.multiFilter = {};

	DataTable.multiFilter.version = '1.2.4';

	/**
 * Se inicializa el componente multiFilter
 *
 * @name init
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 * 
 * @param {object} dt - Es el objeto datatable.
 *
 */
	DataTable.multiFilter.init = function (dt) {
		var ctx = dt.settings()[0];
		//se preConfigura el filtro. 
		preConfigureMultifilter(ctx);

		postConfigureMultifilter(ctx);
	};

	/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  * Local functions
  */

	/**
 * Metodo que realiza la pre-configuración del plugin de filtrado múltiple del componente RUP Table.
 * Este método se ejecuta antes de la incialización del plugin.
 *
 * @name preConfigureMultifilter
 * @function
 * @param {object} settings - Parámetros de configuración del componente.
 */
	function preConfigureMultifilter(ctx) {
		var settings = ctx.oInit;
		var $dropdownDiaglogTemplate;

		//definincion de variables con los selectores
		settings.multiFilter.$dropdownDialog = $('#' + ctx.sTableId + '_multifilter_dropdownDialog');

		//definicion de variables con ids
		settings.multiFilter.dropdownDialogId = ctx.sTableId + '_multifilter_dropdownDialog';

		$dropdownDiaglogTemplate = getMultifilterDialogTemplate(ctx);

		settings.filter.$filterContainer.after($dropdownDiaglogTemplate);

		$('#' + ctx.sTableId).triggerHandler('tableMultiFilterBeforeConfigureMultifilter');
		configureMultifilter(ctx);
		$('#' + ctx.sTableId).triggerHandler('tableMultiFilterAfterConfigureMultifilter');

		// configuracion del resumen del filtro para que
		// apareza el nombre del filtro
		settings.multiFilter.fncFilterName = function (searchString) {

			if (settings.multiFilter.$comboLabel === undefined) {
				if (settings.multiFilter.$filterDefaultName !== undefined) searchString = settings.multiFilter.$filterDefaultName + '  {' + searchString + '}   ';
			} else if (settings.multiFilter.$comboLabel !== undefined && settings.$firstStartUp) {
				if (settings.multiFilter.$comboLabel.val() === '' && settings.multiFilter.$filterDefaultName !== undefined) {
					searchString = settings.multiFilter.$filterDefaultName + '  {' + searchString + '}   ';
				}
			} else if (settings.multiFilter.$comboLabel.val() !== '' && settings.multiFilter.$filterWithName) {
				settings.multiFilter.$filterWithName = false;
				searchString = settings.multiFilter.$comboLabel.val() + '  {' + searchString + '}   ';
			}
			return searchString;
		};
	}

	/**
 * Metodo que realiza la post-configuración del plugin de filtrado múltiple del componente RUP Table.
 * Este método se ejecuta antes de la inicialización del plugin.
 *
 * @name postConfigureMultifilter
 * @function
 * @fires module:rup_table#rupTable_multifilter_fillForm
 * @param {object} settings - Parámetros de configuración del componente.
 */
	function postConfigureMultifilter(ctx) {
		var settings = ctx.oInit;
		var $self = this,
		    dropdownButtonConfig;

		dropdownButtonConfig = $.rup.adapter[jQuery.fn.rup_table.plugins.core.defaults.adapter].multifilter.dropdown;

		$('#' + ctx.sTableId + '_filter_filterButton').rup_button({
			dropdown: {
				dropdownIcon: dropdownButtonConfig.dropdownIcon,
				dropdownDialog: settings.multiFilter.dropdownDialogId,
				dropdownDialogConfig: {
					title: dropdownButtonConfig.dropdownDialogConfig.title + $.rup.i18n.base.rup_table.plugins.multifilter.tittle,
					width: '450px',
					buttons: [{
						id: ctx.sTableId + '_multifilter_BtnSave',
						"class": 'btn-outline-primary',
						text: $.rup.i18n.base.rup_table.plugins.multifilter.save,
						click: function click() {

							if (_checkLabel(ctx)) {

								// creo objeto Filter con los datos del formulario del filtro
								var filter = _createFilterFromForm(ctx);

								var bfr = _validForm(ctx);
								if (bfr === false || bfr === 'stop') {
									settings.multiFilter.$feedback.rup_feedback('set', $.rup.i18n.base.rup_table.plugins.multifilter.errorValidate, 'error');
									return;
								}

								// añado el filtro
								$('#' + ctx.sTableId).triggerHandler('tableMultiFilterBeforeAddFilter');
								_addFilter(filter, ctx);
								$('#' + ctx.sTableId).triggerHandler('tableMultiFilterAfterAddFilter');
							}
						}

					}, {
						id: ctx.sTableId + '_multifilter_BtnApply',
						"class": 'btn-outline-primary',
						text: $.rup.i18n.base.rup_table.plugins.multifilter.apply,
						click: function click() {

							//Deshabilitar el nombre del filtro en el filterSummary una vez que ha terminado el filtro por defecto
							if (settings.$firstStartUp) {

								settings.$firstStartUp = false;
							}

							if (_checkLabel(ctx)) {
								settings.multiFilter.$filterWithName = true;

								var valorFiltro = _searchFilterInCombo(ctx);
								if (valorFiltro !== undefined) {
									//limpiamos el filtro
									$('#' + ctx.sTableId).triggerHandler('tableMultiFilterBeforeCleanFilterForm');
									_cleanFilterForm(ctx);
									$('#' + ctx.sTableId).triggerHandler('tableMultiFilterAfterCleanFilterForm');

									//Cargamos de nuevo el filtro en el formulario del filtro
									// rellenar el formulario del filtro

									_fillForm(valorFiltro, ctx);
									$('#' + ctx.sTableId + '_filter_filterButton').click();
									settings.multiFilter.$closeDialog.click();
								} else {
									settings.multiFilter.$feedback.rup_feedback('set', $.rup.i18n.base.rup_table.plugins.multifilter.errorNoexiste, 'error');
								}
							}
						}
					}, {
						id: ctx.sTableId + '_multifilter_BtnRemove',
						"class": 'btn-outline-primary',
						text: $.rup.i18n.base.rup_table.plugins.multifilter.remove,
						click: function click() {

							if (_checkLabel(ctx)) {

								// creo objeto Filter con los datos del formulario del filtro
								var filter = _createFilterFromForm(ctx);

								// borro el filtro
								$('#' + ctx.sTableId).triggerHandler('tableMultiFilterBeforeDeleteFilter');
								deleteFilter(filter, ctx);
								$('#' + ctx.sTableId).triggerHandler('tableMultiFilterAfterDeleteFilter');
							}
						}
					}, {
						text: $.rup.i18n.base.rup_table.plugins.multifilter.cancel,
						click: function click() {

							var filtroAnterior = settings.multiFilter.filtroAnterior;
							if (filtroAnterior !== null) {
								_fillForm(filtroAnterior, ctx);
							}
							//limpio el filtro del dropdownDIalog
							settings.multiFilter.$comboLabel.val('');
							settings.multiFilter.$closeDialog.click();
						},
						btnType: $.rup.dialog.LINK
					}]
				}
			}

		});

		//definincion de variables con los selectores
		settings.multiFilter.$dropdownButton = $('#' + ctx.sTableId + '_filter_filterButton_dropdown');
		settings.multiFilter.$combo = $('#' + ctx.sTableId + '_multifilter_combo');
		settings.multiFilter.$comboLabel = $('#' + ctx.sTableId + '_multifilter_combo_label');
		settings.multiFilter.$comboButton = $('#' + ctx.sTableId + '_multifilter_dropdownDialog .rup-combobox-toggle');
		settings.multiFilter.$defaultCheck = $('#' + ctx.sTableId + '_multifilter_defaultFilter');
		settings.multiFilter.$feedback = $('#' + ctx.sTableId + '_multifilter_dropdownDialog_feedback');
		settings.multiFilter.$closeDialog = $('#closeText_' + ctx.sTableId + '_multifilter_dropdownDialog');

		// dialog modal para no cambiar el filtro mientras
		// se gestionan los mismos
		$('#' + settings.multiFilter.dropdownDialogId).rup_dialog('setOption', 'modal', true);
		$('#' + settings.multiFilter.dropdownDialogId).rup_dialog('setOption', 'draggable', false);
		$('#' + settings.multiFilter.dropdownDialogId).rup_dialog('setOption', 'resizable', false);

		$('#' + settings.multiFilter.dropdownDialogId).parent().css('width', '500px');

		settings.multiFilter.$dropdownButton.on('click', function () {
			//guardo el filtroAnterior
			var valorFiltro = form2object(settings.filter.$filterContainer[0]);
			var xhrArray = $.rup_utils.jsontoarray(valorFiltro);
			settings.multiFilter.filtroAnterior = valorFiltro;

			//Foco al label al entrar al dialog
			settings.multiFilter.$comboLabel.focus();
		});

		_configCombo(ctx);

		settings.multiFilter.$feedback.rup_feedback({
			block: false
		});

		//gesión por filtroPorDefecto

		//bug IE que al cerrar el dialog con el combo desplegado , la lista del combo sigue abierta
		$('.rup-dropdown-dialog').on('dialogclose', function () {
			settings.multiFilter.$comboLabel.autocomplete('widget').hide();
		});

		//la primera vez que cancelas el filtroAnterior es el filtroPorDefecto
		var valorFiltro = form2object(settings.filter.$filterContainer[0]);
		var xhrArray = $.rup_utils.jsontoarray(valorFiltro);

		settings.multiFilter.filtroAnterior = valorFiltro;
		/*
  $self.on({
  	'rupTable_beforeAdd.multifilter.validate': function(){
  
  		//filterSettings.$filterContainer.rup_validate("resetForm");
  		if (multifilterSettings!==undefined){
  			if(!settings.$firstStartUp){
  				return settings.filter.$filterContainer.valid();
  			}else{
  				return null;
  			}
  		}else{
  			return settings.filter.$filterContainer.valid();
  		}
  	}
  
  });*/
	}

	/**
  * Función que elimina un filtro del multifiltro.
  *
  * @function  deleteFilter
  * @param {object} filter - Objeto json con la información del filtro a eliminar.
  * @example
  * deleteFilter, filter
  */
	function deleteFilter(filter, ctx) {

		var settings = ctx.oInit;

		//reiniciar filter salvado
		settings.multiFilter.$savedFilterName = undefined;
		settings.multiFilter.$savedFilterValue = undefined;

		if (settings.multiFilter.idFilter != null) {
			filter.filtro.filterSelector = settings.multiFilter.idFilter;
		}

		// delete
		$.rup_ajax({
			url: settings.urlBase + '/multiFilter/delete',
			type: 'POST',
			data: $.toJSON(filter),
			dataType: 'json',
			showLoading: false,
			contentType: 'application/json',
			async: false,
			success: function success(data, status, xhr) {
				settings.multiFilter.$feedback.rup_feedback('set', $.rup.i18n.base.rup_table.plugins.multifilter.ok, 'ok');
				settings.multiFilter.$combo.rup_autocomplete('set', '', '');
				settings.multiFilter.$comboLabel.data('tmp.loadObjects.term', null);
				settings.multiFilter.$comboLabel.data('loadObjects', {});

				settings.multiFilter.$comboLabel.data('tmp.data', {});

				if (settings.multiFilter.$comboLabel.autocomplete('widget').is(':visible')) {
					settings.multiFilter.$comboLabel.autocomplete('widget').hide();
				}

				if (data.filterFeedback == 'no_records') {
					settings.multiFilter.$feedback.rup_feedback('set', $.rup.i18n.base.rup_table.plugins.multifilter.noRecords, 'error');
				}
				$('#' + ctx.sTableId).triggerHandler('tableMultiFilterSuccessDeleteFilter');
			},
			complete: function complete() {
				$('#' + ctx.sTableId).triggerHandler('tableMultiFilterCompleteDeleteFilter');
			},
			error: function error(xhr, ajaxOptions, thrownError) {
				settings.multiFilter.$feedback.rup_feedback('set', $.rup.i18n.base.rup_table.plugins.multifilter.error, 'error');
				$('#' + ctx.sTableId).triggerHandler('tableMultiFilterErrorDeleteFilter');
			}
		});
	}

	/**
  * Función que añade un filtro al multifiltro
  *
  * @function  addFilter
 	 * @param {object} filter - Objeto json con la información del filtro a añadir.
 	 * @fires module:rup_table#rupTable_multifilter_beforeAdd
  * @example
  * $("#idComponente").rup_table("addFilter", filter);
  */
	function _addFilter(filter, ctx) {
		var settings = ctx.oInit;

		if (settings.multiFilter.idFilter != null) {
			filter.filtro.filterSelector = settings.multiFilter.idFilter;
		}

		// add Filter
		$.rup_ajax({
			url: settings.urlBase + '/multiFilter/add',
			type: 'POST',
			data: $.toJSON(filter),
			dataType: 'json',
			showLoading: false,
			contentType: 'application/json',
			async: false,
			beforeSend: function beforeSend(xhr, options) {
				return $self.triggerHandler('rupTable_multifilter_beforeAdd', [xhr, options]);
			},
			success: function success(data, status, xhr) {

				settings.multiFilter.$savedFilterName = data.filterName;
				settings.multiFilter.$savedFilterValue = data.filterValue;

				settings.multiFilter.$feedback.rup_feedback('set', $.rup.i18n.base.rup_table.plugins.multifilter.ok, 'ok');

				settings.multiFilter.$comboLabel.data('tmp.loadObjects.term', null);
				settings.multiFilter.$comboLabel.data('loadObjects', {});

				settings.multiFilter.$comboLabel.data('tmp.data', {});

				if (settings.multiFilter.$comboLabel.autocomplete('widget').is(':visible')) {
					settings.multiFilter.$comboLabel.autocomplete('widget').hide();
				}
				$('#' + ctx.sTableId).triggerHandler('tableMultiFilterSuccessAddFilter');
			},
			complete: function complete() {
				$('#' + ctx.sTableId).triggerHandler('tableMultiFilterCompleteAddFilter');
			},
			error: function error(xhr, ajaxOptions, thrownError) {
				settings.multiFilter.$feedback.rup_feedback('set', $.rup.i18n.base.rup_table.plugins.multifilter.error, 'error');
				$('#' + ctx.sTableId).triggerHandler('tableMultiFilterErrorAddFilter');
			}
		});
	}

	function _validForm(ctx) {

		var settings = ctx.oInit;
		if (settings.multiFilter !== undefined) {
			if (!settings.$firstStartUp) {
				return settings.filter.$filterContainer.valid();
			} else {
				return null;
			}
		} else {
			return settings.filter.$filterContainer.valid();
		}
	}

	/**
  * Genera el objeto json de datos de filtrado correspondiente al formulario empleado.
  *
  * @function _createFilterFromForm
 	 * @private
 	 * @param {object} settings - Propiedades de configuración del componente.
 	 * @return {object} - Objeto json con la información de filtrado del formulario.
  * @example
  * $self._createFilterFromForm(settings);
  */
	function _createFilterFromForm(ctx) {
		var settings = ctx.oInit;

		var dataForm = form2object(settings.filter.$filterContainer[0]);

		//cambiar la fecha a milisegundos para guardar en bd
		var fecha;
		$.each($('[ruptype=\'date\']', settings.filter.$filterContainer), function (index, item) {
			fecha = $(item).datepicker('getDate');
			if (fecha != null) dataForm[item.name] = fecha.getTime().toString();
		});

		var dataFormJson = $.toJSON(dataForm);

		var usuario;
		if (settings.multiFilter.userFilter != null) {
			usuario = settings.multiFilter.userFilter;
		} else {
			usuario = LOGGED_USER;
		}

		var filter = {

			filtro: {
				filterSelector: ctx.sTableId,
				filterName: settings.multiFilter.$comboLabel.val(),
				filterValue: dataFormJson,
				filterDefault: settings.multiFilter.$defaultCheck.is(':checked'),
				filterUser: usuario
			}
		};

		return filter;
	}

	/**
  * Valida el label que se introduce asociado al filtrado que se va a añadir.
  *
  * @function _checkLabel
 	 * @private
 	 * @param {object} settings - Propiedades de configuración del componente.
 	 * @return {boolean} - Devuelve si es válido o no el nombre introducido para el filtro.
  * @example
  * $self._configCombo(settings);
  */
	function _checkLabel(ctx) {
		var settings = ctx.oInit;

		if ($.trim(settings.multiFilter.$comboLabel.val()) === '') {

			settings.multiFilter.$feedback.rup_feedback('set', $.rup.i18n.base.rup_table.plugins.multifilter.emptyName, 'error');
			return false;
		} else if (settings.multiFilter.$comboLabel.val().length > settings.multiFilter.labelSize) {
			settings.multiFilter.$feedback.rup_feedback('set', $.rup.i18n.base.rup_table.plugins.multifilter.tooLong, 'error');

			return false;
		}
		return true;
	}

	/**
  * Inicializa los campos del formulario con los valores correspondientes al filtro seleccionado.
  *
  * @function _fillForm
  * @private
  * @param {object} filtroNuevo - Objeto json con los valores de filtrado.
  * @example
  * $self._fillForm(data);
  */
	function _fillForm(filtroNuevo, ctx) {
		var settings = ctx.oInit;
		$('#' + ctx.sTableId).triggerHandler('tableMultiFilterFillForm');
		//cambiar milisengudos a fecha (el formato de bd del  fecha es milisegundos)
		$('[ruptype=\'date\']', settings.filter.$filterContainer).each(function (index, elem) {

			var $campo = jQuery(elem);

			var fechaString;

			var jsonFecha = filtroNuevo[elem.name];
			if (jsonFecha !== undefined) {
				if (jsonFecha.search('/') == -1) {
					var dateFromJson = new Date(parseInt(jsonFecha));

					var dateFormat = $campo.data('datepicker').settings.dateFormat;

					if ($campo.data('datepicker').settings.datetimepicker) {
						// Cuando es fecha-hora
						var dateObj = { hour: dateFromJson.getHours(), minute: dateFromJson.getMinutes(), second: dateFromJson.getSeconds() };
						fechaString = $.datepicker.formatDate(dateFormat, dateFromJson) + ' ' + $.timepicker._formatTime(dateObj, 'hh:mm:ss');
					} else {
						// Solo fecha

						fechaString = $.datepicker.formatDate(dateFormat, dateFromJson);
					}

					filtroNuevo[elem.name] = fechaString;
				}
			}
		});

		// Formatear datos

		var xhrArray = $.rup_utils.jsontoarray(filtroNuevo);

		// rellenar el formulario
		$.rup_utils.populateForm(xhrArray, $('#' + ctx.sTableId + '_filter_form'));
	}

	/**
  * Inicializa el combo de selección de filtrado a aplicar en el formulario.
  *
  * @function _configCombo
 	 * @private
 	 * @param {object} settings - Propiedades de configuración del componente.
  * @example
  * $self._configCombo(settings);
  */
	function _configCombo(ctx) {
		var settings = ctx.oInit;

		settings.multiFilter.$comboLabel.on('change', function () {
			settings.filter.$filterSummary.html('<i></i>');
		});

		// si el filtro es el predefinido que aparezca en negrita
		if (settings.multiFilter.$comboLabel.data('uiAutocomplete') !== undefined) {
			settings.multiFilter.$comboLabel.data('uiAutocomplete')._renderItem = function (ul, item) {

				/*if (item.value) {
    	return $('<li></li>').data(
    		'item.autocomplete', item).append(
    		'<a><b>' + item.label + '</b></a>')
    		.appendTo(ul);
    } else {*/
				return $('<li></li>').data('item.autocomplete', item).append('<a>' + item.label + '</a>').appendTo(ul);
			};
		}

		jQuery('#' + ctx.sTableId + '_multifilter_combo_label').on('rupAutocomplete_loadComplete', function (event, data) {
			var count = -1;
			var objeto = $.grep(data, function (obj, i) {
				if (obj.filterDefault) {
					count = i;
					return obj;
				}
			});
			if (objeto !== undefined) {
				var link = $('#' + ctx.sTableId + '_multifilter_combo_menu a:eq(' + count + ')');
				link.css('font-weight', 'bold');
			}
		});

		settings.multiFilter.$comboLabel.off('blur click');

		settings.multiFilter.$comboLabel.attr('placeholder', $.rup.i18n.base.rup_table.plugins.multifilter.input);

		settings.multiFilter.$comboLabel.on('blur', function (event) {

			// Obtener datos de si viene de
			// seleccionar elemento o si el
			// menú de selección está
			// desplegado
			var selected = settings.multiFilter.$combo.data('selected'),
			    isShowingMenu = $('.ui-autocomplete:visible').length > 0 ? true : false;
			// Borrar índicador de que viene
			// de seleccionar elemento
			settings.multiFilter.$combo.data('selected', false);
			// Si es un evento de teclado
			// pero no es ENTER, omitir esta
			// función
			if (event.type === 'keydown' && event.keyCode !== 13) {
				return true;
			}

			if (isShowingMenu === true && event.type === 'keydown') {
				settings.multiFilter.$combo.focus();
				event.stopPropagation();
				return true;
			}

			var autoCompObject = $(event.currentTarget),
			    loadObjects = settings.multiFilter.$comboLabel.data('loadObjects');

			if (settings.getText === true) {
				settings.multiFilter.$combo.val(autoCompObject.val());
				settings.multiFilter.$combo.attr('rup_autocomplete_label', autoCompObject.val());
			} else {
				if (loadObjects[autoCompObject.val()] !== undefined) {
					settings.multiFilter.$combo.val(loadObjects[autoCompObject.val()]);
					settings.multiFilter.$combo.attr('rup_autocomplete_label', loadObjects[autoCompObject.val()]);
				} else {

					autoCompObject.autocomplete('close');
				}
			}
			// Si el evento es ENTER y viene
			// de seleccionar un elemento o
			// el menú se estaba mostrando,
			// omitir resto de funciones
			// (ej. buscar)
			if (event.type === 'keydown' && event.keyCode === 13 && (selected || isShowingMenu)) {
				return false;
			}
		});

		settings.multiFilter.$comboButton.off('click mousedown');

		settings.multiFilter.$comboButton.on('blur', function () {
			if (settings.multiFilter.$comboLabel.autocomplete('widget').is(':visible')) {
				settings.multiFilter.$comboLabel.autocomplete('widget').hide();
			}
		});

		settings.multiFilter.$comboButton.on('click', function () {
			if (settings.multiFilter.$comboLabel.autocomplete('widget').is(':visible')) {
				settings.multiFilter.$comboLabel.autocomplete('widget').hide();
			} else {
				settings.multiFilter.$comboLabel.autocomplete('search', '');
				settings.multiFilter.$comboLabel.autocomplete('widget').show();
				settings.multiFilter.$comboLabel.autocomplete('widget').trigger('focus');
			}
		});
	}

	/**
  * Devuelve la template html empleada para renderizar los controles del formulario de filtrado múltiple.
  *
  * @function  getMultifilterDialogTemplate
 	 * @param {object} settings - Propiedades de configuración del componente.
 	 * @return {object} - Objeto jQuery con el contenido html de la template.
  * @example
  * $("#idComponente").rup_table("getMultifilterDialogTemplate", settings);
  */
	function getMultifilterDialogTemplate(ctx) {
		var settings = ctx.oInit;
		var multifilterSettings = settings.multiFilter;

		var $dropdownDiaglogTemplate = jQuery('<div id="' + multifilterSettings.dropdownDialogId + '" style="display:none" class="rup_multifilter_dropdown">' + '<div id="' + multifilterSettings.dropdownDialogId + '_feedback"></div>' + '<form>' + '<fieldset class="dropdownButton-inputs">' + '<div id="' + multifilterSettings.dropdownDialogId + '_columna_cnt">' + '<div class="form-row">' + '<div id="' + multifilterSettings.dropdownDialogId + '_lineaCombo"  class="form-group fix-align col-sm">' + '<label for="' + ctx.sTableId + '_multifilter_combo" class="formulario_linea_label">' + $.rup.i18n.base.rup_table.plugins.multifilter.filters + '</label>' + '<input id="' + ctx.sTableId + '_multifilter_combo" class="rup_multifilter_selector" />' + '</div>' + '</div>' + '<div  class="form-row">' + '<div id="' + multifilterSettings.dropdownDialogId + '_lineaDefault" class="form-group col-sm">' + '<label for="' + ctx.sTableId + '_multifilter_defaultFilter" class="formulario_linea_label">' + $.rup.i18n.base.rup_table.plugins.multifilter.defaultFilter + '</label>' + '<input type="checkbox" id="' + ctx.sTableId + '_multifilter_defaultFilter" class="formulario_linea_input form-control"/>' + '</div>' + '</div>' + '</fieldset>' + '</form>' + '</div>');

		return $dropdownDiaglogTemplate;
	}

	/**
  * Realiza la configuración interna del plugin multifilter a partir de las propiedades de configuración indicadas.
  *
  * @function  configureMultifilter
 	 * @param {object} settings - Propiedades de configuración del componente.
  * @example
  * $("#idComponente").rup_table("configureMultifilter", settings);
  */
	function configureMultifilter(ctx) {
		var settings = ctx.oInit;
		settings.filter.$filterForm = $('#' + settings.sTableId + '_filter_form');

		var selector;
		if (settings.multiFilter.idFilter != null) {
			selector = settings.multiFilter.idFilter;
		} else {
			selector = ctx.sTableId;
		}

		var usuario;
		if (settings.multiFilter.userFilter != null) {
			usuario = settings.multiFilter.userFilter;
		} else {
			usuario = LOGGED_USER;
		}

		var getDefault;
		if (settings.multiFilter.getDefault != null) {
			getDefault = settings.multiFilter.getDefault;
		} else {
			getDefault = true;
		}

		jQuery('#' + ctx.sTableId + '_multifilter_combo').rup_autocomplete({
			source: settings.urlBase + '/multiFilter/getAll?filterSelector=' + selector + '&user=' + usuario,
			sourceParam: {
				label: 'filterName',
				value: 'filterDefault',
				data: 'filterValue',
				category: 'filter'
			},
			method: 'GET',
			contains: false,
			combobox: true,
			menuAppendTo: $('#' + settings.multiFilter.dropdownDialogId).parent(),
			appendTo: $('#' + settings.multiFilter.dropdownDialogId).parent(),
			select: function select() {

				var valorFiltro = _searchFilterInCombo(ctx);

				//limpiar Filtro
				$('#' + ctx.sTableId).triggerHandler('tableMultiFilterBeforeCleanFilterForm');
				_cleanFilterForm(ctx);
				$('#' + ctx.sTableId).triggerHandler('tableMultiFilterAfterCleanFilterForm');

				// rellenar el formulario del filtro
				_fillForm(valorFiltro, ctx);

				//

			}
		});

		jQuery('#' + ctx.sTableId + '_multifilter_combo_label').on('autocompleteopen', function () {
			$(this).data('uiAutocomplete').menu.element.css('zIndex', Number($('#' + settings.multiFilter.dropdownDialogId).parent().css('zIndex')) + 1);

			if ($(this).data('tmp.data') !== undefined) {
				var data = $(this).data('tmp.data');
				var count = -1;
				var objeto = $.grep(data, function (obj, i) {
					if (obj.filterDefault) {
						count = i;
						return obj;
					}
				});
				if (objeto !== undefined) {
					var link = $('#' + ctx.sTableId + '_multifilter_combo_menu a:eq(' + count + ')');
					link.css('font-weight', 'bold');
				}
			}
		});

		$('.jstree').on('rup_filter_treeLoaded', function (event, data) {
			$(this).rup_tree('setRupValue', data);
		});

		$('#' + ctx.sTableId + '_filter_cleanButton').on('click', function () {
			settings.multiFilter.$combo.rup_autocomplete('set', '', '');
			settings.filter.$filterSummary.html('<i></i>');
		});
	}

	/**
 * Limpia el filtro
 *
 * @name _clearFilter
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 *
 * @param {object} options Opciones del componente
 *
 */
	function _cleanFilterForm(ctx) {
		var options = ctx.oInit;
		options.$filterForm.resetForm();

		options.filter.$filterSummary.html(' <i></i>');
		jQuery('input,textarea', options.$filterForm).val('');
		jQuery('.ui-selectmenu-status', '.rup-table-filter-fieldset').text('--');
		$.rup_utils.populateForm([], options.$filterForm);
	}

	/**
  * Devuelve el json de filtrado asociado al filtro seleccionado en el combo.
  *
  * @function _searchFilterInCombo
 	 * @private
 	 * @param {object} settings - Propiedades de configuración del componente.
 	 * @return {object} - Json de filtrado asociado al filtro seleccionado en el combo.
  * @example
  * $self._searchFilterInCombo(settings);
  */
	function _searchFilterInCombo(ctx) {
		var settings = ctx.oInit;

		var name = $('#' + ctx.sTableId + '_multifilter_combo_label').val();

		var listaFiltros = $('#' + ctx.sTableId + '_multifilter_combo_label').data('tmp.data');
		// Busco el valor del filtro
		var objFiltro = $.grep(listaFiltros, function (obj, i) {
			if (obj.label === name) return obj;
		});

		var sourceParam = {
			label: 'filterName',
			value: 'filterDefault',
			data: 'filterValue' };

		if (sourceParam !== undefined) {
			if (sourceParam.label !== undefined) {
				objFiltro[0].label = objFiltro[0][sourceParam.label];
			}
			if (sourceParam.data !== undefined) {
				objFiltro[0].data = objFiltro[0][sourceParam.data];
			}
			if (sourceParam.value !== undefined) {
				objFiltro[0].value = objFiltro[0][sourceParam.value];
			}
		}

		// si es filtro por defecto,
		// checkeo el check "Filtro
		// por defecto"
		if (objFiltro.length !== 0) {
			settings.multiFilter.$defaultCheck.attr('checked', objFiltro[0].value);

			var valorFiltro = $.parseJSON(objFiltro[0].data);

			var xhrArray = [];

			xhrArray = $.rup_utils.jsontoarray(valorFiltro);
		}

		if (valorFiltro === undefined && settings.multiFilter.$savedFilterName !== undefined && settings.multiFilter.$savedFilterName === name) {
			valorFiltro = $.parseJSON(settings.multiFilter.$savedFilterValue);
		}
		return valorFiltro;
	}

	/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  * DataTables selectors
  */

	/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  * DataTables API
  *
  * For complete documentation, please refer to the docs/api directory or the
  * DataTables site
  */

	// Local variables to improve compression
	var apiRegister = DataTable.Api.register;

	apiRegister('multiFilter()', function () {
		return this.iterator('table', function (ctx) {
			DataTable.multiFilter.init(new DataTable.Api(ctx));
		});
	});

	apiRegister('multiFilter.fillForm()', function (valorFiltro, ctx) {
		return _fillForm(valorFiltro, ctx);
	});

	// Common events with suitable namespaces
	function namespacedEvents(config) {
		var unique = config._eventNamespace;

		return 'draw.dt.DT' + unique + ' select.dt.DT' + unique + ' deselect.dt.DT' + unique;
	}

	/* * * ** * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  * Initialisation
  */

	// DataTables creation - check if select has been defined in the options. Note
	// this required that the table be in the document! If it isn't then something
	// needs to trigger this method unfortunately. The next major release of
	// DataTables will rework the events and address this.
	$(document).on('preInit.dt.dtSelect', function (e, ctx) {
		if (e.namespace !== 'dt') {
			return;
		}
		if (ctx.oInit.multiFilter !== undefined) {
			DataTable.multiFilter.init(new DataTable.Api(ctx));
		}
	});

	return DataTable.multiFilter;
});
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))

/***/ }),
/* 206 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function(jQuery) {var __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;var _typeof = typeof Symbol === "function" && typeof Symbol.iterator === "symbol" ? function (obj) { return typeof obj; } : function (obj) { return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj; };

/**
  * Módulo que permite toda la multiseleción
  *
  * @summary 		Extensión del componente RUP Datatable
  * @module			"rup.table.multiSelect"
  * @version     1.0.0
  * @license
  * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
  * Solo podrá usarse esta obra si se respeta la Licencia.
  * Puede obtenerse una copia de la Licencia en
  *
  *      http://ec.europa.eu/idabc/eupl.html
  *
  * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
  * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
  * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
  * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
  * que establece la Licencia.
  * @copyright   Copyright 2018 E.J.I.E., S.A.
  *
  */

(function (factory) {
	if (true) {
		// AMD
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(4), __webpack_require__(6), __webpack_require__(8)], __WEBPACK_AMD_DEFINE_RESULT__ = function ($) {
			return factory($, window, document);
		}.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else if ((typeof exports === 'undefined' ? 'undefined' : _typeof(exports)) === 'object') {
		// CommonJS
		module.exports = function (root, $) {
			if (!root) {
				root = window;
			}

			if (!$ || !$.fn.dataTable) {
				$ = require('datatables.net')(root, $).$;
			}

			return factory($, root, root.document);
		};
	} else {
		// Browser
		factory(jQuery, window, document);
	}
})(function ($, window, document, undefined) {
	'use strict';

	var DataTable = $.fn.dataTable;

	// Version information for debugger
	DataTable.multiSelect = {};

	DataTable.multiSelect.version = '1.2.4';

	/**
 * Se inicializa el componente multiselect
 *
 * @name init
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 * 
 * @param {object} dt - Es el objeto datatable.
 *
 */
	DataTable.multiSelect.init = function (dt) {
		var ctx = dt.settings()[0];
		var init = ctx.oInit.multiSelect;
		var defaults = DataTable.defaults.multiSelect;
		var opts = init === undefined ? defaults : init;

		// Set defaults
		var items = 'row';
		var style = 'api';
		var blurable = false;
		var info = true;
		var selector = 'td:first-child';
		var className = 'selected tr-highlight';
		var setStyle = false;

		ctx._multiSelect = {};

		//se Inicializa las propiedades de los select.
		//ctx.multiselection = $self._initializeMultiselectionProps();

		_paintCheckboxSelect(ctx);

		// Initialisation customisations
		if (opts === true) {
			style = 'os';
			setStyle = true;
		} else if (typeof opts === 'string') {
			style = opts;
			setStyle = true;
		} else if ($.isPlainObject(opts)) {
			if (opts.blurable !== undefined) {
				blurable = opts.blurable;
			}

			if (opts.info !== undefined) {
				info = opts.info;
			}

			if (opts.items !== undefined) {
				items = opts.items;
			}

			if (opts.style !== undefined) {
				style = opts.style;
				setStyle = true;
			}

			if (opts.selector !== undefined) {
				selector = opts.selector;
			}

			if (opts.className !== undefined) {
				className = opts.className;
			}
		}

		dt.multiSelect.selector(selector);
		dt.multiSelect.items(items);
		dt.multiSelect.style(style);
		dt.multiSelect.blurable(blurable);
		dt.multiSelect.info(info);
		ctx._multiSelect.className = className;

		// Sort table based on selected rows. Requires Select Datatables extension
		$.fn.dataTable.ext.order['select-checkbox'] = function (settings, col) {
			return this.api().column(col, { order: 'index' }).nodes().map(function (td) {
				if (settings._multiSelect.items === 'row') {
					return $(td).parent().hasClass(settings._multiSelect.className);
				} else if (settings._multiSelect.items === 'cell') {
					return $(td).hasClass(settings._multiSelect.className);
				}
				return false;
			});
		};

		// If the init options haven't enabled select, but there is a selectable
		// class name, then enable
		if (!setStyle && $(dt.table().node()).hasClass('selectable')) {
			dt.smultiSelect.style('os');
		}
	};

	/*
 
 Select is a collection of API methods, event handlers, event emitters and
 buttons (for the `Buttons` extension) for DataTables. It provides the following
 features, with an overview of how they are implemented:
 
 ## Selection of rows, columns and cells. Whether an item is selected or not is
    stored in:
 
 * rows: a `_select_selected` property which contains a boolean value of the
   DataTables' `aoData` object for each row
 * columns: a `_select_selected` property which contains a boolean value of the
   DataTables' `aoColumns` object for each column
 * cells: a `_selected_cells` property which contains an array of boolean values
   of the `aoData` object for each row. The array is the same length as the
   columns array, with each element of it representing a cell.
 
 This method of using boolean flags allows Select to operate when nodes have not
 been created for rows / cells (DataTables' defer rendering feature).
 
 ## API methods
 
 A range of API methods are available for triggering selection and de-selection
 of rows. Methods are also available to configure the selection events that can
 be triggered by an end user (such as which items are to be selected). To a large
 extent, these of API methods *is* Select. It is basically a collection of helper
 functions that can be used to select items in a DataTable.
 
 Configuration of select is held in the object `_select` which is attached to the
 DataTables settings object on initialisation. Select being available on a table
 is not optional when Select is loaded, but its default is for selection only to
 be available via the API - so the end user wouldn't be able to select rows
 without additional configuration.
 
 The `_select` object contains the following properties:
 
 ```
 {
 	items:string     - Can be `rows`, `columns` or `cells`. Defines what item
 	                   will be selected if the user is allowed to activate row
 	                   selection using the mouse.
 	style:string     - Can be `none`, `single`, `multi` or `os`. Defines the
 	                   interaction style when selecting items
 	blurable:boolean - If row selection can be cleared by clicking outside of
 	                   the table
 	info:boolean     - If the selection summary should be shown in the table
 	                   information elements
 }
 ```
 
 In addition to the API methods, Select also extends the DataTables selector
 options for rows, columns and cells adding a `selected` option to the selector
 options object, allowing the developer to select only selected items or
 unselected items.
 
 ## Mouse selection of items
 
 Clicking on items can be used to select items. This is done by a simple event
 handler that will select the items using the API methods.
 
  */

	/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  * Local functions
  */

	/**
  * Add one or more cells to the selection when shift clicking in OS selection
  * style cell selection.
  *
  * Cell range is more complicated than row and column as we want to select
  * in the visible grid rather than by index in sequence. For example, if you
  * click first in cell 1-1 and then shift click in 2-2 - cells 1-2 and 2-1
  * should also be selected (and not 1-3, 1-4. etc)
  *
  * @name cellRange
  * @function
  * @since UDA 3.4.0 // Datatable 1.0.0 
  * 
  * @param  {DataTable.Api} dt   DataTable
  * @param  {object}        idx  Cell index to select to
  * @param  {object}        last Cell index to select from
  * 
  */
	function cellRange(dt, idx, last) {
		var indexes;
		var columnIndexes;
		var rowIndexes;
		var selectColumns = function selectColumns(start, end) {
			if (start > end) {
				var tmp = end;
				end = start;
				start = tmp;
			}

			var record = false;
			return dt.columns(':visible').indexes().filter(function (i) {
				if (i === start) {
					record = true;
				}

				if (i === end) {
					// not else if, as start might === end
					record = false;
					return true;
				}

				return record;
			});
		};

		var selectRows = function selectRows(start, end) {
			var indexes = dt.rows({ search: 'applied' }).indexes();

			// Which comes first - might need to swap
			if (indexes.indexOf(start) > indexes.indexOf(end)) {
				var tmp = end;
				end = start;
				start = tmp;
			}

			var record = false;
			return indexes.filter(function (i) {
				if (i === start) {
					record = true;
				}

				if (i === end) {
					record = false;
					return true;
				}

				return record;
			});
		};

		if (!dt.cells({ selected: true }).any() && !last) {
			// select from the top left cell to this one
			columnIndexes = selectColumns(0, idx.column);
			rowIndexes = selectRows(0, idx.row);
		} else {
			// Get column indexes between old and new
			columnIndexes = selectColumns(last.column, idx.column);
			rowIndexes = selectRows(last.row, idx.row);
		}

		indexes = dt.cells(rowIndexes, columnIndexes).flatten();

		if (!dt.cells(idx, { selected: true }).any()) {
			// Select range
			dt.cells(indexes).select();
		} else {
			// Deselect range
			dt.cells(indexes).deselect();
		}
	}

	/**
  * Disable mouse selection by removing the selectors
  *
  * @name disabledMouseSelection
  * @function
  * @since UDA 3.4.0 // Datatable 1.0.0
  * 
  * @param {DataTable.Api} dt DataTable to remove events from
  * e
  */
	function disableMouseSelection(dt) {
		var ctx = dt.settings()[0];
		var selector = ctx._multiSelect.selector;

		$(dt.table().container()).off('mousedown.dtSelect', selector).off('mouseup.dtSelect', selector).off('click.dtSelect', selector);

		$('body').off('click.dtSelect' + dt.table().node().id);
	}

	/**
  * Attach mouse listeners to the table to allow mouse selection of items
  *
  * @name enableMouseSelection
  * @function
  * @since UDA 3.4.0 // Datatable 1.0.0
  * 
  * @param {DataTable.Api} dt DataTable to remove events from
  * 
  */
	function enableMouseSelection(dt) {
		var container = $(dt.table().container());
		var ctx = dt.settings()[0];
		var selector = ctx._multiSelect.selector;

		container.on('mousedown.dtSelect', selector, function (e) {
			// Disallow text selection for shift clicking on the table so multi
			// element selection doesn't look terrible!
			if (e.shiftKey || e.metaKey || e.ctrlKey) {
				container.css('-moz-user-select', 'none').one('selectstart.dtSelect', selector, function () {
					return false;
				});
			}
		}).on('mouseup.dtSelect', selector, function () {
			// Allow text selection to occur again, Mozilla style (tested in FF
			// 35.0.1 - still required)
			container.css('-moz-user-select', '');
		}).on('click.dtSelect', selector, function (e) {
			var items = dt.multiSelect.items();
			var idx;

			// If text was selected (click and drag), then we shouldn't change
			// the row's selected state
			if (window.getSelection) {
				var selection = window.getSelection();

				// If the element that contains the selection is not in the table, we can ignore it
				// This can happen if the developer selects text from the click event
				if (!selection.anchorNode || $(selection.anchorNode).closest('table')[0] === dt.table().node()) {
					if ($.trim(selection.toString()) !== '') {
						return;
					}
				}
			}

			var ctx = dt.settings()[0];

			// Ignore clicks inside a sub-table
			if ($(e.target).closest('div.dataTables_wrapper')[0] != dt.table().container()) {
				return;
			}

			var cell = dt.cell($(e.target).closest('td, th'));

			// Check the cell actually belongs to the host DataTable (so child
			// rows, etc, are ignored)
			if (!cell.any()) {
				return;
			}

			var event = $.Event('user-select.dt');
			eventTrigger(dt, event, [items, cell, e]);

			if (event.isDefaultPrevented()) {
				return;
			}

			var cellIndex = cell.index();
			if (items === 'row') {
				idx = cellIndex.row;
				typeSelect(e, dt, ctx, 'row', idx);
			} else if (items === 'column') {
				idx = cell.index().column;
				typeSelect(e, dt, ctx, 'column', idx);
			} else if (items === 'cell') {
				idx = cell.index();
				typeSelect(e, dt, ctx, 'cell', idx);
			}

			ctx._multiSelect_lastCell = cellIndex;
		});

		// Blurable
		$('body').on('click.dtSelect' + dt.table().node().id, function (e) {
			if (ctx._multiSelect.blurable) {
				// If the click was inside the DataTables container, don't blur
				if ($(e.target).parents().filter(dt.table().container()).length) {
					return;
				}

				// Ignore elements which have been removed from the DOM (i.e. paging
				// buttons)
				if ($(e.target).parents('html').length === 0) {
					return;
				}

				// Don't blur in Editor form
				if ($(e.target).parents('div.DTE').length) {
					return;
				}

				clear(ctx, true);
			}
		});
	}

	/**
  * Trigger an event on a DataTable
  *
  * @name eventTrigger
  * @function
  * @since UDA 3.4.0 // Datatable 1.0.0
  * 
  * @param {DataTable.Api} api      DataTable to trigger events on
  * @param  {boolean}      selected true if selected, false if deselected
  * @param  {string}       type     Item type acting on
  * @param  {boolean}      any      Require that there are values before
  *     triggering
  * 
  */
	function eventTrigger(api, type, args, any) {
		if (any && !api.flatten().length) {
			return;
		}

		if (typeof type === 'string') {
			type = type + '.dt';
		}

		args.unshift(api);

		$(api.table().node()).trigger(type, args);
	}

	/**
  * Update the information element of the DataTable showing information about the
  * items selected. This is done by adding tags to the existing text
  *
  * @name info
  * @function
  * @since UDA 3.4.0 // Datatable 1.0.0
  *
  * @param {DataTable.Api} api DataTable to update
  * 
  */
	function info(api) {
		var ctx = api.settings()[0];

		if (!ctx._multiSelect.info || !ctx.aanFeatures.i) {
			return;
		}

		if (api.multiSelect.style() === 'api') {
			return;
		}
		var DataTable = $.fn.dataTable;

		var rows = api.rows({ selected: true }).flatten().length;
		var columns = api.columns({ selected: true }).flatten().length;
		var cells = api.cells({ selected: true }).flatten().length;

		var add = function add(el, name, num) {
			name = jQuery.rup.i18nTemplate(ctx.oLanguage, 'fila');
			var sels = jQuery.rup.i18nTemplate(ctx.oLanguage, 'seleccionadas');
			var sel = jQuery.rup.i18nTemplate(ctx.oLanguage, 'seleccionada');
			el.append($('<span class="select-item"/>').append(api.i18n('select.' + name + 's', { _: '%d ' + name + 's ' + sels + '', 0: '', 1: '1 ' + name + ' ' + sel + '' }, num)));
		};

		rows = ctx.multiselection.numSelected;
		//Antes de mostrar la info se ha de ordenar.

		// Internal knowledge of DataTables to loop over all information elements
		$.each(ctx.aanFeatures.i, function (i, el) {
			el = $(el);

			var output = $('<span class="select-info"/>');
			add(output, 'row', rows);
			add(output, 'column', columns);
			add(output, 'cell', cells);

			var exisiting = el.children('span.select-info');
			if (exisiting.length) {
				exisiting.remove();
			}

			if (output.text() !== '') {
				el.append(output);
			}
		});

		$('#' + ctx.sTableId).triggerHandler('tableMultiSelectionRowNumberUpdate');
	}

	/**
  * Initialisation of a new table. Attach event handlers and callbacks to allow
  * Select to operate correctly.
  *
  * This will occur _after_ the initial DataTables initialisation, although
  * before Ajax data is rendered, if there is ajax data
  *
  * @name init
  * @function
  * @since UDA 3.4.0 // Datatable 1.0.0
  * 
  * @param  {DataTable.settings} ctx Settings object to operate on
  * 
  */
	function init(ctx) {
		var api = new DataTable.Api(ctx);

		// Row callback so that classes can be added to rows and cells if the item
		// was selected before the element was created. This will happen with the
		// `deferRender` option enabled.
		//
		// This method of attaching to `aoRowCreatedCallback` is a hack until
		// DataTables has proper events for row manipulation If you are reviewing
		// this code to create your own plug-ins, please do not do this!
		ctx.aoRowCreatedCallback.push({
			fn: function fn(row, data, index) {
				var i, ien;
				var d = ctx.aoData[index];

				// Row
				if (d._multiSelect_selected) {
					$(row).addClass(ctx._multiSelect.className);
				}

				// Cells and columns - if separated out, we would need to do two
				// loops, so it makes sense to combine them into a single one
				for (i = 0, ien = ctx.aoColumns.length; i < ien; i++) {
					if (ctx.aoColumns[i]._multiSelect_selected || d._selected_cells && d._selected_cells[i]) {
						$(d.anCells[i]).addClass(ctx._multiSelect.className);
					}
				}
			},
			sName: 'select-deferRender'
		});

		// On Ajax reload we want to reselect all rows which are currently selected,
		// if there is an rowId (i.e. a unique value to identify each row with)
		api.on('preXhr.dt.dtSelect', function () {
			// note that column selection doesn't need to be cached and then
			// reselected, as they are already selected
			var rows = api.rows({ selected: true }).ids(true).filter(function (d) {
				return d !== undefined;
			});

			var cells = api.cells({ selected: true }).eq(0).map(function (cellIdx) {
				var id = api.row(cellIdx.row).id(true);
				return id ? { row: id, column: cellIdx.column } : undefined;
			}).filter(function (d) {
				return d !== undefined;
			});

			// On the next draw, reselect the currently selected items
			api.one('draw.dt.dtSelect', function () {
				api.rows(rows).multiSelect();

				// `cells` is not a cell index selector, so it needs a loop
				if (cells.any()) {
					cells.each(function (id) {
						api.cells(id.row, id.column).multiSelect();
					});
				}
			});
		});

		// Update the table information element with selected item summary
		api.on('draw.dtSelect.dt select.dtSelect.dt deselect.dtSelect.dt info.dt', function () {
			info(api);
			_drawSelectId(api, ctx);
			//Comprobar si hay algun feedback activado
			var feedback = ctx.multiselection.internalFeedback;
			if (feedback.type !== undefined && feedback.type === 'eliminar') {
				var confDelay = ctx.oInit.feedback.okFeedbackConfig.delay;
				feedback.rup_feedback({ message: feedback.msgFeedBack, type: "ok", block: false });
				//Aseguramos que el estilo es correcto.
				setTimeout(function () {
					feedback.rup_feedback('destroy');
					feedback.css('width', '100%');
					$('#' + ctx.sTableId).triggerHandler('tableMultiSelectFeedbackDestroy');
				}, confDelay);
				feedback.type = '';
				feedback.msgFeedBack = '';
			}
		});

		// Clean up and release
		api.on('destroy.dtSelect', function () {
			disableMouseSelection(api);
			api.off('.dtSelect');
		});
	}

	/**
  * Pinta los elementos selecionables, porque tiene los ids almacenados y mete la clase que se le indica.
  *
  *
  * This will occur _after_ the initial DataTables initialisation, although
  * before Ajax data is rendered
  *
  * @name drawSelectId
  * @function
  * @since UDA 3.4.0 // Datatable 1.0.0
  *
  * @param  {DataTable.api} ctx
  * 
  */
	function _drawSelectId(api, ctx) {
		var DataTable = $.fn.dataTable;
		var pos = -1;

		$.each(ctx.multiselection.selectedIds, function (index, value) {
			var idx = -1;
			$.each(api.context[0].json.rows, function (indexData, valueData) {
				if (value === DataTable.Api().rupTable.getIdPk(valueData)) {
					idx = indexData;
					return false;
				}
			});
			if (idx >= 0) {
				api.context[0].aoData[idx]._multiSelect_selected = true;
				$(api.context[0].aoData[idx].nTr).addClass(api.context[0]._multiSelect.className);
				$(api.context[0].aoData[idx].nTr).triggerHandler('tableHighlightRowAsSelected');
				if (ctx.multiselection.lastSelectedId === value) {
					pos = idx;
				}
				if (pos === -1 && ctx.multiselection.lastSelectedId === '') {
					//En caso de que no hay ninguna coincidencia se pone el ultimo.
					pos = idx;
				}
			}
		});
		if (pos >= 0) {
			DataTable.Api().rupTable.selectPencil(api.context[0], pos);
		}
	}

	/**
  * Pinta la cabecera y pie del datatable con el checkbox all.
  *
  * @name paintCheckboxexSelect
  * @function
  * @since UDA 3.4.0 // Datatable 1.0.0
  *
  * @param  {DataTable.ctx} ctx Settings object to operate on
  *
  */
	function _paintCheckboxSelect(ctx) {
		var columnDefs = ctx.oInit.aoColumnDefs;
		if (columnDefs !== undefined && columnDefs[0].className !== undefined && columnDefs[0].className === 'select-checkbox') {
			//Se rellena todo, la columna select.

			var divHead = $("<div/>").attr('id', 'divSelectTableHead' + ctx.sTableId).addClass("divSelectTableHead");

			var input = $("<input/>").attr('id', 'inputSelectTableHead' + ctx.sTableId).attr('type', 'checkbox').addClass("hiddenInput");

			var label = $("<label/>").attr('id', 'labelSelectTableHead' + ctx.sTableId).attr('for', 'inputSelectTableHead' + ctx.sTableId).addClass("selectTableHead");

			var link = $("<a/>").addClass("ui-icon rup-datatable_checkmenu_arrow").attr('id', 'linkSelectTableHead' + ctx.sTableId);

			input.click(function () {
				var dt = new DataTable.Api(ctx);
				if (input.is(':checked')) {
					label.addClass("selectTableHeadCheck");
					link.addClass("rup-datatable_checkmenu_arrow_margin");
					selectAllPage(dt);
				} else {
					label.removeClass("selectTableHeadCheck");
					link.removeClass("rup-datatable_checkmenu_arrow_margin");
					deselectAllPage(dt);
				}
			});

			link.click(function () {
				var dt = new DataTable.Api(ctx);
				//Marcar todos
				if (ctx.multiselection.selectedAll && ctx.multiselection.deselectedIds.length === 0) {
					$("#contextMenu1 li.context-menu-icon-check").addClass('disabledDatatable');
					$("#contextMenu1 li.context-menu-icon-check_all").addClass('disabledDatatable');
					$("#contextMenu1 li.context-menu-icon-uncheck").removeClass('disabledDatatable');
					$("#contextMenu1 li.context-menu-icon-uncheck_all").removeClass('disabledDatatable');
					// Marcamos el check del tHead
					$("#labelSelectTableHead" + ctx.sTableId).addClass('selectTableHeadCheck');
					$("#linkSelectTableHead" + ctx.sTableId).addClass('rup-datatable_checkmenu_arrow_margin');
				};
				//Desmarcar todos
				if (!ctx.multiselection.selectedAll && ctx.multiselection.selectedIds.length === 0) {
					$("#contextMenu1 li.context-menu-icon-check").removeClass('disabledDatatable');
					$("#contextMenu1 li.context-menu-icon-check_all").removeClass('disabledDatatable');
					$("#contextMenu1 li.context-menu-icon-uncheck").addClass('disabledDatatable');
					$("#contextMenu1 li.context-menu-icon-uncheck_all").addClass('disabledDatatable');
					// Desmarcamos el check del tHead
					$("#labelSelectTableHead" + ctx.sTableId).removeClass('selectTableHeadCheck');
					$("#linkSelectTableHead" + ctx.sTableId).removeClass('rup-datatable_checkmenu_arrow_margin');
				};
				if (ctx.multiselection.selectedIds.length > 0) {
					$("#contextMenu1 li.context-menu-icon-uncheck_all").removeClass('disabledDatatable');
				}
				if (ctx.multiselection.deselectedIds.length > 0) {
					$("#contextMenu1 li.context-menu-icon-check_all").removeClass('disabledDatatable');
				}
				//Si la pagina esta completamente seleccionada
				if (checkPageSelectedAll(dt, true)) {
					$("#contextMenu1 li.context-menu-icon-uncheck_all").removeClass('disabledDatatable');
					$("#contextMenu1 li.context-menu-icon-uncheck").removeClass('disabledDatatable');
					$("#contextMenu1 li.context-menu-icon-check").addClass('disabledDatatable');
					// Marcamos el check del tHead
					$("#labelSelectTableHead" + ctx.sTableId).addClass('selectTableHeadCheck');
					$("#linkSelectTableHead" + ctx.sTableId).addClass('rup-datatable_checkmenu_arrow_margin');
				} else {
					$("#contextMenu1 li.context-menu-icon-check_all").removeClass('disabledDatatable');
					$("#contextMenu1 li.context-menu-icon-check").removeClass('disabledDatatable');
					// Desmarcamos el check del tHead
					$("#labelSelectTableHead" + ctx.sTableId).removeClass('selectTableHeadCheck');
					$("#linkSelectTableHead" + ctx.sTableId).removeClass('rup-datatable_checkmenu_arrow_margin');
				}

				//Si la pagina esta completamente deseleccionada
				if (checkPageSelectedAll(dt, false)) {
					$("#contextMenu1 li.context-menu-icon-check_all").removeClass('disabledDatatable');
					$("#contextMenu1 li.context-menu-icon-check").removeClass('disabledDatatable');
					$("#contextMenu1 li.context-menu-icon-uncheck").addClass('disabledDatatable');
					// Desmarcamos el check del tHead
					$("#labelSelectTableHead" + ctx.sTableId).removeClass('selectTableHeadCheck');
					$("#linkSelectTableHead" + ctx.sTableId).removeClass('rup-datatable_checkmenu_arrow_margin');
				} else {
					$("#contextMenu1 li.context-menu-icon-uncheck_all").removeClass('disabledDatatable');
					$("#contextMenu1 li.context-menu-icon-uncheck").removeClass('disabledDatatable');
					// Marcamos el check del tHead
					$("#labelSelectTableHead" + ctx.sTableId).addClass('selectTableHeadCheck');
					$("#linkSelectTableHead" + ctx.sTableId).addClass('rup-datatable_checkmenu_arrow_margin');
				}
			});

			if (ctx.oInit.headerContextMenu.show) {
				//Se mira si se quiere mostrar el menuContex
				_createContexMenuSelect($('#' + link[0].id), ctx);
				divHead.append(input, label, link);
			}

			if (ctx.nTable.tHead !== null) {
				var th = $(ctx.nTable.tHead.rows[0].cells[0]);
				th.append(divHead);
			}

			//Se aseguro que no sea orderable
			columnDefs[0].orderable = false;

			//Se genera el div para el feedback del datatable.
			var divFeedback = $('<div/>').attr('id', 'rup_feedback_' + ctx.sTableId).insertBefore('#' + ctx.sTableId).css('width', '100%');
			ctx.multiselection.internalFeedback = divFeedback;
		}
	}

	/**
 * Metodo que comprueba que todos los checks de la página están seleccionados
 *
 * @name checkPageSelectedAll
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 *
 * @param {object} dt - Es el objeto datatable.
 * @param {boolean} selected - Es true o false para saber cual de los 2 quieres buscar.
 *
 */
	function checkPageSelectedAll(dt, selected) {
		var count = 0;

		$.each(dt.rows().nodes().flatten(), function (idx, value) {
			if (selected && value.className.indexOf('selected') >= 0) {
				count++;
			} else if (!selected && value.className.indexOf('selected') < 0) {
				count++;
			}
		});
		if (dt.rows().nodes().flatten().length === count) {
			return true;
		}

		return false;
	}

	/**
 * Metodo que crea el contexMenu de la tabla
 *
 * @name createContexMenuSelect
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 * 
 * @param {string} id - Es el identificador del datatable.
 * @param {object} ctx - datatable.settings.
 *
 */
	function _createContexMenuSelect(id, ctx) {
		var items = {};
		var options = ctx.oInit;
		var dt = new DataTable.Api(ctx);

		if (options.headerContextMenu.selectAllPage) {
			jQuery.extend(items, {
				'selectAllPage': {
					name: $.rup.i18nParse($.rup.i18n.base, 'rup_datatable.plugins.multiselection.selectAllPage'),
					icon: 'check',
					disabled: function disabled(key, opt) {
						//
					},
					callback: function callback(key, options) {
						selectAllPage(dt);
					}
				}
			});
		}
		if (options.headerContextMenu.deselectAllPage) {
			jQuery.extend(items, {
				'deselectAllPage': {
					name: $.rup.i18nParse($.rup.i18n.base, 'rup_datatable.plugins.multiselection.deselectAllPage'),
					icon: 'uncheck',
					disabled: function disabled(key, opt) {
						//
					},
					callback: function callback(key, options) {
						deselectAllPage(dt);
					}
				}
			});
		}
		if (options.separator) {
			jQuery.extend(items, {
				'separator': ''
			});
		}
		if (options.headerContextMenu.selectAll) {
			jQuery.extend(items, {
				'selectAll': {
					name: $.rup.i18nParse($.rup.i18n.base, 'rup_datatable.plugins.multiselection.selectAll'),
					icon: 'check_all',
					disabled: function disabled(key, opt) {
						//
					},
					callback: function callback(key, options) {
						selectAll(dt);
					}
				}
			});
		}
		if (options.headerContextMenu.deselectAll) {
			jQuery.extend(items, {
				'deselectAll': {
					name: $.rup.i18nParse($.rup.i18n.base, 'rup_datatable.plugins.multiselection.deselectAll'),
					icon: 'uncheck_all',
					disabled: function disabled(key, opt) {
						//
					},
					callback: function callback(key, options) {
						deselectAll(dt);
					}
				}
			});
		}

		id.rup_contextMenu({
			trigger: 'left',
			items: items,
			position: function position(contextMenu, x, y) {
				contextMenu.$menu.css({
					top: this.parent().offset().top + this.parent().height(),
					left: this.parent().parent().offset().left
				});
			}
		});
	}

	/**
 * Metodo que selecciona todos los elementos de una misma página.
 *
 * @name selectAllPage
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 *
 * @param {object} dt - Datatable.
 *
 */
	function selectAllPage(dt) {
		var ctx = dt.settings()[0];
		ctx.multiselection.accion = "checkAll";
		dt['rows']().multiSelect();

		$("#contextMenu1 li.context-menu-icon-check").addClass('disabledDatatable');
		// Marcamos el check del tHead
		$("#labelSelectTableHead" + ctx.sTableId).addClass('selectTableHeadCheck');
		$("#linkSelectTableHead" + ctx.sTableId).addClass('rup-datatable_checkmenu_arrow_margin');

		//FeedBack
		var countPage = dt.page() + 1;
		var selectMsg = jQuery.rup.i18nTemplate(jQuery.rup.i18n.base, 'rup_datatable.selectMsg', '<b>' + dt.rows()[0].length + '</b>', '<b>' + countPage + '</b>');
		var selectRestMsg = jQuery.rup.i18nTemplate(jQuery.rup.i18n.base, 'rup_datatable.selectRestMsg', ctx.json.recordsTotal);
		var remainingSelectButton = jQuery.rup.i18nTemplate(jQuery.rup.i18n.base, 'rup_datatable.templates.multiselection.selectRemainingRecords', dt.context[0].sTableId, selectRestMsg, jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'selectAll'));
		if (!ctx.multiselection.selectedAll || ctx.multiselection.selectedAll && ctx.multiselection.deselectedIds.length > 0) {
			ctx.multiselection.internalFeedback.rup_feedback({ message: selectMsg + remainingSelectButton, type: "alert" });
			ctx.multiselection.internalFeedback.type = 'fijo';
			$('#' + ctx.sTableId).triggerHandler('tableMultiSelectFeedbackSelectAll');
		}
		$('#' + $(remainingSelectButton)[0].id).on('click', function (event) {
			selectAll(dt);
		});

		$('#' + ctx.multiselection.internalFeedback[0].id + '_closeDiv').on('click', function (event) {
			ctx.multiselection.internalFeedback.rup_feedback('destroy');
			ctx.multiselection.internalFeedback.css('width', '100%');
			$('#' + ctx.sTableId).triggerHandler('tableMultiSelectFeedbackDestroy');
		});

		//Se deja marcado el primero de la pagina.
		ctx.multiselection.lastSelectedId = dt.data()[0].id;
		DataTable.Api().rupTable.selectPencil(ctx, 0);
	}

	/**
 * Metodo que deselecciona todos los elementos de una misma página.
 *
 * @name deselectAllPage
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 * 
 * @param {object} dt - Datatable.
 *
 */
	function deselectAllPage(dt) {
		var ctx = dt.settings()[0];
		ctx.multiselection.accion = "uncheck";
		dt['rows']().deselect();

		$("#contextMenu1 li.context-menu-icon-uncheck").addClass('disabledDatatable');
		// Desmarcamos el check del tHead
		$("#labelSelectTableHead" + ctx.sTableId).removeClass('selectTableHeadCheck');
		$("#linkSelectTableHead" + ctx.sTableId).removeClass('rup-datatable_checkmenu_arrow_margin');

		//FeedBack
		var countPage = dt.page() + 1;
		var deselectMsg = jQuery.rup.i18nTemplate(jQuery.rup.i18n.base, 'rup_datatable.deselectMsg', '<b>' + dt.rows()[0].length + '</b>', '<b>' + countPage + '</b>');
		var selectRestMsg = jQuery.rup.i18nTemplate(jQuery.rup.i18n.base, 'rup_datatable.deselectRestMsg', ctx.multiselection.numSelected);
		var remainingDeselectButton = jQuery.rup.i18nTemplate(jQuery.rup.i18n.base, 'rup_datatable.templates.multiselection.deselectRemainingRecords', dt.context[0].sTableId, selectRestMsg, jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'deSelectAll'));
		if (ctx.multiselection.numSelected > 0) {
			ctx.multiselection.internalFeedback.rup_feedback({ message: deselectMsg + remainingDeselectButton, type: "alert" });
			ctx.multiselection.internalFeedback.type = 'fijo';
			$('#' + ctx.sTableId).triggerHandler('tableMultiSelectFeedbackDeselectAll');
		}
		$('#' + $(remainingDeselectButton)[0].id).on('click', function (event) {
			deselectAll(dt);
		});
		$('#' + ctx.sTableId + ' tbody tr td.select-checkbox span.ui-icon-pencil').remove();
	}

	/**
 * Metodo que selecciona todos los elementos.
 *
 * @name selectAll
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 *
 * @param {object} dt - Datatable.
 *
 */
	function selectAll(dt) {
		var ctx = dt.settings()[0];
		ctx.multiselection.selectedAll = true;
		ctx.multiselection.deselectedIds = [];
		ctx.multiselection.deselectedRowsPerPage = [];
		ctx.multiselection.numSelected = ctx.json.recordsTotal;
		ctx.multiselection.accion = "checkAll";
		$("#contextMenu1 li.context-menu-icon-check_all").addClass('disabledDatatable');
		$("#contextMenu1 li.context-menu-icon-check").addClass('disabledDatatable');
		// Marcamos el check del tHead
		$("#labelSelectTableHead" + ctx.sTableId).addClass('selectTableHeadCheck');
		$("#linkSelectTableHead" + ctx.sTableId).addClass('rup-datatable_checkmenu_arrow_margin');

		dt['rows']().multiSelect();
		if (dt.page() === 0) {
			DataTable.Api().rupTable.selectPencil(ctx, 0);
			ctx.multiselection.lastSelectedId = DataTable.Api().rupTable.getIdPk(dt.data()[0]);
		} else {
			DataTable.Api().rupTable.selectPencil(ctx, -1);
			ctx.multiselection.lastSelectedId = '';
		}

		$('#' + ctx.sTableId).triggerHandler('tableMultiSelectSelectAll');
	}

	/**
 * Metodo que deselecciona todos los elementos.
 *
 * @name deselectAll
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 *
 * @param {object} dt - Datatable.
 *
 */
	function deselectAll(dt) {
		var ctx = dt.settings()[0];
		$self._initializeMultiselectionProps(ctx);

		ctx.multiselection.accion = "uncheckAll";
		$('#' + ctx.sTableId + ' tbody tr td.select-checkbox span.ui-icon-pencil').remove();
		dt['rows']().deselect();
	}

	/**
  * Add one or more items (rows or columns) to the selection when shift clicking
  * in OS selection style
  *
  * @name rowColumnRange
  * @function
  * @since UDA 3.4.0 // Datatable 1.0.0
  * 
  * @param  {DataTable.Api} dt   DataTable
  * @param  {string}        type Row or column range selector
  * @param  {object}        idx  Item index to select to
  * @param  {object}        last Item index to select from
  * 
  */
	function rowColumnRange(dt, type, idx, last) {
		// Add a range of rows from the last selected row to this one
		var indexes = dt[type + 's']({ search: 'applied' }).indexes();
		var idx1 = $.inArray(last, indexes);
		var idx2 = $.inArray(idx, indexes);

		if (!dt[type + 's']({ selected: true }).any() && idx1 === -1) {
			// select from top to here - slightly odd, but both Windows and Mac OS
			// do this
			indexes.splice($.inArray(idx, indexes) + 1, indexes.length);
		} else {
			// reverse so we can shift click 'up' as well as down
			if (idx1 > idx2) {
				var tmp = idx2;
				idx2 = idx1;
				idx1 = tmp;
			}

			indexes.splice(idx2 + 1, indexes.length);
			indexes.splice(0, idx1);
		}

		if (!dt[type](idx, { selected: true }).any()) {
			// Select range
			dt[type + 's'](indexes).select();
		} else {
			// Deselect range - need to keep the clicked on row selected
			indexes.splice($.inArray(idx, indexes), 1);
			dt[type + 's'](indexes).deselect();
		}
	}

	/**
  * Clear all selected items
  *
  * @name clear
  * @function
  * @since UDA 3.4.0 // Datatable 1.0.0
  * 
  * @param  {DataTable.settings} ctx Settings object of the host DataTable
  * @param  {boolean} [force=false] Force the de-selection to happen, regardless
  *     of selection style
  * 
  */
	function clear(ctx, force) {
		if (force || ctx._multiSelect.style === 'single') {
			var api = new DataTable.Api(ctx);

			api.rows({ selected: true }).deselect();
			api.columns({ selected: true }).deselect();
			api.cells({ selected: true }).deselect();
		}
	}

	/**
  * Select items based on the current configuration for style and items.
  *
  * @name typeSelect
  * @function
  * @since UDA 3.4.0 // Datatable 1.0.0
  *
  * @param  {object}             e    Mouse event object
  * @param  {DataTables.Api}     dt   DataTable
  * @param  {DataTable.settings} ctx  Settings object of the host DataTable
  * @param  {string}             type Items to select
  * @param  {int|object}         idx  Index of the item to select
  * 
  */
	function typeSelect(e, dt, ctx, type, idx) {
		var style = dt.multiSelect.style();
		var isSelected = dt[type](idx, { selected: true }).any();

		if (style === 'os') {
			if (e.ctrlKey || e.metaKey) {
				// Add or remove from the selection
				dt[type](idx).multiSelect(!isSelected);
			} else if (e.shiftKey) {
				if (type === 'cell') {
					cellRange(dt, idx, ctx._multiSelect_lastCell || null);
				} else {
					rowColumnRange(dt, type, idx, ctx._multiSelect_lastCell ? ctx._multiSelect_lastCell[type] : null);
				}
			} else {
				// No cmd or shift click - deselect if selected, or select
				// this row only
				var selected = dt[type + 's']({ selected: true });

				if (isSelected && selected.flatten().length === 1) {
					dt[type](idx).deselect();
				} else {
					selected.deselect();
					dt[type](idx).select();
				}
			}
		} else if (style == 'multi+shift') {
			if (e.shiftKey) {
				if (type === 'cell') {
					cellRange(dt, idx, ctx._multiSelect_lastCell || null);
				} else {
					rowColumnRange(dt, type, idx, ctx._multiSelect_lastCell ? ctx._multiSelect_lastCell[type] : null);
				}
			} else {
				dt[type](idx).multiSelect(!isSelected);
			}
		} else {
			dt[type](idx).multiSelect(!isSelected);
		}
	}

	/**
 * Metodo que inicialida las propiedades para el multiselect.
 *
 * @name initializeMultiselectionProps
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 *
 *
 */
	function _initializeMultiselectionProps(ctx) {
		var $self = {};
		// Se almacenan en los settings internos las estructuras de control de los registros seleccionados
		if ($self.multiselection === undefined) {
			$self.multiselection = {};
		}
		if (ctx.multiselection !== undefined) {
			$self.multiselection.internalFeedback = ctx.multiselection.internalFeedback;
		}
		// Flag indicador de selección de todos los registros
		$self.multiselection.selectedAll = false;
		// Numero de registros seleccionados
		$self.multiselection.numSelected = 0;
		// Propiedades de selección de registros
		$self.multiselection.selectedRowsPerPage = [];
		//$self.multiselection.selectedLinesPerPage = [];
		//$self.multiselection.selectedRows = [];
		$self.multiselection.selectedIds = [];
		$self.multiselection.lastSelectedId = "";
		//$self.multiselection.selectedPages = [];
		// Propiedades de deselección de registros
		$self.multiselection.deselectedRowsPerPage = [];
		//$self.multiselection.deselectedLinesPerPage = [];
		//$self.multiselection.deselectedRows = [];
		$self.multiselection.deselectedIds = [];
		$self.multiselection.accion = ""; //uncheckAll,uncheck
		//$self.multiselection.deselectedPages = [];
		$("#contextMenu1 li.context-menu-icon-uncheck").addClass('disabledDatatable');
		$("#contextMenu1 li.context-menu-icon-uncheck_all").addClass('disabledDatatable');
		// Desmarcamos el check del tHead
		$("#labelSelectTableHead" + ctx.sTableId).removeClass('selectTableHeadCheck');
		$("#linkSelectTableHead" + ctx.sTableId).removeClass('rup-datatable_checkmenu_arrow_margin');

		DataTable.Api().rupTable.selectPencil(ctx, -1);
		return $self.multiselection;
	};

	/**
 * Metodo que añade y quita los seleccionados.
 *
 * @name maintIdsRows
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 * 
 * @param  {DataTables.Api}     DataTable   DataTable
 * @param  {string}     id   - id seleccionado
 * @param  {boolean}    select   si es seleccionado o no
 * @param  {integer}    pagina   página en la que se encuentra el seleccionado
 * @param  {integer}    line   linea en la que se encuentra el seleccionado
 *
 */
	//1 select, 0 deselect
	function maintIdsRows(DataTable, id, select, pagina, line, ctx) {
		var indexInArray = -1;

		if (select) {
			// se elimina de los deselecionados
			indexInArray = jQuery.inArray(id, ctx.multiselection.deselectedIds);
			if (indexInArray > -1 && !pagina) {
				//Si se encuentra y además no se está paginando.
				ctx.multiselection.deselectedIds.splice(indexInArray, 1);
				ctx.multiselection.deselectedRowsPerPage.splice(indexInArray, 1);
				if (ctx.multiselection.numSelected === ctx.json.recordsTotal) {
					ctx.multiselection.selectedAll = true;
				}
			}
			if (id !== undefined && ctx.multiselection.selectedIds.indexOf(id) < 0) {
				var pos = 0;
				var arra = { id: id, page: ctx.json.page, line: line };
				//ctx.multiselection.selectedIds.splice(pos,0,id);
				//ctx.multiselection.selectedRowsPerPage.splice(pos,0,{id:id,page:ctx.json.page,line:line});

				//Inicio de ordenacion, Se ordena los selected ids.

				$.each(ctx.multiselection.selectedRowsPerPage, function (index, p) {
					if (arra.page < p.page) {
						pos = index;
						return false;
					} else if (arra.page === p.page) {
						// mirar linea
						if (arra.line < p.line) {
							pos = index;
							return false;
						} else {
							pos = index + 1; //Posible
						}
					} else if (arra.page > p.page) {
						pos = index + 1; //Posible
					}
				});

				ctx.multiselection.selectedIds.splice(pos, 0, id);
				ctx.multiselection.selectedRowsPerPage.splice(pos, 0, arra);

				//FIn ordenacion
			}
		} else {
			//Deselect
			indexInArray = jQuery.inArray(id, ctx.multiselection.selectedIds); //Se elimina el ids

			if (indexInArray > -1) {
				//se borra
				ctx.multiselection.selectedIds.splice(indexInArray, 1);
				ctx.multiselection.selectedRowsPerPage.splice(indexInArray, 1);
				if (ctx.multiselection.lastSelectedId === id) {
					ctx.multiselection.lastSelectedId = "";
				}
				DataTable.Api().rupTable.selectPencil(ctx, -1);
				if (ctx.multiselection.numSelected === 0) {
					ctx.multiselection.selectedAll = false;
				}
			}
			//Se mete el id para mantener el selectAll o no.
			if (id !== undefined && ctx.multiselection.deselectedIds.indexOf(id) < 0) {
				if (line === undefined) {
					$.each(ctx.json.rows, function (index, value) {
						if (DataTable.Api().rupTable.getIdPk(value) === id) {
							line = index;
							return false;
						}
					});
				}
				var posDeselect = 0;
				var arraDeselect = { id: id, page: ctx.json.page, line: line };

				//Inicio de ordenacion, Se ordena los selected ids.
				$.each(ctx.multiselection.deselectedRowsPerPage, function (index, p) {
					if (arraDeselect.page < p.page) {
						posDeselect = index;
						return false;
					} else if (arraDeselect.page === p.page) {
						// mirar linea
						if (arraDeselect.line < p.line) {
							posDeselect = index;
							return false;
						} else {
							posDeselect = index + 1; //Posible
						}
					} else if (arraDeselect.page > p.page) {
						posDeselect = index + 1; //Posible
					}
				});

				ctx.multiselection.deselectedIds.splice(posDeselect, 0, id);
				ctx.multiselection.deselectedRowsPerPage.splice(posDeselect, 0, arraDeselect);
				if (ctx.multiselection.lastSelectedId === id) {
					ctx.multiselection.lastSelectedId = '';
				}
				DataTable.Api().rupTable.selectPencil(ctx, -1);
			}
		}
	}

	/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  * DataTables selectors
  */

	// row and column are basically identical just assigned to different properties
	// and checking a different array, so we can dynamically create the functions to
	// reduce the code size
	$.each([{ type: 'row', prop: 'aoData' }, { type: 'column', prop: 'aoColumns' }], function (i, o) {
		DataTable.ext.selector[o.type].push(function (settings, opts, indexes) {
			var selected = opts.selected;
			var data;
			var out = [];

			if (selected === undefined) {
				return indexes;
			}

			for (var i = 0, ien = indexes.length; i < ien; i++) {
				data = settings[o.prop][indexes[i]];

				if (selected === true && data._multiSelect_selected === true || selected === false && !data._multiSelect_selected) {
					out.push(indexes[i]);
				}
			}

			return out;
		});
	});

	DataTable.ext.selector.cell.push(function (settings, opts, cells) {
		var selected = opts.selected;
		var rowData;
		var out = [];

		if (selected === undefined) {
			return cells;
		}

		for (var i = 0, ien = cells.length; i < ien; i++) {
			rowData = settings.aoData[cells[i].row];

			if (selected === true && rowData._selected_cells && rowData._selected_cells[cells[i].column] === true || selected === false && (!rowData._selected_cells || !rowData._selected_cells[cells[i].column])) {
				out.push(cells[i]);
			}
		}

		return out;
	});

	/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  * DataTables API
  *
  * For complete documentation, please refer to the docs/api directory or the
  * DataTables site
  */

	// Local variables to improve compression
	var apiRegister = DataTable.Api.register;
	var apiRegisterPlural = DataTable.Api.registerPlural;

	apiRegister('multiSelect()', function () {
		return this.iterator('table', function (ctx) {
			DataTable.multiSelect.init(new DataTable.Api(ctx));
		});
	});

	apiRegister('multiSelect.blurable()', function (flag) {
		if (flag === undefined) {
			return this.context[0]._multiSelect.blurable;
		}

		return this.iterator('table', function (ctx) {
			ctx._multiSelect.blurable = flag;
		});
	});

	apiRegister('multiSelect.info()', function (flag) {
		if (info === undefined) {
			return this.context[0]._multiSelect.info;
		}

		return this.iterator('table', function (ctx) {
			ctx._multiSelect.info = flag;
		});
	});

	apiRegister('multiSelect.items()', function (items) {
		if (items === undefined) {
			return this.context[0]._multiSelect.items;
		}

		return this.iterator('table', function (ctx) {
			ctx._multiSelect.items = items;

			eventTrigger(new DataTable.Api(ctx), 'selectItems', [items]);
		});
	});

	// Takes effect from the _next_ selection. None disables future selection, but
	// does not clear the current selection. Use the `deselect` methods for that
	apiRegister('multiSelect.style()', function (style) {
		if (style === undefined) {
			return this.context[0]._multiSelect.style;
		}

		return this.iterator('table', function (ctx) {
			ctx._multiSelect.style = style;

			if (!ctx._multiSelect_init) {
				init(ctx);
			}

			// Add / remove mouse event handlers. They aren't required when only
			// API selection is available
			var dt = new DataTable.Api(ctx);
			disableMouseSelection(dt);

			if (style !== 'api') {
				enableMouseSelection(dt);
			}

			eventTrigger(new DataTable.Api(ctx), 'selectStyle', [style]);
		});
	});

	apiRegister('multiSelect.selector()', function (selector) {
		if (selector === undefined) {
			return this.context[0]._multiSelect.selector;
		}

		return this.iterator('table', function (ctx) {
			disableMouseSelection(new DataTable.Api(ctx));

			ctx._multiSelect.selector = selector;

			if (ctx._multiSelect.style !== 'api') {
				enableMouseSelection(new DataTable.Api(ctx));
			}
		});
	});

	apiRegister('multiSelect.deselectAll()', function (dt) {
		deselectAll(dt);
	});

	apiRegisterPlural('rows().multiSelect()', 'row().multiSelect()', function (multiSelect) {
		var api = this;
		var DataTable = $.fn.dataTable;
		var pagina = true;
		var ctx = api.context[0];

		if (ctx.multiselection === undefined) {
			return false;
		}
		//Al pagina comprobar el checkGeneral.

		//Se miral si hay feedback y en ese caso se elimina.
		var feedBack = ctx.multiselection.internalFeedback;
		if ($('#rup_feedback_' + ctx.sTableId).children().length > 1 && feedBack.type !== undefined && feedBack.type === 'fijo') {
			ctx.multiselection.internalFeedback.rup_feedback('destroy');
			ctx.multiselection.internalFeedback.css('width', '100%');
			$('#' + ctx.sTableId).triggerHandler('tableMultiSelectFeedbackDestroy');
		}

		if (multiSelect === false) {
			maintIdsRows(DataTable, DataTable.Api().rupTable.getIdPk(api.data()), 0, pagina, 0, ctx);
			//Cuando se resta de 1 en 1 la accion es empty
			ctx.multiselection.accion = '';
			var deselectes = this.deselect();
			return deselectes;
		}

		this.iterator('row', function (ctx, idx) {
			$(ctx.aoData[idx].nTr).triggerHandler('tableMultiSelectBeforeSelectRow');
			clear(ctx);
			pagina = false;
			ctx.aoData[idx]._multiSelect_selected = true;
			$(ctx.aoData[idx].nTr).addClass(ctx._multiSelect.className);
			var id = DataTable.Api().rupTable.getIdPk(ctx.aoData[idx]._aData);

			//Se mira el contador para sumar seleccionados
			if (ctx.multiselection.numSelected < ctx.json.recordsTotal && id !== undefined && ctx.multiselection.selectedIds.indexOf(id) < 0) {
				ctx.multiselection.numSelected++;
			}

			//para seleccionar todos los de la pagina actual.
			maintIdsRows(DataTable, id, 1, pagina, idx, ctx);
			//Se marca el ultimo.
			ctx.multiselection.lastSelectedId = id;
			$(ctx.aoData[idx].nTr).triggerHandler('tableMultiSelectAfterSelectRow');
		});
		if (pagina) {
			//Cuando se pagina, se filtra, o se reordena.
			if (ctx.multiselection.selectedAll) {
				//Si pagina y están todos sleccionados se pintan.
				var ctx = api.settings()[0];
				$.each(api.context[0].aoData, function (idx) {
					var id = DataTable.Api().rupTable.getIdPk(ctx.aoData[idx]._aData);
					//Si esta en la lista de deselecionados, significa que no debería marcarse.
					if (jQuery.inArray(id, ctx.multiselection.deselectedIds) === -1) {
						ctx.aoData[idx]._multiSelect_selected = true;
						$(ctx.aoData[idx].nTr).addClass(ctx._multiSelect.className);

						//para seleccionar todos los de la pagina actual.
						maintIdsRows(DataTable, id, 1, pagina, 0, ctx);
					}
				});
			}
			if (ctx.oInit.buttons !== undefined) {
				//Mirar la propiedad para el contex menu y dejar la clase marcada.
				$('#' + ctx.sTableId + ' > tbody > tr').addClass('context-menu-cursor');
			}
		}
		this.iterator('table', function (ctx, i) {
			eventTrigger(api, 'select', ['row', api[i]], true);
		});

		//al paginar
		var input = $("#divSelectTableHead" + ctx.sTableId + " :input");
		var label = $("#divSelectTableHead" + ctx.sTableId).find("label");
		var link = $("#divSelectTableHead" + ctx.sTableId).find("a");

		if (checkPageSelectedAll(api, true)) {
			input.attr('checked', true);
			label.addClass("selectTableHeadCheck");
			link.addClass("rup-datatable_checkmenu_arrow_margin");
		} else {
			input.attr('checked', false);
			label.removeClass("selectTableHeadCheck");
			link.removeClass("rup-datatable_checkmenu_arrow_margin");
		}

		return this;
	});

	apiRegisterPlural('columns().multiSelect()', 'column().multiSelect()', function (multiSelect) {
		var api = this;

		if (multiSelect === false) {
			return this.deselect();
		}

		this.iterator('column', function (ctx, idx) {
			clear(ctx);

			ctx.aoColumns[idx]._multiSelect_selected = true;

			var column = new DataTable.Api(ctx).column(idx);

			$(column.header()).addClass(ctx._multiSelect.className);
			$(column.footer()).addClass(ctx._multiSelect.className);

			column.nodes().to$().addClass(ctx._multiSelect.className);
		});

		this.iterator('table', function (ctx, i) {
			eventTrigger(api, 'multiSelect', ['column', api[i]], true);
		});

		return this;
	});

	apiRegisterPlural('cells().multiSelect()', 'cell().multiSelect()', function (multiSelect) {
		var api = this;

		if (multiSelect === false) {
			return this.deselect();
		}

		this.iterator('cell', function (ctx, rowIdx, colIdx) {
			clear(ctx);

			var data = ctx.aoData[rowIdx];

			if (data._selected_cells === undefined) {
				data._selected_cells = [];
			}

			data._selected_cells[colIdx] = true;

			if (data.anCells) {
				$(data.anCells[colIdx]).addClass(ctx._multiSelect.className);
			}
		});

		this.iterator('table', function (ctx, i) {
			eventTrigger(api, 'multiSelect', ['cell', api[i]], true);
		});

		return this;
	});

	apiRegisterPlural('rows().deselect()', 'row().deselect()', function () {
		var api = this;
		var DataTable = $.fn.dataTable;
		var ctx = api.context[0];
		//Se mira si hay feedback y en ese caso se elimina.
		var feedBack = ctx.multiselection.internalFeedback;
		if ($('#rup_feedback_' + ctx.sTableId).children().length > 1 && feedBack.type !== undefined && feedBack.type === 'fijo') {
			ctx.multiselection.internalFeedback.rup_feedback('destroy');
			ctx.multiselection.internalFeedback.css('width', '100%');
			$('#' + ctx.sTableId).triggerHandler('tableMultiSelectFeedbackDestroy');
		}

		this.iterator('row', function (ctx, idx) {
			ctx.aoData[idx]._multiSelect_selected = false;
			$(ctx.aoData[idx].nTr).removeClass(ctx._multiSelect.className);
			var id = DataTable.Api().rupTable.getIdPk(ctx.aoData[idx]._aData);

			//Se mira el contador para restar deselecionados.
			if (ctx.multiselection.numSelected > 0 && id !== undefined && ctx.multiselection.deselectedIds.indexOf(id) < 0) {
				ctx.multiselection.numSelected--;
			}

			//para deseleccionar todos los de la pagina actual.
			if (ctx.multiselection.numSelected > 0 && ctx.multiselection.accion === "uncheckAll" || ctx.multiselection.numSelected >= 0 && ctx.multiselection.accion === "uncheck") {
				maintIdsRows(DataTable, id, 0, false, 0, ctx);
			} else if (ctx.multiselection.accion === "") {
				//es que se resta uno solo.
				ctx.multiselection.numSelected--;
			}
		});

		this.iterator('table', function (ctx, i) {
			eventTrigger(api, 'deselect', ['row', api[i]], true);
		});

		//al paginar
		var input = $("#divSelectTableHead" + ctx.sTableId + " :input");
		var label = $("#divSelectTableHead" + ctx.sTableId).find("label");
		var link = $("#divSelectTableHead" + ctx.sTableId).find("a");

		if (checkPageSelectedAll(api, true)) {
			input.attr('checked', true);
			label.addClass("selectTableHeadCheck");
			link.addClass("rup-datatable_checkmenu_arrow_margin");
		} else {
			input.attr('checked', false);
			label.removeClass("selectTableHeadCheck");
			link.removeClass("rup-datatable_checkmenu_arrow_margin");
		}

		return this;
	});

	apiRegisterPlural('columns().deselect()', 'column().deselect()', function () {
		var api = this;

		this.iterator('column', function (ctx, idx) {
			ctx.aoColumns[idx]._multiSelect_selected = false;

			var api = new DataTable.Api(ctx);
			var column = api.column(idx);

			$(column.header()).removeClass(ctx._multiSelect.className);
			$(column.footer()).removeClass(ctx._multiSelect.className);

			// Need to loop over each cell, rather than just using
			// `column().nodes()` as cells which are individually selected should
			// not have the `selected` class removed from them
			api.cells(null, idx).indexes().each(function (cellIdx) {
				var data = ctx.aoData[cellIdx.row];
				var cellSelected = data._selected_cells;

				if (data.anCells && (!cellSelected || !cellSelected[cellIdx.column])) {
					$(data.anCells[cellIdx.column]).removeClass(ctx._multiSelect.className);
				}
			});
		});

		this.iterator('table', function (ctx, i) {
			eventTrigger(api, 'deselect', ['column', api[i]], true);
		});

		return this;
	});

	apiRegisterPlural('cells().deselect()', 'cell().deselect()', function () {
		var api = this;

		this.iterator('cell', function (ctx, rowIdx, colIdx) {
			var data = ctx.aoData[rowIdx];

			data._selected_cells[colIdx] = false;

			// Remove class only if the cells exist, and the cell is not column
			// selected, in which case the class should remain (since it is selected
			// in the column)
			if (data.anCells && !ctx.aoColumns[colIdx]._multiSelect_selected) {
				$(data.anCells[colIdx]).removeClass(ctx._multiSelect.className);
			}
		});

		this.iterator('table', function (ctx, i) {
			eventTrigger(api, 'deselect', ['cell', api[i]], true);
		});

		return this;
	});

	/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  * Buttons
  */
	function i18n(label, def) {
		return function (dt) {
			return dt.i18n('buttons.' + label, def);
		};
	}

	// Common events with suitable namespaces
	function namespacedEvents(config) {
		var unique = config._eventNamespace;

		return 'draw.dt.DT' + unique + ' multiSelect.dt.DT' + unique + ' deselect.dt.DT' + unique;
	}

	var _buttonNamespace = 0;

	$.extend(DataTable.ext.buttons, {
		selected: {
			text: i18n('selected', 'Selected'),
			className: 'buttons-selected',
			init: function init(dt, node, config) {
				var that = this;
				config._eventNamespace = '.multiSelect' + _buttonNamespace++;

				// .DT namespace listeners are removed by DataTables automatically
				// on table destroy
				dt.on(namespacedEvents(config), function () {
					var enable = that.rows({ selected: true }).any() || that.columns({ selected: true }).any() || that.cells({ selected: true }).any();

					that.enable(enable);
				});

				this.disable();
			},
			destroy: function destroy(dt, node, config) {
				dt.off(config._eventNamespace);
			}
		},
		selectedSingle: {
			text: i18n('selectedSingle', 'Selected single'),
			className: 'buttons-selected-single',
			init: function init(dt, node, config) {
				var that = this;
				config._eventNamespace = '.multiSelect' + _buttonNamespace++;

				dt.on(namespacedEvents(config), function () {
					var count = dt.rows({ selected: true }).flatten().length + dt.columns({ selected: true }).flatten().length + dt.cells({ selected: true }).flatten().length;

					that.enable(count === 1);
				});

				this.disable();
			},
			destroy: function destroy(dt, node, config) {
				dt.off(config._eventNamespace);
			}
		},
		selectAll: {
			text: i18n('selectAll', 'Select all'),
			className: 'buttons-select-all',
			action: function action() {
				var items = this.multiSelect.items();
				this[items + 's']().select();
			}
		},
		selectNone: {
			text: i18n('selectNone', 'Deselect all'),
			className: 'buttons-select-none',
			action: function action() {
				clear(this.settings()[0], true);
			},
			init: function init(dt, node, config) {
				var that = this;
				config._eventNamespace = '.multiSelect' + _buttonNamespace++;

				dt.on(namespacedEvents(config), function () {
					var count = dt.rows({ selected: true }).flatten().length + dt.columns({ selected: true }).flatten().length + dt.cells({ selected: true }).flatten().length;

					that.enable(count > 0);
				});

				this.disable();
			},
			destroy: function destroy(dt, node, config) {
				dt.off(config._eventNamespace);
			}
		}
	});

	$.each(['Row', 'Column', 'Cell'], function (i, item) {
		var lc = item.toLowerCase();

		DataTable.ext.buttons['multiSelect' + item + 's'] = {
			text: i18n('multiSelect' + item + 's', 'multiSelect ' + lc + 's'),
			className: 'buttons-select-' + lc + 's',
			action: function action() {
				this.select.items(lc);
			},
			init: function init(dt) {
				var that = this;

				dt.on('selectItems.dt.DT', function (e, ctx, items) {
					that.active(items === lc);
				});
			}
		};
	});

	/* * * ** * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  * Initialisation
  */

	// DataTables creation - check if select has been defined in the options. Note
	// this required that the table be in the document! If it isn't then something
	// needs to trigger this method unfortunately. The next major release of
	// DataTables will rework the events and address this.
	$(document).on('preInit.dt.dtSelect', function (e, ctx) {
		if (e.namespace !== 'dt') {
			return;
		}
		if (ctx.oInit.multiSelect !== undefined) {
			DataTable.multiSelect.init(new DataTable.Api(ctx));
		}
	});

	return DataTable.multiSelect;
});
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))

/***/ }),
/* 207 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;var _typeof = typeof Symbol === "function" && typeof Symbol.iterator === "symbol" ? function (obj) { return typeof obj; } : function (obj) { return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj; };

(function (root, factory) {
	if (true) {
		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else if ((typeof module === 'undefined' ? 'undefined' : _typeof(module)) === 'object' && module.exports) {
		// Node. Does not work with strict CommonJS, but
		// only CommonJS-like environments that support module.exports,
		// like Node.
		module.exports = factory();
	} else {
		// Browser globals (root is window)
		root.returnExports = factory();
	}
})(typeof self !== 'undefined' ? self : undefined, function () {

	var TableRequest = function TableRequest(data) {

		var start = data.start,
		    length = data.length,
		    page = start / length + 1,
		    sidx,
		    sord;

		if (data.order.length > 0) {
			sidx = data.columns[data.order[0].column].colSidx || data.columns[data.order[0].column].data;
			sord = data.order[0].dir;
		}

		// super(length, (start / length) + 1, 'id', 'asc');
		this._data = data;
		this._start = start;
		this._length = length;
		this._filter = data.filter;

		this._rows = length;
		this._page = page;
		this._sidx = sidx;
		this._sord = sord;
		this._filter = data.filter;
	};

	TableRequest.prototype = {

		set rows(rows) {
			this._rows = rows;
		},
		get rows() {
			return this._rows;
		},
		set page(page) {
			this._page = page;
		},
		get page() {
			return this._page;
		},
		set sidx(sidx) {
			this._sidx = sidx;
		},
		get sidx() {
			return this._sidx;
		},
		set sord(sord) {
			this._sord = sord;
		},
		get sord() {
			return this._sord;
		},
		set filter(filter) {
			this._filter = filter;
		},
		get filter() {
			return this._filter;
		}
	};

	/**
 	* Obtiene el objeto a mapear en el multiselect.
 	*
 	* @name getData
 	* @function
 	* @since UDA 3.4.0 // Datatable 1.0.0
 	*
 	* @return {TableRequest}
 	*
   */
	TableRequest.prototype.getData = function () {

		return {
			rows: this._rows,
			page: this._page,
			sidx: this._sidx,
			sord: this._sord,
			filter: this._filter,
			nd: Date.now(),
			core: {
				pkToken: '~',
				pkNames: ['id']
			}
		};
	};

	return TableRequest;
});

/***/ }),
/* 208 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;var _typeof = typeof Symbol === "function" && typeof Symbol.iterator === "symbol" ? function (obj) { return typeof obj; } : function (obj) { return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj; };

/*! RowGroup 1.0.2
 * ©2017 SpryMedia Ltd - datatables.net/license
 */

/**
 * @summary     RowGroup
 * @description RowGrouping for DataTables
 * @version     1.0.2
 * @file        rup.table.rowGroup.js
 *  
 * @contact     datatables.net
 * @copyright   Copyright 2017 SpryMedia Ltd.
 *
 * This source file is free software, available under the following license:
 *   MIT license - http://datatables.net/license/mit
 *
 * This source file is distributed in the hope that it will be useful, but
 * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
 * or FITNESS FOR A PARTICULAR PURPOSE. See the license files for details.
 *
 * For details please refer to: http://www.datatables.net
 */

(function (factory) {
	if (true) {
		// AMD
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(4)], __WEBPACK_AMD_DEFINE_RESULT__ = function ($) {
			return factory($, window, document);
		}.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else if ((typeof exports === 'undefined' ? 'undefined' : _typeof(exports)) === 'object') {
		// CommonJS
		module.exports = function (root, $) {
			if (!root) {
				root = window;
			}

			if (!$ || !$.fn.dataTable) {
				$ = require('datatables.net')(root, $).$;
			}

			return factory($, root, root.document);
		};
	} else {
		// Browser
		factory(jQuery, window, document);
	}
})(function ($, window, document, undefined) {
	'use strict';

	var DataTable = $.fn.dataTable;

	var RowGroup = function RowGroup(dt, opts) {
		// Sanity check that we are using DataTables 1.10 or newer
		if (!DataTable.versionCheck || !DataTable.versionCheck('1.10.8')) {
			throw 'RowGroup requires DataTables 1.10.8 or newer';
		}

		// User and defaults configuration object
		this.c = $.extend(true, {}, DataTable.defaults.rowGroup, RowGroup.defaults, opts);

		// Internal settings
		this.s = {
			dt: new DataTable.Api(dt),

			dataFn: DataTable.ext.oApi._fnGetObjectDataFn(this.c.dataSrc)
		};

		// DOM items
		this.dom = {};

		// Check if row grouping has already been initialised on this table
		var settings = this.s.dt.settings()[0];
		var existing = settings.rowGroup;
		if (existing) {
			return existing;
		}

		settings.rowGroup = this;
		this._constructor();
	};

	$.extend(RowGroup.prototype, {
		/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
   * API methods for DataTables API interface
   */

		/**
   * Get/set the grouping data source - need to call draw after this is
   * executed as a setter
   * @returns string~RowGroup
   */
		dataSrc: function dataSrc(val) {
			if (val === undefined) {
				return this.c.dataSrc;
			}

			var dt = this.s.dt;

			this.c.dataSrc = val;
			this.s.dataFn = DataTable.ext.oApi._fnGetObjectDataFn(this.c.dataSrc);

			$(dt.table().node()).triggerHandler('rowgroup-datasrc.dt', [dt, val]);

			return this;
		},

		/**
   * Disable - need to call draw after this is executed
   * @returns RowGroup
   */
		disable: function disable() {
			this.c.enable = false;
			return this;
		},

		/**
   * Enable - need to call draw after this is executed
   * @returns RowGroup
   */
		enable: function enable(flag) {
			if (flag === false) {
				return this.disable();
			}

			this.c.enable = true;
			return this;
		},

		/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
   * Constructor
   */
		_constructor: function _constructor() {
			var that = this;
			var dt = this.s.dt;

			dt.on('draw.dtrg', function () {
				if (that.c.enable) {
					that._draw();
				}
			});

			dt.on('column-visibility.dt.dtrg responsive-resize.dt.dtrg', function () {
				that._adjustColspan();
			});

			dt.on('destroy', function () {
				dt.off('.dtrg');
			});
		},

		/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
   * Private methods
   */

		/**
   * Adjust column span when column visibility changes
   * @private
   */
		_adjustColspan: function _adjustColspan() {
			$('tr.' + this.c.className, this.s.dt.table().body()).attr('colspan', this._colspan());
		},

		/**
   * Get the number of columns that a grouping row should span
   * @private
   */
		_colspan: function _colspan() {
			return this.s.dt.columns().visible().reduce(function (a, b) {
				return a + b;
			}, 0);
		},

		/**
   * Update function that is called whenever we need to draw the grouping rows
   * @private
   */
		_draw: function _draw() {
			var that = this;
			var dt = this.s.dt;
			var rows = dt.rows({ page: 'current' });
			var groupedRows = [];
			var last, display;

			rows.every(function () {
				var d = this.data();
				var group = that.s.dataFn(d);

				if (last === undefined || group !== last) {
					groupedRows.push([]);
					last = group;
				}

				groupedRows[groupedRows.length - 1].push(this.index());
			});

			for (var i = 0, ien = groupedRows.length; i < ien; i++) {
				var group = groupedRows[i];
				var firstRow = dt.row(group[0]);
				var groupName = this.s.dataFn(firstRow.data());
				var span = $('<span/>').addClass('cursor_pointer ui-icon tree-wrap-ltr ui-icon-circlesmall-minus');
				span.attr('identificador', i);

				if (this.c.startRender) {
					display = this.c.startRender.call(this, dt.rows(group), groupName);

					var trCreate = this._rowWrap(display, this.c.startClassName);

					trCreate.insertBefore(firstRow.node());

					$('td', trCreate).prepend(span);
					span.click(function () {
						var position = Number(this.getAttribute('identificador'));
						if ($(this).hasClass('ui-icon-circlesmall-minus')) {
							$(this.parentNode.parentElement).nextAll().slice(0, groupedRows[position].length).hide();
							$(this).addClass('ui-icon-circlesmall-plus');
							$(this).removeClass('ui-icon-circlesmall-minus');
						} else {
							$(this.parentNode.parentElement).nextAll().slice(0, groupedRows[position].length).show();
							$(this).addClass('ui-icon-circlesmall-minus');
							$(this).removeClass('ui-icon-circlesmall-plus');
						}
						$(this).triggerHandler('tablaGroupingClickGroup');
					});
				}

				if (this.c.endRender) {
					display = this.c.endRender.call(this, dt.rows(group), groupName);

					var trCreate = this._rowWrap(display, this.c.endClassName);

					trCreate.insertAfter(dt.row(group[group.length - 1]).node());

					$('td', trCreate).prepend(span);
					span.click(function () {
						var position = Number(this.getAttribute('identificador'));
						if ($(this).hasClass('ui-icon-circlesmall-minus')) {
							$(this.parentNode.parentElement).prevAll().slice(0, groupedRows[position].length).hide();
							$(this).addClass('ui-icon-circlesmall-plus');
							$(this).removeClass('ui-icon-circlesmall-minus');
						} else {
							$(this.parentNode.parentElement).prevAll().slice(0, groupedRows[position].length).show();
							$(this).addClass('ui-icon-circlesmall-minus');
							$(this).removeClass('ui-icon-circlesmall-plus');
						}
						$(this).triggerHandler('tablaGroupingClickGroup');
					});
				}
			}
		},

		/**
   * Take a rendered value from an end user and make it suitable for display
   * as a row, by wrapping it in a row, or detecting that it is a row.
   * @param [node|jQuery|string] display Display value
   * @param [string] className Class to add to the row
   * @private
   */
		_rowWrap: function _rowWrap(display, className) {
			var row;

			if ((typeof display === 'undefined' ? 'undefined' : _typeof(display)) === 'object' && display.nodeName && display.nodeName.toLowerCase() === 'tr') {
				row = $(display);
			} else if (display instanceof $ && display.length && display[0].nodeName.toLowerCase() === 'tr') {
				row = display;
			} else {
				row = $('<tr/>').append($('<td/>').attr('colspan', this._colspan()).append(display));
			}

			return row.addClass(this.c.className).addClass(className);
		}
	});

	/**
  * RowGroup default settings for initialisation
  *
  * @namespace
  * @name RowGroup.defaults
  * @static
  */
	RowGroup.defaults = {
		/**
   * Class to apply to grouping rows - applied to both the start and
   * end grouping rows.
   * @type string
   */
		className: 'group',

		/**
   * Data property from which to read the grouping information
   * @type string|integer
   */
		dataSrc: 0,

		/**
   * Initial enablement state
   * @boolean
   */
		enable: true,

		/**
   * Class name to give to the end grouping row
   * @type string
   */
		endClassName: 'group-end',

		/**
   * End grouping label function
   * @function
   */
		endRender: null,

		/**
   * Class name to give to the start grouping row
   * @type string
   */
		startClassName: 'group-start',

		/**
   * Start grouping label function
   * @function
   */
		startRender: function startRender(rows, group) {
			return group;
		}
	};

	RowGroup.version = "1.0.2";

	$.fn.dataTable.RowGroup = RowGroup;
	$.fn.DataTable.RowGroup = RowGroup;

	DataTable.Api.register('rowGroup()', function () {
		return this;
	});

	DataTable.Api.register('rowGroup().disable()', function () {
		return this.iterator('table', function (ctx) {
			if (ctx.rowGroup) {
				ctx.rowGroup.enable(false);
			}
		});
	});

	DataTable.Api.register('rowGroup().enable()', function (opts) {
		return this.iterator('table', function (ctx) {
			if (ctx.rowGroup) {
				ctx.rowGroup.enable(opts === undefined ? true : opts);
			}
		});
	});

	DataTable.Api.register('rowGroup().dataSrc()', function (val) {
		if (val === undefined) {
			return this.context[0].rowGroup.dataSrc();
		}

		return this.iterator('table', function (ctx) {
			if (ctx.rowGroup) {
				ctx.rowGroup.dataSrc(val);
			}
		});
	});

	// Attach a listener to the document which listens for DataTables initialisation
	// events so we can automatically initialise
	$(document).on('preInit.dt.dtrg', function (e, settings, json) {
		if (e.namespace !== 'dt') {
			return;
		}

		var init = settings.oInit.rowGroup;
		var defaults = DataTable.defaults.rowGroup;

		if (init || defaults) {
			var opts = $.extend({}, defaults, init);

			if (init !== false) {
				new RowGroup(settings, opts);
			}
		}
	});

	return RowGroup;
});

/***/ }),
/* 209 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function(jQuery) {var __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;var _typeof = typeof Symbol === "function" && typeof Symbol.iterator === "symbol" ? function (obj) { return typeof obj; } : function (obj) { return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj; };

/**
  * Buscador interno del datatable
  *
  * @summary 		Extensión del componente RUP Datatable
  * @module			"rup.table.seeker"
  * @version     1.0.0
  * @license
  * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
  * Solo podrá usarse esta obra si se respeta la Licencia.
  * Puede obtenerse una copia de la Licencia en
  *
  *      http://ec.europa.eu/idabc/eupl.html
  *
  * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
  * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
  * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
  * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
  * que establece la Licencia.
  * @copyright   Copyright 2018 E.J.I.E., S.A.
  *
  */

(function (factory) {
	if (true) {
		// AMD
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(4)], __WEBPACK_AMD_DEFINE_RESULT__ = function ($) {
			return factory($, window, document);
		}.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else if ((typeof exports === 'undefined' ? 'undefined' : _typeof(exports)) === 'object') {
		// CommonJS
		module.exports = function (root, $) {
			if (!root) {
				root = window;
			}

			if (!$ || !$.fn.dataTable) {
				$ = require('datatables.net')(root, $).$;
			}

			return factory($, root, root.document);
		};
	} else {
		// Browser
		factory(jQuery, window, document);
	}
})(function ($, window, document, undefined) {
	'use strict';

	var DataTable = $.fn.dataTable;

	// Version information for debugger
	DataTable.seeker = {};

	DataTable.seeker.version = '1.2.4';

	/**
  * 
 * Se inicializa el componente seeker
 *
 * @name init
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 * 
 * @param {object} dt - Es el objeto datatable.
 *
 */
	DataTable.seeker.init = function (dt) {

		var ctx = dt.settings()[0];
		//Se inicializa por cada instancia 1 tabla 1 instancia
		ctx.seeker = {};
		_createFilterColumn(dt, ctx);

		var ajaxOptions = {
			url: ctx.oInit.urlBase + '/search',
			accepts: { '*': '*/*', 'html': 'text/html', 'json': 'application/json, text/javascript',
				'script': 'text/javascript, application/javascript, application/ecmascript, application/x-ecmascript',
				'text': 'text/plain', 'xml': 'application/xml, text/xml' },
			type: 'POST',
			data: _getDatos(ctx),
			dataType: 'json',
			showLoading: false,
			contentType: 'application/json',
			async: true,
			success: function success(data, status, xhr) {
				$('#' + ctx.sTableId).triggerHandler('tableSeekerSearchSucess');
				ctx.seeker.search.funcionParams = data;
				ctx.seeker.search.pos = 0; // se inicializa por cada busqueda.
				_processData(dt, ctx, data);
			},
			error: function error(xhr, ajaxOptions, thrownError) {
				console.log('Errors ' + thrownError + ": " + xhr.responseText);
				$('#' + ctx.sTableId).triggerHandler('tableSeekerSearchError');
			},
			complete: function complete(xhr, status) {
				$('#' + ctx.sTableId).triggerHandler('tableSeekerSearchComplete');
			}
		};

		ctx.seeker.ajaxOption = ajaxOptions;

		//Ver el buscador interno de la tabla.
		if (ctx.fnRecordsTotal() === 0) {
			ctx.seeker.search.$searchRow.hide();
		} else {
			ctx.seeker.search.$searchRow.show();
		}

		$('#' + ctx.sTableId).triggerHandler('tableSeekerAfterCreateToolbar');
	};

	/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  * Local functions
  */

	function _eventTrigger(api, type, args, any) {
		if (any && !api.flatten().length) {
			return;
		}

		if (typeof type === 'string') {
			type = type + '.dt';
		}

		args.unshift(api);

		$(api.table().node()).trigger(type, args);
	}
	/**
 * Crea los componentes principales del buscador.
 *
 * @name createFilterColumn
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 * 
 * @param {object} dt - Es el objeto datatable.
 * @param {object} ctx - Es el contecto del datatable donde esta la configuración del mismo.
 *
 */
	function _createFilterColumn(dt, ctx) {

		var idTabla = ctx.sTableId;
		$('#' + idTabla + ' tfoot').css('display', 'table-header-group');
		$('#' + idTabla + ' tfoot th').each(function () {
			var title = $(this).text();
			if ($(this).index() > 0 || ctx.oInit.multiSelect === undefined) {
				var position = $(this).index() + 1;
				var nombre = $('#' + idTabla + ' thead th:nth-child(' + position + ')').attr('data-col-prop');
				$(this).html('<input type="text" placeholder="' + title + '" name="' + nombre + '" id="' + nombre + '_seeker"/>');
			}
		});

		dt.columns().eq(0).each(function (colIdx) {
			if (colIdx > 0) {
				$('input', $('#' + idTabla + ' tfoot')[0].rows[0].cells[colIdx]).on('keypress', function (ev) {
					this.focus();
					if (ev.keyCode === 13 && this.value !== '') {
						//Se hace la llamada de busqueda.
						ctx.seeker.ajaxOption.data = _getDatos(ctx);
						var ajaxOptions = $.extend(true, [], ctx.seeker.ajaxOption);
						//Se pasa sin el internalFeedback ya que no es necesario.
						if (ajaxOptions.data.multiselection !== undefined && ajaxOptions.data.multiselection.internalFeedback !== undefined) {
							ajaxOptions.data.multiselection.internalFeedback = [];
						}
						$('#' + ctx.sTableId).triggerHandler('tableSeekerBeforeSearch');
						$('#' + idTabla + '_search_searchForm').rup_form('ajaxSubmit', ajaxOptions);
						$('#' + ctx.sTableId).triggerHandler('tableSeekerAfterSearch');
					}
				});
			}
		});

		_createSearchRow(dt, ctx);
		ctx.seeker.searchForm = $('#' + idTabla + ' tfoot tr:nth-child(2)');
		ctx.seeker.searchForm.hide();
		_createRupComponent(dt, ctx);
	}
	/**
 * Genera la barra de controles para gestionar la búsqueda..
 *
 * @name createSearchRow
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 * 
 * @param {object} dt - Es el objeto datatable.
 * @param {object} ctx - Es el contexto del datatable donde esta la configuración del mismo.
 *
 */
	function _createSearchRow(dt, ctx) {
		var idTabla = ctx.sTableId;
		var $gridHead = jQuery('tfoot', '#' + idTabla),

		// Templates
		searchRowHeaderTmpl = jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.templates.search.searchRowHeader'),
		    collapseLayerTmpl = jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.templates.search.collapseLayer'),
		    collapseIconTmpl = jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.templates.search.collapseIcon'),
		    collapseLabelTmpl = jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.templates.search.collapseLabel'),
		    matchedLayerTmpl = jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.templates.search.matchedLayer'),
		    matchedLabelTmpl = jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.templates.search.matchedLabel'),
		    navLayerTmpl = jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.templates.search.navLayer'),
		    navButtonTmpl = jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.templates.search.navButton'),
		    navSearchButtonTmpl = jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.templates.search.navSearchButton'),
		    navClearButtonTmpl = jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.templates.search.navClearButton'),


		// Objetos
		$searchRow = $(jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.templates.search.searchRow')),
		    $searchRowHeader = $(jQuery.jgrid.format(searchRowHeaderTmpl, $gridHead.find('th').length)),

		// Capa que controla el colapso del formualario
		$collapseLayer = $(jQuery.jgrid.format(collapseLayerTmpl, 'searchCollapseLayer_' + idTabla)),
		    $collapseIcon = $(jQuery.jgrid.format(collapseIconTmpl, 'searchCollapseIcon_' + idTabla)),
		    $collapseLabel = $(jQuery.jgrid.format(collapseLabelTmpl, 'searchCollapsLabel_' + idTabla, jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.plugins.search.searchCriteria'))),

		// Capa que muestra el número de ocurrencias
		$matchedLayer = $(jQuery.jgrid.format(matchedLayerTmpl, 'matchedLayer_' + idTabla)),
		    $matchedLabel = $(jQuery.jgrid.format(matchedLabelTmpl, 'matchedLabel_' + idTabla, jQuery.jgrid.format(jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.plugins.search.matchedRecords'), 0))),


		// Capa que controla la navegación entre las diferentes ocurrencias
		$navLayer = $(jQuery.jgrid.format(navLayerTmpl, 'searchNavLayer_' + idTabla)),
		    $firstNavButton = $(jQuery.jgrid.format(navButtonTmpl, 'search_nav_first_' + idTabla, jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.first'))),
		    $backNavButton = $(jQuery.jgrid.format(navButtonTmpl, 'search_nav_back_' + idTabla, jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.previous'))),
		    $forwardNavButton = $(jQuery.jgrid.format(navButtonTmpl, 'search_nav_forward_' + idTabla, jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.next'))),
		    $lastNavButton = $(jQuery.jgrid.format(navButtonTmpl, 'search_nav_last_' + idTabla, jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.last'))),
		    $navSearchButton = $(jQuery.jgrid.format(navSearchButtonTmpl, 'search_nav_button_' + idTabla, jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.search.Find'))),
		    $navClearButton = $(jQuery.jgrid.format(navClearButtonTmpl, 'search_nav_clear_button' + idTabla, jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.search.Reset')));

		// Construcción del objeto final
		$collapseLayer.append($collapseIcon).append($collapseLabel);
		$matchedLayer.append($matchedLabel);
		$navLayer.append($firstNavButton).append($backNavButton).append($forwardNavButton).append($lastNavButton).append($navSearchButton).append($navClearButton);

		$searchRowHeader.append($collapseLayer);
		$searchRowHeader.append($matchedLayer);
		$searchRowHeader.append($navLayer);

		$searchRow.append($searchRowHeader);

		$gridHead.prepend($searchRow);
		jQuery('tfoot tr.search_row', '#' + idTabla + '').addClass('ui-state-default');

		ctx.seeker.search = ctx.seeker.search || {};

		ctx.seeker.search.created = false;

		ctx.seeker.search.$collapseIcon = $collapseIcon;
		ctx.seeker.search.$searchRow = $searchRow;
		ctx.seeker.search.$matchedLabel = $matchedLabel;
		ctx.seeker.search.$firstNavButton = $firstNavButton;
		ctx.seeker.search.$backNavButton = $backNavButton;
		ctx.seeker.search.$forwardNavButton = $forwardNavButton;
		ctx.seeker.search.$lastNavButton = $lastNavButton;

		// Creacion del enlace de mostrar/ocultar el formulario
		$collapseIcon.add($collapseLabel).on('click', function () {
			if (!ctx.seeker.search.created) {
				ctx.seeker.search.$collapseIcon.removeClass('ui-icon-triangle-1-e');
				ctx.seeker.search.$collapseIcon.addClass('ui-icon-triangle-1-s');
				ctx.seeker.search.created = true;
				ctx.seeker.searchForm.show();
				$navLayer.show();
			} else {
				ctx.seeker.search.$collapseIcon.removeClass('ui-icon-triangle-1-s');
				ctx.seeker.search.$collapseIcon.addClass('ui-icon-triangle-1-e');
				ctx.seeker.search.created = false;
				ctx.seeker.searchForm.hide();
				$navLayer.hide();
			}
		});

		// Evento de búsqueda asociado al botón
		$navSearchButton.on('click', function () {
			$('#' + ctx.sTableId).triggerHandler('tableSeekerBeforeSearch');
			ctx.seeker.ajaxOption.data = _getDatos(ctx);
			var ajaxOptions = $.extend(true, [], ctx.seeker.ajaxOption);
			//Se pasa sin el internalFeedback ya que no es necesario.
			if (ajaxOptions.data.multiselection !== undefined && ajaxOptions.data.multiselection.internalFeedback !== undefined) {
				ajaxOptions.data.multiselection.internalFeedback = [];
			}
			$('#' + ctx.sTableId).triggerHandler('tableSeekerBeforeSearch');
			$('#' + idTabla + '_search_searchForm').rup_form('ajaxSubmit', ajaxOptions);
			$('#' + ctx.sTableId).triggerHandler('tableSeekerAfterSearch');
		});

		// Evento asociado a limpiar el fomulario de búsqueda
		$navClearButton.on('click', function () {
			_limpiarSeeker(dt, ctx);
		});

		$navLayer.hide();

		function doSearchButtonNavigation($button, buttonId) {
			if (!$button.hasClass('ui-state-disabled')) {
				$self.rup_table('navigateToMatchedRow', buttonId);
			}
		}

		// Elemento primero
		$firstNavButton.on('click', function () {
			ctx.seeker.search.pos = 0;
			_processData(dt, ctx, ctx.seeker.search.funcionParams);
		});

		// Elemento anterior
		$backNavButton.on('click', function () {
			ctx.seeker.search.pos--;
			_processData(dt, ctx, ctx.seeker.search.funcionParams);
		});

		// Elemento siguiente
		$forwardNavButton.on('click', function () {
			ctx.seeker.search.accion = 'next';
			ctx.seeker.search.pos++;
			_processData(dt, ctx, ctx.seeker.search.funcionParams);
		});

		// Elemento ultimo
		$lastNavButton.on('click', function () {
			ctx.seeker.search.pos = ctx.seeker.search.funcionParams.length - 1;
			_processData(dt, ctx, ctx.seeker.search.funcionParams);
		});

		// Se recubre con un form
		var $searchForm = jQuery('<form>').attr('id', idTabla + '_search_searchForm');

		ctx.seeker.search.$searchForm = jQuery('#' + idTabla + '_search_searchForm');
		ctx.seeker.search.$searchRow.hide();
		$('#' + idTabla).wrapAll($searchForm);
		ctx.seeker.search.pos = 0;
		ctx.seeker.search.accion = '';
	}

	/**
 * Selecciona con la lupa los rows seleccionados. Una vez se han encontrado.
 *
 * @name selectSearch
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 * 
 * @param {object} dt - Es el objeto datatable.
 * @param {object} ctx - Es el contecto del datatable donde esta la configuración del mismo.
 * @param {object} rows - Filas del datatable de la página actual.
 *
 */
	function _selectSearch(dt, ctx, rows) {
		//Se limina el lapicero indicador.
		$('#' + ctx.sTableId + ' tbody tr td.select-checkbox span.ui-icon-search').remove();
		$('#' + ctx.sTableId + ' tbody tr td span.ui-icon-search').remove();

		//se añade el span con la lupa
		if (rows.length > 0 && ctx.fnRecordsTotal() > 0) {
			//Se selecciona el primero y se limpian los datos.
			var rowSelected = '';

			$.each(ctx.json.rows, function (idx, value) {
				if (rows[ctx.seeker.search.pos].pageLine - 1 === idx) {
					rowSelected = dt.rows().nodes()[idx];
				}
				var result = $.grep(rows, function (v) {
					return DataTable.Api().rupTable.getIdPk(v.pk) === DataTable.Api().rupTable.getIdPk(value);
				});
				if (result.length === 1) {
					var spanSearch = $("<span/>").addClass('ui-icon ui-icon-rupInfoCol ui-icon-search filtered-row');
					if (ctx.oInit.multiSelect !== undefined) {
						$($('#' + ctx.sTableId + ' tbody tr td.select-checkbox')[idx]).append(spanSearch);
					} else if (ctx.oInit.select !== undefined) {
						$($('#' + ctx.sTableId + ' tbody tr td:nth-child(1)')[idx]).append(spanSearch);
					}
				}
			});
			var rowUnique = rows[ctx.seeker.search.pos];
			var rowList = ctx.json.rows[rowUnique.pageLine - 1];
			if (rowSelected !== '' && rowSelected.className.indexOf('selected') < 0 && rowUnique.page === Number(ctx.json.page) && DataTable.Api().rupTable.getIdPk(rowUnique.pk) === DataTable.Api().rupTable.getIdPk(rowList) && (ctx.oInit.formEdit === undefined || ctx.oInit.formEdit.$navigationBar.funcionParams === undefined || ctx.oInit.formEdit.$navigationBar.funcionParams.length === undefined)) {
				//si no esta ya seleccionada.
				if (ctx.oInit.multiSelect !== undefined) {
					dt['row'](rowUnique.pageLine - 1).multiSelect();
				} else if (ctx.oInit.select !== undefined) {
					DataTable.Api().select.selectRowIndex(dt, rowUnique.pageLine);
				}
			}
			ctx.seeker.search.accion = '';
		}
	}

	/**
 * Metodo para saber si hay que paginar o no.
 *
 * @name paginar
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 * 
 * @param {object} ctx - Es el contexto del datatable donde esta la configuración del mismo.
 * @param {object} dato - Son los datos de las filas que viene del controller..
 *
 */
	function _paginar(ctx, dato) {
		var paginar = false;
		if (dato !== undefined && dato.page !== Number(ctx.json.page)) {
			paginar = true;
		}

		return paginar;
	}

	/**
 * Actualiza la navegación del seeker.
 *
 * @name updateDetailSeekPagination
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 * 
 * @param {integer} currentRowNum - Número de la posción actual del registro selecionado.
 * @param {integer} totalRowNum - Número total de registros seleccionados.
 *
 */
	function _updateDetailSeekPagination(currentRowNum, totalRowNum, ctx) {

		if (currentRowNum === 1) {
			ctx.seeker.search.$firstNavButton.addClass('ui-state-disabled');
			ctx.seeker.search.$backNavButton.addClass('ui-state-disabled');
		} else {
			ctx.seeker.search.$firstNavButton.removeClass('ui-state-disabled');
			ctx.seeker.search.$backNavButton.removeClass('ui-state-disabled');
		}
		if (currentRowNum === totalRowNum) {
			ctx.seeker.search.$forwardNavButton.addClass('ui-state-disabled');
			ctx.seeker.search.$lastNavButton.addClass('ui-state-disabled');
		} else {
			ctx.seeker.search.$forwardNavButton.removeClass('ui-state-disabled');
			ctx.seeker.search.$lastNavButton.removeClass('ui-state-disabled');
		}

		ctx.seeker.search.$matchedLabel.html(jQuery.jgrid.format(jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.plugins.search.matchedRecordsCount'), Number(currentRowNum), Number(totalRowNum)));
	}

	/**
 * Metodo para procesar los datos provinientes del controller.
 *
 * @name processData
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 * 
 * @param {object} dt - Es el objeto datatable.
 * @param {object} ctx - Es el contecto del datatable donde esta la configuración del mismo.
 * @param {object} dato - Son los datos de las filas que viene del controller.
 *
 */
	function _processData(dt, ctx, data) {
		if (ctx.oInit.multiSelect !== undefined) {
			DataTable.Api().multiSelect.deselectAll(dt);
		} else if (ctx.oInit.select !== undefined) {
			DataTable.Api().select.deselect(ctx);
		}
		if (!_paginar(ctx, data[ctx.seeker.search.pos])) {
			_selectSearch(dt, ctx, data);
		} else {
			var tabla = $('#' + ctx.sTableId);
			tabla.dataTable().fnPageChange(data[ctx.seeker.search.pos].page - 1);
		}

		if (data.length === 0) {
			ctx.seeker.search.$firstNavButton.add(ctx.seeker.search.$backNavButton).add(ctx.seeker.search.$forwardNavButton).add(ctx.seeker.search.$lastNavButton).addClass('ui-state-disabled');
			ctx.seeker.search.$matchedLabel.html(jQuery.jgrid.format(jQuery.rup.i18nParse(jQuery.rup.i18n.base, 'rup_datatable.plugins.search.matchedRecords'), '0'));
		} else {
			_updateDetailSeekPagination(ctx.seeker.search.pos + 1, data.length, ctx);
		}
	}

	/**
 * Se obtienen los datos del formulario del seeker.
 *
 * @name getDatos
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 * 
 * @param {object} ctx - Es el contecto del datatable donde esta la configuración del mismo.
 * 
 * @return {object} Devuelve el objeto mapeado de todos los campos.
 *
 */
	function _getDatos(ctx) {
		var datos = ctx.aBaseJson;
		if (datos !== undefined) {
			datos.search = form2object($(ctx.seeker.search.$searchForm.selector)[0]);
		}
		return datos;
	}

	/**
 * Partiendo de los inputs del seeker, se convierten en componentes rup dependiendo del tipo..
 *
 * @name createRupComponent
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 * 
 * @param {object} dt - Es el objeto datatable.
 * @param {object} ctx - Es el contecto del datatable donde esta la configuración del mismo.
 *
 */
	function _createRupComponent(dt, ctx) {
		var colModel = ctx.oInit.seeker.colModel,
		    searchEditOptions;
		if (colModel !== undefined) {
			$('#' + ctx.sTableId + ' tfoot tr:eq(1) th').each(function (i) {
				// El primer tr corresponde al desplegable de filtros
				if (i > 0) {
					//La primera columna no vale es la de los select
					var cellColModel = colModel[i - 1];
					var searchRupType = cellColModel.searchoptions !== undefined && cellColModel.searchoptions.rupType !== undefined ? cellColModel.searchoptions.rupType : cellColModel.rupType;

					var colModelName = cellColModel.name;
					var $elem = $('[name=\'' + colModelName + '\']', ctx.seeker.searchForm);
					// Se añade el title de los elementos de acuerdo al colname
					$elem.attr({
						'title': ctx.aoColumns[i - 1].sTitle,
						'class': 'editable customelement'
					}).removeAttr('readOnly');

					// En caso de tratarse de un componente rup, se inicializa de acuerdo a la configuracón especificada en el colModel
					if (searchRupType !== undefined) {
						searchEditOptions = cellColModel.searchoptions || cellColModel.editoptions;

						/*
       * PRE Configuración de los componentes RUP
       */
						if (searchRupType === 'combo') {
							searchEditOptions = $.extend({}, { menuWidth: $elem.width() }, searchEditOptions, { width: '97%' });
						} else if (searchRupType === 'date') {
							$elem.css('width', '86%');
							$elem.css('max-width', '80px');
							$elem.css('min-width', '75px');
						}

						// Invocación al componente RUP
						$elem['rup_' + searchRupType](searchEditOptions);
					}
				}
			});
		}
	}

	function _limpiarSeeker(dt, ctx) {
		$('#' + ctx.sTableId).triggerHandler('tableSeekerBeforeClear');
		jQuery('input,textarea', '#' + ctx.sTableId + ' tfoot').val('');
		jQuery('tfoot [ruptype=\'combo\']', 'table tfoot').rup_combo('clear');
		jQuery('.ui-selectmenu-status', 'table tfoot').text('--');
		ctx.seeker.search.funcionParams = {};
		ctx.seeker.search.pos = 0;
		_processData(dt, ctx, []);
		$('#' + ctx.sTableId).triggerHandler('tableSeekerAfterClear');
	}
	/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  * DataTables API
  *
  * For complete documentation, please refer to the docs/api directory or the
  * DataTables site
  */

	// Local variables to improve compression
	var apiRegister = DataTable.Api.register;

	apiRegister('seeker.eventTrigger()', function (api, type, args, any) {
		DataTable.seeker._eventTrigger(api, type, args, any);
	});

	apiRegister('seeker.selectSearch()', function (dt, ctx, rows) {
		_selectSearch(dt, ctx, rows);
	});

	apiRegister('seeker.limpiarSeeker()', function (dt, ctx) {
		_limpiarSeeker(dt, ctx);
	});

	apiRegister('seeker.updateDetailSeekPagination()', function (currentRowNum, totalRowNum, ctx) {
		_updateDetailSeekPagination(currentRowNum, totalRowNum, ctx);
	});

	/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  * Initialization
  */

	// DataTables creation - check if select has been defined in the options. Note
	// this required that the table be in the document! If it isn't then something
	// needs to trigger this method unfortunately. The next major release of
	// DataTables will rework the events and address this.
	$(document).on('plugin-init.dt', function (e, ctx) {
		if (e.namespace !== 'dt') {
			return;
		}
		if (ctx.oInit.seeker !== undefined) {
			DataTable.seeker.init(new DataTable.Api(ctx));
		} else {
			$('tfoot').hide();
		}
	});

	return DataTable.seeker;
});
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))

/***/ }),
/* 210 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;var _typeof = typeof Symbol === "function" && typeof Symbol.iterator === "symbol" ? function (obj) { return typeof obj; } : function (obj) { return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj; };

/**
  * Módulo que permite toda la seleción simple
  *
  * @summary 		Extensión del componente RUP Datatable
  * @module			"rup.table.select"
  * @version     1.0.0
  * @license
  * Licencia con arreglo a la EUPL, Versión 1.1 exclusivamente (la «Licencia»);
  * Solo podrá usarse esta obra si se respeta la Licencia.
  * Puede obtenerse una copia de la Licencia en
  *
  *      http://ec.europa.eu/idabc/eupl.html
  *
  * Salvo cuando lo exija la legislación aplicable o se acuerde por escrito,
  * el programa distribuido con arreglo a la Licencia se distribuye «TAL CUAL»,
  * SIN GARANTÍAS NI CONDICIONES DE NINGÚN TIPO, ni expresas ni implícitas.
  * Véase la Licencia en el idioma concreto que rige los permisos y limitaciones
  * que establece la Licencia.
  * @copyright   Copyright 2018 E.J.I.E., S.A.
  *
  */

(function (factory) {
	if (true) {
		// AMD
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(4), __webpack_require__(6), __webpack_require__(8)], __WEBPACK_AMD_DEFINE_RESULT__ = function ($) {
			return factory($, window, document);
		}.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else if ((typeof exports === 'undefined' ? 'undefined' : _typeof(exports)) === 'object') {
		// CommonJS
		module.exports = function (root, $) {
			if (!root) {
				root = window;
			}

			if (!$ || !$.fn.dataTable) {
				$ = require('datatables.net')(root, $).$;
			}

			return factory($, root, root.document);
		};
	} else {
		// Browser
		factory(jQuery, window, document);
	}
})(function ($, window, document, undefined) {
	'use strict';

	var DataTable = $.fn.dataTable;

	// Version information for debugger
	DataTable.select = {};

	DataTable.select.version = '1.2.4';

	/**
 * Se inicializa el componente select
 *
 * @name init
 * @function
 * @since UDA 3.4.0 // Datatable 1.0.0
 * 
 * @param {object} dt - Es el objeto datatable.
 *
 */
	DataTable.select.init = function (dt) {
		var ctx = dt.settings()[0];
		ctx.select = [];
		var rowsBody = $(ctx.nTBody);
		//Se edita el row/fila.
		rowsBody.on('click.DT', 'tr[role="row"]', function () {
			$(this).triggerHandler('tableSelectBeforeSelectRow');
			var idRow = this._DT_RowIndex;
			_selectRowIndex(dt, idRow, $(this));
			$(this).triggerHandler('tableSelectAfterSelectRow');
		});

		//Se genera el div para el feedback del datatable.
		var divFeedback = $('<div/>').attr('id', 'rup_feedback_' + ctx.sTableId).insertBefore('#' + ctx.sTableId).css('width', '100%');
		ctx.multiselection.internalFeedback = divFeedback;
	};

	/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  * Local functions
  */

	/**
  * Pinta los elementos selecionables, porque tiene los ids almacenados y mete la clase que se le indica.
  *
  *
  * This will occur _after_ the initial DataTables initialisation, although
  * before Ajax data is rendered
  *
  * @name drawSelectId
  * @function
  * @since UDA 3.4.0 // Datatable 1.0.0
  *
  * 
  */
	function _drawSelectId(ctx) {

		if (ctx.multiselection.selectedRowsPerPage.length === 1) {
			var row = ctx.multiselection.selectedRowsPerPage[0];
			var rowSelectAux = ctx.json.rows[row.line];

			if (rowSelectAux !== undefined && row.id === DataTable.Api().rupTable.getIdPk(rowSelectAux)) {
				var rowsBody = $(ctx.nTBody);
				var line = row.line + 1;
				$('tr:nth-child(' + line + ')', rowsBody).addClass('selected tr-highlight');
			}
		}
	}

	/**
  * Pinta los elementos selecionables, porque tiene los ids almacenados y mete la clase que se le indica.
  *
  *
  * This will occur _after_ the initial DataTables initialisation, although
  * before Ajax data is rendered
  *
  * @name drawSelectId
  * @function
  * @since UDA 3.4.0 // Datatable 1.0.0
  *
  * 
  */
	function _selectRowIndex(dt, index, tr) {
		var ctx = dt.settings()[0];
		ctx.multiselection.selectedRowsPerPage = [];
		ctx.oInit.select.funcionParams = '';
		var rowsBody = $(ctx.nTBody);
		if (tr.hasClass("tr-highlight")) {
			tr.removeClass('selected tr-highlight');
			ctx.multiselection.numSelected = 0;
			ctx.multiselection.selectedIds = [];
			ctx.multiselection.lastSelectedId = '';
		} else {
			$('tr', rowsBody).removeClass('selected tr-highlight');
			tr.addClass('selected tr-highlight');
			tr.triggerHandler('tableHighlightRowAsSelected');
			var row = ctx.json.rows[index];
			if (row !== undefined) {
				var arra = { id: DataTable.Api().rupTable.getIdPk(row), page: dt.page() + 1, line: index };
				ctx.multiselection.selectedRowsPerPage.splice(0, 0, arra);
				ctx.multiselection.numSelected = 1;
				ctx.multiselection.selectedIds = [DataTable.Api().rupTable.getIdPk(row)];
				ctx.multiselection.lastSelectedId = DataTable.Api().rupTable.getIdPk(row);
			}
		}
		if (ctx.oInit.buttons !== undefined) {
			DataTable.Api().buttons.displayRegex(ctx);
		}
	}

	/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  * DataTables selectors
  */

	/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  * DataTables API
  *
  * For complete documentation, please refer to the docs/api directory or the
  * DataTables site
  */

	// Local variables to improve compression
	var apiRegister = DataTable.Api.register;

	apiRegister('select()', function () {
		return this.iterator('table', function (ctx) {
			DataTable.select.init(new DataTable.Api(ctx));
		});
	});

	apiRegister('select.drawSelectId()', function (ctx) {
		_drawSelectId(ctx);
	});

	apiRegister('select.deselect()', function (ctx) {
		var rowsBody = $(ctx.nTBody);
		$('tr', rowsBody).removeClass('selected tr-highlight');
		ctx.multiselection.numSelected = 0;
		ctx.multiselection.selectedIds = [];
	});

	apiRegister('select.selectRowIndex()', function (dt, index, isDoubleClick) {
		var ctx = dt.settings()[0];
		var rowsBody = $(ctx.nTBody);
		var countTr = index;
		if (isDoubleClick !== undefined) {
			countTr = countTr + 1;
		}
		var tr = $('tr:nth-child(' + countTr + ')', rowsBody);
		_selectRowIndex(dt, index, tr);
	});

	// Common events with suitable namespaces
	function namespacedEvents(config) {
		var unique = config._eventNamespace;

		return 'draw.dt.DT' + unique + ' select.dt.DT' + unique + ' deselect.dt.DT' + unique;
	}

	/* * * ** * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
  * Initialisation
  */

	// DataTables creation - check if select has been defined in the options. Note
	// this required that the table be in the document! If it isn't then something
	// needs to trigger this method unfortunately. The next major release of
	// DataTables will rework the events and address this.
	$(document).on('preInit.dt.dtSelect', function (e, ctx) {
		if (e.namespace !== 'dt') {
			return;
		}
		if (ctx.oInit.select !== undefined) {
			DataTable.select.init(new DataTable.Api(ctx));
		}
	});

	return DataTable.select;
});

/***/ }),
/* 211 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function(jQuery) {Object.defineProperty(exports, "__esModule", {
  value: true
});

var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();

var _util = __webpack_require__(22);

var _util2 = _interopRequireDefault(_util);

function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }

function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }

/**
 * --------------------------------------------------------------------------
 * Bootstrap (v4.0.0-alpha.5): dropdown.js
 * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)
 * --------------------------------------------------------------------------
 */

var Dropdown = function ($) {

  /**
   * ------------------------------------------------------------------------
   * Constants
   * ------------------------------------------------------------------------
   */

  var NAME = 'dropdown';
  var VERSION = '4.0.0-alpha.5';
  var DATA_KEY = 'bs.dropdown';
  var EVENT_KEY = '.' + DATA_KEY;
  var DATA_API_KEY = '.data-api';
  var JQUERY_NO_CONFLICT = $.fn[NAME];
  var ESCAPE_KEYCODE = 27; // KeyboardEvent.which value for Escape (Esc) key
  var ARROW_UP_KEYCODE = 38; // KeyboardEvent.which value for up arrow key
  var ARROW_DOWN_KEYCODE = 40; // KeyboardEvent.which value for down arrow key
  var RIGHT_MOUSE_BUTTON_WHICH = 3; // MouseEvent.which value for the right button (assuming a right-handed mouse)

  var Event = {
    HIDE: 'hide' + EVENT_KEY,
    HIDDEN: 'hidden' + EVENT_KEY,
    SHOW: 'show' + EVENT_KEY,
    SHOWN: 'shown' + EVENT_KEY,
    CLICK: 'click' + EVENT_KEY,
    CLICK_DATA_API: 'click' + EVENT_KEY + DATA_API_KEY,
    KEYDOWN_DATA_API: 'keydown' + EVENT_KEY + DATA_API_KEY
  };

  var ClassName = {
    BACKDROP: 'dropdown-backdrop',
    DISABLED: 'disabled',
    OPEN: 'open'
  };

  var Selector = {
    BACKDROP: '.dropdown-backdrop',
    DATA_TOGGLE: '[data-toggle="dropdown"]',
    FORM_CHILD: '.dropdown form',
    ROLE_MENU: '[role="menu"]',
    ROLE_LISTBOX: '[role="listbox"]',
    NAVBAR_NAV: '.navbar-nav',
    VISIBLE_ITEMS: '[role="menu"] li:not(.disabled) a, ' + '[role="listbox"] li:not(.disabled) a'

    /**
     * ------------------------------------------------------------------------
     * Class Definition
     * ------------------------------------------------------------------------
     */

  };
  var Dropdown = function () {
    function Dropdown(element) {
      _classCallCheck(this, Dropdown);

      this._element = element;

      this._addEventListeners();
    }

    // getters

    _createClass(Dropdown, [{
      key: 'toggle',


      // public

      value: function toggle() {
        if (this.disabled || $(this).hasClass(ClassName.DISABLED)) {
          return false;
        }

        var parent = Dropdown._getParentFromElement(this);
        var isActive = $(parent).hasClass(ClassName.OPEN);

        Dropdown._clearMenus();

        if (isActive) {
          return false;
        }

        if ('ontouchstart' in document.documentElement && !$(parent).closest(Selector.NAVBAR_NAV).length) {

          // if mobile we use a backdrop because click events don't delegate
          var dropdown = document.createElement('div');
          dropdown.className = ClassName.BACKDROP;
          $(dropdown).insertBefore(this);
          $(dropdown).on('click', Dropdown._clearMenus);
        }

        var relatedTarget = { relatedTarget: this };
        var showEvent = $.Event(Event.SHOW, relatedTarget);

        $(parent).trigger(showEvent);

        if (showEvent.isDefaultPrevented()) {
          return false;
        }

        this.focus();
        this.setAttribute('aria-expanded', 'true');

        $(parent).toggleClass(ClassName.OPEN);
        $(parent).trigger($.Event(Event.SHOWN, relatedTarget));

        return false;
      }
    }, {
      key: 'dispose',
      value: function dispose() {
        $.removeData(this._element, DATA_KEY);
        $(this._element).off(EVENT_KEY);
        this._element = null;
      }

      // private

    }, {
      key: '_addEventListeners',
      value: function _addEventListeners() {
        $(this._element).on(Event.CLICK, this.toggle);
      }

      // static

    }], [{
      key: '_jQueryInterface',
      value: function _jQueryInterface(config) {
        return this.each(function () {
          var data = $(this).data(DATA_KEY);

          if (!data) {
            $(this).data(DATA_KEY, data = new Dropdown(this));
          }

          if (typeof config === 'string') {
            if (data[config] === undefined) {
              throw new Error('No method named "' + config + '"');
            }
            data[config].call(this);
          }
        });
      }
    }, {
      key: '_clearMenus',
      value: function _clearMenus(event) {
        if (event && event.which === RIGHT_MOUSE_BUTTON_WHICH) {
          return;
        }

        var backdrop = $(Selector.BACKDROP)[0];
        if (backdrop) {
          backdrop.parentNode.removeChild(backdrop);
        }

        var toggles = $.makeArray($(Selector.DATA_TOGGLE));

        for (var i = 0; i < toggles.length; i++) {
          var parent = Dropdown._getParentFromElement(toggles[i]);
          var relatedTarget = { relatedTarget: toggles[i] };

          if (!$(parent).hasClass(ClassName.OPEN)) {
            continue;
          }

          if (event && event.type === 'click' && /input|textarea/i.test(event.target.tagName) && $.contains(parent, event.target)) {
            continue;
          }

          var hideEvent = $.Event(Event.HIDE, relatedTarget);
          $(parent).trigger(hideEvent);
          if (hideEvent.isDefaultPrevented()) {
            continue;
          }

          toggles[i].setAttribute('aria-expanded', 'false');

          $(parent).removeClass(ClassName.OPEN).trigger($.Event(Event.HIDDEN, relatedTarget));
        }
      }
    }, {
      key: '_getParentFromElement',
      value: function _getParentFromElement(element) {
        var parent = void 0;
        var selector = _util2.default.getSelectorFromElement(element);

        if (selector) {
          parent = $(selector)[0];
        }

        return parent || element.parentNode;
      }
    }, {
      key: '_dataApiKeydownHandler',
      value: function _dataApiKeydownHandler(event) {
        if (!/(38|40|27|32)/.test(event.which) || /input|textarea/i.test(event.target.tagName)) {
          return;
        }

        event.preventDefault();
        event.stopPropagation();

        if (this.disabled || $(this).hasClass(ClassName.DISABLED)) {
          return;
        }

        var parent = Dropdown._getParentFromElement(this);
        var isActive = $(parent).hasClass(ClassName.OPEN);

        if (!isActive && event.which !== ESCAPE_KEYCODE || isActive && event.which === ESCAPE_KEYCODE) {

          if (event.which === ESCAPE_KEYCODE) {
            var toggle = $(parent).find(Selector.DATA_TOGGLE)[0];
            $(toggle).trigger('focus');
          }

          $(this).trigger('click');
          return;
        }

        var items = $.makeArray($(Selector.VISIBLE_ITEMS));

        items = items.filter(function (item) {
          return item.offsetWidth || item.offsetHeight;
        });

        if (!items.length) {
          return;
        }

        var index = items.indexOf(event.target);

        if (event.which === ARROW_UP_KEYCODE && index > 0) {
          // up
          index--;
        }

        if (event.which === ARROW_DOWN_KEYCODE && index < items.length - 1) {
          // down
          index++;
        }

        if (index < 0) {
          index = 0;
        }

        items[index].focus();
      }
    }, {
      key: 'VERSION',
      get: function get() {
        return VERSION;
      }
    }]);

    return Dropdown;
  }();

  /**
   * ------------------------------------------------------------------------
   * Data Api implementation
   * ------------------------------------------------------------------------
   */

  $(document).on(Event.KEYDOWN_DATA_API, Selector.DATA_TOGGLE, Dropdown._dataApiKeydownHandler).on(Event.KEYDOWN_DATA_API, Selector.ROLE_MENU, Dropdown._dataApiKeydownHandler).on(Event.KEYDOWN_DATA_API, Selector.ROLE_LISTBOX, Dropdown._dataApiKeydownHandler).on(Event.CLICK_DATA_API, Dropdown._clearMenus).on(Event.CLICK_DATA_API, Selector.DATA_TOGGLE, Dropdown.prototype.toggle).on(Event.CLICK_DATA_API, Selector.FORM_CHILD, function (e) {
    e.stopPropagation();
  });

  /**
   * ------------------------------------------------------------------------
   * jQuery
   * ------------------------------------------------------------------------
   */

  $.fn[NAME] = Dropdown._jQueryInterface;
  $.fn[NAME].Constructor = Dropdown;
  $.fn[NAME].noConflict = function () {
    $.fn[NAME] = JQUERY_NO_CONFLICT;
    return Dropdown._jQueryInterface;
  };

  return Dropdown;
}(jQuery);

exports.default = Dropdown;
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))

/***/ }),
/* 212 */
/***/ (function(module, exports, __webpack_require__) {

/* WEBPACK VAR INJECTION */(function($, global) {__webpack_require__(172);

__webpack_require__(171);

__webpack_require__(148);

__webpack_require__(173);

__webpack_require__(2);

__webpack_require__(17);

__webpack_require__(149);

__webpack_require__(150);

__webpack_require__(151);

__webpack_require__(152);

__webpack_require__(153);

__webpack_require__(154);

__webpack_require__(6);

__webpack_require__(147);

__webpack_require__(155);

__webpack_require__(156);

__webpack_require__(12);

__webpack_require__(8);

__webpack_require__(13);

__webpack_require__(157);

__webpack_require__(159);

__webpack_require__(160);

__webpack_require__(161);

__webpack_require__(162);

__webpack_require__(14);

__webpack_require__(163);

__webpack_require__(164);

__webpack_require__(15);

__webpack_require__(165);

__webpack_require__(166);

__webpack_require__(167);

__webpack_require__(16);

__webpack_require__(9);

__webpack_require__(168);

__webpack_require__(169);

__webpack_require__(18);

__webpack_require__(170);

__webpack_require__(158);

// import 'tether';
global.$ = global.jQuery = $;
/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0), __webpack_require__(10)))

/***/ }),
/* 213 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_RESULT__;/*
 * JavaScript Canvas to Blob
 * https://github.com/blueimp/JavaScript-Canvas-to-Blob
 *
 * Copyright 2012, Sebastian Tschan
 * https://blueimp.net
 *
 * Licensed under the MIT license:
 * http://www.opensource.org/licenses/MIT
 *
 * Based on stackoverflow user Stoive's code snippet:
 * http://stackoverflow.com/q/4998908
 */

/*global window, atob, Blob, ArrayBuffer, Uint8Array, define, module */

;(function (window) {
  'use strict'

  var CanvasPrototype = window.HTMLCanvasElement &&
                          window.HTMLCanvasElement.prototype
  var hasBlobConstructor = window.Blob && (function () {
    try {
      return Boolean(new Blob())
    } catch (e) {
      return false
    }
  }())
  var hasArrayBufferViewSupport = hasBlobConstructor && window.Uint8Array &&
    (function () {
      try {
        return new Blob([new Uint8Array(100)]).size === 100
      } catch (e) {
        return false
      }
    }())
  var BlobBuilder = window.BlobBuilder || window.WebKitBlobBuilder ||
                      window.MozBlobBuilder || window.MSBlobBuilder
  var dataURIPattern = /^data:((.*?)(;charset=.*?)?)(;base64)?,/
  var dataURLtoBlob = (hasBlobConstructor || BlobBuilder) && window.atob &&
    window.ArrayBuffer && window.Uint8Array &&
    function (dataURI) {
      var matches,
        mediaType,
        isBase64,
        dataString,
        byteString,
        arrayBuffer,
        intArray,
        i,
        bb
      // Parse the dataURI components as per RFC 2397
      matches = dataURI.match(dataURIPattern)
      if (!matches) {
        throw new Error('invalid data URI')
      }
      // Default to text/plain;charset=US-ASCII
      mediaType = matches[2]
        ? matches[1]
        : 'text/plain' + (matches[3] || ';charset=US-ASCII')
      isBase64 = !!matches[4]
      dataString = dataURI.slice(matches[0].length)
      if (isBase64) {
        // Convert base64 to raw binary data held in a string:
        byteString = atob(dataString)
      } else {
        // Convert base64/URLEncoded data component to raw binary:
        byteString = decodeURIComponent(dataString)
      }
      // Write the bytes of the string to an ArrayBuffer:
      arrayBuffer = new ArrayBuffer(byteString.length)
      intArray = new Uint8Array(arrayBuffer)
      for (i = 0; i < byteString.length; i += 1) {
        intArray[i] = byteString.charCodeAt(i)
      }
      // Write the ArrayBuffer (or ArrayBufferView) to a blob:
      if (hasBlobConstructor) {
        return new Blob(
          [hasArrayBufferViewSupport ? intArray : arrayBuffer],
          {type: mediaType}
        )
      }
      bb = new BlobBuilder()
      bb.append(arrayBuffer)
      return bb.getBlob(mediaType)
    }
  if (window.HTMLCanvasElement && !CanvasPrototype.toBlob) {
    if (CanvasPrototype.mozGetAsFile) {
      CanvasPrototype.toBlob = function (callback, type, quality) {
        if (quality && CanvasPrototype.toDataURL && dataURLtoBlob) {
          callback(dataURLtoBlob(this.toDataURL(type, quality)))
        } else {
          callback(this.mozGetAsFile('blob', type))
        }
      }
    } else if (CanvasPrototype.toDataURL && dataURLtoBlob) {
      CanvasPrototype.toBlob = function (callback, type, quality) {
        callback(dataURLtoBlob(this.toDataURL(type, quality)))
      }
    }
  }
  if (true) {
    !(__WEBPACK_AMD_DEFINE_RESULT__ = function () {
      return dataURLtoBlob
    }.call(exports, __webpack_require__, exports, module),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__))
  } else if (typeof module === 'object' && module.exports) {
    module.exports = dataURLtoBlob
  } else {
    window.dataURLtoBlob = dataURLtoBlob
  }
}(window))


/***/ }),
/* 214 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*
 * jQuery File Upload Audio Preview Plugin
 * https://github.com/blueimp/jQuery-File-Upload
 *
 * Copyright 2013, Sebastian Tschan
 * https://blueimp.net
 *
 * Licensed under the MIT license:
 * http://www.opensource.org/licenses/MIT
 */

/* jshint nomen:false */
/* global define, require, window, document */

;(function (factory) {
    'use strict';
    if (true) {
        // Register as an anonymous AMD module:
        !(__WEBPACK_AMD_DEFINE_ARRAY__ = [
            __webpack_require__(0),
            __webpack_require__(5),
            __webpack_require__(7)
        ], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
    } else if (typeof exports === 'object') {
        // Node/CommonJS:
        factory(
            require('jquery'),
            require('load-image')
        );
    } else {
        // Browser globals:
        factory(
            window.jQuery,
            window.loadImage
        );
    }
}(function ($, loadImage) {
    'use strict';

    // Prepend to the default processQueue:
    $.blueimp.fileupload.prototype.options.processQueue.unshift(
        {
            action: 'loadAudio',
            // Use the action as prefix for the "@" options:
            prefix: true,
            fileTypes: '@',
            maxFileSize: '@',
            disabled: '@disableAudioPreview'
        },
        {
            action: 'setAudio',
            name: '@audioPreviewName',
            disabled: '@disableAudioPreview'
        }
    );

    // The File Upload Audio Preview plugin extends the fileupload widget
    // with audio preview functionality:
    $.widget('blueimp.fileupload', $.blueimp.fileupload, {

        options: {
            // The regular expression for the types of audio files to load,
            // matched against the file type:
            loadAudioFileTypes: /^audio\/.*$/
        },

        _audioElement: document.createElement('audio'),

        processActions: {

            // Loads the audio file given via data.files and data.index
            // as audio element if the browser supports playing it.
            // Accepts the options fileTypes (regular expression)
            // and maxFileSize (integer) to limit the files to load:
            loadAudio: function (data, options) {
                if (options.disabled) {
                    return data;
                }
                var file = data.files[data.index],
                    url,
                    audio;
                if (this._audioElement.canPlayType &&
                        this._audioElement.canPlayType(file.type) &&
                        ($.type(options.maxFileSize) !== 'number' ||
                            file.size <= options.maxFileSize) &&
                        (!options.fileTypes ||
                            options.fileTypes.test(file.type))) {
                    url = loadImage.createObjectURL(file);
                    if (url) {
                        audio = this._audioElement.cloneNode(false);
                        audio.src = url;
                        audio.controls = true;
                        data.audio = audio;
                        return data;
                    }
                }
                return data;
            },

            // Sets the audio element as a property of the file object:
            setAudio: function (data, options) {
                if (data.audio && !options.disabled) {
                    data.files[data.index][options.name || 'preview'] = data.audio;
                }
                return data;
            }

        }

    });

}));


/***/ }),
/* 215 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*
 * jQuery File Upload Image Preview & Resize Plugin
 * https://github.com/blueimp/jQuery-File-Upload
 *
 * Copyright 2013, Sebastian Tschan
 * https://blueimp.net
 *
 * Licensed under the MIT license:
 * http://www.opensource.org/licenses/MIT
 */

/* jshint nomen:false */
/* global define, require, window, Blob */

;(function (factory) {
    'use strict';
    if (true) {
        // Register as an anonymous AMD module:
        !(__WEBPACK_AMD_DEFINE_ARRAY__ = [
            __webpack_require__(0),
            __webpack_require__(5),
            __webpack_require__(24),
            __webpack_require__(220),
            __webpack_require__(213),
            __webpack_require__(7)
        ], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
    } else if (typeof exports === 'object') {
        // Node/CommonJS:
        factory(
            require('jquery'),
            require('blueimp-load-image/js/load-image'),
            require('blueimp-load-image/js/load-image-meta'),
            require('blueimp-load-image/js/load-image-exif'),
            require('blueimp-canvas-to-blob'),
            require('./jquery.fileupload-process')
        );
    } else {
        // Browser globals:
        factory(
            window.jQuery,
            window.loadImage
        );
    }
}(function ($, loadImage) {
    'use strict';

    // Prepend to the default processQueue:
    $.blueimp.fileupload.prototype.options.processQueue.unshift(
        {
            action: 'loadImageMetaData',
            disableImageHead: '@',
            disableExif: '@',
            disableExifThumbnail: '@',
            disableExifSub: '@',
            disableExifGps: '@',
            disabled: '@disableImageMetaDataLoad'
        },
        {
            action: 'loadImage',
            // Use the action as prefix for the "@" options:
            prefix: true,
            fileTypes: '@',
            maxFileSize: '@',
            noRevoke: '@',
            disabled: '@disableImageLoad'
        },
        {
            action: 'resizeImage',
            // Use "image" as prefix for the "@" options:
            prefix: 'image',
            maxWidth: '@',
            maxHeight: '@',
            minWidth: '@',
            minHeight: '@',
            crop: '@',
            orientation: '@',
            forceResize: '@',
            disabled: '@disableImageResize'
        },
        {
            action: 'saveImage',
            quality: '@imageQuality',
            type: '@imageType',
            disabled: '@disableImageResize'
        },
        {
            action: 'saveImageMetaData',
            disabled: '@disableImageMetaDataSave'
        },
        {
            action: 'resizeImage',
            // Use "preview" as prefix for the "@" options:
            prefix: 'preview',
            maxWidth: '@',
            maxHeight: '@',
            minWidth: '@',
            minHeight: '@',
            crop: '@',
            orientation: '@',
            thumbnail: '@',
            canvas: '@',
            disabled: '@disableImagePreview'
        },
        {
            action: 'setImage',
            name: '@imagePreviewName',
            disabled: '@disableImagePreview'
        },
        {
            action: 'deleteImageReferences',
            disabled: '@disableImageReferencesDeletion'
        }
    );

    // The File Upload Resize plugin extends the fileupload widget
    // with image resize functionality:
    $.widget('blueimp.fileupload', $.blueimp.fileupload, {

        options: {
            // The regular expression for the types of images to load:
            // matched against the file type:
            loadImageFileTypes: /^image\/(gif|jpeg|png|svg\+xml)$/,
            // The maximum file size of images to load:
            loadImageMaxFileSize: 10000000, // 10MB
            // The maximum width of resized images:
            imageMaxWidth: 1920,
            // The maximum height of resized images:
            imageMaxHeight: 1080,
            // Defines the image orientation (1-8) or takes the orientation
            // value from Exif data if set to true:
            imageOrientation: false,
            // Define if resized images should be cropped or only scaled:
            imageCrop: false,
            // Disable the resize image functionality by default:
            disableImageResize: true,
            // The maximum width of the preview images:
            previewMaxWidth: 80,
            // The maximum height of the preview images:
            previewMaxHeight: 80,
            // Defines the preview orientation (1-8) or takes the orientation
            // value from Exif data if set to true:
            previewOrientation: true,
            // Create the preview using the Exif data thumbnail:
            previewThumbnail: true,
            // Define if preview images should be cropped or only scaled:
            previewCrop: false,
            // Define if preview images should be resized as canvas elements:
            previewCanvas: true
        },

        processActions: {

            // Loads the image given via data.files and data.index
            // as img element, if the browser supports the File API.
            // Accepts the options fileTypes (regular expression)
            // and maxFileSize (integer) to limit the files to load:
            loadImage: function (data, options) {
                if (options.disabled) {
                    return data;
                }
                var that = this,
                    file = data.files[data.index],
                    dfd = $.Deferred();
                if (($.type(options.maxFileSize) === 'number' &&
                            file.size > options.maxFileSize) ||
                        (options.fileTypes &&
                            !options.fileTypes.test(file.type)) ||
                        !loadImage(
                            file,
                            function (img) {
                                if (img.src) {
                                    data.img = img;
                                }
                                dfd.resolveWith(that, [data]);
                            },
                            options
                        )) {
                    return data;
                }
                return dfd.promise();
            },

            // Resizes the image given as data.canvas or data.img
            // and updates data.canvas or data.img with the resized image.
            // Also stores the resized image as preview property.
            // Accepts the options maxWidth, maxHeight, minWidth,
            // minHeight, canvas and crop:
            resizeImage: function (data, options) {
                if (options.disabled || !(data.canvas || data.img)) {
                    return data;
                }
                options = $.extend({canvas: true}, options);
                var that = this,
                    dfd = $.Deferred(),
                    img = (options.canvas && data.canvas) || data.img,
                    resolve = function (newImg) {
                        if (newImg && (newImg.width !== img.width ||
                                newImg.height !== img.height ||
                                options.forceResize)) {
                            data[newImg.getContext ? 'canvas' : 'img'] = newImg;
                        }
                        data.preview = newImg;
                        dfd.resolveWith(that, [data]);
                    },
                    thumbnail;
                if (data.exif) {
                    if (options.orientation === true) {
                        options.orientation = data.exif.get('Orientation');
                    }
                    if (options.thumbnail) {
                        thumbnail = data.exif.get('Thumbnail');
                        if (thumbnail) {
                            loadImage(thumbnail, resolve, options);
                            return dfd.promise();
                        }
                    }
                    // Prevent orienting the same image twice:
                    if (data.orientation) {
                        delete options.orientation;
                    } else {
                        data.orientation = options.orientation;
                    }
                }
                if (img) {
                    resolve(loadImage.scale(img, options));
                    return dfd.promise();
                }
                return data;
            },

            // Saves the processed image given as data.canvas
            // inplace at data.index of data.files:
            saveImage: function (data, options) {
                if (!data.canvas || options.disabled) {
                    return data;
                }
                var that = this,
                    file = data.files[data.index],
                    dfd = $.Deferred();
                if (data.canvas.toBlob) {
                    data.canvas.toBlob(
                        function (blob) {
                            if (!blob.name) {
                                if (file.type === blob.type) {
                                    blob.name = file.name;
                                } else if (file.name) {
                                    blob.name = file.name.replace(
                                        /\.\w+$/,
                                        '.' + blob.type.substr(6)
                                    );
                                }
                            }
                            // Don't restore invalid meta data:
                            if (file.type !== blob.type) {
                                delete data.imageHead;
                            }
                            // Store the created blob at the position
                            // of the original file in the files list:
                            data.files[data.index] = blob;
                            dfd.resolveWith(that, [data]);
                        },
                        options.type || file.type,
                        options.quality
                    );
                } else {
                    return data;
                }
                return dfd.promise();
            },

            loadImageMetaData: function (data, options) {
                if (options.disabled) {
                    return data;
                }
                var that = this,
                    dfd = $.Deferred();
                loadImage.parseMetaData(data.files[data.index], function (result) {
                    $.extend(data, result);
                    dfd.resolveWith(that, [data]);
                }, options);
                return dfd.promise();
            },

            saveImageMetaData: function (data, options) {
                if (!(data.imageHead && data.canvas &&
                        data.canvas.toBlob && !options.disabled)) {
                    return data;
                }
                var file = data.files[data.index],
                    blob = new Blob([
                        data.imageHead,
                        // Resized images always have a head size of 20 bytes,
                        // including the JPEG marker and a minimal JFIF header:
                        this._blobSlice.call(file, 20)
                    ], {type: file.type});
                blob.name = file.name;
                data.files[data.index] = blob;
                return data;
            },

            // Sets the resized version of the image as a property of the
            // file object, must be called after "saveImage":
            setImage: function (data, options) {
                if (data.preview && !options.disabled) {
                    data.files[data.index][options.name || 'preview'] = data.preview;
                }
                return data;
            },

            deleteImageReferences: function (data, options) {
                if (!options.disabled) {
                    delete data.img;
                    delete data.canvas;
                    delete data.preview;
                    delete data.imageHead;
                }
                return data;
            }

        }

    });

}));


/***/ }),
/* 216 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*
 * jQuery File Upload User Interface Plugin
 * https://github.com/blueimp/jQuery-File-Upload
 *
 * Copyright 2010, Sebastian Tschan
 * https://blueimp.net
 *
 * Licensed under the MIT license:
 * http://www.opensource.org/licenses/MIT
 */

/* jshint nomen:false */
/* global define, require, window */

;(function (factory) {
    'use strict';
    if (true) {
        // Register as an anonymous AMD module:
        !(__WEBPACK_AMD_DEFINE_ARRAY__ = [
            __webpack_require__(0),
            __webpack_require__(221),
            __webpack_require__(215),
            __webpack_require__(214),
            __webpack_require__(218),
            __webpack_require__(217)
        ], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
    } else if (typeof exports === 'object') {
        // Node/CommonJS:
        factory(
            require('jquery'),
            require('tmpl')
        );
    } else {
        // Browser globals:
        factory(
            window.jQuery,
            window.tmpl
        );
    }
}(function ($, tmpl) {
    'use strict';

    $.blueimp.fileupload.prototype._specialOptions.push(
        'filesContainer',
        'uploadTemplateId',
        'downloadTemplateId'
    );

    // The UI version extends the file upload widget
    // and adds complete user interface interaction:
    $.widget('blueimp.fileupload', $.blueimp.fileupload, {

        options: {
            // By default, files added to the widget are uploaded as soon
            // as the user clicks on the start buttons. To enable automatic
            // uploads, set the following option to true:
            autoUpload: false,
            // The ID of the upload template:
            uploadTemplateId: 'template-upload',
            // The ID of the download template:
            downloadTemplateId: 'template-download',
            // The container for the list of files. If undefined, it is set to
            // an element with class "files" inside of the widget element:
            filesContainer: undefined,
            // By default, files are appended to the files container.
            // Set the following option to true, to prepend files instead:
            prependFiles: false,
            // The expected data type of the upload response, sets the dataType
            // option of the $.ajax upload requests:
            dataType: 'json',

            // Error and info messages:
            messages: {
                unknownError: 'Unknown error'
            },

            // Function returning the current number of files,
            // used by the maxNumberOfFiles validation:
            getNumberOfFiles: function () {
                return this.filesContainer.children()
                    .not('.processing').length;
            },

            // Callback to retrieve the list of files from the server response:
            getFilesFromResponse: function (data) {
                if (data.result && $.isArray(data.result.files)) {
                    return data.result.files;
                }
                return [];
            },

            // The add callback is invoked as soon as files are added to the fileupload
            // widget (via file input selection, drag & drop or add API call).
            // See the basic file upload widget for more information:
            add: function (e, data) {
                if (e.isDefaultPrevented()) {
                    return false;
                }
                var $this = $(this),
                    that = $this.data('blueimp-fileupload') ||
                        $this.data('fileupload'),
                    options = that.options;
                data.context = that._renderUpload(data.files)
                    .data('data', data)
                    .addClass('processing');
                options.filesContainer[
                    options.prependFiles ? 'prepend' : 'append'
                ](data.context);
                that._forceReflow(data.context);
                that._transition(data.context);
                data.process(function () {
                    return $this.fileupload('process', data);
                }).always(function () {
                    data.context.each(function (index) {
                        $(this).find('.size').text(
                            that._formatFileSize(data.files[index].size)
                        );
                    }).removeClass('processing');
                    that._renderPreviews(data);
                }).done(function () {
                    data.context.find('.start').prop('disabled', false);
                    if ((that._trigger('added', e, data) !== false) &&
                            (options.autoUpload || data.autoUpload) &&
                            data.autoUpload !== false) {
                        data.submit();
                    }
                }).fail(function () {
                    if (data.files.error) {
                        data.context.each(function (index) {
                            var error = data.files[index].error;
                            if (error) {
                                $(this).find('.error').text(error);
                            }
                        });
                    }
                });
            },
            // Callback for the start of each file upload request:
            send: function (e, data) {
                if (e.isDefaultPrevented()) {
                    return false;
                }
                var that = $(this).data('blueimp-fileupload') ||
                        $(this).data('fileupload');
                if (data.context && data.dataType &&
                        data.dataType.substr(0, 6) === 'iframe') {
                    // Iframe Transport does not support progress events.
                    // In lack of an indeterminate progress bar, we set
                    // the progress to 100%, showing the full animated bar:
                    data.context
                        .find('.progress').addClass(
                            !$.support.transition && 'progress-animated'
                        )
                        .attr('aria-valuenow', 100)
                        .children().first().css(
                            'width',
                            '100%'
                        );
                }
                return that._trigger('sent', e, data);
            },
            // Callback for successful uploads:
            done: function (e, data) {
                if (e.isDefaultPrevented()) {
                    return false;
                }
                var that = $(this).data('blueimp-fileupload') ||
                        $(this).data('fileupload'),
                    getFilesFromResponse = data.getFilesFromResponse ||
                        that.options.getFilesFromResponse,
                    files = getFilesFromResponse(data),
                    template,
                    deferred;
                if (data.context) {
                    data.context.each(function (index) {
                        var file = files[index] ||
                                {error: 'Empty file upload result'};
                        deferred = that._addFinishedDeferreds();
                        that._transition($(this)).done(
                            function () {
                                var node = $(this);
                                template = that._renderDownload([file])
                                    .replaceAll(node);
                                that._forceReflow(template);
                                that._transition(template).done(
                                    function () {
                                        data.context = $(this);
                                        that._trigger('completed', e, data);
                                        that._trigger('finished', e, data);
                                        deferred.resolve();
                                    }
                                );
                            }
                        );
                    });
                } else {
                    template = that._renderDownload(files)[
                        that.options.prependFiles ? 'prependTo' : 'appendTo'
                    ](that.options.filesContainer);
                    that._forceReflow(template);
                    deferred = that._addFinishedDeferreds();
                    that._transition(template).done(
                        function () {
                            data.context = $(this);
                            that._trigger('completed', e, data);
                            that._trigger('finished', e, data);
                            deferred.resolve();
                        }
                    );
                }
            },
            // Callback for failed (abort or error) uploads:
            fail: function (e, data) {
                if (e.isDefaultPrevented()) {
                    return false;
                }
                var that = $(this).data('blueimp-fileupload') ||
                        $(this).data('fileupload'),
                    template,
                    deferred;
                if (data.context) {
                    data.context.each(function (index) {
                        if (data.errorThrown !== 'abort') {
                            var file = data.files[index];
                            file.error = file.error || data.errorThrown ||
                                data.i18n('unknownError');
                            deferred = that._addFinishedDeferreds();
                            that._transition($(this)).done(
                                function () {
                                    var node = $(this);
                                    template = that._renderDownload([file])
                                        .replaceAll(node);
                                    that._forceReflow(template);
                                    that._transition(template).done(
                                        function () {
                                            data.context = $(this);
                                            that._trigger('failed', e, data);
                                            that._trigger('finished', e, data);
                                            deferred.resolve();
                                        }
                                    );
                                }
                            );
                        } else {
                            deferred = that._addFinishedDeferreds();
                            that._transition($(this)).done(
                                function () {
                                    $(this).remove();
                                    that._trigger('failed', e, data);
                                    that._trigger('finished', e, data);
                                    deferred.resolve();
                                }
                            );
                        }
                    });
                } else if (data.errorThrown !== 'abort') {
                    data.context = that._renderUpload(data.files)[
                        that.options.prependFiles ? 'prependTo' : 'appendTo'
                    ](that.options.filesContainer)
                        .data('data', data);
                    that._forceReflow(data.context);
                    deferred = that._addFinishedDeferreds();
                    that._transition(data.context).done(
                        function () {
                            data.context = $(this);
                            that._trigger('failed', e, data);
                            that._trigger('finished', e, data);
                            deferred.resolve();
                        }
                    );
                } else {
                    that._trigger('failed', e, data);
                    that._trigger('finished', e, data);
                    that._addFinishedDeferreds().resolve();
                }
            },
            // Callback for upload progress events:
            progress: function (e, data) {
                if (e.isDefaultPrevented()) {
                    return false;
                }
                var progress = Math.floor(data.loaded / data.total * 100);
                if (data.context) {
                    data.context.each(function () {
                        $(this).find('.progress')
                            .attr('aria-valuenow', progress)
                            .children().first().css(
                                'width',
                                progress + '%'
                            );
                    });
                }
            },
            // Callback for global upload progress events:
            progressall: function (e, data) {
                if (e.isDefaultPrevented()) {
                    return false;
                }
                var $this = $(this),
                    progress = Math.floor(data.loaded / data.total * 100),
                    globalProgressNode = $this.find('.fileupload-progress'),
                    extendedProgressNode = globalProgressNode
                        .find('.progress-extended');
                if (extendedProgressNode.length) {
                    extendedProgressNode.html(
                        ($this.data('blueimp-fileupload') || $this.data('fileupload'))
                            ._renderExtendedProgress(data)
                    );
                }
                globalProgressNode
                    .find('.progress')
                    .attr('aria-valuenow', progress)
                    .children().first().css(
                        'width',
                        progress + '%'
                    );
            },
            // Callback for uploads start, equivalent to the global ajaxStart event:
            start: function (e) {
                if (e.isDefaultPrevented()) {
                    return false;
                }
                var that = $(this).data('blueimp-fileupload') ||
                        $(this).data('fileupload');
                that._resetFinishedDeferreds();
                that._transition($(this).find('.fileupload-progress')).done(
                    function () {
                        that._trigger('started', e);
                    }
                );
            },
            // Callback for uploads stop, equivalent to the global ajaxStop event:
            stop: function (e) {
                if (e.isDefaultPrevented()) {
                    return false;
                }
                var that = $(this).data('blueimp-fileupload') ||
                        $(this).data('fileupload'),
                    deferred = that._addFinishedDeferreds();
                $.when.apply($, that._getFinishedDeferreds())
                    .done(function () {
                        that._trigger('stopped', e);
                    });
                that._transition($(this).find('.fileupload-progress')).done(
                    function () {
                        $(this).find('.progress')
                            .attr('aria-valuenow', '0')
                            .children().first().css('width', '0%');
                        $(this).find('.progress-extended').html('&nbsp;');
                        deferred.resolve();
                    }
                );
            },
            processstart: function (e) {
                if (e.isDefaultPrevented()) {
                    return false;
                }
                $(this).addClass('fileupload-processing');
            },
            processstop: function (e) {
                if (e.isDefaultPrevented()) {
                    return false;
                }
                $(this).removeClass('fileupload-processing');
            },
            // Callback for file deletion:
            destroy: function (e, data) {
                if (e.isDefaultPrevented()) {
                    return false;
                }
                var that = $(this).data('blueimp-fileupload') ||
                        $(this).data('fileupload'),
                    removeNode = function () {
                        that._transition(data.context).done(
                            function () {
                                $(this).remove();
                                that._trigger('destroyed', e, data);
                            }
                        );
                    };
                if (data.url) {
                    data.dataType = data.dataType || that.options.dataType;
                    $.ajax(data).done(removeNode).fail(function () {
                        that._trigger('destroyfailed', e, data);
                    });
                } else {
                    removeNode();
                }
            }
        },

        _resetFinishedDeferreds: function () {
            this._finishedUploads = [];
        },

        _addFinishedDeferreds: function (deferred) {
            if (!deferred) {
                deferred = $.Deferred();
            }
            this._finishedUploads.push(deferred);
            return deferred;
        },

        _getFinishedDeferreds: function () {
            return this._finishedUploads;
        },

        // Link handler, that allows to download files
        // by drag & drop of the links to the desktop:
        _enableDragToDesktop: function () {
            var link = $(this),
                url = link.prop('href'),
                name = link.prop('download'),
                type = 'application/octet-stream';
            link.bind('dragstart', function (e) {
                try {
                    e.originalEvent.dataTransfer.setData(
                        'DownloadURL',
                        [type, name, url].join(':')
                    );
                } catch (ignore) {}
            });
        },

        _formatFileSize: function (bytes) {
            if (typeof bytes !== 'number') {
                return '';
            }
            if (bytes >= 1000000000) {
                return (bytes / 1000000000).toFixed(2) + ' GB';
            }
            if (bytes >= 1000000) {
                return (bytes / 1000000).toFixed(2) + ' MB';
            }
            return (bytes / 1000).toFixed(2) + ' KB';
        },

        _formatBitrate: function (bits) {
            if (typeof bits !== 'number') {
                return '';
            }
            if (bits >= 1000000000) {
                return (bits / 1000000000).toFixed(2) + ' Gbit/s';
            }
            if (bits >= 1000000) {
                return (bits / 1000000).toFixed(2) + ' Mbit/s';
            }
            if (bits >= 1000) {
                return (bits / 1000).toFixed(2) + ' kbit/s';
            }
            return bits.toFixed(2) + ' bit/s';
        },

        _formatTime: function (seconds) {
            var date = new Date(seconds * 1000),
                days = Math.floor(seconds / 86400);
            days = days ? days + 'd ' : '';
            return days +
                ('0' + date.getUTCHours()).slice(-2) + ':' +
                ('0' + date.getUTCMinutes()).slice(-2) + ':' +
                ('0' + date.getUTCSeconds()).slice(-2);
        },

        _formatPercentage: function (floatValue) {
            return (floatValue * 100).toFixed(2) + ' %';
        },

        _renderExtendedProgress: function (data) {
            return this._formatBitrate(data.bitrate) + ' | ' +
                this._formatTime(
                    (data.total - data.loaded) * 8 / data.bitrate
                ) + ' | ' +
                this._formatPercentage(
                    data.loaded / data.total
                ) + ' | ' +
                this._formatFileSize(data.loaded) + ' / ' +
                this._formatFileSize(data.total);
        },

        _renderTemplate: function (func, files) {
            if (!func) {
                return $();
            }
            var result = func({
                files: files,
                formatFileSize: this._formatFileSize,
                options: this.options
            });
            if (result instanceof $) {
                return result;
            }
            return $(this.options.templatesContainer).html(result).children();
        },

        _renderPreviews: function (data) {
            data.context.find('.preview').each(function (index, elm) {
                $(elm).append(data.files[index].preview);
            });
        },

        _renderUpload: function (files) {
            return this._renderTemplate(
                this.options.uploadTemplate,
                files
            );
        },

        _renderDownload: function (files) {
            return this._renderTemplate(
                this.options.downloadTemplate,
                files
            ).find('a[download]').each(this._enableDragToDesktop).end();
        },

        _startHandler: function (e) {
            e.preventDefault();
            var button = $(e.currentTarget),
                template = button.closest('.template-upload'),
                data = template.data('data');
            button.prop('disabled', true);
            if (data && data.submit) {
                data.submit();
            }
        },

        _cancelHandler: function (e) {
            e.preventDefault();
            var template = $(e.currentTarget)
                    .closest('.template-upload,.template-download'),
                data = template.data('data') || {};
            data.context = data.context || template;
            if (data.abort) {
                data.abort();
            } else {
                data.errorThrown = 'abort';
                this._trigger('fail', e, data);
            }
        },

        _deleteHandler: function (e) {
            e.preventDefault();
            var button = $(e.currentTarget);
            this._trigger('destroy', e, $.extend({
                context: button.closest('.template-download'),
                type: 'DELETE'
            }, button.data()));
        },

        _forceReflow: function (node) {
            return $.support.transition && node.length &&
                node[0].offsetWidth;
        },

        _transition: function (node) {
            var dfd = $.Deferred();
            if ($.support.transition && node.hasClass('fade') && node.is(':visible')) {
                node.bind(
                    $.support.transition.end,
                    function (e) {
                        // Make sure we don't respond to other transitions events
                        // in the container element, e.g. from button elements:
                        if (e.target === node[0]) {
                            node.unbind($.support.transition.end);
                            dfd.resolveWith(node);
                        }
                    }
                ).toggleClass('in');
            } else {
                node.toggleClass('in');
                dfd.resolveWith(node);
            }
            return dfd;
        },

        _initButtonBarEventHandlers: function () {
            var fileUploadButtonBar = this.element.find('.fileupload-buttonbar'),
                filesList = this.options.filesContainer;
            this._on(fileUploadButtonBar.find('.start'), {
                click: function (e) {
                    e.preventDefault();
                    filesList.find('.start').click();
                }
            });
            this._on(fileUploadButtonBar.find('.cancel'), {
                click: function (e) {
                    e.preventDefault();
                    filesList.find('.cancel').click();
                }
            });
            this._on(fileUploadButtonBar.find('.delete'), {
                click: function (e) {
                    e.preventDefault();
                    filesList.find('.toggle:checked')
                        .closest('.template-download')
                        .find('.delete').click();
                    fileUploadButtonBar.find('.toggle')
                        .prop('checked', false);
                }
            });
            this._on(fileUploadButtonBar.find('.toggle'), {
                change: function (e) {
                    filesList.find('.toggle').prop(
                        'checked',
                        $(e.currentTarget).is(':checked')
                    );
                }
            });
        },

        _destroyButtonBarEventHandlers: function () {
            this._off(
                this.element.find('.fileupload-buttonbar')
                    .find('.start, .cancel, .delete'),
                'click'
            );
            this._off(
                this.element.find('.fileupload-buttonbar .toggle'),
                'change.'
            );
        },

        _initEventHandlers: function () {
            this._super();
            this._on(this.options.filesContainer, {
                'click .start': this._startHandler,
                'click .cancel': this._cancelHandler,
                'click .delete': this._deleteHandler
            });
            this._initButtonBarEventHandlers();
        },

        _destroyEventHandlers: function () {
            this._destroyButtonBarEventHandlers();
            this._off(this.options.filesContainer, 'click');
            this._super();
        },

        _enableFileInputButton: function () {
            this.element.find('.fileinput-button input')
                .prop('disabled', false)
                .parent().removeClass('disabled');
        },

        _disableFileInputButton: function () {
            this.element.find('.fileinput-button input')
                .prop('disabled', true)
                .parent().addClass('disabled');
        },

        _initTemplates: function () {
            var options = this.options;
            options.templatesContainer = this.document[0].createElement(
                options.filesContainer.prop('nodeName')
            );
            if (tmpl) {
                if (options.uploadTemplateId) {
                    options.uploadTemplate = tmpl(options.uploadTemplateId);
                }
                if (options.downloadTemplateId) {
                    options.downloadTemplate = tmpl(options.downloadTemplateId);
                }
            }
        },

        _initFilesContainer: function () {
            var options = this.options;
            if (options.filesContainer === undefined) {
                options.filesContainer = this.element.find('.files');
            } else if (!(options.filesContainer instanceof $)) {
                options.filesContainer = $(options.filesContainer);
            }
        },

        _initSpecialOptions: function () {
            this._super();
            this._initFilesContainer();
            this._initTemplates();
        },

        _create: function () {
            this._super();
            this._resetFinishedDeferreds();
            if (!$.support.fileInput) {
                this._disableFileInputButton();
            }
        },

        enable: function () {
            var wasDisabled = false;
            if (this.options.disabled) {
                wasDisabled = true;
            }
            this._super();
            if (wasDisabled) {
                this.element.find('input, button').prop('disabled', false);
                this._enableFileInputButton();
            }
        },

        disable: function () {
            if (!this.options.disabled) {
                this.element.find('input, button').prop('disabled', true);
                this._disableFileInputButton();
            }
            this._super();
        }

    });

}));


/***/ }),
/* 217 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*
 * jQuery File Upload Validation Plugin
 * https://github.com/blueimp/jQuery-File-Upload
 *
 * Copyright 2013, Sebastian Tschan
 * https://blueimp.net
 *
 * Licensed under the MIT license:
 * http://www.opensource.org/licenses/MIT
 */

/* global define, require, window */

;(function (factory) {
    'use strict';
    if (true) {
        // Register as an anonymous AMD module:
        !(__WEBPACK_AMD_DEFINE_ARRAY__ = [
            __webpack_require__(0),
            __webpack_require__(7)
        ], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
    } else if (typeof exports === 'object') {
        // Node/CommonJS:
        factory(require('jquery'));
    } else {
        // Browser globals:
        factory(
            window.jQuery
        );
    }
}(function ($) {
    'use strict';

    // Append to the default processQueue:
    $.blueimp.fileupload.prototype.options.processQueue.push(
        {
            action: 'validate',
            // Always trigger this action,
            // even if the previous action was rejected:
            always: true,
            // Options taken from the global options map:
            acceptFileTypes: '@',
            maxFileSize: '@',
            minFileSize: '@',
            maxNumberOfFiles: '@',
            disabled: '@disableValidation'
        }
    );

    // The File Upload Validation plugin extends the fileupload widget
    // with file validation functionality:
    $.widget('blueimp.fileupload', $.blueimp.fileupload, {

        options: {
            /*
            // The regular expression for allowed file types, matches
            // against either file type or file name:
            acceptFileTypes: /(\.|\/)(gif|jpe?g|png)$/i,
            // The maximum allowed file size in bytes:
            maxFileSize: 10000000, // 10 MB
            // The minimum allowed file size in bytes:
            minFileSize: undefined, // No minimal file size
            // The limit of files to be uploaded:
            maxNumberOfFiles: 10,
            */

            // Function returning the current number of files,
            // has to be overriden for maxNumberOfFiles validation:
            getNumberOfFiles: $.noop,

            // Error and info messages:
            messages: {
                maxNumberOfFiles: 'Maximum number of files exceeded',
                acceptFileTypes: 'File type not allowed',
                maxFileSize: 'File is too large',
                minFileSize: 'File is too small'
            }
        },

        processActions: {

            validate: function (data, options) {
                if (options.disabled) {
                    return data;
                }
                var dfd = $.Deferred(),
                    settings = this.options,
                    file = data.files[data.index],
                    fileSize;
                if (options.minFileSize || options.maxFileSize) {
                    fileSize = file.size;
                }
                if ($.type(options.maxNumberOfFiles) === 'number' &&
                        (settings.getNumberOfFiles() || 0) + data.files.length >
                            options.maxNumberOfFiles) {
                    file.error = settings.i18n('maxNumberOfFiles');
                } else if (options.acceptFileTypes &&
                        !(options.acceptFileTypes.test(file.type) ||
                        options.acceptFileTypes.test(file.name))) {
                    file.error = settings.i18n('acceptFileTypes');
                } else if (fileSize > options.maxFileSize) {
                    file.error = settings.i18n('maxFileSize');
                } else if ($.type(fileSize) === 'number' &&
                        fileSize < options.minFileSize) {
                    file.error = settings.i18n('minFileSize');
                } else {
                    delete file.error;
                }
                if (file.error || data.files.error) {
                    data.files.error = true;
                    dfd.rejectWith(this, [data]);
                } else {
                    dfd.resolveWith(this, [data]);
                }
                return dfd.promise();
            }

        }

    });

}));


/***/ }),
/* 218 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*
 * jQuery File Upload Video Preview Plugin
 * https://github.com/blueimp/jQuery-File-Upload
 *
 * Copyright 2013, Sebastian Tschan
 * https://blueimp.net
 *
 * Licensed under the MIT license:
 * http://www.opensource.org/licenses/MIT
 */

/* jshint nomen:false */
/* global define, require, window, document */

;(function (factory) {
    'use strict';
    if (true) {
        // Register as an anonymous AMD module:
        !(__WEBPACK_AMD_DEFINE_ARRAY__ = [
            __webpack_require__(0),
            __webpack_require__(5),
            __webpack_require__(7)
        ], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
    } else if (typeof exports === 'object') {
        // Node/CommonJS:
        factory(
            require('jquery'),
            require('load-image')
        );
    } else {
        // Browser globals:
        factory(
            window.jQuery,
            window.loadImage
        );
    }
}(function ($, loadImage) {
    'use strict';

    // Prepend to the default processQueue:
    $.blueimp.fileupload.prototype.options.processQueue.unshift(
        {
            action: 'loadVideo',
            // Use the action as prefix for the "@" options:
            prefix: true,
            fileTypes: '@',
            maxFileSize: '@',
            disabled: '@disableVideoPreview'
        },
        {
            action: 'setVideo',
            name: '@videoPreviewName',
            disabled: '@disableVideoPreview'
        }
    );

    // The File Upload Video Preview plugin extends the fileupload widget
    // with video preview functionality:
    $.widget('blueimp.fileupload', $.blueimp.fileupload, {

        options: {
            // The regular expression for the types of video files to load,
            // matched against the file type:
            loadVideoFileTypes: /^video\/.*$/
        },

        _videoElement: document.createElement('video'),

        processActions: {

            // Loads the video file given via data.files and data.index
            // as video element if the browser supports playing it.
            // Accepts the options fileTypes (regular expression)
            // and maxFileSize (integer) to limit the files to load:
            loadVideo: function (data, options) {
                if (options.disabled) {
                    return data;
                }
                var file = data.files[data.index],
                    url,
                    video;
                if (this._videoElement.canPlayType &&
                        this._videoElement.canPlayType(file.type) &&
                        ($.type(options.maxFileSize) !== 'number' ||
                            file.size <= options.maxFileSize) &&
                        (!options.fileTypes ||
                            options.fileTypes.test(file.type))) {
                    url = loadImage.createObjectURL(file);
                    if (url) {
                        video = this._videoElement.cloneNode(false);
                        video.src = url;
                        video.controls = true;
                        data.video = video;
                        return data;
                    }
                }
                return data;
            },

            // Sets the video element as a property of the file object:
            setVideo: function (data, options) {
                if (data.video && !options.disabled) {
                    data.files[data.index][options.name || 'preview'] = data.video;
                }
                return data;
            }

        }

    });

}));


/***/ }),
/* 219 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*
 * jQuery File Upload Plugin
 * https://github.com/blueimp/jQuery-File-Upload
 *
 * Copyright 2010, Sebastian Tschan
 * https://blueimp.net
 *
 * Licensed under the MIT license:
 * http://www.opensource.org/licenses/MIT
 */

/* jshint nomen:false */
/* global define, require, window, document, location, Blob, FormData */

;(function (factory) {
    'use strict';
    if (true) {
        // Register as an anonymous AMD module:
        !(__WEBPACK_AMD_DEFINE_ARRAY__ = [
            __webpack_require__(0),
            __webpack_require__(267)
        ], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
    } else if (typeof exports === 'object') {
        // Node/CommonJS:
        factory(
            require('jquery'),
            require('./vendor/jquery.ui.widget')
        );
    } else {
        // Browser globals:
        factory(window.jQuery);
    }
}(function ($) {
    'use strict';

    // Detect file input support, based on
    // http://viljamis.com/blog/2012/file-upload-support-on-mobile/
    $.support.fileInput = !(new RegExp(
        // Handle devices which give false positives for the feature detection:
        '(Android (1\\.[0156]|2\\.[01]))' +
            '|(Windows Phone (OS 7|8\\.0))|(XBLWP)|(ZuneWP)|(WPDesktop)' +
            '|(w(eb)?OSBrowser)|(webOS)' +
            '|(Kindle/(1\\.0|2\\.[05]|3\\.0))'
    ).test(window.navigator.userAgent) ||
        // Feature detection for all other devices:
        $('<input type="file">').prop('disabled'));

    // The FileReader API is not actually used, but works as feature detection,
    // as some Safari versions (5?) support XHR file uploads via the FormData API,
    // but not non-multipart XHR file uploads.
    // window.XMLHttpRequestUpload is not available on IE10, so we check for
    // window.ProgressEvent instead to detect XHR2 file upload capability:
    $.support.xhrFileUpload = !!(window.ProgressEvent && window.FileReader);
    $.support.xhrFormDataFileUpload = !!window.FormData;

    // Detect support for Blob slicing (required for chunked uploads):
    $.support.blobSlice = window.Blob && (Blob.prototype.slice ||
        Blob.prototype.webkitSlice || Blob.prototype.mozSlice);

    // Helper function to create drag handlers for dragover/dragenter/dragleave:
    function getDragHandler(type) {
        var isDragOver = type === 'dragover';
        return function (e) {
            e.dataTransfer = e.originalEvent && e.originalEvent.dataTransfer;
            var dataTransfer = e.dataTransfer;
            if (dataTransfer && $.inArray('Files', dataTransfer.types) !== -1 &&
                    this._trigger(
                        type,
                        $.Event(type, {delegatedEvent: e})
                    ) !== false) {
                e.preventDefault();
                if (isDragOver) {
                    dataTransfer.dropEffect = 'copy';
                }
            }
        };
    }

    // The fileupload widget listens for change events on file input fields defined
    // via fileInput setting and paste or drop events of the given dropZone.
    // In addition to the default jQuery Widget methods, the fileupload widget
    // exposes the "add" and "send" methods, to add or directly send files using
    // the fileupload API.
    // By default, files added via file input selection, paste, drag & drop or
    // "add" method are uploaded immediately, but it is possible to override
    // the "add" callback option to queue file uploads.
    $.widget('blueimp.fileupload', {

        options: {
            // The drop target element(s), by the default the complete document.
            // Set to null to disable drag & drop support:
            dropZone: $(document),
            // The paste target element(s), by the default undefined.
            // Set to a DOM node or jQuery object to enable file pasting:
            pasteZone: undefined,
            // The file input field(s), that are listened to for change events.
            // If undefined, it is set to the file input fields inside
            // of the widget element on plugin initialization.
            // Set to null to disable the change listener.
            fileInput: undefined,
            // By default, the file input field is replaced with a clone after
            // each input field change event. This is required for iframe transport
            // queues and allows change events to be fired for the same file
            // selection, but can be disabled by setting the following option to false:
            replaceFileInput: true,
            // The parameter name for the file form data (the request argument name).
            // If undefined or empty, the name property of the file input field is
            // used, or "files[]" if the file input name property is also empty,
            // can be a string or an array of strings:
            paramName: undefined,
            // By default, each file of a selection is uploaded using an individual
            // request for XHR type uploads. Set to false to upload file
            // selections in one request each:
            singleFileUploads: true,
            // To limit the number of files uploaded with one XHR request,
            // set the following option to an integer greater than 0:
            limitMultiFileUploads: undefined,
            // The following option limits the number of files uploaded with one
            // XHR request to keep the request size under or equal to the defined
            // limit in bytes:
            limitMultiFileUploadSize: undefined,
            // Multipart file uploads add a number of bytes to each uploaded file,
            // therefore the following option adds an overhead for each file used
            // in the limitMultiFileUploadSize configuration:
            limitMultiFileUploadSizeOverhead: 512,
            // Set the following option to true to issue all file upload requests
            // in a sequential order:
            sequentialUploads: false,
            // To limit the number of concurrent uploads,
            // set the following option to an integer greater than 0:
            limitConcurrentUploads: undefined,
            // Set the following option to true to force iframe transport uploads:
            forceIframeTransport: false,
            // Set the following option to the location of a redirect url on the
            // origin server, for cross-domain iframe transport uploads:
            redirect: undefined,
            // The parameter name for the redirect url, sent as part of the form
            // data and set to 'redirect' if this option is empty:
            redirectParamName: undefined,
            // Set the following option to the location of a postMessage window,
            // to enable postMessage transport uploads:
            postMessage: undefined,
            // By default, XHR file uploads are sent as multipart/form-data.
            // The iframe transport is always using multipart/form-data.
            // Set to false to enable non-multipart XHR uploads:
            multipart: true,
            // To upload large files in smaller chunks, set the following option
            // to a preferred maximum chunk size. If set to 0, null or undefined,
            // or the browser does not support the required Blob API, files will
            // be uploaded as a whole.
            maxChunkSize: undefined,
            // When a non-multipart upload or a chunked multipart upload has been
            // aborted, this option can be used to resume the upload by setting
            // it to the size of the already uploaded bytes. This option is most
            // useful when modifying the options object inside of the "add" or
            // "send" callbacks, as the options are cloned for each file upload.
            uploadedBytes: undefined,
            // By default, failed (abort or error) file uploads are removed from the
            // global progress calculation. Set the following option to false to
            // prevent recalculating the global progress data:
            recalculateProgress: true,
            // Interval in milliseconds to calculate and trigger progress events:
            progressInterval: 100,
            // Interval in milliseconds to calculate progress bitrate:
            bitrateInterval: 500,
            // By default, uploads are started automatically when adding files:
            autoUpload: true,

            // Error and info messages:
            messages: {
                uploadedBytes: 'Uploaded bytes exceed file size'
            },

            // Translation function, gets the message key to be translated
            // and an object with context specific data as arguments:
            i18n: function (message, context) {
                message = this.messages[message] || message.toString();
                if (context) {
                    $.each(context, function (key, value) {
                        message = message.replace('{' + key + '}', value);
                    });
                }
                return message;
            },

            // Additional form data to be sent along with the file uploads can be set
            // using this option, which accepts an array of objects with name and
            // value properties, a function returning such an array, a FormData
            // object (for XHR file uploads), or a simple object.
            // The form of the first fileInput is given as parameter to the function:
            formData: function (form) {
                return form.serializeArray();
            },

            // The add callback is invoked as soon as files are added to the fileupload
            // widget (via file input selection, drag & drop, paste or add API call).
            // If the singleFileUploads option is enabled, this callback will be
            // called once for each file in the selection for XHR file uploads, else
            // once for each file selection.
            //
            // The upload starts when the submit method is invoked on the data parameter.
            // The data object contains a files property holding the added files
            // and allows you to override plugin options as well as define ajax settings.
            //
            // Listeners for this callback can also be bound the following way:
            // .bind('fileuploadadd', func);
            //
            // data.submit() returns a Promise object and allows to attach additional
            // handlers using jQuery's Deferred callbacks:
            // data.submit().done(func).fail(func).always(func);
            add: function (e, data) {
                if (e.isDefaultPrevented()) {
                    return false;
                }
                if (data.autoUpload || (data.autoUpload !== false &&
                        $(this).fileupload('option', 'autoUpload'))) {
                    data.process().done(function () {
                        data.submit();
                    });
                }
            },

            // Other callbacks:

            // Callback for the submit event of each file upload:
            // submit: function (e, data) {}, // .bind('fileuploadsubmit', func);

            // Callback for the start of each file upload request:
            // send: function (e, data) {}, // .bind('fileuploadsend', func);

            // Callback for successful uploads:
            // done: function (e, data) {}, // .bind('fileuploaddone', func);

            // Callback for failed (abort or error) uploads:
            // fail: function (e, data) {}, // .bind('fileuploadfail', func);

            // Callback for completed (success, abort or error) requests:
            // always: function (e, data) {}, // .bind('fileuploadalways', func);

            // Callback for upload progress events:
            // progress: function (e, data) {}, // .bind('fileuploadprogress', func);

            // Callback for global upload progress events:
            // progressall: function (e, data) {}, // .bind('fileuploadprogressall', func);

            // Callback for uploads start, equivalent to the global ajaxStart event:
            // start: function (e) {}, // .bind('fileuploadstart', func);

            // Callback for uploads stop, equivalent to the global ajaxStop event:
            // stop: function (e) {}, // .bind('fileuploadstop', func);

            // Callback for change events of the fileInput(s):
            // change: function (e, data) {}, // .bind('fileuploadchange', func);

            // Callback for paste events to the pasteZone(s):
            // paste: function (e, data) {}, // .bind('fileuploadpaste', func);

            // Callback for drop events of the dropZone(s):
            // drop: function (e, data) {}, // .bind('fileuploaddrop', func);

            // Callback for dragover events of the dropZone(s):
            // dragover: function (e) {}, // .bind('fileuploaddragover', func);

            // Callback for the start of each chunk upload request:
            // chunksend: function (e, data) {}, // .bind('fileuploadchunksend', func);

            // Callback for successful chunk uploads:
            // chunkdone: function (e, data) {}, // .bind('fileuploadchunkdone', func);

            // Callback for failed (abort or error) chunk uploads:
            // chunkfail: function (e, data) {}, // .bind('fileuploadchunkfail', func);

            // Callback for completed (success, abort or error) chunk upload requests:
            // chunkalways: function (e, data) {}, // .bind('fileuploadchunkalways', func);

            // The plugin options are used as settings object for the ajax calls.
            // The following are jQuery ajax settings required for the file uploads:
            processData: false,
            contentType: false,
            cache: false,
            timeout: 0
        },

        // A list of options that require reinitializing event listeners and/or
        // special initialization code:
        _specialOptions: [
            'fileInput',
            'dropZone',
            'pasteZone',
            'multipart',
            'forceIframeTransport'
        ],

        _blobSlice: $.support.blobSlice && function () {
            var slice = this.slice || this.webkitSlice || this.mozSlice;
            return slice.apply(this, arguments);
        },

        _BitrateTimer: function () {
            this.timestamp = ((Date.now) ? Date.now() : (new Date()).getTime());
            this.loaded = 0;
            this.bitrate = 0;
            this.getBitrate = function (now, loaded, interval) {
                var timeDiff = now - this.timestamp;
                if (!this.bitrate || !interval || timeDiff > interval) {
                    this.bitrate = (loaded - this.loaded) * (1000 / timeDiff) * 8;
                    this.loaded = loaded;
                    this.timestamp = now;
                }
                return this.bitrate;
            };
        },

        _isXHRUpload: function (options) {
            return !options.forceIframeTransport &&
                ((!options.multipart && $.support.xhrFileUpload) ||
                $.support.xhrFormDataFileUpload);
        },

        _getFormData: function (options) {
            var formData;
            if ($.type(options.formData) === 'function') {
                return options.formData(options.form);
            }
            if ($.isArray(options.formData)) {
                return options.formData;
            }
            if ($.type(options.formData) === 'object') {
                formData = [];
                $.each(options.formData, function (name, value) {
                    formData.push({name: name, value: value});
                });
                return formData;
            }
            return [];
        },

        _getTotal: function (files) {
            var total = 0;
            $.each(files, function (index, file) {
                total += file.size || 1;
            });
            return total;
        },

        _initProgressObject: function (obj) {
            var progress = {
                loaded: 0,
                total: 0,
                bitrate: 0
            };
            if (obj._progress) {
                $.extend(obj._progress, progress);
            } else {
                obj._progress = progress;
            }
        },

        _initResponseObject: function (obj) {
            var prop;
            if (obj._response) {
                for (prop in obj._response) {
                    if (obj._response.hasOwnProperty(prop)) {
                        delete obj._response[prop];
                    }
                }
            } else {
                obj._response = {};
            }
        },

        _onProgress: function (e, data) {
            if (e.lengthComputable) {
                var now = ((Date.now) ? Date.now() : (new Date()).getTime()),
                    loaded;
                if (data._time && data.progressInterval &&
                        (now - data._time < data.progressInterval) &&
                        e.loaded !== e.total) {
                    return;
                }
                data._time = now;
                loaded = Math.floor(
                    e.loaded / e.total * (data.chunkSize || data._progress.total)
                ) + (data.uploadedBytes || 0);
                // Add the difference from the previously loaded state
                // to the global loaded counter:
                this._progress.loaded += (loaded - data._progress.loaded);
                this._progress.bitrate = this._bitrateTimer.getBitrate(
                    now,
                    this._progress.loaded,
                    data.bitrateInterval
                );
                data._progress.loaded = data.loaded = loaded;
                data._progress.bitrate = data.bitrate = data._bitrateTimer.getBitrate(
                    now,
                    loaded,
                    data.bitrateInterval
                );
                // Trigger a custom progress event with a total data property set
                // to the file size(s) of the current upload and a loaded data
                // property calculated accordingly:
                this._trigger(
                    'progress',
                    $.Event('progress', {delegatedEvent: e}),
                    data
                );
                // Trigger a global progress event for all current file uploads,
                // including ajax calls queued for sequential file uploads:
                this._trigger(
                    'progressall',
                    $.Event('progressall', {delegatedEvent: e}),
                    this._progress
                );
            }
        },

        _initProgressListener: function (options) {
            var that = this,
                xhr = options.xhr ? options.xhr() : $.ajaxSettings.xhr();
            // Accesss to the native XHR object is required to add event listeners
            // for the upload progress event:
            if (xhr.upload) {
                $(xhr.upload).bind('progress', function (e) {
                    var oe = e.originalEvent;
                    // Make sure the progress event properties get copied over:
                    e.lengthComputable = oe.lengthComputable;
                    e.loaded = oe.loaded;
                    e.total = oe.total;
                    that._onProgress(e, options);
                });
                options.xhr = function () {
                    return xhr;
                };
            }
        },

        _isInstanceOf: function (type, obj) {
            // Cross-frame instanceof check
            return Object.prototype.toString.call(obj) === '[object ' + type + ']';
        },

        _initXHRData: function (options) {
            var that = this,
                formData,
                file = options.files[0],
                // Ignore non-multipart setting if not supported:
                multipart = options.multipart || !$.support.xhrFileUpload,
                paramName = $.type(options.paramName) === 'array' ?
                    options.paramName[0] : options.paramName;
            options.headers = $.extend({}, options.headers);
            if (options.contentRange) {
                options.headers['Content-Range'] = options.contentRange;
            }
            if (!multipart || options.blob || !this._isInstanceOf('File', file)) {
                options.headers['Content-Disposition'] = 'attachment; filename="' +
                    encodeURI(file.name) + '"';
            }
            if (!multipart) {
                options.contentType = file.type || 'application/octet-stream';
                options.data = options.blob || file;
            } else if ($.support.xhrFormDataFileUpload) {
                if (options.postMessage) {
                    // window.postMessage does not allow sending FormData
                    // objects, so we just add the File/Blob objects to
                    // the formData array and let the postMessage window
                    // create the FormData object out of this array:
                    formData = this._getFormData(options);
                    if (options.blob) {
                        formData.push({
                            name: paramName,
                            value: options.blob
                        });
                    } else {
                        $.each(options.files, function (index, file) {
                            formData.push({
                                name: ($.type(options.paramName) === 'array' &&
                                    options.paramName[index]) || paramName,
                                value: file
                            });
                        });
                    }
                } else {
                    if (that._isInstanceOf('FormData', options.formData)) {
                        formData = options.formData;
                    } else {
                        formData = new FormData();
                        $.each(this._getFormData(options), function (index, field) {
                            formData.append(field.name, field.value);
                        });
                    }
                    if (options.blob) {
                        formData.append(paramName, options.blob, file.name);
                    } else {
                        $.each(options.files, function (index, file) {
                            // This check allows the tests to run with
                            // dummy objects:
                            if (that._isInstanceOf('File', file) ||
                                    that._isInstanceOf('Blob', file)) {
                                formData.append(
                                    ($.type(options.paramName) === 'array' &&
                                        options.paramName[index]) || paramName,
                                    file,
                                    file.uploadName || file.name
                                );
                            }
                        });
                    }
                }
                options.data = formData;
            }
            // Blob reference is not needed anymore, free memory:
            options.blob = null;
        },

        _initIframeSettings: function (options) {
            var targetHost = $('<a></a>').prop('href', options.url).prop('host');
            // Setting the dataType to iframe enables the iframe transport:
            options.dataType = 'iframe ' + (options.dataType || '');
            // The iframe transport accepts a serialized array as form data:
            options.formData = this._getFormData(options);
            // Add redirect url to form data on cross-domain uploads:
            if (options.redirect && targetHost && targetHost !== location.host) {
                options.formData.push({
                    name: options.redirectParamName || 'redirect',
                    value: options.redirect
                });
            }
        },

        _initDataSettings: function (options) {
            if (this._isXHRUpload(options)) {
                if (!this._chunkedUpload(options, true)) {
                    if (!options.data) {
                        this._initXHRData(options);
                    }
                    this._initProgressListener(options);
                }
                if (options.postMessage) {
                    // Setting the dataType to postmessage enables the
                    // postMessage transport:
                    options.dataType = 'postmessage ' + (options.dataType || '');
                }
            } else {
                this._initIframeSettings(options);
            }
        },

        _getParamName: function (options) {
            var fileInput = $(options.fileInput),
                paramName = options.paramName;
            if (!paramName) {
                paramName = [];
                fileInput.each(function () {
                    var input = $(this),
                        name = input.prop('name') || 'files[]',
                        i = (input.prop('files') || [1]).length;
                    while (i) {
                        paramName.push(name);
                        i -= 1;
                    }
                });
                if (!paramName.length) {
                    paramName = [fileInput.prop('name') || 'files[]'];
                }
            } else if (!$.isArray(paramName)) {
                paramName = [paramName];
            }
            return paramName;
        },

        _initFormSettings: function (options) {
            // Retrieve missing options from the input field and the
            // associated form, if available:
            if (!options.form || !options.form.length) {
                options.form = $(options.fileInput.prop('form'));
                // If the given file input doesn't have an associated form,
                // use the default widget file input's form:
                if (!options.form.length) {
                    options.form = $(this.options.fileInput.prop('form'));
                }
            }
            options.paramName = this._getParamName(options);
            if (!options.url) {
                options.url = options.form.prop('action') || location.href;
            }
            // The HTTP request method must be "POST" or "PUT":
            options.type = (options.type ||
                ($.type(options.form.prop('method')) === 'string' &&
                    options.form.prop('method')) || ''
                ).toUpperCase();
            if (options.type !== 'POST' && options.type !== 'PUT' &&
                    options.type !== 'PATCH') {
                options.type = 'POST';
            }
            if (!options.formAcceptCharset) {
                options.formAcceptCharset = options.form.attr('accept-charset');
            }
        },

        _getAJAXSettings: function (data) {
            var options = $.extend({}, this.options, data);
            this._initFormSettings(options);
            this._initDataSettings(options);
            return options;
        },

        // jQuery 1.6 doesn't provide .state(),
        // while jQuery 1.8+ removed .isRejected() and .isResolved():
        _getDeferredState: function (deferred) {
            if (deferred.state) {
                return deferred.state();
            }
            if (deferred.isResolved()) {
                return 'resolved';
            }
            if (deferred.isRejected()) {
                return 'rejected';
            }
            return 'pending';
        },

        // Maps jqXHR callbacks to the equivalent
        // methods of the given Promise object:
        _enhancePromise: function (promise) {
            promise.success = promise.done;
            promise.error = promise.fail;
            promise.complete = promise.always;
            return promise;
        },

        // Creates and returns a Promise object enhanced with
        // the jqXHR methods abort, success, error and complete:
        _getXHRPromise: function (resolveOrReject, context, args) {
            var dfd = $.Deferred(),
                promise = dfd.promise();
            context = context || this.options.context || promise;
            if (resolveOrReject === true) {
                dfd.resolveWith(context, args);
            } else if (resolveOrReject === false) {
                dfd.rejectWith(context, args);
            }
            promise.abort = dfd.promise;
            return this._enhancePromise(promise);
        },

        // Adds convenience methods to the data callback argument:
        _addConvenienceMethods: function (e, data) {
            var that = this,
                getPromise = function (args) {
                    return $.Deferred().resolveWith(that, args).promise();
                };
            data.process = function (resolveFunc, rejectFunc) {
                if (resolveFunc || rejectFunc) {
                    data._processQueue = this._processQueue =
                        (this._processQueue || getPromise([this])).then(
                            function () {
                                if (data.errorThrown) {
                                    return $.Deferred()
                                        .rejectWith(that, [data]).promise();
                                }
                                return getPromise(arguments);
                            }
                        ).then(resolveFunc, rejectFunc);
                }
                return this._processQueue || getPromise([this]);
            };
            data.submit = function () {
                if (this.state() !== 'pending') {
                    data.jqXHR = this.jqXHR =
                        (that._trigger(
                            'submit',
                            $.Event('submit', {delegatedEvent: e}),
                            this
                        ) !== false) && that._onSend(e, this);
                }
                return this.jqXHR || that._getXHRPromise();
            };
            data.abort = function () {
                if (this.jqXHR) {
                    return this.jqXHR.abort();
                }
                this.errorThrown = 'abort';
                that._trigger('fail', null, this);
                return that._getXHRPromise(false);
            };
            data.state = function () {
                if (this.jqXHR) {
                    return that._getDeferredState(this.jqXHR);
                }
                if (this._processQueue) {
                    return that._getDeferredState(this._processQueue);
                }
            };
            data.processing = function () {
                return !this.jqXHR && this._processQueue && that
                    ._getDeferredState(this._processQueue) === 'pending';
            };
            data.progress = function () {
                return this._progress;
            };
            data.response = function () {
                return this._response;
            };
        },

        // Parses the Range header from the server response
        // and returns the uploaded bytes:
        _getUploadedBytes: function (jqXHR) {
            var range = jqXHR.getResponseHeader('Range'),
                parts = range && range.split('-'),
                upperBytesPos = parts && parts.length > 1 &&
                    parseInt(parts[1], 10);
            return upperBytesPos && upperBytesPos + 1;
        },

        // Uploads a file in multiple, sequential requests
        // by splitting the file up in multiple blob chunks.
        // If the second parameter is true, only tests if the file
        // should be uploaded in chunks, but does not invoke any
        // upload requests:
        _chunkedUpload: function (options, testOnly) {
            options.uploadedBytes = options.uploadedBytes || 0;
            var that = this,
                file = options.files[0],
                fs = file.size,
                ub = options.uploadedBytes,
                mcs = options.maxChunkSize || fs,
                slice = this._blobSlice,
                dfd = $.Deferred(),
                promise = dfd.promise(),
                jqXHR,
                upload;
            if (!(this._isXHRUpload(options) && slice && (ub || mcs < fs)) ||
                    options.data) {
                return false;
            }
            if (testOnly) {
                return true;
            }
            if (ub >= fs) {
                file.error = options.i18n('uploadedBytes');
                return this._getXHRPromise(
                    false,
                    options.context,
                    [null, 'error', file.error]
                );
            }
            // The chunk upload method:
            upload = function () {
                // Clone the options object for each chunk upload:
                var o = $.extend({}, options),
                    currentLoaded = o._progress.loaded;
                o.blob = slice.call(
                    file,
                    ub,
                    ub + mcs,
                    file.type
                );
                // Store the current chunk size, as the blob itself
                // will be dereferenced after data processing:
                o.chunkSize = o.blob.size;
                // Expose the chunk bytes position range:
                o.contentRange = 'bytes ' + ub + '-' +
                    (ub + o.chunkSize - 1) + '/' + fs;
                // Process the upload data (the blob and potential form data):
                that._initXHRData(o);
                // Add progress listeners for this chunk upload:
                that._initProgressListener(o);
                jqXHR = ((that._trigger('chunksend', null, o) !== false && $.ajax(o)) ||
                        that._getXHRPromise(false, o.context))
                    .done(function (result, textStatus, jqXHR) {
                        ub = that._getUploadedBytes(jqXHR) ||
                            (ub + o.chunkSize);
                        // Create a progress event if no final progress event
                        // with loaded equaling total has been triggered
                        // for this chunk:
                        if (currentLoaded + o.chunkSize - o._progress.loaded) {
                            that._onProgress($.Event('progress', {
                                lengthComputable: true,
                                loaded: ub - o.uploadedBytes,
                                total: ub - o.uploadedBytes
                            }), o);
                        }
                        options.uploadedBytes = o.uploadedBytes = ub;
                        o.result = result;
                        o.textStatus = textStatus;
                        o.jqXHR = jqXHR;
                        that._trigger('chunkdone', null, o);
                        that._trigger('chunkalways', null, o);
                        if (ub < fs) {
                            // File upload not yet complete,
                            // continue with the next chunk:
                            upload();
                        } else {
                            dfd.resolveWith(
                                o.context,
                                [result, textStatus, jqXHR]
                            );
                        }
                    })
                    .fail(function (jqXHR, textStatus, errorThrown) {
                        o.jqXHR = jqXHR;
                        o.textStatus = textStatus;
                        o.errorThrown = errorThrown;
                        that._trigger('chunkfail', null, o);
                        that._trigger('chunkalways', null, o);
                        dfd.rejectWith(
                            o.context,
                            [jqXHR, textStatus, errorThrown]
                        );
                    });
            };
            this._enhancePromise(promise);
            promise.abort = function () {
                return jqXHR.abort();
            };
            upload();
            return promise;
        },

        _beforeSend: function (e, data) {
            if (this._active === 0) {
                // the start callback is triggered when an upload starts
                // and no other uploads are currently running,
                // equivalent to the global ajaxStart event:
                this._trigger('start');
                // Set timer for global bitrate progress calculation:
                this._bitrateTimer = new this._BitrateTimer();
                // Reset the global progress values:
                this._progress.loaded = this._progress.total = 0;
                this._progress.bitrate = 0;
            }
            // Make sure the container objects for the .response() and
            // .progress() methods on the data object are available
            // and reset to their initial state:
            this._initResponseObject(data);
            this._initProgressObject(data);
            data._progress.loaded = data.loaded = data.uploadedBytes || 0;
            data._progress.total = data.total = this._getTotal(data.files) || 1;
            data._progress.bitrate = data.bitrate = 0;
            this._active += 1;
            // Initialize the global progress values:
            this._progress.loaded += data.loaded;
            this._progress.total += data.total;
        },

        _onDone: function (result, textStatus, jqXHR, options) {
            var total = options._progress.total,
                response = options._response;
            if (options._progress.loaded < total) {
                // Create a progress event if no final progress event
                // with loaded equaling total has been triggered:
                this._onProgress($.Event('progress', {
                    lengthComputable: true,
                    loaded: total,
                    total: total
                }), options);
            }
            response.result = options.result = result;
            response.textStatus = options.textStatus = textStatus;
            response.jqXHR = options.jqXHR = jqXHR;
            this._trigger('done', null, options);
        },

        _onFail: function (jqXHR, textStatus, errorThrown, options) {
            var response = options._response;
            if (options.recalculateProgress) {
                // Remove the failed (error or abort) file upload from
                // the global progress calculation:
                this._progress.loaded -= options._progress.loaded;
                this._progress.total -= options._progress.total;
            }
            response.jqXHR = options.jqXHR = jqXHR;
            response.textStatus = options.textStatus = textStatus;
            response.errorThrown = options.errorThrown = errorThrown;
            this._trigger('fail', null, options);
        },

        _onAlways: function (jqXHRorResult, textStatus, jqXHRorError, options) {
            // jqXHRorResult, textStatus and jqXHRorError are added to the
            // options object via done and fail callbacks
            this._trigger('always', null, options);
        },

        _onSend: function (e, data) {
            if (!data.submit) {
                this._addConvenienceMethods(e, data);
            }
            var that = this,
                jqXHR,
                aborted,
                slot,
                pipe,
                options = that._getAJAXSettings(data),
                send = function () {
                    that._sending += 1;
                    // Set timer for bitrate progress calculation:
                    options._bitrateTimer = new that._BitrateTimer();
                    jqXHR = jqXHR || (
                        ((aborted || that._trigger(
                            'send',
                            $.Event('send', {delegatedEvent: e}),
                            options
                        ) === false) &&
                        that._getXHRPromise(false, options.context, aborted)) ||
                        that._chunkedUpload(options) || $.ajax(options)
                    ).done(function (result, textStatus, jqXHR) {
                        that._onDone(result, textStatus, jqXHR, options);
                    }).fail(function (jqXHR, textStatus, errorThrown) {
                        that._onFail(jqXHR, textStatus, errorThrown, options);
                    }).always(function (jqXHRorResult, textStatus, jqXHRorError) {
                        that._onAlways(
                            jqXHRorResult,
                            textStatus,
                            jqXHRorError,
                            options
                        );
                        that._sending -= 1;
                        that._active -= 1;
                        if (options.limitConcurrentUploads &&
                                options.limitConcurrentUploads > that._sending) {
                            // Start the next queued upload,
                            // that has not been aborted:
                            var nextSlot = that._slots.shift();
                            while (nextSlot) {
                                if (that._getDeferredState(nextSlot) === 'pending') {
                                    nextSlot.resolve();
                                    break;
                                }
                                nextSlot = that._slots.shift();
                            }
                        }
                        if (that._active === 0) {
                            // The stop callback is triggered when all uploads have
                            // been completed, equivalent to the global ajaxStop event:
                            that._trigger('stop');
                        }
                    });
                    return jqXHR;
                };
            this._beforeSend(e, options);
            if (this.options.sequentialUploads ||
                    (this.options.limitConcurrentUploads &&
                    this.options.limitConcurrentUploads <= this._sending)) {
                if (this.options.limitConcurrentUploads > 1) {
                    slot = $.Deferred();
                    this._slots.push(slot);
                    pipe = slot.then(send);
                } else {
                    this._sequence = this._sequence.then(send, send);
                    pipe = this._sequence;
                }
                // Return the piped Promise object, enhanced with an abort method,
                // which is delegated to the jqXHR object of the current upload,
                // and jqXHR callbacks mapped to the equivalent Promise methods:
                pipe.abort = function () {
                    aborted = [undefined, 'abort', 'abort'];
                    if (!jqXHR) {
                        if (slot) {
                            slot.rejectWith(options.context, aborted);
                        }
                        return send();
                    }
                    return jqXHR.abort();
                };
                return this._enhancePromise(pipe);
            }
            return send();
        },

        _onAdd: function (e, data) {
            var that = this,
                result = true,
                options = $.extend({}, this.options, data),
                files = data.files,
                filesLength = files.length,
                limit = options.limitMultiFileUploads,
                limitSize = options.limitMultiFileUploadSize,
                overhead = options.limitMultiFileUploadSizeOverhead,
                batchSize = 0,
                paramName = this._getParamName(options),
                paramNameSet,
                paramNameSlice,
                fileSet,
                i,
                j = 0;
            if (!filesLength) {
                return false;
            }
            if (limitSize && files[0].size === undefined) {
                limitSize = undefined;
            }
            if (!(options.singleFileUploads || limit || limitSize) ||
                    !this._isXHRUpload(options)) {
                fileSet = [files];
                paramNameSet = [paramName];
            } else if (!(options.singleFileUploads || limitSize) && limit) {
                fileSet = [];
                paramNameSet = [];
                for (i = 0; i < filesLength; i += limit) {
                    fileSet.push(files.slice(i, i + limit));
                    paramNameSlice = paramName.slice(i, i + limit);
                    if (!paramNameSlice.length) {
                        paramNameSlice = paramName;
                    }
                    paramNameSet.push(paramNameSlice);
                }
            } else if (!options.singleFileUploads && limitSize) {
                fileSet = [];
                paramNameSet = [];
                for (i = 0; i < filesLength; i = i + 1) {
                    batchSize += files[i].size + overhead;
                    if (i + 1 === filesLength ||
                            ((batchSize + files[i + 1].size + overhead) > limitSize) ||
                            (limit && i + 1 - j >= limit)) {
                        fileSet.push(files.slice(j, i + 1));
                        paramNameSlice = paramName.slice(j, i + 1);
                        if (!paramNameSlice.length) {
                            paramNameSlice = paramName;
                        }
                        paramNameSet.push(paramNameSlice);
                        j = i + 1;
                        batchSize = 0;
                    }
                }
            } else {
                paramNameSet = paramName;
            }
            data.originalFiles = files;
            $.each(fileSet || files, function (index, element) {
                var newData = $.extend({}, data);
                newData.files = fileSet ? element : [element];
                newData.paramName = paramNameSet[index];
                that._initResponseObject(newData);
                that._initProgressObject(newData);
                that._addConvenienceMethods(e, newData);
                result = that._trigger(
                    'add',
                    $.Event('add', {delegatedEvent: e}),
                    newData
                );
                return result;
            });
            return result;
        },

        _replaceFileInput: function (data) {
            var input = data.fileInput,
                inputClone = input.clone(true),
                restoreFocus = input.is(document.activeElement);
            // Add a reference for the new cloned file input to the data argument:
            data.fileInputClone = inputClone;
            $('<form></form>').append(inputClone)[0].reset();
            // Detaching allows to insert the fileInput on another form
            // without loosing the file input value:
            input.after(inputClone).detach();
            // If the fileInput had focus before it was detached,
            // restore focus to the inputClone.
            if (restoreFocus) {
                inputClone.focus();
            }
            // Avoid memory leaks with the detached file input:
            $.cleanData(input.unbind('remove'));
            // Replace the original file input element in the fileInput
            // elements set with the clone, which has been copied including
            // event handlers:
            this.options.fileInput = this.options.fileInput.map(function (i, el) {
                if (el === input[0]) {
                    return inputClone[0];
                }
                return el;
            });
            // If the widget has been initialized on the file input itself,
            // override this.element with the file input clone:
            if (input[0] === this.element[0]) {
                this.element = inputClone;
            }
        },

        _handleFileTreeEntry: function (entry, path) {
            var that = this,
                dfd = $.Deferred(),
                errorHandler = function (e) {
                    if (e && !e.entry) {
                        e.entry = entry;
                    }
                    // Since $.when returns immediately if one
                    // Deferred is rejected, we use resolve instead.
                    // This allows valid files and invalid items
                    // to be returned together in one set:
                    dfd.resolve([e]);
                },
                successHandler = function (entries) {
                    that._handleFileTreeEntries(
                        entries,
                        path + entry.name + '/'
                    ).done(function (files) {
                        dfd.resolve(files);
                    }).fail(errorHandler);
                },
                readEntries = function () {
                    dirReader.readEntries(function (results) {
                        if (!results.length) {
                            successHandler(entries);
                        } else {
                            entries = entries.concat(results);
                            readEntries();
                        }
                    }, errorHandler);
                },
                dirReader, entries = [];
            path = path || '';
            if (entry.isFile) {
                if (entry._file) {
                    // Workaround for Chrome bug #149735
                    entry._file.relativePath = path;
                    dfd.resolve(entry._file);
                } else {
                    entry.file(function (file) {
                        file.relativePath = path;
                        dfd.resolve(file);
                    }, errorHandler);
                }
            } else if (entry.isDirectory) {
                dirReader = entry.createReader();
                readEntries();
            } else {
                // Return an empy list for file system items
                // other than files or directories:
                dfd.resolve([]);
            }
            return dfd.promise();
        },

        _handleFileTreeEntries: function (entries, path) {
            var that = this;
            return $.when.apply(
                $,
                $.map(entries, function (entry) {
                    return that._handleFileTreeEntry(entry, path);
                })
            ).then(function () {
                return Array.prototype.concat.apply(
                    [],
                    arguments
                );
            });
        },

        _getDroppedFiles: function (dataTransfer) {
            dataTransfer = dataTransfer || {};
            var items = dataTransfer.items;
            if (items && items.length && (items[0].webkitGetAsEntry ||
                    items[0].getAsEntry)) {
                return this._handleFileTreeEntries(
                    $.map(items, function (item) {
                        var entry;
                        if (item.webkitGetAsEntry) {
                            entry = item.webkitGetAsEntry();
                            if (entry) {
                                // Workaround for Chrome bug #149735:
                                entry._file = item.getAsFile();
                            }
                            return entry;
                        }
                        return item.getAsEntry();
                    })
                );
            }
            return $.Deferred().resolve(
                $.makeArray(dataTransfer.files)
            ).promise();
        },

        _getSingleFileInputFiles: function (fileInput) {
            fileInput = $(fileInput);
            var entries = fileInput.prop('webkitEntries') ||
                    fileInput.prop('entries'),
                files,
                value;
            if (entries && entries.length) {
                return this._handleFileTreeEntries(entries);
            }
            files = $.makeArray(fileInput.prop('files'));
            if (!files.length) {
                value = fileInput.prop('value');
                if (!value) {
                    return $.Deferred().resolve([]).promise();
                }
                // If the files property is not available, the browser does not
                // support the File API and we add a pseudo File object with
                // the input value as name with path information removed:
                files = [{name: value.replace(/^.*\\/, '')}];
            } else if (files[0].name === undefined && files[0].fileName) {
                // File normalization for Safari 4 and Firefox 3:
                $.each(files, function (index, file) {
                    file.name = file.fileName;
                    file.size = file.fileSize;
                });
            }
            return $.Deferred().resolve(files).promise();
        },

        _getFileInputFiles: function (fileInput) {
            if (!(fileInput instanceof $) || fileInput.length === 1) {
                return this._getSingleFileInputFiles(fileInput);
            }
            return $.when.apply(
                $,
                $.map(fileInput, this._getSingleFileInputFiles)
            ).then(function () {
                return Array.prototype.concat.apply(
                    [],
                    arguments
                );
            });
        },

        _onChange: function (e) {
            var that = this,
                data = {
                    fileInput: $(e.target),
                    form: $(e.target.form)
                };
            this._getFileInputFiles(data.fileInput).always(function (files) {
                data.files = files;
                if (that.options.replaceFileInput) {
                    that._replaceFileInput(data);
                }
                if (that._trigger(
                        'change',
                        $.Event('change', {delegatedEvent: e}),
                        data
                    ) !== false) {
                    that._onAdd(e, data);
                }
            });
        },

        _onPaste: function (e) {
            var items = e.originalEvent && e.originalEvent.clipboardData &&
                    e.originalEvent.clipboardData.items,
                data = {files: []};
            if (items && items.length) {
                $.each(items, function (index, item) {
                    var file = item.getAsFile && item.getAsFile();
                    if (file) {
                        data.files.push(file);
                    }
                });
                if (this._trigger(
                        'paste',
                        $.Event('paste', {delegatedEvent: e}),
                        data
                    ) !== false) {
                    this._onAdd(e, data);
                }
            }
        },

        _onDrop: function (e) {
            e.dataTransfer = e.originalEvent && e.originalEvent.dataTransfer;
            var that = this,
                dataTransfer = e.dataTransfer,
                data = {};
            if (dataTransfer && dataTransfer.files && dataTransfer.files.length) {
                e.preventDefault();
                this._getDroppedFiles(dataTransfer).always(function (files) {
                    data.files = files;
                    if (that._trigger(
                            'drop',
                            $.Event('drop', {delegatedEvent: e}),
                            data
                        ) !== false) {
                        that._onAdd(e, data);
                    }
                });
            }
        },

        _onDragOver: getDragHandler('dragover'),

        _onDragEnter: getDragHandler('dragenter'),

        _onDragLeave: getDragHandler('dragleave'),

        _initEventHandlers: function () {
            if (this._isXHRUpload(this.options)) {
                this._on(this.options.dropZone, {
                    dragover: this._onDragOver,
                    drop: this._onDrop,
                    // event.preventDefault() on dragenter is required for IE10+:
                    dragenter: this._onDragEnter,
                    // dragleave is not required, but added for completeness:
                    dragleave: this._onDragLeave
                });
                this._on(this.options.pasteZone, {
                    paste: this._onPaste
                });
            }
            if ($.support.fileInput) {
                this._on(this.options.fileInput, {
                    change: this._onChange
                });
            }
        },

        _destroyEventHandlers: function () {
            this._off(this.options.dropZone, 'dragenter dragleave dragover drop');
            this._off(this.options.pasteZone, 'paste');
            this._off(this.options.fileInput, 'change');
        },

        _setOption: function (key, value) {
            var reinit = $.inArray(key, this._specialOptions) !== -1;
            if (reinit) {
                this._destroyEventHandlers();
            }
            this._super(key, value);
            if (reinit) {
                this._initSpecialOptions();
                this._initEventHandlers();
            }
        },

        _initSpecialOptions: function () {
            var options = this.options;
            if (options.fileInput === undefined) {
                options.fileInput = this.element.is('input[type="file"]') ?
                        this.element : this.element.find('input[type="file"]');
            } else if (!(options.fileInput instanceof $)) {
                options.fileInput = $(options.fileInput);
            }
            if (!(options.dropZone instanceof $)) {
                options.dropZone = $(options.dropZone);
            }
            if (!(options.pasteZone instanceof $)) {
                options.pasteZone = $(options.pasteZone);
            }
        },

        _getRegExp: function (str) {
            var parts = str.split('/'),
                modifiers = parts.pop();
            parts.shift();
            return new RegExp(parts.join('/'), modifiers);
        },

        _isRegExpOption: function (key, value) {
            return key !== 'url' && $.type(value) === 'string' &&
                /^\/.*\/[igm]{0,3}$/.test(value);
        },

        _initDataAttributes: function () {
            var that = this,
                options = this.options,
                data = this.element.data();
            // Initialize options set via HTML5 data-attributes:
            $.each(
                this.element[0].attributes,
                function (index, attr) {
                    var key = attr.name.toLowerCase(),
                        value;
                    if (/^data-/.test(key)) {
                        // Convert hyphen-ated key to camelCase:
                        key = key.slice(5).replace(/-[a-z]/g, function (str) {
                            return str.charAt(1).toUpperCase();
                        });
                        value = data[key];
                        if (that._isRegExpOption(key, value)) {
                            value = that._getRegExp(value);
                        }
                        options[key] = value;
                    }
                }
            );
        },

        _create: function () {
            this._initDataAttributes();
            this._initSpecialOptions();
            this._slots = [];
            this._sequence = this._getXHRPromise(true);
            this._sending = this._active = 0;
            this._initProgressObject(this);
            this._initEventHandlers();
        },

        // This method is exposed to the widget API and allows to query
        // the number of active uploads:
        active: function () {
            return this._active;
        },

        // This method is exposed to the widget API and allows to query
        // the widget upload progress.
        // It returns an object with loaded, total and bitrate properties
        // for the running uploads:
        progress: function () {
            return this._progress;
        },

        // This method is exposed to the widget API and allows adding files
        // using the fileupload API. The data parameter accepts an object which
        // must have a files property and can contain additional options:
        // .fileupload('add', {files: filesList});
        add: function (data) {
            var that = this;
            if (!data || this.options.disabled) {
                return;
            }
            if (data.fileInput && !data.files) {
                this._getFileInputFiles(data.fileInput).always(function (files) {
                    data.files = files;
                    that._onAdd(null, data);
                });
            } else {
                data.files = $.makeArray(data.files);
                this._onAdd(null, data);
            }
        },

        // This method is exposed to the widget API and allows sending files
        // using the fileupload API. The data parameter accepts an object which
        // must have a files or fileInput property and can contain additional options:
        // .fileupload('send', {files: filesList});
        // The method returns a Promise object for the file upload call.
        send: function (data) {
            if (data && !this.options.disabled) {
                if (data.fileInput && !data.files) {
                    var that = this,
                        dfd = $.Deferred(),
                        promise = dfd.promise(),
                        jqXHR,
                        aborted;
                    promise.abort = function () {
                        aborted = true;
                        if (jqXHR) {
                            return jqXHR.abort();
                        }
                        dfd.reject(null, 'abort', 'abort');
                        return promise;
                    };
                    this._getFileInputFiles(data.fileInput).always(
                        function (files) {
                            if (aborted) {
                                return;
                            }
                            if (!files.length) {
                                dfd.reject();
                                return;
                            }
                            data.files = files;
                            jqXHR = that._onSend(null, data);
                            jqXHR.then(
                                function (result, textStatus, jqXHR) {
                                    dfd.resolve(result, textStatus, jqXHR);
                                },
                                function (jqXHR, textStatus, errorThrown) {
                                    dfd.reject(jqXHR, textStatus, errorThrown);
                                }
                            );
                        }
                    );
                    return this._enhancePromise(promise);
                }
                data.files = $.makeArray(data.files);
                if (data.files.length) {
                    return this._onSend(null, data);
                }
            }
            return this._getXHRPromise(false, data && data.context);
        }

    });

}));


/***/ }),
/* 220 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*
 * JavaScript Load Image Exif Parser
 * https://github.com/blueimp/JavaScript-Load-Image
 *
 * Copyright 2013, Sebastian Tschan
 * https://blueimp.net
 *
 * Licensed under the MIT license:
 * http://www.opensource.org/licenses/MIT
 */

/*global define, module, require, window, console */

;(function (factory) {
  'use strict'
  if (true) {
    // Register as an anonymous AMD module:
    !(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(5), __webpack_require__(24)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__))
  } else if (typeof module === 'object' && module.exports) {
    factory(require('./load-image'), require('./load-image-meta'))
  } else {
    // Browser globals:
    factory(window.loadImage)
  }
}(function (loadImage) {
  'use strict'

  loadImage.ExifMap = function () {
    return this
  }

  loadImage.ExifMap.prototype.map = {
    'Orientation': 0x0112
  }

  loadImage.ExifMap.prototype.get = function (id) {
    return this[id] || this[this.map[id]]
  }

  loadImage.getExifThumbnail = function (dataView, offset, length) {
    var hexData,
      i,
      b
    if (!length || offset + length > dataView.byteLength) {
      console.log('Invalid Exif data: Invalid thumbnail data.')
      return
    }
    hexData = []
    for (i = 0; i < length; i += 1) {
      b = dataView.getUint8(offset + i)
      hexData.push((b < 16 ? '0' : '') + b.toString(16))
    }
    return 'data:image/jpeg,%' + hexData.join('%')
  }

  loadImage.exifTagTypes = {
    // byte, 8-bit unsigned int:
    1: {
      getValue: function (dataView, dataOffset) {
        return dataView.getUint8(dataOffset)
      },
      size: 1
    },
    // ascii, 8-bit byte:
    2: {
      getValue: function (dataView, dataOffset) {
        return String.fromCharCode(dataView.getUint8(dataOffset))
      },
      size: 1,
      ascii: true
    },
    // short, 16 bit int:
    3: {
      getValue: function (dataView, dataOffset, littleEndian) {
        return dataView.getUint16(dataOffset, littleEndian)
      },
      size: 2
    },
    // long, 32 bit int:
    4: {
      getValue: function (dataView, dataOffset, littleEndian) {
        return dataView.getUint32(dataOffset, littleEndian)
      },
      size: 4
    },
    // rational = two long values, first is numerator, second is denominator:
    5: {
      getValue: function (dataView, dataOffset, littleEndian) {
        return dataView.getUint32(dataOffset, littleEndian) /
        dataView.getUint32(dataOffset + 4, littleEndian)
      },
      size: 8
    },
    // slong, 32 bit signed int:
    9: {
      getValue: function (dataView, dataOffset, littleEndian) {
        return dataView.getInt32(dataOffset, littleEndian)
      },
      size: 4
    },
    // srational, two slongs, first is numerator, second is denominator:
    10: {
      getValue: function (dataView, dataOffset, littleEndian) {
        return dataView.getInt32(dataOffset, littleEndian) /
        dataView.getInt32(dataOffset + 4, littleEndian)
      },
      size: 8
    }
  }
  // undefined, 8-bit byte, value depending on field:
  loadImage.exifTagTypes[7] = loadImage.exifTagTypes[1]

  loadImage.getExifValue = function (dataView, tiffOffset, offset, type, length, littleEndian) {
    var tagType = loadImage.exifTagTypes[type]
    var tagSize
    var dataOffset
    var values
    var i
    var str
    var c
    if (!tagType) {
      console.log('Invalid Exif data: Invalid tag type.')
      return
    }
    tagSize = tagType.size * length
    // Determine if the value is contained in the dataOffset bytes,
    // or if the value at the dataOffset is a pointer to the actual data:
    dataOffset = tagSize > 4
      ? tiffOffset + dataView.getUint32(offset + 8, littleEndian)
      : (offset + 8)
    if (dataOffset + tagSize > dataView.byteLength) {
      console.log('Invalid Exif data: Invalid data offset.')
      return
    }
    if (length === 1) {
      return tagType.getValue(dataView, dataOffset, littleEndian)
    }
    values = []
    for (i = 0; i < length; i += 1) {
      values[i] = tagType.getValue(dataView, dataOffset + i * tagType.size, littleEndian)
    }
    if (tagType.ascii) {
      str = ''
      // Concatenate the chars:
      for (i = 0; i < values.length; i += 1) {
        c = values[i]
        // Ignore the terminating NULL byte(s):
        if (c === '\u0000') {
          break
        }
        str += c
      }
      return str
    }
    return values
  }

  loadImage.parseExifTag = function (dataView, tiffOffset, offset, littleEndian, data) {
    var tag = dataView.getUint16(offset, littleEndian)
    data.exif[tag] = loadImage.getExifValue(
      dataView,
      tiffOffset,
      offset,
      dataView.getUint16(offset + 2, littleEndian), // tag type
      dataView.getUint32(offset + 4, littleEndian), // tag length
      littleEndian
    )
  }

  loadImage.parseExifTags = function (dataView, tiffOffset, dirOffset, littleEndian, data) {
    var tagsNumber,
      dirEndOffset,
      i
    if (dirOffset + 6 > dataView.byteLength) {
      console.log('Invalid Exif data: Invalid directory offset.')
      return
    }
    tagsNumber = dataView.getUint16(dirOffset, littleEndian)
    dirEndOffset = dirOffset + 2 + 12 * tagsNumber
    if (dirEndOffset + 4 > dataView.byteLength) {
      console.log('Invalid Exif data: Invalid directory size.')
      return
    }
    for (i = 0; i < tagsNumber; i += 1) {
      this.parseExifTag(
        dataView,
        tiffOffset,
        dirOffset + 2 + 12 * i, // tag offset
        littleEndian,
        data
      )
    }
    // Return the offset to the next directory:
    return dataView.getUint32(dirEndOffset, littleEndian)
  }

  loadImage.parseExifData = function (dataView, offset, length, data, options) {
    if (options.disableExif) {
      return
    }
    var tiffOffset = offset + 10
    var littleEndian
    var dirOffset
    var thumbnailData
    // Check for the ASCII code for "Exif" (0x45786966):
    if (dataView.getUint32(offset + 4) !== 0x45786966) {
      // No Exif data, might be XMP data instead
      return
    }
    if (tiffOffset + 8 > dataView.byteLength) {
      console.log('Invalid Exif data: Invalid segment size.')
      return
    }
    // Check for the two null bytes:
    if (dataView.getUint16(offset + 8) !== 0x0000) {
      console.log('Invalid Exif data: Missing byte alignment offset.')
      return
    }
    // Check the byte alignment:
    switch (dataView.getUint16(tiffOffset)) {
      case 0x4949:
        littleEndian = true
        break
      case 0x4D4D:
        littleEndian = false
        break
      default:
        console.log('Invalid Exif data: Invalid byte alignment marker.')
        return
    }
    // Check for the TIFF tag marker (0x002A):
    if (dataView.getUint16(tiffOffset + 2, littleEndian) !== 0x002A) {
      console.log('Invalid Exif data: Missing TIFF marker.')
      return
    }
    // Retrieve the directory offset bytes, usually 0x00000008 or 8 decimal:
    dirOffset = dataView.getUint32(tiffOffset + 4, littleEndian)
    // Create the exif object to store the tags:
    data.exif = new loadImage.ExifMap()
    // Parse the tags of the main image directory and retrieve the
    // offset to the next directory, usually the thumbnail directory:
    dirOffset = loadImage.parseExifTags(
      dataView,
      tiffOffset,
      tiffOffset + dirOffset,
      littleEndian,
      data
    )
    if (dirOffset && !options.disableExifThumbnail) {
      thumbnailData = {exif: {}}
      dirOffset = loadImage.parseExifTags(
        dataView,
        tiffOffset,
        tiffOffset + dirOffset,
        littleEndian,
        thumbnailData
      )
      // Check for JPEG Thumbnail offset:
      if (thumbnailData.exif[0x0201]) {
        data.exif.Thumbnail = loadImage.getExifThumbnail(
          dataView,
          tiffOffset + thumbnailData.exif[0x0201],
          thumbnailData.exif[0x0202] // Thumbnail data length
        )
      }
    }
    // Check for Exif Sub IFD Pointer:
    if (data.exif[0x8769] && !options.disableExifSub) {
      loadImage.parseExifTags(
        dataView,
        tiffOffset,
        tiffOffset + data.exif[0x8769], // directory offset
        littleEndian,
        data
      )
    }
    // Check for GPS Info IFD Pointer:
    if (data.exif[0x8825] && !options.disableExifGps) {
      loadImage.parseExifTags(
        dataView,
        tiffOffset,
        tiffOffset + data.exif[0x8825], // directory offset
        littleEndian,
        data
      )
    }
  }

  // Registers the Exif parser for the APP1 JPEG meta data segment:
  loadImage.metaDataParsers.jpeg[0xffe1].push(loadImage.parseExifData)

  // Adds the following properties to the parseMetaData callback data:
  // * exif: The exif tags, parsed by the parseExifData method

  // Adds the following options to the parseMetaData method:
  // * disableExif: Disables Exif parsing.
  // * disableExifThumbnail: Disables parsing of the Exif Thumbnail.
  // * disableExifSub: Disables parsing of the Exif Sub IFD.
  // * disableExifGps: Disables parsing of the Exif GPS Info IFD.
}))


/***/ }),
/* 221 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_RESULT__;/*
 * JavaScript Templates
 * https://github.com/blueimp/JavaScript-Templates
 *
 * Copyright 2011, Sebastian Tschan
 * https://blueimp.net
 *
 * Licensed under the MIT license:
 * http://www.opensource.org/licenses/MIT
 *
 * Inspired by John Resig's JavaScript Micro-Templating:
 * http://ejohn.org/blog/javascript-micro-templating/
 */

/*global document, define, module */

;(function ($) {
  'use strict'
  var tmpl = function (str, data) {
    var f = !/[^\w\-\.:]/.test(str)
      ? tmpl.cache[str] = tmpl.cache[str] || tmpl(tmpl.load(str))
      : new Function(// eslint-disable-line no-new-func
        tmpl.arg + ',tmpl',
        'var _e=tmpl.encode' + tmpl.helper + ",_s='" +
          str.replace(tmpl.regexp, tmpl.func) + "';return _s;"
      )
    return data ? f(data, tmpl) : function (data) {
      return f(data, tmpl)
    }
  }
  tmpl.cache = {}
  tmpl.load = function (id) {
    return document.getElementById(id).innerHTML
  }
  tmpl.regexp = /([\s'\\])(?!(?:[^{]|\{(?!%))*%\})|(?:\{%(=|#)([\s\S]+?)%\})|(\{%)|(%\})/g
  tmpl.func = function (s, p1, p2, p3, p4, p5) {
    if (p1) { // whitespace, quote and backspace in HTML context
      return {
        '\n': '\\n',
        '\r': '\\r',
        '\t': '\\t',
        ' ': ' '
      }[p1] || '\\' + p1
    }
    if (p2) { // interpolation: {%=prop%}, or unescaped: {%#prop%}
      if (p2 === '=') {
        return "'+_e(" + p3 + ")+'"
      }
      return "'+(" + p3 + "==null?'':" + p3 + ")+'"
    }
    if (p4) { // evaluation start tag: {%
      return "';"
    }
    if (p5) { // evaluation end tag: %}
      return "_s+='"
    }
  }
  tmpl.encReg = /[<>&"'\x00]/g
  tmpl.encMap = {
    '<': '&lt;',
    '>': '&gt;',
    '&': '&amp;',
    '"': '&quot;',
    "'": '&#39;'
  }
  tmpl.encode = function (s) {
    return (s == null ? '' : '' + s).replace(
      tmpl.encReg,
      function (c) {
        return tmpl.encMap[c] || ''
      }
    )
  }
  tmpl.arg = 'o'
  tmpl.helper = ",print=function(s,e){_s+=e?(s==null?'':s):_e(s);}" +
                  ',include=function(s,d){_s+=tmpl(s,d);}'
  if (true) {
    !(__WEBPACK_AMD_DEFINE_RESULT__ = function () {
      return tmpl
    }.call(exports, __webpack_require__, exports, module),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__))
  } else if (typeof module === 'object' && module.exports) {
    module.exports = tmpl
  } else {
    $.tmpl = tmpl
  }
}(this))


/***/ }),
/* 222 */
/***/ (function(module, exports, __webpack_require__) {

var Chart = __webpack_require__(241)();

__webpack_require__(240)(Chart);
__webpack_require__(239)(Chart);
__webpack_require__(236)(Chart);
__webpack_require__(237)(Chart);
__webpack_require__(238)(Chart);
__webpack_require__(242)(Chart);
__webpack_require__(243)(Chart);
__webpack_require__(244)(Chart);
__webpack_require__(245)(Chart);
__webpack_require__(246)(Chart);
__webpack_require__(247)(Chart);
__webpack_require__(248)(Chart);

__webpack_require__(230)(Chart);
__webpack_require__(231)(Chart);
__webpack_require__(232)(Chart);
__webpack_require__(233)(Chart);
__webpack_require__(234)(Chart);
__webpack_require__(235)(Chart);

__webpack_require__(253)(Chart);
__webpack_require__(254)(Chart);
__webpack_require__(255)(Chart);
__webpack_require__(256)(Chart);
__webpack_require__(257)(Chart);

__webpack_require__(249)(Chart);
__webpack_require__(250)(Chart);
__webpack_require__(251)(Chart);
__webpack_require__(252)(Chart);

__webpack_require__(223)(Chart);
__webpack_require__(224)(Chart);
__webpack_require__(225)(Chart);
__webpack_require__(226)(Chart);
__webpack_require__(227)(Chart);
__webpack_require__(228)(Chart);
__webpack_require__(229)(Chart);

window.Chart = module.exports = Chart;


/***/ }),
/* 223 */
/***/ (function(module, exports, __webpack_require__) {

"use strict";


module.exports = function(Chart) {

	Chart.Bar = function(context, config) {
		config.type = 'bar';

		return new Chart(context, config);
	};

};

/***/ }),
/* 224 */
/***/ (function(module, exports, __webpack_require__) {

"use strict";


module.exports = function(Chart) {

	Chart.Bubble = function(context, config) {
		config.type = 'bubble';
		return new Chart(context, config);
	};

};

/***/ }),
/* 225 */
/***/ (function(module, exports, __webpack_require__) {

"use strict";


module.exports = function(Chart) {

	Chart.Doughnut = function(context, config) {
		config.type = 'doughnut';

		return new Chart(context, config);
	};

};

/***/ }),
/* 226 */
/***/ (function(module, exports, __webpack_require__) {

"use strict";


module.exports = function(Chart) {

	Chart.Line = function(context, config) {
		config.type = 'line';

		return new Chart(context, config);
	};

};

/***/ }),
/* 227 */
/***/ (function(module, exports, __webpack_require__) {

"use strict";


module.exports = function(Chart) {

	Chart.PolarArea = function(context, config) {
		config.type = 'polarArea';

		return new Chart(context, config);
	};

};

/***/ }),
/* 228 */
/***/ (function(module, exports, __webpack_require__) {

"use strict";


module.exports = function(Chart) {

	var helpers = Chart.helpers;

	var defaultConfig = {
		aspectRatio: 1
	};

	Chart.Radar = function(context, config) {
		config.options = helpers.configMerge(defaultConfig, config.options);
		config.type = 'radar';

		return new Chart(context, config);
	};

};


/***/ }),
/* 229 */
/***/ (function(module, exports, __webpack_require__) {

"use strict";


module.exports = function(Chart) {

	var defaultConfig = {
		hover: {
			mode: 'single'
		},

		scales: {
			xAxes: [{
				type: "linear", // scatter should not use a category axis
				position: "bottom",
				id: "x-axis-1" // need an ID so datasets can reference the scale
			}],
			yAxes: [{
				type: "linear",
				position: "left",
				id: "y-axis-1"
			}]
		},

		tooltips: {
			callbacks: {
				title: function(tooltipItems, data) {
					// Title doesn't make sense for scatter since we format the data as a point
					return '';
				},
				label: function(tooltipItem, data) {
					return '(' + tooltipItem.xLabel + ', ' + tooltipItem.yLabel + ')';
				}
			}
		}
	};

	// Register the default config for this type
	Chart.defaults.scatter = defaultConfig;

	// Scatter charts use line controllers
	Chart.controllers.scatter = Chart.controllers.line;

	Chart.Scatter = function(context, config) {
		config.type = 'scatter';
		return new Chart(context, config);
	};

};

/***/ }),
/* 230 */
/***/ (function(module, exports, __webpack_require__) {

"use strict";


module.exports = function(Chart) {

	var helpers = Chart.helpers;

	Chart.defaults.bar = {
		hover: {
			mode: "label"
		},

		scales: {
			xAxes: [{
				type: "category",

				// Specific to Bar Controller
				categoryPercentage: 0.8,
				barPercentage: 0.9,

				// grid line settings
				gridLines: {
					offsetGridLines: true
				}
			}],
			yAxes: [{
				type: "linear"
			}]
		}
	};

	Chart.controllers.bar = Chart.DatasetController.extend({
		initialize: function(chart, datasetIndex) {
			Chart.DatasetController.prototype.initialize.call(this, chart, datasetIndex);

			// Use this to indicate that this is a bar dataset.
			this.getMeta().bar = true;
		},
		// Get the number of datasets that display bars. We use this to correctly calculate the bar width
		getBarCount: function getBarCount() {
			var barCount = 0;
			helpers.each(this.chart.data.datasets, function(dataset, datasetIndex) {
				var meta = this.chart.getDatasetMeta(datasetIndex);
				if (meta.bar && this.chart.isDatasetVisible(datasetIndex)) {
					++barCount;
				}
			}, this);
			return barCount;
		},

		addElements: function() {
			var meta = this.getMeta();
			helpers.each(this.getDataset().data, function(value, index) {
				meta.data[index] = meta.data[index] || new Chart.elements.Rectangle({
					_chart: this.chart.chart,
					_datasetIndex: this.index,
					_index: index
				});
			}, this);
		},

		addElementAndReset: function(index) {
			var rectangle = new Chart.elements.Rectangle({
				_chart: this.chart.chart,
				_datasetIndex: this.index,
				_index: index
			});

			var numBars = this.getBarCount();

			// Add to the points array and reset it
			this.getMeta().data.splice(index, 0, rectangle);
			this.updateElement(rectangle, index, true, numBars);
		},

		update: function update(reset) {
			var numBars = this.getBarCount();

			helpers.each(this.getMeta().data, function(rectangle, index) {
				this.updateElement(rectangle, index, reset, numBars);
			}, this);
		},

		updateElement: function updateElement(rectangle, index, reset, numBars) {
			var meta = this.getMeta();
			var xScale = this.getScaleForId(meta.xAxisID);
			var yScale = this.getScaleForId(meta.yAxisID);

			var yScalePoint;

			if (yScale.min < 0 && yScale.max < 0) {
				// all less than 0. use the top
				yScalePoint = yScale.getPixelForValue(yScale.max);
			} else if (yScale.min > 0 && yScale.max > 0) {
				yScalePoint = yScale.getPixelForValue(yScale.min);
			} else {
				yScalePoint = yScale.getPixelForValue(0);
			}

			helpers.extend(rectangle, {
				// Utility
				_chart: this.chart.chart,
				_xScale: xScale,
				_yScale: yScale,
				_datasetIndex: this.index,
				_index: index,


				// Desired view properties
				_model: {
					x: this.calculateBarX(index, this.index),
					y: reset ? yScalePoint : this.calculateBarY(index, this.index),

					// Tooltip
					label: this.chart.data.labels[index],
					datasetLabel: this.getDataset().label,

					// Appearance
					base: reset ? yScalePoint : this.calculateBarBase(this.index, index),
					width: this.calculateBarWidth(numBars),
					backgroundColor: rectangle.custom && rectangle.custom.backgroundColor ? rectangle.custom.backgroundColor : helpers.getValueAtIndexOrDefault(this.getDataset().backgroundColor, index, this.chart.options.elements.rectangle.backgroundColor),
					borderSkipped: rectangle.custom && rectangle.custom.borderSkipped ? rectangle.custom.borderSkipped : this.chart.options.elements.rectangle.borderSkipped,
					borderColor: rectangle.custom && rectangle.custom.borderColor ? rectangle.custom.borderColor : helpers.getValueAtIndexOrDefault(this.getDataset().borderColor, index, this.chart.options.elements.rectangle.borderColor),
					borderWidth: rectangle.custom && rectangle.custom.borderWidth ? rectangle.custom.borderWidth : helpers.getValueAtIndexOrDefault(this.getDataset().borderWidth, index, this.chart.options.elements.rectangle.borderWidth)
				}
			});
			rectangle.pivot();
		},

		calculateBarBase: function(datasetIndex, index) {
			var meta = this.getMeta();
			var xScale = this.getScaleForId(meta.xAxisID);
			var yScale = this.getScaleForId(meta.yAxisID);

			var base = 0;

			if (yScale.options.stacked) {

				var value = this.chart.data.datasets[datasetIndex].data[index];

				if (value < 0) {
					for (var i = 0; i < datasetIndex; i++) {
						var negDS = this.chart.data.datasets[i];
						var negDSMeta = this.chart.getDatasetMeta(i);
						if (negDSMeta.bar && negDSMeta.yAxisID === yScale.id && this.chart.isDatasetVisible(i)) {
							base += negDS.data[index] < 0 ? negDS.data[index] : 0;
						}
					}
				} else {
					for (var j = 0; j < datasetIndex; j++) {
						var posDS = this.chart.data.datasets[j];
						var posDSMeta = this.chart.getDatasetMeta(j);
						if (posDSMeta.bar && posDSMeta.yAxisID === yScale.id && this.chart.isDatasetVisible(j)) {
							base += posDS.data[index] > 0 ? posDS.data[index] : 0;
						}
					}
				}

				return yScale.getPixelForValue(base);
			}

			base = yScale.getPixelForValue(yScale.min);

			if (yScale.beginAtZero || ((yScale.min <= 0 && yScale.max >= 0) || (yScale.min >= 0 && yScale.max <= 0))) {
				base = yScale.getPixelForValue(0, 0);
				//base += yScale.options.gridLines.lineWidth;
			} else if (yScale.min < 0 && yScale.max < 0) {
				// All values are negative. Use the top as the base
				base = yScale.getPixelForValue(yScale.max);
			}

			return base;

		},

		getRuler: function() {
			var meta = this.getMeta();
			var xScale = this.getScaleForId(meta.xAxisID);
			var yScale = this.getScaleForId(meta.yAxisID);
			var datasetCount = this.getBarCount();

			var tickWidth = (function() {
				var min = xScale.getPixelForTick(1) - xScale.getPixelForTick(0);
				for (var i = 2; i < this.getDataset().data.length; i++) {
					min = Math.min(xScale.getPixelForTick(i) - xScale.getPixelForTick(i - 1), min);
				}
				return min;
			}).call(this);
			var categoryWidth = tickWidth * xScale.options.categoryPercentage;
			var categorySpacing = (tickWidth - (tickWidth * xScale.options.categoryPercentage)) / 2;
			var fullBarWidth = categoryWidth / datasetCount;

			if (xScale.ticks.length !== this.chart.data.labels.length) {
			    var perc = xScale.ticks.length / this.chart.data.labels.length;
			    fullBarWidth = fullBarWidth * perc;
			}

			var barWidth = fullBarWidth * xScale.options.barPercentage;
			var barSpacing = fullBarWidth - (fullBarWidth * xScale.options.barPercentage);

			return {
				datasetCount: datasetCount,
				tickWidth: tickWidth,
				categoryWidth: categoryWidth,
				categorySpacing: categorySpacing,
				fullBarWidth: fullBarWidth,
				barWidth: barWidth,
				barSpacing: barSpacing
			};
		},

		calculateBarWidth: function() {
			var xScale = this.getScaleForId(this.getMeta().xAxisID);
			var ruler = this.getRuler();
			return xScale.options.stacked ? ruler.categoryWidth : ruler.barWidth;
		},

		// Get bar index from the given dataset index accounting for the fact that not all bars are visible
		getBarIndex: function(datasetIndex) {
			var barIndex = 0;
			var meta, j;

			for (j = 0; j < datasetIndex; ++j) {
				meta = this.chart.getDatasetMeta(j);
				if (meta.bar && this.chart.isDatasetVisible(j)) {
					++barIndex;
				}
			}

			return barIndex;
		},

		calculateBarX: function(index, datasetIndex) {
			var meta = this.getMeta();
			var yScale = this.getScaleForId(meta.yAxisID);
			var xScale = this.getScaleForId(meta.xAxisID);
			var barIndex = this.getBarIndex(datasetIndex);

			var ruler = this.getRuler();
			var leftTick = xScale.getPixelForValue(null, index, datasetIndex, this.chart.isCombo);
			leftTick -= this.chart.isCombo ? (ruler.tickWidth / 2) : 0;

			if (xScale.options.stacked) {
				return leftTick + (ruler.categoryWidth / 2) + ruler.categorySpacing;
			}

			return leftTick +
				(ruler.barWidth / 2) +
				ruler.categorySpacing +
				(ruler.barWidth * barIndex) +
				(ruler.barSpacing / 2) +
				(ruler.barSpacing * barIndex);
		},

		calculateBarY: function(index, datasetIndex) {
			var meta = this.getMeta();
			var xScale = this.getScaleForId(meta.xAxisID);
			var yScale = this.getScaleForId(meta.yAxisID);

			var value = this.getDataset().data[index];

			if (yScale.options.stacked) {

				var sumPos = 0,
					sumNeg = 0;

				for (var i = 0; i < datasetIndex; i++) {
					var ds = this.chart.data.datasets[i];
					var dsMeta = this.chart.getDatasetMeta(i);
					if (dsMeta.bar && dsMeta.yAxisID === yScale.id && this.chart.isDatasetVisible(i)) {
						if (ds.data[index] < 0) {
							sumNeg += ds.data[index] || 0;
						} else {
							sumPos += ds.data[index] || 0;
						}
					}
				}

				if (value < 0) {
					return yScale.getPixelForValue(sumNeg + value);
				} else {
					return yScale.getPixelForValue(sumPos + value);
				}
			}

			return yScale.getPixelForValue(value);
		},

		draw: function(ease) {
			var easingDecimal = ease || 1;
			helpers.each(this.getMeta().data, function(rectangle, index) {
				var d = this.getDataset().data[index];
				if (d !== null && d !== undefined && !isNaN(d)) {
					rectangle.transition(easingDecimal).draw();
				}
			}, this);
		},

		setHoverStyle: function(rectangle) {
			var dataset = this.chart.data.datasets[rectangle._datasetIndex];
			var index = rectangle._index;

			rectangle._model.backgroundColor = rectangle.custom && rectangle.custom.hoverBackgroundColor ? rectangle.custom.hoverBackgroundColor : helpers.getValueAtIndexOrDefault(dataset.hoverBackgroundColor, index, helpers.color(rectangle._model.backgroundColor).saturate(0.5).darken(0.1).rgbString());
			rectangle._model.borderColor = rectangle.custom && rectangle.custom.hoverBorderColor ? rectangle.custom.hoverBorderColor : helpers.getValueAtIndexOrDefault(dataset.hoverBorderColor, index, helpers.color(rectangle._model.borderColor).saturate(0.5).darken(0.1).rgbString());
			rectangle._model.borderWidth = rectangle.custom && rectangle.custom.hoverBorderWidth ? rectangle.custom.hoverBorderWidth : helpers.getValueAtIndexOrDefault(dataset.hoverBorderWidth, index, rectangle._model.borderWidth);
		},

		removeHoverStyle: function(rectangle) {
			var dataset = this.chart.data.datasets[rectangle._datasetIndex];
			var index = rectangle._index;

			rectangle._model.backgroundColor = rectangle.custom && rectangle.custom.backgroundColor ? rectangle.custom.backgroundColor : helpers.getValueAtIndexOrDefault(this.getDataset().backgroundColor, index, this.chart.options.elements.rectangle.backgroundColor);
			rectangle._model.borderColor = rectangle.custom && rectangle.custom.borderColor ? rectangle.custom.borderColor : helpers.getValueAtIndexOrDefault(this.getDataset().borderColor, index, this.chart.options.elements.rectangle.borderColor);
			rectangle._model.borderWidth = rectangle.custom && rectangle.custom.borderWidth ? rectangle.custom.borderWidth : helpers.getValueAtIndexOrDefault(this.getDataset().borderWidth, index, this.chart.options.elements.rectangle.borderWidth);
		}

	});


	// including horizontalBar in the bar file, instead of a file of its own
	// it extends bar (like pie extends doughnut)
	Chart.defaults.horizontalBar = {
		hover: {
			mode: "label"
		},

		scales: {
			xAxes: [{
				type: "linear",
				position: "bottom"
			}],
			yAxes: [{
				position: "left",
				type: "category",

				// Specific to Horizontal Bar Controller
				categoryPercentage: 0.8,
				barPercentage: 0.9,

				// grid line settings
				gridLines: {
					offsetGridLines: true
				}
			}]
		},
	};

	Chart.controllers.horizontalBar = Chart.controllers.bar.extend({
		updateElement: function updateElement(rectangle, index, reset, numBars) {
			var meta = this.getMeta();
			var xScale = this.getScaleForId(meta.xAxisID);
			var yScale = this.getScaleForId(meta.yAxisID);

			var xScalePoint;

			if (xScale.min < 0 && xScale.max < 0) {
				// all less than 0. use the right
				xScalePoint = xScale.getPixelForValue(xScale.max);
			} else if (xScale.min > 0 && xScale.max > 0) {
				xScalePoint = xScale.getPixelForValue(xScale.min);
			} else {
				xScalePoint = xScale.getPixelForValue(0);
			}

			helpers.extend(rectangle, {
				// Utility
				_chart: this.chart.chart,
				_xScale: xScale,
				_yScale: yScale,
				_datasetIndex: this.index,
				_index: index,

				// Desired view properties
				_model: {
					x: reset ? xScalePoint : this.calculateBarX(index, this.index),
					y: this.calculateBarY(index, this.index),

					// Tooltip
					label: this.chart.data.labels[index],
					datasetLabel: this.getDataset().label,

					// Appearance
					base: reset ? xScalePoint : this.calculateBarBase(this.index, index),
					height: this.calculateBarHeight(numBars),
					backgroundColor: rectangle.custom && rectangle.custom.backgroundColor ? rectangle.custom.backgroundColor : helpers.getValueAtIndexOrDefault(this.getDataset().backgroundColor, index, this.chart.options.elements.rectangle.backgroundColor),
					borderSkipped: rectangle.custom && rectangle.custom.borderSkipped ? rectangle.custom.borderSkipped : this.chart.options.elements.rectangle.borderSkipped,
					borderColor: rectangle.custom && rectangle.custom.borderColor ? rectangle.custom.borderColor : helpers.getValueAtIndexOrDefault(this.getDataset().borderColor, index, this.chart.options.elements.rectangle.borderColor),
					borderWidth: rectangle.custom && rectangle.custom.borderWidth ? rectangle.custom.borderWidth : helpers.getValueAtIndexOrDefault(this.getDataset().borderWidth, index, this.chart.options.elements.rectangle.borderWidth)
				},

				draw: function () {

					var ctx = this._chart.ctx;
					var vm = this._view;

					var halfHeight = vm.height / 2,
						topY = vm.y - halfHeight,
						bottomY = vm.y + halfHeight,
						right = vm.base - (vm.base - vm.x),
						halfStroke = vm.borderWidth / 2;

					// Canvas doesn't allow us to stroke inside the width so we can
					// adjust the sizes to fit if we're setting a stroke on the line
					if (vm.borderWidth) {
						topY += halfStroke;
						bottomY -= halfStroke;
						right += halfStroke;
					}

					ctx.beginPath();

					ctx.fillStyle = vm.backgroundColor;
					ctx.strokeStyle = vm.borderColor;
					ctx.lineWidth = vm.borderWidth;

					// Corner points, from bottom-left to bottom-right clockwise
					// | 1 2 |
					// | 0 3 |
					var corners = [
						[vm.base, bottomY],
						[vm.base, topY],
						[right, topY],
						[right, bottomY]
					];

					// Find first (starting) corner with fallback to 'bottom'
					var borders = ['bottom', 'left', 'top', 'right'];
					var startCorner = borders.indexOf(vm.borderSkipped, 0);
					if (startCorner === -1)
						startCorner = 0;

					function cornerAt(index) {
						return corners[(startCorner + index) % 4];
					}

					// Draw rectangle from 'startCorner'
					ctx.moveTo.apply(ctx, cornerAt(0));
					for (var i = 1; i < 4; i++)
						ctx.lineTo.apply(ctx, cornerAt(i));

					ctx.fill();
					if (vm.borderWidth) {
						ctx.stroke();
					}
				},

				inRange: function (mouseX, mouseY) {
					var vm = this._view;
					var inRange = false;

					if (vm) {
						if (vm.x < vm.base) {
							inRange = (mouseY >= vm.y - vm.height / 2 && mouseY <= vm.y + vm.height / 2) && (mouseX >= vm.x && mouseX <= vm.base);
						} else {
							inRange = (mouseY >= vm.y - vm.height / 2 && mouseY <= vm.y + vm.height / 2) && (mouseX >= vm.base && mouseX <= vm.x);
						}
					}

					return inRange;
				}
			});

			rectangle.pivot();
		},

		calculateBarBase: function (datasetIndex, index) {
			var meta = this.getMeta();
			var xScale = this.getScaleForId(meta.xAxisID);
			var yScale = this.getScaleForId(meta.yAxisID);

			var base = 0;

			if (xScale.options.stacked) {

				var value = this.chart.data.datasets[datasetIndex].data[index];

				if (value < 0) {
					for (var i = 0; i < datasetIndex; i++) {
						var negDS = this.chart.data.datasets[i];
						var negDSMeta = this.chart.getDatasetMeta(i);
						if (negDSMeta.bar && negDSMeta.xAxisID === xScale.id && this.chart.isDatasetVisible(i)) {
							base += negDS.data[index] < 0 ? negDS.data[index] : 0;
						}
					}
				} else {
					for (var j = 0; j < datasetIndex; j++) {
						var posDS = this.chart.data.datasets[j];
						var posDSMeta = this.chart.getDatasetMeta(j);
						if (posDSMeta.bar && posDSMeta.xAxisID === xScale.id && this.chart.isDatasetVisible(j)) {
							base += posDS.data[index] > 0 ? posDS.data[index] : 0;
						}
					}
				}

				return xScale.getPixelForValue(base);
			}

			base = xScale.getPixelForValue(xScale.min);

			if (xScale.beginAtZero || ((xScale.min <= 0 && xScale.max >= 0) || (xScale.min >= 0 && xScale.max <= 0))) {
				base = xScale.getPixelForValue(0, 0);
			} else if (xScale.min < 0 && xScale.max < 0) {
				// All values are negative. Use the right as the base
				base = xScale.getPixelForValue(xScale.max);
			}

			return base;
		},

		getRuler: function () {
			var meta = this.getMeta();
			var xScale = this.getScaleForId(meta.xAxisID);
			var yScale = this.getScaleForId(meta.yAxisID);
			var datasetCount = this.getBarCount();

			var tickHeight = (function () {
				var min = yScale.getPixelForTick(1) - yScale.getPixelForTick(0);
				for (var i = 2; i < this.getDataset().data.length; i++) {
					min = Math.min(yScale.getPixelForTick(i) - yScale.getPixelForTick(i - 1), min);
				}
				return min;
			}).call(this);
			var categoryHeight = tickHeight * yScale.options.categoryPercentage;
			var categorySpacing = (tickHeight - (tickHeight * yScale.options.categoryPercentage)) / 2;
			var fullBarHeight = categoryHeight / datasetCount;

			if (yScale.ticks.length !== this.chart.data.labels.length) {
				var perc = yScale.ticks.length / this.chart.data.labels.length;
				fullBarHeight = fullBarHeight * perc;
			}

			var barHeight = fullBarHeight * yScale.options.barPercentage;
			var barSpacing = fullBarHeight - (fullBarHeight * yScale.options.barPercentage);

			return {
				datasetCount: datasetCount,
				tickHeight: tickHeight,
				categoryHeight: categoryHeight,
				categorySpacing: categorySpacing,
				fullBarHeight: fullBarHeight,
				barHeight: barHeight,
				barSpacing: barSpacing,
			};
		},

		calculateBarHeight: function () {
			var yScale = this.getScaleForId(this.getMeta().yAxisID);
			var ruler = this.getRuler();
			return yScale.options.stacked ? ruler.categoryHeight : ruler.barHeight;
		},

		calculateBarX: function (index, datasetIndex) {
			var meta = this.getMeta();
			var xScale = this.getScaleForId(meta.xAxisID);
			var yScale = this.getScaleForId(meta.yAxisID);

			var value = this.getDataset().data[index];

			if (xScale.options.stacked) {

				var sumPos = 0,
					sumNeg = 0;

				for (var i = 0; i < datasetIndex; i++) {
					var ds = this.chart.data.datasets[i];
					var dsMeta = this.chart.getDatasetMeta(i);
					if (dsMeta.bar && dsMeta.xAxisID === xScale.id && this.chart.isDatasetVisible(i)) {
						if (ds.data[index] < 0) {
							sumNeg += ds.data[index] || 0;
						} else {
							sumPos += ds.data[index] || 0;
						}
					}
				}

				if (value < 0) {
					return xScale.getPixelForValue(sumNeg + value);
				} else {
					return xScale.getPixelForValue(sumPos + value);
				}
			}

			return xScale.getPixelForValue(value);
		},

		calculateBarY: function (index, datasetIndex) {
			var meta = this.getMeta();
			var yScale = this.getScaleForId(meta.yAxisID);
			var xScale = this.getScaleForId(meta.xAxisID);
			var barIndex = this.getBarIndex(datasetIndex);

			var ruler = this.getRuler();
			var topTick = yScale.getPixelForValue(null, index, datasetIndex, this.chart.isCombo);
			topTick -= this.chart.isCombo ? (ruler.tickHeight / 2) : 0;

			if (yScale.options.stacked) {
				return topTick + (ruler.categoryHeight / 2) + ruler.categorySpacing;
			}

			return topTick +
				(ruler.barHeight / 2) +
				ruler.categorySpacing +
				(ruler.barHeight * barIndex) +
				(ruler.barSpacing / 2) +
				(ruler.barSpacing * barIndex);
		}
	});
};


/***/ }),
/* 231 */
/***/ (function(module, exports, __webpack_require__) {

"use strict";


module.exports = function(Chart) {

	var helpers = Chart.helpers;

	Chart.defaults.bubble = {
		hover: {
			mode: "single"
		},

		scales: {
			xAxes: [{
				type: "linear", // bubble should probably use a linear scale by default
				position: "bottom",
				id: "x-axis-0" // need an ID so datasets can reference the scale
			}],
			yAxes: [{
				type: "linear",
				position: "left",
				id: "y-axis-0"
			}]
		},

		tooltips: {
			callbacks: {
				title: function(tooltipItems, data) {
					// Title doesn't make sense for scatter since we format the data as a point
					return '';
				},
				label: function(tooltipItem, data) {
					var datasetLabel = data.datasets[tooltipItem.datasetIndex].label || '';
					var dataPoint = data.datasets[tooltipItem.datasetIndex].data[tooltipItem.index];
					return datasetLabel + ': (' + dataPoint.x + ', ' + dataPoint.y + ', ' + dataPoint.r + ')';
				}
			}
		}
	};


	Chart.controllers.bubble = Chart.DatasetController.extend({
		addElements: function() {
			var meta = this.getMeta();
			helpers.each(this.getDataset().data, function(value, index) {
				meta.data[index] = meta.data[index] || new Chart.elements.Point({
					_chart: this.chart.chart,
					_datasetIndex: this.index,
					_index: index
				});
			}, this);
		},
		addElementAndReset: function(index) {
			var point = new Chart.elements.Point({
				_chart: this.chart.chart,
				_datasetIndex: this.index,
				_index: index
			});

			// Add to the points array and reset it
			this.getMeta().data.splice(index, 0, point);
			this.updateElement(point, index, true);
		},

		update: function update(reset) {
			var meta = this.getMeta();
			var points = meta.data;
			var yScale = this.getScaleForId(meta.yAxisID);
			var xScale = this.getScaleForId(meta.xAxisID);
			var scaleBase;

			if (yScale.min < 0 && yScale.max < 0) {
				scaleBase = yScale.getPixelForValue(yScale.max);
			} else if (yScale.min > 0 && yScale.max > 0) {
				scaleBase = yScale.getPixelForValue(yScale.min);
			} else {
				scaleBase = yScale.getPixelForValue(0);
			}

			// Update Points
			helpers.each(points, function(point, index) {
				this.updateElement(point, index, reset);
			}, this);

		},

		updateElement: function(point, index, reset) {
			var meta = this.getMeta();
			var yScale = this.getScaleForId(meta.yAxisID);
			var xScale = this.getScaleForId(meta.xAxisID);
			var scaleBase;

			if (yScale.min < 0 && yScale.max < 0) {
				scaleBase = yScale.getPixelForValue(yScale.max);
			} else if (yScale.min > 0 && yScale.max > 0) {
				scaleBase = yScale.getPixelForValue(yScale.min);
			} else {
				scaleBase = yScale.getPixelForValue(0);
			}

			helpers.extend(point, {
				// Utility
				_chart: this.chart.chart,
				_xScale: xScale,
				_yScale: yScale,
				_datasetIndex: this.index,
				_index: index,

				// Desired view properties
				_model: {
					x: reset ? xScale.getPixelForDecimal(0.5) : xScale.getPixelForValue(this.getDataset().data[index], index, this.index, this.chart.isCombo),
					y: reset ? scaleBase : yScale.getPixelForValue(this.getDataset().data[index], index, this.index),
					// Appearance
					radius: reset ? 0 : point.custom && point.custom.radius ? point.custom.radius : this.getRadius(this.getDataset().data[index]),
					backgroundColor: point.custom && point.custom.backgroundColor ? point.custom.backgroundColor : helpers.getValueAtIndexOrDefault(this.getDataset().backgroundColor, index, this.chart.options.elements.point.backgroundColor),
					borderColor: point.custom && point.custom.borderColor ? point.custom.borderColor : helpers.getValueAtIndexOrDefault(this.getDataset().borderColor, index, this.chart.options.elements.point.borderColor),
					borderWidth: point.custom && point.custom.borderWidth ? point.custom.borderWidth : helpers.getValueAtIndexOrDefault(this.getDataset().borderWidth, index, this.chart.options.elements.point.borderWidth),

					// Tooltip
					hitRadius: point.custom && point.custom.hitRadius ? point.custom.hitRadius : helpers.getValueAtIndexOrDefault(this.getDataset().hitRadius, index, this.chart.options.elements.point.hitRadius)
				}
			});

			point._model.skip = point.custom && point.custom.skip ? point.custom.skip : (isNaN(point._model.x) || isNaN(point._model.y));

			point.pivot();
		},

		getRadius: function(value) {
			return value.r || this.chart.options.elements.point.radius;
		},

		draw: function(ease) {
			var easingDecimal = ease || 1;

			// Transition and Draw the Points
			helpers.each(this.getMeta().data, function(point, index) {
				point.transition(easingDecimal);
				point.draw();
			});

		},

		setHoverStyle: function(point) {
			// Point
			var dataset = this.chart.data.datasets[point._datasetIndex];
			var index = point._index;

			point._model.radius = point.custom && point.custom.hoverRadius ? point.custom.hoverRadius : (helpers.getValueAtIndexOrDefault(dataset.hoverRadius, index, this.chart.options.elements.point.hoverRadius)) + this.getRadius(this.getDataset().data[point._index]);
			point._model.backgroundColor = point.custom && point.custom.hoverBackgroundColor ? point.custom.hoverBackgroundColor : helpers.getValueAtIndexOrDefault(dataset.hoverBackgroundColor, index, helpers.color(point._model.backgroundColor).saturate(0.5).darken(0.1).rgbString());
			point._model.borderColor = point.custom && point.custom.hoverBorderColor ? point.custom.hoverBorderColor : helpers.getValueAtIndexOrDefault(dataset.hoverBorderColor, index, helpers.color(point._model.borderColor).saturate(0.5).darken(0.1).rgbString());
			point._model.borderWidth = point.custom && point.custom.hoverBorderWidth ? point.custom.hoverBorderWidth : helpers.getValueAtIndexOrDefault(dataset.hoverBorderWidth, index, point._model.borderWidth);
		},

		removeHoverStyle: function(point) {
			var dataset = this.chart.data.datasets[point._datasetIndex];
			var index = point._index;

			point._model.radius = point.custom && point.custom.radius ? point.custom.radius : this.getRadius(this.getDataset().data[point._index]);
			point._model.backgroundColor = point.custom && point.custom.backgroundColor ? point.custom.backgroundColor : helpers.getValueAtIndexOrDefault(this.getDataset().backgroundColor, index, this.chart.options.elements.point.backgroundColor);
			point._model.borderColor = point.custom && point.custom.borderColor ? point.custom.borderColor : helpers.getValueAtIndexOrDefault(this.getDataset().borderColor, index, this.chart.options.elements.point.borderColor);
			point._model.borderWidth = point.custom && point.custom.borderWidth ? point.custom.borderWidth : helpers.getValueAtIndexOrDefault(this.getDataset().borderWidth, index, this.chart.options.elements.point.borderWidth);
		}
	});
};

/***/ }),
/* 232 */
/***/ (function(module, exports, __webpack_require__) {

"use strict";


module.exports = function(Chart) {

	var helpers = Chart.helpers;

	Chart.defaults.doughnut = {
		animation: {
			//Boolean - Whether we animate the rotation of the Doughnut
			animateRotate: true,
			//Boolean - Whether we animate scaling the Doughnut from the centre
			animateScale: false
		},
		aspectRatio: 1,
		hover: {
			mode: 'single'
		},
		legendCallback: function(chart) {
			var text = [];
			text.push('<ul class="' + chart.id + '-legend">');

			if (chart.data.datasets.length) {
				for (var i = 0; i < chart.data.datasets[0].data.length; ++i) {
					text.push('<li><span style="background-color:' + chart.data.datasets[0].backgroundColor[i] + '"></span>');
					if (chart.data.labels[i]) {
						text.push(chart.data.labels[i]);
					}
					text.push('</li>');
				}
			}

			text.push('</ul>');
			return text.join("");
		},
		legend: {
			labels: {
				generateLabels: function(chart) {
					var data = chart.data;
					if (data.labels.length && data.datasets.length) {
						return data.labels.map(function(label, i) {
							var meta = chart.getDatasetMeta(0);
							var ds = data.datasets[0];
							var arc = meta.data[i];
							var fill = arc.custom && arc.custom.backgroundColor ? arc.custom.backgroundColor : helpers.getValueAtIndexOrDefault(ds.backgroundColor, i, this.chart.options.elements.arc.backgroundColor);
							var stroke = arc.custom && arc.custom.borderColor ? arc.custom.borderColor : helpers.getValueAtIndexOrDefault(ds.borderColor, i, this.chart.options.elements.arc.borderColor);
							var bw = arc.custom && arc.custom.borderWidth ? arc.custom.borderWidth : helpers.getValueAtIndexOrDefault(ds.borderWidth, i, this.chart.options.elements.arc.borderWidth);

							return {
								text: label,
								fillStyle: fill,
								strokeStyle: stroke,
								lineWidth: bw,
								hidden: isNaN(ds.data[i]) || meta.data[i].hidden,

								// Extra data used for toggling the correct item
								index: i
							};
						}, this);
					} else {
						return [];
					}
				}
			},

			onClick: function(e, legendItem) {
				var index = legendItem.index;
				var chart = this.chart;
				var i, ilen, meta;

				for (i = 0, ilen = (chart.data.datasets || []).length; i < ilen; ++i) {
					meta = chart.getDatasetMeta(i);
					meta.data[index].hidden = !meta.data[index].hidden;
				}

				chart.update();
			}
		},

		//The percentage of the chart that we cut out of the middle.
		cutoutPercentage: 50,

		//The rotation of the chart, where the first data arc begins.
		rotation: Math.PI * -0.5,

		//The total circumference of the chart.
		circumference: Math.PI * 2.0,

		// Need to override these to give a nice default
		tooltips: {
			callbacks: {
				title: function() {
					return '';
				},
				label: function(tooltipItem, data) {
					return data.labels[tooltipItem.index] + ': ' + data.datasets[tooltipItem.datasetIndex].data[tooltipItem.index];
				}
			}
		}
	};

	Chart.defaults.pie = helpers.clone(Chart.defaults.doughnut);
	helpers.extend(Chart.defaults.pie, {
		cutoutPercentage: 0
	});


	Chart.controllers.doughnut = Chart.controllers.pie = Chart.DatasetController.extend({
		linkScales: function() {
			// no scales for doughnut
		},

		addElements: function() {
			var meta = this.getMeta();
			helpers.each(this.getDataset().data, function(value, index) {
				meta.data[index] = meta.data[index] || new Chart.elements.Arc({
					_chart: this.chart.chart,
					_datasetIndex: this.index,
					_index: index
				});
			}, this);
		},

		addElementAndReset: function(index, colorForNewElement) {
			var arc = new Chart.elements.Arc({
				_chart: this.chart.chart,
				_datasetIndex: this.index,
				_index: index
			});

			if (colorForNewElement && helpers.isArray(this.getDataset().backgroundColor)) {
				this.getDataset().backgroundColor.splice(index, 0, colorForNewElement);
			}

			// Add to the points array and reset it
			this.getMeta().data.splice(index, 0, arc);
			this.updateElement(arc, index, true);
		},

		// Get index of the dataset in relation to the visible datasets. This allows determining the inner and outer radius correctly
		getRingIndex: function getRingIndex(datasetIndex) {
			var ringIndex = 0;

			for (var j = 0; j < datasetIndex; ++j) {
				if (this.chart.isDatasetVisible(j)) {
					++ringIndex;
				}
			}

			return ringIndex;
		},

		update: function update(reset) {
			var availableWidth = this.chart.chartArea.right - this.chart.chartArea.left - this.chart.options.elements.arc.borderWidth;
			var availableHeight = this.chart.chartArea.bottom - this.chart.chartArea.top - this.chart.options.elements.arc.borderWidth;
			var minSize = Math.min(availableWidth, availableHeight);
			var offset = {x: 0, y: 0};

			// If the chart's circumference isn't a full circle, calculate minSize as a ratio of the width/height of the arc
			if (this.chart.options.circumference < Math.PI * 2.0) {
				var startAngle = this.chart.options.rotation % (Math.PI * 2.0);
				startAngle += Math.PI * 2.0 * (startAngle >= Math.PI ? -1 : startAngle < -Math.PI ? 1 : 0);
				var endAngle = startAngle + this.chart.options.circumference;
				var start = {x: Math.cos(startAngle), y: Math.sin(startAngle)};
				var end = {x: Math.cos(endAngle), y: Math.sin(endAngle)};
				var contains0 = (startAngle <= 0 && 0 <= endAngle) || (startAngle <= Math.PI * 2.0 && Math.PI * 2.0 <= endAngle);
				var contains90 = (startAngle <= Math.PI * 0.5 && Math.PI * 0.5 <= endAngle) || (startAngle <= Math.PI * 2.5 && Math.PI * 2.5 <= endAngle);
				var contains180 = (startAngle <= -Math.PI && -Math.PI <= endAngle) || (startAngle <= Math.PI && Math.PI <= endAngle);
				var contains270 = (startAngle <= -Math.PI * 0.5 && -Math.PI * 0.5 <= endAngle) || (startAngle <= Math.PI * 1.5 && Math.PI * 1.5 <= endAngle);
				var cutout = this.chart.options.cutoutPercentage / 100.0;
				var min = {x: contains180 ? -1 : Math.min(start.x * (start.x < 0 ? 1 : cutout), end.x * (end.x < 0 ? 1 : cutout)), y: contains270 ? -1 : Math.min(start.y * (start.y < 0 ? 1 : cutout), end.y * (end.y < 0 ? 1 : cutout))};
				var max = {x: contains0 ? 1 : Math.max(start.x * (start.x > 0 ? 1 : cutout), end.x * (end.x > 0 ? 1 : cutout)), y: contains90 ? 1 : Math.max(start.y * (start.y > 0 ? 1 : cutout), end.y * (end.y > 0 ? 1 : cutout))};
				var size = {width: (max.x - min.x) * 0.5, height: (max.y - min.y) * 0.5};
				minSize = Math.min(availableWidth / size.width, availableHeight / size.height);
				offset = {x: (max.x + min.x) * -0.5, y: (max.y + min.y) * -0.5};
			}

			this.chart.outerRadius = Math.max(minSize / 2, 0);
			this.chart.innerRadius = Math.max(this.chart.options.cutoutPercentage ? (this.chart.outerRadius / 100) * (this.chart.options.cutoutPercentage) : 1, 0);
			this.chart.radiusLength = (this.chart.outerRadius - this.chart.innerRadius) / this.chart.getVisibleDatasetCount();
			this.chart.offsetX = offset.x * this.chart.outerRadius;
			this.chart.offsetY = offset.y * this.chart.outerRadius;

			this.getMeta().total = this.calculateTotal();

			this.outerRadius = this.chart.outerRadius - (this.chart.radiusLength * this.getRingIndex(this.index));
			this.innerRadius = this.outerRadius - this.chart.radiusLength;

			helpers.each(this.getMeta().data, function(arc, index) {
				this.updateElement(arc, index, reset);
			}, this);
		},

		updateElement: function(arc, index, reset) {
			var centerX = (this.chart.chartArea.left + this.chart.chartArea.right) / 2;
			var centerY = (this.chart.chartArea.top + this.chart.chartArea.bottom) / 2;
			var startAngle = this.chart.options.rotation; // non reset case handled later
			var endAngle = this.chart.options.rotation; // non reset case handled later
			var circumference = reset && this.chart.options.animation.animateRotate ? 0 : arc.hidden? 0 : this.calculateCircumference(this.getDataset().data[index]) * (this.chart.options.circumference / (2.0 * Math.PI));
			var innerRadius = reset && this.chart.options.animation.animateScale ? 0 : this.innerRadius;
			var outerRadius = reset && this.chart.options.animation.animateScale ? 0 : this.outerRadius;

			helpers.extend(arc, {
				// Utility
				_chart: this.chart.chart,
				_datasetIndex: this.index,
				_index: index,

				// Desired view properties
				_model: {
					x: centerX + this.chart.offsetX,
					y: centerY + this.chart.offsetY,
					startAngle: startAngle,
					endAngle: endAngle,
					circumference: circumference,
					outerRadius: outerRadius,
					innerRadius: innerRadius,

					backgroundColor: arc.custom && arc.custom.backgroundColor ? arc.custom.backgroundColor : helpers.getValueAtIndexOrDefault(this.getDataset().backgroundColor, index, this.chart.options.elements.arc.backgroundColor),
					hoverBackgroundColor: arc.custom && arc.custom.hoverBackgroundColor ? arc.custom.hoverBackgroundColor : helpers.getValueAtIndexOrDefault(this.getDataset().hoverBackgroundColor, index, this.chart.options.elements.arc.hoverBackgroundColor),
					borderWidth: arc.custom && arc.custom.borderWidth ? arc.custom.borderWidth : helpers.getValueAtIndexOrDefault(this.getDataset().borderWidth, index, this.chart.options.elements.arc.borderWidth),
					borderColor: arc.custom && arc.custom.borderColor ? arc.custom.borderColor : helpers.getValueAtIndexOrDefault(this.getDataset().borderColor, index, this.chart.options.elements.arc.borderColor),

					label: helpers.getValueAtIndexOrDefault(this.getDataset().label, index, this.chart.data.labels[index])
				}
			});

			// Set correct angles if not resetting
			if (!reset || !this.chart.options.animation.animateRotate) {

				if (index === 0) {
					arc._model.startAngle = this.chart.options.rotation;
				} else {
					arc._model.startAngle = this.getMeta().data[index - 1]._model.endAngle;
				}

				arc._model.endAngle = arc._model.startAngle + arc._model.circumference;
			}

			arc.pivot();
		},

		draw: function(ease) {
			var easingDecimal = ease || 1;
			helpers.each(this.getMeta().data, function(arc, index) {
				arc.transition(easingDecimal).draw();
			});
		},

		setHoverStyle: function(arc) {
			var dataset = this.chart.data.datasets[arc._datasetIndex];
			var index = arc._index;

			arc._model.backgroundColor = arc.custom && arc.custom.hoverBackgroundColor ? arc.custom.hoverBackgroundColor : helpers.getValueAtIndexOrDefault(dataset.hoverBackgroundColor, index, helpers.color(arc._model.backgroundColor).saturate(0.5).darken(0.1).rgbString());
			arc._model.borderColor = arc.custom && arc.custom.hoverBorderColor ? arc.custom.hoverBorderColor : helpers.getValueAtIndexOrDefault(dataset.hoverBorderColor, index, helpers.color(arc._model.borderColor).saturate(0.5).darken(0.1).rgbString());
			arc._model.borderWidth = arc.custom && arc.custom.hoverBorderWidth ? arc.custom.hoverBorderWidth : helpers.getValueAtIndexOrDefault(dataset.hoverBorderWidth, index, arc._model.borderWidth);
		},

		removeHoverStyle: function(arc) {
			var dataset = this.chart.data.datasets[arc._datasetIndex];
			var index = arc._index;

			arc._model.backgroundColor = arc.custom && arc.custom.backgroundColor ? arc.custom.backgroundColor : helpers.getValueAtIndexOrDefault(this.getDataset().backgroundColor, index, this.chart.options.elements.arc.backgroundColor);
			arc._model.borderColor = arc.custom && arc.custom.borderColor ? arc.custom.borderColor : helpers.getValueAtIndexOrDefault(this.getDataset().borderColor, index, this.chart.options.elements.arc.borderColor);
			arc._model.borderWidth = arc.custom && arc.custom.borderWidth ? arc.custom.borderWidth : helpers.getValueAtIndexOrDefault(this.getDataset().borderWidth, index, this.chart.options.elements.arc.borderWidth);
		},

		calculateTotal: function() {
			var dataset = this.getDataset();
			var meta = this.getMeta();
			var total = 0;
			var value;

			helpers.each(meta.data, function(element, index) {
				value = dataset.data[index];
				if (!isNaN(value) && !element.hidden) {
					total += Math.abs(value);
				}
			});

			return total;
		},

		calculateCircumference: function(value) {
			var total = this.getMeta().total;
			if (total > 0 && !isNaN(value)) {
				return (Math.PI * 2.0) * (value / total);
			} else {
				return 0;
			}
		}
	});
};


/***/ }),
/* 233 */
/***/ (function(module, exports, __webpack_require__) {

"use strict";


module.exports = function(Chart) {

	var helpers = Chart.helpers;

	Chart.defaults.line = {
		showLines: true,

		hover: {
			mode: "label"
		},

		scales: {
			xAxes: [{
				type: "category",
				id: 'x-axis-0'
			}],
			yAxes: [{
				type: "linear",
				id: 'y-axis-0'
			}]
		}
	};


	Chart.controllers.line = Chart.DatasetController.extend({
		addElements: function() {
			var meta = this.getMeta();
			meta.dataset = meta.dataset || new Chart.elements.Line({
				_chart: this.chart.chart,
				_datasetIndex: this.index,
				_points: meta.data
			});

			helpers.each(this.getDataset().data, function(value, index) {
				meta.data[index] = meta.data[index] || new Chart.elements.Point({
					_chart: this.chart.chart,
					_datasetIndex: this.index,
					_index: index
				});
			}, this);
		},

		addElementAndReset: function(index) {
			var point = new Chart.elements.Point({
				_chart: this.chart.chart,
				_datasetIndex: this.index,
				_index: index
			});

			// Add to the points array and reset it
			this.getMeta().data.splice(index, 0, point);
			this.updateElement(point, index, true);

			// Make sure bezier control points are updated
			if (this.chart.options.showLines && this.chart.options.elements.line.tension !== 0)
				this.updateBezierControlPoints();
		},

		update: function update(reset) {
			var meta = this.getMeta();
			var line = meta.dataset;
			var points = meta.data;

			var yScale = this.getScaleForId(meta.yAxisID);
			var xScale = this.getScaleForId(meta.xAxisID);
			var scaleBase;

			if (yScale.min < 0 && yScale.max < 0) {
				scaleBase = yScale.getPixelForValue(yScale.max);
			} else if (yScale.min > 0 && yScale.max > 0) {
				scaleBase = yScale.getPixelForValue(yScale.min);
			} else {
				scaleBase = yScale.getPixelForValue(0);
			}

			// Update Line
			if (this.chart.options.showLines) {
				// Utility
				line._scale = yScale;
				line._datasetIndex = this.index;
				// Data
				line._children = points;
				// Model

				// Compatibility: If the properties are defined with only the old name, use those values
				if ((this.getDataset().tension !== undefined) && (this.getDataset().lineTension === undefined))
				{
					this.getDataset().lineTension = this.getDataset().tension;
				}

				line._model = {
					// Appearance
					tension: line.custom && line.custom.tension ? line.custom.tension : helpers.getValueOrDefault(this.getDataset().lineTension, this.chart.options.elements.line.tension),
					backgroundColor: line.custom && line.custom.backgroundColor ? line.custom.backgroundColor : (this.getDataset().backgroundColor || this.chart.options.elements.line.backgroundColor),
					borderWidth: line.custom && line.custom.borderWidth ? line.custom.borderWidth : (this.getDataset().borderWidth || this.chart.options.elements.line.borderWidth),
					borderColor: line.custom && line.custom.borderColor ? line.custom.borderColor : (this.getDataset().borderColor || this.chart.options.elements.line.borderColor),
					borderCapStyle: line.custom && line.custom.borderCapStyle ? line.custom.borderCapStyle : (this.getDataset().borderCapStyle || this.chart.options.elements.line.borderCapStyle),
					borderDash: line.custom && line.custom.borderDash ? line.custom.borderDash : (this.getDataset().borderDash || this.chart.options.elements.line.borderDash),
					borderDashOffset: line.custom && line.custom.borderDashOffset ? line.custom.borderDashOffset : (this.getDataset().borderDashOffset || this.chart.options.elements.line.borderDashOffset),
					borderJoinStyle: line.custom && line.custom.borderJoinStyle ? line.custom.borderJoinStyle : (this.getDataset().borderJoinStyle || this.chart.options.elements.line.borderJoinStyle),
					fill: line.custom && line.custom.fill ? line.custom.fill : (this.getDataset().fill !== undefined ? this.getDataset().fill : this.chart.options.elements.line.fill),
					// Scale
					scaleTop: yScale.top,
					scaleBottom: yScale.bottom,
					scaleZero: scaleBase
				};
				line.pivot();
			}

			// Update Points
			helpers.each(points, function(point, index) {
				this.updateElement(point, index, reset);
			}, this);

			if (this.chart.options.showLines && this.chart.options.elements.line.tension !== 0)
				this.updateBezierControlPoints();
		},

		getPointBackgroundColor: function(point, index) {
			var backgroundColor = this.chart.options.elements.point.backgroundColor;
			var dataset = this.getDataset();

			if (point.custom && point.custom.backgroundColor) {
				backgroundColor = point.custom.backgroundColor;
			} else if (dataset.pointBackgroundColor) {
				backgroundColor = helpers.getValueAtIndexOrDefault(dataset.pointBackgroundColor, index, backgroundColor);
			} else if (dataset.backgroundColor) {
				backgroundColor = dataset.backgroundColor;
			}

			return backgroundColor;
		},
		getPointBorderColor: function(point, index) {
			var borderColor = this.chart.options.elements.point.borderColor;
			var dataset = this.getDataset();

			if (point.custom && point.custom.borderColor) {
				borderColor = point.custom.borderColor;
			} else if (dataset.pointBorderColor) {
				borderColor = helpers.getValueAtIndexOrDefault(this.getDataset().pointBorderColor, index, borderColor);
			} else if (dataset.borderColor) {
				borderColor = dataset.borderColor;
			}

			return borderColor;
		},
		getPointBorderWidth: function(point, index) {
			var borderWidth = this.chart.options.elements.point.borderWidth;
			var dataset = this.getDataset();

			if (point.custom && point.custom.borderWidth !== undefined) {
				borderWidth = point.custom.borderWidth;
			} else if (dataset.pointBorderWidth !== undefined) {
				borderWidth = helpers.getValueAtIndexOrDefault(dataset.pointBorderWidth, index, borderWidth);
			} else if (dataset.borderWidth !== undefined) {
				borderWidth = dataset.borderWidth;
			}

			return borderWidth;
		},

		updateElement: function(point, index, reset) {
			var meta = this.getMeta();
			var yScale = this.getScaleForId(meta.yAxisID);
			var xScale = this.getScaleForId(meta.xAxisID);
			var scaleBase;

			if (yScale.min < 0 && yScale.max < 0) {
				scaleBase = yScale.getPixelForValue(yScale.max);
			} else if (yScale.min > 0 && yScale.max > 0) {
				scaleBase = yScale.getPixelForValue(yScale.min);
			} else {
				scaleBase = yScale.getPixelForValue(0);
			}

			// Utility
			point._chart = this.chart.chart;
			point._xScale = xScale;
			point._yScale = yScale;
			point._datasetIndex = this.index;
			point._index = index;

			// Desired view properties

			// Compatibility: If the properties are defined with only the old name, use those values
			if ((this.getDataset().radius !== undefined) && (this.getDataset().pointRadius === undefined))
			{
				this.getDataset().pointRadius = this.getDataset().radius;
			}
			if ((this.getDataset().hitRadius !== undefined) && (this.getDataset().pointHitRadius === undefined))
			{
				this.getDataset().pointHitRadius = this.getDataset().hitRadius;
			}

			point._model = {
				x: xScale.getPixelForValue(this.getDataset().data[index], index, this.index, this.chart.isCombo),
				y: reset ? scaleBase : this.calculatePointY(this.getDataset().data[index], index, this.index, this.chart.isCombo),
				// Appearance
				radius: point.custom && point.custom.radius ? point.custom.radius : helpers.getValueAtIndexOrDefault(this.getDataset().pointRadius, index, this.chart.options.elements.point.radius),
				pointStyle: point.custom && point.custom.pointStyle ? point.custom.pointStyle : helpers.getValueAtIndexOrDefault(this.getDataset().pointStyle, index, this.chart.options.elements.point.pointStyle),
				backgroundColor: this.getPointBackgroundColor(point, index),
				borderColor: this.getPointBorderColor(point, index),
				borderWidth: this.getPointBorderWidth(point, index),
				tension: meta.dataset._model ? meta.dataset._model.tension : 0,
				// Tooltip
				hitRadius: point.custom && point.custom.hitRadius ? point.custom.hitRadius : helpers.getValueAtIndexOrDefault(this.getDataset().pointHitRadius, index, this.chart.options.elements.point.hitRadius)
			};

			point._model.skip = point.custom && point.custom.skip ? point.custom.skip : (isNaN(point._model.x) || isNaN(point._model.y));
		},

		calculatePointY: function(value, index, datasetIndex, isCombo) {
			var meta = this.getMeta();
			var xScale = this.getScaleForId(meta.xAxisID);
			var yScale = this.getScaleForId(meta.yAxisID);

			if (yScale.options.stacked) {

				var sumPos = 0,
					sumNeg = 0;

				for (var i = 0; i < datasetIndex; i++) {
					var ds = this.chart.data.datasets[i];
					var dsMeta = this.chart.getDatasetMeta(i);
					if (dsMeta.type === 'line' && this.chart.isDatasetVisible(i)) {
						if (ds.data[index] < 0) {
							sumNeg += ds.data[index] || 0;
						} else {
							sumPos += ds.data[index] || 0;
						}
					}
				}

				if (value < 0) {
					return yScale.getPixelForValue(sumNeg + value);
				} else {
					return yScale.getPixelForValue(sumPos + value);
				}
			}

			return yScale.getPixelForValue(value);
		},

		updateBezierControlPoints: function() {
			// Update bezier control points
			var meta = this.getMeta();
			helpers.each(meta.data, function(point, index) {
				var controlPoints = helpers.splineCurve(
					helpers.previousItem(meta.data, index)._model,
					point._model,
					helpers.nextItem(meta.data, index)._model,
					meta.dataset._model.tension
				);

				// Prevent the bezier going outside of the bounds of the graph
				point._model.controlPointPreviousX = Math.max(Math.min(controlPoints.previous.x, this.chart.chartArea.right), this.chart.chartArea.left);
				point._model.controlPointPreviousY = Math.max(Math.min(controlPoints.previous.y, this.chart.chartArea.bottom), this.chart.chartArea.top);

				point._model.controlPointNextX = Math.max(Math.min(controlPoints.next.x, this.chart.chartArea.right), this.chart.chartArea.left);
				point._model.controlPointNextY = Math.max(Math.min(controlPoints.next.y, this.chart.chartArea.bottom), this.chart.chartArea.top);

				// Now pivot the point for animation
				point.pivot();
			}, this);
		},

		draw: function(ease) {
			var meta = this.getMeta();
			var easingDecimal = ease || 1;

			// Transition Point Locations
			helpers.each(meta.data, function(point) {
				point.transition(easingDecimal);
			});

			// Transition and Draw the line
			if (this.chart.options.showLines)
				meta.dataset.transition(easingDecimal).draw();

			// Draw the points
			helpers.each(meta.data, function(point) {
				point.draw();
			});
		},

		setHoverStyle: function(point) {
			// Point
			var dataset = this.chart.data.datasets[point._datasetIndex];
			var index = point._index;

			point._model.radius = point.custom && point.custom.hoverRadius ? point.custom.hoverRadius : helpers.getValueAtIndexOrDefault(dataset.pointHoverRadius, index, this.chart.options.elements.point.hoverRadius);
			point._model.backgroundColor = point.custom && point.custom.hoverBackgroundColor ? point.custom.hoverBackgroundColor : helpers.getValueAtIndexOrDefault(dataset.pointHoverBackgroundColor, index, helpers.color(point._model.backgroundColor).saturate(0.5).darken(0.1).rgbString());
			point._model.borderColor = point.custom && point.custom.hoverBorderColor ? point.custom.hoverBorderColor : helpers.getValueAtIndexOrDefault(dataset.pointHoverBorderColor, index, helpers.color(point._model.borderColor).saturate(0.5).darken(0.1).rgbString());
			point._model.borderWidth = point.custom && point.custom.hoverBorderWidth ? point.custom.hoverBorderWidth : helpers.getValueAtIndexOrDefault(dataset.pointHoverBorderWidth, index, point._model.borderWidth);
		},

		removeHoverStyle: function(point) {
			var dataset = this.chart.data.datasets[point._datasetIndex];
			var index = point._index;

			// Compatibility: If the properties are defined with only the old name, use those values
			if ((this.getDataset().radius !== undefined) && (this.getDataset().pointRadius === undefined))
			{
				this.getDataset().pointRadius = this.getDataset().radius;
			}

			point._model.radius = point.custom && point.custom.radius ? point.custom.radius : helpers.getValueAtIndexOrDefault(this.getDataset().pointRadius, index, this.chart.options.elements.point.radius);
			point._model.backgroundColor = this.getPointBackgroundColor(point, index);
			point._model.borderColor = this.getPointBorderColor(point, index);
			point._model.borderWidth = this.getPointBorderWidth(point, index);
		}
	});
};


/***/ }),
/* 234 */
/***/ (function(module, exports, __webpack_require__) {

"use strict";


module.exports = function(Chart) {

	var helpers = Chart.helpers;

	Chart.defaults.polarArea = {

		scale: {
			type: "radialLinear",
			lineArc: true // so that lines are circular
		},

		//Boolean - Whether to animate the rotation of the chart
		animation: {
			animateRotate: true,
			animateScale: true
		},

		aspectRatio: 1,
		legendCallback: function(chart) {
			var text = [];
			text.push('<ul class="' + chart.id + '-legend">');

			if (chart.data.datasets.length) {
				for (var i = 0; i < chart.data.datasets[0].data.length; ++i) {
					text.push('<li><span style="background-color:' + chart.data.datasets[0].backgroundColor[i] + '">');
					if (chart.data.labels[i]) {
						text.push(chart.data.labels[i]);
					}
					text.push('</span></li>');
				}
			}

			text.push('</ul>');
			return text.join("");
		},
		legend: {
			labels: {
				generateLabels: function(chart) {
					var data = chart.data;
					if (data.labels.length && data.datasets.length) {
						return data.labels.map(function(label, i) {
							var meta = chart.getDatasetMeta(0);
							var ds = data.datasets[0];
							var arc = meta.data[i];
							var fill = arc.custom && arc.custom.backgroundColor ? arc.custom.backgroundColor : helpers.getValueAtIndexOrDefault(ds.backgroundColor, i, this.chart.options.elements.arc.backgroundColor);
							var stroke = arc.custom && arc.custom.borderColor ? arc.custom.borderColor : helpers.getValueAtIndexOrDefault(ds.borderColor, i, this.chart.options.elements.arc.borderColor);
							var bw = arc.custom && arc.custom.borderWidth ? arc.custom.borderWidth : helpers.getValueAtIndexOrDefault(ds.borderWidth, i, this.chart.options.elements.arc.borderWidth);

							return {
								text: label,
								fillStyle: fill,
								strokeStyle: stroke,
								lineWidth: bw,
								hidden: isNaN(ds.data[i]) || meta.data[i].hidden,

								// Extra data used for toggling the correct item
								index: i
							};
						}, this);
					} else {
						return [];
					}
				}
			},

			onClick: function(e, legendItem) {
				var index = legendItem.index;
				var chart = this.chart;
				var i, ilen, meta;

				for (i = 0, ilen = (chart.data.datasets || []).length; i < ilen; ++i) {
					meta = chart.getDatasetMeta(i);
					meta.data[index].hidden = !meta.data[index].hidden;
				}

				chart.update();
			}
		},

		// Need to override these to give a nice default
		tooltips: {
			callbacks: {
				title: function() {
					return '';
				},
				label: function(tooltipItem, data) {
					return data.labels[tooltipItem.index] + ': ' + tooltipItem.yLabel;
				}
			}
		}
	};

	Chart.controllers.polarArea = Chart.DatasetController.extend({
		linkScales: function() {
			// no scales for doughnut
		},

		addElements: function() {
			var meta = this.getMeta();
			helpers.each(this.getDataset().data, function(value, index) {
				meta.data[index] = meta.data[index] || new Chart.elements.Arc({
					_chart: this.chart.chart,
					_datasetIndex: this.index,
					_index: index
				});
			}, this);
		},

		addElementAndReset: function(index) {
			var arc = new Chart.elements.Arc({
				_chart: this.chart.chart,
				_datasetIndex: this.index,
				_index: index
			});

			// Add to the points array and reset it
			this.getMeta().data.splice(index, 0, arc);
			this.updateElement(arc, index, true);
		},

		update: function update(reset) {
			var meta = this.getMeta();
			var minSize = Math.min(this.chart.chartArea.right - this.chart.chartArea.left, this.chart.chartArea.bottom - this.chart.chartArea.top);
			this.chart.outerRadius = Math.max((minSize - this.chart.options.elements.arc.borderWidth / 2) / 2, 0);
			this.chart.innerRadius = Math.max(this.chart.options.cutoutPercentage ? (this.chart.outerRadius / 100) * (this.chart.options.cutoutPercentage) : 1, 0);
			this.chart.radiusLength = (this.chart.outerRadius - this.chart.innerRadius) / this.chart.getVisibleDatasetCount();

			this.outerRadius = this.chart.outerRadius - (this.chart.radiusLength * this.index);
			this.innerRadius = this.outerRadius - this.chart.radiusLength;

			meta.count = this.countVisibleElements();

			helpers.each(meta.data, function(arc, index) {
				this.updateElement(arc, index, reset);
			}, this);
		},

		updateElement: function(arc, index, reset) {
			var circumference = this.calculateCircumference(this.getDataset().data[index]);
			var centerX = (this.chart.chartArea.left + this.chart.chartArea.right) / 2;
			var centerY = (this.chart.chartArea.top + this.chart.chartArea.bottom) / 2;

			// If there is NaN data before us, we need to calculate the starting angle correctly.
			// We could be way more efficient here, but its unlikely that the polar area chart will have a lot of data
			var visibleCount = 0;
			var meta = this.getMeta();
			for (var i = 0; i < index; ++i) {
				if (!isNaN(this.getDataset().data[i]) && !meta.data[i].hidden) {
					++visibleCount;
				}
			}

			var distance = arc.hidden? 0 : this.chart.scale.getDistanceFromCenterForValue(this.getDataset().data[index]);
			var startAngle = (-0.5 * Math.PI) + (circumference * visibleCount);
			var endAngle = startAngle + (arc.hidden? 0 : circumference);

			var resetModel = {
				x: centerX,
				y: centerY,
				innerRadius: 0,
				outerRadius: this.chart.options.animation.animateScale ? 0 : this.chart.scale.getDistanceFromCenterForValue(this.getDataset().data[index]),
				startAngle: this.chart.options.animation.animateRotate ? Math.PI * -0.5 : startAngle,
				endAngle: this.chart.options.animation.animateRotate ? Math.PI * -0.5 : endAngle,

				backgroundColor: arc.custom && arc.custom.backgroundColor ? arc.custom.backgroundColor : helpers.getValueAtIndexOrDefault(this.getDataset().backgroundColor, index, this.chart.options.elements.arc.backgroundColor),
				borderWidth: arc.custom && arc.custom.borderWidth ? arc.custom.borderWidth : helpers.getValueAtIndexOrDefault(this.getDataset().borderWidth, index, this.chart.options.elements.arc.borderWidth),
				borderColor: arc.custom && arc.custom.borderColor ? arc.custom.borderColor : helpers.getValueAtIndexOrDefault(this.getDataset().borderColor, index, this.chart.options.elements.arc.borderColor),

				label: helpers.getValueAtIndexOrDefault(this.chart.data.labels, index, this.chart.data.labels[index])
			};

			helpers.extend(arc, {
				// Utility
				_chart: this.chart.chart,
				_datasetIndex: this.index,
				_index: index,
				_scale: this.chart.scale,

				// Desired view properties
				_model: reset ? resetModel : {
					x: centerX,
					y: centerY,
					innerRadius: 0,
					outerRadius: distance,
					startAngle: startAngle,
					endAngle: endAngle,

					backgroundColor: arc.custom && arc.custom.backgroundColor ? arc.custom.backgroundColor : helpers.getValueAtIndexOrDefault(this.getDataset().backgroundColor, index, this.chart.options.elements.arc.backgroundColor),
					borderWidth: arc.custom && arc.custom.borderWidth ? arc.custom.borderWidth : helpers.getValueAtIndexOrDefault(this.getDataset().borderWidth, index, this.chart.options.elements.arc.borderWidth),
					borderColor: arc.custom && arc.custom.borderColor ? arc.custom.borderColor : helpers.getValueAtIndexOrDefault(this.getDataset().borderColor, index, this.chart.options.elements.arc.borderColor),

					label: helpers.getValueAtIndexOrDefault(this.chart.data.labels, index, this.chart.data.labels[index])
				}
			});

			arc.pivot();
		},

		draw: function(ease) {
			var easingDecimal = ease || 1;
			helpers.each(this.getMeta().data, function(arc, index) {
				arc.transition(easingDecimal).draw();
			});
		},

		setHoverStyle: function(arc) {
			var dataset = this.chart.data.datasets[arc._datasetIndex];
			var index = arc._index;

			arc._model.backgroundColor = arc.custom && arc.custom.hoverBackgroundColor ? arc.custom.hoverBackgroundColor : helpers.getValueAtIndexOrDefault(dataset.hoverBackgroundColor, index, helpers.color(arc._model.backgroundColor).saturate(0.5).darken(0.1).rgbString());
			arc._model.borderColor = arc.custom && arc.custom.hoverBorderColor ? arc.custom.hoverBorderColor : helpers.getValueAtIndexOrDefault(dataset.hoverBorderColor, index, helpers.color(arc._model.borderColor).saturate(0.5).darken(0.1).rgbString());
			arc._model.borderWidth = arc.custom && arc.custom.hoverBorderWidth ? arc.custom.hoverBorderWidth : helpers.getValueAtIndexOrDefault(dataset.hoverBorderWidth, index, arc._model.borderWidth);
		},

		removeHoverStyle: function(arc) {
			var dataset = this.chart.data.datasets[arc._datasetIndex];
			var index = arc._index;

			arc._model.backgroundColor = arc.custom && arc.custom.backgroundColor ? arc.custom.backgroundColor : helpers.getValueAtIndexOrDefault(this.getDataset().backgroundColor, index, this.chart.options.elements.arc.backgroundColor);
			arc._model.borderColor = arc.custom && arc.custom.borderColor ? arc.custom.borderColor : helpers.getValueAtIndexOrDefault(this.getDataset().borderColor, index, this.chart.options.elements.arc.borderColor);
			arc._model.borderWidth = arc.custom && arc.custom.borderWidth ? arc.custom.borderWidth : helpers.getValueAtIndexOrDefault(this.getDataset().borderWidth, index, this.chart.options.elements.arc.borderWidth);
		},

		countVisibleElements: function() {
			var dataset = this.getDataset();
			var meta = this.getMeta();
			var count = 0;

			helpers.each(meta.data, function(element, index) {
				if (!isNaN(dataset.data[index]) && !element.hidden) {
					count++;
				}
			});

			return count;
		},

		calculateCircumference: function(value) {
			var count = this.getMeta().count;
			if (count > 0 && !isNaN(value)) {
				return (2 * Math.PI) / count;
			} else {
				return 0;
			}
		}
	});
};


/***/ }),
/* 235 */
/***/ (function(module, exports, __webpack_require__) {

"use strict";


module.exports = function(Chart) {

	var helpers = Chart.helpers;


	Chart.defaults.radar = {
		scale: {
			type: "radialLinear"
		},
		elements: {
			line: {
				tension: 0 // no bezier in radar
			}
		}
	};

	Chart.controllers.radar = Chart.DatasetController.extend({
		linkScales: function() {
			// No need. Single scale only
		},

		addElements: function() {
			var meta = this.getMeta();

			meta.dataset = meta.dataset || new Chart.elements.Line({
				_chart: this.chart.chart,
				_datasetIndex: this.index,
				_points: meta.data,
				_loop: true
			});

			helpers.each(this.getDataset().data, function(value, index) {
				meta.data[index] = meta.data[index] || new Chart.elements.Point({
					_chart: this.chart.chart,
					_datasetIndex: this.index,
					_index: index,
					_model: {
						x: 0, //xScale.getPixelForValue(null, index, true),
						y: 0 //this.chartArea.bottom,
					}
				});
			}, this);
		},
		addElementAndReset: function(index) {
			var point = new Chart.elements.Point({
				_chart: this.chart.chart,
				_datasetIndex: this.index,
				_index: index
			});

			// Add to the points array and reset it
			this.getMeta().data.splice(index, 0, point);
			this.updateElement(point, index, true);

			// Make sure bezier control points are updated
			this.updateBezierControlPoints();
		},

		update: function update(reset) {
			var meta = this.getMeta();
			var line = meta.dataset;
			var points = meta.data;

			var scale = this.chart.scale;
			var scaleBase;

			if (scale.min < 0 && scale.max < 0) {
				scaleBase = scale.getPointPositionForValue(0, scale.max);
			} else if (scale.min > 0 && scale.max > 0) {
				scaleBase = scale.getPointPositionForValue(0, scale.min);
			} else {
				scaleBase = scale.getPointPositionForValue(0, 0);
			}

			// Compatibility: If the properties are defined with only the old name, use those values
			if ((this.getDataset().tension !== undefined) && (this.getDataset().lineTension === undefined))
			{
				this.getDataset().lineTension = this.getDataset().tension;
			}

			helpers.extend(meta.dataset, {
				// Utility
				_datasetIndex: this.index,
				// Data
				_children: points,
				// Model
				_model: {
					// Appearance
					tension: line.custom && line.custom.tension ? line.custom.tension : helpers.getValueOrDefault(this.getDataset().lineTension, this.chart.options.elements.line.tension),
					backgroundColor: line.custom && line.custom.backgroundColor ? line.custom.backgroundColor : (this.getDataset().backgroundColor || this.chart.options.elements.line.backgroundColor),
					borderWidth: line.custom && line.custom.borderWidth ? line.custom.borderWidth : (this.getDataset().borderWidth || this.chart.options.elements.line.borderWidth),
					borderColor: line.custom && line.custom.borderColor ? line.custom.borderColor : (this.getDataset().borderColor || this.chart.options.elements.line.borderColor),
					fill: line.custom && line.custom.fill ? line.custom.fill : (this.getDataset().fill !== undefined ? this.getDataset().fill : this.chart.options.elements.line.fill),
					borderCapStyle: line.custom && line.custom.borderCapStyle ? line.custom.borderCapStyle : (this.getDataset().borderCapStyle || this.chart.options.elements.line.borderCapStyle),
					borderDash: line.custom && line.custom.borderDash ? line.custom.borderDash : (this.getDataset().borderDash || this.chart.options.elements.line.borderDash),
					borderDashOffset: line.custom && line.custom.borderDashOffset ? line.custom.borderDashOffset : (this.getDataset().borderDashOffset || this.chart.options.elements.line.borderDashOffset),
					borderJoinStyle: line.custom && line.custom.borderJoinStyle ? line.custom.borderJoinStyle : (this.getDataset().borderJoinStyle || this.chart.options.elements.line.borderJoinStyle),

					// Scale
					scaleTop: scale.top,
					scaleBottom: scale.bottom,
					scaleZero: scaleBase
				}
			});

			meta.dataset.pivot();

			// Update Points
			helpers.each(points, function(point, index) {
				this.updateElement(point, index, reset);
			}, this);


			// Update bezier control points
			this.updateBezierControlPoints();
		},
		updateElement: function(point, index, reset) {
			var pointPosition = this.chart.scale.getPointPositionForValue(index, this.getDataset().data[index]);

			helpers.extend(point, {
				// Utility
				_datasetIndex: this.index,
				_index: index,
				_scale: this.chart.scale,

				// Desired view properties
				_model: {
					x: reset ? this.chart.scale.xCenter : pointPosition.x, // value not used in dataset scale, but we want a consistent API between scales
					y: reset ? this.chart.scale.yCenter : pointPosition.y,

					// Appearance
					tension: point.custom && point.custom.tension ? point.custom.tension : helpers.getValueOrDefault(this.getDataset().tension, this.chart.options.elements.line.tension),
					radius: point.custom && point.custom.radius ? point.custom.radius : helpers.getValueAtIndexOrDefault(this.getDataset().pointRadius, index, this.chart.options.elements.point.radius),
					backgroundColor: point.custom && point.custom.backgroundColor ? point.custom.backgroundColor : helpers.getValueAtIndexOrDefault(this.getDataset().pointBackgroundColor, index, this.chart.options.elements.point.backgroundColor),
					borderColor: point.custom && point.custom.borderColor ? point.custom.borderColor : helpers.getValueAtIndexOrDefault(this.getDataset().pointBorderColor, index, this.chart.options.elements.point.borderColor),
					borderWidth: point.custom && point.custom.borderWidth ? point.custom.borderWidth : helpers.getValueAtIndexOrDefault(this.getDataset().pointBorderWidth, index, this.chart.options.elements.point.borderWidth),
					pointStyle: point.custom && point.custom.pointStyle ? point.custom.pointStyle : helpers.getValueAtIndexOrDefault(this.getDataset().pointStyle, index, this.chart.options.elements.point.pointStyle),

					// Tooltip
					hitRadius: point.custom && point.custom.hitRadius ? point.custom.hitRadius : helpers.getValueAtIndexOrDefault(this.getDataset().hitRadius, index, this.chart.options.elements.point.hitRadius)
				}
			});

			point._model.skip = point.custom && point.custom.skip ? point.custom.skip : (isNaN(point._model.x) || isNaN(point._model.y));
		},
		updateBezierControlPoints: function() {
			var meta = this.getMeta();
			helpers.each(meta.data, function(point, index) {
				var controlPoints = helpers.splineCurve(
					helpers.previousItem(meta.data, index, true)._model,
					point._model,
					helpers.nextItem(meta.data, index, true)._model,
					point._model.tension
				);

				// Prevent the bezier going outside of the bounds of the graph
				point._model.controlPointPreviousX = Math.max(Math.min(controlPoints.previous.x, this.chart.chartArea.right), this.chart.chartArea.left);
				point._model.controlPointPreviousY = Math.max(Math.min(controlPoints.previous.y, this.chart.chartArea.bottom), this.chart.chartArea.top);

				point._model.controlPointNextX = Math.max(Math.min(controlPoints.next.x, this.chart.chartArea.right), this.chart.chartArea.left);
				point._model.controlPointNextY = Math.max(Math.min(controlPoints.next.y, this.chart.chartArea.bottom), this.chart.chartArea.top);

				// Now pivot the point for animation
				point.pivot();
			}, this);
		},

		draw: function(ease) {
			var meta = this.getMeta();
			var easingDecimal = ease || 1;

			// Transition Point Locations
			helpers.each(meta.data, function(point, index) {
				point.transition(easingDecimal);
			});

			// Transition and Draw the line
			meta.dataset.transition(easingDecimal).draw();

			// Draw the points
			helpers.each(meta.data, function(point) {
				point.draw();
			});
		},

		setHoverStyle: function(point) {
			// Point
			var dataset = this.chart.data.datasets[point._datasetIndex];
			var index = point._index;

			point._model.radius = point.custom && point.custom.hoverRadius ? point.custom.hoverRadius : helpers.getValueAtIndexOrDefault(dataset.pointHoverRadius, index, this.chart.options.elements.point.hoverRadius);
			point._model.backgroundColor = point.custom && point.custom.hoverBackgroundColor ? point.custom.hoverBackgroundColor : helpers.getValueAtIndexOrDefault(dataset.pointHoverBackgroundColor, index, helpers.color(point._model.backgroundColor).saturate(0.5).darken(0.1).rgbString());
			point._model.borderColor = point.custom && point.custom.hoverBorderColor ? point.custom.hoverBorderColor : helpers.getValueAtIndexOrDefault(dataset.pointHoverBorderColor, index, helpers.color(point._model.borderColor).saturate(0.5).darken(0.1).rgbString());
			point._model.borderWidth = point.custom && point.custom.hoverBorderWidth ? point.custom.hoverBorderWidth : helpers.getValueAtIndexOrDefault(dataset.pointHoverBorderWidth, index, point._model.borderWidth);
		},

		removeHoverStyle: function(point) {
			var dataset = this.chart.data.datasets[point._datasetIndex];
			var index = point._index;

			point._model.radius = point.custom && point.custom.radius ? point.custom.radius : helpers.getValueAtIndexOrDefault(this.getDataset().radius, index, this.chart.options.elements.point.radius);
			point._model.backgroundColor = point.custom && point.custom.backgroundColor ? point.custom.backgroundColor : helpers.getValueAtIndexOrDefault(this.getDataset().pointBackgroundColor, index, this.chart.options.elements.point.backgroundColor);
			point._model.borderColor = point.custom && point.custom.borderColor ? point.custom.borderColor : helpers.getValueAtIndexOrDefault(this.getDataset().pointBorderColor, index, this.chart.options.elements.point.borderColor);
			point._model.borderWidth = point.custom && point.custom.borderWidth ? point.custom.borderWidth : helpers.getValueAtIndexOrDefault(this.getDataset().pointBorderWidth, index, this.chart.options.elements.point.borderWidth);
		}
	});
};

/***/ }),
/* 236 */
/***/ (function(module, exports, __webpack_require__) {

"use strict";
/*global window: false */


module.exports = function(Chart) {

	var helpers = Chart.helpers;

	Chart.defaults.global.animation = {
		duration: 1000,
		easing: "easeOutQuart",
		onProgress: helpers.noop,
		onComplete: helpers.noop
	};

	Chart.Animation = Chart.Element.extend({
		currentStep: null, // the current animation step
		numSteps: 60, // default number of steps
		easing: "", // the easing to use for this animation
		render: null, // render function used by the animation service

		onAnimationProgress: null, // user specified callback to fire on each step of the animation
		onAnimationComplete: null // user specified callback to fire when the animation finishes
	});

	Chart.animationService = {
		frameDuration: 17,
		animations: [],
		dropFrames: 0,
		request: null,
		addAnimation: function(chartInstance, animationObject, duration, lazy) {

			if (!lazy) {
				chartInstance.animating = true;
			}

			for (var index = 0; index < this.animations.length; ++index) {
				if (this.animations[index].chartInstance === chartInstance) {
					// replacing an in progress animation
					this.animations[index].animationObject = animationObject;
					return;
				}
			}

			this.animations.push({
				chartInstance: chartInstance,
				animationObject: animationObject
			});

			// If there are no animations queued, manually kickstart a digest, for lack of a better word
			if (this.animations.length === 1) {
				this.requestAnimationFrame();
			}
		},
		// Cancel the animation for a given chart instance
		cancelAnimation: function(chartInstance) {
			var index = helpers.findIndex(this.animations, function(animationWrapper) {
				return animationWrapper.chartInstance === chartInstance;
			});

			if (index !== -1) {
				this.animations.splice(index, 1);
				chartInstance.animating = false;
			}
		},
		requestAnimationFrame: function() {
			var me = this;
			if (me.request === null) {
				// Skip animation frame requests until the active one is executed.
				// This can happen when processing mouse events, e.g. 'mousemove'
				// and 'mouseout' events will trigger multiple renders.
				me.request = helpers.requestAnimFrame.call(window, function() {
					me.request = null;
					me.startDigest();
				});
			}
		},
		startDigest: function() {

			var startTime = Date.now();
			var framesToDrop = 0;

			if (this.dropFrames > 1) {
				framesToDrop = Math.floor(this.dropFrames);
				this.dropFrames = this.dropFrames % 1;
			}

			var i = 0;
			while (i < this.animations.length) {
				if (this.animations[i].animationObject.currentStep === null) {
					this.animations[i].animationObject.currentStep = 0;
				}

				this.animations[i].animationObject.currentStep += 1 + framesToDrop;

				if (this.animations[i].animationObject.currentStep > this.animations[i].animationObject.numSteps) {
					this.animations[i].animationObject.currentStep = this.animations[i].animationObject.numSteps;
				}

				this.animations[i].animationObject.render(this.animations[i].chartInstance, this.animations[i].animationObject);
				if (this.animations[i].animationObject.onAnimationProgress && this.animations[i].animationObject.onAnimationProgress.call) {
					this.animations[i].animationObject.onAnimationProgress.call(this.animations[i].chartInstance, this.animations[i]);
				}

				if (this.animations[i].animationObject.currentStep === this.animations[i].animationObject.numSteps) {
					if (this.animations[i].animationObject.onAnimationComplete && this.animations[i].animationObject.onAnimationComplete.call) {
						this.animations[i].animationObject.onAnimationComplete.call(this.animations[i].chartInstance, this.animations[i]);
					}

					// executed the last frame. Remove the animation.
					this.animations[i].chartInstance.animating = false;

					this.animations.splice(i, 1);
				} else {
					++i;
				}
			}

			var endTime = Date.now();
			var dropFrames = (endTime - startTime) / this.frameDuration;

			this.dropFrames += dropFrames;

			// Do we have more stuff to animate?
			if (this.animations.length > 0) {
				this.requestAnimationFrame();
			}
		}
	};
};

/***/ }),
/* 237 */
/***/ (function(module, exports, __webpack_require__) {

"use strict";


module.exports = function(Chart) {

	var helpers = Chart.helpers;
	//Create a dictionary of chart types, to allow for extension of existing types
	Chart.types = {};

	//Store a reference to each instance - allowing us to globally resize chart instances on window resize.
	//Destroy method on the chart will remove the instance of the chart from this reference.
	Chart.instances = {};

	// Controllers available for dataset visualization eg. bar, line, slice, etc.
	Chart.controllers = {};

	// The main controller of a chart
	Chart.Controller = function(instance) {

		this.chart = instance;
		this.config = instance.config;
		this.options = this.config.options = helpers.configMerge(Chart.defaults.global, Chart.defaults[this.config.type], this.config.options || {});
		this.id = helpers.uid();

		Object.defineProperty(this, 'data', {
			get: function() {
				return this.config.data;
			}
		});

		//Add the chart instance to the global namespace
		Chart.instances[this.id] = this;

		if (this.options.responsive) {
			// Silent resize before chart draws
			this.resize(true);
		}

		this.initialize();

		return this;
	};

	helpers.extend(Chart.Controller.prototype, {

		initialize: function initialize() {
			// Before init plugin notification
			Chart.pluginService.notifyPlugins('beforeInit', [this]);

			this.bindEvents();

			// Make sure controllers are built first so that each dataset is bound to an axis before the scales
			// are built
			this.ensureScalesHaveIDs();
			this.buildOrUpdateControllers();
			this.buildScales();
			this.buildSurroundingItems();
			this.updateLayout();
			this.resetElements();
			this.initToolTip();
			this.update();

			// After init plugin notification
			Chart.pluginService.notifyPlugins('afterInit', [this]);

			return this;
		},

		clear: function clear() {
			helpers.clear(this.chart);
			return this;
		},

		stop: function stop() {
			// Stops any current animation loop occuring
			Chart.animationService.cancelAnimation(this);
			return this;
		},

		resize: function resize(silent) {
			var canvas = this.chart.canvas;
			var newWidth = helpers.getMaximumWidth(this.chart.canvas);
			var newHeight = (this.options.maintainAspectRatio && isNaN(this.chart.aspectRatio) === false && isFinite(this.chart.aspectRatio) && this.chart.aspectRatio !== 0) ? newWidth / this.chart.aspectRatio : helpers.getMaximumHeight(this.chart.canvas);

			var sizeChanged = this.chart.width !== newWidth || this.chart.height !== newHeight;

			if (!sizeChanged)
				return this;

			canvas.width = this.chart.width = newWidth;
			canvas.height = this.chart.height = newHeight;

			helpers.retinaScale(this.chart);

			if (!silent) {
				this.stop();
				this.update(this.options.responsiveAnimationDuration);
			}

			return this;
		},
		ensureScalesHaveIDs: function ensureScalesHaveIDs() {
			var defaultXAxisID = 'x-axis-';
			var defaultYAxisID = 'y-axis-';

			if (this.options.scales) {
				if (this.options.scales.xAxes && this.options.scales.xAxes.length) {
					helpers.each(this.options.scales.xAxes, function(xAxisOptions, index) {
						xAxisOptions.id = xAxisOptions.id || (defaultXAxisID + index);
					});
				}

				if (this.options.scales.yAxes && this.options.scales.yAxes.length) {
					// Build the y axes
					helpers.each(this.options.scales.yAxes, function(yAxisOptions, index) {
						yAxisOptions.id = yAxisOptions.id || (defaultYAxisID + index);
					});
				}
			}
		},
		buildScales: function buildScales() {
			// Map of scale ID to scale object so we can lookup later
			this.scales = {};

			// Build the x axes
			if (this.options.scales) {
				if (this.options.scales.xAxes && this.options.scales.xAxes.length) {
					helpers.each(this.options.scales.xAxes, function(xAxisOptions, index) {
						var xType = helpers.getValueOrDefault(xAxisOptions.type, 'category');
						var ScaleClass = Chart.scaleService.getScaleConstructor(xType);
						if (ScaleClass) {
							var scale = new ScaleClass({
								ctx: this.chart.ctx,
								options: xAxisOptions,
								chart: this,
								id: xAxisOptions.id
							});

							this.scales[scale.id] = scale;
						}
					}, this);
				}

				if (this.options.scales.yAxes && this.options.scales.yAxes.length) {
					// Build the y axes
					helpers.each(this.options.scales.yAxes, function(yAxisOptions, index) {
						var yType = helpers.getValueOrDefault(yAxisOptions.type, 'linear');
						var ScaleClass = Chart.scaleService.getScaleConstructor(yType);
						if (ScaleClass) {
							var scale = new ScaleClass({
								ctx: this.chart.ctx,
								options: yAxisOptions,
								chart: this,
								id: yAxisOptions.id
							});

							this.scales[scale.id] = scale;
						}
					}, this);
				}
			}
			if (this.options.scale) {
				// Build radial axes
				var ScaleClass = Chart.scaleService.getScaleConstructor(this.options.scale.type);
				if (ScaleClass) {
					var scale = new ScaleClass({
						ctx: this.chart.ctx,
						options: this.options.scale,
						chart: this
					});

					this.scale = scale;

					this.scales.radialScale = scale;
				}
			}

			Chart.scaleService.addScalesToLayout(this);
		},

		buildSurroundingItems: function() {
			if (this.options.title) {
				this.titleBlock = new Chart.Title({
					ctx: this.chart.ctx,
					options: this.options.title,
					chart: this
				});

				Chart.layoutService.addBox(this, this.titleBlock);
			}

			if (this.options.legend) {
				this.legend = new Chart.Legend({
					ctx: this.chart.ctx,
					options: this.options.legend,
					chart: this
				});

				Chart.layoutService.addBox(this, this.legend);
			}
		},

		updateLayout: function() {
			Chart.layoutService.update(this, this.chart.width, this.chart.height);
		},

		buildOrUpdateControllers: function buildOrUpdateControllers() {
			var types = [];
			var newControllers = [];

			helpers.each(this.data.datasets, function(dataset, datasetIndex) {
				var meta = this.getDatasetMeta(datasetIndex);
				if (!meta.type) {
					meta.type = dataset.type || this.config.type;
				}

				types.push(meta.type);

				if (meta.controller) {
					meta.controller.updateIndex(datasetIndex);
				} else {
					meta.controller = new Chart.controllers[meta.type](this, datasetIndex);
					newControllers.push(meta.controller);
				}
			}, this);

			if (types.length > 1) {
				for (var i = 1; i < types.length; i++) {
					if (types[i] !== types[i - 1]) {
						this.isCombo = true;
						break;
					}
				}
			}

			return newControllers;
		},

		resetElements: function resetElements() {
			helpers.each(this.data.datasets, function(dataset, datasetIndex) {
				this.getDatasetMeta(datasetIndex).controller.reset();
			}, this);
		},

		update: function update(animationDuration, lazy) {
			Chart.pluginService.notifyPlugins('beforeUpdate', [this]);

			// In case the entire data object changed
			this.tooltip._data = this.data;

			// Make sure dataset controllers are updated and new controllers are reset
			var newControllers = this.buildOrUpdateControllers();

			// Make sure all dataset controllers have correct meta data counts
			helpers.each(this.data.datasets, function(dataset, datasetIndex) {
				this.getDatasetMeta(datasetIndex).controller.buildOrUpdateElements();
			}, this);

			Chart.layoutService.update(this, this.chart.width, this.chart.height);

			// Can only reset the new controllers after the scales have been updated
			helpers.each(newControllers, function(controller) {
				controller.reset();
			});

			// This will loop through any data and do the appropriate element update for the type
			helpers.each(this.data.datasets, function(dataset, datasetIndex) {
				this.getDatasetMeta(datasetIndex).controller.update();
			}, this);

			this.render(animationDuration, lazy);

			Chart.pluginService.notifyPlugins('afterUpdate', [this]);
		},

		render: function render(duration, lazy) {
			Chart.pluginService.notifyPlugins('beforeRender', [this]);

			if (this.options.animation && ((typeof duration !== 'undefined' && duration !== 0) || (typeof duration === 'undefined' && this.options.animation.duration !== 0))) {
				var animation = new Chart.Animation();
				animation.numSteps = (duration || this.options.animation.duration) / 16.66; //60 fps
				animation.easing = this.options.animation.easing;

				// render function
				animation.render = function(chartInstance, animationObject) {
					var easingFunction = helpers.easingEffects[animationObject.easing];
					var stepDecimal = animationObject.currentStep / animationObject.numSteps;
					var easeDecimal = easingFunction(stepDecimal);

					chartInstance.draw(easeDecimal, stepDecimal, animationObject.currentStep);
				};

				// user events
				animation.onAnimationProgress = this.options.animation.onProgress;
				animation.onAnimationComplete = this.options.animation.onComplete;

				Chart.animationService.addAnimation(this, animation, duration, lazy);
			} else {
				this.draw();
				if (this.options.animation && this.options.animation.onComplete && this.options.animation.onComplete.call) {
					this.options.animation.onComplete.call(this);
				}
			}
			return this;
		},

		draw: function(ease) {
			var easingDecimal = ease || 1;
			this.clear();

			Chart.pluginService.notifyPlugins('beforeDraw', [this, easingDecimal]);

			// Draw all the scales
			helpers.each(this.boxes, function(box) {
				box.draw(this.chartArea);
			}, this);
			if (this.scale) {
				this.scale.draw();
			}

			// Clip out the chart area so that anything outside does not draw. This is necessary for zoom and pan to function
			this.chart.ctx.save();
			this.chart.ctx.beginPath();
			this.chart.ctx.rect(this.chartArea.left, this.chartArea.top, this.chartArea.right - this.chartArea.left, this.chartArea.bottom - this.chartArea.top);
			this.chart.ctx.clip();

			// Draw each dataset via its respective controller (reversed to support proper line stacking)
			helpers.each(this.data.datasets, function(dataset, datasetIndex) {
				if (this.isDatasetVisible(datasetIndex)) {
					this.getDatasetMeta(datasetIndex).controller.draw(ease);
				}
			}, this, true);

			// Restore from the clipping operation
			this.chart.ctx.restore();

			// Finally draw the tooltip
			this.tooltip.transition(easingDecimal).draw();

			Chart.pluginService.notifyPlugins('afterDraw', [this, easingDecimal]);
		},

		// Get the single element that was clicked on
		// @return : An object containing the dataset index and element index of the matching element. Also contains the rectangle that was draw
		getElementAtEvent: function(e) {
			var eventPosition = helpers.getRelativePosition(e, this.chart);
			var elementsArray = [];

			helpers.each(this.data.datasets, function(dataset, datasetIndex) {
				if (this.isDatasetVisible(datasetIndex)) {
					var meta = this.getDatasetMeta(datasetIndex);
					helpers.each(meta.data, function(element, index) {
						if (element.inRange(eventPosition.x, eventPosition.y)) {
							elementsArray.push(element);
							return elementsArray;
						}
					});
				}
			}, this);

			return elementsArray;
		},

		getElementsAtEvent: function(e) {
			var eventPosition = helpers.getRelativePosition(e, this.chart);
			var elementsArray = [];

			var found = (function() {
				if (this.data.datasets) {
					for (var i = 0; i < this.data.datasets.length; i++) {
						var meta = this.getDatasetMeta(i);
						if (this.isDatasetVisible(i)) {
							for (var j = 0; j < meta.data.length; j++) {
								if (meta.data[j].inRange(eventPosition.x, eventPosition.y)) {
									return meta.data[j];
								}
							}
						}
					}
				}
			}).call(this);

			if (!found) {
				return elementsArray;
			}

			helpers.each(this.data.datasets, function(dataset, datasetIndex) {
				if (this.isDatasetVisible(datasetIndex)) {
					var meta = this.getDatasetMeta(datasetIndex);
					elementsArray.push(meta.data[found._index]);
				}
			}, this);

			return elementsArray;
		},

		getDatasetAtEvent: function(e) {
			var elementsArray = this.getElementAtEvent(e);

			if (elementsArray.length > 0) {
				elementsArray = this.getDatasetMeta(elementsArray[0]._datasetIndex).data;
			}

			return elementsArray;
		},

		getDatasetMeta: function(datasetIndex) {
			var dataset = this.data.datasets[datasetIndex];
			if (!dataset._meta) {
				dataset._meta = {};
			}

			var meta = dataset._meta[this.id];
			if (!meta) {
				meta = dataset._meta[this.id] = {
				type: null,
				data: [],
				dataset: null,
				controller: null,
				hidden: null,			// See isDatasetVisible() comment
				xAxisID: null,
				yAxisID: null
			};
			}

			return meta;
		},

		getVisibleDatasetCount: function() {
			var count = 0;
			for (var i = 0, ilen = this.data.datasets.length; i<ilen; ++i) {
				 if (this.isDatasetVisible(i)) {
					count++;
				}
			}
			return count;
		},

		isDatasetVisible: function(datasetIndex) {
			var meta = this.getDatasetMeta(datasetIndex);

			// meta.hidden is a per chart dataset hidden flag override with 3 states: if true or false,
			// the dataset.hidden value is ignored, else if null, the dataset hidden state is returned.
			return typeof meta.hidden === 'boolean'? !meta.hidden : !this.data.datasets[datasetIndex].hidden;
		},

		generateLegend: function generateLegend() {
			return this.options.legendCallback(this);
		},

		destroy: function destroy() {
			this.clear();
			helpers.unbindEvents(this, this.events);
			helpers.removeResizeListener(this.chart.canvas.parentNode);

			// Reset canvas height/width attributes
			var canvas = this.chart.canvas;
			canvas.width = this.chart.width;
			canvas.height = this.chart.height;

			// if we scaled the canvas in response to a devicePixelRatio !== 1, we need to undo that transform here
			if (this.chart.originalDevicePixelRatio !== undefined) {
				this.chart.ctx.scale(1 / this.chart.originalDevicePixelRatio, 1 / this.chart.originalDevicePixelRatio);
			}

			// Reset to the old style since it may have been changed by the device pixel ratio changes
			canvas.style.width = this.chart.originalCanvasStyleWidth;
			canvas.style.height = this.chart.originalCanvasStyleHeight;

			Chart.pluginService.notifyPlugins('destroy', [this]);

			delete Chart.instances[this.id];
		},

		toBase64Image: function toBase64Image() {
			return this.chart.canvas.toDataURL.apply(this.chart.canvas, arguments);
		},

		initToolTip: function initToolTip() {
			this.tooltip = new Chart.Tooltip({
				_chart: this.chart,
				_chartInstance: this,
				_data: this.data,
				_options: this.options
			}, this);
		},

		bindEvents: function bindEvents() {
			helpers.bindEvents(this, this.options.events, function(evt) {
				this.eventHandler(evt);
			});
		},
		eventHandler: function eventHandler(e) {
			this.lastActive = this.lastActive || [];
			this.lastTooltipActive = this.lastTooltipActive || [];

			// Find Active Elements for hover and tooltips
			if (e.type === 'mouseout') {
				this.active = [];
				this.tooltipActive = [];
			} else {

				var _this = this;
				var getItemsForMode = function(mode) {
					switch (mode) {
						case 'single':
							return _this.getElementAtEvent(e);
						case 'label':
							return _this.getElementsAtEvent(e);
						case 'dataset':
							return _this.getDatasetAtEvent(e);
						default:
							return e;
					}
				};

				this.active = getItemsForMode(this.options.hover.mode);
				this.tooltipActive = getItemsForMode(this.options.tooltips.mode);
			}

			// On Hover hook
			if (this.options.hover.onHover) {
				this.options.hover.onHover.call(this, this.active);
			}

			if (e.type === 'mouseup' || e.type === 'click') {
				if (this.options.onClick) {
					this.options.onClick.call(this, e, this.active);
				}

				if (this.legend && this.legend.handleEvent) {
					this.legend.handleEvent(e);
				}
			}

			// Remove styling for last active (even if it may still be active)
			if (this.lastActive.length) {
				switch (this.options.hover.mode) {
					case 'single':
						this.getDatasetMeta(this.lastActive[0]._datasetIndex).controller.removeHoverStyle(this.lastActive[0], this.lastActive[0]._datasetIndex, this.lastActive[0]._index);
						break;
					case 'label':
					case 'dataset':
						for (var i = 0; i < this.lastActive.length; i++) {
							if (this.lastActive[i])
								this.getDatasetMeta(this.lastActive[i]._datasetIndex).controller.removeHoverStyle(this.lastActive[i], this.lastActive[i]._datasetIndex, this.lastActive[i]._index);
						}
						break;
					default:
						// Don't change anything
				}
			}

			// Built in hover styling
			if (this.active.length && this.options.hover.mode) {
				switch (this.options.hover.mode) {
					case 'single':
						this.getDatasetMeta(this.active[0]._datasetIndex).controller.setHoverStyle(this.active[0]);
						break;
					case 'label':
					case 'dataset':
						for (var j = 0; j < this.active.length; j++) {
							if (this.active[j])
								this.getDatasetMeta(this.active[j]._datasetIndex).controller.setHoverStyle(this.active[j]);
						}
						break;
					default:
						// Don't change anything
				}
			}


			// Built in Tooltips
			if (this.options.tooltips.enabled || this.options.tooltips.custom) {

				// The usual updates
				this.tooltip.initialize();
				this.tooltip._active = this.tooltipActive;
				this.tooltip.update(true);
			}

			// Hover animations
			this.tooltip.pivot();

			if (!this.animating) {
				var changed;

				helpers.each(this.active, function(element, index) {
					if (element !== this.lastActive[index]) {
						changed = true;
					}
				}, this);

				helpers.each(this.tooltipActive, function(element, index) {
					if (element !== this.lastTooltipActive[index]) {
						changed = true;
					}
				}, this);

				// If entering, leaving, or changing elements, animate the change via pivot
				if ((this.lastActive.length !== this.active.length) ||
					(this.lastTooltipActive.length !== this.tooltipActive.length) ||
					changed) {

					this.stop();

					if (this.options.tooltips.enabled || this.options.tooltips.custom) {
						this.tooltip.update(true);
					}

					// We only need to render at this point. Updating will cause scales to be recomputed generating flicker & using more
					// memory than necessary.
					this.render(this.options.hover.animationDuration, true);
				}
			}

			// Remember Last Actives
			this.lastActive = this.active;
			this.lastTooltipActive = this.tooltipActive;
			return this;
		}
	});
};


/***/ }),
/* 238 */
/***/ (function(module, exports, __webpack_require__) {

"use strict";


module.exports = function(Chart) {

	var helpers = Chart.helpers;
	var noop = helpers.noop;

	// Base class for all dataset controllers (line, bar, etc)
	Chart.DatasetController = function(chart, datasetIndex) {
		this.initialize.call(this, chart, datasetIndex);
	};

	helpers.extend(Chart.DatasetController.prototype, {
		initialize: function(chart, datasetIndex) {
			this.chart = chart;
			this.index = datasetIndex;
			this.linkScales();
			this.addElements();
		},
		updateIndex: function(datasetIndex) {
			this.index = datasetIndex;
		},

		linkScales: function() {
			var meta = this.getMeta();
			var dataset = this.getDataset();

			if (meta.xAxisID === null) {
				meta.xAxisID = dataset.xAxisID || this.chart.options.scales.xAxes[0].id;
			}
			if (meta.yAxisID === null) {
				meta.yAxisID = dataset.yAxisID || this.chart.options.scales.yAxes[0].id;
			}
		},

		getDataset: function() {
			return this.chart.data.datasets[this.index];
		},

		getMeta: function() {
			return this.chart.getDatasetMeta(this.index);
		},

		getScaleForId: function(scaleID) {
			return this.chart.scales[scaleID];
		},

		reset: function() {
			this.update(true);
		},

		buildOrUpdateElements: function buildOrUpdateElements() {
			// Handle the number of data points changing
			var meta = this.getMeta(),
				md = meta.data,
				numData = this.getDataset().data.length,
				numMetaData = md.length;

			// Make sure that we handle number of datapoints changing
			if (numData < numMetaData) {
				// Remove excess bars for data points that have been removed
				md.splice(numData, numMetaData - numData);
			} else if (numData > numMetaData) {
				// Add new elements
				for (var index = numMetaData; index < numData; ++index) {
					this.addElementAndReset(index);
				}
			}
		},

		// Controllers should implement the following
		addElements: noop,
		addElementAndReset: noop,
		draw: noop,
		removeHoverStyle: noop,
		setHoverStyle: noop,
		update: noop
	});

	Chart.DatasetController.extend = helpers.inherits;
};

/***/ }),
/* 239 */
/***/ (function(module, exports, __webpack_require__) {

"use strict";


module.exports = function(Chart) {

  var helpers = Chart.helpers;

  Chart.elements = {};

  Chart.Element = function(configuration) {
    helpers.extend(this, configuration);
    this.initialize.apply(this, arguments);
  };
  helpers.extend(Chart.Element.prototype, {
    initialize: function() {
      this.hidden = false;
    },
    pivot: function() {
      if (!this._view) {
        this._view = helpers.clone(this._model);
      }
      this._start = helpers.clone(this._view);
      return this;
    },
    transition: function(ease) {
      if (!this._view) {
        this._view = helpers.clone(this._model);
      }

      // No animation -> No Transition
      if (ease === 1) {
        this._view = this._model;
        this._start = null;
        return this;
      }

      if (!this._start) {
        this.pivot();
      }

      helpers.each(this._model, function(value, key) {

        if (key[0] === '_' || !this._model.hasOwnProperty(key)) {
          // Only non-underscored properties
        }

        // Init if doesn't exist
        else if (!this._view.hasOwnProperty(key)) {
          if (typeof value === 'number' && !isNaN(this._view[key])) {
            this._view[key] = value * ease;
          } else {
            this._view[key] = value;
          }
        }

        // No unnecessary computations
        else if (value === this._view[key]) {
          // It's the same! Woohoo!
        }

        // Color transitions if possible
        else if (typeof value === 'string') {
          try {
            var color = helpers.color(this._start[key]).mix(helpers.color(this._model[key]), ease);
            this._view[key] = color.rgbString();
          } catch (err) {
            this._view[key] = value;
          }
        }
        // Number transitions
        else if (typeof value === 'number') {
          var startVal = this._start[key] !== undefined && isNaN(this._start[key]) === false ? this._start[key] : 0;
          this._view[key] = ((this._model[key] - startVal) * ease) + startVal;
        }
        // Everything else
        else {
          this._view[key] = value;
        }
      }, this);

      return this;
    },
    tooltipPosition: function() {
      return {
        x: this._model.x,
        y: this._model.y
      };
    },
    hasValue: function() {
      return helpers.isNumber(this._model.x) && helpers.isNumber(this._model.y);
    }
  });

  Chart.Element.extend = helpers.inherits;

};


/***/ }),
/* 240 */
/***/ (function(module, exports, __webpack_require__) {

"use strict";
/*global window: false */
/*global document: false */


var color = __webpack_require__(259);

module.exports = function(Chart) {

	//Global Chart helpers object for utility methods and classes
	var helpers = Chart.helpers = {};

	//-- Basic js utility methods
	helpers.each = function(loopable, callback, self, reverse) {
		// Check to see if null or undefined firstly.
		var i, len;
		if (helpers.isArray(loopable)) {
			len = loopable.length;
			if (reverse) {
				for (i = len - 1; i >= 0; i--) {
					callback.call(self, loopable[i], i);
				}
			} else {
				for (i = 0; i < len; i++) {
					callback.call(self, loopable[i], i);
				}
			}
		} else if (typeof loopable === 'object') {
			var keys = Object.keys(loopable);
			len = keys.length;
			for (i = 0; i < len; i++) {
				callback.call(self, loopable[keys[i]], keys[i]);
			}
		}
	};
	helpers.clone = function(obj) {
		var objClone = {};
		helpers.each(obj, function(value, key) {
			if (obj.hasOwnProperty(key)) {
				if (helpers.isArray(value)) {
					objClone[key] = value.slice(0);
				} else if (typeof value === 'object' && value !== null) {
					objClone[key] = helpers.clone(value);
				} else {
					objClone[key] = value;
				}
			}
		});
		return objClone;
	};
	helpers.extend = function(base) {
		var len = arguments.length;
		var additionalArgs = [];
		for (var i = 1; i < len; i++) {
			additionalArgs.push(arguments[i]);
		}
		helpers.each(additionalArgs, function(extensionObject) {
			helpers.each(extensionObject, function(value, key) {
				if (extensionObject.hasOwnProperty(key)) {
					base[key] = value;
				}
			});
		});
		return base;
	};
	// Need a special merge function to chart configs since they are now grouped
	helpers.configMerge = function(_base) {
		var base = helpers.clone(_base);
		helpers.each(Array.prototype.slice.call(arguments, 1), function(extension) {
			helpers.each(extension, function(value, key) {
				if (extension.hasOwnProperty(key)) {
					if (key === 'scales') {
						// Scale config merging is complex. Add out own function here for that
						base[key] = helpers.scaleMerge(base.hasOwnProperty(key) ? base[key] : {}, value);

					} else if (key === 'scale') {
						// Used in polar area & radar charts since there is only one scale
						base[key] = helpers.configMerge(base.hasOwnProperty(key) ? base[key] : {}, Chart.scaleService.getScaleDefaults(value.type), value);
					} else if (base.hasOwnProperty(key) && helpers.isArray(base[key]) && helpers.isArray(value)) {
						// In this case we have an array of objects replacing another array. Rather than doing a strict replace,
						// merge. This allows easy scale option merging
						var baseArray = base[key];

						helpers.each(value, function(valueObj, index) {

							if (index < baseArray.length) {
								if (typeof baseArray[index] === 'object' && baseArray[index] !== null && typeof valueObj === 'object' && valueObj !== null) {
									// Two objects are coming together. Do a merge of them.
									baseArray[index] = helpers.configMerge(baseArray[index], valueObj);
								} else {
									// Just overwrite in this case since there is nothing to merge
									baseArray[index] = valueObj;
								}
							} else {
								baseArray.push(valueObj); // nothing to merge
							}
						});

					} else if (base.hasOwnProperty(key) && typeof base[key] === "object" && base[key] !== null && typeof value === "object") {
						// If we are overwriting an object with an object, do a merge of the properties.
						base[key] = helpers.configMerge(base[key], value);

					} else {
						// can just overwrite the value in this case
						base[key] = value;
					}
				}
			});
		});

		return base;
	};
	helpers.extendDeep = function(_base) {
		return _extendDeep.apply(this, arguments);

		function _extendDeep(dst) {
			helpers.each(arguments, function(obj) {
				if (obj !== dst) {
					helpers.each(obj, function(value, key) {
						if (dst[key] && dst[key].constructor && dst[key].constructor === Object) {
							_extendDeep(dst[key], value);
						} else {
							dst[key] = value;
						}
					});
				}
			});
			return dst;
		}
	};
	helpers.scaleMerge = function(_base, extension) {
		var base = helpers.clone(_base);

		helpers.each(extension, function(value, key) {
			if (extension.hasOwnProperty(key)) {
				if (key === 'xAxes' || key === 'yAxes') {
					// These properties are arrays of items
					if (base.hasOwnProperty(key)) {
						helpers.each(value, function(valueObj, index) {
							var axisType = helpers.getValueOrDefault(valueObj.type, key === 'xAxes' ? 'category' : 'linear');
							var axisDefaults = Chart.scaleService.getScaleDefaults(axisType);
							if (index >= base[key].length || !base[key][index].type) {
								base[key].push(helpers.configMerge(axisDefaults, valueObj));
							} else if (valueObj.type && valueObj.type !== base[key][index].type) {
								// Type changed. Bring in the new defaults before we bring in valueObj so that valueObj can override the correct scale defaults
								base[key][index] = helpers.configMerge(base[key][index], axisDefaults, valueObj);
							} else {
								// Type is the same
								base[key][index] = helpers.configMerge(base[key][index], valueObj);
							}
						});
					} else {
						base[key] = [];
						helpers.each(value, function(valueObj) {
							var axisType = helpers.getValueOrDefault(valueObj.type, key === 'xAxes' ? 'category' : 'linear');
							base[key].push(helpers.configMerge(Chart.scaleService.getScaleDefaults(axisType), valueObj));
						});
					}
				} else if (base.hasOwnProperty(key) && typeof base[key] === "object" && base[key] !== null && typeof value === "object") {
					// If we are overwriting an object with an object, do a merge of the properties.
					base[key] = helpers.configMerge(base[key], value);

				} else {
					// can just overwrite the value in this case
					base[key] = value;
				}
			}
		});

		return base;
	};
	helpers.getValueAtIndexOrDefault = function(value, index, defaultValue) {
		if (value === undefined || value === null) {
			return defaultValue;
		}

		if (helpers.isArray(value)) {
			return index < value.length ? value[index] : defaultValue;
		}

		return value;
	};
	helpers.getValueOrDefault = function(value, defaultValue) {
		return value === undefined ? defaultValue : value;
	};
	helpers.indexOf = function(arrayToSearch, item) {
		if (Array.prototype.indexOf) {
			return arrayToSearch.indexOf(item);
		} else {
			for (var i = 0; i < arrayToSearch.length; i++) {
				if (arrayToSearch[i] === item)
					return i;
			}
			return -1;
		}
	};
	helpers.where = function(collection, filterCallback) {
		var filtered = [];

		helpers.each(collection, function(item) {
			if (filterCallback(item)) {
				filtered.push(item);
			}
		});

		return filtered;
	};
	helpers.findIndex = function(arrayToSearch, callback, thisArg) {
		var index = -1;
		if (Array.prototype.findIndex) {
			index = arrayToSearch.findIndex(callback, thisArg);
		} else {
			for (var i = 0; i < arrayToSearch.length; ++i) {
				thisArg = thisArg !== undefined ? thisArg : arrayToSearch;

				if (callback.call(thisArg, arrayToSearch[i], i, arrayToSearch)) {
					index = i;
					break;
				}
			}
		}

		return index;
	};
	helpers.findNextWhere = function(arrayToSearch, filterCallback, startIndex) {
		// Default to start of the array
		if (startIndex === undefined || startIndex === null) {
			startIndex = -1;
		}
		for (var i = startIndex + 1; i < arrayToSearch.length; i++) {
			var currentItem = arrayToSearch[i];
			if (filterCallback(currentItem)) {
				return currentItem;
			}
		}
	};
	helpers.findPreviousWhere = function(arrayToSearch, filterCallback, startIndex) {
		// Default to end of the array
		if (startIndex === undefined || startIndex === null) {
			startIndex = arrayToSearch.length;
		}
		for (var i = startIndex - 1; i >= 0; i--) {
			var currentItem = arrayToSearch[i];
			if (filterCallback(currentItem)) {
				return currentItem;
			}
		}
	};
	helpers.inherits = function(extensions) {
		//Basic javascript inheritance based on the model created in Backbone.js
		var parent = this;
		var ChartElement = (extensions && extensions.hasOwnProperty("constructor")) ? extensions.constructor : function() {
			return parent.apply(this, arguments);
		};

		var Surrogate = function() {
			this.constructor = ChartElement;
		};
		Surrogate.prototype = parent.prototype;
		ChartElement.prototype = new Surrogate();

		ChartElement.extend = helpers.inherits;

		if (extensions) {
			helpers.extend(ChartElement.prototype, extensions);
		}

		ChartElement.__super__ = parent.prototype;

		return ChartElement;
	};
	helpers.noop = function() {};
	helpers.uid = (function() {
		var id = 0;
		return function() {
			return id++;
		};
	})();
	helpers.warn = function(str) {
		//Method for warning of errors
		if (console && typeof console.warn === "function") {
			console.warn(str);
		}
	};
	//-- Math methods
	helpers.isNumber = function(n) {
		return !isNaN(parseFloat(n)) && isFinite(n);
	};
	helpers.almostEquals = function(x, y, epsilon) {
		return Math.abs(x - y) < epsilon;
	};
	helpers.max = function(array) {
		return array.reduce(function(max, value) {
			if (!isNaN(value)) {
				return Math.max(max, value);
			} else {
				return max;
			}
		}, Number.NEGATIVE_INFINITY);
	};
	helpers.min = function(array) {
		return array.reduce(function(min, value) {
			if (!isNaN(value)) {
				return Math.min(min, value);
			} else {
				return min;
			}
		}, Number.POSITIVE_INFINITY);
	};
	helpers.sign = function(x) {
		if (Math.sign) {
			return Math.sign(x);
		} else {
			x = +x; // convert to a number
			if (x === 0 || isNaN(x)) {
				return x;
			}
			return x > 0 ? 1 : -1;
		}
	};
	helpers.log10 = function(x) {
		if (Math.log10) {
			return Math.log10(x);
		} else {
			return Math.log(x) / Math.LN10;
		}
	};
	helpers.toRadians = function(degrees) {
		return degrees * (Math.PI / 180);
	};
	helpers.toDegrees = function(radians) {
		return radians * (180 / Math.PI);
	};
	// Gets the angle from vertical upright to the point about a centre.
	helpers.getAngleFromPoint = function(centrePoint, anglePoint) {
		var distanceFromXCenter = anglePoint.x - centrePoint.x,
			distanceFromYCenter = anglePoint.y - centrePoint.y,
			radialDistanceFromCenter = Math.sqrt(distanceFromXCenter * distanceFromXCenter + distanceFromYCenter * distanceFromYCenter);

		var angle = Math.atan2(distanceFromYCenter, distanceFromXCenter);

		if (angle < (-0.5 * Math.PI)) {
			angle += 2.0 * Math.PI; // make sure the returned angle is in the range of (-PI/2, 3PI/2]
		}

		return {
			angle: angle,
			distance: radialDistanceFromCenter
		};
	};
	helpers.aliasPixel = function(pixelWidth) {
		return (pixelWidth % 2 === 0) ? 0 : 0.5;
	};
	helpers.splineCurve = function(firstPoint, middlePoint, afterPoint, t) {
		//Props to Rob Spencer at scaled innovation for his post on splining between points
		//http://scaledinnovation.com/analytics/splines/aboutSplines.html

		// This function must also respect "skipped" points

		var previous = firstPoint.skip ? middlePoint : firstPoint,
			current = middlePoint,
			next = afterPoint.skip ? middlePoint : afterPoint;

		var d01 = Math.sqrt(Math.pow(current.x - previous.x, 2) + Math.pow(current.y - previous.y, 2));
		var d12 = Math.sqrt(Math.pow(next.x - current.x, 2) + Math.pow(next.y - current.y, 2));

		var s01 = d01 / (d01 + d12);
		var s12 = d12 / (d01 + d12);

		// If all points are the same, s01 & s02 will be inf
		s01 = isNaN(s01) ? 0 : s01;
		s12 = isNaN(s12) ? 0 : s12;

		var fa = t * s01; // scaling factor for triangle Ta
		var fb = t * s12;

		return {
			previous: {
				x: current.x - fa * (next.x - previous.x),
				y: current.y - fa * (next.y - previous.y)
			},
			next: {
				x: current.x + fb * (next.x - previous.x),
				y: current.y + fb * (next.y - previous.y)
			}
		};
	};
	helpers.nextItem = function(collection, index, loop) {
		if (loop) {
			return index >= collection.length - 1 ? collection[0] : collection[index + 1];
		}

		return index >= collection.length - 1 ? collection[collection.length - 1] : collection[index + 1];
	};
	helpers.previousItem = function(collection, index, loop) {
		if (loop) {
			return index <= 0 ? collection[collection.length - 1] : collection[index - 1];
		}
		return index <= 0 ? collection[0] : collection[index - 1];
	};
	// Implementation of the nice number algorithm used in determining where axis labels will go
	helpers.niceNum = function(range, round) {
		var exponent = Math.floor(helpers.log10(range));
		var fraction = range / Math.pow(10, exponent);
		var niceFraction;

		if (round) {
			if (fraction < 1.5) {
				niceFraction = 1;
			} else if (fraction < 3) {
				niceFraction = 2;
			} else if (fraction < 7) {
				niceFraction = 5;
			} else {
				niceFraction = 10;
			}
		} else {
			if (fraction <= 1.0) {
				niceFraction = 1;
			} else if (fraction <= 2) {
				niceFraction = 2;
			} else if (fraction <= 5) {
				niceFraction = 5;
			} else {
				niceFraction = 10;
			}
		}

		return niceFraction * Math.pow(10, exponent);
	};
	//Easing functions adapted from Robert Penner's easing equations
	//http://www.robertpenner.com/easing/
	var easingEffects = helpers.easingEffects = {
		linear: function(t) {
			return t;
		},
		easeInQuad: function(t) {
			return t * t;
		},
		easeOutQuad: function(t) {
			return -1 * t * (t - 2);
		},
		easeInOutQuad: function(t) {
			if ((t /= 1 / 2) < 1) {
				return 1 / 2 * t * t;
			}
			return -1 / 2 * ((--t) * (t - 2) - 1);
		},
		easeInCubic: function(t) {
			return t * t * t;
		},
		easeOutCubic: function(t) {
			return 1 * ((t = t / 1 - 1) * t * t + 1);
		},
		easeInOutCubic: function(t) {
			if ((t /= 1 / 2) < 1) {
				return 1 / 2 * t * t * t;
			}
			return 1 / 2 * ((t -= 2) * t * t + 2);
		},
		easeInQuart: function(t) {
			return t * t * t * t;
		},
		easeOutQuart: function(t) {
			return -1 * ((t = t / 1 - 1) * t * t * t - 1);
		},
		easeInOutQuart: function(t) {
			if ((t /= 1 / 2) < 1) {
				return 1 / 2 * t * t * t * t;
			}
			return -1 / 2 * ((t -= 2) * t * t * t - 2);
		},
		easeInQuint: function(t) {
			return 1 * (t /= 1) * t * t * t * t;
		},
		easeOutQuint: function(t) {
			return 1 * ((t = t / 1 - 1) * t * t * t * t + 1);
		},
		easeInOutQuint: function(t) {
			if ((t /= 1 / 2) < 1) {
				return 1 / 2 * t * t * t * t * t;
			}
			return 1 / 2 * ((t -= 2) * t * t * t * t + 2);
		},
		easeInSine: function(t) {
			return -1 * Math.cos(t / 1 * (Math.PI / 2)) + 1;
		},
		easeOutSine: function(t) {
			return 1 * Math.sin(t / 1 * (Math.PI / 2));
		},
		easeInOutSine: function(t) {
			return -1 / 2 * (Math.cos(Math.PI * t / 1) - 1);
		},
		easeInExpo: function(t) {
			return (t === 0) ? 1 : 1 * Math.pow(2, 10 * (t / 1 - 1));
		},
		easeOutExpo: function(t) {
			return (t === 1) ? 1 : 1 * (-Math.pow(2, -10 * t / 1) + 1);
		},
		easeInOutExpo: function(t) {
			if (t === 0) {
				return 0;
			}
			if (t === 1) {
				return 1;
			}
			if ((t /= 1 / 2) < 1) {
				return 1 / 2 * Math.pow(2, 10 * (t - 1));
			}
			return 1 / 2 * (-Math.pow(2, -10 * --t) + 2);
		},
		easeInCirc: function(t) {
			if (t >= 1) {
				return t;
			}
			return -1 * (Math.sqrt(1 - (t /= 1) * t) - 1);
		},
		easeOutCirc: function(t) {
			return 1 * Math.sqrt(1 - (t = t / 1 - 1) * t);
		},
		easeInOutCirc: function(t) {
			if ((t /= 1 / 2) < 1) {
				return -1 / 2 * (Math.sqrt(1 - t * t) - 1);
			}
			return 1 / 2 * (Math.sqrt(1 - (t -= 2) * t) + 1);
		},
		easeInElastic: function(t) {
			var s = 1.70158;
			var p = 0;
			var a = 1;
			if (t === 0) {
				return 0;
			}
			if ((t /= 1) === 1) {
				return 1;
			}
			if (!p) {
				p = 1 * 0.3;
			}
			if (a < Math.abs(1)) {
				a = 1;
				s = p / 4;
			} else {
				s = p / (2 * Math.PI) * Math.asin(1 / a);
			}
			return -(a * Math.pow(2, 10 * (t -= 1)) * Math.sin((t * 1 - s) * (2 * Math.PI) / p));
		},
		easeOutElastic: function(t) {
			var s = 1.70158;
			var p = 0;
			var a = 1;
			if (t === 0) {
				return 0;
			}
			if ((t /= 1) === 1) {
				return 1;
			}
			if (!p) {
				p = 1 * 0.3;
			}
			if (a < Math.abs(1)) {
				a = 1;
				s = p / 4;
			} else {
				s = p / (2 * Math.PI) * Math.asin(1 / a);
			}
			return a * Math.pow(2, -10 * t) * Math.sin((t * 1 - s) * (2 * Math.PI) / p) + 1;
		},
		easeInOutElastic: function(t) {
			var s = 1.70158;
			var p = 0;
			var a = 1;
			if (t === 0) {
				return 0;
			}
			if ((t /= 1 / 2) === 2) {
				return 1;
			}
			if (!p) {
				p = 1 * (0.3 * 1.5);
			}
			if (a < Math.abs(1)) {
				a = 1;
				s = p / 4;
			} else {
				s = p / (2 * Math.PI) * Math.asin(1 / a);
			}
			if (t < 1) {
				return -0.5 * (a * Math.pow(2, 10 * (t -= 1)) * Math.sin((t * 1 - s) * (2 * Math.PI) / p));
			}
			return a * Math.pow(2, -10 * (t -= 1)) * Math.sin((t * 1 - s) * (2 * Math.PI) / p) * 0.5 + 1;
		},
		easeInBack: function(t) {
			var s = 1.70158;
			return 1 * (t /= 1) * t * ((s + 1) * t - s);
		},
		easeOutBack: function(t) {
			var s = 1.70158;
			return 1 * ((t = t / 1 - 1) * t * ((s + 1) * t + s) + 1);
		},
		easeInOutBack: function(t) {
			var s = 1.70158;
			if ((t /= 1 / 2) < 1) {
				return 1 / 2 * (t * t * (((s *= (1.525)) + 1) * t - s));
			}
			return 1 / 2 * ((t -= 2) * t * (((s *= (1.525)) + 1) * t + s) + 2);
		},
		easeInBounce: function(t) {
			return 1 - easingEffects.easeOutBounce(1 - t);
		},
		easeOutBounce: function(t) {
			if ((t /= 1) < (1 / 2.75)) {
				return 1 * (7.5625 * t * t);
			} else if (t < (2 / 2.75)) {
				return 1 * (7.5625 * (t -= (1.5 / 2.75)) * t + 0.75);
			} else if (t < (2.5 / 2.75)) {
				return 1 * (7.5625 * (t -= (2.25 / 2.75)) * t + 0.9375);
			} else {
				return 1 * (7.5625 * (t -= (2.625 / 2.75)) * t + 0.984375);
			}
		},
		easeInOutBounce: function(t) {
			if (t < 1 / 2) {
				return easingEffects.easeInBounce(t * 2) * 0.5;
			}
			return easingEffects.easeOutBounce(t * 2 - 1) * 0.5 + 1 * 0.5;
		}
	};
	//Request animation polyfill - http://www.paulirish.com/2011/requestanimationframe-for-smart-animating/
	helpers.requestAnimFrame = (function() {
		return window.requestAnimationFrame ||
			window.webkitRequestAnimationFrame ||
			window.mozRequestAnimationFrame ||
			window.oRequestAnimationFrame ||
			window.msRequestAnimationFrame ||
			function(callback) {
				return window.setTimeout(callback, 1000 / 60);
			};
	})();
	helpers.cancelAnimFrame = (function() {
		return window.cancelAnimationFrame ||
			window.webkitCancelAnimationFrame ||
			window.mozCancelAnimationFrame ||
			window.oCancelAnimationFrame ||
			window.msCancelAnimationFrame ||
			function(callback) {
				return window.clearTimeout(callback, 1000 / 60);
			};
	})();
	//-- DOM methods
	helpers.getRelativePosition = function(evt, chart) {
		var mouseX, mouseY;
		var e = evt.originalEvent || evt,
			canvas = evt.currentTarget || evt.srcElement,
			boundingRect = canvas.getBoundingClientRect();

		if (e.touches && e.touches.length > 0) {
			mouseX = e.touches[0].clientX;
			mouseY = e.touches[0].clientY;

		} else {
			mouseX = e.clientX;
			mouseY = e.clientY;
		}

		// Scale mouse coordinates into canvas coordinates
		// by following the pattern laid out by 'jerryj' in the comments of
		// http://www.html5canvastutorials.com/advanced/html5-canvas-mouse-coordinates/
		var paddingLeft = parseFloat(helpers.getStyle(canvas, 'padding-left'));
		var paddingTop = parseFloat(helpers.getStyle(canvas, 'padding-top'));
		var paddingRight = parseFloat(helpers.getStyle(canvas, 'padding-right'));
		var paddingBottom = parseFloat(helpers.getStyle(canvas, 'padding-bottom'));
		var width = boundingRect.right - boundingRect.left - paddingLeft - paddingRight;
		var height = boundingRect.bottom - boundingRect.top - paddingTop - paddingBottom;

		// We divide by the current device pixel ratio, because the canvas is scaled up by that amount in each direction. However
		// the backend model is in unscaled coordinates. Since we are going to deal with our model coordinates, we go back here
		mouseX = Math.round((mouseX - boundingRect.left - paddingLeft) / (width) * canvas.width / chart.currentDevicePixelRatio);
		mouseY = Math.round((mouseY - boundingRect.top - paddingTop) / (height) * canvas.height / chart.currentDevicePixelRatio);

		return {
			x: mouseX,
			y: mouseY
		};

	};
	helpers.addEvent = function(node, eventType, method) {
		if (node.addEventListener) {
			node.addEventListener(eventType, method);
		} else if (node.attachEvent) {
			node.attachEvent("on" + eventType, method);
		} else {
			node["on" + eventType] = method;
		}
	};
	helpers.removeEvent = function(node, eventType, handler) {
		if (node.removeEventListener) {
			node.removeEventListener(eventType, handler, false);
		} else if (node.detachEvent) {
			node.detachEvent("on" + eventType, handler);
		} else {
			node["on" + eventType] = helpers.noop;
		}
	};
	helpers.bindEvents = function(chartInstance, arrayOfEvents, handler) {
		// Create the events object if it's not already present
		if (!chartInstance.events)
			chartInstance.events = {};

		helpers.each(arrayOfEvents, function(eventName) {
			chartInstance.events[eventName] = function() {
				handler.apply(chartInstance, arguments);
			};
			helpers.addEvent(chartInstance.chart.canvas, eventName, chartInstance.events[eventName]);
		});
	};
	helpers.unbindEvents = function(chartInstance, arrayOfEvents) {
		helpers.each(arrayOfEvents, function(handler, eventName) {
			helpers.removeEvent(chartInstance.chart.canvas, eventName, handler);
		});
	};

	// Private helper function to convert max-width/max-height values that may be percentages into a number
	function parseMaxStyle(styleValue, node, parentProperty) {
		var valueInPixels;
		if (typeof(styleValue) === 'string') {
			valueInPixels = parseInt(styleValue, 10);

			if (styleValue.indexOf('%') != -1) {
				// percentage * size in dimension
				valueInPixels = valueInPixels / 100 * node.parentNode[parentProperty];
			}
		} else {
			valueInPixels = styleValue;
		}

		return valueInPixels;
	}

	// Private helper to get a constraint dimension
	// @param domNode : the node to check the constraint on
	// @param maxStyle : the style that defines the maximum for the direction we are using (max-width / max-height)
	// @param percentageProperty : property of parent to use when calculating width as a percentage
	function getConstraintDimension(domNode, maxStyle, percentageProperty) {
		var constrainedDimension;
		var constrainedNode = document.defaultView.getComputedStyle(domNode)[maxStyle];
		var constrainedContainer = document.defaultView.getComputedStyle(domNode.parentNode)[maxStyle];
		var hasCNode = constrainedNode !== null && constrainedNode !== "none";
		var hasCContainer = constrainedContainer !== null && constrainedContainer !== "none";

		if (hasCNode || hasCContainer) {
			constrainedDimension = Math.min((hasCNode ? parseMaxStyle(constrainedNode, domNode, percentageProperty) : Number.POSITIVE_INFINITY), (hasCContainer ? parseMaxStyle(constrainedContainer, domNode.parentNode, percentageProperty) : Number.POSITIVE_INFINITY));
		}
		return constrainedDimension;
	}
	// returns Number or undefined if no constraint
	helpers.getConstraintWidth = function(domNode) {
		return getConstraintDimension(domNode, 'max-width', 'clientWidth');
	};
	// returns Number or undefined if no constraint
	helpers.getConstraintHeight = function(domNode) {
		return getConstraintDimension(domNode, 'max-height', 'clientHeight');
	};
	helpers.getMaximumWidth = function(domNode) {
		var container = domNode.parentNode;
		var padding = parseInt(helpers.getStyle(container, 'padding-left')) + parseInt(helpers.getStyle(container, 'padding-right'));

		var w = container.clientWidth - padding;
		var cw = helpers.getConstraintWidth(domNode);
		if (cw !== undefined) {
			w = Math.min(w, cw);
		}

		return w;
	};
	helpers.getMaximumHeight = function(domNode) {
		var container = domNode.parentNode;
		var padding = parseInt(helpers.getStyle(container, 'padding-top')) + parseInt(helpers.getStyle(container, 'padding-bottom'));

		var h = container.clientHeight - padding;
		var ch = helpers.getConstraintHeight(domNode);
		if (ch !== undefined) {
			h = Math.min(h, ch);
		}

		return h;
	};
	helpers.getStyle = function(el, property) {
		return el.currentStyle ?
			el.currentStyle[property] :
			document.defaultView.getComputedStyle(el, null).getPropertyValue(property);
	};
	helpers.retinaScale = function(chart) {
		var ctx = chart.ctx;
		var width = chart.canvas.width;
		var height = chart.canvas.height;
		var pixelRatio = chart.currentDevicePixelRatio = window.devicePixelRatio || 1;

		if (pixelRatio !== 1) {
			ctx.canvas.height = height * pixelRatio;
			ctx.canvas.width = width * pixelRatio;
			ctx.scale(pixelRatio, pixelRatio);

			// Store the device pixel ratio so that we can go backwards in `destroy`.
			// The devicePixelRatio changes with zoom, so there are no guarantees that it is the same
			// when destroy is called
			chart.originalDevicePixelRatio = chart.originalDevicePixelRatio || pixelRatio;
		}

		ctx.canvas.style.width = width + 'px';
		ctx.canvas.style.height = height + 'px';
	};
	//-- Canvas methods
	helpers.clear = function(chart) {
		chart.ctx.clearRect(0, 0, chart.width, chart.height);
	};
	helpers.fontString = function(pixelSize, fontStyle, fontFamily) {
		return fontStyle + " " + pixelSize + "px " + fontFamily;
	};
	helpers.longestText = function(ctx, font, arrayOfStrings, cache) {
		cache = cache || {};
		cache.data = cache.data || {};
		cache.garbageCollect = cache.garbageCollect || [];

		if (cache.font !== font) {
			cache.data = {};
			cache.garbageCollect = [];
			cache.font = font;
		}

		ctx.font = font;
		var longest = 0;
		helpers.each(arrayOfStrings, function(string) {
			// Undefined strings should not be measured
			if (string !== undefined && string !== null) {
				var textWidth = cache.data[string];
				if (!textWidth) {
					textWidth = cache.data[string] = ctx.measureText(string).width;
					cache.garbageCollect.push(string);
				}

				if (textWidth > longest) {
					longest = textWidth;
				}
			}
		});

		var gcLen = cache.garbageCollect.length / 2;
		if (gcLen > arrayOfStrings.length) {
			for (var i = 0; i < gcLen; i++) {
				delete cache.data[cache.garbageCollect[i]];
			}
			cache.garbageCollect.splice(0, gcLen);
		}

		return longest;
	};
	helpers.drawRoundedRectangle = function(ctx, x, y, width, height, radius) {
		ctx.beginPath();
		ctx.moveTo(x + radius, y);
		ctx.lineTo(x + width - radius, y);
		ctx.quadraticCurveTo(x + width, y, x + width, y + radius);
		ctx.lineTo(x + width, y + height - radius);
		ctx.quadraticCurveTo(x + width, y + height, x + width - radius, y + height);
		ctx.lineTo(x + radius, y + height);
		ctx.quadraticCurveTo(x, y + height, x, y + height - radius);
		ctx.lineTo(x, y + radius);
		ctx.quadraticCurveTo(x, y, x + radius, y);
		ctx.closePath();
	};
	helpers.color = function(c) {
		if (!color) {
			console.log('Color.js not found!');
			return c;
		}

		/* global CanvasGradient */
		if (c instanceof CanvasGradient) {
			return color(Chart.defaults.global.defaultColor);
		}

		return color(c);
	};
	helpers.addResizeListener = function(node, callback) {
		// Hide an iframe before the node
		var hiddenIframe = document.createElement('iframe');
		var hiddenIframeClass = 'chartjs-hidden-iframe';

		if (hiddenIframe.classlist) {
			// can use classlist
			hiddenIframe.classlist.add(hiddenIframeClass);
		} else {
			hiddenIframe.setAttribute('class', hiddenIframeClass);
		}

		// Set the style
		hiddenIframe.style.width = '100%';
		hiddenIframe.style.display = 'block';
		hiddenIframe.style.border = 0;
		hiddenIframe.style.height = 0;
		hiddenIframe.style.margin = 0;
		hiddenIframe.style.position = 'absolute';
		hiddenIframe.style.left = 0;
		hiddenIframe.style.right = 0;
		hiddenIframe.style.top = 0;
		hiddenIframe.style.bottom = 0;

		// Insert the iframe so that contentWindow is available
		node.insertBefore(hiddenIframe, node.firstChild);

		(hiddenIframe.contentWindow || hiddenIframe).onresize = function() {
			if (callback) {
				callback();
			}
		};
	};
	helpers.removeResizeListener = function(node) {
		var hiddenIframe = node.querySelector('.chartjs-hidden-iframe');

		// Remove the resize detect iframe
		if (hiddenIframe) {
			hiddenIframe.parentNode.removeChild(hiddenIframe);
		}
	};
	helpers.isArray = function(obj) {
		if (!Array.isArray) {
			return Object.prototype.toString.call(obj) === '[object Array]';
		}
		return Array.isArray(obj);
	};
	helpers.pushAllIfDefined = function(element, array) {
		if (typeof element === "undefined") {
			return;
		}

		if (helpers.isArray(element)) {
			array.push.apply(array, element);
		} else {
			array.push(element);
		}
	};
	helpers.callCallback = function(fn, args, _tArg) {
		if (fn && typeof fn.call === 'function') {
			fn.apply(_tArg, args);
		}
	};

};


/***/ }),
/* 241 */
/***/ (function(module, exports, __webpack_require__) {

"use strict";


module.exports = function() {

	//Occupy the global variable of Chart, and create a simple base class
	var Chart = function(context, config) {
		this.config = config;

		// Support a jQuery'd canvas element
		if (context.length && context[0].getContext) {
			context = context[0];
		}

		// Support a canvas domnode
		if (context.getContext) {
			context = context.getContext("2d");
		}

		this.ctx = context;
		this.canvas = context.canvas;

		// Figure out what the size of the chart will be.
		// If the canvas has a specified width and height, we use those else
		// we look to see if the canvas node has a CSS width and height.
		// If there is still no height, fill the parent container
		this.width = context.canvas.width || parseInt(Chart.helpers.getStyle(context.canvas, 'width')) || Chart.helpers.getMaximumWidth(context.canvas);
		this.height = context.canvas.height || parseInt(Chart.helpers.getStyle(context.canvas, 'height')) || Chart.helpers.getMaximumHeight(context.canvas);

		this.aspectRatio = this.width / this.height;

		if (isNaN(this.aspectRatio) || isFinite(this.aspectRatio) === false) {
			// If the canvas has no size, try and figure out what the aspect ratio will be.
			// Some charts prefer square canvases (pie, radar, etc). If that is specified, use that
			// else use the canvas default ratio of 2
			this.aspectRatio = config.aspectRatio !== undefined ? config.aspectRatio : 2;
		}

		// Store the original style of the element so we can set it back
		this.originalCanvasStyleWidth = context.canvas.style.width;
		this.originalCanvasStyleHeight = context.canvas.style.height;

		// High pixel density displays - multiply the size of the canvas height/width by the device pixel ratio, then scale.
		Chart.helpers.retinaScale(this);

		if (config) {
			this.controller = new Chart.Controller(this);
		}

		// Always bind this so that if the responsive state changes we still work
		var _this = this;
		Chart.helpers.addResizeListener(context.canvas.parentNode, function() {
			if (_this.controller && _this.controller.config.options.responsive) {
				_this.controller.resize();
			}
		});

		return this.controller ? this.controller : this;

	};

	//Globally expose the defaults to allow for user updating/changing
	Chart.defaults = {
		global: {
			responsive: true,
			responsiveAnimationDuration: 0,
			maintainAspectRatio: true,
			events: ["mousemove", "mouseout", "click", "touchstart", "touchmove"],
			hover: {
				onHover: null,
				mode: 'single',
				animationDuration: 400
			},
			onClick: null,
			defaultColor: 'rgba(0,0,0,0.1)',
			defaultFontColor: '#666',
			defaultFontFamily: "'Helvetica Neue', 'Helvetica', 'Arial', sans-serif",
			defaultFontSize: 12,
			defaultFontStyle: 'normal',
			showLines: true,

			// Element defaults defined in element extensions
			elements: {},

			// Legend callback string
			legendCallback: function(chart) {
				var text = [];
				text.push('<ul class="' + chart.id + '-legend">');
				for (var i = 0; i < chart.data.datasets.length; i++) {
					text.push('<li><span style="background-color:' + chart.data.datasets[i].backgroundColor + '"></span>');
					if (chart.data.datasets[i].label) {
						text.push(chart.data.datasets[i].label);
					}
					text.push('</li>');
				}
				text.push('</ul>');

				return text.join("");
			}
		}
	};

	return Chart;

};


/***/ }),
/* 242 */
/***/ (function(module, exports, __webpack_require__) {

"use strict";


module.exports = function(Chart) {

	var helpers = Chart.helpers;

	// The layout service is very self explanatory.  It's responsible for the layout within a chart.
	// Scales, Legends and Plugins all rely on the layout service and can easily register to be placed anywhere they need
	// It is this service's responsibility of carrying out that layout.
	Chart.layoutService = {
		defaults: {},

		// Register a box to a chartInstance. A box is simply a reference to an object that requires layout. eg. Scales, Legend, Plugins.
		addBox: function(chartInstance, box) {
			if (!chartInstance.boxes) {
				chartInstance.boxes = [];
			}
			chartInstance.boxes.push(box);
		},

		removeBox: function(chartInstance, box) {
			if (!chartInstance.boxes) {
				return;
			}
			chartInstance.boxes.splice(chartInstance.boxes.indexOf(box), 1);
		},

		// The most important function
		update: function(chartInstance, width, height) {

			if (!chartInstance) {
				return;
			}

			var xPadding = 0;
			var yPadding = 0;

			var leftBoxes = helpers.where(chartInstance.boxes, function(box) {
				return box.options.position === "left";
			});
			var rightBoxes = helpers.where(chartInstance.boxes, function(box) {
				return box.options.position === "right";
			});
			var topBoxes = helpers.where(chartInstance.boxes, function(box) {
				return box.options.position === "top";
			});
			var bottomBoxes = helpers.where(chartInstance.boxes, function(box) {
				return box.options.position === "bottom";
			});

			// Boxes that overlay the chartarea such as the radialLinear scale
			var chartAreaBoxes = helpers.where(chartInstance.boxes, function(box) {
				return box.options.position === "chartArea";
			});

			// Ensure that full width boxes are at the very top / bottom
			topBoxes.sort(function(a, b) {
				return (b.options.fullWidth ? 1 : 0) - (a.options.fullWidth ? 1 : 0);
			});
			bottomBoxes.sort(function(a, b) {
				return (a.options.fullWidth ? 1 : 0) - (b.options.fullWidth ? 1 : 0);
			});

			// Essentially we now have any number of boxes on each of the 4 sides.
			// Our canvas looks like the following.
			// The areas L1 and L2 are the left axes. R1 is the right axis, T1 is the top axis and
			// B1 is the bottom axis
			// There are also 4 quadrant-like locations (left to right instead of clockwise) reserved for chart overlays
			// These locations are single-box locations only, when trying to register a chartArea location that is already taken,
			// an error will be thrown.
			//
			// |----------------------------------------------------|
			// |                  T1 (Full Width)                   |
			// |----------------------------------------------------|
			// |    |    |                 T2                  |    |
			// |    |----|-------------------------------------|----|
			// |    |    | C1 |                           | C2 |    |
			// |    |    |----|                           |----|    |
			// |    |    |                                     |    |
			// | L1 | L2 |           ChartArea (C0)            | R1 |
			// |    |    |                                     |    |
			// |    |    |----|                           |----|    |
			// |    |    | C3 |                           | C4 |    |
			// |    |----|-------------------------------------|----|
			// |    |    |                 B1                  |    |
			// |----------------------------------------------------|
			// |                  B2 (Full Width)                   |
			// |----------------------------------------------------|
			//
			// What we do to find the best sizing, we do the following
			// 1. Determine the minimum size of the chart area.
			// 2. Split the remaining width equally between each vertical axis
			// 3. Split the remaining height equally between each horizontal axis
			// 4. Give each layout the maximum size it can be. The layout will return it's minimum size
			// 5. Adjust the sizes of each axis based on it's minimum reported size.
			// 6. Refit each axis
			// 7. Position each axis in the final location
			// 8. Tell the chart the final location of the chart area
			// 9. Tell any axes that overlay the chart area the positions of the chart area

			// Step 1
			var chartWidth = width - (2 * xPadding);
			var chartHeight = height - (2 * yPadding);
			var chartAreaWidth = chartWidth / 2; // min 50%
			var chartAreaHeight = chartHeight / 2; // min 50%

			// Step 2
			var verticalBoxWidth = (width - chartAreaWidth) / (leftBoxes.length + rightBoxes.length);

			// Step 3
			var horizontalBoxHeight = (height - chartAreaHeight) / (topBoxes.length + bottomBoxes.length);

			// Step 4
			var maxChartAreaWidth = chartWidth;
			var maxChartAreaHeight = chartHeight;
			var minBoxSizes = [];

			helpers.each(leftBoxes.concat(rightBoxes, topBoxes, bottomBoxes), getMinimumBoxSize);

			function getMinimumBoxSize(box) {
				var minSize;
				var isHorizontal = box.isHorizontal();

				if (isHorizontal) {
					minSize = box.update(box.options.fullWidth ? chartWidth : maxChartAreaWidth, horizontalBoxHeight);
					maxChartAreaHeight -= minSize.height;
				} else {
					minSize = box.update(verticalBoxWidth, chartAreaHeight);
					maxChartAreaWidth -= minSize.width;
				}

				minBoxSizes.push({
					horizontal: isHorizontal,
					minSize: minSize,
					box: box
				});
			}

			// At this point, maxChartAreaHeight and maxChartAreaWidth are the size the chart area could
			// be if the axes are drawn at their minimum sizes.

			// Steps 5 & 6
			var totalLeftBoxesWidth = xPadding;
			var totalRightBoxesWidth = xPadding;
			var totalTopBoxesHeight = yPadding;
			var totalBottomBoxesHeight = yPadding;

			// Update, and calculate the left and right margins for the horizontal boxes
			helpers.each(leftBoxes.concat(rightBoxes), fitBox);

			helpers.each(leftBoxes, function(box) {
				totalLeftBoxesWidth += box.width;
			});

			helpers.each(rightBoxes, function(box) {
				totalRightBoxesWidth += box.width;
			});

			// Set the Left and Right margins for the horizontal boxes
			helpers.each(topBoxes.concat(bottomBoxes), fitBox);

			// Function to fit a box
			function fitBox(box) {
				var minBoxSize = helpers.findNextWhere(minBoxSizes, function(minBoxSize) {
					return minBoxSize.box === box;
				});

				if (minBoxSize) {
					if (box.isHorizontal()) {
						var scaleMargin = {
							left: totalLeftBoxesWidth,
							right: totalRightBoxesWidth,
							top: 0,
							bottom: 0
						};

						// Don't use min size here because of label rotation. When the labels are rotated, their rotation highly depends
						// on the margin. Sometimes they need to increase in size slightly
						box.update(box.options.fullWidth ? chartWidth : maxChartAreaWidth, chartHeight / 2, scaleMargin);
					} else {
						box.update(minBoxSize.minSize.width, maxChartAreaHeight);
					}
				}
			}

			// Figure out how much margin is on the top and bottom of the vertical boxes
			helpers.each(topBoxes, function(box) {
				totalTopBoxesHeight += box.height;
			});

			helpers.each(bottomBoxes, function(box) {
				totalBottomBoxesHeight += box.height;
			});

			// Let the left layout know the final margin
			helpers.each(leftBoxes.concat(rightBoxes), finalFitVerticalBox);

			function finalFitVerticalBox(box) {
				var minBoxSize = helpers.findNextWhere(minBoxSizes, function(minBoxSize) {
					return minBoxSize.box === box;
				});

				var scaleMargin = {
					left: 0,
					right: 0,
					top: totalTopBoxesHeight,
					bottom: totalBottomBoxesHeight
				};

				if (minBoxSize) {
					box.update(minBoxSize.minSize.width, maxChartAreaHeight, scaleMargin);
				}
			}

			// Recalculate because the size of each layout might have changed slightly due to the margins (label rotation for instance)
			totalLeftBoxesWidth = xPadding;
			totalRightBoxesWidth = xPadding;
			totalTopBoxesHeight = yPadding;
			totalBottomBoxesHeight = yPadding;

			helpers.each(leftBoxes, function(box) {
				totalLeftBoxesWidth += box.width;
			});

			helpers.each(rightBoxes, function(box) {
				totalRightBoxesWidth += box.width;
			});

			helpers.each(topBoxes, function(box) {
				totalTopBoxesHeight += box.height;
			});
			helpers.each(bottomBoxes, function(box) {
				totalBottomBoxesHeight += box.height;
			});

			// Figure out if our chart area changed. This would occur if the dataset layout label rotation
			// changed due to the application of the margins in step 6. Since we can only get bigger, this is safe to do
			// without calling `fit` again
			var newMaxChartAreaHeight = height - totalTopBoxesHeight - totalBottomBoxesHeight;
			var newMaxChartAreaWidth = width - totalLeftBoxesWidth - totalRightBoxesWidth;

			if (newMaxChartAreaWidth !== maxChartAreaWidth || newMaxChartAreaHeight !== maxChartAreaHeight) {
				helpers.each(leftBoxes, function(box) {
					box.height = newMaxChartAreaHeight;
				});

				helpers.each(rightBoxes, function(box) {
					box.height = newMaxChartAreaHeight;
				});

				helpers.each(topBoxes, function(box) {
					if (!box.options.fullWidth) {
						box.width = newMaxChartAreaWidth;
					}
				});

				helpers.each(bottomBoxes, function(box) {
					if (!box.options.fullWidth) {
						box.width = newMaxChartAreaWidth;
					}
				});

				maxChartAreaHeight = newMaxChartAreaHeight;
				maxChartAreaWidth = newMaxChartAreaWidth;
			}

			// Step 7 - Position the boxes
			var left = xPadding;
			var top = yPadding;
			var right = 0;
			var bottom = 0;

			helpers.each(leftBoxes.concat(topBoxes), placeBox);

			// Account for chart width and height
			left += maxChartAreaWidth;
			top += maxChartAreaHeight;

			helpers.each(rightBoxes, placeBox);
			helpers.each(bottomBoxes, placeBox);

			function placeBox(box) {
				if (box.isHorizontal()) {
					box.left = box.options.fullWidth ? xPadding : totalLeftBoxesWidth;
					box.right = box.options.fullWidth ? width - xPadding : totalLeftBoxesWidth + maxChartAreaWidth;
					box.top = top;
					box.bottom = top + box.height;

					// Move to next point
					top = box.bottom;

				} else {

					box.left = left;
					box.right = left + box.width;
					box.top = totalTopBoxesHeight;
					box.bottom = totalTopBoxesHeight + maxChartAreaHeight;

					// Move to next point
					left = box.right;
				}
			}

			// Step 8
			chartInstance.chartArea = {
				left: totalLeftBoxesWidth,
				top: totalTopBoxesHeight,
				right: totalLeftBoxesWidth + maxChartAreaWidth,
				bottom: totalTopBoxesHeight + maxChartAreaHeight
			};

			// Step 9
			helpers.each(chartAreaBoxes, function(box) {
				box.left = chartInstance.chartArea.left;
				box.top = chartInstance.chartArea.top;
				box.right = chartInstance.chartArea.right;
				box.bottom = chartInstance.chartArea.bottom;

				box.update(maxChartAreaWidth, maxChartAreaHeight);
			});
		}
	};
};


/***/ }),
/* 243 */
/***/ (function(module, exports, __webpack_require__) {

"use strict";


module.exports = function(Chart) {

	var helpers = Chart.helpers;
	var noop = helpers.noop;

	Chart.defaults.global.legend = {

		display: true,
		position: 'top',
		fullWidth: true, // marks that this box should take the full width of the canvas (pushing down other boxes)
		reverse: false,

		// a callback that will handle
		onClick: function(e, legendItem) {
			var index = legendItem.datasetIndex;
			var ci = this.chart;
			var meta = ci.getDatasetMeta(index);

			// See controller.isDatasetVisible comment
			meta.hidden = meta.hidden === null? !ci.data.datasets[index].hidden : null;

			// We hid a dataset ... rerender the chart
			ci.update();
		},

		labels: {
			boxWidth: 40,
			padding: 10,
			// Generates labels shown in the legend
			// Valid properties to return:
			// text : text to display
			// fillStyle : fill of coloured box
			// strokeStyle: stroke of coloured box
			// hidden : if this legend item refers to a hidden item
			// lineCap : cap style for line
			// lineDash
			// lineDashOffset :
			// lineJoin :
			// lineWidth :
			generateLabels: function(chart) {
				var data = chart.data;
				return helpers.isArray(data.datasets) ? data.datasets.map(function(dataset, i) {
					return {
						text: dataset.label,
						fillStyle: dataset.backgroundColor,
						hidden: !chart.isDatasetVisible(i),
						lineCap: dataset.borderCapStyle,
						lineDash: dataset.borderDash,
						lineDashOffset: dataset.borderDashOffset,
						lineJoin: dataset.borderJoinStyle,
						lineWidth: dataset.borderWidth,
						strokeStyle: dataset.borderColor,

						// Below is extra data used for toggling the datasets
						datasetIndex: i
					};
				}, this) : [];
			}
		}
	};

	Chart.Legend = Chart.Element.extend({

		initialize: function(config) {
			helpers.extend(this, config);

			// Contains hit boxes for each dataset (in dataset order)
			this.legendHitBoxes = [];

			// Are we in doughnut mode which has a different data type
			this.doughnutMode = false;
		},

		// These methods are ordered by lifecyle. Utilities then follow.
		// Any function defined here is inherited by all legend types.
		// Any function can be extended by the legend type

		beforeUpdate: noop,
		update: function(maxWidth, maxHeight, margins) {

			// Update Lifecycle - Probably don't want to ever extend or overwrite this function ;)
			this.beforeUpdate();

			// Absorb the master measurements
			this.maxWidth = maxWidth;
			this.maxHeight = maxHeight;
			this.margins = margins;

			// Dimensions
			this.beforeSetDimensions();
			this.setDimensions();
			this.afterSetDimensions();
			// Labels
			this.beforeBuildLabels();
			this.buildLabels();
			this.afterBuildLabels();

			// Fit
			this.beforeFit();
			this.fit();
			this.afterFit();
			//
			this.afterUpdate();

			return this.minSize;
		},
		afterUpdate: noop,

		//

		beforeSetDimensions: noop,
		setDimensions: function() {
			// Set the unconstrained dimension before label rotation
			if (this.isHorizontal()) {
				// Reset position before calculating rotation
				this.width = this.maxWidth;
				this.left = 0;
				this.right = this.width;
			} else {
				this.height = this.maxHeight;

				// Reset position before calculating rotation
				this.top = 0;
				this.bottom = this.height;
			}

			// Reset padding
			this.paddingLeft = 0;
			this.paddingTop = 0;
			this.paddingRight = 0;
			this.paddingBottom = 0;

			// Reset minSize
			this.minSize = {
				width: 0,
				height: 0
			};
		},
		afterSetDimensions: noop,

		//

		beforeBuildLabels: noop,
		buildLabels: function() {
			this.legendItems = this.options.labels.generateLabels.call(this, this.chart);
			if(this.options.reverse){
				this.legendItems.reverse();
			}
		},
		afterBuildLabels: noop,

		//

		beforeFit: noop,
		fit: function() {
			var opts = this.options;
			var labelOpts = opts.labels;
			var display = opts.display;

			var ctx = this.ctx;

			var globalDefault = Chart.defaults.global,
				itemOrDefault = helpers.getValueOrDefault,
				fontSize = itemOrDefault(labelOpts.fontSize, globalDefault.defaultFontSize),
				fontStyle = itemOrDefault(labelOpts.fontStyle, globalDefault.defaultFontStyle),
				fontFamily = itemOrDefault(labelOpts.fontFamily, globalDefault.defaultFontFamily),
				labelFont = helpers.fontString(fontSize, fontStyle, fontFamily);

			// Reset hit boxes
			var hitboxes = this.legendHitBoxes = [];

			var minSize = this.minSize;
			var isHorizontal = this.isHorizontal();

			if (isHorizontal) {
				minSize.width = this.maxWidth; // fill all the width
				minSize.height = display ? 10 : 0;
			} else {
				minSize.width = display ? 10 : 0;
				minSize.height = this.maxHeight; // fill all the height
			}

			// Increase sizes here
			if (display) {
				if (isHorizontal) {
					// Labels

					// Width of each line of legend boxes. Labels wrap onto multiple lines when there are too many to fit on one
					var lineWidths = this.lineWidths = [0];
					var totalHeight = this.legendItems.length ? fontSize + (labelOpts.padding) : 0;

					ctx.textAlign = "left";
					ctx.textBaseline = 'top';
					ctx.font = labelFont;

					helpers.each(this.legendItems, function(legendItem, i) {
						var width = labelOpts.boxWidth + (fontSize / 2) + ctx.measureText(legendItem.text).width;
						if (lineWidths[lineWidths.length - 1] + width + labelOpts.padding >= this.width) {
							totalHeight += fontSize + (labelOpts.padding);
							lineWidths[lineWidths.length] = this.left;
						}

						// Store the hitbox width and height here. Final position will be updated in `draw`
						hitboxes[i] = {
							left: 0,
							top: 0,
							width: width,
							height: fontSize
						};

						lineWidths[lineWidths.length - 1] += width + labelOpts.padding;
					}, this);

					minSize.height += totalHeight;

				} else {
					// TODO vertical
				}
			}

			this.width = minSize.width;
			this.height = minSize.height;
		},
		afterFit: noop,

		// Shared Methods
		isHorizontal: function() {
			return this.options.position === "top" || this.options.position === "bottom";
		},

		// Actualy draw the legend on the canvas
		draw: function() {
			var opts = this.options;
			var labelOpts = opts.labels;
			var globalDefault = Chart.defaults.global,
				lineDefault = globalDefault.elements.line,
				legendWidth = this.width,
				lineWidths = this.lineWidths;

			if (opts.display) {
				var ctx = this.ctx,
					cursor = {
						x: this.left + ((legendWidth - lineWidths[0]) / 2),
						y: this.top + labelOpts.padding,
						line: 0
					},
					itemOrDefault = helpers.getValueOrDefault,
					fontColor = itemOrDefault(labelOpts.fontColor, globalDefault.defaultFontColor),
					fontSize = itemOrDefault(labelOpts.fontSize, globalDefault.defaultFontSize),
					fontStyle = itemOrDefault(labelOpts.fontStyle, globalDefault.defaultFontStyle),
					fontFamily = itemOrDefault(labelOpts.fontFamily, globalDefault.defaultFontFamily),
					labelFont = helpers.fontString(fontSize, fontStyle, fontFamily);

				// Horizontal
				if (this.isHorizontal()) {
					// Labels
					ctx.textAlign = "left";
					ctx.textBaseline = 'top';
					ctx.lineWidth = 0.5;
					ctx.strokeStyle = fontColor; // for strikethrough effect
					ctx.fillStyle = fontColor; // render in correct colour
					ctx.font = labelFont;

					var boxWidth = labelOpts.boxWidth,
						hitboxes = this.legendHitBoxes;

					helpers.each(this.legendItems, function(legendItem, i) {
						var textWidth = ctx.measureText(legendItem.text).width,
							width = boxWidth + (fontSize / 2) + textWidth,
							x = cursor.x,
							y = cursor.y;

						if (x + width >= legendWidth) {
							y = cursor.y += fontSize + (labelOpts.padding);
							cursor.line++;
							x = cursor.x = this.left + ((legendWidth - lineWidths[cursor.line]) / 2);
						}

						// Set the ctx for the box
						ctx.save();

						ctx.fillStyle = itemOrDefault(legendItem.fillStyle, globalDefault.defaultColor);
						ctx.lineCap = itemOrDefault(legendItem.lineCap, lineDefault.borderCapStyle);
						ctx.lineDashOffset = itemOrDefault(legendItem.lineDashOffset, lineDefault.borderDashOffset);
						ctx.lineJoin = itemOrDefault(legendItem.lineJoin, lineDefault.borderJoinStyle);
						ctx.lineWidth = itemOrDefault(legendItem.lineWidth, lineDefault.borderWidth);
						ctx.strokeStyle = itemOrDefault(legendItem.strokeStyle, globalDefault.defaultColor);

						if (ctx.setLineDash) {
							// IE 9 and 10 do not support line dash
							ctx.setLineDash(itemOrDefault(legendItem.lineDash, lineDefault.borderDash));
						}

						// Draw the box
						ctx.strokeRect(x, y, boxWidth, fontSize);
						ctx.fillRect(x, y, boxWidth, fontSize);

						ctx.restore();

						hitboxes[i].left = x;
						hitboxes[i].top = y;

						// Fill the actual label
						ctx.fillText(legendItem.text, boxWidth + (fontSize / 2) + x, y);

						if (legendItem.hidden) {
							// Strikethrough the text if hidden
							ctx.beginPath();
							ctx.lineWidth = 2;
							ctx.moveTo(boxWidth + (fontSize / 2) + x, y + (fontSize / 2));
							ctx.lineTo(boxWidth + (fontSize / 2) + x + textWidth, y + (fontSize / 2));
							ctx.stroke();
						}

						cursor.x += width + (labelOpts.padding);
					}, this);
				} else {

				}
			}
		},

		// Handle an event
		handleEvent: function(e) {
			var position = helpers.getRelativePosition(e, this.chart.chart),
				x = position.x,
				y = position.y,
				opts = this.options;

			if (x >= this.left && x <= this.right && y >= this.top && y <= this.bottom) {
				// See if we are touching one of the dataset boxes
				var lh = this.legendHitBoxes;
				for (var i = 0; i < lh.length; ++i) {
					var hitBox = lh[i];

					if (x >= hitBox.left && x <= hitBox.left + hitBox.width && y >= hitBox.top && y <= hitBox.top + hitBox.height) {
						// Touching an element
						if (opts.onClick) {
							opts.onClick.call(this, e, this.legendItems[i]);
						}
						break;
					}
				}
			}
		}
	});

};


/***/ }),
/* 244 */
/***/ (function(module, exports, __webpack_require__) {

"use strict";


module.exports = function(Chart) {
	var helpers = Chart.helpers;

	// Plugins are stored here
	Chart.plugins = [];
	Chart.pluginService = {
		// Register a new plugin
		register: function(plugin) {
			var p = Chart.plugins;
			if (p.indexOf(plugin) === -1) {
				p.push(plugin);
			}
		},

		// Remove a registered plugin
		remove: function(plugin) {
			var p = Chart.plugins;
			var idx = p.indexOf(plugin);
			if (idx !== -1) {
				p.splice(idx, 1);
			}
		},

		// Iterate over all plugins
		notifyPlugins: function(method, args, scope) {
			helpers.each(Chart.plugins, function(plugin) {
				if (plugin[method] && typeof plugin[method] === 'function') {
					plugin[method].apply(scope, args);
				}
			}, scope);
		}
	};

	var noop = helpers.noop;
	Chart.PluginBase = Chart.Element.extend({
		// Plugin methods. All functions are passed the chart instance

		// Called at start of chart init
		beforeInit: noop,

		// Called at end of chart init
		afterInit: noop,

		// Called at start of update
		beforeUpdate: noop,

		// Called at end of update
		afterUpdate: noop,

		// Called at start of draw
		beforeDraw: noop,

		// Called at end of draw
		afterDraw: noop,

		// Called during destroy
		destroy: noop,
	});
};


/***/ }),
/* 245 */
/***/ (function(module, exports, __webpack_require__) {

"use strict";


module.exports = function(Chart) {

	var helpers = Chart.helpers;

	Chart.defaults.scale = {
		display: true,
		position: "left",

		// grid line settings
		gridLines: {
			display: true,
			color: "rgba(0, 0, 0, 0.1)",
			lineWidth: 1,
			drawOnChartArea: true,
			drawTicks: true,
			tickMarkLength: 10,
			zeroLineWidth: 1,
			zeroLineColor: "rgba(0,0,0,0.25)",
			offsetGridLines: false
		},

		// scale label
		scaleLabel: {
			// actual label
			labelString: '',

			// display property
			display: false
		},

		// label settings
		ticks: {
			beginAtZero: false,
			maxRotation: 50,
			mirror: false,
			padding: 10,
			reverse: false,
			display: true,
			autoSkip: true,
			autoSkipPadding: 0,
			callback: function(value) {
				return '' + value;
			}
		}
	};

	Chart.Scale = Chart.Element.extend({

		// These methods are ordered by lifecyle. Utilities then follow.
		// Any function defined here is inherited by all scale types.
		// Any function can be extended by the scale type

		beforeUpdate: function() {
			helpers.callCallback(this.options.beforeUpdate, [this]);
		},
		update: function(maxWidth, maxHeight, margins) {

			// Update Lifecycle - Probably don't want to ever extend or overwrite this function ;)
			this.beforeUpdate();

			// Absorb the master measurements
			this.maxWidth = maxWidth;
			this.maxHeight = maxHeight;
			this.margins = helpers.extend({
				left: 0,
				right: 0,
				top: 0,
				bottom: 0
			}, margins);

			// Dimensions
			this.beforeSetDimensions();
			this.setDimensions();
			this.afterSetDimensions();

			// Data min/max
			this.beforeDataLimits();
			this.determineDataLimits();
			this.afterDataLimits();

			// Ticks
			this.beforeBuildTicks();
			this.buildTicks();
			this.afterBuildTicks();

			this.beforeTickToLabelConversion();
			this.convertTicksToLabels();
			this.afterTickToLabelConversion();

			// Tick Rotation
			this.beforeCalculateTickRotation();
			this.calculateTickRotation();
			this.afterCalculateTickRotation();
			// Fit
			this.beforeFit();
			this.fit();
			this.afterFit();
			//
			this.afterUpdate();

			return this.minSize;

		},
		afterUpdate: function() {
			helpers.callCallback(this.options.afterUpdate, [this]);
		},

		//

		beforeSetDimensions: function() {
			helpers.callCallback(this.options.beforeSetDimensions, [this]);
		},
		setDimensions: function() {
			// Set the unconstrained dimension before label rotation
			if (this.isHorizontal()) {
				// Reset position before calculating rotation
				this.width = this.maxWidth;
				this.left = 0;
				this.right = this.width;
			} else {
				this.height = this.maxHeight;

				// Reset position before calculating rotation
				this.top = 0;
				this.bottom = this.height;
			}

			// Reset padding
			this.paddingLeft = 0;
			this.paddingTop = 0;
			this.paddingRight = 0;
			this.paddingBottom = 0;
		},
		afterSetDimensions: function() {
			helpers.callCallback(this.options.afterSetDimensions, [this]);
		},

		// Data limits
		beforeDataLimits: function() {
			helpers.callCallback(this.options.beforeDataLimits, [this]);
		},
		determineDataLimits: helpers.noop,
		afterDataLimits: function() {
			helpers.callCallback(this.options.afterDataLimits, [this]);
		},

		//
		beforeBuildTicks: function() {
			helpers.callCallback(this.options.beforeBuildTicks, [this]);
		},
		buildTicks: helpers.noop,
		afterBuildTicks: function() {
			helpers.callCallback(this.options.afterBuildTicks, [this]);
		},

		beforeTickToLabelConversion: function() {
			helpers.callCallback(this.options.beforeTickToLabelConversion, [this]);
		},
		convertTicksToLabels: function() {
			// Convert ticks to strings
			this.ticks = this.ticks.map(function(numericalTick, index, ticks) {
					if (this.options.ticks.userCallback) {
						return this.options.ticks.userCallback(numericalTick, index, ticks);
					}
					return this.options.ticks.callback(numericalTick, index, ticks);
				},
				this);
		},
		afterTickToLabelConversion: function() {
			helpers.callCallback(this.options.afterTickToLabelConversion, [this]);
		},

		//

		beforeCalculateTickRotation: function() {
			helpers.callCallback(this.options.beforeCalculateTickRotation, [this]);
		},
		calculateTickRotation: function() {
			//Get the width of each grid by calculating the difference
			//between x offsets between 0 and 1.
			var tickFontSize = helpers.getValueOrDefault(this.options.ticks.fontSize, Chart.defaults.global.defaultFontSize);
			var tickFontStyle = helpers.getValueOrDefault(this.options.ticks.fontStyle, Chart.defaults.global.defaultFontStyle);
			var tickFontFamily = helpers.getValueOrDefault(this.options.ticks.fontFamily, Chart.defaults.global.defaultFontFamily);
			var tickLabelFont = helpers.fontString(tickFontSize, tickFontStyle, tickFontFamily);
			this.ctx.font = tickLabelFont;

			var firstWidth = this.ctx.measureText(this.ticks[0]).width;
			var lastWidth = this.ctx.measureText(this.ticks[this.ticks.length - 1]).width;
			var firstRotated;

			this.labelRotation = 0;
			this.paddingRight = 0;
			this.paddingLeft = 0;

			if (this.options.display) {
				if (this.isHorizontal()) {
					this.paddingRight = lastWidth / 2 + 3;
					this.paddingLeft = firstWidth / 2 + 3;

					if (!this.longestTextCache) {
						this.longestTextCache = {};
					}
					var originalLabelWidth = helpers.longestText(this.ctx, tickLabelFont, this.ticks, this.longestTextCache);
					var labelWidth = originalLabelWidth;
					var cosRotation;
					var sinRotation;

					// Allow 3 pixels x2 padding either side for label readability
					// only the index matters for a dataset scale, but we want a consistent interface between scales
					var tickWidth = this.getPixelForTick(1) - this.getPixelForTick(0) - 6;

					//Max label rotation can be set or default to 90 - also act as a loop counter
					while (labelWidth > tickWidth && this.labelRotation < this.options.ticks.maxRotation) {
						cosRotation = Math.cos(helpers.toRadians(this.labelRotation));
						sinRotation = Math.sin(helpers.toRadians(this.labelRotation));

						firstRotated = cosRotation * firstWidth;

						// We're right aligning the text now.
						if (firstRotated + tickFontSize / 2 > this.yLabelWidth) {
							this.paddingLeft = firstRotated + tickFontSize / 2;
						}

						this.paddingRight = tickFontSize / 2;

						if (sinRotation * originalLabelWidth > this.maxHeight) {
							// go back one step
							this.labelRotation--;
							break;
						}

						this.labelRotation++;
						labelWidth = cosRotation * originalLabelWidth;
					}
				}
			}

			if (this.margins) {
				this.paddingLeft = Math.max(this.paddingLeft - this.margins.left, 0);
				this.paddingRight = Math.max(this.paddingRight - this.margins.right, 0);
			}
		},
		afterCalculateTickRotation: function() {
			helpers.callCallback(this.options.afterCalculateTickRotation, [this]);
		},

		//

		beforeFit: function() {
			helpers.callCallback(this.options.beforeFit, [this]);
		},
		fit: function() {

			this.minSize = {
				width: 0,
				height: 0
			};

			var tickFontSize = helpers.getValueOrDefault(this.options.ticks.fontSize, Chart.defaults.global.defaultFontSize);
			var tickFontStyle = helpers.getValueOrDefault(this.options.ticks.fontStyle, Chart.defaults.global.defaultFontStyle);
			var tickFontFamily = helpers.getValueOrDefault(this.options.ticks.fontFamily, Chart.defaults.global.defaultFontFamily);
			var tickLabelFont = helpers.fontString(tickFontSize, tickFontStyle, tickFontFamily);

			var scaleLabelFontSize = helpers.getValueOrDefault(this.options.scaleLabel.fontSize, Chart.defaults.global.defaultFontSize);
			var scaleLabelFontStyle = helpers.getValueOrDefault(this.options.scaleLabel.fontStyle, Chart.defaults.global.defaultFontStyle);
			var scaleLabelFontFamily = helpers.getValueOrDefault(this.options.scaleLabel.fontFamily, Chart.defaults.global.defaultFontFamily);
			var scaleLabelFont = helpers.fontString(scaleLabelFontSize, scaleLabelFontStyle, scaleLabelFontFamily);

			// Width
			if (this.isHorizontal()) {
				// subtract the margins to line up with the chartArea if we are a full width scale
				this.minSize.width = this.isFullWidth() ? this.maxWidth - this.margins.left - this.margins.right : this.maxWidth;
			} else {
				this.minSize.width = this.options.gridLines.tickMarkLength;
			}

			// height
			if (this.isHorizontal()) {
				this.minSize.height = this.options.gridLines.tickMarkLength;
			} else {
				this.minSize.height = this.maxHeight; // fill all the height
			}

			// Are we showing a title for the scale?
			if (this.options.scaleLabel.display) {
				if (this.isHorizontal()) {
					this.minSize.height += (scaleLabelFontSize * 1.5);
				} else {
					this.minSize.width += (scaleLabelFontSize * 1.5);
				}
			}

			if (this.options.ticks.display && this.options.display) {
				// Don't bother fitting the ticks if we are not showing them
				if (!this.longestTextCache) {
					this.longestTextCache = {};
				}

				var largestTextWidth = helpers.longestText(this.ctx, tickLabelFont, this.ticks, this.longestTextCache);

				if (this.isHorizontal()) {
					// A horizontal axis is more constrained by the height.
					this.longestLabelWidth = largestTextWidth;

					// TODO - improve this calculation
					var labelHeight = (Math.sin(helpers.toRadians(this.labelRotation)) * this.longestLabelWidth) + 1.5 * tickFontSize;

					this.minSize.height = Math.min(this.maxHeight, this.minSize.height + labelHeight);
					this.ctx.font = tickLabelFont;

					var firstLabelWidth = this.ctx.measureText(this.ticks[0]).width;
					var lastLabelWidth = this.ctx.measureText(this.ticks[this.ticks.length - 1]).width;

					// Ensure that our ticks are always inside the canvas. When rotated, ticks are right aligned which means that the right padding is dominated
					// by the font height
					var cosRotation = Math.cos(helpers.toRadians(this.labelRotation));
					var sinRotation = Math.sin(helpers.toRadians(this.labelRotation));
					this.paddingLeft = this.labelRotation !== 0 ? (cosRotation * firstLabelWidth) + 3 : firstLabelWidth / 2 + 3; // add 3 px to move away from canvas edges
					this.paddingRight = this.labelRotation !== 0 ? (sinRotation * (tickFontSize / 2)) + 3 : lastLabelWidth / 2 + 3; // when rotated
				} else {
					// A vertical axis is more constrained by the width. Labels are the dominant factor here, so get that length first
					var maxLabelWidth = this.maxWidth - this.minSize.width;

					// Account for padding
					if (!this.options.ticks.mirror) {
						largestTextWidth += this.options.ticks.padding;
					}

					if (largestTextWidth < maxLabelWidth) {
						// We don't need all the room
						this.minSize.width += largestTextWidth;
					} else {
						// Expand to max size
						this.minSize.width = this.maxWidth;
					}

					this.paddingTop = tickFontSize / 2;
					this.paddingBottom = tickFontSize / 2;
				}
			}

			if (this.margins) {
				this.paddingLeft = Math.max(this.paddingLeft - this.margins.left, 0);
				this.paddingTop = Math.max(this.paddingTop - this.margins.top, 0);
				this.paddingRight = Math.max(this.paddingRight - this.margins.right, 0);
				this.paddingBottom = Math.max(this.paddingBottom - this.margins.bottom, 0);
			}

			this.width = this.minSize.width;
			this.height = this.minSize.height;

		},
		afterFit: function() {
			helpers.callCallback(this.options.afterFit, [this]);
		},

		// Shared Methods
		isHorizontal: function() {
			return this.options.position === "top" || this.options.position === "bottom";
		},
		isFullWidth: function() {
			return (this.options.fullWidth);
		},

		// Get the correct value. NaN bad inputs, If the value type is object get the x or y based on whether we are horizontal or not
		getRightValue: function getRightValue(rawValue) {
			// Null and undefined values first
			if (rawValue === null || typeof(rawValue) === 'undefined') {
				return NaN;
			}
			// isNaN(object) returns true, so make sure NaN is checking for a number
			if (typeof(rawValue) === 'number' && isNaN(rawValue)) {
				return NaN;
			}
			// If it is in fact an object, dive in one more level
			if (typeof(rawValue) === "object") {
				if (rawValue instanceof Date) {
					return rawValue;
				} else {
					return getRightValue(this.isHorizontal() ? rawValue.x : rawValue.y);
				}
			}

			// Value is good, return it
			return rawValue;
		},

		// Used to get the value to display in the tooltip for the data at the given index
		// function getLabelForIndex(index, datasetIndex)
		getLabelForIndex: helpers.noop,

		// Used to get data value locations.  Value can either be an index or a numerical value
		getPixelForValue: helpers.noop,

		// Used to get the data value from a given pixel. This is the inverse of getPixelForValue
		getValueForPixel: helpers.noop,

		// Used for tick location, should
		getPixelForTick: function(index, includeOffset) {
			if (this.isHorizontal()) {
				var innerWidth = this.width - (this.paddingLeft + this.paddingRight);
				var tickWidth = innerWidth / Math.max((this.ticks.length - ((this.options.gridLines.offsetGridLines) ? 0 : 1)), 1);
				var pixel = (tickWidth * index) + this.paddingLeft;

				if (includeOffset) {
					pixel += tickWidth / 2;
				}

				var finalVal = this.left + Math.round(pixel);
				finalVal += this.isFullWidth() ? this.margins.left : 0;
				return finalVal;
			} else {
				var innerHeight = this.height - (this.paddingTop + this.paddingBottom);
				return this.top + (index * (innerHeight / (this.ticks.length - 1)));
			}
		},

		// Utility for getting the pixel location of a percentage of scale
		getPixelForDecimal: function(decimal /*, includeOffset*/ ) {
			if (this.isHorizontal()) {
				var innerWidth = this.width - (this.paddingLeft + this.paddingRight);
				var valueOffset = (innerWidth * decimal) + this.paddingLeft;

				var finalVal = this.left + Math.round(valueOffset);
				finalVal += this.isFullWidth() ? this.margins.left : 0;
				return finalVal;
			} else {
				return this.top + (decimal * this.height);
			}
		},

		// Actualy draw the scale on the canvas
		// @param {rectangle} chartArea : the area of the chart to draw full grid lines on
		draw: function(chartArea) {
			if (this.options.display) {

				var setContextLineSettings;
				var isRotated = this.labelRotation !== 0;
				var skipRatio;
				var scaleLabelX;
				var scaleLabelY;
				var useAutoskipper = this.options.ticks.autoSkip;


				// figure out the maximum number of gridlines to show
				var maxTicks;

				if (this.options.ticks.maxTicksLimit) {
					maxTicks = this.options.ticks.maxTicksLimit;
				}

				var tickFontColor = helpers.getValueOrDefault(this.options.ticks.fontColor, Chart.defaults.global.defaultFontColor);
				var tickFontSize = helpers.getValueOrDefault(this.options.ticks.fontSize, Chart.defaults.global.defaultFontSize);
				var tickFontStyle = helpers.getValueOrDefault(this.options.ticks.fontStyle, Chart.defaults.global.defaultFontStyle);
				var tickFontFamily = helpers.getValueOrDefault(this.options.ticks.fontFamily, Chart.defaults.global.defaultFontFamily);
				var tickLabelFont = helpers.fontString(tickFontSize, tickFontStyle, tickFontFamily);
				var tl = this.options.gridLines.tickMarkLength;

				var scaleLabelFontColor = helpers.getValueOrDefault(this.options.scaleLabel.fontColor, Chart.defaults.global.defaultFontColor);
				var scaleLabelFontSize = helpers.getValueOrDefault(this.options.scaleLabel.fontSize, Chart.defaults.global.defaultFontSize);
				var scaleLabelFontStyle = helpers.getValueOrDefault(this.options.scaleLabel.fontStyle, Chart.defaults.global.defaultFontStyle);
				var scaleLabelFontFamily = helpers.getValueOrDefault(this.options.scaleLabel.fontFamily, Chart.defaults.global.defaultFontFamily);
				var scaleLabelFont = helpers.fontString(scaleLabelFontSize, scaleLabelFontStyle, scaleLabelFontFamily);

				var cosRotation = Math.cos(helpers.toRadians(this.labelRotation));
				var sinRotation = Math.sin(helpers.toRadians(this.labelRotation));
				var longestRotatedLabel = this.longestLabelWidth * cosRotation;
				var rotatedLabelHeight = tickFontSize * sinRotation;

				// Make sure we draw text in the correct color and font
				this.ctx.fillStyle = tickFontColor;

				if (this.isHorizontal()) {
					setContextLineSettings = true;
					var yTickStart = this.options.position === "bottom" ? this.top : this.bottom - tl;
					var yTickEnd = this.options.position === "bottom" ? this.top + tl : this.bottom;
					skipRatio = false;

					if (((longestRotatedLabel / 2) + this.options.ticks.autoSkipPadding) * this.ticks.length > (this.width - (this.paddingLeft + this.paddingRight))) {
						skipRatio = 1 + Math.floor((((longestRotatedLabel / 2) + this.options.ticks.autoSkipPadding) * this.ticks.length) / (this.width - (this.paddingLeft + this.paddingRight)));
					}

					// if they defined a max number of ticks,
					// increase skipRatio until that number is met
					if (maxTicks && this.ticks.length > maxTicks) {
						while (!skipRatio || this.ticks.length / (skipRatio || 1) > maxTicks) {
							if (!skipRatio) {
								skipRatio = 1;
							}
							skipRatio += 1;
						}
					}

					if (!useAutoskipper) {
						skipRatio = false;
					}

					helpers.each(this.ticks, function(label, index) {
						// Blank ticks
						var isLastTick = this.ticks.length === index + 1;

						// Since we always show the last tick,we need may need to hide the last shown one before
						var shouldSkip = (skipRatio > 1 && index % skipRatio > 0) || (index % skipRatio === 0 && index + skipRatio > this.ticks.length);
						if (shouldSkip && !isLastTick || (label === undefined || label === null)) {
							return;
						}
						var xLineValue = this.getPixelForTick(index); // xvalues for grid lines
						var xLabelValue = this.getPixelForTick(index, this.options.gridLines.offsetGridLines); // x values for ticks (need to consider offsetLabel option)

						if (this.options.gridLines.display) {
							if (index === (typeof this.zeroLineIndex !== 'undefined' ? this.zeroLineIndex : 0)) {
								// Draw the first index specially
								this.ctx.lineWidth = this.options.gridLines.zeroLineWidth;
								this.ctx.strokeStyle = this.options.gridLines.zeroLineColor;
								setContextLineSettings = true; // reset next time
							} else if (setContextLineSettings) {
								this.ctx.lineWidth = this.options.gridLines.lineWidth;
								this.ctx.strokeStyle = this.options.gridLines.color;
								setContextLineSettings = false;
							}

							xLineValue += helpers.aliasPixel(this.ctx.lineWidth);

							// Draw the label area
							this.ctx.beginPath();

							if (this.options.gridLines.drawTicks) {
								this.ctx.moveTo(xLineValue, yTickStart);
								this.ctx.lineTo(xLineValue, yTickEnd);
							}

							// Draw the chart area
							if (this.options.gridLines.drawOnChartArea) {
								this.ctx.moveTo(xLineValue, chartArea.top);
								this.ctx.lineTo(xLineValue, chartArea.bottom);
							}

							// Need to stroke in the loop because we are potentially changing line widths & colours
							this.ctx.stroke();
						}

						if (this.options.ticks.display) {
							this.ctx.save();
							this.ctx.translate(xLabelValue, (isRotated) ? this.top + 12 : this.options.position === "top" ? this.bottom - tl : this.top + tl);
							this.ctx.rotate(helpers.toRadians(this.labelRotation) * -1);
							this.ctx.font = tickLabelFont;
							this.ctx.textAlign = (isRotated) ? "right" : "center";
							this.ctx.textBaseline = (isRotated) ? "middle" : this.options.position === "top" ? "bottom" : "top";
							this.ctx.fillText(label, 0, 0);
							this.ctx.restore();
						}
					}, this);

					if (this.options.scaleLabel.display) {
						// Draw the scale label
						this.ctx.textAlign = "center";
						this.ctx.textBaseline = 'middle';
						this.ctx.fillStyle = scaleLabelFontColor; // render in correct colour
						this.ctx.font = scaleLabelFont;

						scaleLabelX = this.left + ((this.right - this.left) / 2); // midpoint of the width
						scaleLabelY = this.options.position === 'bottom' ? this.bottom - (scaleLabelFontSize / 2) : this.top + (scaleLabelFontSize / 2);

						this.ctx.fillText(this.options.scaleLabel.labelString, scaleLabelX, scaleLabelY);
					}

				} else {
					setContextLineSettings = true;
					var xTickStart = this.options.position === "right" ? this.left : this.right - 5;
					var xTickEnd = this.options.position === "right" ? this.left + 5 : this.right;

					helpers.each(this.ticks, function(label, index) {
						// If the callback returned a null or undefined value, do not draw this line
						if (label === undefined || label === null) {
							return;
						}

						var yLineValue = this.getPixelForTick(index); // xvalues for grid lines

						if (this.options.gridLines.display) {
							if (index === (typeof this.zeroLineIndex !== 'undefined' ? this.zeroLineIndex : 0)) {
								// Draw the first index specially
								this.ctx.lineWidth = this.options.gridLines.zeroLineWidth;
								this.ctx.strokeStyle = this.options.gridLines.zeroLineColor;
								setContextLineSettings = true; // reset next time
							} else if (setContextLineSettings) {
								this.ctx.lineWidth = this.options.gridLines.lineWidth;
								this.ctx.strokeStyle = this.options.gridLines.color;
								setContextLineSettings = false;
							}

							yLineValue += helpers.aliasPixel(this.ctx.lineWidth);

							// Draw the label area
							this.ctx.beginPath();

							if (this.options.gridLines.drawTicks) {
								this.ctx.moveTo(xTickStart, yLineValue);
								this.ctx.lineTo(xTickEnd, yLineValue);
							}

							// Draw the chart area
							if (this.options.gridLines.drawOnChartArea) {
								this.ctx.moveTo(chartArea.left, yLineValue);
								this.ctx.lineTo(chartArea.right, yLineValue);
							}

							// Need to stroke in the loop because we are potentially changing line widths & colours
							this.ctx.stroke();
						}

						if (this.options.ticks.display) {
							var xLabelValue;
							var yLabelValue = this.getPixelForTick(index, this.options.gridLines.offsetGridLines); // x values for ticks (need to consider offsetLabel option)

							this.ctx.save();

							if (this.options.position === "left") {
								if (this.options.ticks.mirror) {
									xLabelValue = this.right + this.options.ticks.padding;
									this.ctx.textAlign = "left";
								} else {
									xLabelValue = this.right - this.options.ticks.padding;
									this.ctx.textAlign = "right";
								}
							} else {
								// right side
								if (this.options.ticks.mirror) {
									xLabelValue = this.left - this.options.ticks.padding;
									this.ctx.textAlign = "right";
								} else {
									xLabelValue = this.left + this.options.ticks.padding;
									this.ctx.textAlign = "left";
								}
							}

							this.ctx.translate(xLabelValue, yLabelValue);
							this.ctx.rotate(helpers.toRadians(this.labelRotation) * -1);
							this.ctx.font = tickLabelFont;
							this.ctx.textBaseline = "middle";
							this.ctx.fillText(label, 0, 0);
							this.ctx.restore();
						}
					}, this);

					if (this.options.scaleLabel.display) {
						// Draw the scale label
						scaleLabelX = this.options.position === 'left' ? this.left + (scaleLabelFontSize / 2) : this.right - (scaleLabelFontSize / 2);
						scaleLabelY = this.top + ((this.bottom - this.top) / 2);
						var rotation = this.options.position === 'left' ? -0.5 * Math.PI : 0.5 * Math.PI;

						this.ctx.save();
						this.ctx.translate(scaleLabelX, scaleLabelY);
						this.ctx.rotate(rotation);
						this.ctx.textAlign = "center";
						this.ctx.fillStyle =scaleLabelFontColor; // render in correct colour
						this.ctx.font = scaleLabelFont;
						this.ctx.textBaseline = 'middle';
						this.ctx.fillText(this.options.scaleLabel.labelString, 0, 0);
						this.ctx.restore();
					}
				}

				// Draw the line at the edge of the axis
				this.ctx.lineWidth = this.options.gridLines.lineWidth;
				this.ctx.strokeStyle = this.options.gridLines.color;
				var x1 = this.left,
					x2 = this.right,
					y1 = this.top,
					y2 = this.bottom;

				if (this.isHorizontal()) {
					y1 = y2 = this.options.position === 'top' ? this.bottom : this.top;
					y1 += helpers.aliasPixel(this.ctx.lineWidth);
					y2 += helpers.aliasPixel(this.ctx.lineWidth);
				} else {
					x1 = x2 = this.options.position === 'left' ? this.right : this.left;
					x1 += helpers.aliasPixel(this.ctx.lineWidth);
					x2 += helpers.aliasPixel(this.ctx.lineWidth);
				}

				this.ctx.beginPath();
				this.ctx.moveTo(x1, y1);
				this.ctx.lineTo(x2, y2);
				this.ctx.stroke();
			}
		}
	});
};


/***/ }),
/* 246 */
/***/ (function(module, exports, __webpack_require__) {

"use strict";


module.exports = function(Chart) {

	var helpers = Chart.helpers;

	Chart.scaleService = {
		// Scale registration object. Extensions can register new scale types (such as log or DB scales) and then
		// use the new chart options to grab the correct scale
		constructors: {},
		// Use a registration function so that we can move to an ES6 map when we no longer need to support
		// old browsers

		// Scale config defaults
		defaults: {},
		registerScaleType: function(type, scaleConstructor, defaults) {
			this.constructors[type] = scaleConstructor;
			this.defaults[type] = helpers.clone(defaults);
		},
		getScaleConstructor: function(type) {
			return this.constructors.hasOwnProperty(type) ? this.constructors[type] : undefined;
		},
		getScaleDefaults: function(type) {
			// Return the scale defaults merged with the global settings so that we always use the latest ones
			return this.defaults.hasOwnProperty(type) ? helpers.scaleMerge(Chart.defaults.scale, this.defaults[type]) : {};
		},
		addScalesToLayout: function(chartInstance) {
			// Adds each scale to the chart.boxes array to be sized accordingly
			helpers.each(chartInstance.scales, function(scale) {
				Chart.layoutService.addBox(chartInstance, scale);
			});
		}
	};
};

/***/ }),
/* 247 */
/***/ (function(module, exports, __webpack_require__) {

"use strict";


module.exports = function(Chart) {

	var helpers = Chart.helpers;

	Chart.defaults.global.title = {
		display: false,
		position: 'top',
		fullWidth: true, // marks that this box should take the full width of the canvas (pushing down other boxes)

		fontStyle: 'bold',
		padding: 10,

		// actual title
		text: ''
	};

	var noop = helpers.noop;
	Chart.Title = Chart.Element.extend({

		initialize: function(config) {
			helpers.extend(this, config);
			this.options = helpers.configMerge(Chart.defaults.global.title, config.options);

			// Contains hit boxes for each dataset (in dataset order)
			this.legendHitBoxes = [];
		},

		// These methods are ordered by lifecyle. Utilities then follow.

		beforeUpdate: noop,
		update: function(maxWidth, maxHeight, margins) {

			// Update Lifecycle - Probably don't want to ever extend or overwrite this function ;)
			this.beforeUpdate();

			// Absorb the master measurements
			this.maxWidth = maxWidth;
			this.maxHeight = maxHeight;
			this.margins = margins;

			// Dimensions
			this.beforeSetDimensions();
			this.setDimensions();
			this.afterSetDimensions();
			// Labels
			this.beforeBuildLabels();
			this.buildLabels();
			this.afterBuildLabels();

			// Fit
			this.beforeFit();
			this.fit();
			this.afterFit();
			//
			this.afterUpdate();

			return this.minSize;

		},
		afterUpdate: noop,

		//

		beforeSetDimensions: noop,
		setDimensions: function() {
			// Set the unconstrained dimension before label rotation
			if (this.isHorizontal()) {
				// Reset position before calculating rotation
				this.width = this.maxWidth;
				this.left = 0;
				this.right = this.width;
			} else {
				this.height = this.maxHeight;

				// Reset position before calculating rotation
				this.top = 0;
				this.bottom = this.height;
			}

			// Reset padding
			this.paddingLeft = 0;
			this.paddingTop = 0;
			this.paddingRight = 0;
			this.paddingBottom = 0;

			// Reset minSize
			this.minSize = {
				width: 0,
				height: 0
			};
		},
		afterSetDimensions: noop,

		//

		beforeBuildLabels: noop,
		buildLabels: noop,
		afterBuildLabels: noop,

		//

		beforeFit: noop,
		fit: function() {

			var ctx = this.ctx,
				valueOrDefault = helpers.getValueOrDefault,
				opts = this.options,
				globalDefaults = Chart.defaults.global,
				display = opts.display,
				fontSize = valueOrDefault(opts.fontSize, globalDefaults.defaultFontSize),
				minSize = this.minSize;

			if (this.isHorizontal()) {
				minSize.width = this.maxWidth; // fill all the width
				minSize.height = display ? fontSize + (opts.padding * 2) : 0;
			} else {
				minSize.width = display ? fontSize + (opts.padding * 2) : 0;
				minSize.height = this.maxHeight; // fill all the height
			}

			this.width = minSize.width;
			this.height = minSize.height;

		},
		afterFit: noop,

		// Shared Methods
		isHorizontal: function() {
			var pos = this.options.position;
			return pos === "top" || pos === "bottom";
		},

		// Actualy draw the title block on the canvas
		draw: function() {
			var ctx = this.ctx,
				valueOrDefault = helpers.getValueOrDefault,
				opts = this.options,
				globalDefaults = Chart.defaults.global;

			if (opts.display) {
				var fontSize = valueOrDefault(opts.fontSize, globalDefaults.defaultFontSize),
					fontStyle = valueOrDefault(opts.fontStyle, globalDefaults.defaultFontStyle),
					fontFamily = valueOrDefault(opts.fontFamily, globalDefaults.defaultFontFamily),
					titleFont = helpers.fontString(fontSize, fontStyle, fontFamily),
					rotation = 0,
					titleX, 
					titleY;

				ctx.fillStyle = valueOrDefault(opts.fontColor, globalDefaults.defaultFontColor); // render in correct colour
				ctx.font = titleFont;

				// Horizontal
				if (this.isHorizontal()) {
					titleX = this.left + ((this.right - this.left) / 2); // midpoint of the width
					titleY = this.top + ((this.bottom - this.top) / 2); // midpoint of the height
				} else {
					titleX = opts.position === 'left' ? this.left + (fontSize / 2) : this.right - (fontSize / 2);
					titleY = this.top + ((this.bottom - this.top) / 2);
					rotation = Math.PI * (opts.position === 'left' ? -0.5 : 0.5);
				}

				ctx.save();
				ctx.translate(titleX, titleY);
				ctx.rotate(rotation);
				ctx.textAlign = 'center';
				ctx.textBaseline = 'middle';
				ctx.fillText(opts.text, 0, 0);
				ctx.restore();
			}
		}
	});
};

/***/ }),
/* 248 */
/***/ (function(module, exports, __webpack_require__) {

"use strict";


module.exports = function(Chart) {

	var helpers = Chart.helpers;

	Chart.defaults.global.tooltips = {
		enabled: true,
		custom: null,
		mode: 'single',
		backgroundColor: "rgba(0,0,0,0.8)",
		titleFontStyle: "bold",
		titleSpacing: 2,
		titleMarginBottom: 6,
		titleColor: "#fff",
		titleAlign: "left",
		bodySpacing: 2,
		bodyColor: "#fff",
		bodyAlign: "left",
		footerFontStyle: "bold",
		footerSpacing: 2,
		footerMarginTop: 6,
		footerColor: "#fff",
		footerAlign: "left",
		yPadding: 6,
		xPadding: 6,
		yAlign : 'center',
		xAlign : 'center',
		caretSize: 5,
		cornerRadius: 6,
		multiKeyBackground: '#fff',
		callbacks: {
			// Args are: (tooltipItems, data)
			beforeTitle: helpers.noop,
			title: function(tooltipItems, data) {
				// Pick first xLabel for now
				var title = '';

				if (tooltipItems.length > 0) {
					if (tooltipItems[0].xLabel) {
						title = tooltipItems[0].xLabel;
					} else if (data.labels.length > 0 && tooltipItems[0].index < data.labels.length) {
						title = data.labels[tooltipItems[0].index];
					}
				}

				return title;
			},
			afterTitle: helpers.noop,

			// Args are: (tooltipItems, data)
			beforeBody: helpers.noop,

			// Args are: (tooltipItem, data)
			beforeLabel: helpers.noop,
			label: function(tooltipItem, data) {
				var datasetLabel = data.datasets[tooltipItem.datasetIndex].label || '';
				return datasetLabel + ': ' + tooltipItem.yLabel;
			},
			afterLabel: helpers.noop,

			// Args are: (tooltipItems, data)
			afterBody: helpers.noop,

			// Args are: (tooltipItems, data)
			beforeFooter: helpers.noop,
			footer: helpers.noop,
			afterFooter: helpers.noop
		}
	};

	// Helper to push or concat based on if the 2nd parameter is an array or not
	function pushOrConcat(base, toPush) {
		if (toPush) {
			if (helpers.isArray(toPush)) {
				base = base.concat(toPush);
			} else {
				base.push(toPush);
			}
		}

		return base;
	}

	Chart.Tooltip = Chart.Element.extend({
		initialize: function() {
			var options = this._options;
			helpers.extend(this, {
				_model: {
					// Positioning
					xPadding: options.tooltips.xPadding,
					yPadding: options.tooltips.yPadding,
					xAlign : options.tooltips.yAlign,
					yAlign : options.tooltips.xAlign,

					// Body
					bodyColor: options.tooltips.bodyColor,
					_bodyFontFamily: helpers.getValueOrDefault(options.tooltips.bodyFontFamily, Chart.defaults.global.defaultFontFamily),
					_bodyFontStyle: helpers.getValueOrDefault(options.tooltips.bodyFontStyle, Chart.defaults.global.defaultFontStyle),
					_bodyAlign: options.tooltips.bodyAlign,
					bodyFontSize: helpers.getValueOrDefault(options.tooltips.bodyFontSize, Chart.defaults.global.defaultFontSize),
					bodySpacing: options.tooltips.bodySpacing,

					// Title
					titleColor: options.tooltips.titleColor,
					_titleFontFamily: helpers.getValueOrDefault(options.tooltips.titleFontFamily, Chart.defaults.global.defaultFontFamily),
					_titleFontStyle: helpers.getValueOrDefault(options.tooltips.titleFontStyle, Chart.defaults.global.defaultFontStyle),
					titleFontSize: helpers.getValueOrDefault(options.tooltips.titleFontSize, Chart.defaults.global.defaultFontSize),
					_titleAlign: options.tooltips.titleAlign,
					titleSpacing: options.tooltips.titleSpacing,
					titleMarginBottom: options.tooltips.titleMarginBottom,

					// Footer
					footerColor: options.tooltips.footerColor,
					_footerFontFamily: helpers.getValueOrDefault(options.tooltips.footerFontFamily, Chart.defaults.global.defaultFontFamily),
					_footerFontStyle: helpers.getValueOrDefault(options.tooltips.footerFontStyle, Chart.defaults.global.defaultFontStyle),
					footerFontSize: helpers.getValueOrDefault(options.tooltips.footerFontSize, Chart.defaults.global.defaultFontSize),
					_footerAlign: options.tooltips.footerAlign,
					footerSpacing: options.tooltips.footerSpacing,
					footerMarginTop: options.tooltips.footerMarginTop,

					// Appearance
					caretSize: options.tooltips.caretSize,
					cornerRadius: options.tooltips.cornerRadius,
					backgroundColor: options.tooltips.backgroundColor,
					opacity: 0,
					legendColorBackground: options.tooltips.multiKeyBackground
				}
			});
		},

		// Get the title
		// Args are: (tooltipItem, data)
		getTitle: function() {
			var beforeTitle = this._options.tooltips.callbacks.beforeTitle.apply(this, arguments),
				title = this._options.tooltips.callbacks.title.apply(this, arguments),
				afterTitle = this._options.tooltips.callbacks.afterTitle.apply(this, arguments);

			var lines = [];
			lines = pushOrConcat(lines, beforeTitle);
			lines = pushOrConcat(lines, title);
			lines = pushOrConcat(lines, afterTitle);

			return lines;
		},

		// Args are: (tooltipItem, data)
		getBeforeBody: function() {
			var lines = this._options.tooltips.callbacks.beforeBody.apply(this, arguments);
			return helpers.isArray(lines) ? lines : lines !== undefined ? [lines] : [];
		},

		// Args are: (tooltipItem, data)
		getBody: function(tooltipItems, data) {
			var lines = [];

			helpers.each(tooltipItems, function(bodyItem) {
				helpers.pushAllIfDefined(this._options.tooltips.callbacks.beforeLabel.call(this, bodyItem, data), lines);
				helpers.pushAllIfDefined(this._options.tooltips.callbacks.label.call(this, bodyItem, data), lines);
				helpers.pushAllIfDefined(this._options.tooltips.callbacks.afterLabel.call(this, bodyItem, data), lines);
			}, this);

			return lines;
		},

		// Args are: (tooltipItem, data)
		getAfterBody: function() {
			var lines = this._options.tooltips.callbacks.afterBody.apply(this, arguments);
			return helpers.isArray(lines) ? lines : lines !== undefined ? [lines] : [];
		},

		// Get the footer and beforeFooter and afterFooter lines
		// Args are: (tooltipItem, data)
		getFooter: function() {
			var beforeFooter = this._options.tooltips.callbacks.beforeFooter.apply(this, arguments);
			var footer = this._options.tooltips.callbacks.footer.apply(this, arguments);
			var afterFooter = this._options.tooltips.callbacks.afterFooter.apply(this, arguments);

			var lines = [];
			lines = pushOrConcat(lines, beforeFooter);
			lines = pushOrConcat(lines, footer);
			lines = pushOrConcat(lines, afterFooter);

			return lines;
		},

		getAveragePosition: function(elements) {

			if (!elements.length) {
				return false;
			}

			var xPositions = [];
			var yPositions = [];

			helpers.each(elements, function(el) {
				if (el) {
					var pos = el.tooltipPosition();
					xPositions.push(pos.x);
					yPositions.push(pos.y);
				}
			});

			var x = 0,
				y = 0;
			for (var i = 0; i < xPositions.length; i++) {
				x += xPositions[i];
				y += yPositions[i];
			}

			return {
				x: Math.round(x / xPositions.length),
				y: Math.round(y / xPositions.length)
			};

		},

		update: function(changed) {
			if (this._active.length) {
				this._model.opacity = 1;

				var element = this._active[0],
					labelColors = [],
					tooltipPosition;

				var tooltipItems = [];

				if (this._options.tooltips.mode === 'single') {
					var yScale = element._yScale || element._scale; // handle radar || polarArea charts
					tooltipItems.push({
						xLabel: element._xScale ? element._xScale.getLabelForIndex(element._index, element._datasetIndex) : '',
						yLabel: yScale ? yScale.getLabelForIndex(element._index, element._datasetIndex) : '',
						index: element._index,
						datasetIndex: element._datasetIndex
					});
					tooltipPosition = this.getAveragePosition(this._active);
				} else {
					helpers.each(this._data.datasets, function(dataset, datasetIndex) {
						if (!this._chartInstance.isDatasetVisible(datasetIndex)) {
							return;
						}

						var meta = this._chartInstance.getDatasetMeta(datasetIndex);
						var currentElement = meta.data[element._index];
						if (currentElement) {
							var yScale = element._yScale || element._scale; // handle radar || polarArea charts

							tooltipItems.push({
								xLabel: currentElement._xScale ? currentElement._xScale.getLabelForIndex(currentElement._index, currentElement._datasetIndex) : '',
								yLabel: yScale ? yScale.getLabelForIndex(currentElement._index, currentElement._datasetIndex) : '',
								index: element._index,
								datasetIndex: datasetIndex
							});
						}
					}, this);

					helpers.each(this._active, function(active) {
						if (active) {
							labelColors.push({
								borderColor: active._view.borderColor,
								backgroundColor: active._view.backgroundColor
							});
						}
					}, null);

					tooltipPosition = this.getAveragePosition(this._active);
				}

				// Build the Text Lines
				helpers.extend(this._model, {
					title: this.getTitle(tooltipItems, this._data),
					beforeBody: this.getBeforeBody(tooltipItems, this._data),
					body: this.getBody(tooltipItems, this._data),
					afterBody: this.getAfterBody(tooltipItems, this._data),
					footer: this.getFooter(tooltipItems, this._data)
				});

				helpers.extend(this._model, {
					x: Math.round(tooltipPosition.x),
					y: Math.round(tooltipPosition.y),
					caretPadding: helpers.getValueOrDefault(tooltipPosition.padding, 2),
					labelColors: labelColors
				});

				// We need to determine alignment of
				var tooltipSize = this.getTooltipSize(this._model);
				this.determineAlignment(tooltipSize); // Smart Tooltip placement to stay on the canvas

				helpers.extend(this._model, this.getBackgroundPoint(this._model, tooltipSize));
			} else {
				this._model.opacity = 0;
			}

			if (changed && this._options.tooltips.custom) {
				this._options.tooltips.custom.call(this, this._model);
			}

			return this;
		},
		getTooltipSize: function getTooltipSize(vm) {
			var ctx = this._chart.ctx;

			var size = {
				height: vm.yPadding * 2, // Tooltip Padding
				width: 0
			};
			var combinedBodyLength = vm.body.length + vm.beforeBody.length + vm.afterBody.length;

			size.height += vm.title.length * vm.titleFontSize; // Title Lines
			size.height += (vm.title.length - 1) * vm.titleSpacing; // Title Line Spacing
			size.height += vm.title.length ? vm.titleMarginBottom : 0; // Title's bottom Margin
			size.height += combinedBodyLength * vm.bodyFontSize; // Body Lines
			size.height += combinedBodyLength ? (combinedBodyLength - 1) * vm.bodySpacing : 0; // Body Line Spacing
			size.height += vm.footer.length ? vm.footerMarginTop : 0; // Footer Margin
			size.height += vm.footer.length * (vm.footerFontSize); // Footer Lines
			size.height += vm.footer.length ? (vm.footer.length - 1) * vm.footerSpacing : 0; // Footer Line Spacing

			// Width
			ctx.font = helpers.fontString(vm.titleFontSize, vm._titleFontStyle, vm._titleFontFamily);
			helpers.each(vm.title, function(line) {
				size.width = Math.max(size.width, ctx.measureText(line).width);
			});

			ctx.font = helpers.fontString(vm.bodyFontSize, vm._bodyFontStyle, vm._bodyFontFamily);
			helpers.each(vm.beforeBody.concat(vm.afterBody), function(line) {
				size.width = Math.max(size.width, ctx.measureText(line).width);
			});
			helpers.each(vm.body, function(line) {
				size.width = Math.max(size.width, ctx.measureText(line).width + (this._options.tooltips.mode !== 'single' ? (vm.bodyFontSize + 2) : 0));
			}, this);

			ctx.font = helpers.fontString(vm.footerFontSize, vm._footerFontStyle, vm._footerFontFamily);
			helpers.each(vm.footer, function(line) {
				size.width = Math.max(size.width, ctx.measureText(line).width);
			});
			size.width += 2 * vm.xPadding;

			return size;
		},
		determineAlignment: function determineAlignment(size) {
			if (this._model.y < size.height) {
				this._model.yAlign = 'top';
			} else if (this._model.y > (this._chart.height - size.height)) {
				this._model.yAlign = 'bottom';
			}

			var lf, rf; // functions to determine left, right alignment
			var olf, orf; // functions to determine if left/right alignment causes tooltip to go outside chart
			var yf; // function to get the y alignment if the tooltip goes outside of the left or right edges
			var _this = this;
			var midX = (this._chartInstance.chartArea.left + this._chartInstance.chartArea.right) / 2;
			var midY = (this._chartInstance.chartArea.top + this._chartInstance.chartArea.bottom) / 2;

			if (this._model.yAlign === 'center') {
				lf = function(x) {
					return x <= midX;
				};
				rf = function(x) {
					return x > midX;
				};
			} else {
				lf = function(x) {
					return x <= (size.width / 2);
				};
				rf = function(x) {
					return x >= (_this._chart.width - (size.width / 2));
				};
			}

			olf = function(x) {
				return x + size.width > _this._chart.width;
			};
			orf = function(x) {
				return x - size.width < 0;
			};
			yf = function(y) {
				return y <= midY ? 'top' : 'bottom';
			};

			if (lf(this._model.x)) {
				this._model.xAlign = 'left';

				// Is tooltip too wide and goes over the right side of the chart.?
				if (olf(this._model.x)) {
					this._model.xAlign = 'center';
					this._model.yAlign = yf(this._model.y);
				}
			} else if (rf(this._model.x)) {
				this._model.xAlign = 'right';

				// Is tooltip too wide and goes outside left edge of canvas?
				if (orf(this._model.x)) {
					this._model.xAlign = 'center';
					this._model.yAlign = yf(this._model.y);
				}
			}
		},
		getBackgroundPoint: function getBackgroundPoint(vm, size) {
			// Background Position
			var pt = {
				x: vm.x,
				y: vm.y
			};

			if (vm.xAlign === 'right') {
				pt.x -= size.width;
			} else if (vm.xAlign === 'center') {
				pt.x -= (size.width / 2);
			}

			if (vm.yAlign === 'top') {
				pt.y += vm.caretPadding + vm.caretSize;
			} else if (vm.yAlign === 'bottom') {
				pt.y -= size.height + vm.caretPadding + vm.caretSize;
			} else {
				pt.y -= (size.height / 2);
			}

			if (vm.yAlign === 'center') {
				if (vm.xAlign === 'left') {
					pt.x += vm.caretPadding + vm.caretSize;
				} else if (vm.xAlign === 'right') {
					pt.x -= vm.caretPadding + vm.caretSize;
				}
			} else {
				if (vm.xAlign === 'left') {
					pt.x -= vm.cornerRadius + vm.caretPadding;
				} else if (vm.xAlign === 'right') {
					pt.x += vm.cornerRadius + vm.caretPadding;
				}
			}

			return pt;
		},
		drawCaret: function drawCaret(tooltipPoint, size, opacity, caretPadding) {
			var vm = this._view;
			var ctx = this._chart.ctx;
			var x1, x2, x3;
			var y1, y2, y3;

			if (vm.yAlign === 'center') {
				// Left or right side
				if (vm.xAlign === 'left') {
					x1 = tooltipPoint.x;
					x2 = x1 - vm.caretSize;
					x3 = x1;
				} else {
					x1 = tooltipPoint.x + size.width;
					x2 = x1 + vm.caretSize;
					x3 = x1;
				}

				y2 = tooltipPoint.y + (size.height / 2);
				y1 = y2 - vm.caretSize;
				y3 = y2 + vm.caretSize;
			} else {
				if (vm.xAlign === 'left') {
					x1 = tooltipPoint.x + vm.cornerRadius;
					x2 = x1 + vm.caretSize;
					x3 = x2 + vm.caretSize;
				} else if (vm.xAlign === 'right') {
					x1 = tooltipPoint.x + size.width - vm.cornerRadius;
					x2 = x1 - vm.caretSize;
					x3 = x2 - vm.caretSize;
				} else {
					x2 = tooltipPoint.x + (size.width / 2);
					x1 = x2 - vm.caretSize;
					x3 = x2 + vm.caretSize;
				}

				if (vm.yAlign === 'top') {
					y1 = tooltipPoint.y;
					y2 = y1 - vm.caretSize;
					y3 = y1;
				} else {
					y1 = tooltipPoint.y + size.height;
					y2 = y1 + vm.caretSize;
					y3 = y1;
				}
			}

			var bgColor = helpers.color(vm.backgroundColor);
			ctx.fillStyle = bgColor.alpha(opacity * bgColor.alpha()).rgbString();
			ctx.beginPath();
			ctx.moveTo(x1, y1);
			ctx.lineTo(x2, y2);
			ctx.lineTo(x3, y3);
			ctx.closePath();
			ctx.fill();
		},
		drawTitle: function drawTitle(pt, vm, ctx, opacity) {
			if (vm.title.length) {
				ctx.textAlign = vm._titleAlign;
				ctx.textBaseline = "top";

				var titleColor = helpers.color(vm.titleColor);
				ctx.fillStyle = titleColor.alpha(opacity * titleColor.alpha()).rgbString();
				ctx.font = helpers.fontString(vm.titleFontSize, vm._titleFontStyle, vm._titleFontFamily);

				helpers.each(vm.title, function(title, i) {
					ctx.fillText(title, pt.x, pt.y);
					pt.y += vm.titleFontSize + vm.titleSpacing; // Line Height and spacing

					if (i + 1 === vm.title.length) {
						pt.y += vm.titleMarginBottom - vm.titleSpacing; // If Last, add margin, remove spacing
					}
				});
			}
		},
		drawBody: function drawBody(pt, vm, ctx, opacity) {
			ctx.textAlign = vm._bodyAlign;
			ctx.textBaseline = "top";

			var bodyColor = helpers.color(vm.bodyColor);
			ctx.fillStyle = bodyColor.alpha(opacity * bodyColor.alpha()).rgbString();
			ctx.font = helpers.fontString(vm.bodyFontSize, vm._bodyFontStyle, vm._bodyFontFamily);

			// Before Body
			helpers.each(vm.beforeBody, function(beforeBody) {
				ctx.fillText(beforeBody, pt.x, pt.y);
				pt.y += vm.bodyFontSize + vm.bodySpacing;
			});

			helpers.each(vm.body, function(body, i) {
				// Draw Legend-like boxes if needed
				if (this._options.tooltips.mode !== 'single') {
					// Fill a white rect so that colours merge nicely if the opacity is < 1
					ctx.fillStyle = helpers.color(vm.legendColorBackground).alpha(opacity).rgbaString();
					ctx.fillRect(pt.x, pt.y, vm.bodyFontSize, vm.bodyFontSize);

					// Border
					ctx.strokeStyle = helpers.color(vm.labelColors[i].borderColor).alpha(opacity).rgbaString();
					ctx.strokeRect(pt.x, pt.y, vm.bodyFontSize, vm.bodyFontSize);

					// Inner square
					ctx.fillStyle = helpers.color(vm.labelColors[i].backgroundColor).alpha(opacity).rgbaString();
					ctx.fillRect(pt.x + 1, pt.y + 1, vm.bodyFontSize - 2, vm.bodyFontSize - 2);

					ctx.fillStyle = helpers.color(vm.bodyColor).alpha(opacity).rgbaString(); // Return fill style for text
				}

				// Body Line
				ctx.fillText(body, pt.x + (this._options.tooltips.mode !== 'single' ? (vm.bodyFontSize + 2) : 0), pt.y);

				pt.y += vm.bodyFontSize + vm.bodySpacing;
			}, this);

			// After Body
			helpers.each(vm.afterBody, function(afterBody) {
				ctx.fillText(afterBody, pt.x, pt.y);
				pt.y += vm.bodyFontSize;
			});

			pt.y -= vm.bodySpacing; // Remove last body spacing
		},
		drawFooter: function drawFooter(pt, vm, ctx, opacity) {
			if (vm.footer.length) {
				pt.y += vm.footerMarginTop;

				ctx.textAlign = vm._footerAlign;
				ctx.textBaseline = "top";

				var footerColor = helpers.color(vm.footerColor);
				ctx.fillStyle = footerColor.alpha(opacity * footerColor.alpha()).rgbString();
				ctx.font = helpers.fontString(vm.footerFontSize, vm._footerFontStyle, vm._footerFontFamily);

				helpers.each(vm.footer, function(footer) {
					ctx.fillText(footer, pt.x, pt.y);
					pt.y += vm.footerFontSize + vm.footerSpacing;
				});
			}
		},
		draw: function draw() {
			var ctx = this._chart.ctx;
			var vm = this._view;

			if (vm.opacity === 0) {
				return;
			}

			var caretPadding = vm.caretPadding;
			var tooltipSize = this.getTooltipSize(vm);
			var pt = {
				x: vm.x,
				y: vm.y
			};

			// IE11/Edge does not like very small opacities, so snap to 0
			var opacity = Math.abs(vm.opacity < 1e-3) ? 0 : vm.opacity;

			if (this._options.tooltips.enabled) {
				// Draw Background
				var bgColor = helpers.color(vm.backgroundColor);
				ctx.fillStyle = bgColor.alpha(opacity * bgColor.alpha()).rgbString();
				helpers.drawRoundedRectangle(ctx, pt.x, pt.y, tooltipSize.width, tooltipSize.height, vm.cornerRadius);
				ctx.fill();

				// Draw Caret
				this.drawCaret(pt, tooltipSize, opacity, caretPadding);

				// Draw Title, Body, and Footer
				pt.x += vm.xPadding;
				pt.y += vm.yPadding;

				// Titles
				this.drawTitle(pt, vm, ctx, opacity);

				// Body
				this.drawBody(pt, vm, ctx, opacity);

				// Footer
				this.drawFooter(pt, vm, ctx, opacity);
			}
		}
	});
};


/***/ }),
/* 249 */
/***/ (function(module, exports, __webpack_require__) {

"use strict";


module.exports = function(Chart, moment) {

  var helpers = Chart.helpers,
    globalOpts = Chart.defaults.global;

  globalOpts.elements.arc = {
    backgroundColor: globalOpts.defaultColor,
    borderColor: "#fff",
    borderWidth: 2
  };

  Chart.elements.Arc = Chart.Element.extend({
    inLabelRange: function(mouseX) {
      var vm = this._view;

      if (vm) {
        return (Math.pow(mouseX - vm.x, 2) < Math.pow(vm.radius + vm.hoverRadius, 2));
      } else {
        return false;
      }
    },
    inRange: function(chartX, chartY) {
      var vm = this._view;

      if (vm) {
        var pointRelativePosition = helpers.getAngleFromPoint(vm, {
            x: chartX,
            y: chartY
          }),
          angle = pointRelativePosition.angle,
          distance = pointRelativePosition.distance;

        //Sanitise angle range
        var startAngle = vm.startAngle;
        var endAngle = vm.endAngle;
        while (endAngle < startAngle) {
          endAngle += 2.0 * Math.PI;
        }
        while (angle > endAngle) {
          angle -= 2.0 * Math.PI;
        }
        while (angle < startAngle) {
          angle += 2.0 * Math.PI;
        }

        //Check if within the range of the open/close angle
        var betweenAngles = (angle >= startAngle && angle <= endAngle),
          withinRadius = (distance >= vm.innerRadius && distance <= vm.outerRadius);

        return (betweenAngles && withinRadius);
      } else {
        return false;
      }
    },
    tooltipPosition: function() {
      var vm = this._view;

      var centreAngle = vm.startAngle + ((vm.endAngle - vm.startAngle) / 2),
        rangeFromCentre = (vm.outerRadius - vm.innerRadius) / 2 + vm.innerRadius;
      return {
        x: vm.x + (Math.cos(centreAngle) * rangeFromCentre),
        y: vm.y + (Math.sin(centreAngle) * rangeFromCentre)
      };
    },
    draw: function() {

      var ctx = this._chart.ctx,
        vm = this._view,
        sA = vm.startAngle,
        eA = vm.endAngle;

      ctx.beginPath();

      ctx.arc(vm.x, vm.y, vm.outerRadius, sA, eA);
      ctx.arc(vm.x, vm.y, vm.innerRadius, eA, sA, true);

      ctx.closePath();
      ctx.strokeStyle = vm.borderColor;
      ctx.lineWidth = vm.borderWidth;

      ctx.fillStyle = vm.backgroundColor;

      ctx.fill();
      ctx.lineJoin = 'bevel';

      if (vm.borderWidth) {
        ctx.stroke();
      }
    }
  });
};


/***/ }),
/* 250 */
/***/ (function(module, exports, __webpack_require__) {

"use strict";


module.exports = function(Chart) {

	var helpers = Chart.helpers;

	Chart.defaults.global.elements.line = {
		tension: 0.4,
		backgroundColor: Chart.defaults.global.defaultColor,
		borderWidth: 3,
		borderColor: Chart.defaults.global.defaultColor,
		borderCapStyle: 'butt',
		borderDash: [],
		borderDashOffset: 0.0,
		borderJoinStyle: 'miter',
		fill: true // do we fill in the area between the line and its base axis
	};

	Chart.elements.Line = Chart.Element.extend({
		lineToNextPoint: function(previousPoint, point, nextPoint, skipHandler, previousSkipHandler) {
			var ctx = this._chart.ctx;

			if (point._view.skip) {
				skipHandler.call(this, previousPoint, point, nextPoint);
			} else if (previousPoint._view.skip) {
				previousSkipHandler.call(this, previousPoint, point, nextPoint);
			} else if (point._view.tension === 0) {
				ctx.lineTo(point._view.x, point._view.y);
			} else {
				// Line between points
				ctx.bezierCurveTo(
					previousPoint._view.controlPointNextX,
					previousPoint._view.controlPointNextY,
					point._view.controlPointPreviousX,
					point._view.controlPointPreviousY,
					point._view.x,
					point._view.y
				);
			}
		},

		draw: function() {
			var _this = this;

			var vm = this._view;
			var ctx = this._chart.ctx;
			var first = this._children[0];
			var last = this._children[this._children.length - 1];

			function loopBackToStart(drawLineToCenter) {
				if (!first._view.skip && !last._view.skip) {
					// Draw a bezier line from last to first
					ctx.bezierCurveTo(
						last._view.controlPointNextX,
						last._view.controlPointNextY,
						first._view.controlPointPreviousX,
						first._view.controlPointPreviousY,
						first._view.x,
						first._view.y
					);
				} else if (drawLineToCenter) {
					// Go to center
					ctx.lineTo(_this._view.scaleZero.x, _this._view.scaleZero.y);
				}
			}

			ctx.save();

			// If we had points and want to fill this line, do so.
			if (this._children.length > 0 && vm.fill) {
				// Draw the background first (so the border is always on top)
				ctx.beginPath();

				helpers.each(this._children, function(point, index) {
					var previous = helpers.previousItem(this._children, index);
					var next = helpers.nextItem(this._children, index);

					// First point moves to it's starting position no matter what
					if (index === 0) {
						if (this._loop) {
							ctx.moveTo(vm.scaleZero.x, vm.scaleZero.y);
						} else {
							ctx.moveTo(point._view.x, vm.scaleZero);
						}

						if (point._view.skip) {
							if (!this._loop) {
								ctx.moveTo(next._view.x, this._view.scaleZero);
							}
						} else {
							ctx.lineTo(point._view.x, point._view.y);
						}
					} else {
						this.lineToNextPoint(previous, point, next, function(previousPoint, point, nextPoint) {
							if (this._loop) {
								// Go to center
								ctx.lineTo(this._view.scaleZero.x, this._view.scaleZero.y);
							} else {
								ctx.lineTo(previousPoint._view.x, this._view.scaleZero);
								ctx.moveTo(nextPoint._view.x, this._view.scaleZero);
							}
						}, function(previousPoint, point) {
							// If we skipped the last point, draw a line to ourselves so that the fill is nice
							ctx.lineTo(point._view.x, point._view.y);
						});
					}
				}, this);

				// For radial scales, loop back around to the first point
				if (this._loop) {
					loopBackToStart(true);
				} else {
					//Round off the line by going to the base of the chart, back to the start, then fill.
					ctx.lineTo(this._children[this._children.length - 1]._view.x, vm.scaleZero);
					ctx.lineTo(this._children[0]._view.x, vm.scaleZero);
				}

				ctx.fillStyle = vm.backgroundColor || Chart.defaults.global.defaultColor;
				ctx.closePath();
				ctx.fill();
			}

			// Now draw the line between all the points with any borders
			ctx.lineCap = vm.borderCapStyle || Chart.defaults.global.elements.line.borderCapStyle;

			// IE 9 and 10 do not support line dash
			if (ctx.setLineDash) {
				ctx.setLineDash(vm.borderDash || Chart.defaults.global.elements.line.borderDash);
			}

			ctx.lineDashOffset = vm.borderDashOffset || Chart.defaults.global.elements.line.borderDashOffset;
			ctx.lineJoin = vm.borderJoinStyle || Chart.defaults.global.elements.line.borderJoinStyle;
			ctx.lineWidth = vm.borderWidth || Chart.defaults.global.elements.line.borderWidth;
			ctx.strokeStyle = vm.borderColor || Chart.defaults.global.defaultColor;
			ctx.beginPath();

			helpers.each(this._children, function(point, index) {
				var previous = helpers.previousItem(this._children, index);
				var next = helpers.nextItem(this._children, index);

				if (index === 0) {
					ctx.moveTo(point._view.x, point._view.y);
				} else {
					this.lineToNextPoint(previous, point, next, function(previousPoint, point, nextPoint) {
						ctx.moveTo(nextPoint._view.x, nextPoint._view.y);
					}, function(previousPoint, point) {
						// If we skipped the last point, move up to our point preventing a line from being drawn
						ctx.moveTo(point._view.x, point._view.y);
					});
				}
			}, this);

			if (this._loop && this._children.length > 0) {
				loopBackToStart();
			}

			ctx.stroke();
			ctx.restore();
		}
	});
};

/***/ }),
/* 251 */
/***/ (function(module, exports, __webpack_require__) {

"use strict";


module.exports = function(Chart) {

	var helpers = Chart.helpers,
		globalOpts = Chart.defaults.global;

	globalOpts.elements.point = {
		radius: 3,
		pointStyle: 'circle',
		backgroundColor: globalOpts.defaultColor,
		borderWidth: 1,
		borderColor: globalOpts.defaultColor,
		// Hover
		hitRadius: 1,
		hoverRadius: 4,
		hoverBorderWidth: 1
	};


	Chart.elements.Point = Chart.Element.extend({
		inRange: function(mouseX, mouseY) {
			var vm = this._view;
			return vm ? ((Math.pow(mouseX - vm.x, 2) + Math.pow(mouseY - vm.y, 2)) < Math.pow(vm.hitRadius + vm.radius, 2)) : false;
		},
		inLabelRange: function(mouseX) {
			var vm = this._view;
			return vm ? (Math.pow(mouseX - vm.x, 2) < Math.pow(vm.radius + vm.hitRadius, 2)) : false; 
		},
		tooltipPosition: function() {
			var vm = this._view;
			return {
				x: vm.x,
				y: vm.y,
				padding: vm.radius + vm.borderWidth
			};
		},
		draw: function() {
			var vm = this._view,
				x = vm.x,
				y = vm.y;
			var ctx = this._chart.ctx;

			if (vm.skip) {
				return;
			}

			var pointStyle = vm.pointStyle;
			if (typeof pointStyle === 'object' && ((pointStyle.toString() === '[object HTMLImageElement]') || (pointStyle.toString() === '[object HTMLCanvasElement]'))) {
				ctx.drawImage(pointStyle, x - pointStyle.width / 2, y - pointStyle.height / 2);
				return;
			}

			if (!isNaN(vm.radius) && vm.radius > 0) {

				ctx.strokeStyle = vm.borderColor || Chart.defaults.global.defaultColor;
				ctx.lineWidth = helpers.getValueOrDefault(vm.borderWidth, Chart.defaults.global.elements.point.borderWidth);

				ctx.fillStyle = vm.backgroundColor || Chart.defaults.global.defaultColor;

				var radius = vm.radius;

				var xOffset,
					yOffset;

				switch (pointStyle) {
					// Default includes circle
					default: 
						ctx.beginPath();
						ctx.arc(x, y, radius, 0, Math.PI * 2);
						ctx.closePath();
						ctx.fill();
						break;
					case 'triangle':
						ctx.beginPath();
						var edgeLength = 3 * radius / Math.sqrt(3);
						var height = edgeLength * Math.sqrt(3) / 2;
						ctx.moveTo(x - edgeLength / 2, y + height / 3);
						ctx.lineTo(x + edgeLength / 2, y + height / 3);
						ctx.lineTo(x, y - 2 * height / 3);
						ctx.closePath();
						ctx.fill();
						break;
					case 'rect':
						ctx.fillRect(x - 1 / Math.SQRT2 * radius, y - 1 / Math.SQRT2 * radius, 2 / Math.SQRT2 * radius, 2 / Math.SQRT2 * radius);
						ctx.strokeRect(x - 1 / Math.SQRT2 * radius, y - 1 / Math.SQRT2 * radius, 2 / Math.SQRT2 * radius, 2 / Math.SQRT2 * radius);
						break;
					case 'rectRot':
						ctx.translate(x, y);
						ctx.rotate(Math.PI / 4);
						ctx.fillRect(-1 / Math.SQRT2 * radius, -1 / Math.SQRT2 * radius, 2 / Math.SQRT2 * radius, 2 / Math.SQRT2 * radius);
						ctx.strokeRect(-1 / Math.SQRT2 * radius, -1 / Math.SQRT2 * radius, 2 / Math.SQRT2 * radius, 2 / Math.SQRT2 * radius);
						ctx.setTransform(1, 0, 0, 1, 0, 0);
						break;
					case 'cross':
						ctx.beginPath();
						ctx.moveTo(x, y + radius);
						ctx.lineTo(x, y - radius);
						ctx.moveTo(x - radius, y);
						ctx.lineTo(x + radius, y);
						ctx.closePath();
						break;
					case 'crossRot':
						ctx.beginPath();
						xOffset = Math.cos(Math.PI / 4) * radius;
						yOffset = Math.sin(Math.PI / 4) * radius;
						ctx.moveTo(x - xOffset, y - yOffset);
						ctx.lineTo(x + xOffset, y + yOffset);
						ctx.moveTo(x - xOffset, y + yOffset);
						ctx.lineTo(x + xOffset, y - yOffset);
						ctx.closePath();
						break;
					case 'star':
						ctx.beginPath();
						ctx.moveTo(x, y + radius);
						ctx.lineTo(x, y - radius);
						ctx.moveTo(x - radius, y);
						ctx.lineTo(x + radius, y);
						xOffset = Math.cos(Math.PI / 4) * radius;
						yOffset = Math.sin(Math.PI / 4) * radius;
						ctx.moveTo(x - xOffset, y - yOffset);
						ctx.lineTo(x + xOffset, y + yOffset);
						ctx.moveTo(x - xOffset, y + yOffset);
						ctx.lineTo(x + xOffset, y - yOffset);
						ctx.closePath();
						break;
					case 'line':
						ctx.beginPath();
						ctx.moveTo(x - radius, y);
						ctx.lineTo(x + radius, y);
						ctx.closePath();
						break;
					case 'dash':
						ctx.beginPath();
						ctx.moveTo(x, y);
						ctx.lineTo(x + radius, y);
						ctx.closePath();
						break;
				}

				ctx.stroke();
			}
		}
	});
};

/***/ }),
/* 252 */
/***/ (function(module, exports, __webpack_require__) {

"use strict";


module.exports = function(Chart) {

	var helpers = Chart.helpers,
		globalOpts = Chart.defaults.global;

	globalOpts.elements.rectangle = {
		backgroundColor: globalOpts.defaultColor,
		borderWidth: 0,
		borderColor: globalOpts.defaultColor,
		borderSkipped: 'bottom'
	};

	Chart.elements.Rectangle = Chart.Element.extend({
		draw: function() {
			var ctx = this._chart.ctx;
			var vm = this._view;

			var halfWidth = vm.width / 2,
				leftX = vm.x - halfWidth,
				rightX = vm.x + halfWidth,
				top = vm.base - (vm.base - vm.y),
				halfStroke = vm.borderWidth / 2;

			// Canvas doesn't allow us to stroke inside the width so we can
			// adjust the sizes to fit if we're setting a stroke on the line
			if (vm.borderWidth) {
				leftX += halfStroke;
				rightX -= halfStroke;
				top += halfStroke;
			}

			ctx.beginPath();
			ctx.fillStyle = vm.backgroundColor;
			ctx.strokeStyle = vm.borderColor;
			ctx.lineWidth = vm.borderWidth;

			// Corner points, from bottom-left to bottom-right clockwise
			// | 1 2 |
			// | 0 3 |
			var corners = [
				[leftX, vm.base],
				[leftX, top],
				[rightX, top],
				[rightX, vm.base]
			];

			// Find first (starting) corner with fallback to 'bottom' 
			var borders = ['bottom', 'left', 'top', 'right'];
			var startCorner = borders.indexOf(vm.borderSkipped, 0);
			if (startCorner === -1)
				startCorner = 0;

			function cornerAt(index) {
				return corners[(startCorner + index) % 4];
			}

			// Draw rectangle from 'startCorner'
			ctx.moveTo.apply(ctx, cornerAt(0));
			for (var i = 1; i < 4; i++)
				ctx.lineTo.apply(ctx, cornerAt(i));

			ctx.fill();
			if (vm.borderWidth) {
				ctx.stroke();
			}
		},
		height: function() {
			var vm = this._view;
			return vm.base - vm.y;
		},
		inRange: function(mouseX, mouseY) {
			var vm = this._view;
			return vm ? 
					(vm.y < vm.base ? 
						(mouseX >= vm.x - vm.width / 2 && mouseX <= vm.x + vm.width / 2) && (mouseY >= vm.y && mouseY <= vm.base) :
						(mouseX >= vm.x - vm.width / 2 && mouseX <= vm.x + vm.width / 2) && (mouseY >= vm.base && mouseY <= vm.y)) :
					false;
		},
		inLabelRange: function(mouseX) {
			var vm = this._view;
			return vm ? (mouseX >= vm.x - vm.width / 2 && mouseX <= vm.x + vm.width / 2) : false;
		},
		tooltipPosition: function() {
			var vm = this._view;
			return {
				x: vm.x,
				y: vm.y
			};
		}
	});

};

/***/ }),
/* 253 */
/***/ (function(module, exports, __webpack_require__) {

"use strict";


module.exports = function(Chart) {

	var helpers = Chart.helpers;
	// Default config for a category scale
	var defaultConfig = {
		position: "bottom"
	};

	var DatasetScale = Chart.Scale.extend({
		// Implement this so that 
		determineDataLimits: function() {
			this.minIndex = 0;
			this.maxIndex = this.chart.data.labels.length - 1;
			var findIndex;

			if (this.options.ticks.min !== undefined) {
				// user specified min value
				findIndex = helpers.indexOf(this.chart.data.labels, this.options.ticks.min);
				this.minIndex = findIndex !== -1 ? findIndex : this.minIndex;
			}

			if (this.options.ticks.max !== undefined) {
				// user specified max value
				findIndex = helpers.indexOf(this.chart.data.labels, this.options.ticks.max);
				this.maxIndex = findIndex !== -1 ? findIndex : this.maxIndex;
			}

			this.min = this.chart.data.labels[this.minIndex];
			this.max = this.chart.data.labels[this.maxIndex];
		},

		buildTicks: function(index) {
			// If we are viewing some subset of labels, slice the original array
			this.ticks = (this.minIndex === 0 && this.maxIndex === this.chart.data.labels.length - 1) ? this.chart.data.labels : this.chart.data.labels.slice(this.minIndex, this.maxIndex + 1);
		},

		getLabelForIndex: function(index, datasetIndex) {
			return this.ticks[index];
		},

		// Used to get data value locations.  Value can either be an index or a numerical value
		getPixelForValue: function(value, index, datasetIndex, includeOffset) {
			// 1 is added because we need the length but we have the indexes
			var offsetAmt = Math.max((this.maxIndex + 1 - this.minIndex - ((this.options.gridLines.offsetGridLines) ? 0 : 1)), 1);

			if (this.isHorizontal()) {
				var innerWidth = this.width - (this.paddingLeft + this.paddingRight);
				var valueWidth = innerWidth / offsetAmt;
				var widthOffset = (valueWidth * (index - this.minIndex)) + this.paddingLeft;

				if (this.options.gridLines.offsetGridLines && includeOffset) {
					widthOffset += (valueWidth / 2);
				}

				return this.left + Math.round(widthOffset);
			} else {
				var innerHeight = this.height - (this.paddingTop + this.paddingBottom);
				var valueHeight = innerHeight / offsetAmt;
				var heightOffset = (valueHeight * (index - this.minIndex)) + this.paddingTop;

				if (this.options.gridLines.offsetGridLines && includeOffset) {
					heightOffset += (valueHeight / 2);
				}

				return this.top + Math.round(heightOffset);
			}
		},
		getPixelForTick: function(index, includeOffset) {
			return this.getPixelForValue(this.ticks[index], index + this.minIndex, null, includeOffset);
		},
		getValueForPixel: function(pixel) {
			var value
;			var offsetAmt = Math.max((this.ticks.length - ((this.options.gridLines.offsetGridLines) ? 0 : 1)), 1);
			var horz = this.isHorizontal();
			var innerDimension = horz ? this.width - (this.paddingLeft + this.paddingRight) : this.height - (this.paddingTop + this.paddingBottom);
			var valueDimension = innerDimension / offsetAmt;

			if (this.options.gridLines.offsetGridLines) {
				pixel -= (valueDimension / 2);
			}
			pixel -= horz ? this.paddingLeft : this.paddingTop;

			if (pixel <= 0) {
				value = 0;
			} else {
				value = Math.round(pixel / valueDimension);
			}

			return value;
		}
	});

	Chart.scaleService.registerScaleType("category", DatasetScale, defaultConfig);

};

/***/ }),
/* 254 */
/***/ (function(module, exports, __webpack_require__) {

"use strict";


module.exports = function(Chart) {

	var helpers = Chart.helpers;

	var defaultConfig = {
		position: "left",
		ticks: {
			callback: function(tickValue, index, ticks) {
				// If we have lots of ticks, don't use the ones
				var delta = ticks.length > 3 ? ticks[2] - ticks[1] : ticks[1] - ticks[0];

				// If we have a number like 2.5 as the delta, figure out how many decimal places we need
				if (Math.abs(delta) > 1) {
					if (tickValue !== Math.floor(tickValue)) {
						// not an integer
						delta = tickValue - Math.floor(tickValue);
					}
				}

				var logDelta = helpers.log10(Math.abs(delta));
				var tickString = '';

				if (tickValue !== 0) {
					var numDecimal = -1 * Math.floor(logDelta);
					numDecimal = Math.max(Math.min(numDecimal, 20), 0); // toFixed has a max of 20 decimal places
					tickString = tickValue.toFixed(numDecimal);
				} else {
					tickString = '0'; // never show decimal places for 0
				}

				return tickString;
			}
		}
	};

	var LinearScale = Chart.Scale.extend({
		determineDataLimits: function() {
			// First Calculate the range
			this.min = null;
			this.max = null;

			if (this.options.stacked) {
				var valuesPerType = {};
				var hasPositiveValues = false;
				var hasNegativeValues = false;

				helpers.each(this.chart.data.datasets, function(dataset, datasetIndex) {
					var meta = this.chart.getDatasetMeta(datasetIndex);
					if (valuesPerType[meta.type] === undefined) {
						valuesPerType[meta.type] = {
							positiveValues: [],
							negativeValues: []
						};
					}

					// Store these per type
					var positiveValues = valuesPerType[meta.type].positiveValues;
					var negativeValues = valuesPerType[meta.type].negativeValues;

					if (this.chart.isDatasetVisible(datasetIndex) && (this.isHorizontal() ? meta.xAxisID === this.id : meta.yAxisID === this.id)) {
						helpers.each(dataset.data, function(rawValue, index) {
							var value = +this.getRightValue(rawValue);
							if (isNaN(value) || meta.data[index].hidden) {
								return;
							}

							positiveValues[index] = positiveValues[index] || 0;
							negativeValues[index] = negativeValues[index] || 0;

							if (this.options.relativePoints) {
								positiveValues[index] = 100;
							} else {
								if (value < 0) {
									hasNegativeValues = true;
									negativeValues[index] += value;
								} else {
									hasPositiveValues = true;
									positiveValues[index] += value;
								}
							}
						}, this);
					}
				}, this);

				helpers.each(valuesPerType, function(valuesForType) {
					var values = valuesForType.positiveValues.concat(valuesForType.negativeValues);
					var minVal = helpers.min(values);
					var maxVal = helpers.max(values);
					this.min = this.min === null ? minVal : Math.min(this.min, minVal);
					this.max = this.max === null ? maxVal : Math.max(this.max, maxVal);
				}, this);

			} else {
				helpers.each(this.chart.data.datasets, function(dataset, datasetIndex) {
					var meta = this.chart.getDatasetMeta(datasetIndex);
					if (this.chart.isDatasetVisible(datasetIndex) && (this.isHorizontal() ? meta.xAxisID === this.id : meta.yAxisID === this.id)) {
						helpers.each(dataset.data, function(rawValue, index) {
							var value = +this.getRightValue(rawValue);
							if (isNaN(value) || meta.data[index].hidden) {
								return;
							}

							if (this.min === null) {
								this.min = value;
							} else if (value < this.min) {
								this.min = value;
							}

							if (this.max === null) {
								this.max = value;
							} else if (value > this.max) {
								this.max = value;
							}
						}, this);
					}
				}, this);
			}

			// If we are forcing it to begin at 0, but 0 will already be rendered on the chart,
			// do nothing since that would make the chart weird. If the user really wants a weird chart
			// axis, they can manually override it
			if (this.options.ticks.beginAtZero) {
				var minSign = helpers.sign(this.min);
				var maxSign = helpers.sign(this.max);

				if (minSign < 0 && maxSign < 0) {
					// move the top up to 0
					this.max = 0;
				} else if (minSign > 0 && maxSign > 0) {
					// move the botttom down to 0
					this.min = 0;
				}
			}

			if (this.options.ticks.min !== undefined) {
				this.min = this.options.ticks.min;
			} else if (this.options.ticks.suggestedMin !== undefined) {
				this.min = Math.min(this.min, this.options.ticks.suggestedMin);
			}

			if (this.options.ticks.max !== undefined) {
				this.max = this.options.ticks.max;
			} else if (this.options.ticks.suggestedMax !== undefined) {
				this.max = Math.max(this.max, this.options.ticks.suggestedMax);
			}

			if (this.min === this.max) {
				this.min--;
				this.max++;
			}
		},
		buildTicks: function() {

			// Then calulate the ticks
			this.ticks = [];

			// Figure out what the max number of ticks we can support it is based on the size of
			// the axis area. For now, we say that the minimum tick spacing in pixels must be 50
			// We also limit the maximum number of ticks to 11 which gives a nice 10 squares on
			// the graph

			var maxTicks;

			if (this.isHorizontal()) {
				maxTicks = Math.min(this.options.ticks.maxTicksLimit ? this.options.ticks.maxTicksLimit : 11, Math.ceil(this.width / 50));
			} else {
				// The factor of 2 used to scale the font size has been experimentally determined.
				var tickFontSize = helpers.getValueOrDefault(this.options.ticks.fontSize, Chart.defaults.global.defaultFontSize);
				maxTicks = Math.min(this.options.ticks.maxTicksLimit ? this.options.ticks.maxTicksLimit : 11, Math.ceil(this.height / (2 * tickFontSize)));
			}

			// Make sure we always have at least 2 ticks
			maxTicks = Math.max(2, maxTicks);

			// To get a "nice" value for the tick spacing, we will use the appropriately named
			// "nice number" algorithm. See http://stackoverflow.com/questions/8506881/nice-label-algorithm-for-charts-with-minimum-ticks
			// for details.

			var spacing;
			var fixedStepSizeSet = (this.options.ticks.fixedStepSize && this.options.ticks.fixedStepSize > 0) || (this.options.ticks.stepSize && this.options.ticks.stepSize > 0);
			if (fixedStepSizeSet) {
				spacing = helpers.getValueOrDefault(this.options.ticks.fixedStepSize, this.options.ticks.stepSize);
			} else {
				var niceRange = helpers.niceNum(this.max - this.min, false);
				spacing = helpers.niceNum(niceRange / (maxTicks - 1), true);
			}
			var niceMin = Math.floor(this.min / spacing) * spacing;
			var niceMax = Math.ceil(this.max / spacing) * spacing;
			var numSpaces = (niceMax - niceMin) / spacing;

			// If very close to our rounded value, use it.
			if (helpers.almostEquals(numSpaces, Math.round(numSpaces), spacing / 1000)) {
				numSpaces = Math.round(numSpaces);
			} else {
				numSpaces = Math.ceil(numSpaces);
			}

			// Put the values into the ticks array
			this.ticks.push(this.options.ticks.min !== undefined ? this.options.ticks.min : niceMin);
			for (var j = 1; j < numSpaces; ++j) {
				this.ticks.push(niceMin + (j * spacing));
			}
			this.ticks.push(this.options.ticks.max !== undefined ? this.options.ticks.max : niceMax);

			if (this.options.position === "left" || this.options.position === "right") {
				// We are in a vertical orientation. The top value is the highest. So reverse the array
				this.ticks.reverse();
			}

			// At this point, we need to update our max and min given the tick values since we have expanded the
			// range of the scale
			this.max = helpers.max(this.ticks);
			this.min = helpers.min(this.ticks);

			if (this.options.ticks.reverse) {
				this.ticks.reverse();

				this.start = this.max;
				this.end = this.min;
			} else {
				this.start = this.min;
				this.end = this.max;
			}
		},
		getLabelForIndex: function(index, datasetIndex) {
			return +this.getRightValue(this.chart.data.datasets[datasetIndex].data[index]);
		},
		convertTicksToLabels: function() {
			this.ticksAsNumbers = this.ticks.slice();
			this.zeroLineIndex = this.ticks.indexOf(0);

			Chart.Scale.prototype.convertTicksToLabels.call(this);
		},
		// Utils
		getPixelForValue: function(value, index, datasetIndex, includeOffset) {
			// This must be called after fit has been run so that
			//      this.left, this.top, this.right, and this.bottom have been defined
			var rightValue = +this.getRightValue(value);
			var pixel;
			var range = this.end - this.start;

			if (this.isHorizontal()) {
				var innerWidth = this.width - (this.paddingLeft + this.paddingRight);
				pixel = this.left + (innerWidth / range * (rightValue - this.start));
				return Math.round(pixel + this.paddingLeft);
			} else {
				var innerHeight = this.height - (this.paddingTop + this.paddingBottom);
				pixel = (this.bottom - this.paddingBottom) - (innerHeight / range * (rightValue - this.start));
				return Math.round(pixel);
			}
		},
		getValueForPixel: function(pixel) {
			var offset;

			if (this.isHorizontal()) {
				var innerWidth = this.width - (this.paddingLeft + this.paddingRight);
				offset = (pixel - this.left - this.paddingLeft) / innerWidth;
			} else {
				var innerHeight = this.height - (this.paddingTop + this.paddingBottom);
				offset = (this.bottom - this.paddingBottom - pixel) / innerHeight;
			}

			return this.start + ((this.end - this.start) * offset);
		},
		getPixelForTick: function(index, includeOffset) {
			return this.getPixelForValue(this.ticksAsNumbers[index], null, null, includeOffset);
		}
	});
	Chart.scaleService.registerScaleType("linear", LinearScale, defaultConfig);

};

/***/ }),
/* 255 */
/***/ (function(module, exports, __webpack_require__) {

"use strict";


module.exports = function(Chart) {

	var helpers = Chart.helpers;

	var defaultConfig = {
		position: "left",

		// label settings
		ticks: {
			callback: function(value, index, arr) {
				var remain = value / (Math.pow(10, Math.floor(Chart.helpers.log10(value))));

				if (remain === 1 || remain === 2 || remain === 5 || index === 0 || index === arr.length - 1) {
					return value.toExponential();
				} else {
					return '';
				}
			}
		}
	};

	var LogarithmicScale = Chart.Scale.extend({
		determineDataLimits: function() {
			// Calculate Range
			this.min = null;
			this.max = null;

			if (this.options.stacked) {
				var valuesPerType = {};

				helpers.each(this.chart.data.datasets, function(dataset, datasetIndex) {
					var meta = this.chart.getDatasetMeta(datasetIndex);
					if (this.chart.isDatasetVisible(datasetIndex) && (this.isHorizontal() ? meta.xAxisID === this.id : meta.yAxisID === this.id)) {
						if (valuesPerType[meta.type] === undefined) {
							valuesPerType[meta.type] = [];
						}

						helpers.each(dataset.data, function(rawValue, index) {
							var values = valuesPerType[meta.type];
							var value = +this.getRightValue(rawValue);
							if (isNaN(value) || meta.data[index].hidden) {
								return;
							}

							values[index] = values[index] || 0;

							if (this.options.relativePoints) {
								values[index] = 100;
							} else {
								// Don't need to split positive and negative since the log scale can't handle a 0 crossing
								values[index] += value;
							}
						}, this);
					}
				}, this);

				helpers.each(valuesPerType, function(valuesForType) {
					var minVal = helpers.min(valuesForType);
					var maxVal = helpers.max(valuesForType);
					this.min = this.min === null ? minVal : Math.min(this.min, minVal);
					this.max = this.max === null ? maxVal : Math.max(this.max, maxVal);
				}, this);

			} else {
				helpers.each(this.chart.data.datasets, function(dataset, datasetIndex) {
					var meta = this.chart.getDatasetMeta(datasetIndex);
					if (this.chart.isDatasetVisible(datasetIndex) && (this.isHorizontal() ? meta.xAxisID === this.id : meta.yAxisID === this.id)) {
						helpers.each(dataset.data, function(rawValue, index) {
							var value = +this.getRightValue(rawValue);
							if (isNaN(value) || meta.data[index].hidden) {
								return;
							}

							if (this.min === null) {
								this.min = value;
							} else if (value < this.min) {
								this.min = value;
							}

							if (this.max === null) {
								this.max = value;
							} else if (value > this.max) {
								this.max = value;
							}
						}, this);
					}
				}, this);
			}

			this.min = this.options.ticks.min !== undefined ? this.options.ticks.min : this.min;
			this.max = this.options.ticks.max !== undefined ? this.options.ticks.max : this.max;

			if (this.min === this.max) {
				if (this.min !== 0 && this.min !== null) {
					this.min = Math.pow(10, Math.floor(helpers.log10(this.min)) - 1);
					this.max = Math.pow(10, Math.floor(helpers.log10(this.max)) + 1);
				} else {
					this.min = 1;
					this.max = 10;
				}
			}
		},
		buildTicks: function() {
			// Reset the ticks array. Later on, we will draw a grid line at these positions
			// The array simply contains the numerical value of the spots where ticks will be
			this.ticks = [];

			// Figure out what the max number of ticks we can support it is based on the size of
			// the axis area. For now, we say that the minimum tick spacing in pixels must be 50
			// We also limit the maximum number of ticks to 11 which gives a nice 10 squares on
			// the graph

			var tickVal = this.options.ticks.min !== undefined ? this.options.ticks.min : Math.pow(10, Math.floor(helpers.log10(this.min)));

			while (tickVal < this.max) {
				this.ticks.push(tickVal);

				var exp = Math.floor(helpers.log10(tickVal));
				var significand = Math.floor(tickVal / Math.pow(10, exp)) + 1;

				if (significand === 10) {
					significand = 1;
					++exp;
				}

				tickVal = significand * Math.pow(10, exp);
			}

			var lastTick = this.options.ticks.max !== undefined ? this.options.ticks.max : tickVal;
			this.ticks.push(lastTick);

			if (this.options.position === "left" || this.options.position === "right") {
				// We are in a vertical orientation. The top value is the highest. So reverse the array
				this.ticks.reverse();
			}

			// At this point, we need to update our max and min given the tick values since we have expanded the
			// range of the scale
			this.max = helpers.max(this.ticks);
			this.min = helpers.min(this.ticks);

			if (this.options.ticks.reverse) {
				this.ticks.reverse();

				this.start = this.max;
				this.end = this.min;
			} else {
				this.start = this.min;
				this.end = this.max;
			}
		},
		convertTicksToLabels: function() {
			this.tickValues = this.ticks.slice();

			Chart.Scale.prototype.convertTicksToLabels.call(this);
		},
		// Get the correct tooltip label
		getLabelForIndex: function(index, datasetIndex) {
			return +this.getRightValue(this.chart.data.datasets[datasetIndex].data[index]);
		},
		getPixelForTick: function(index, includeOffset) {
			return this.getPixelForValue(this.tickValues[index], null, null, includeOffset);
		},
		getPixelForValue: function(value, index, datasetIndex, includeOffset) {
			var pixel;

			var newVal = +this.getRightValue(value)
;			var range = helpers.log10(this.end) - helpers.log10(this.start);

			if (this.isHorizontal()) {

				if (newVal === 0) {
					pixel = this.left + this.paddingLeft;
				} else {
					var innerWidth = this.width - (this.paddingLeft + this.paddingRight);
					pixel = this.left + (innerWidth / range * (helpers.log10(newVal) - helpers.log10(this.start)));
					pixel += this.paddingLeft;
				}
			} else {
				// Bottom - top since pixels increase downard on a screen
				if (newVal === 0) {
					pixel = this.top + this.paddingTop;
				} else {
					var innerHeight = this.height - (this.paddingTop + this.paddingBottom);
					pixel = (this.bottom - this.paddingBottom) - (innerHeight / range * (helpers.log10(newVal) - helpers.log10(this.start)));
				}
			}

			return pixel;
		},
		getValueForPixel: function(pixel) {
			var offset;
			var range = helpers.log10(this.end) - helpers.log10(this.start);
			var value;

			if (this.isHorizontal()) {
				var innerWidth = this.width - (this.paddingLeft + this.paddingRight);
				value = this.start * Math.pow(10, (pixel - this.left - this.paddingLeft) * range / innerWidth);
			} else {
				var innerHeight = this.height - (this.paddingTop + this.paddingBottom);
				value = Math.pow(10, (this.bottom - this.paddingBottom - pixel) * range / innerHeight) / this.start;
			}

			return value;
		}

	});
	Chart.scaleService.registerScaleType("logarithmic", LogarithmicScale, defaultConfig);

};

/***/ }),
/* 256 */
/***/ (function(module, exports, __webpack_require__) {

"use strict";


module.exports = function(Chart) {

	var helpers = Chart.helpers;

	var defaultConfig = {
		display: true,

		//Boolean - Whether to animate scaling the chart from the centre
		animate: true,
		lineArc: false,
		position: "chartArea",

		angleLines: {
			display: true,
			color: "rgba(0, 0, 0, 0.1)",
			lineWidth: 1
		},

		// label settings
		ticks: {
			//Boolean - Show a backdrop to the scale label
			showLabelBackdrop: true,

			//String - The colour of the label backdrop
			backdropColor: "rgba(255,255,255,0.75)",

			//Number - The backdrop padding above & below the label in pixels
			backdropPaddingY: 2,

			//Number - The backdrop padding to the side of the label in pixels
			backdropPaddingX: 2
		},

		pointLabels: {
			//Number - Point label font size in pixels
			fontSize: 10,

			//Function - Used to convert point labels
			callback: function(label) {
				return label;
			}
		}
	};

	var LinearRadialScale = Chart.Scale.extend({
		getValueCount: function() {
			return this.chart.data.labels.length;
		},
		setDimensions: function() {
			// Set the unconstrained dimension before label rotation
			this.width = this.maxWidth;
			this.height = this.maxHeight;
			this.xCenter = Math.round(this.width / 2);
			this.yCenter = Math.round(this.height / 2);

			var minSize = helpers.min([this.height, this.width]);
			var tickFontSize = helpers.getValueOrDefault(this.options.ticks.fontSize, Chart.defaults.global.defaultFontSize);
			this.drawingArea = (this.options.display) ? (minSize / 2) - (tickFontSize / 2 + this.options.ticks.backdropPaddingY) : (minSize / 2);
		},
		determineDataLimits: function() {
			this.min = null;
			this.max = null;

			helpers.each(this.chart.data.datasets, function(dataset, datasetIndex) {
				if (this.chart.isDatasetVisible(datasetIndex)) {
					var meta = this.chart.getDatasetMeta(datasetIndex);
					helpers.each(dataset.data, function(rawValue, index) {
						var value = +this.getRightValue(rawValue);
						if (isNaN(value) || meta.data[index].hidden) {
							return;
						}

						if (this.min === null) {
							this.min = value;
						} else if (value < this.min) {
							this.min = value;
						}

						if (this.max === null) {
							this.max = value;
						} else if (value > this.max) {
							this.max = value;
						}
					}, this);
				}
			}, this);

			// If we are forcing it to begin at 0, but 0 will already be rendered on the chart,
			// do nothing since that would make the chart weird. If the user really wants a weird chart
			// axis, they can manually override it
			if (this.options.ticks.beginAtZero) {
				var minSign = helpers.sign(this.min);
				var maxSign = helpers.sign(this.max);

				if (minSign < 0 && maxSign < 0) {
					// move the top up to 0
					this.max = 0;
				} else if (minSign > 0 && maxSign > 0) {
					// move the botttom down to 0
					this.min = 0;
				}
			}

			if (this.options.ticks.min !== undefined) {
				this.min = this.options.ticks.min;
			} else if (this.options.ticks.suggestedMin !== undefined) {
				this.min = Math.min(this.min, this.options.ticks.suggestedMin);
			}

			if (this.options.ticks.max !== undefined) {
				this.max = this.options.ticks.max;
			} else if (this.options.ticks.suggestedMax !== undefined) {
				this.max = Math.max(this.max, this.options.ticks.suggestedMax);
			}

			if (this.min === this.max) {
				this.min--;
				this.max++;
			}
		},
		buildTicks: function() {


			this.ticks = [];

			// Figure out what the max number of ticks we can support it is based on the size of
			// the axis area. For now, we say that the minimum tick spacing in pixels must be 50
			// We also limit the maximum number of ticks to 11 which gives a nice 10 squares on
			// the graph
			var tickFontSize = helpers.getValueOrDefault(this.options.ticks.fontSize, Chart.defaults.global.defaultFontSize);
			var maxTicks = Math.min(this.options.ticks.maxTicksLimit ? this.options.ticks.maxTicksLimit : 11, Math.ceil(this.drawingArea / (1.5 * tickFontSize)));
			maxTicks = Math.max(2, maxTicks); // Make sure we always have at least 2 ticks

			// To get a "nice" value for the tick spacing, we will use the appropriately named
			// "nice number" algorithm. See http://stackoverflow.com/questions/8506881/nice-label-algorithm-for-charts-with-minimum-ticks
			// for details.

			var niceRange = helpers.niceNum(this.max - this.min, false);
			var spacing = helpers.niceNum(niceRange / (maxTicks - 1), true);
			var niceMin = Math.floor(this.min / spacing) * spacing;
			var niceMax = Math.ceil(this.max / spacing) * spacing;

			var numSpaces = Math.ceil((niceMax - niceMin) / spacing);

			// Put the values into the ticks array
			this.ticks.push(this.options.ticks.min !== undefined ? this.options.ticks.min : niceMin);
			for (var j = 1; j < numSpaces; ++j) {
				this.ticks.push(niceMin + (j * spacing));
			}
			this.ticks.push(this.options.ticks.max !== undefined ? this.options.ticks.max : niceMax);

			// At this point, we need to update our max and min given the tick values since we have expanded the
			// range of the scale
			this.max = helpers.max(this.ticks);
			this.min = helpers.min(this.ticks);

			if (this.options.ticks.reverse) {
				this.ticks.reverse();

				this.start = this.max;
				this.end = this.min;
			} else {
				this.start = this.min;
				this.end = this.max;
			}

			this.zeroLineIndex = this.ticks.indexOf(0);
		},
		convertTicksToLabels: function() {
			Chart.Scale.prototype.convertTicksToLabels.call(this);

			// Point labels
			this.pointLabels = this.chart.data.labels.map(this.options.pointLabels.callback, this);
		},
		getLabelForIndex: function(index, datasetIndex) {
			return +this.getRightValue(this.chart.data.datasets[datasetIndex].data[index]);
		},
		fit: function() {
			/*
			 * Right, this is really confusing and there is a lot of maths going on here
			 * The gist of the problem is here: https://gist.github.com/nnnick/696cc9c55f4b0beb8fe9
			 *
			 * Reaction: https://dl.dropboxusercontent.com/u/34601363/toomuchscience.gif
			 *
			 * Solution:
			 *
			 * We assume the radius of the polygon is half the size of the canvas at first
			 * at each index we check if the text overlaps.
			 *
			 * Where it does, we store that angle and that index.
			 *
			 * After finding the largest index and angle we calculate how much we need to remove
			 * from the shape radius to move the point inwards by that x.
			 *
			 * We average the left and right distances to get the maximum shape radius that can fit in the box
			 * along with labels.
			 *
			 * Once we have that, we can find the centre point for the chart, by taking the x text protrusion
			 * on each side, removing that from the size, halving it and adding the left x protrusion width.
			 *
			 * This will mean we have a shape fitted to the canvas, as large as it can be with the labels
			 * and position it in the most space efficient manner
			 *
			 * https://dl.dropboxusercontent.com/u/34601363/yeahscience.gif
			 */

			var pointLabelFontSize = helpers.getValueOrDefault(this.options.pointLabels.fontSize, Chart.defaults.global.defaultFontSize);
			var pointLabeFontStyle = helpers.getValueOrDefault(this.options.pointLabels.fontStyle, Chart.defaults.global.defaultFontStyle);
			var pointLabeFontFamily = helpers.getValueOrDefault(this.options.pointLabels.fontFamily, Chart.defaults.global.defaultFontFamily);
			var pointLabeFont = helpers.fontString(pointLabelFontSize, pointLabeFontStyle, pointLabeFontFamily);

			// Get maximum radius of the polygon. Either half the height (minus the text width) or half the width.
			// Use this to calculate the offset + change. - Make sure L/R protrusion is at least 0 to stop issues with centre points
			var largestPossibleRadius = helpers.min([(this.height / 2 - pointLabelFontSize - 5), this.width / 2]),
				pointPosition,
				i,
				textWidth,
				halfTextWidth,
				furthestRight = this.width,
				furthestRightIndex,
				furthestRightAngle,
				furthestLeft = 0,
				furthestLeftIndex,
				furthestLeftAngle,
				xProtrusionLeft,
				xProtrusionRight,
				radiusReductionRight,
				radiusReductionLeft,
				maxWidthRadius;
			this.ctx.font = pointLabeFont;

			for (i = 0; i < this.getValueCount(); i++) {
				// 5px to space the text slightly out - similar to what we do in the draw function.
				pointPosition = this.getPointPosition(i, largestPossibleRadius);
				textWidth = this.ctx.measureText(this.pointLabels[i] ? this.pointLabels[i] : '').width + 5;
				if (i === 0 || i === this.getValueCount() / 2) {
					// If we're at index zero, or exactly the middle, we're at exactly the top/bottom
					// of the radar chart, so text will be aligned centrally, so we'll half it and compare
					// w/left and right text sizes
					halfTextWidth = textWidth / 2;
					if (pointPosition.x + halfTextWidth > furthestRight) {
						furthestRight = pointPosition.x + halfTextWidth;
						furthestRightIndex = i;
					}
					if (pointPosition.x - halfTextWidth < furthestLeft) {
						furthestLeft = pointPosition.x - halfTextWidth;
						furthestLeftIndex = i;
					}
				} else if (i < this.getValueCount() / 2) {
					// Less than half the values means we'll left align the text
					if (pointPosition.x + textWidth > furthestRight) {
						furthestRight = pointPosition.x + textWidth;
						furthestRightIndex = i;
					}
				} else if (i > this.getValueCount() / 2) {
					// More than half the values means we'll right align the text
					if (pointPosition.x - textWidth < furthestLeft) {
						furthestLeft = pointPosition.x - textWidth;
						furthestLeftIndex = i;
					}
				}
			}

			xProtrusionLeft = furthestLeft;
			xProtrusionRight = Math.ceil(furthestRight - this.width);

			furthestRightAngle = this.getIndexAngle(furthestRightIndex);
			furthestLeftAngle = this.getIndexAngle(furthestLeftIndex);

			radiusReductionRight = xProtrusionRight / Math.sin(furthestRightAngle + Math.PI / 2);
			radiusReductionLeft = xProtrusionLeft / Math.sin(furthestLeftAngle + Math.PI / 2);

			// Ensure we actually need to reduce the size of the chart
			radiusReductionRight = (helpers.isNumber(radiusReductionRight)) ? radiusReductionRight : 0;
			radiusReductionLeft = (helpers.isNumber(radiusReductionLeft)) ? radiusReductionLeft : 0;

			this.drawingArea = Math.round(largestPossibleRadius - (radiusReductionLeft + radiusReductionRight) / 2);
			this.setCenterPoint(radiusReductionLeft, radiusReductionRight);
		},
		setCenterPoint: function(leftMovement, rightMovement) {

			var maxRight = this.width - rightMovement - this.drawingArea,
				maxLeft = leftMovement + this.drawingArea;

			this.xCenter = Math.round(((maxLeft + maxRight) / 2) + this.left);
			// Always vertically in the centre as the text height doesn't change
			this.yCenter = Math.round((this.height / 2) + this.top);
		},

		getIndexAngle: function(index) {
			var angleMultiplier = (Math.PI * 2) / this.getValueCount();
			// Start from the top instead of right, so remove a quarter of the circle

			return index * angleMultiplier - (Math.PI / 2);
		},
		getDistanceFromCenterForValue: function(value) {
			if (value === null) {
				return 0; // null always in center
			}

			// Take into account half font size + the yPadding of the top value
			var scalingFactor = this.drawingArea / (this.max - this.min);
			if (this.options.reverse) {
				return (this.max - value) * scalingFactor;
			} else {
				return (value - this.min) * scalingFactor;
			}
		},
		getPointPosition: function(index, distanceFromCenter) {
			var thisAngle = this.getIndexAngle(index);
			return {
				x: Math.round(Math.cos(thisAngle) * distanceFromCenter) + this.xCenter,
				y: Math.round(Math.sin(thisAngle) * distanceFromCenter) + this.yCenter
			};
		},
		getPointPositionForValue: function(index, value) {
			return this.getPointPosition(index, this.getDistanceFromCenterForValue(value));
		},
		draw: function() {
			if (this.options.display) {
				var ctx = this.ctx;
				helpers.each(this.ticks, function(label, index) {
					// Don't draw a centre value (if it is minimum)
					if (index > 0 || this.options.reverse) {
						var yCenterOffset = this.getDistanceFromCenterForValue(this.ticks[index]);
						var yHeight = this.yCenter - yCenterOffset;

						// Draw circular lines around the scale
						if (this.options.gridLines.display) {
							ctx.strokeStyle = this.options.gridLines.color;
							ctx.lineWidth = this.options.gridLines.lineWidth;

							if (this.options.lineArc) {
								// Draw circular arcs between the points
								ctx.beginPath();
								ctx.arc(this.xCenter, this.yCenter, yCenterOffset, 0, Math.PI * 2);
								ctx.closePath();
								ctx.stroke();
							} else {
								// Draw straight lines connecting each index
								ctx.beginPath();
								for (var i = 0; i < this.getValueCount(); i++) {
									var pointPosition = this.getPointPosition(i, this.getDistanceFromCenterForValue(this.ticks[index]));
									if (i === 0) {
										ctx.moveTo(pointPosition.x, pointPosition.y);
									} else {
										ctx.lineTo(pointPosition.x, pointPosition.y);
									}
								}
								ctx.closePath();
								ctx.stroke();
							}
						}

						if (this.options.ticks.display) {
							var tickFontColor = helpers.getValueOrDefault(this.options.ticks.fontColor, Chart.defaults.global.defaultFontColor);
							var tickFontSize = helpers.getValueOrDefault(this.options.ticks.fontSize, Chart.defaults.global.defaultFontSize);
							var tickFontStyle = helpers.getValueOrDefault(this.options.ticks.fontStyle, Chart.defaults.global.defaultFontStyle);
							var tickFontFamily = helpers.getValueOrDefault(this.options.ticks.fontFamily, Chart.defaults.global.defaultFontFamily);
							var tickLabelFont = helpers.fontString(tickFontSize, tickFontStyle, tickFontFamily);
							ctx.font = tickLabelFont;

							if (this.options.ticks.showLabelBackdrop) {
								var labelWidth = ctx.measureText(label).width;
								ctx.fillStyle = this.options.ticks.backdropColor;
								ctx.fillRect(
									this.xCenter - labelWidth / 2 - this.options.ticks.backdropPaddingX,
									yHeight - tickFontSize / 2 - this.options.ticks.backdropPaddingY,
									labelWidth + this.options.ticks.backdropPaddingX * 2,
									tickFontSize + this.options.ticks.backdropPaddingY * 2
								);
							}

							ctx.textAlign = 'center';
							ctx.textBaseline = "middle";
							ctx.fillStyle = tickFontColor;
							ctx.fillText(label, this.xCenter, yHeight);
						}
					}
				}, this);

				if (!this.options.lineArc) {
					ctx.lineWidth = this.options.angleLines.lineWidth;
					ctx.strokeStyle = this.options.angleLines.color;

					for (var i = this.getValueCount() - 1; i >= 0; i--) {
						if (this.options.angleLines.display) {
							var outerPosition = this.getPointPosition(i, this.getDistanceFromCenterForValue(this.options.reverse ? this.min : this.max));
							ctx.beginPath();
							ctx.moveTo(this.xCenter, this.yCenter);
							ctx.lineTo(outerPosition.x, outerPosition.y);
							ctx.stroke();
							ctx.closePath();
						}
						// Extra 3px out for some label spacing
						var pointLabelPosition = this.getPointPosition(i, this.getDistanceFromCenterForValue(this.options.reverse ? this.min : this.max) + 5);

						var pointLabelFontColor = helpers.getValueOrDefault(this.options.pointLabels.fontColor, Chart.defaults.global.defaultFontColor);
						var pointLabelFontSize = helpers.getValueOrDefault(this.options.pointLabels.fontSize, Chart.defaults.global.defaultFontSize);
						var pointLabeFontStyle = helpers.getValueOrDefault(this.options.pointLabels.fontStyle, Chart.defaults.global.defaultFontStyle);
						var pointLabeFontFamily = helpers.getValueOrDefault(this.options.pointLabels.fontFamily, Chart.defaults.global.defaultFontFamily);
						var pointLabeFont = helpers.fontString(pointLabelFontSize, pointLabeFontStyle, pointLabeFontFamily);

						ctx.font = pointLabeFont;
						ctx.fillStyle = pointLabelFontColor;

						var labelsCount = this.pointLabels.length,
							halfLabelsCount = this.pointLabels.length / 2,
							quarterLabelsCount = halfLabelsCount / 2,
							upperHalf = (i < quarterLabelsCount || i > labelsCount - quarterLabelsCount),
							exactQuarter = (i === quarterLabelsCount || i === labelsCount - quarterLabelsCount);
						if (i === 0) {
							ctx.textAlign = 'center';
						} else if (i === halfLabelsCount) {
							ctx.textAlign = 'center';
						} else if (i < halfLabelsCount) {
							ctx.textAlign = 'left';
						} else {
							ctx.textAlign = 'right';
						}

						// Set the correct text baseline based on outer positioning
						if (exactQuarter) {
							ctx.textBaseline = 'middle';
						} else if (upperHalf) {
							ctx.textBaseline = 'bottom';
						} else {
							ctx.textBaseline = 'top';
						}

						ctx.fillText(this.pointLabels[i] ? this.pointLabels[i] : '', pointLabelPosition.x, pointLabelPosition.y);
					}
				}
			}
		}
	});
	Chart.scaleService.registerScaleType("radialLinear", LinearRadialScale, defaultConfig);

};

/***/ }),
/* 257 */
/***/ (function(module, exports, __webpack_require__) {

"use strict";
/*global window: false */


var moment = __webpack_require__(1);
moment = typeof(moment) === 'function' ? moment : window.moment;

module.exports = function(Chart) {

	var helpers = Chart.helpers;
	var time = {
		units: [{
			name: 'millisecond',
			steps: [1, 2, 5, 10, 20, 50, 100, 250, 500]
		}, {
			name: 'second',
			steps: [1, 2, 5, 10, 30]
		}, {
			name: 'minute',
			steps: [1, 2, 5, 10, 30]
		}, {
			name: 'hour',
			steps: [1, 2, 3, 6, 12]
		}, {
			name: 'day',
			steps: [1, 2, 5]
		}, {
			name: 'week',
			maxStep: 4
		}, {
			name: 'month',
			maxStep: 3
		}, {
			name: 'quarter',
			maxStep: 4
		}, {
			name: 'year',
			maxStep: false
		}]
	};

	var defaultConfig = {
		position: "bottom",

		time: {
			parser: false, // false == a pattern string from http://momentjs.com/docs/#/parsing/string-format/ or a custom callback that converts its argument to a moment
			format: false, // DEPRECATED false == date objects, moment object, callback or a pattern string from http://momentjs.com/docs/#/parsing/string-format/
			unit: false, // false == automatic or override with week, month, year, etc.
			round: false, // none, or override with week, month, year, etc.
			displayFormat: false, // DEPRECATED

			// defaults to unit's corresponding unitFormat below or override using pattern string from http://momentjs.com/docs/#/displaying/format/
			displayFormats: {
				'millisecond': 'h:mm:ss.SSS a', // 11:20:01.123 AM,
				'second': 'h:mm:ss a', // 11:20:01 AM
				'minute': 'h:mm:ss a', // 11:20:01 AM
				'hour': 'MMM D, hA', // Sept 4, 5PM
				'day': 'll', // Sep 4 2015
				'week': 'll', // Week 46, or maybe "[W]WW - YYYY" ?
				'month': 'MMM YYYY', // Sept 2015
				'quarter': '[Q]Q - YYYY', // Q3
				'year': 'YYYY' // 2015
			}
		},
		ticks: {
			autoSkip: false
		}
	};

	var TimeScale = Chart.Scale.extend({
		initialize: function() {
			if (!moment) {
				throw new Error('Chart.js - Moment.js could not be found! You must include it before Chart.js to use the time scale. Download at https://momentjs.com');
			}

			Chart.Scale.prototype.initialize.call(this);
		},
		getLabelMoment: function(datasetIndex, index) {
			return this.labelMoments[datasetIndex][index];
		},
		determineDataLimits: function() {
			this.labelMoments = [];

			// Only parse these once. If the dataset does not have data as x,y pairs, we will use
			// these
			var scaleLabelMoments = [];
			if (this.chart.data.labels && this.chart.data.labels.length > 0) {
				helpers.each(this.chart.data.labels, function(label, index) {
					var labelMoment = this.parseTime(label);

					if (labelMoment.isValid()) {
						if (this.options.time.round) {
							labelMoment.startOf(this.options.time.round);
						}
						scaleLabelMoments.push(labelMoment);
					}
				}, this);

				this.firstTick = moment.min.call(this, scaleLabelMoments);
				this.lastTick = moment.max.call(this, scaleLabelMoments);
			} else {
				this.firstTick = null;
				this.lastTick = null;
			}

			helpers.each(this.chart.data.datasets, function(dataset, datasetIndex) {
				var momentsForDataset = [];
				var datasetVisible = this.chart.isDatasetVisible(datasetIndex);

				if (typeof dataset.data[0] === 'object') {
					helpers.each(dataset.data, function(value, index) {
						var labelMoment = this.parseTime(this.getRightValue(value));

						if (labelMoment.isValid()) {
							if (this.options.time.round) {
								labelMoment.startOf(this.options.time.round);
							}
							momentsForDataset.push(labelMoment);

							if (datasetVisible) {
								// May have gone outside the scale ranges, make sure we keep the first and last ticks updated
								this.firstTick = this.firstTick !== null ? moment.min(this.firstTick, labelMoment) : labelMoment;
								this.lastTick = this.lastTick !== null ? moment.max(this.lastTick, labelMoment) : labelMoment;
							}
						}
					}, this);
				} else {
					// We have no labels. Use the ones from the scale
					momentsForDataset = scaleLabelMoments;
				}

				this.labelMoments.push(momentsForDataset);
			}, this);

			// Set these after we've done all the data
			if (this.options.time.min) {
				this.firstTick = this.parseTime(this.options.time.min);
			}

			if (this.options.time.max) {
				this.lastTick = this.parseTime(this.options.time.max);
			}

			// We will modify these, so clone for later
			this.firstTick = (this.firstTick || moment()).clone();
			this.lastTick = (this.lastTick || moment()).clone();
		},
		buildTicks: function(index) {

			this.ctx.save();
			var tickFontSize = helpers.getValueOrDefault(this.options.ticks.fontSize, Chart.defaults.global.defaultFontSize);
			var tickFontStyle = helpers.getValueOrDefault(this.options.ticks.fontStyle, Chart.defaults.global.defaultFontStyle);
			var tickFontFamily = helpers.getValueOrDefault(this.options.ticks.fontFamily, Chart.defaults.global.defaultFontFamily);
			var tickLabelFont = helpers.fontString(tickFontSize, tickFontStyle, tickFontFamily);
			this.ctx.font = tickLabelFont;

			this.ticks = [];
			this.unitScale = 1; // How much we scale the unit by, ie 2 means 2x unit per step
			this.scaleSizeInUnits = 0; // How large the scale is in the base unit (seconds, minutes, etc)

			// Set unit override if applicable
			if (this.options.time.unit) {
				this.tickUnit = this.options.time.unit || 'day';
				this.displayFormat = this.options.time.displayFormats[this.tickUnit];
				this.scaleSizeInUnits = this.lastTick.diff(this.firstTick, this.tickUnit, true);
				this.unitScale = helpers.getValueOrDefault(this.options.time.unitStepSize, 1);
			} else {
				// Determine the smallest needed unit of the time
				var innerWidth = this.isHorizontal() ? this.width - (this.paddingLeft + this.paddingRight) : this.height - (this.paddingTop + this.paddingBottom);

				// Crude approximation of what the label length might be
				var tempFirstLabel = this.tickFormatFunction(this.firstTick, 0, []);
				var tickLabelWidth = this.ctx.measureText(tempFirstLabel).width;
				var cosRotation = Math.cos(helpers.toRadians(this.options.ticks.maxRotation));
				var sinRotation = Math.sin(helpers.toRadians(this.options.ticks.maxRotation));
				tickLabelWidth = (tickLabelWidth * cosRotation) + (tickFontSize * sinRotation);
				var labelCapacity = innerWidth / (tickLabelWidth);

				// Start as small as possible
				this.tickUnit = 'millisecond';
				this.scaleSizeInUnits = this.lastTick.diff(this.firstTick, this.tickUnit, true);
				this.displayFormat = this.options.time.displayFormats[this.tickUnit];

				var unitDefinitionIndex = 0;
				var unitDefinition = time.units[unitDefinitionIndex];

				// While we aren't ideal and we don't have units left
				while (unitDefinitionIndex < time.units.length) {
					// Can we scale this unit. If `false` we can scale infinitely
					this.unitScale = 1;

					if (helpers.isArray(unitDefinition.steps) && Math.ceil(this.scaleSizeInUnits / labelCapacity) < helpers.max(unitDefinition.steps)) {
						// Use one of the prefedined steps
						for (var idx = 0; idx < unitDefinition.steps.length; ++idx) {
							if (unitDefinition.steps[idx] >= Math.ceil(this.scaleSizeInUnits / labelCapacity)) {
								this.unitScale = helpers.getValueOrDefault(this.options.time.unitStepSize, unitDefinition.steps[idx]);
								break;
							}
						}

						break;
					} else if ((unitDefinition.maxStep === false) || (Math.ceil(this.scaleSizeInUnits / labelCapacity) < unitDefinition.maxStep)) {
						// We have a max step. Scale this unit
						this.unitScale = helpers.getValueOrDefault(this.options.time.unitStepSize, Math.ceil(this.scaleSizeInUnits / labelCapacity));
						break;
					} else {
						// Move to the next unit up
						++unitDefinitionIndex;
						unitDefinition = time.units[unitDefinitionIndex];

						this.tickUnit = unitDefinition.name;
						var leadingUnitBuffer = this.firstTick.diff(this.firstTick.clone().startOf(this.tickUnit), this.tickUnit, true);
						var trailingUnitBuffer = this.lastTick.clone().add(1, this.tickUnit).startOf(this.tickUnit).diff(this.lastTick, this.tickUnit, true);
						this.scaleSizeInUnits = this.lastTick.diff(this.firstTick, this.tickUnit, true) + leadingUnitBuffer + trailingUnitBuffer;
						this.displayFormat = this.options.time.displayFormats[unitDefinition.name];
					}
				}
			}

			var roundedStart;

			// Only round the first tick if we have no hard minimum
			if (!this.options.time.min) {
				this.firstTick.startOf(this.tickUnit);
				roundedStart = this.firstTick;
			} else {
				roundedStart = this.firstTick.clone().startOf(this.tickUnit);
			}

			// Only round the last tick if we have no hard maximum
			if (!this.options.time.max) {
				var roundedEnd = this.lastTick.clone().startOf(this.tickUnit);
				if (roundedEnd.diff(this.lastTick, this.tickUnit, true) !== 0) {
					// Do not use end of because we need this to be in the next time unit
					this.lastTick.add(1, this.tickUnit).startOf(this.tickUnit);
				}
			}

			this.smallestLabelSeparation = this.width;

			helpers.each(this.chart.data.datasets, function(dataset, datasetIndex) {
				for (var i = 1; i < this.labelMoments[datasetIndex].length; i++) {
					this.smallestLabelSeparation = Math.min(this.smallestLabelSeparation, this.labelMoments[datasetIndex][i].diff(this.labelMoments[datasetIndex][i - 1], this.tickUnit, true));
				}
			}, this);

			// Tick displayFormat override
			if (this.options.time.displayFormat) {
				this.displayFormat = this.options.time.displayFormat;
			}

			// first tick. will have been rounded correctly if options.time.min is not specified
			this.ticks.push(this.firstTick.clone());

			// For every unit in between the first and last moment, create a moment and add it to the ticks tick
			for (var i = 1; i <= this.scaleSizeInUnits; ++i) {
				var newTick = roundedStart.clone().add(i, this.tickUnit);

				// Are we greater than the max time
				if (this.options.time.max && newTick.diff(this.lastTick, this.tickUnit, true) >= 0) {
					break;
				}

				if (i % this.unitScale === 0) {
					this.ticks.push(newTick);
				}
			}

			// Always show the right tick
			var diff = this.ticks[this.ticks.length - 1].diff(this.lastTick, this.tickUnit);
			if (diff !== 0 || this.scaleSizeInUnits === 0) {
				// this is a weird case. If the <max> option is the same as the end option, we can't just diff the times because the tick was created from the roundedStart
				// but the last tick was not rounded.
				if (this.options.time.max) {
					this.ticks.push(this.lastTick.clone());
					this.scaleSizeInUnits = this.lastTick.diff(this.ticks[0], this.tickUnit, true);
				} else {
					this.ticks.push(this.lastTick.clone());
					this.scaleSizeInUnits = this.lastTick.diff(this.firstTick, this.tickUnit, true);
				}
			}
			
			this.ctx.restore();
		},
		// Get tooltip label
		getLabelForIndex: function(index, datasetIndex) {
			var label = this.chart.data.labels && index < this.chart.data.labels.length ? this.chart.data.labels[index] : '';

			if (typeof this.chart.data.datasets[datasetIndex].data[0] === 'object') {
				label = this.getRightValue(this.chart.data.datasets[datasetIndex].data[index]);
			}

			// Format nicely
			if (this.options.time.tooltipFormat) {
				label = this.parseTime(label).format(this.options.time.tooltipFormat);
			}

			return label;
		},
		// Function to format an individual tick mark
		tickFormatFunction: function tickFormatFunction(tick, index, ticks) {
			var formattedTick = tick.format(this.displayFormat);

			if (this.options.ticks.userCallback) {
				return this.options.ticks.userCallback(formattedTick, index, ticks);
			} else {
				return formattedTick;
			}
		},
		convertTicksToLabels: function() {
			this.tickMoments = this.ticks;
			this.ticks = this.ticks.map(this.tickFormatFunction, this);
		},
		getPixelForValue: function(value, index, datasetIndex, includeOffset) {
			var labelMoment = value && value.isValid && value.isValid() ? value : this.getLabelMoment(datasetIndex, index);

			if (labelMoment) {
				var offset = labelMoment.diff(this.firstTick, this.tickUnit, true);

				var decimal = offset / this.scaleSizeInUnits;

				if (this.isHorizontal()) {
					var innerWidth = this.width - (this.paddingLeft + this.paddingRight);
					var valueWidth = innerWidth / Math.max(this.ticks.length - 1, 1);
					var valueOffset = (innerWidth * decimal) + this.paddingLeft;

					return this.left + Math.round(valueOffset);
				} else {
					var innerHeight = this.height - (this.paddingTop + this.paddingBottom);
					var valueHeight = innerHeight / Math.max(this.ticks.length - 1, 1);
					var heightOffset = (innerHeight * decimal) + this.paddingTop;

					return this.top + Math.round(heightOffset);
				}
			}
		},
		getPixelForTick: function(index, includeOffset) {
			return this.getPixelForValue(this.tickMoments[index], null, null, includeOffset);
		},
		getValueForPixel: function(pixel) {
			var innerDimension = this.isHorizontal() ? this.width - (this.paddingLeft + this.paddingRight) : this.height - (this.paddingTop + this.paddingBottom);
			var offset = (pixel - (this.isHorizontal() ? this.left + this.paddingLeft : this.top + this.paddingTop)) / innerDimension;
			offset *= this.scaleSizeInUnits;
			return this.firstTick.clone().add(moment.duration(offset, this.tickUnit).asSeconds(), 'seconds');
		},
		parseTime: function(label) {
			if (typeof this.options.time.parser === 'string') {
				return moment(label, this.options.time.parser);
			}
			if (typeof this.options.time.parser === 'function') {
				return this.options.time.parser(label);
			}
			// Date objects
			if (typeof label.getMonth === 'function' || typeof label === 'number') {
				return moment(label);
			}
			// Moment support
			if (label.isValid && label.isValid()) {
				return label;
			}
			// Custom parsing (return an instance of moment)
			if (typeof this.options.time.format !== 'string' && this.options.time.format.call) {
				console.warn("options.time.format is deprecated and replaced by options.time.parser. See http://nnnick.github.io/Chart.js/docs-v2/#scales-time-scale");
				return this.options.time.format(label);
			}
			// Moment format parsing
			return moment(label, this.options.time.format);
		}
	});
	Chart.scaleService.registerScaleType("time", TimeScale, defaultConfig);

};


/***/ }),
/* 258 */
/***/ (function(module, exports, __webpack_require__) {

/* MIT license */
var colorNames = __webpack_require__(262);

module.exports = {
   getRgba: getRgba,
   getHsla: getHsla,
   getRgb: getRgb,
   getHsl: getHsl,
   getHwb: getHwb,
   getAlpha: getAlpha,

   hexString: hexString,
   rgbString: rgbString,
   rgbaString: rgbaString,
   percentString: percentString,
   percentaString: percentaString,
   hslString: hslString,
   hslaString: hslaString,
   hwbString: hwbString,
   keyword: keyword
}

function getRgba(string) {
   if (!string) {
      return;
   }
   var abbr =  /^#([a-fA-F0-9]{3})$/,
       hex =  /^#([a-fA-F0-9]{6})$/,
       rgba = /^rgba?\(\s*([+-]?\d+)\s*,\s*([+-]?\d+)\s*,\s*([+-]?\d+)\s*(?:,\s*([+-]?[\d\.]+)\s*)?\)$/,
       per = /^rgba?\(\s*([+-]?[\d\.]+)\%\s*,\s*([+-]?[\d\.]+)\%\s*,\s*([+-]?[\d\.]+)\%\s*(?:,\s*([+-]?[\d\.]+)\s*)?\)$/,
       keyword = /(\w+)/;

   var rgb = [0, 0, 0],
       a = 1,
       match = string.match(abbr);
   if (match) {
      match = match[1];
      for (var i = 0; i < rgb.length; i++) {
         rgb[i] = parseInt(match[i] + match[i], 16);
      }
   }
   else if (match = string.match(hex)) {
      match = match[1];
      for (var i = 0; i < rgb.length; i++) {
         rgb[i] = parseInt(match.slice(i * 2, i * 2 + 2), 16);
      }
   }
   else if (match = string.match(rgba)) {
      for (var i = 0; i < rgb.length; i++) {
         rgb[i] = parseInt(match[i + 1]);
      }
      a = parseFloat(match[4]);
   }
   else if (match = string.match(per)) {
      for (var i = 0; i < rgb.length; i++) {
         rgb[i] = Math.round(parseFloat(match[i + 1]) * 2.55);
      }
      a = parseFloat(match[4]);
   }
   else if (match = string.match(keyword)) {
      if (match[1] == "transparent") {
         return [0, 0, 0, 0];
      }
      rgb = colorNames[match[1]];
      if (!rgb) {
         return;
      }
   }

   for (var i = 0; i < rgb.length; i++) {
      rgb[i] = scale(rgb[i], 0, 255);
   }
   if (!a && a != 0) {
      a = 1;
   }
   else {
      a = scale(a, 0, 1);
   }
   rgb[3] = a;
   return rgb;
}

function getHsla(string) {
   if (!string) {
      return;
   }
   var hsl = /^hsla?\(\s*([+-]?\d+)(?:deg)?\s*,\s*([+-]?[\d\.]+)%\s*,\s*([+-]?[\d\.]+)%\s*(?:,\s*([+-]?[\d\.]+)\s*)?\)/;
   var match = string.match(hsl);
   if (match) {
      var alpha = parseFloat(match[4]);
      var h = scale(parseInt(match[1]), 0, 360),
          s = scale(parseFloat(match[2]), 0, 100),
          l = scale(parseFloat(match[3]), 0, 100),
          a = scale(isNaN(alpha) ? 1 : alpha, 0, 1);
      return [h, s, l, a];
   }
}

function getHwb(string) {
   if (!string) {
      return;
   }
   var hwb = /^hwb\(\s*([+-]?\d+)(?:deg)?\s*,\s*([+-]?[\d\.]+)%\s*,\s*([+-]?[\d\.]+)%\s*(?:,\s*([+-]?[\d\.]+)\s*)?\)/;
   var match = string.match(hwb);
   if (match) {
    var alpha = parseFloat(match[4]);
      var h = scale(parseInt(match[1]), 0, 360),
          w = scale(parseFloat(match[2]), 0, 100),
          b = scale(parseFloat(match[3]), 0, 100),
          a = scale(isNaN(alpha) ? 1 : alpha, 0, 1);
      return [h, w, b, a];
   }
}

function getRgb(string) {
   var rgba = getRgba(string);
   return rgba && rgba.slice(0, 3);
}

function getHsl(string) {
  var hsla = getHsla(string);
  return hsla && hsla.slice(0, 3);
}

function getAlpha(string) {
   var vals = getRgba(string);
   if (vals) {
      return vals[3];
   }
   else if (vals = getHsla(string)) {
      return vals[3];
   }
   else if (vals = getHwb(string)) {
      return vals[3];
   }
}

// generators
function hexString(rgb) {
   return "#" + hexDouble(rgb[0]) + hexDouble(rgb[1])
              + hexDouble(rgb[2]);
}

function rgbString(rgba, alpha) {
   if (alpha < 1 || (rgba[3] && rgba[3] < 1)) {
      return rgbaString(rgba, alpha);
   }
   return "rgb(" + rgba[0] + ", " + rgba[1] + ", " + rgba[2] + ")";
}

function rgbaString(rgba, alpha) {
   if (alpha === undefined) {
      alpha = (rgba[3] !== undefined ? rgba[3] : 1);
   }
   return "rgba(" + rgba[0] + ", " + rgba[1] + ", " + rgba[2]
           + ", " + alpha + ")";
}

function percentString(rgba, alpha) {
   if (alpha < 1 || (rgba[3] && rgba[3] < 1)) {
      return percentaString(rgba, alpha);
   }
   var r = Math.round(rgba[0]/255 * 100),
       g = Math.round(rgba[1]/255 * 100),
       b = Math.round(rgba[2]/255 * 100);

   return "rgb(" + r + "%, " + g + "%, " + b + "%)";
}

function percentaString(rgba, alpha) {
   var r = Math.round(rgba[0]/255 * 100),
       g = Math.round(rgba[1]/255 * 100),
       b = Math.round(rgba[2]/255 * 100);
   return "rgba(" + r + "%, " + g + "%, " + b + "%, " + (alpha || rgba[3] || 1) + ")";
}

function hslString(hsla, alpha) {
   if (alpha < 1 || (hsla[3] && hsla[3] < 1)) {
      return hslaString(hsla, alpha);
   }
   return "hsl(" + hsla[0] + ", " + hsla[1] + "%, " + hsla[2] + "%)";
}

function hslaString(hsla, alpha) {
   if (alpha === undefined) {
      alpha = (hsla[3] !== undefined ? hsla[3] : 1);
   }
   return "hsla(" + hsla[0] + ", " + hsla[1] + "%, " + hsla[2] + "%, "
           + alpha + ")";
}

// hwb is a bit different than rgb(a) & hsl(a) since there is no alpha specific syntax
// (hwb have alpha optional & 1 is default value)
function hwbString(hwb, alpha) {
   if (alpha === undefined) {
      alpha = (hwb[3] !== undefined ? hwb[3] : 1);
   }
   return "hwb(" + hwb[0] + ", " + hwb[1] + "%, " + hwb[2] + "%"
           + (alpha !== undefined && alpha !== 1 ? ", " + alpha : "") + ")";
}

function keyword(rgb) {
  return reverseNames[rgb.slice(0, 3)];
}

// helpers
function scale(num, min, max) {
   return Math.min(Math.max(min, num), max);
}

function hexDouble(num) {
  var str = num.toString(16).toUpperCase();
  return (str.length < 2) ? "0" + str : str;
}


//create a list of reverse color names
var reverseNames = {};
for (var name in colorNames) {
   reverseNames[colorNames[name]] = name;
}


/***/ }),
/* 259 */
/***/ (function(module, exports, __webpack_require__) {

/* MIT license */

var convert = __webpack_require__(261),
  string = __webpack_require__(258);

var Color = function(obj) {
  if (obj instanceof Color) return obj;
  if (!(this instanceof Color)) return new Color(obj);

  this.values = {
    rgb: [0, 0, 0],
    hsl: [0, 0, 0],
    hsv: [0, 0, 0],
    hwb: [0, 0, 0],
    cmyk: [0, 0, 0, 0],
    alpha: 1
  }

  // parse Color() argument
  if (typeof obj == "string") {
    var vals = string.getRgba(obj);
    if (vals) {
      this.setValues("rgb", vals);
    } else if (vals = string.getHsla(obj)) {
      this.setValues("hsl", vals);
    } else if (vals = string.getHwb(obj)) {
      this.setValues("hwb", vals);
    } else {
      throw new Error("Unable to parse color from string \"" + obj + "\"");
    }
  } else if (typeof obj == "object") {
    var vals = obj;
    if (vals["r"] !== undefined || vals["red"] !== undefined) {
      this.setValues("rgb", vals)
    } else if (vals["l"] !== undefined || vals["lightness"] !== undefined) {
      this.setValues("hsl", vals)
    } else if (vals["v"] !== undefined || vals["value"] !== undefined) {
      this.setValues("hsv", vals)
    } else if (vals["w"] !== undefined || vals["whiteness"] !== undefined) {
      this.setValues("hwb", vals)
    } else if (vals["c"] !== undefined || vals["cyan"] !== undefined) {
      this.setValues("cmyk", vals)
    } else {
      throw new Error("Unable to parse color from object " + JSON.stringify(obj));
    }
  }
}

Color.prototype = {
  rgb: function(vals) {
    return this.setSpace("rgb", arguments);
  },
  hsl: function(vals) {
    return this.setSpace("hsl", arguments);
  },
  hsv: function(vals) {
    return this.setSpace("hsv", arguments);
  },
  hwb: function(vals) {
    return this.setSpace("hwb", arguments);
  },
  cmyk: function(vals) {
    return this.setSpace("cmyk", arguments);
  },

  rgbArray: function() {
    return this.values.rgb;
  },
  hslArray: function() {
    return this.values.hsl;
  },
  hsvArray: function() {
    return this.values.hsv;
  },
  hwbArray: function() {
    if (this.values.alpha !== 1) {
      return this.values.hwb.concat([this.values.alpha])
    }
    return this.values.hwb;
  },
  cmykArray: function() {
    return this.values.cmyk;
  },
  rgbaArray: function() {
    var rgb = this.values.rgb;
    return rgb.concat([this.values.alpha]);
  },
  hslaArray: function() {
    var hsl = this.values.hsl;
    return hsl.concat([this.values.alpha]);
  },
  alpha: function(val) {
    if (val === undefined) {
      return this.values.alpha;
    }
    this.setValues("alpha", val);
    return this;
  },

  red: function(val) {
    return this.setChannel("rgb", 0, val);
  },
  green: function(val) {
    return this.setChannel("rgb", 1, val);
  },
  blue: function(val) {
    return this.setChannel("rgb", 2, val);
  },
  hue: function(val) {
    return this.setChannel("hsl", 0, val);
  },
  saturation: function(val) {
    return this.setChannel("hsl", 1, val);
  },
  lightness: function(val) {
    return this.setChannel("hsl", 2, val);
  },
  saturationv: function(val) {
    return this.setChannel("hsv", 1, val);
  },
  whiteness: function(val) {
    return this.setChannel("hwb", 1, val);
  },
  blackness: function(val) {
    return this.setChannel("hwb", 2, val);
  },
  value: function(val) {
    return this.setChannel("hsv", 2, val);
  },
  cyan: function(val) {
    return this.setChannel("cmyk", 0, val);
  },
  magenta: function(val) {
    return this.setChannel("cmyk", 1, val);
  },
  yellow: function(val) {
    return this.setChannel("cmyk", 2, val);
  },
  black: function(val) {
    return this.setChannel("cmyk", 3, val);
  },

  hexString: function() {
    return string.hexString(this.values.rgb);
  },
  rgbString: function() {
    return string.rgbString(this.values.rgb, this.values.alpha);
  },
  rgbaString: function() {
    return string.rgbaString(this.values.rgb, this.values.alpha);
  },
  percentString: function() {
    return string.percentString(this.values.rgb, this.values.alpha);
  },
  hslString: function() {
    return string.hslString(this.values.hsl, this.values.alpha);
  },
  hslaString: function() {
    return string.hslaString(this.values.hsl, this.values.alpha);
  },
  hwbString: function() {
    return string.hwbString(this.values.hwb, this.values.alpha);
  },
  keyword: function() {
    return string.keyword(this.values.rgb, this.values.alpha);
  },

  rgbNumber: function() {
    return (this.values.rgb[0] << 16) | (this.values.rgb[1] << 8) | this.values.rgb[2];
  },

  luminosity: function() {
    // http://www.w3.org/TR/WCAG20/#relativeluminancedef
    var rgb = this.values.rgb;
    var lum = [];
    for (var i = 0; i < rgb.length; i++) {
      var chan = rgb[i] / 255;
      lum[i] = (chan <= 0.03928) ? chan / 12.92 : Math.pow(((chan + 0.055) / 1.055), 2.4)
    }
    return 0.2126 * lum[0] + 0.7152 * lum[1] + 0.0722 * lum[2];
  },

  contrast: function(color2) {
    // http://www.w3.org/TR/WCAG20/#contrast-ratiodef
    var lum1 = this.luminosity();
    var lum2 = color2.luminosity();
    if (lum1 > lum2) {
      return (lum1 + 0.05) / (lum2 + 0.05)
    };
    return (lum2 + 0.05) / (lum1 + 0.05);
  },

  level: function(color2) {
    var contrastRatio = this.contrast(color2);
    return (contrastRatio >= 7.1) ? 'AAA' : (contrastRatio >= 4.5) ? 'AA' : '';
  },

  dark: function() {
    // YIQ equation from http://24ways.org/2010/calculating-color-contrast
    var rgb = this.values.rgb,
      yiq = (rgb[0] * 299 + rgb[1] * 587 + rgb[2] * 114) / 1000;
    return yiq < 128;
  },

  light: function() {
    return !this.dark();
  },

  negate: function() {
    var rgb = []
    for (var i = 0; i < 3; i++) {
      rgb[i] = 255 - this.values.rgb[i];
    }
    this.setValues("rgb", rgb);
    return this;
  },

  lighten: function(ratio) {
    this.values.hsl[2] += this.values.hsl[2] * ratio;
    this.setValues("hsl", this.values.hsl);
    return this;
  },

  darken: function(ratio) {
    this.values.hsl[2] -= this.values.hsl[2] * ratio;
    this.setValues("hsl", this.values.hsl);
    return this;
  },

  saturate: function(ratio) {
    this.values.hsl[1] += this.values.hsl[1] * ratio;
    this.setValues("hsl", this.values.hsl);
    return this;
  },

  desaturate: function(ratio) {
    this.values.hsl[1] -= this.values.hsl[1] * ratio;
    this.setValues("hsl", this.values.hsl);
    return this;
  },

  whiten: function(ratio) {
    this.values.hwb[1] += this.values.hwb[1] * ratio;
    this.setValues("hwb", this.values.hwb);
    return this;
  },

  blacken: function(ratio) {
    this.values.hwb[2] += this.values.hwb[2] * ratio;
    this.setValues("hwb", this.values.hwb);
    return this;
  },

  greyscale: function() {
    var rgb = this.values.rgb;
    // http://en.wikipedia.org/wiki/Grayscale#Converting_color_to_grayscale
    var val = rgb[0] * 0.3 + rgb[1] * 0.59 + rgb[2] * 0.11;
    this.setValues("rgb", [val, val, val]);
    return this;
  },

  clearer: function(ratio) {
    this.setValues("alpha", this.values.alpha - (this.values.alpha * ratio));
    return this;
  },

  opaquer: function(ratio) {
    this.setValues("alpha", this.values.alpha + (this.values.alpha * ratio));
    return this;
  },

  rotate: function(degrees) {
    var hue = this.values.hsl[0];
    hue = (hue + degrees) % 360;
    hue = hue < 0 ? 360 + hue : hue;
    this.values.hsl[0] = hue;
    this.setValues("hsl", this.values.hsl);
    return this;
  },

  mix: function(color2, weight) {
    weight = 1 - (weight == null ? 0.5 : weight);

    // algorithm from Sass's mix(). Ratio of first color in mix is
    // determined by the alphas of both colors and the weight
    var t1 = weight * 2 - 1,
      d = this.alpha() - color2.alpha();

    var weight1 = (((t1 * d == -1) ? t1 : (t1 + d) / (1 + t1 * d)) + 1) / 2;
    var weight2 = 1 - weight1;

    var rgb = this.rgbArray();
    var rgb2 = color2.rgbArray();

    for (var i = 0; i < rgb.length; i++) {
      rgb[i] = rgb[i] * weight1 + rgb2[i] * weight2;
    }
    this.setValues("rgb", rgb);

    var alpha = this.alpha() * weight + color2.alpha() * (1 - weight);
    this.setValues("alpha", alpha);

    return this;
  },

  toJSON: function() {
    return this.rgb();
  },

  clone: function() {
    return new Color(this.rgb());
  }
}


Color.prototype.getValues = function(space) {
  var vals = {};
  for (var i = 0; i < space.length; i++) {
    vals[space.charAt(i)] = this.values[space][i];
  }
  if (this.values.alpha != 1) {
    vals["a"] = this.values.alpha;
  }
  // {r: 255, g: 255, b: 255, a: 0.4}
  return vals;
}

Color.prototype.setValues = function(space, vals) {
  var spaces = {
    "rgb": ["red", "green", "blue"],
    "hsl": ["hue", "saturation", "lightness"],
    "hsv": ["hue", "saturation", "value"],
    "hwb": ["hue", "whiteness", "blackness"],
    "cmyk": ["cyan", "magenta", "yellow", "black"]
  };

  var maxes = {
    "rgb": [255, 255, 255],
    "hsl": [360, 100, 100],
    "hsv": [360, 100, 100],
    "hwb": [360, 100, 100],
    "cmyk": [100, 100, 100, 100]
  };

  var alpha = 1;
  if (space == "alpha") {
    alpha = vals;
  } else if (vals.length) {
    // [10, 10, 10]
    this.values[space] = vals.slice(0, space.length);
    alpha = vals[space.length];
  } else if (vals[space.charAt(0)] !== undefined) {
    // {r: 10, g: 10, b: 10}
    for (var i = 0; i < space.length; i++) {
      this.values[space][i] = vals[space.charAt(i)];
    }
    alpha = vals.a;
  } else if (vals[spaces[space][0]] !== undefined) {
    // {red: 10, green: 10, blue: 10}
    var chans = spaces[space];
    for (var i = 0; i < space.length; i++) {
      this.values[space][i] = vals[chans[i]];
    }
    alpha = vals.alpha;
  }
  this.values.alpha = Math.max(0, Math.min(1, (alpha !== undefined ? alpha : this.values.alpha)));
  if (space == "alpha") {
    return;
  }

  // cap values of the space prior converting all values
  for (var i = 0; i < space.length; i++) {
    var capped = Math.max(0, Math.min(maxes[space][i], this.values[space][i]));
    this.values[space][i] = Math.round(capped);
  }

  // convert to all the other color spaces
  for (var sname in spaces) {
    if (sname != space) {
      this.values[sname] = convert[space][sname](this.values[space])
    }

    // cap values
    for (var i = 0; i < sname.length; i++) {
      var capped = Math.max(0, Math.min(maxes[sname][i], this.values[sname][i]));
      this.values[sname][i] = Math.round(capped);
    }
  }
  return true;
}

Color.prototype.setSpace = function(space, args) {
  var vals = args[0];
  if (vals === undefined) {
    // color.rgb()
    return this.getValues(space);
  }
  // color.rgb(10, 10, 10)
  if (typeof vals == "number") {
    vals = Array.prototype.slice.call(args);
  }
  this.setValues(space, vals);
  return this;
}

Color.prototype.setChannel = function(space, index, val) {
  if (val === undefined) {
    // color.red()
    return this.values[space][index];
  }
  // color.red(100)
  this.values[space][index] = val;
  this.setValues(space, this.values[space]);
  return this;
}

window.Color = module.exports = Color


/***/ }),
/* 260 */
/***/ (function(module, exports) {

/* MIT license */

module.exports = {
  rgb2hsl: rgb2hsl,
  rgb2hsv: rgb2hsv,
  rgb2hwb: rgb2hwb,
  rgb2cmyk: rgb2cmyk,
  rgb2keyword: rgb2keyword,
  rgb2xyz: rgb2xyz,
  rgb2lab: rgb2lab,
  rgb2lch: rgb2lch,

  hsl2rgb: hsl2rgb,
  hsl2hsv: hsl2hsv,
  hsl2hwb: hsl2hwb,
  hsl2cmyk: hsl2cmyk,
  hsl2keyword: hsl2keyword,

  hsv2rgb: hsv2rgb,
  hsv2hsl: hsv2hsl,
  hsv2hwb: hsv2hwb,
  hsv2cmyk: hsv2cmyk,
  hsv2keyword: hsv2keyword,

  hwb2rgb: hwb2rgb,
  hwb2hsl: hwb2hsl,
  hwb2hsv: hwb2hsv,
  hwb2cmyk: hwb2cmyk,
  hwb2keyword: hwb2keyword,

  cmyk2rgb: cmyk2rgb,
  cmyk2hsl: cmyk2hsl,
  cmyk2hsv: cmyk2hsv,
  cmyk2hwb: cmyk2hwb,
  cmyk2keyword: cmyk2keyword,

  keyword2rgb: keyword2rgb,
  keyword2hsl: keyword2hsl,
  keyword2hsv: keyword2hsv,
  keyword2hwb: keyword2hwb,
  keyword2cmyk: keyword2cmyk,
  keyword2lab: keyword2lab,
  keyword2xyz: keyword2xyz,

  xyz2rgb: xyz2rgb,
  xyz2lab: xyz2lab,
  xyz2lch: xyz2lch,

  lab2xyz: lab2xyz,
  lab2rgb: lab2rgb,
  lab2lch: lab2lch,

  lch2lab: lch2lab,
  lch2xyz: lch2xyz,
  lch2rgb: lch2rgb
}


function rgb2hsl(rgb) {
  var r = rgb[0]/255,
      g = rgb[1]/255,
      b = rgb[2]/255,
      min = Math.min(r, g, b),
      max = Math.max(r, g, b),
      delta = max - min,
      h, s, l;

  if (max == min)
    h = 0;
  else if (r == max)
    h = (g - b) / delta;
  else if (g == max)
    h = 2 + (b - r) / delta;
  else if (b == max)
    h = 4 + (r - g)/ delta;

  h = Math.min(h * 60, 360);

  if (h < 0)
    h += 360;

  l = (min + max) / 2;

  if (max == min)
    s = 0;
  else if (l <= 0.5)
    s = delta / (max + min);
  else
    s = delta / (2 - max - min);

  return [h, s * 100, l * 100];
}

function rgb2hsv(rgb) {
  var r = rgb[0],
      g = rgb[1],
      b = rgb[2],
      min = Math.min(r, g, b),
      max = Math.max(r, g, b),
      delta = max - min,
      h, s, v;

  if (max == 0)
    s = 0;
  else
    s = (delta/max * 1000)/10;

  if (max == min)
    h = 0;
  else if (r == max)
    h = (g - b) / delta;
  else if (g == max)
    h = 2 + (b - r) / delta;
  else if (b == max)
    h = 4 + (r - g) / delta;

  h = Math.min(h * 60, 360);

  if (h < 0)
    h += 360;

  v = ((max / 255) * 1000) / 10;

  return [h, s, v];
}

function rgb2hwb(rgb) {
  var r = rgb[0],
      g = rgb[1],
      b = rgb[2],
      h = rgb2hsl(rgb)[0],
      w = 1/255 * Math.min(r, Math.min(g, b)),
      b = 1 - 1/255 * Math.max(r, Math.max(g, b));

  return [h, w * 100, b * 100];
}

function rgb2cmyk(rgb) {
  var r = rgb[0] / 255,
      g = rgb[1] / 255,
      b = rgb[2] / 255,
      c, m, y, k;

  k = Math.min(1 - r, 1 - g, 1 - b);
  c = (1 - r - k) / (1 - k) || 0;
  m = (1 - g - k) / (1 - k) || 0;
  y = (1 - b - k) / (1 - k) || 0;
  return [c * 100, m * 100, y * 100, k * 100];
}

function rgb2keyword(rgb) {
  return reverseKeywords[JSON.stringify(rgb)];
}

function rgb2xyz(rgb) {
  var r = rgb[0] / 255,
      g = rgb[1] / 255,
      b = rgb[2] / 255;

  // assume sRGB
  r = r > 0.04045 ? Math.pow(((r + 0.055) / 1.055), 2.4) : (r / 12.92);
  g = g > 0.04045 ? Math.pow(((g + 0.055) / 1.055), 2.4) : (g / 12.92);
  b = b > 0.04045 ? Math.pow(((b + 0.055) / 1.055), 2.4) : (b / 12.92);

  var x = (r * 0.4124) + (g * 0.3576) + (b * 0.1805);
  var y = (r * 0.2126) + (g * 0.7152) + (b * 0.0722);
  var z = (r * 0.0193) + (g * 0.1192) + (b * 0.9505);

  return [x * 100, y *100, z * 100];
}

function rgb2lab(rgb) {
  var xyz = rgb2xyz(rgb),
        x = xyz[0],
        y = xyz[1],
        z = xyz[2],
        l, a, b;

  x /= 95.047;
  y /= 100;
  z /= 108.883;

  x = x > 0.008856 ? Math.pow(x, 1/3) : (7.787 * x) + (16 / 116);
  y = y > 0.008856 ? Math.pow(y, 1/3) : (7.787 * y) + (16 / 116);
  z = z > 0.008856 ? Math.pow(z, 1/3) : (7.787 * z) + (16 / 116);

  l = (116 * y) - 16;
  a = 500 * (x - y);
  b = 200 * (y - z);

  return [l, a, b];
}

function rgb2lch(args) {
  return lab2lch(rgb2lab(args));
}

function hsl2rgb(hsl) {
  var h = hsl[0] / 360,
      s = hsl[1] / 100,
      l = hsl[2] / 100,
      t1, t2, t3, rgb, val;

  if (s == 0) {
    val = l * 255;
    return [val, val, val];
  }

  if (l < 0.5)
    t2 = l * (1 + s);
  else
    t2 = l + s - l * s;
  t1 = 2 * l - t2;

  rgb = [0, 0, 0];
  for (var i = 0; i < 3; i++) {
    t3 = h + 1 / 3 * - (i - 1);
    t3 < 0 && t3++;
    t3 > 1 && t3--;

    if (6 * t3 < 1)
      val = t1 + (t2 - t1) * 6 * t3;
    else if (2 * t3 < 1)
      val = t2;
    else if (3 * t3 < 2)
      val = t1 + (t2 - t1) * (2 / 3 - t3) * 6;
    else
      val = t1;

    rgb[i] = val * 255;
  }

  return rgb;
}

function hsl2hsv(hsl) {
  var h = hsl[0],
      s = hsl[1] / 100,
      l = hsl[2] / 100,
      sv, v;

  if(l === 0) {
      // no need to do calc on black
      // also avoids divide by 0 error
      return [0, 0, 0];
  }

  l *= 2;
  s *= (l <= 1) ? l : 2 - l;
  v = (l + s) / 2;
  sv = (2 * s) / (l + s);
  return [h, sv * 100, v * 100];
}

function hsl2hwb(args) {
  return rgb2hwb(hsl2rgb(args));
}

function hsl2cmyk(args) {
  return rgb2cmyk(hsl2rgb(args));
}

function hsl2keyword(args) {
  return rgb2keyword(hsl2rgb(args));
}


function hsv2rgb(hsv) {
  var h = hsv[0] / 60,
      s = hsv[1] / 100,
      v = hsv[2] / 100,
      hi = Math.floor(h) % 6;

  var f = h - Math.floor(h),
      p = 255 * v * (1 - s),
      q = 255 * v * (1 - (s * f)),
      t = 255 * v * (1 - (s * (1 - f))),
      v = 255 * v;

  switch(hi) {
    case 0:
      return [v, t, p];
    case 1:
      return [q, v, p];
    case 2:
      return [p, v, t];
    case 3:
      return [p, q, v];
    case 4:
      return [t, p, v];
    case 5:
      return [v, p, q];
  }
}

function hsv2hsl(hsv) {
  var h = hsv[0],
      s = hsv[1] / 100,
      v = hsv[2] / 100,
      sl, l;

  l = (2 - s) * v;
  sl = s * v;
  sl /= (l <= 1) ? l : 2 - l;
  sl = sl || 0;
  l /= 2;
  return [h, sl * 100, l * 100];
}

function hsv2hwb(args) {
  return rgb2hwb(hsv2rgb(args))
}

function hsv2cmyk(args) {
  return rgb2cmyk(hsv2rgb(args));
}

function hsv2keyword(args) {
  return rgb2keyword(hsv2rgb(args));
}

// http://dev.w3.org/csswg/css-color/#hwb-to-rgb
function hwb2rgb(hwb) {
  var h = hwb[0] / 360,
      wh = hwb[1] / 100,
      bl = hwb[2] / 100,
      ratio = wh + bl,
      i, v, f, n;

  // wh + bl cant be > 1
  if (ratio > 1) {
    wh /= ratio;
    bl /= ratio;
  }

  i = Math.floor(6 * h);
  v = 1 - bl;
  f = 6 * h - i;
  if ((i & 0x01) != 0) {
    f = 1 - f;
  }
  n = wh + f * (v - wh);  // linear interpolation

  switch (i) {
    default:
    case 6:
    case 0: r = v; g = n; b = wh; break;
    case 1: r = n; g = v; b = wh; break;
    case 2: r = wh; g = v; b = n; break;
    case 3: r = wh; g = n; b = v; break;
    case 4: r = n; g = wh; b = v; break;
    case 5: r = v; g = wh; b = n; break;
  }

  return [r * 255, g * 255, b * 255];
}

function hwb2hsl(args) {
  return rgb2hsl(hwb2rgb(args));
}

function hwb2hsv(args) {
  return rgb2hsv(hwb2rgb(args));
}

function hwb2cmyk(args) {
  return rgb2cmyk(hwb2rgb(args));
}

function hwb2keyword(args) {
  return rgb2keyword(hwb2rgb(args));
}

function cmyk2rgb(cmyk) {
  var c = cmyk[0] / 100,
      m = cmyk[1] / 100,
      y = cmyk[2] / 100,
      k = cmyk[3] / 100,
      r, g, b;

  r = 1 - Math.min(1, c * (1 - k) + k);
  g = 1 - Math.min(1, m * (1 - k) + k);
  b = 1 - Math.min(1, y * (1 - k) + k);
  return [r * 255, g * 255, b * 255];
}

function cmyk2hsl(args) {
  return rgb2hsl(cmyk2rgb(args));
}

function cmyk2hsv(args) {
  return rgb2hsv(cmyk2rgb(args));
}

function cmyk2hwb(args) {
  return rgb2hwb(cmyk2rgb(args));
}

function cmyk2keyword(args) {
  return rgb2keyword(cmyk2rgb(args));
}


function xyz2rgb(xyz) {
  var x = xyz[0] / 100,
      y = xyz[1] / 100,
      z = xyz[2] / 100,
      r, g, b;

  r = (x * 3.2406) + (y * -1.5372) + (z * -0.4986);
  g = (x * -0.9689) + (y * 1.8758) + (z * 0.0415);
  b = (x * 0.0557) + (y * -0.2040) + (z * 1.0570);

  // assume sRGB
  r = r > 0.0031308 ? ((1.055 * Math.pow(r, 1.0 / 2.4)) - 0.055)
    : r = (r * 12.92);

  g = g > 0.0031308 ? ((1.055 * Math.pow(g, 1.0 / 2.4)) - 0.055)
    : g = (g * 12.92);

  b = b > 0.0031308 ? ((1.055 * Math.pow(b, 1.0 / 2.4)) - 0.055)
    : b = (b * 12.92);

  r = Math.min(Math.max(0, r), 1);
  g = Math.min(Math.max(0, g), 1);
  b = Math.min(Math.max(0, b), 1);

  return [r * 255, g * 255, b * 255];
}

function xyz2lab(xyz) {
  var x = xyz[0],
      y = xyz[1],
      z = xyz[2],
      l, a, b;

  x /= 95.047;
  y /= 100;
  z /= 108.883;

  x = x > 0.008856 ? Math.pow(x, 1/3) : (7.787 * x) + (16 / 116);
  y = y > 0.008856 ? Math.pow(y, 1/3) : (7.787 * y) + (16 / 116);
  z = z > 0.008856 ? Math.pow(z, 1/3) : (7.787 * z) + (16 / 116);

  l = (116 * y) - 16;
  a = 500 * (x - y);
  b = 200 * (y - z);

  return [l, a, b];
}

function xyz2lch(args) {
  return lab2lch(xyz2lab(args));
}

function lab2xyz(lab) {
  var l = lab[0],
      a = lab[1],
      b = lab[2],
      x, y, z, y2;

  if (l <= 8) {
    y = (l * 100) / 903.3;
    y2 = (7.787 * (y / 100)) + (16 / 116);
  } else {
    y = 100 * Math.pow((l + 16) / 116, 3);
    y2 = Math.pow(y / 100, 1/3);
  }

  x = x / 95.047 <= 0.008856 ? x = (95.047 * ((a / 500) + y2 - (16 / 116))) / 7.787 : 95.047 * Math.pow((a / 500) + y2, 3);

  z = z / 108.883 <= 0.008859 ? z = (108.883 * (y2 - (b / 200) - (16 / 116))) / 7.787 : 108.883 * Math.pow(y2 - (b / 200), 3);

  return [x, y, z];
}

function lab2lch(lab) {
  var l = lab[0],
      a = lab[1],
      b = lab[2],
      hr, h, c;

  hr = Math.atan2(b, a);
  h = hr * 360 / 2 / Math.PI;
  if (h < 0) {
    h += 360;
  }
  c = Math.sqrt(a * a + b * b);
  return [l, c, h];
}

function lab2rgb(args) {
  return xyz2rgb(lab2xyz(args));
}

function lch2lab(lch) {
  var l = lch[0],
      c = lch[1],
      h = lch[2],
      a, b, hr;

  hr = h / 360 * 2 * Math.PI;
  a = c * Math.cos(hr);
  b = c * Math.sin(hr);
  return [l, a, b];
}

function lch2xyz(args) {
  return lab2xyz(lch2lab(args));
}

function lch2rgb(args) {
  return lab2rgb(lch2lab(args));
}

function keyword2rgb(keyword) {
  return cssKeywords[keyword];
}

function keyword2hsl(args) {
  return rgb2hsl(keyword2rgb(args));
}

function keyword2hsv(args) {
  return rgb2hsv(keyword2rgb(args));
}

function keyword2hwb(args) {
  return rgb2hwb(keyword2rgb(args));
}

function keyword2cmyk(args) {
  return rgb2cmyk(keyword2rgb(args));
}

function keyword2lab(args) {
  return rgb2lab(keyword2rgb(args));
}

function keyword2xyz(args) {
  return rgb2xyz(keyword2rgb(args));
}

var cssKeywords = {
  aliceblue:  [240,248,255],
  antiquewhite: [250,235,215],
  aqua: [0,255,255],
  aquamarine: [127,255,212],
  azure:  [240,255,255],
  beige:  [245,245,220],
  bisque: [255,228,196],
  black:  [0,0,0],
  blanchedalmond: [255,235,205],
  blue: [0,0,255],
  blueviolet: [138,43,226],
  brown:  [165,42,42],
  burlywood:  [222,184,135],
  cadetblue:  [95,158,160],
  chartreuse: [127,255,0],
  chocolate:  [210,105,30],
  coral:  [255,127,80],
  cornflowerblue: [100,149,237],
  cornsilk: [255,248,220],
  crimson:  [220,20,60],
  cyan: [0,255,255],
  darkblue: [0,0,139],
  darkcyan: [0,139,139],
  darkgoldenrod:  [184,134,11],
  darkgray: [169,169,169],
  darkgreen:  [0,100,0],
  darkgrey: [169,169,169],
  darkkhaki:  [189,183,107],
  darkmagenta:  [139,0,139],
  darkolivegreen: [85,107,47],
  darkorange: [255,140,0],
  darkorchid: [153,50,204],
  darkred:  [139,0,0],
  darksalmon: [233,150,122],
  darkseagreen: [143,188,143],
  darkslateblue:  [72,61,139],
  darkslategray:  [47,79,79],
  darkslategrey:  [47,79,79],
  darkturquoise:  [0,206,209],
  darkviolet: [148,0,211],
  deeppink: [255,20,147],
  deepskyblue:  [0,191,255],
  dimgray:  [105,105,105],
  dimgrey:  [105,105,105],
  dodgerblue: [30,144,255],
  firebrick:  [178,34,34],
  floralwhite:  [255,250,240],
  forestgreen:  [34,139,34],
  fuchsia:  [255,0,255],
  gainsboro:  [220,220,220],
  ghostwhite: [248,248,255],
  gold: [255,215,0],
  goldenrod:  [218,165,32],
  gray: [128,128,128],
  green:  [0,128,0],
  greenyellow:  [173,255,47],
  grey: [128,128,128],
  honeydew: [240,255,240],
  hotpink:  [255,105,180],
  indianred:  [205,92,92],
  indigo: [75,0,130],
  ivory:  [255,255,240],
  khaki:  [240,230,140],
  lavender: [230,230,250],
  lavenderblush:  [255,240,245],
  lawngreen:  [124,252,0],
  lemonchiffon: [255,250,205],
  lightblue:  [173,216,230],
  lightcoral: [240,128,128],
  lightcyan:  [224,255,255],
  lightgoldenrodyellow: [250,250,210],
  lightgray:  [211,211,211],
  lightgreen: [144,238,144],
  lightgrey:  [211,211,211],
  lightpink:  [255,182,193],
  lightsalmon:  [255,160,122],
  lightseagreen:  [32,178,170],
  lightskyblue: [135,206,250],
  lightslategray: [119,136,153],
  lightslategrey: [119,136,153],
  lightsteelblue: [176,196,222],
  lightyellow:  [255,255,224],
  lime: [0,255,0],
  limegreen:  [50,205,50],
  linen:  [250,240,230],
  magenta:  [255,0,255],
  maroon: [128,0,0],
  mediumaquamarine: [102,205,170],
  mediumblue: [0,0,205],
  mediumorchid: [186,85,211],
  mediumpurple: [147,112,219],
  mediumseagreen: [60,179,113],
  mediumslateblue:  [123,104,238],
  mediumspringgreen:  [0,250,154],
  mediumturquoise:  [72,209,204],
  mediumvioletred:  [199,21,133],
  midnightblue: [25,25,112],
  mintcream:  [245,255,250],
  mistyrose:  [255,228,225],
  moccasin: [255,228,181],
  navajowhite:  [255,222,173],
  navy: [0,0,128],
  oldlace:  [253,245,230],
  olive:  [128,128,0],
  olivedrab:  [107,142,35],
  orange: [255,165,0],
  orangered:  [255,69,0],
  orchid: [218,112,214],
  palegoldenrod:  [238,232,170],
  palegreen:  [152,251,152],
  paleturquoise:  [175,238,238],
  palevioletred:  [219,112,147],
  papayawhip: [255,239,213],
  peachpuff:  [255,218,185],
  peru: [205,133,63],
  pink: [255,192,203],
  plum: [221,160,221],
  powderblue: [176,224,230],
  purple: [128,0,128],
  rebeccapurple: [102, 51, 153],
  red:  [255,0,0],
  rosybrown:  [188,143,143],
  royalblue:  [65,105,225],
  saddlebrown:  [139,69,19],
  salmon: [250,128,114],
  sandybrown: [244,164,96],
  seagreen: [46,139,87],
  seashell: [255,245,238],
  sienna: [160,82,45],
  silver: [192,192,192],
  skyblue:  [135,206,235],
  slateblue:  [106,90,205],
  slategray:  [112,128,144],
  slategrey:  [112,128,144],
  snow: [255,250,250],
  springgreen:  [0,255,127],
  steelblue:  [70,130,180],
  tan:  [210,180,140],
  teal: [0,128,128],
  thistle:  [216,191,216],
  tomato: [255,99,71],
  turquoise:  [64,224,208],
  violet: [238,130,238],
  wheat:  [245,222,179],
  white:  [255,255,255],
  whitesmoke: [245,245,245],
  yellow: [255,255,0],
  yellowgreen:  [154,205,50]
};

var reverseKeywords = {};
for (var key in cssKeywords) {
  reverseKeywords[JSON.stringify(cssKeywords[key])] = key;
}


/***/ }),
/* 261 */
/***/ (function(module, exports, __webpack_require__) {

var conversions = __webpack_require__(260);

var convert = function() {
   return new Converter();
}

for (var func in conversions) {
  // export Raw versions
  convert[func + "Raw"] =  (function(func) {
    // accept array or plain args
    return function(arg) {
      if (typeof arg == "number")
        arg = Array.prototype.slice.call(arguments);
      return conversions[func](arg);
    }
  })(func);

  var pair = /(\w+)2(\w+)/.exec(func),
      from = pair[1],
      to = pair[2];

  // export rgb2hsl and ["rgb"]["hsl"]
  convert[from] = convert[from] || {};

  convert[from][to] = convert[func] = (function(func) { 
    return function(arg) {
      if (typeof arg == "number")
        arg = Array.prototype.slice.call(arguments);
      
      var val = conversions[func](arg);
      if (typeof val == "string" || val === undefined)
        return val; // keyword

      for (var i = 0; i < val.length; i++)
        val[i] = Math.round(val[i]);
      return val;
    }
  })(func);
}


/* Converter does lazy conversion and caching */
var Converter = function() {
   this.convs = {};
};

/* Either get the values for a space or
  set the values for a space, depending on args */
Converter.prototype.routeSpace = function(space, args) {
   var values = args[0];
   if (values === undefined) {
      // color.rgb()
      return this.getValues(space);
   }
   // color.rgb(10, 10, 10)
   if (typeof values == "number") {
      values = Array.prototype.slice.call(args);        
   }

   return this.setValues(space, values);
};
  
/* Set the values for a space, invalidating cache */
Converter.prototype.setValues = function(space, values) {
   this.space = space;
   this.convs = {};
   this.convs[space] = values;
   return this;
};

/* Get the values for a space. If there's already
  a conversion for the space, fetch it, otherwise
  compute it */
Converter.prototype.getValues = function(space) {
   var vals = this.convs[space];
   if (!vals) {
      var fspace = this.space,
          from = this.convs[fspace];
      vals = convert[fspace][space](from);

      this.convs[space] = vals;
   }
  return vals;
};

["rgb", "hsl", "hsv", "cmyk", "keyword"].forEach(function(space) {
   Converter.prototype[space] = function(vals) {
      return this.routeSpace(space, arguments);
   }
});

module.exports = convert;

/***/ }),
/* 262 */
/***/ (function(module, exports, __webpack_require__) {

"use strict";


module.exports = {
	"aliceblue": [240, 248, 255],
	"antiquewhite": [250, 235, 215],
	"aqua": [0, 255, 255],
	"aquamarine": [127, 255, 212],
	"azure": [240, 255, 255],
	"beige": [245, 245, 220],
	"bisque": [255, 228, 196],
	"black": [0, 0, 0],
	"blanchedalmond": [255, 235, 205],
	"blue": [0, 0, 255],
	"blueviolet": [138, 43, 226],
	"brown": [165, 42, 42],
	"burlywood": [222, 184, 135],
	"cadetblue": [95, 158, 160],
	"chartreuse": [127, 255, 0],
	"chocolate": [210, 105, 30],
	"coral": [255, 127, 80],
	"cornflowerblue": [100, 149, 237],
	"cornsilk": [255, 248, 220],
	"crimson": [220, 20, 60],
	"cyan": [0, 255, 255],
	"darkblue": [0, 0, 139],
	"darkcyan": [0, 139, 139],
	"darkgoldenrod": [184, 134, 11],
	"darkgray": [169, 169, 169],
	"darkgreen": [0, 100, 0],
	"darkgrey": [169, 169, 169],
	"darkkhaki": [189, 183, 107],
	"darkmagenta": [139, 0, 139],
	"darkolivegreen": [85, 107, 47],
	"darkorange": [255, 140, 0],
	"darkorchid": [153, 50, 204],
	"darkred": [139, 0, 0],
	"darksalmon": [233, 150, 122],
	"darkseagreen": [143, 188, 143],
	"darkslateblue": [72, 61, 139],
	"darkslategray": [47, 79, 79],
	"darkslategrey": [47, 79, 79],
	"darkturquoise": [0, 206, 209],
	"darkviolet": [148, 0, 211],
	"deeppink": [255, 20, 147],
	"deepskyblue": [0, 191, 255],
	"dimgray": [105, 105, 105],
	"dimgrey": [105, 105, 105],
	"dodgerblue": [30, 144, 255],
	"firebrick": [178, 34, 34],
	"floralwhite": [255, 250, 240],
	"forestgreen": [34, 139, 34],
	"fuchsia": [255, 0, 255],
	"gainsboro": [220, 220, 220],
	"ghostwhite": [248, 248, 255],
	"gold": [255, 215, 0],
	"goldenrod": [218, 165, 32],
	"gray": [128, 128, 128],
	"green": [0, 128, 0],
	"greenyellow": [173, 255, 47],
	"grey": [128, 128, 128],
	"honeydew": [240, 255, 240],
	"hotpink": [255, 105, 180],
	"indianred": [205, 92, 92],
	"indigo": [75, 0, 130],
	"ivory": [255, 255, 240],
	"khaki": [240, 230, 140],
	"lavender": [230, 230, 250],
	"lavenderblush": [255, 240, 245],
	"lawngreen": [124, 252, 0],
	"lemonchiffon": [255, 250, 205],
	"lightblue": [173, 216, 230],
	"lightcoral": [240, 128, 128],
	"lightcyan": [224, 255, 255],
	"lightgoldenrodyellow": [250, 250, 210],
	"lightgray": [211, 211, 211],
	"lightgreen": [144, 238, 144],
	"lightgrey": [211, 211, 211],
	"lightpink": [255, 182, 193],
	"lightsalmon": [255, 160, 122],
	"lightseagreen": [32, 178, 170],
	"lightskyblue": [135, 206, 250],
	"lightslategray": [119, 136, 153],
	"lightslategrey": [119, 136, 153],
	"lightsteelblue": [176, 196, 222],
	"lightyellow": [255, 255, 224],
	"lime": [0, 255, 0],
	"limegreen": [50, 205, 50],
	"linen": [250, 240, 230],
	"magenta": [255, 0, 255],
	"maroon": [128, 0, 0],
	"mediumaquamarine": [102, 205, 170],
	"mediumblue": [0, 0, 205],
	"mediumorchid": [186, 85, 211],
	"mediumpurple": [147, 112, 219],
	"mediumseagreen": [60, 179, 113],
	"mediumslateblue": [123, 104, 238],
	"mediumspringgreen": [0, 250, 154],
	"mediumturquoise": [72, 209, 204],
	"mediumvioletred": [199, 21, 133],
	"midnightblue": [25, 25, 112],
	"mintcream": [245, 255, 250],
	"mistyrose": [255, 228, 225],
	"moccasin": [255, 228, 181],
	"navajowhite": [255, 222, 173],
	"navy": [0, 0, 128],
	"oldlace": [253, 245, 230],
	"olive": [128, 128, 0],
	"olivedrab": [107, 142, 35],
	"orange": [255, 165, 0],
	"orangered": [255, 69, 0],
	"orchid": [218, 112, 214],
	"palegoldenrod": [238, 232, 170],
	"palegreen": [152, 251, 152],
	"paleturquoise": [175, 238, 238],
	"palevioletred": [219, 112, 147],
	"papayawhip": [255, 239, 213],
	"peachpuff": [255, 218, 185],
	"peru": [205, 133, 63],
	"pink": [255, 192, 203],
	"plum": [221, 160, 221],
	"powderblue": [176, 224, 230],
	"purple": [128, 0, 128],
	"rebeccapurple": [102, 51, 153],
	"red": [255, 0, 0],
	"rosybrown": [188, 143, 143],
	"royalblue": [65, 105, 225],
	"saddlebrown": [139, 69, 19],
	"salmon": [250, 128, 114],
	"sandybrown": [244, 164, 96],
	"seagreen": [46, 139, 87],
	"seashell": [255, 245, 238],
	"sienna": [160, 82, 45],
	"silver": [192, 192, 192],
	"skyblue": [135, 206, 235],
	"slateblue": [106, 90, 205],
	"slategray": [112, 128, 144],
	"slategrey": [112, 128, 144],
	"snow": [255, 250, 250],
	"springgreen": [0, 255, 127],
	"steelblue": [70, 130, 180],
	"tan": [210, 180, 140],
	"teal": [0, 128, 128],
	"thistle": [216, 191, 216],
	"tomato": [255, 99, 71],
	"turquoise": [64, 224, 208],
	"violet": [238, 130, 238],
	"wheat": [245, 222, 179],
	"white": [255, 255, 255],
	"whitesmoke": [245, 245, 245],
	"yellow": [255, 255, 0],
	"yellowgreen": [154, 205, 50]
};


/***/ }),
/* 263 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*! Bootstrap 4 integration for DataTables' Responsive
 * ©2016 SpryMedia Ltd - datatables.net/license
 */

(function( factory ){
	if ( true ) {
		// AMD
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(25), __webpack_require__(264)], __WEBPACK_AMD_DEFINE_RESULT__ = function ( $ ) {
			return factory( $, window, document );
		}.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	}
	else if ( typeof exports === 'object' ) {
		// CommonJS
		module.exports = function (root, $) {
			if ( ! root ) {
				root = window;
			}

			if ( ! $ || ! $.fn.dataTable ) {
				$ = require('datatables.net-bs4')(root, $).$;
			}

			if ( ! $.fn.dataTable.Responsive ) {
				require('datatables.net-responsive')(root, $);
			}

			return factory( $, root, root.document );
		};
	}
	else {
		// Browser
		factory( jQuery, window, document );
	}
}(function( $, window, document, undefined ) {
'use strict';
var DataTable = $.fn.dataTable;


var _display = DataTable.Responsive.display;
var _original = _display.modal;
var _modal = $(
	'<div class="modal fade dtr-bs-modal" role="dialog">'+
		'<div class="modal-dialog" role="document">'+
			'<div class="modal-content">'+
				'<div class="modal-header">'+
					'<button type="button" class="close" data-dismiss="modal" aria-label="Close"><span aria-hidden="true">&times;</span></button>'+
				'</div>'+
				'<div class="modal-body"/>'+
			'</div>'+
		'</div>'+
	'</div>'
);

_display.modal = function ( options ) {
	return function ( row, update, render ) {
		if ( ! $.fn.modal ) {
			_original( row, update, render );
		}
		else {
			if ( ! update ) {
				if ( options && options.header ) {
					var header = _modal.find('div.modal-header');
					var button = header.find('button').detach();
					
					header
						.empty()
						.append( '<h4 class="modal-title">'+options.header( row )+'</h4>' )
						.append( button );
				}

				_modal.find( 'div.modal-body' )
					.empty()
					.append( render() );

				_modal
					.appendTo( 'body' )
					.modal();
			}
		}
	};
};


return DataTable.Responsive;
}));


/***/ }),
/* 264 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*! Responsive 2.2.1-dev
 * 2014-2017 SpryMedia Ltd - datatables.net/license
 */

/**
 * @summary     Responsive
 * @description Responsive tables plug-in for DataTables
 * @version     2.2.1-dev
 * @file        dataTables.responsive.js
 *  
 * @contact     www.sprymedia.co.uk/contact
 * @copyright   Copyright 2014-2017 SpryMedia Ltd.
 *
 * This source file is free software, available under the following license:
 *   MIT license - http://datatables.net/license/mit
 *
 * This source file is distributed in the hope that it will be useful, but
 * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
 * or FITNESS FOR A PARTICULAR PURPOSE. See the license files for details.
 *
 * For details please refer to: http://www.datatables.net
 */
(function( factory ){
	if ( true ) {
		// AMD
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(4)], __WEBPACK_AMD_DEFINE_RESULT__ = function ( $ ) {
			return factory( $, window, document );
		}.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	}
	else if ( typeof exports === 'object' ) {
		// CommonJS
		module.exports = function (root, $) {
			if ( ! root ) {
				root = window;
			}

			if ( ! $ || ! $.fn.dataTable ) {
				$ = require('datatables.net')(root, $).$;
			}

			return factory( $, root, root.document );
		};
	}
	else {
		// Browser
		factory( jQuery, window, document );
	}
}(function( $, window, document, undefined ) {
'use strict';
var DataTable = $.fn.dataTable;


/**
 * Responsive is a plug-in for the DataTables library that makes use of
 * DataTables' ability to change the visibility of columns, changing the
 * visibility of columns so the displayed columns fit into the table container.
 * The end result is that complex tables will be dynamically adjusted to fit
 * into the viewport, be it on a desktop, tablet or mobile browser.
 *
 * Responsive for DataTables has two modes of operation, which can used
 * individually or combined:
 *
 * * Class name based control - columns assigned class names that match the
 *   breakpoint logic can be shown / hidden as required for each breakpoint.
 * * Automatic control - columns are automatically hidden when there is no
 *   room left to display them. Columns removed from the right.
 *
 * In additional to column visibility control, Responsive also has built into
 * options to use DataTables' child row display to show / hide the information
 * from the table that has been hidden. There are also two modes of operation
 * for this child row display:
 *
 * * Inline - when the control element that the user can use to show / hide
 *   child rows is displayed inside the first column of the table.
 * * Column - where a whole column is dedicated to be the show / hide control.
 *
 * Initialisation of Responsive is performed by:
 *
 * * Adding the class `responsive` or `dt-responsive` to the table. In this case
 *   Responsive will automatically be initialised with the default configuration
 *   options when the DataTable is created.
 * * Using the `responsive` option in the DataTables configuration options. This
 *   can also be used to specify the configuration options, or simply set to
 *   `true` to use the defaults.
 *
 *  @class
 *  @param {object} settings DataTables settings object for the host table
 *  @param {object} [opts] Configuration options
 *  @requires jQuery 1.7+
 *  @requires DataTables 1.10.3+
 *
 *  @example
 *      $('#example').DataTable( {
 *        responsive: true
 *      } );
 *    } );
 */
var Responsive = function ( settings, opts ) {
	// Sanity check that we are using DataTables 1.10 or newer
	if ( ! DataTable.versionCheck || ! DataTable.versionCheck( '1.10.10' ) ) {
		throw 'DataTables Responsive requires DataTables 1.10.10 or newer';
	}

	this.s = {
		dt: new DataTable.Api( settings ),
		columns: [],
		current: []
	};

	// Check if responsive has already been initialised on this table
	if ( this.s.dt.settings()[0].responsive ) {
		return;
	}

	// details is an object, but for simplicity the user can give it as a string
	// or a boolean
	if ( opts && typeof opts.details === 'string' ) {
		opts.details = { type: opts.details };
	}
	else if ( opts && opts.details === false ) {
		opts.details = { type: false };
	}
	else if ( opts && opts.details === true ) {
		opts.details = { type: 'inline' };
	}

	this.c = $.extend( true, {}, Responsive.defaults, DataTable.defaults.responsive, opts );
	settings.responsive = this;
	this._constructor();
};

$.extend( Responsive.prototype, {
	/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
	 * Constructor
	 */

	/**
	 * Initialise the Responsive instance
	 *
	 * @private
	 */
	_constructor: function ()
	{
		var that = this;
		var dt = this.s.dt;
		var dtPrivateSettings = dt.settings()[0];
		var oldWindowWidth = $(window).width();

		dt.settings()[0]._responsive = this;

		// Use DataTables' throttle function to avoid processor thrashing on
		// resize
		$(window).on( 'resize.dtr orientationchange.dtr', DataTable.util.throttle( function () {
			// iOS has a bug whereby resize can fire when only scrolling
			// See: http://stackoverflow.com/questions/8898412
			var width = $(window).width();

			if ( width !== oldWindowWidth ) {
				that._resize();
				oldWindowWidth = width;
			}
		} ) );

		// DataTables doesn't currently trigger an event when a row is added, so
		// we need to hook into its private API to enforce the hidden rows when
		// new data is added
		dtPrivateSettings.oApi._fnCallbackReg( dtPrivateSettings, 'aoRowCreatedCallback', function (tr, data, idx) {
			if ( $.inArray( false, that.s.current ) !== -1 ) {
				$('>td, >th', tr).each( function ( i ) {
					var idx = dt.column.index( 'toData', i );

					if ( that.s.current[idx] === false ) {
						$(this).css('display', 'none');
					}
				} );
			}
		} );

		// Destroy event handler
		dt.on( 'destroy.dtr', function () {
			dt.off( '.dtr' );
			$( dt.table().body() ).off( '.dtr' );
			$(window).off( 'resize.dtr orientationchange.dtr' );

			// Restore the columns that we've hidden
			$.each( that.s.current, function ( i, val ) {
				if ( val === false ) {
					that._setColumnVis( i, true );
				}
			} );
		} );

		// Reorder the breakpoints array here in case they have been added out
		// of order
		this.c.breakpoints.sort( function (a, b) {
			return a.width < b.width ? 1 :
				a.width > b.width ? -1 : 0;
		} );

		this._classLogic();
		this._resizeAuto();

		// Details handler
		var details = this.c.details;

		if ( details.type !== false ) {
			that._detailsInit();

			// DataTables will trigger this event on every column it shows and
			// hides individually
			dt.on( 'column-visibility.dtr', function (e, ctx, col, vis, recalc) {
				if ( recalc ) {
					that._classLogic();
					that._resizeAuto();
					that._resize();
				}
			} );

			// Redraw the details box on each draw which will happen if the data
			// has changed. This is used until DataTables implements a native
			// `updated` event for rows
			dt.on( 'draw.dtr', function () {
				that._redrawChildren();
			} );

			$(dt.table().node()).addClass( 'dtr-'+details.type );
		}

		dt.on( 'column-reorder.dtr', function (e, settings, details) {
			that._classLogic();
			that._resizeAuto();
			that._resize();
		} );

		// Change in column sizes means we need to calc
		dt.on( 'column-sizing.dtr', function () {
			that._resizeAuto();
			that._resize();
		});

		// On Ajax reload we want to reopen any child rows which are displayed
		// by responsive
		dt.on( 'preXhr.dtr', function () {
			var rowIds = [];
			dt.rows().every( function () {
				if ( this.child.isShown() ) {
					rowIds.push( this.id(true) );
				}
			} );

			dt.one( 'draw.dtr', function () {
				that._resizeAuto();
				that._resize();

				dt.rows( rowIds ).every( function () {
					that._detailsDisplay( this, false );
				} );
			} );
		});

		dt.on( 'init.dtr', function (e, settings, details) {
			that._resizeAuto();
			that._resize();

			// If columns were hidden, then DataTables needs to adjust the
			// column sizing
			if ( $.inArray( false, that.s.current ) ) {
				dt.columns.adjust();
			}
		} );

		// First pass - draw the table for the current viewport size
		this._resize();
	},


	/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
	 * Private methods
	 */

	/**
	 * Calculate the visibility for the columns in a table for a given
	 * breakpoint. The result is pre-determined based on the class logic if
	 * class names are used to control all columns, but the width of the table
	 * is also used if there are columns which are to be automatically shown
	 * and hidden.
	 *
	 * @param  {string} breakpoint Breakpoint name to use for the calculation
	 * @return {array} Array of boolean values initiating the visibility of each
	 *   column.
	 *  @private
	 */
	_columnsVisiblity: function ( breakpoint )
	{
		var dt = this.s.dt;
		var columns = this.s.columns;
		var i, ien;

		// Create an array that defines the column ordering based first on the
		// column's priority, and secondly the column index. This allows the
		// columns to be removed from the right if the priority matches
		var order = columns
			.map( function ( col, idx ) {
				return {
					columnIdx: idx,
					priority: col.priority
				};
			} )
			.sort( function ( a, b ) {
				if ( a.priority !== b.priority ) {
					return a.priority - b.priority;
				}
				return a.columnIdx - b.columnIdx;
			} );

		// Class logic - determine which columns are in this breakpoint based
		// on the classes. If no class control (i.e. `auto`) then `-` is used
		// to indicate this to the rest of the function
		var display = $.map( columns, function ( col ) {
			return col.auto && col.minWidth === null ?
				false :
				col.auto === true ?
					'-' :
					$.inArray( breakpoint, col.includeIn ) !== -1;
		} );

		// Auto column control - first pass: how much width is taken by the
		// ones that must be included from the non-auto columns
		var requiredWidth = 0;
		for ( i=0, ien=display.length ; i<ien ; i++ ) {
			if ( display[i] === true ) {
				requiredWidth += columns[i].minWidth;
			}
		}

		// Second pass, use up any remaining width for other columns. For
		// scrolling tables we need to subtract the width of the scrollbar. It
		// may not be requires which makes this sub-optimal, but it would
		// require another full redraw to make complete use of those extra few
		// pixels
		var scrolling = dt.settings()[0].oScroll;
		var bar = scrolling.sY || scrolling.sX ? scrolling.iBarWidth : 0;
		var widthAvailable = dt.table().container().offsetWidth - bar;
		var usedWidth = widthAvailable - requiredWidth;

		// Control column needs to always be included. This makes it sub-
		// optimal in terms of using the available with, but to stop layout
		// thrashing or overflow. Also we need to account for the control column
		// width first so we know how much width is available for the other
		// columns, since the control column might not be the first one shown
		for ( i=0, ien=display.length ; i<ien ; i++ ) {
			if ( columns[i].control ) {
				usedWidth -= columns[i].minWidth;
			}
		}

		// Allow columns to be shown (counting by priority and then right to
		// left) until we run out of room
		var empty = false;
		for ( i=0, ien=order.length ; i<ien ; i++ ) {
			var colIdx = order[i].columnIdx;

			if ( display[colIdx] === '-' && ! columns[colIdx].control && columns[colIdx].minWidth ) {
				// Once we've found a column that won't fit we don't let any
				// others display either, or columns might disappear in the
				// middle of the table
				if ( empty || usedWidth - columns[colIdx].minWidth < 0 ) {
					empty = true;
					display[colIdx] = false;
				}
				else {
					display[colIdx] = true;
				}

				usedWidth -= columns[colIdx].minWidth;
			}
		}

		// Determine if the 'control' column should be shown (if there is one).
		// This is the case when there is a hidden column (that is not the
		// control column). The two loops look inefficient here, but they are
		// trivial and will fly through. We need to know the outcome from the
		// first , before the action in the second can be taken
		var showControl = false;

		for ( i=0, ien=columns.length ; i<ien ; i++ ) {
			if ( ! columns[i].control && ! columns[i].never && ! display[i] ) {
				showControl = true;
				break;
			}
		}

		for ( i=0, ien=columns.length ; i<ien ; i++ ) {
			if ( columns[i].control ) {
				display[i] = showControl;
			}
		}

		// Finally we need to make sure that there is at least one column that
		// is visible
		if ( $.inArray( true, display ) === -1 ) {
			display[0] = true;
		}

		return display;
	},


	/**
	 * Create the internal `columns` array with information about the columns
	 * for the table. This includes determining which breakpoints the column
	 * will appear in, based upon class names in the column, which makes up the
	 * vast majority of this method.
	 *
	 * @private
	 */
	_classLogic: function ()
	{
		var that = this;
		var calc = {};
		var breakpoints = this.c.breakpoints;
		var dt = this.s.dt;
		var columns = dt.columns().eq(0).map( function (i) {
			var column = this.column(i);
			var className = column.header().className;
			var priority = dt.settings()[0].aoColumns[i].responsivePriority;

			if ( priority === undefined ) {
				var dataPriority = $(column.header()).data('priority');

				priority = dataPriority !== undefined ?
					dataPriority * 1 :
					10000;
			}

			return {
				className: className,
				includeIn: [],
				auto:      false,
				control:   false,
				never:     className.match(/\bnever\b/) ? true : false,
				priority:  priority
			};
		} );

		// Simply add a breakpoint to `includeIn` array, ensuring that there are
		// no duplicates
		var add = function ( colIdx, name ) {
			var includeIn = columns[ colIdx ].includeIn;

			if ( $.inArray( name, includeIn ) === -1 ) {
				includeIn.push( name );
			}
		};

		var column = function ( colIdx, name, operator, matched ) {
			var size, i, ien;

			if ( ! operator ) {
				columns[ colIdx ].includeIn.push( name );
			}
			else if ( operator === 'max-' ) {
				// Add this breakpoint and all smaller
				size = that._find( name ).width;

				for ( i=0, ien=breakpoints.length ; i<ien ; i++ ) {
					if ( breakpoints[i].width <= size ) {
						add( colIdx, breakpoints[i].name );
					}
				}
			}
			else if ( operator === 'min-' ) {
				// Add this breakpoint and all larger
				size = that._find( name ).width;

				for ( i=0, ien=breakpoints.length ; i<ien ; i++ ) {
					if ( breakpoints[i].width >= size ) {
						add( colIdx, breakpoints[i].name );
					}
				}
			}
			else if ( operator === 'not-' ) {
				// Add all but this breakpoint
				for ( i=0, ien=breakpoints.length ; i<ien ; i++ ) {
					if ( breakpoints[i].name.indexOf( matched ) === -1 ) {
						add( colIdx, breakpoints[i].name );
					}
				}
			}
		};

		// Loop over each column and determine if it has a responsive control
		// class
		columns.each( function ( col, i ) {
			var classNames = col.className.split(' ');
			var hasClass = false;

			// Split the class name up so multiple rules can be applied if needed
			for ( var k=0, ken=classNames.length ; k<ken ; k++ ) {
				var className = $.trim( classNames[k] );

				if ( className === 'all' ) {
					// Include in all
					hasClass = true;
					col.includeIn = $.map( breakpoints, function (a) {
						return a.name;
					} );
					return;
				}
				else if ( className === 'none' || col.never ) {
					// Include in none (default) and no auto
					hasClass = true;
					return;
				}
				else if ( className === 'control' ) {
					// Special column that is only visible, when one of the other
					// columns is hidden. This is used for the details control
					hasClass = true;
					col.control = true;
					return;
				}

				$.each( breakpoints, function ( j, breakpoint ) {
					// Does this column have a class that matches this breakpoint?
					var brokenPoint = breakpoint.name.split('-');
					var re = new RegExp( '(min\\-|max\\-|not\\-)?('+brokenPoint[0]+')(\\-[_a-zA-Z0-9])?' );
					var match = className.match( re );

					if ( match ) {
						hasClass = true;

						if ( match[2] === brokenPoint[0] && match[3] === '-'+brokenPoint[1] ) {
							// Class name matches breakpoint name fully
							column( i, breakpoint.name, match[1], match[2]+match[3] );
						}
						else if ( match[2] === brokenPoint[0] && ! match[3] ) {
							// Class name matched primary breakpoint name with no qualifier
							column( i, breakpoint.name, match[1], match[2] );
						}
					}
				} );
			}

			// If there was no control class, then automatic sizing is used
			if ( ! hasClass ) {
				col.auto = true;
			}
		} );

		this.s.columns = columns;
	},


	/**
	 * Show the details for the child row
	 *
	 * @param  {DataTables.Api} row    API instance for the row
	 * @param  {boolean}        update Update flag
	 * @private
	 */
	_detailsDisplay: function ( row, update )
	{
		var that = this;
		var dt = this.s.dt;
		var details = this.c.details;

		if ( details && details.type !== false ) {
			var res = details.display( row, update, function () {
				return details.renderer(
					dt, row[0], that._detailsObj(row[0])
				);
			} );

			if ( res === true || res === false ) {
				$(dt.table().node()).triggerHandler( 'responsive-display.dt', [dt, row, res, update] );
			}
		}
	},


	/**
	 * Initialisation for the details handler
	 *
	 * @private
	 */
	_detailsInit: function ()
	{
		var that    = this;
		var dt      = this.s.dt;
		var details = this.c.details;

		// The inline type always uses the first child as the target
		if ( details.type === 'inline' ) {
			details.target = 'td:first-child, th:first-child';
		}

		// Keyboard accessibility
		dt.on( 'draw.dtr', function () {
			that._tabIndexes();
		} );
		that._tabIndexes(); // Initial draw has already happened

		$( dt.table().body() ).on( 'keyup.dtr', 'td, th', function (e) {
			if ( e.keyCode === 13 && $(this).data('dtr-keyboard') ) {
				$(this).click();
			}
		} );

		// type.target can be a string jQuery selector or a column index
		var target   = details.target;
		var selector = typeof target === 'string' ? target : 'td, th';

		// Click handler to show / hide the details rows when they are available
		$( dt.table().body() )
			.on( 'click.dtr mousedown.dtr mouseup.dtr', selector, function (e) {
				// If the table is not collapsed (i.e. there is no hidden columns)
				// then take no action
				if ( ! $(dt.table().node()).hasClass('collapsed' ) ) {
					return;
				}

				// Check that the row is actually a DataTable's controlled node
				if ( $.inArray( $(this).closest('tr').get(0), dt.rows().nodes().toArray() ) === -1 ) {
					return;
				}

				// For column index, we determine if we should act or not in the
				// handler - otherwise it is already okay
				if ( typeof target === 'number' ) {
					var targetIdx = target < 0 ?
						dt.columns().eq(0).length + target :
						target;

					if ( dt.cell( this ).index().column !== targetIdx ) {
						return;
					}
				}

				// $().closest() includes itself in its check
				var row = dt.row( $(this).closest('tr') );

				// Check event type to do an action
				if ( e.type === 'click' ) {
					// The renderer is given as a function so the caller can execute it
					// only when they need (i.e. if hiding there is no point is running
					// the renderer)
					that._detailsDisplay( row, false );
				}
				else if ( e.type === 'mousedown' ) {
					// For mouse users, prevent the focus ring from showing
					$(this).css('outline', 'none');
				}
				else if ( e.type === 'mouseup' ) {
					// And then re-allow at the end of the click
					$(this).blur().css('outline', '');
				}
			} );
	},


	/**
	 * Get the details to pass to a renderer for a row
	 * @param  {int} rowIdx Row index
	 * @private
	 */
	_detailsObj: function ( rowIdx )
	{
		var that = this;
		var dt = this.s.dt;

		return $.map( this.s.columns, function( col, i ) {
			// Never and control columns should not be passed to the renderer
			if ( col.never || col.control ) {
				return;
			}

			return {
				title:       dt.settings()[0].aoColumns[ i ].sTitle,
				data:        dt.cell( rowIdx, i ).render( that.c.orthogonal ),
				hidden:      dt.column( i ).visible() && !that.s.current[ i ],
				columnIndex: i,
				rowIndex:    rowIdx
			};
		} );
	},


	/**
	 * Find a breakpoint object from a name
	 *
	 * @param  {string} name Breakpoint name to find
	 * @return {object}      Breakpoint description object
	 * @private
	 */
	_find: function ( name )
	{
		var breakpoints = this.c.breakpoints;

		for ( var i=0, ien=breakpoints.length ; i<ien ; i++ ) {
			if ( breakpoints[i].name === name ) {
				return breakpoints[i];
			}
		}
	},


	/**
	 * Re-create the contents of the child rows as the display has changed in
	 * some way.
	 *
	 * @private
	 */
	_redrawChildren: function ()
	{
		var that = this;
		var dt = this.s.dt;

		dt.rows( {page: 'current'} ).iterator( 'row', function ( settings, idx ) {
			var row = dt.row( idx );

			that._detailsDisplay( dt.row( idx ), true );
		} );
	},


	/**
	 * Alter the table display for a resized viewport. This involves first
	 * determining what breakpoint the window currently is in, getting the
	 * column visibilities to apply and then setting them.
	 *
	 * @private
	 */
	_resize: function ()
	{
		var that = this;
		var dt = this.s.dt;
		var width = $(window).width();
		var breakpoints = this.c.breakpoints;
		var breakpoint = breakpoints[0].name;
		var columns = this.s.columns;
		var i, ien;
		var oldVis = this.s.current.slice();

		// Determine what breakpoint we are currently at
		for ( i=breakpoints.length-1 ; i>=0 ; i-- ) {
			if ( width <= breakpoints[i].width ) {
				breakpoint = breakpoints[i].name;
				break;
			}
		}
		
		// Show the columns for that break point
		var columnsVis = this._columnsVisiblity( breakpoint );
		this.s.current = columnsVis;

		// Set the class before the column visibility is changed so event
		// listeners know what the state is. Need to determine if there are
		// any columns that are not visible but can be shown
		var collapsedClass = false;
		for ( i=0, ien=columns.length ; i<ien ; i++ ) {
			if ( columnsVis[i] === false && ! columns[i].never && ! columns[i].control ) {
				collapsedClass = true;
				break;
			}
		}

		$( dt.table().node() ).toggleClass( 'collapsed', collapsedClass );

		var changed = false;
		var visible = 0;

		dt.columns().eq(0).each( function ( colIdx, i ) {
			if ( columnsVis[i] === true ) {
				visible++;
			}

			if ( columnsVis[i] !== oldVis[i] ) {
				changed = true;
				that._setColumnVis( colIdx, columnsVis[i] );
			}
		} );

		if ( changed ) {
			this._redrawChildren();

			// Inform listeners of the change
			$(dt.table().node()).trigger( 'responsive-resize.dt', [dt, this.s.current] );

			// If no records, update the "No records" display element
			if ( dt.page.info().recordsDisplay === 0 ) {
				$('td', dt.table().body()).eq(0).attr('colspan', visible);
			}
		}
	},


	/**
	 * Determine the width of each column in the table so the auto column hiding
	 * has that information to work with. This method is never going to be 100%
	 * perfect since column widths can change slightly per page, but without
	 * seriously compromising performance this is quite effective.
	 *
	 * @private
	 */
	_resizeAuto: function ()
	{
		var dt = this.s.dt;
		var columns = this.s.columns;

		// Are we allowed to do auto sizing?
		if ( ! this.c.auto ) {
			return;
		}

		// Are there any columns that actually need auto-sizing, or do they all
		// have classes defined
		if ( $.inArray( true, $.map( columns, function (c) { return c.auto; } ) ) === -1 ) {
			return;
		}

		// Need to restore all children. They will be reinstated by a re-render
		if ( ! $.isEmptyObject( _childNodeStore ) ) {
			$.each( _childNodeStore, function ( key ) {
				var idx = key.split('-');

				_childNodesRestore( dt, idx[0]*1, idx[1]*1 );
			} );
		}

		// Clone the table with the current data in it
		var tableWidth   = dt.table().node().offsetWidth;
		var columnWidths = dt.columns;
		var clonedTable  = dt.table().node().cloneNode( false );
		var clonedHeader = $( dt.table().header().cloneNode( false ) ).appendTo( clonedTable );
		var clonedBody   = $( dt.table().body() ).clone( false, false ).empty().appendTo( clonedTable ); // use jQuery because of IE8

		// Header
		var headerCells = dt.columns()
			.header()
			.filter( function (idx) {
				return dt.column(idx).visible();
			} )
			.to$()
			.clone( false )
			.css( 'display', 'table-cell' )
			.css( 'min-width', 0 );

		// Body rows - we don't need to take account of DataTables' column
		// visibility since we implement our own here (hence the `display` set)
		$(clonedBody)
			.append( $(dt.rows( { page: 'current' } ).nodes()).clone( false ) )
			.find( 'th, td' ).css( 'display', '' );

		// Footer
		var footer = dt.table().footer();
		if ( footer ) {
			var clonedFooter = $( footer.cloneNode( false ) ).appendTo( clonedTable );
			var footerCells = dt.columns()
				.footer()
				.filter( function (idx) {
					return dt.column(idx).visible();
				} )
				.to$()
				.clone( false )
				.css( 'display', 'table-cell' );

			$('<tr/>')
				.append( footerCells )
				.appendTo( clonedFooter );
		}

		$('<tr/>')
			.append( headerCells )
			.appendTo( clonedHeader );

		// In the inline case extra padding is applied to the first column to
		// give space for the show / hide icon. We need to use this in the
		// calculation
		if ( this.c.details.type === 'inline' ) {
			$(clonedTable).addClass( 'dtr-inline collapsed' );
		}
		
		// It is unsafe to insert elements with the same name into the DOM
		// multiple times. For example, cloning and inserting a checked radio
		// clears the chcecked state of the original radio.
		$( clonedTable ).find( '[name]' ).removeAttr( 'name' );
		
		var inserted = $('<div/>')
			.css( {
				width: 1,
				height: 1,
				overflow: 'hidden',
				clear: 'both'
			} )
			.append( clonedTable );

		inserted.insertBefore( dt.table().node() );

		// The cloned header now contains the smallest that each column can be
		headerCells.each( function (i) {
			var idx = dt.column.index( 'fromVisible', i );
			columns[ idx ].minWidth =  this.offsetWidth || 0;
		} );

		inserted.remove();
	},

	/**
	 * Set a column's visibility.
	 *
	 * We don't use DataTables' column visibility controls in order to ensure
	 * that column visibility can Responsive can no-exist. Since only IE8+ is
	 * supported (and all evergreen browsers of course) the control of the
	 * display attribute works well.
	 *
	 * @param {integer} col      Column index
	 * @param {boolean} showHide Show or hide (true or false)
	 * @private
	 */
	_setColumnVis: function ( col, showHide )
	{
		var dt = this.s.dt;
		var display = showHide ? '' : 'none'; // empty string will remove the attr

		$( dt.column( col ).header() ).css( 'display', display );
		$( dt.column( col ).footer() ).css( 'display', display );
		dt.column( col ).nodes().to$().css( 'display', display );

		// If the are child nodes stored, we might need to reinsert them
		if ( ! $.isEmptyObject( _childNodeStore ) ) {
			dt.cells( null, col ).indexes().each( function (idx) {
				_childNodesRestore( dt, idx.row, idx.column );
			} );
		}
	},


	/**
	 * Update the cell tab indexes for keyboard accessibility. This is called on
	 * every table draw - that is potentially inefficient, but also the least
	 * complex option given that column visibility can change on the fly. Its a
	 * shame user-focus was removed from CSS 3 UI, as it would have solved this
	 * issue with a single CSS statement.
	 *
	 * @private
	 */
	_tabIndexes: function ()
	{
		var dt = this.s.dt;
		var cells = dt.cells( { page: 'current' } ).nodes().to$();
		var ctx = dt.settings()[0];
		var target = this.c.details.target;

		cells.filter( '[data-dtr-keyboard]' ).removeData( '[data-dtr-keyboard]' );

		var selector = typeof target === 'number' ?
			':eq('+target+')' :
			target;

		// This is a bit of a hack - we need to limit the selected nodes to just
		// those of this table
		if ( selector === 'td:first-child, th:first-child' ) {
			selector = '>td:first-child, >th:first-child';
		}

		$( selector, dt.rows( { page: 'current' } ).nodes() )
			.attr( 'tabIndex', ctx.iTabIndex )
			.data( 'dtr-keyboard', 1 );
	}
} );


/**
 * List of default breakpoints. Each item in the array is an object with two
 * properties:
 *
 * * `name` - the breakpoint name.
 * * `width` - the breakpoint width
 *
 * @name Responsive.breakpoints
 * @static
 */
Responsive.breakpoints = [
	{ name: 'desktop',  width: Infinity },
	{ name: 'tablet-l', width: 1024 },
	{ name: 'tablet-p', width: 768 },
	{ name: 'mobile-l', width: 480 },
	{ name: 'mobile-p', width: 320 }
];


/**
 * Display methods - functions which define how the hidden data should be shown
 * in the table.
 *
 * @namespace
 * @name Responsive.defaults
 * @static
 */
Responsive.display = {
	childRow: function ( row, update, render ) {
		if ( update ) {
			if ( $(row.node()).hasClass('parent') ) {
				row.child( render(), 'child' ).show();

				return true;
			}
		}
		else {
			if ( ! row.child.isShown()  ) {
				row.child( render(), 'child' ).show();
				$( row.node() ).addClass( 'parent' );

				return true;
			}
			else {
				row.child( false );
				$( row.node() ).removeClass( 'parent' );

				return false;
			}
		}
	},

	childRowImmediate: function ( row, update, render ) {
		if ( (! update && row.child.isShown()) || ! row.responsive.hasHidden() ) {
			// User interaction and the row is show, or nothing to show
			row.child( false );
			$( row.node() ).removeClass( 'parent' );

			return false;
		}
		else {
			// Display
			row.child( render(), 'child' ).show();
			$( row.node() ).addClass( 'parent' );

			return true;
		}
	},

	// This is a wrapper so the modal options for Bootstrap and jQuery UI can
	// have options passed into them. This specific one doesn't need to be a
	// function but it is for consistency in the `modal` name
	modal: function ( options ) {
		return function ( row, update, render ) {
			if ( ! update ) {
				// Show a modal
				var close = function () {
					modal.remove(); // will tidy events for us
					$(document).off( 'keypress.dtr' );
				};

				var modal = $('<div class="dtr-modal"/>')
					.append( $('<div class="dtr-modal-display"/>')
						.append( $('<div class="dtr-modal-content"/>')
							.append( render() )
						)
						.append( $('<div class="dtr-modal-close">&times;</div>' )
							.click( function () {
								close();
							} )
						)
					)
					.append( $('<div class="dtr-modal-background"/>')
						.click( function () {
							close();
						} )
					)
					.appendTo( 'body' );

				$(document).on( 'keyup.dtr', function (e) {
					if ( e.keyCode === 27 ) {
						e.stopPropagation();

						close();
					}
				} );
			}
			else {
				$('div.dtr-modal-content')
					.empty()
					.append( render() );
			}

			if ( options && options.header ) {
				$('div.dtr-modal-content').prepend(
					'<h2>'+options.header( row )+'</h2>'
				);
			}
		};
	}
};


var _childNodeStore = {};

function _childNodes( dt, row, col ) {
	var name = row+'-'+col;

	if ( _childNodeStore[ name ] ) {
		return _childNodeStore[ name ];
	}

	// https://jsperf.com/childnodes-array-slice-vs-loop
	var nodes = [];
	var children = dt.cell( row, col ).node().childNodes;
	for ( var i=0, ien=children.length ; i<ien ; i++ ) {
		nodes.push( children[i] );
	}

	_childNodeStore[ name ] = nodes;

	return nodes;
}

function _childNodesRestore( dt, row, col ) {
	var name = row+'-'+col;

	if ( ! _childNodeStore[ name ] ) {
		return;
	}

	var node = dt.cell( row, col ).node();
	var store = _childNodeStore[ name ];
	var parent = store[0].parentNode;
	var parentChildren = parent.childNodes;
	var a = [];

	for ( var i=0, ien=parentChildren.length ; i<ien ; i++ ) {
		a.push( parentChildren[i] );
	}

	for ( var j=0, jen=a.length ; j<jen ; j++ ) {
		node.appendChild( a[j] );
	}

	_childNodeStore[ name ] = undefined;
}


/**
 * Display methods - functions which define how the hidden data should be shown
 * in the table.
 *
 * @namespace
 * @name Responsive.defaults
 * @static
 */
Responsive.renderer = {
	listHiddenNodes: function () {
		return function ( api, rowIdx, columns ) {
			var ul = $('<ul data-dtr-index="'+rowIdx+'" class="dtr-details"/>');
			var found = false;

			var data = $.each( columns, function ( i, col ) {
				if ( col.hidden ) {
					$(
						'<li data-dtr-index="'+col.columnIndex+'" data-dt-row="'+col.rowIndex+'" data-dt-column="'+col.columnIndex+'">'+
							'<span class="dtr-title">'+
								col.title+
							'</span> '+
						'</li>'
					)
						.append( $('<span class="dtr-data"/>').append( _childNodes( api, col.rowIndex, col.columnIndex ) ) )// api.cell( col.rowIndex, col.columnIndex ).node().childNodes ) )
						.appendTo( ul );

					found = true;
				}
			} );

			return found ?
				ul :
				false;
		};
	},

	listHidden: function () {
		return function ( api, rowIdx, columns ) {
			var data = $.map( columns, function ( col ) {
				return col.hidden ?
					'<li data-dtr-index="'+col.columnIndex+'" data-dt-row="'+col.rowIndex+'" data-dt-column="'+col.columnIndex+'">'+
						'<span class="dtr-title">'+
							col.title+
						'</span> '+
						'<span class="dtr-data">'+
							col.data+
						'</span>'+
					'</li>' :
					'';
			} ).join('');

			return data ?
				$('<ul data-dtr-index="'+rowIdx+'" class="dtr-details"/>').append( data ) :
				false;
		}
	},

	tableAll: function ( options ) {
		options = $.extend( {
			tableClass: ''
		}, options );

		return function ( api, rowIdx, columns ) {
			var data = $.map( columns, function ( col ) {
				return '<tr data-dt-row="'+col.rowIndex+'" data-dt-column="'+col.columnIndex+'">'+
						'<td>'+col.title+':'+'</td> '+
						'<td>'+col.data+'</td>'+
					'</tr>';
			} ).join('');

			return $('<table class="'+options.tableClass+' dtr-details" width="100%"/>').append( data );
		}
	}
};

/**
 * Responsive default settings for initialisation
 *
 * @namespace
 * @name Responsive.defaults
 * @static
 */
Responsive.defaults = {
	/**
	 * List of breakpoints for the instance. Note that this means that each
	 * instance can have its own breakpoints. Additionally, the breakpoints
	 * cannot be changed once an instance has been creased.
	 *
	 * @type {Array}
	 * @default Takes the value of `Responsive.breakpoints`
	 */
	breakpoints: Responsive.breakpoints,

	/**
	 * Enable / disable auto hiding calculations. It can help to increase
	 * performance slightly if you disable this option, but all columns would
	 * need to have breakpoint classes assigned to them
	 *
	 * @type {Boolean}
	 * @default  `true`
	 */
	auto: true,

	/**
	 * Details control. If given as a string value, the `type` property of the
	 * default object is set to that value, and the defaults used for the rest
	 * of the object - this is for ease of implementation.
	 *
	 * The object consists of the following properties:
	 *
	 * * `display` - A function that is used to show and hide the hidden details
	 * * `renderer` - function that is called for display of the child row data.
	 *   The default function will show the data from the hidden columns
	 * * `target` - Used as the selector for what objects to attach the child
	 *   open / close to
	 * * `type` - `false` to disable the details display, `inline` or `column`
	 *   for the two control types
	 *
	 * @type {Object|string}
	 */
	details: {
		display: Responsive.display.childRow,

		renderer: Responsive.renderer.listHidden(),

		target: 0,

		type: 'inline'
	},

	/**
	 * Orthogonal data request option. This is used to define the data type
	 * requested when Responsive gets the data to show in the child row.
	 *
	 * @type {String}
	 */
	orthogonal: 'display'
};


/*
 * API
 */
var Api = $.fn.dataTable.Api;

// Doesn't do anything - work around for a bug in DT... Not documented
Api.register( 'responsive()', function () {
	return this;
} );

Api.register( 'responsive.index()', function ( li ) {
	li = $(li);

	return {
		column: li.data('dtr-index'),
		row:    li.parent().data('dtr-index')
	};
} );

Api.register( 'responsive.rebuild()', function () {
	return this.iterator( 'table', function ( ctx ) {
		if ( ctx._responsive ) {
			ctx._responsive._classLogic();
		}
	} );
} );

Api.register( 'responsive.recalc()', function () {
	return this.iterator( 'table', function ( ctx ) {
		if ( ctx._responsive ) {
			ctx._responsive._resizeAuto();
			ctx._responsive._resize();
		}
	} );
} );

Api.register( 'responsive.hasHidden()', function () {
	var ctx = this.context[0];

	return ctx._responsive ?
		$.inArray( false, ctx._responsive.s.current ) !== -1 :
		false;
} );

Api.registerPlural( 'columns().responsiveHidden()', 'column().responsiveHidden()', function () {
	return this.iterator( 'column', function ( settings, column ) {
		return settings._responsive ?
			settings._responsive.s.current[ column ] :
			false;
	}, 1 );
} );


/**
 * Version information
 *
 * @name Responsive.version
 * @static
 */
Responsive.version = '2.2.1-dev';


$.fn.dataTable.Responsive = Responsive;
$.fn.DataTable.Responsive = Responsive;

// Attach a listener to the document which listens for DataTables initialisation
// events so we can automatically initialise
$(document).on( 'preInit.dt.dtr', function (e, settings, json) {
	if ( e.namespace !== 'dt' ) {
		return;
	}

	if ( $(settings.nTable).hasClass( 'responsive' ) ||
		 $(settings.nTable).hasClass( 'dt-responsive' ) ||
		 settings.oInit.responsive ||
		 DataTable.defaults.responsive
	) {
		var init = settings.oInit.responsive;

		if ( init !== false ) {
			new Responsive( settings, $.isPlainObject( init ) ? init : {}  );
		}
	}
} );


return Responsive;
}));


/***/ }),
/* 265 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*!
 * jQuery contextMenu v2.2.3 - Plugin for simple contextMenu handling
 *
 * Version: v2.2.3
 *
 * Authors: Björn Brala (SWIS.nl), Rodney Rehm, Addy Osmani (patches for FF)
 * Web: http://swisnl.github.io/jQuery-contextMenu/
 *
 * Copyright (c) 2011-2016 SWIS BV and contributors
 *
 * Licensed under
 *   MIT License http://www.opensource.org/licenses/mit-license
 *   GPL v3 http://opensource.org/licenses/GPL-3.0
 *
 * Date: 2016-07-17T19:36:02.968Z
 */

(function (factory) {
    if (true) {
        // AMD. Register as anonymous module.
        !(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
    } else if (typeof exports === 'object') {
        // Node / CommonJS
        factory(require('jquery'));
    } else {
        // Browser globals.
        factory(jQuery);
    }
})(function ($) {

    'use strict';

    // TODO: -
    // ARIA stuff: menuitem, menuitemcheckbox und menuitemradio
    // create <menu> structure if $.support[htmlCommand || htmlMenuitem] and !opt.disableNative

    // determine html5 compatibility
    $.support.htmlMenuitem = ('HTMLMenuItemElement' in window);
    $.support.htmlCommand = ('HTMLCommandElement' in window);
    $.support.eventSelectstart = ('onselectstart' in document.documentElement);
    /* // should the need arise, test for css user-select
     $.support.cssUserSelect = (function(){
     var t = false,
     e = document.createElement('div');

     $.each('Moz|Webkit|Khtml|O|ms|Icab|'.split('|'), function(i, prefix) {
     var propCC = prefix + (prefix ? 'U' : 'u') + 'serSelect',
     prop = (prefix ? ('-' + prefix.toLowerCase() + '-') : '') + 'user-select';

     e.style.cssText = prop + ': text;';
     if (e.style[propCC] == 'text') {
     t = true;
     return false;
     }

     return true;
     });

     return t;
     })();
     */

    /* jshint ignore:start */
    if (!$.ui || !$.widget) {
        // duck punch $.cleanData like jQueryUI does to get that remove event
        $.cleanData = (function (orig) {
            return function (elems) {
                var events, elem, i;
                for (i = 0; elems[i] != null; i++) {
                    elem = elems[i];
                    try {
                        // Only trigger remove when necessary to save time
                        events = $._data(elem, 'events');
                        if (events && events.remove) {
                            $(elem).triggerHandler('remove');
                        }

                        // Http://bugs.jquery.com/ticket/8235
                    } catch (e) {}
                }
                orig(elems);
            };
        })($.cleanData);
    }
    /* jshint ignore:end */

    var // currently active contextMenu trigger
        $currentTrigger = null,
    // is contextMenu initialized with at least one menu?
        initialized = false,
    // window handle
        $win = $(window),
    // number of registered menus
        counter = 0,
    // mapping selector to namespace
        namespaces = {},
    // mapping namespace to options
        menus = {},
    // custom command type handlers
        types = {},
    // default values
        defaults = {
            // selector of contextMenu trigger
            selector: null,
            // where to append the menu to
            appendTo: null,
            // method to trigger context menu ["right", "left", "hover"]
            trigger: 'right',
            // hide menu when mouse leaves trigger / menu elements
            autoHide: false,
            // ms to wait before showing a hover-triggered context menu
            delay: 200,
            // flag denoting if a second trigger should simply move (true) or rebuild (false) an open menu
            // as long as the trigger happened on one of the trigger-element's child nodes
            reposition: true,

            // Default classname configuration to be able avoid conflicts in frameworks
            classNames : {

                hover: 'context-menu-hover', // Item hover
                disabled: 'context-menu-disabled', // Item disabled
                visible: 'context-menu-visible', // Item visible
                notSelectable: 'context-menu-not-selectable', // Item not selectable

                icon: 'context-menu-icon',
                iconEdit: 'context-menu-icon-edit',
                iconCut: 'context-menu-icon-cut',
                iconCopy: 'context-menu-icon-copy',
                iconPaste: 'context-menu-icon-paste',
                iconDelete: 'context-menu-icon-delete',
                iconAdd: 'context-menu-icon-add',
                iconQuit: 'context-menu-icon-quit'
            },

            // determine position to show menu at
            determinePosition: function ($menu) {
                // position to the lower middle of the trigger element
                if ($.ui && $.ui.position) {
                    // .position() is provided as a jQuery UI utility
                    // (...and it won't work on hidden elements)
                    $menu.css('display', 'block').position({
                        my: 'center top',
                        at: 'center bottom',
                        of: this,
                        offset: '0 5',
                        collision: 'fit'
                    }).css('display', 'none');
                } else {
                    // determine contextMenu position
                    var offset = this.offset();
                    offset.top += this.outerHeight();
                    offset.left += this.outerWidth() / 2 - $menu.outerWidth() / 2;
                    $menu.css(offset);
                }
            },
            // position menu
            position: function (opt, x, y) {
                var offset;
                // determine contextMenu position
                if (!x && !y) {
                    opt.determinePosition.call(this, opt.$menu);
                    return;
                } else if (x === 'maintain' && y === 'maintain') {
                    // x and y must not be changed (after re-show on command click)
                    offset = opt.$menu.position();
                } else {
                    // x and y are given (by mouse event)
                    offset = {top: y, left: x};
                }

                // correct offset if viewport demands it
                var bottom = $win.scrollTop() + $win.height(),
                    right = $win.scrollLeft() + $win.width(),
                    height = opt.$menu.outerHeight(),
                    width = opt.$menu.outerWidth();

                if (offset.top + height > bottom) {
                    offset.top -= height;
                }

                if (offset.top < 0) {
                    offset.top = 0;
                }

                if (offset.left + width > right) {
                    offset.left -= width;
                }

                if (offset.left < 0) {
                    offset.left = 0;
                }

                opt.$menu.css(offset);
            },
            // position the sub-menu
            positionSubmenu: function ($menu) {
                if ($.ui && $.ui.position) {
                    // .position() is provided as a jQuery UI utility
                    // (...and it won't work on hidden elements)
                    $menu.css('display', 'block').position({
                        my: 'left top',
                        at: 'right top',
                        of: this,
                        collision: 'flipfit fit'
                    }).css('display', '');
                } else {
                    // determine contextMenu position
                    var offset = {
                        top: 0,
                        left: this.outerWidth()
                    };
                    $menu.css(offset);
                }
            },
            // offset to add to zIndex
            zIndex: 1,
            // show hide animation settings
            animation: {
                duration: 50,
                show: 'slideDown',
                hide: 'slideUp'
            },
            // events
            events: {
                show: $.noop,
                hide: $.noop
            },
            // default callback
            callback: null,
            // list of contextMenu items
            items: {}
        },
    // mouse position for hover activation
        hoveract = {
            timer: null,
            pageX: null,
            pageY: null
        },
    // determine zIndex
        zindex = function ($t) {
            var zin = 0,
                $tt = $t;

            while (true) {
                zin = Math.max(zin, parseInt($tt.css('z-index'), 10) || 0);
                $tt = $tt.parent();
                if (!$tt || !$tt.length || 'html body'.indexOf($tt.prop('nodeName').toLowerCase()) > -1) {
                    break;
                }
            }
            return zin;
        },
    // event handlers
        handle = {
            // abort anything
            abortevent: function (e) {
                e.preventDefault();
                e.stopImmediatePropagation();
            },
            // contextmenu show dispatcher
            contextmenu: function (e) {
                var $this = $(this);

                // disable actual context-menu if we are using the right mouse button as the trigger
                if (e.data.trigger === 'right') {
                    e.preventDefault();
                    e.stopImmediatePropagation();
                }

                // abort native-triggered events unless we're triggering on right click
                if ((e.data.trigger !== 'right' && e.data.trigger !== 'demand') && e.originalEvent) {
                    return;
                }

                // Let the current contextmenu decide if it should show or not based on its own trigger settings
                if (e.mouseButton !== undefined && e.data) {
                    if (!(e.data.trigger === 'left' && e.mouseButton === 0) && !(e.data.trigger === 'right' && e.mouseButton === 2)) {
                        // Mouse click is not valid.
                        return;
                    }
                }

                // abort event if menu is visible for this trigger
                if ($this.hasClass('context-menu-active')) {
                    return;
                }

                if (!$this.hasClass('context-menu-disabled')) {
                    // theoretically need to fire a show event at <menu>
                    // http://www.whatwg.org/specs/web-apps/current-work/multipage/interactive-elements.html#context-menus
                    // var evt = jQuery.Event("show", { data: data, pageX: e.pageX, pageY: e.pageY, relatedTarget: this });
                    // e.data.$menu.trigger(evt);

                    $currentTrigger = $this;
                    if (e.data.build) {
                        var built = e.data.build($currentTrigger, e);
                        // abort if build() returned false
                        if (built === false) {
                            return;
                        }

                        // dynamically build menu on invocation
                        e.data = $.extend(true, {}, defaults, e.data, built || {});

                        // abort if there are no items to display
                        if (!e.data.items || $.isEmptyObject(e.data.items)) {
                            // Note: jQuery captures and ignores errors from event handlers
                            if (window.console) {
                                (console.error || console.log).call(console, 'No items specified to show in contextMenu');
                            }

                            throw new Error('No Items specified');
                        }

                        // backreference for custom command type creation
                        e.data.$trigger = $currentTrigger;

                        op.create(e.data);
                    }
                    var showMenu = false;
                    for (var item in e.data.items) {
                        if (e.data.items.hasOwnProperty(item)) {
                            var visible;
                            if ($.isFunction(e.data.items[item].visible)) {
                                visible = e.data.items[item].visible.call($(e.currentTarget), item, e.data);
                            } else if (typeof item.visible !== 'undefined') {
                                visible = e.data.items[item].visible === true;
                            } else {
                                visible = true;
                            }
                            if (visible) {
                                showMenu = true;
                            }
                        }
                    }
                    if (showMenu) {
                        // show menu
                        op.show.call($this, e.data, e.pageX, e.pageY);
                    }
                }
            },
            // contextMenu left-click trigger
            click: function (e) {
                e.preventDefault();
                e.stopImmediatePropagation();
                $(this).trigger($.Event('contextmenu', {data: e.data, pageX: e.pageX, pageY: e.pageY}));
            },
            // contextMenu right-click trigger
            mousedown: function (e) {
                // register mouse down
                var $this = $(this);

                // hide any previous menus
                if ($currentTrigger && $currentTrigger.length && !$currentTrigger.is($this)) {
                    $currentTrigger.data('contextMenu').$menu.trigger('contextmenu:hide');
                }

                // activate on right click
                if (e.button === 2) {
                    $currentTrigger = $this.data('contextMenuActive', true);
                }
            },
            // contextMenu right-click trigger
            mouseup: function (e) {
                // show menu
                var $this = $(this);
                if ($this.data('contextMenuActive') && $currentTrigger && $currentTrigger.length && $currentTrigger.is($this) && !$this.hasClass('context-menu-disabled')) {
                    e.preventDefault();
                    e.stopImmediatePropagation();
                    $currentTrigger = $this;
                    $this.trigger($.Event('contextmenu', {data: e.data, pageX: e.pageX, pageY: e.pageY}));
                }

                $this.removeData('contextMenuActive');
            },
            // contextMenu hover trigger
            mouseenter: function (e) {
                var $this = $(this),
                    $related = $(e.relatedTarget),
                    $document = $(document);

                // abort if we're coming from a menu
                if ($related.is('.context-menu-list') || $related.closest('.context-menu-list').length) {
                    return;
                }

                // abort if a menu is shown
                if ($currentTrigger && $currentTrigger.length) {
                    return;
                }

                hoveract.pageX = e.pageX;
                hoveract.pageY = e.pageY;
                hoveract.data = e.data;
                $document.on('mousemove.contextMenuShow', handle.mousemove);
                hoveract.timer = setTimeout(function () {
                    hoveract.timer = null;
                    $document.off('mousemove.contextMenuShow');
                    $currentTrigger = $this;
                    $this.trigger($.Event('contextmenu', {
                        data: hoveract.data,
                        pageX: hoveract.pageX,
                        pageY: hoveract.pageY
                    }));
                }, e.data.delay);
            },
            // contextMenu hover trigger
            mousemove: function (e) {
                hoveract.pageX = e.pageX;
                hoveract.pageY = e.pageY;
            },
            // contextMenu hover trigger
            mouseleave: function (e) {
                // abort if we're leaving for a menu
                var $related = $(e.relatedTarget);
                if ($related.is('.context-menu-list') || $related.closest('.context-menu-list').length) {
                    return;
                }

                try {
                    clearTimeout(hoveract.timer);
                } catch (e) {
                }

                hoveract.timer = null;
            },
            // click on layer to hide contextMenu
            layerClick: function (e) {
                var $this = $(this),
                    root = $this.data('contextMenuRoot'),
                    button = e.button,
                    x = e.pageX,
                    y = e.pageY,
                    target,
                    offset;

                e.preventDefault();
                e.stopImmediatePropagation();

                setTimeout(function () {
                    var $window;
                    var triggerAction = ((root.trigger === 'left' && button === 0) || (root.trigger === 'right' && button === 2));

                    // find the element that would've been clicked, wasn't the layer in the way
                    if (document.elementFromPoint && root.$layer) {
                        root.$layer.hide();
                        target = document.elementFromPoint(x - $win.scrollLeft(), y - $win.scrollTop());
                        root.$layer.show();
                    }

                    if (root.reposition && triggerAction) {
                        if (document.elementFromPoint) {
                            if (root.$trigger.is(target) || root.$trigger.has(target).length) {
                                root.position.call(root.$trigger, root, x, y);
                                return;
                            }
                        } else {
                            offset = root.$trigger.offset();
                            $window = $(window);
                            // while this looks kinda awful, it's the best way to avoid
                            // unnecessarily calculating any positions
                            offset.top += $window.scrollTop();
                            if (offset.top <= e.pageY) {
                                offset.left += $window.scrollLeft();
                                if (offset.left <= e.pageX) {
                                    offset.bottom = offset.top + root.$trigger.outerHeight();
                                    if (offset.bottom >= e.pageY) {
                                        offset.right = offset.left + root.$trigger.outerWidth();
                                        if (offset.right >= e.pageX) {
                                            // reposition
                                            root.position.call(root.$trigger, root, x, y);
                                            return;
                                        }
                                    }
                                }
                            }
                        }
                    }

                    if (target && triggerAction) {
                        root.$trigger.one('contextmenu:hidden', function () {
                            $(target).contextMenu({ x: x, y: y, button: button });
                        });
                    }

                    if (root != null && root.$menu != null) {
                        root.$menu.trigger('contextmenu:hide');
                    }
                }, 50);
            },
            // key handled :hover
            keyStop: function (e, opt) {
                if (!opt.isInput) {
                    e.preventDefault();
                }

                e.stopPropagation();
            },
            key: function (e) {

                var opt = {};

                // Only get the data from $currentTrigger if it exists
                if ($currentTrigger) {
                    opt = $currentTrigger.data('contextMenu') || {};
                }
                // If the trigger happen on a element that are above the contextmenu do this
                if (opt.zIndex === undefined) {
                    opt.zIndex = 0;
				}
                var targetZIndex = 0;
                var getZIndexOfTriggerTarget = function (target) {
					if (target.style.zIndex !== '') {
						targetZIndex = target.style.zIndex;
					} else {
						if (target.offsetParent !== null && target.offsetParent !== undefined) {
							getZIndexOfTriggerTarget(target.offsetParent);
						}
						else if (target.parentElement !== null && target.parentElement !== undefined) {
							getZIndexOfTriggerTarget(target.parentElement);
						}
					}
                };
                getZIndexOfTriggerTarget(e.target);
                // If targetZIndex is heigher then opt.zIndex dont progress any futher.
                // This is used to make sure that if you are using a dialog with a input / textarea / contenteditable div
                // and its above the contextmenu it wont steal keys events
                if (targetZIndex > opt.zIndex) {
                    return;
				}
                switch (e.keyCode) {
                    case 9:
                    case 38: // up
                        handle.keyStop(e, opt);
                        // if keyCode is [38 (up)] or [9 (tab) with shift]
                        if (opt.isInput) {
                            if (e.keyCode === 9 && e.shiftKey) {
                                e.preventDefault();
                                if(opt.$selected) {
                                    opt.$selected.find('input, textarea, select').blur();
                                }
                                opt.$menu.trigger('prevcommand');
                                return;
                            } else if (e.keyCode === 38 && opt.$selected.find('input, textarea, select').prop('type') === 'checkbox') {
                                // checkboxes don't capture this key
                                e.preventDefault();
                                return;
                            }
                        } else if (e.keyCode !== 9 || e.shiftKey) {
                            opt.$menu.trigger('prevcommand');
                            return;
                        }
                        break;
                    // omitting break;
                    // case 9: // tab - reached through omitted break;
                    case 40: // down
                        handle.keyStop(e, opt);
                        if (opt.isInput) {
                            if (e.keyCode === 9) {
                                e.preventDefault();
                                if(opt.$selected) {
                                    opt.$selected.find('input, textarea, select').blur();
                                }
                                opt.$menu.trigger('nextcommand');
                                return;
                            } else if (e.keyCode === 40 && opt.$selected.find('input, textarea, select').prop('type') === 'checkbox') {
                                // checkboxes don't capture this key
                                e.preventDefault();
                                return;
                            }
                        } else {
                            opt.$menu.trigger('nextcommand');
                            return;
                        }
                        break;

                    case 37: // left
                        handle.keyStop(e, opt);
                        if (opt.isInput || !opt.$selected || !opt.$selected.length) {
                            break;
                        }

                        if (!opt.$selected.parent().hasClass('context-menu-root')) {
                            var $parent = opt.$selected.parent().parent();
                            opt.$selected.trigger('contextmenu:blur');
                            opt.$selected = $parent;
                            return;
                        }
                        break;

                    case 39: // right
                        handle.keyStop(e, opt);
                        if (opt.isInput || !opt.$selected || !opt.$selected.length) {
                            break;
                        }

                        var itemdata = opt.$selected.data('contextMenu') || {};
                        if (itemdata.$menu && opt.$selected.hasClass('context-menu-submenu')) {
                            opt.$selected = null;
                            itemdata.$selected = null;
                            itemdata.$menu.trigger('nextcommand');
                            return;
                        }
                        break;

                    case 35: // end
                    case 36: // home
                        if (opt.$selected && opt.$selected.find('input, textarea, select').length) {
                            return;
                        } else {
                            (opt.$selected && opt.$selected.parent() || opt.$menu)
                                .children(':not(.' + opt.classNames.disabled + ', .' + opt.classNames.notSelectable + ')')[e.keyCode === 36 ? 'first' : 'last']()
                                .trigger('contextmenu:focus');
                            e.preventDefault();
                            return;
                        }
                        break;

                    case 13: // enter
                        handle.keyStop(e, opt);
                        if (opt.isInput) {
                            if (opt.$selected && !opt.$selected.is('textarea, select')) {
                                e.preventDefault();
                                return;
                            }
                            break;
                        }
                        if (typeof opt.$selected !== 'undefined' && opt.$selected !== null) {
                            opt.$selected.trigger('mouseup');
                        }
                        return;

                    case 32: // space
                    case 33: // page up
                    case 34: // page down
                        // prevent browser from scrolling down while menu is visible
                        handle.keyStop(e, opt);
                        return;

                    case 27: // esc
                        handle.keyStop(e, opt);
                        opt.$menu.trigger('contextmenu:hide');
                        return;

                    default: // 0-9, a-z
                        var k = (String.fromCharCode(e.keyCode)).toUpperCase();
                        if (opt.accesskeys && opt.accesskeys[k]) {
                            // according to the specs accesskeys must be invoked immediately
                            opt.accesskeys[k].$node.trigger(opt.accesskeys[k].$menu ? 'contextmenu:focus' : 'mouseup');
                            return;
                        }
                        break;
                }
                // pass event to selected item,
                // stop propagation to avoid endless recursion
                e.stopPropagation();
                if (typeof opt.$selected !== 'undefined' && opt.$selected !== null) {
                    opt.$selected.trigger(e);
                }
            },
            // select previous possible command in menu
            prevItem: function (e) {
                e.stopPropagation();
                var opt = $(this).data('contextMenu') || {};
                var root = $(this).data('contextMenuRoot') || {};

                // obtain currently selected menu
                if (opt.$selected) {
                    var $s = opt.$selected;
                    opt = opt.$selected.parent().data('contextMenu') || {};
                    opt.$selected = $s;
                }

                var $children = opt.$menu.children(),
                    $prev = !opt.$selected || !opt.$selected.prev().length ? $children.last() : opt.$selected.prev(),
                    $round = $prev;

                // skip disabled or hidden elements
                while ($prev.hasClass(root.classNames.disabled) || $prev.hasClass(root.classNames.notSelectable) || $prev.is(':hidden')) {
                    if ($prev.prev().length) {
                        $prev = $prev.prev();
                    } else {
                        $prev = $children.last();
                    }
                    if ($prev.is($round)) {
                        // break endless loop
                        return;
                    }
                }

                // leave current
                if (opt.$selected) {
                    handle.itemMouseleave.call(opt.$selected.get(0), e);
                }

                // activate next
                handle.itemMouseenter.call($prev.get(0), e);

                // focus input
                var $input = $prev.find('input, textarea, select');
                if ($input.length) {
                    $input.focus();
                }
            },
            // select next possible command in menu
            nextItem: function (e) {
                e.stopPropagation();
                var opt = $(this).data('contextMenu') || {};
                var root = $(this).data('contextMenuRoot') || {};

                // obtain currently selected menu
                if (opt.$selected) {
                    var $s = opt.$selected;
                    opt = opt.$selected.parent().data('contextMenu') || {};
                    opt.$selected = $s;
                }

                var $children = opt.$menu.children(),
                    $next = !opt.$selected || !opt.$selected.next().length ? $children.first() : opt.$selected.next(),
                    $round = $next;

                // skip disabled
                while ($next.hasClass(root.classNames.disabled) || $next.hasClass(root.classNames.notSelectable) || $next.is(':hidden')) {
                    if ($next.next().length) {
                        $next = $next.next();
                    } else {
                        $next = $children.first();
                    }
                    if ($next.is($round)) {
                        // break endless loop
                        return;
                    }
                }

                // leave current
                if (opt.$selected) {
                    handle.itemMouseleave.call(opt.$selected.get(0), e);
                }

                // activate next
                handle.itemMouseenter.call($next.get(0), e);

                // focus input
                var $input = $next.find('input, textarea, select');
                if ($input.length) {
                    $input.focus();
                }
            },
            // flag that we're inside an input so the key handler can act accordingly
            focusInput: function () {
                var $this = $(this).closest('.context-menu-item'),
                    data = $this.data(),
                    opt = data.contextMenu,
                    root = data.contextMenuRoot;

                root.$selected = opt.$selected = $this;
                root.isInput = opt.isInput = true;
            },
            // flag that we're inside an input so the key handler can act accordingly
            blurInput: function () {
                var $this = $(this).closest('.context-menu-item'),
                    data = $this.data(),
                    opt = data.contextMenu,
                    root = data.contextMenuRoot;

                root.isInput = opt.isInput = false;
            },
            // :hover on menu
            menuMouseenter: function () {
                var root = $(this).data().contextMenuRoot;
                root.hovering = true;
            },
            // :hover on menu
            menuMouseleave: function (e) {
                var root = $(this).data().contextMenuRoot;
                if (root.$layer && root.$layer.is(e.relatedTarget)) {
                    root.hovering = false;
                }
            },
            // :hover done manually so key handling is possible
            itemMouseenter: function (e) {
                var $this = $(this),
                    data = $this.data(),
                    opt = data.contextMenu,
                    root = data.contextMenuRoot;

                root.hovering = true;

                // abort if we're re-entering
                if (e && root.$layer && root.$layer.is(e.relatedTarget)) {
                    e.preventDefault();
                    e.stopImmediatePropagation();
                }

                // make sure only one item is selected
                (opt.$menu ? opt : root).$menu
                    .children('.' + root.classNames.hover).trigger('contextmenu:blur')
                    .children('.hover').trigger('contextmenu:blur');

                if ($this.hasClass(root.classNames.disabled) || $this.hasClass(root.classNames.notSelectable)) {
                    opt.$selected = null;
                    return;
                }

                $this.trigger('contextmenu:focus');
            },
            // :hover done manually so key handling is possible
            itemMouseleave: function (e) {
                var $this = $(this),
                    data = $this.data(),
                    opt = data.contextMenu,
                    root = data.contextMenuRoot;

                if (root !== opt && root.$layer && root.$layer.is(e.relatedTarget)) {
                    if (typeof root.$selected !== 'undefined' && root.$selected !== null) {
                        root.$selected.trigger('contextmenu:blur');
                    }
                    e.preventDefault();
                    e.stopImmediatePropagation();
                    root.$selected = opt.$selected = opt.$node;
                    return;
                }

                $this.trigger('contextmenu:blur');
            },
            // contextMenu item click
            itemClick: function (e) {
                var $this = $(this),
                    data = $this.data(),
                    opt = data.contextMenu,
                    root = data.contextMenuRoot,
                    key = data.contextMenuKey,
                    callback;

                // abort if the key is unknown or disabled or is a menu
                if (!opt.items[key] || $this.is('.' + root.classNames.disabled + ', .context-menu-submenu, .context-menu-separator, .' + root.classNames.notSelectable)) {
                    return;
                }

                e.preventDefault();
                e.stopImmediatePropagation();

                if ($.isFunction(opt.callbacks[key]) && Object.prototype.hasOwnProperty.call(opt.callbacks, key)) {
                    // item-specific callback
                    callback = opt.callbacks[key];
                } else if ($.isFunction(root.callback)) {
                    // default callback
                    callback = root.callback;
                } else {
                    // no callback, no action
                    return;
                }

                // hide menu if callback doesn't stop that
                if (callback.call(root.$trigger, key, root) !== false) {
                    root.$menu.trigger('contextmenu:hide');
                } else if (root.$menu.parent().length) {
                    op.update.call(root.$trigger, root);
                }
            },
            // ignore click events on input elements
            inputClick: function (e) {
                e.stopImmediatePropagation();
            },
            // hide <menu>
            hideMenu: function (e, data) {
                var root = $(this).data('contextMenuRoot');
                op.hide.call(root.$trigger, root, data && data.force);
            },
            // focus <command>
            focusItem: function (e) {
                e.stopPropagation();
                var $this = $(this),
                    data = $this.data(),
                    opt = data.contextMenu,
                    root = data.contextMenuRoot;

                if ($this.hasClass(root.classNames.disabled) || $this.hasClass(root.classNames.notSelectable)) {
                    return;
                }

                $this
                    .addClass([root.classNames.hover, root.classNames.visible].join(' '))
                    // select other items and included items
                    .parent().find('.context-menu-item').not($this)
                    .removeClass(root.classNames.visible)
                    .filter('.' + root.classNames.hover)
                    .trigger('contextmenu:blur');

                // remember selected
                opt.$selected = root.$selected = $this;

                // position sub-menu - do after show so dumb $.ui.position can keep up
                if (opt.$node) {
                    root.positionSubmenu.call(opt.$node, opt.$menu);
                }
            },
            // blur <command>
            blurItem: function (e) {
                e.stopPropagation();
                var $this = $(this),
                    data = $this.data(),
                    opt = data.contextMenu,
                    root = data.contextMenuRoot;

                if (opt.autoHide) { // for tablets and touch screens this needs to remain
                    $this.removeClass(root.classNames.visible);
                }
                $this.removeClass(root.classNames.hover);
                opt.$selected = null;
            }
        },
    // operations
        op = {
            show: function (opt, x, y) {
                var $trigger = $(this),
                    css = {};

                // hide any open menus
                $('#context-menu-layer').trigger('mousedown');

                // backreference for callbacks
                opt.$trigger = $trigger;

                // show event
                if (opt.events.show.call($trigger, opt) === false) {
                    $currentTrigger = null;
                    return;
                }

                // create or update context menu
                op.update.call($trigger, opt);

                // position menu
                opt.position.call($trigger, opt, x, y);

                // make sure we're in front
                if (opt.zIndex) {
                  var additionalZValue = opt.zIndex;
                  // If opt.zIndex is a function, call the function to get the right zIndex.
                  if (typeof opt.zIndex === 'function') {
                      additionalZValue = opt.zIndex.call($trigger, opt);
                  }
                  css.zIndex = zindex($trigger) + additionalZValue;
                }

                // add layer
                op.layer.call(opt.$menu, opt, css.zIndex);

                // adjust sub-menu zIndexes
                opt.$menu.find('ul').css('zIndex', css.zIndex + 1);

                // position and show context menu
                opt.$menu.css(css)[opt.animation.show](opt.animation.duration, function () {
                    $trigger.trigger('contextmenu:visible');
                });
                // make options available and set state
                $trigger
                    .data('contextMenu', opt)
                    .addClass('context-menu-active');

                // register key handler
                $(document).off('keydown.contextMenu').on('keydown.contextMenu', handle.key);
                // register autoHide handler
                if (opt.autoHide) {
                    // mouse position handler
                    $(document).on('mousemove.contextMenuAutoHide', function (e) {
                        // need to capture the offset on mousemove,
                        // since the page might've been scrolled since activation
                        var pos = $trigger.offset();
                        pos.right = pos.left + $trigger.outerWidth();
                        pos.bottom = pos.top + $trigger.outerHeight();

                        if (opt.$layer && !opt.hovering && (!(e.pageX >= pos.left && e.pageX <= pos.right) || !(e.pageY >= pos.top && e.pageY <= pos.bottom))) {
                            /* Additional hover check after short time, you might just miss the edge of the menu */
                            setTimeout(function () {
                                if (!opt.hovering && opt.$menu != null) { opt.$menu.trigger('contextmenu:hide'); }
                            }, 50);
                        }
                    });
                }
            },
            hide: function (opt, force) {
                var $trigger = $(this);
                if (!opt) {
                    opt = $trigger.data('contextMenu') || {};
                }

                // hide event
                if (!force && opt.events && opt.events.hide.call($trigger, opt) === false) {
                    return;
                }

                // remove options and revert state
                $trigger
                    .removeData('contextMenu')
                    .removeClass('context-menu-active');

                if (opt.$layer) {
                    // keep layer for a bit so the contextmenu event can be aborted properly by opera
                    setTimeout((function ($layer) {
                        return function () {
                            $layer.remove();
                        };
                    })(opt.$layer), 10);

                    try {
                        delete opt.$layer;
                    } catch (e) {
                        opt.$layer = null;
                    }
                }

                // remove handle
                $currentTrigger = null;
                // remove selected
                opt.$menu.find('.' + opt.classNames.hover).trigger('contextmenu:blur');
                opt.$selected = null;
                // collapse all submenus
                opt.$menu.find('.' + opt.classNames.visible).removeClass(opt.classNames.visible);
                // unregister key and mouse handlers
                // $(document).off('.contextMenuAutoHide keydown.contextMenu'); // http://bugs.jquery.com/ticket/10705
                $(document).off('.contextMenuAutoHide').off('keydown.contextMenu');
                // hide menu
                if(opt.$menu){
                    opt.$menu[opt.animation.hide](opt.animation.duration, function () {
                        // tear down dynamically built menu after animation is completed.
                        if (opt.build) {
                            opt.$menu.remove();
                            $.each(opt, function (key) {
                                switch (key) {
                                    case 'ns':
                                    case 'selector':
                                    case 'build':
                                    case 'trigger':
                                        return true;

                                    default:
                                        opt[key] = undefined;
                                        try {
                                            delete opt[key];
                                        } catch (e) {
                                        }
                                        return true;
                                }
                            });
                        }

                        setTimeout(function () {
                            $trigger.trigger('contextmenu:hidden');
                        }, 10);
                    });
                }
            },
            create: function (opt, root) {
                if (root === undefined) {
                    root = opt;
                }
                // create contextMenu
                opt.$menu = $('<ul class="context-menu-list"></ul>').addClass(opt.className || '').data({
                    'contextMenu': opt,
                    'contextMenuRoot': root
                });

                $.each(['callbacks', 'commands', 'inputs'], function (i, k) {
                    opt[k] = {};
                    if (!root[k]) {
                        root[k] = {};
                    }
                });

                if(!root.accesskeys){
                    root.accesskeys = {};
                }

                function createNameNode(item) {
                    var $name = $('<span></span>');
                    if (item._accesskey) {
                        if (item._beforeAccesskey) {
                            $name.append(document.createTextNode(item._beforeAccesskey));
                        }
                        $('<span></span>')
                            .addClass('context-menu-accesskey')
                            .text(item._accesskey)
                            .appendTo($name);
                        if (item._afterAccesskey) {
                            $name.append(document.createTextNode(item._afterAccesskey));
                        }
                    } else {
                        if (item.isHtmlName) {
                            // restrict use with access keys
                            if (typeof item.accesskey !== 'undefined') {
                                throw new Error('accesskeys are not compatible with HTML names and cannot be used together in the same item');
                            }
                            $name.html(item.name);
                        } else {
                            $name.text(item.name);
                        }
                    }
                    return $name;
                }

                // create contextMenu items
                $.each(opt.items, function (key, item) {
                    var $t = $('<li class="context-menu-item"></li>').addClass(item.className || ''),
                        $label = null,
                        $input = null;

                    // iOS needs to see a click-event bound to an element to actually
                    // have the TouchEvents infrastructure trigger the click event
                    $t.on('click', $.noop);

                    // Make old school string seperator a real item so checks wont be
                    // akward later.
                    // And normalize 'cm_separator' into 'cm_seperator'.
                    if (typeof item === 'string' || item.type === 'cm_separator') {
                        item = { type : 'cm_seperator' };
                    }

                    item.$node = $t.data({
                        'contextMenu': opt,
                        'contextMenuRoot': root,
                        'contextMenuKey': key
                    });

                    // register accesskey
                    // NOTE: the accesskey attribute should be applicable to any element, but Safari5 and Chrome13 still can't do that
                    if (typeof item.accesskey !== 'undefined') {
                        var aks = splitAccesskey(item.accesskey);
                        for (var i = 0, ak; ak = aks[i]; i++) {
                            if (!root.accesskeys[ak]) {
                                root.accesskeys[ak] = item;
                                var matched = item.name.match(new RegExp('^(.*?)(' + ak + ')(.*)$', 'i'));
                                if (matched) {
                                    item._beforeAccesskey = matched[1];
                                    item._accesskey = matched[2];
                                    item._afterAccesskey = matched[3];
                                }
                                break;
                            }
                        }
                    }

                    if (item.type && types[item.type]) {
                        // run custom type handler
                        types[item.type].call($t, item, opt, root);
                        // register commands
                        $.each([opt, root], function (i, k) {
                            k.commands[key] = item;
                            // Overwrite only if undefined or the item is appended to the root. This so it
                            // doesn't overwrite callbacks of root elements if the name is the same.
                            if ($.isFunction(item.callback) && (k.callbacks[key] === undefined || opt.type === undefined)) {
                                k.callbacks[key] = item.callback;
                            }
                        });
                    } else {
                        // add label for input
                        if (item.type === 'cm_seperator') {
                            $t.addClass('context-menu-separator ' + root.classNames.notSelectable);
                        } else if (item.type === 'html') {
                            $t.addClass('context-menu-html ' + root.classNames.notSelectable);
                        } else if (item.type) {
                            $label = $('<label></label>').appendTo($t);
                            createNameNode(item).appendTo($label);

                            $t.addClass('context-menu-input');
                            opt.hasTypes = true;
                            $.each([opt, root], function (i, k) {
                                k.commands[key] = item;
                                k.inputs[key] = item;
                            });
                        } else if (item.items) {
                            item.type = 'sub';
                        }

                        switch (item.type) {
                            case 'cm_seperator':
                                break;

                            case 'text':
                                $input = $('<input type="text" value="1" name="" value="">')
                                    .attr('name', 'context-menu-input-' + key)
                                    .val(item.value || '')
                                    .appendTo($label);
                                break;

                            case 'textarea':
                                $input = $('<textarea name=""></textarea>')
                                    .attr('name', 'context-menu-input-' + key)
                                    .val(item.value || '')
                                    .appendTo($label);

                                if (item.height) {
                                    $input.height(item.height);
                                }
                                break;

                            case 'checkbox':
                                $input = $('<input type="checkbox" value="1" name="" value="">')
                                    .attr('name', 'context-menu-input-' + key)
                                    .val(item.value || '')
                                    .prop('checked', !!item.selected)
                                    .prependTo($label);
                                break;

                            case 'radio':
                                $input = $('<input type="radio" value="1" name="" value="">')
                                    .attr('name', 'context-menu-input-' + item.radio)
                                    .val(item.value || '')
                                    .prop('checked', !!item.selected)
                                    .prependTo($label);
                                break;

                            case 'select':
                                $input = $('<select name="">')
                                    .attr('name', 'context-menu-input-' + key)
                                    .appendTo($label);
                                if (item.options) {
                                    $.each(item.options, function (value, text) {
                                        $('<option></option>').val(value).text(text).appendTo($input);
                                    });
                                    $input.val(item.selected);
                                }
                                break;

                            case 'sub':
                                createNameNode(item).appendTo($t);

                                item.appendTo = item.$node;
                                op.create(item, root);
                                $t.data('contextMenu', item).addClass('context-menu-submenu');
                                item.callback = null;
                                break;

                            case 'html':
                                $(item.html).appendTo($t);
                                break;

                            default:
                                $.each([opt, root], function (i, k) {
                                    k.commands[key] = item;
                                    // Overwrite only if undefined or the item is appended to the root. This so it
                                    // doesn't overwrite callbacks of root elements if the name is the same.
                                    if ($.isFunction(item.callback) && (k.callbacks[key] === undefined || opt.type === undefined)) {
                                        k.callbacks[key] = item.callback;
                                    }
                                });
                                createNameNode(item).appendTo($t);
                                break;
                        }

                        // disable key listener in <input>
                        if (item.type && item.type !== 'sub' && item.type !== 'html' && item.type !== 'cm_seperator') {
                            $input
                                .on('focus', handle.focusInput)
                                .on('blur', handle.blurInput);

                            if (item.events) {
                                $input.on(item.events, opt);
                            }
                        }

                        // add icons
                        if (item.icon) {
                            if ($.isFunction(item.icon)) {
                                item._icon = item.icon.call(this, this, $t, key, item);
                            } else {
                                if ( typeof(item.icon) === 'string' && item.icon.substring(0,3) == 'fa-' ) {
                                    // to enable font awesome
                                    item._icon = root.classNames.icon + ' ' + root.classNames.icon + '--fa fa ' + item.icon;
                                } else {
                                    item._icon = root.classNames.icon + ' ' + root.classNames.icon + '-' + item.icon;
                                }
                            }
                            $t.addClass(item._icon);
                        }
                    }

                    // cache contained elements
                    item.$input = $input;
                    item.$label = $label;

                    // attach item to menu
                    $t.appendTo(opt.$menu);

                    // Disable text selection
                    if (!opt.hasTypes && $.support.eventSelectstart) {
                        // browsers support user-select: none,
                        // IE has a special event for text-selection
                        // browsers supporting neither will not be preventing text-selection
                        $t.on('selectstart.disableTextSelect', handle.abortevent);
                    }
                });
                // attach contextMenu to <body> (to bypass any possible overflow:hidden issues on parents of the trigger element)
                if (!opt.$node) {
                    opt.$menu.css('display', 'none').addClass('context-menu-root');
                }
                opt.$menu.appendTo(opt.appendTo || document.body);
            },
            resize: function ($menu, nested) {
                var domMenu;
                // determine widths of submenus, as CSS won't grow them automatically
                // position:absolute within position:absolute; min-width:100; max-width:200; results in width: 100;
                // kinda sucks hard...

                // determine width of absolutely positioned element
                $menu.css({position: 'absolute', display: 'block'});
                // don't apply yet, because that would break nested elements' widths
                $menu.data('width',
                    (domMenu = $menu.get(0)).getBoundingClientRect ?
                        Math.ceil(domMenu.getBoundingClientRect().width) :
                        $menu.outerWidth() + 1); // outerWidth() returns rounded pixels
                // reset styles so they allow nested elements to grow/shrink naturally
                $menu.css({
                    position: 'static',
                    minWidth: '0px',
                    maxWidth: '100000px'
                });
                // identify width of nested menus
                $menu.find('> li > ul').each(function () {
                    op.resize($(this), true);
                });
                // reset and apply changes in the end because nested
                // elements' widths wouldn't be calculatable otherwise
                if (!nested) {
                    $menu.find('ul').addBack().css({
                        position: '',
                        display: '',
                        minWidth: '',
                        maxWidth: ''
                    }).outerWidth(function () {
                        return $(this).data('width');
                    });
                }
            },
            update: function (opt, root) {
                var $trigger = this;
                if (root === undefined) {
                    root = opt;
                    op.resize(opt.$menu);
                }
                // re-check disabled for each item
                opt.$menu.children().each(function () {
                    var $item = $(this),
                        key = $item.data('contextMenuKey'),
                        item = opt.items[key],
                        disabled = ($.isFunction(item.disabled) && item.disabled.call($trigger, key, root)) || item.disabled === true,
                        visible;
                    if ($.isFunction(item.visible)) {
                        visible = item.visible.call($trigger, key, root);
                    } else if (typeof item.visible !== 'undefined') {
                        visible = item.visible === true;
                    } else {
                        visible = true;
                    }
                    $item[visible ? 'show' : 'hide']();

                    // dis- / enable item
                    $item[disabled ? 'addClass' : 'removeClass'](root.classNames.disabled);

                    if ($.isFunction(item.icon)) {
                        $item.removeClass(item._icon);
                        item._icon = item.icon.call(this, $trigger, $item, key, item);
                        $item.addClass(item._icon);
                    }

                    if (item.type) {
                        // dis- / enable input elements
                        $item.find('input, select, textarea').prop('disabled', disabled);

                        // update input states
                        switch (item.type) {
                            case 'text':
                            case 'textarea':
                                item.$input.val(item.value || '');
                                break;

                            case 'checkbox':
                            case 'radio':
                                item.$input.val(item.value || '').prop('checked', !!item.selected);
                                break;

                            case 'select':
                                item.$input.val(item.selected || '');
                                break;
                        }
                    }

                    if (item.$menu) {
                        // update sub-menu
                        op.update.call($trigger, item, root);
                    }
                });
            },
            layer: function (opt, zIndex) {
                // add transparent layer for click area
                // filter and background for Internet Explorer, Issue #23
                var $layer = opt.$layer = $('<div id="context-menu-layer" style="position:fixed; z-index:' + zIndex + '; top:0; left:0; opacity: 0; filter: alpha(opacity=0); background-color: #000;"></div>')
                    .css({height: $win.height(), width: $win.width(), display: 'block'})
                    .data('contextMenuRoot', opt)
                    .insertBefore(this)
                    .on('contextmenu', handle.abortevent)
                    .on('mousedown', handle.layerClick);

                // IE6 doesn't know position:fixed;
                if (document.body.style.maxWidth === undefined) { // IE6 doesn't support maxWidth
                    $layer.css({
                        'position': 'absolute',
                        'height': $(document).height()
                    });
                }

                return $layer;
            }
        };

    // split accesskey according to http://www.whatwg.org/specs/web-apps/current-work/multipage/editing.html#assigned-access-key
    function splitAccesskey(val) {
        var t = val.split(/\s+/),
            keys = [];

        for (var i = 0, k; k = t[i]; i++) {
            k = k.charAt(0).toUpperCase(); // first character only
            // theoretically non-accessible characters should be ignored, but different systems, different keyboard layouts, ... screw it.
            // a map to look up already used access keys would be nice
            keys.push(k);
        }

        return keys;
    }

// handle contextMenu triggers
    $.fn.contextMenu = function (operation) {
        var $t = this, $o = operation;
        if (this.length > 0) {  // this is not a build on demand menu
            if (operation === undefined) {
                this.first().trigger('contextmenu');
            } else if (operation.x !== undefined && operation.y !== undefined) {
                this.first().trigger($.Event('contextmenu', { pageX: operation.x, pageY: operation.y, mouseButton: operation.button }));
            } else if (operation === 'hide') {
                var $menu = this.first().data('contextMenu') ? this.first().data('contextMenu').$menu : null;
                if($menu){
                    $menu.trigger('contextmenu:hide');
                }
            } else if (operation === 'destroy') {
                $.contextMenu('destroy', {context: this});
            } else if ($.isPlainObject(operation)) {
                operation.context = this;
                $.contextMenu('create', operation);
            } else if (operation) {
                this.removeClass('context-menu-disabled');
            } else if (!operation) {
                this.addClass('context-menu-disabled');
            }
        } else {
            $.each(menus, function () {
                if (this.selector === $t.selector) {
                    $o.data = this;

                    $.extend($o.data, {trigger: 'demand'});
                }
            });

            handle.contextmenu.call($o.target, $o);
        }

        return this;
    };

    // manage contextMenu instances
    $.contextMenu = function (operation, options) {
        if (typeof operation !== 'string') {
            options = operation;
            operation = 'create';
        }

        if (typeof options === 'string') {
            options = {selector: options};
        } else if (options === undefined) {
            options = {};
        }

        // merge with default options
        var o = $.extend(true, {}, defaults, options || {});
        var $document = $(document);
        var $context = $document;
        var _hasContext = false;

        if (!o.context || !o.context.length) {
            o.context = document;
        } else {
            // you never know what they throw at you...
            $context = $(o.context).first();
            o.context = $context.get(0);
            _hasContext = o.context !== document;
        }

        switch (operation) {
            case 'create':
                // no selector no joy
                if (!o.selector) {
                    throw new Error('No selector specified');
                }
                // make sure internal classes are not bound to
                if (o.selector.match(/.context-menu-(list|item|input)($|\s)/)) {
                    throw new Error('Cannot bind to selector "' + o.selector + '" as it contains a reserved className');
                }
                if (!o.build && (!o.items || $.isEmptyObject(o.items))) {
                    throw new Error('No Items specified');
                }
                counter++;
                o.ns = '.contextMenu' + counter;
                if (!_hasContext) {
                    namespaces[o.selector] = o.ns;
                }
                menus[o.ns] = o;

                // default to right click
                if (!o.trigger) {
                    o.trigger = 'right';
                }

                if (!initialized) {
                    var itemClick = o.itemClickEvent === 'click' ? 'click.contextMenu' : 'mouseup.contextMenu';
                    var contextMenuItemObj = {
                            // 'mouseup.contextMenu': handle.itemClick,
                            // 'click.contextMenu': handle.itemClick,
                            'contextmenu:focus.contextMenu': handle.focusItem,
                            'contextmenu:blur.contextMenu': handle.blurItem,
                            'contextmenu.contextMenu': handle.abortevent,
                            'mouseenter.contextMenu': handle.itemMouseenter,
                            'mouseleave.contextMenu': handle.itemMouseleave
                        };
                    contextMenuItemObj[itemClick] = handle.itemClick;
                    // make sure item click is registered first
                    $document
                        .on({
                            'contextmenu:hide.contextMenu': handle.hideMenu,
                            'prevcommand.contextMenu': handle.prevItem,
                            'nextcommand.contextMenu': handle.nextItem,
                            'contextmenu.contextMenu': handle.abortevent,
                            'mouseenter.contextMenu': handle.menuMouseenter,
                            'mouseleave.contextMenu': handle.menuMouseleave
                        }, '.context-menu-list')
                        .on('mouseup.contextMenu', '.context-menu-input', handle.inputClick)
                        .on(contextMenuItemObj, '.context-menu-item');

                    initialized = true;
                }

                // engage native contextmenu event
                $context
                    .on('contextmenu' + o.ns, o.selector, o, handle.contextmenu);

                if (_hasContext) {
                    // add remove hook, just in case
                    $context.on('remove' + o.ns, function () {
                        $(this).contextMenu('destroy');
                    });
                }

                switch (o.trigger) {
                    case 'hover':
                        $context
                            .on('mouseenter' + o.ns, o.selector, o, handle.mouseenter)
                            .on('mouseleave' + o.ns, o.selector, o, handle.mouseleave);
                        break;

                    case 'left':
                        $context.on('click' + o.ns, o.selector, o, handle.click);
                        break;
                    /*
                     default:
                     // http://www.quirksmode.org/dom/events/contextmenu.html
                     $document
                     .on('mousedown' + o.ns, o.selector, o, handle.mousedown)
                     .on('mouseup' + o.ns, o.selector, o, handle.mouseup);
                     break;
                     */
                }

                // create menu
                if (!o.build) {
                    op.create(o);
                }
                break;

            case 'destroy':
                var $visibleMenu;
                if (_hasContext) {
                    // get proper options
                    var context = o.context;
                    $.each(menus, function (ns, o) {
                        if (o.context !== context) {
                            return true;
                        }

                        $visibleMenu = $('.context-menu-list').filter(':visible');
                        if ($visibleMenu.length && $visibleMenu.data().contextMenuRoot.$trigger.is($(o.context).find(o.selector))) {
                            $visibleMenu.trigger('contextmenu:hide', {force: true});
                        }

                        try {
                            if (menus[o.ns].$menu) {
                                menus[o.ns].$menu.remove();
                            }

                            delete menus[o.ns];
                        } catch (e) {
                            menus[o.ns] = null;
                        }

                        $(o.context).off(o.ns);

                        return true;
                    });
                } else if (!o.selector) {
                    $document.off('.contextMenu .contextMenuAutoHide');
                    $.each(menus, function (ns, o) {
                        $(o.context).off(o.ns);
                    });

                    namespaces = {};
                    menus = {};
                    counter = 0;
                    initialized = false;

                    $('#context-menu-layer, .context-menu-list').remove();
                } else if (namespaces[o.selector]) {
                    $visibleMenu = $('.context-menu-list').filter(':visible');
                    if ($visibleMenu.length && $visibleMenu.data().contextMenuRoot.$trigger.is(o.selector)) {
                        $visibleMenu.trigger('contextmenu:hide', {force: true});
                    }

                    try {
                        if (menus[namespaces[o.selector]].$menu) {
                            menus[namespaces[o.selector]].$menu.remove();
                        }

                        delete menus[namespaces[o.selector]];
                    } catch (e) {
                        menus[namespaces[o.selector]] = null;
                    }

                    $document.off(namespaces[o.selector]);
                }
                break;

            case 'html5':
                // if <command> or <menuitem> are not handled by the browser,
                // or options was a bool true,
                // initialize $.contextMenu for them
                if ((!$.support.htmlCommand && !$.support.htmlMenuitem) || (typeof options === 'boolean' && options)) {
                    $('menu[type="context"]').each(function () {
                        if (this.id) {
                            $.contextMenu({
                                selector: '[contextmenu=' + this.id + ']',
                                items: $.contextMenu.fromMenu(this)
                            });
                        }
                    }).css('display', 'none');
                }
                break;

            default:
                throw new Error('Unknown operation "' + operation + '"');
        }

        return this;
    };

// import values into <input> commands
    $.contextMenu.setInputValues = function (opt, data) {
        if (data === undefined) {
            data = {};
        }

        $.each(opt.inputs, function (key, item) {
            switch (item.type) {
                case 'text':
                case 'textarea':
                    item.value = data[key] || '';
                    break;

                case 'checkbox':
                    item.selected = data[key] ? true : false;
                    break;

                case 'radio':
                    item.selected = (data[item.radio] || '') === item.value;
                    break;

                case 'select':
                    item.selected = data[key] || '';
                    break;
            }
        });
    };

// export values from <input> commands
    $.contextMenu.getInputValues = function (opt, data) {
        if (data === undefined) {
            data = {};
        }

        $.each(opt.inputs, function (key, item) {
            switch (item.type) {
                case 'text':
                case 'textarea':
                case 'select':
                    data[key] = item.$input.val();
                    break;

                case 'checkbox':
                    data[key] = item.$input.prop('checked');
                    break;

                case 'radio':
                    if (item.$input.prop('checked')) {
                        data[item.radio] = item.value;
                    }
                    break;
            }
        });

        return data;
    };

// find <label for="xyz">
    function inputLabel(node) {
        return (node.id && $('label[for="' + node.id + '"]').val()) || node.name;
    }

// convert <menu> to items object
    function menuChildren(items, $children, counter) {
        if (!counter) {
            counter = 0;
        }

        $children.each(function () {
            var $node = $(this),
                node = this,
                nodeName = this.nodeName.toLowerCase(),
                label,
                item;

            // extract <label><input>
            if (nodeName === 'label' && $node.find('input, textarea, select').length) {
                label = $node.text();
                $node = $node.children().first();
                node = $node.get(0);
                nodeName = node.nodeName.toLowerCase();
            }

            /*
             * <menu> accepts flow-content as children. that means <embed>, <canvas> and such are valid menu items.
             * Not being the sadistic kind, $.contextMenu only accepts:
             * <command>, <menuitem>, <hr>, <span>, <p> <input [text, radio, checkbox]>, <textarea>, <select> and of course <menu>.
             * Everything else will be imported as an html node, which is not interfaced with contextMenu.
             */

            // http://www.whatwg.org/specs/web-apps/current-work/multipage/commands.html#concept-command
            switch (nodeName) {
                // http://www.whatwg.org/specs/web-apps/current-work/multipage/interactive-elements.html#the-menu-element
                case 'menu':
                    item = {name: $node.attr('label'), items: {}};
                    counter = menuChildren(item.items, $node.children(), counter);
                    break;

                // http://www.whatwg.org/specs/web-apps/current-work/multipage/commands.html#using-the-a-element-to-define-a-command
                case 'a':
                // http://www.whatwg.org/specs/web-apps/current-work/multipage/commands.html#using-the-button-element-to-define-a-command
                case 'button':
                    item = {
                        name: $node.text(),
                        disabled: !!$node.attr('disabled'),
                        callback: (function () {
                            return function () {
                                $node.click();
                            };
                        })()
                    };
                    break;

                // http://www.whatwg.org/specs/web-apps/current-work/multipage/commands.html#using-the-command-element-to-define-a-command

                case 'menuitem':
                case 'command':
                    switch ($node.attr('type')) {
                        case undefined:
                        case 'command':
                        case 'menuitem':
                            item = {
                                name: $node.attr('label'),
                                disabled: !!$node.attr('disabled'),
                                icon: $node.attr('icon'),
                                callback: (function () {
                                    return function () {
                                        $node.click();
                                    };
                                })()
                            };
                            break;

                        case 'checkbox':
                            item = {
                                type: 'checkbox',
                                disabled: !!$node.attr('disabled'),
                                name: $node.attr('label'),
                                selected: !!$node.attr('checked')
                            };
                            break;
                        case 'radio':
                            item = {
                                type: 'radio',
                                disabled: !!$node.attr('disabled'),
                                name: $node.attr('label'),
                                radio: $node.attr('radiogroup'),
                                value: $node.attr('id'),
                                selected: !!$node.attr('checked')
                            };
                            break;

                        default:
                            item = undefined;
                    }
                    break;

                case 'hr':
                    item = '-------';
                    break;

                case 'input':
                    switch ($node.attr('type')) {
                        case 'text':
                            item = {
                                type: 'text',
                                name: label || inputLabel(node),
                                disabled: !!$node.attr('disabled'),
                                value: $node.val()
                            };
                            break;

                        case 'checkbox':
                            item = {
                                type: 'checkbox',
                                name: label || inputLabel(node),
                                disabled: !!$node.attr('disabled'),
                                selected: !!$node.attr('checked')
                            };
                            break;

                        case 'radio':
                            item = {
                                type: 'radio',
                                name: label || inputLabel(node),
                                disabled: !!$node.attr('disabled'),
                                radio: !!$node.attr('name'),
                                value: $node.val(),
                                selected: !!$node.attr('checked')
                            };
                            break;

                        default:
                            item = undefined;
                            break;
                    }
                    break;

                case 'select':
                    item = {
                        type: 'select',
                        name: label || inputLabel(node),
                        disabled: !!$node.attr('disabled'),
                        selected: $node.val(),
                        options: {}
                    };
                    $node.children().each(function () {
                        item.options[this.value] = $(this).text();
                    });
                    break;

                case 'textarea':
                    item = {
                        type: 'textarea',
                        name: label || inputLabel(node),
                        disabled: !!$node.attr('disabled'),
                        value: $node.val()
                    };
                    break;

                case 'label':
                    break;

                default:
                    item = {type: 'html', html: $node.clone(true)};
                    break;
            }

            if (item) {
                counter++;
                items['key' + counter] = item;
            }
        });

        return counter;
    }

// convert html5 menu
    $.contextMenu.fromMenu = function (element) {
        var $this = $(element),
            items = {};

        menuChildren(items, $this.children());

        return items;
    };

// make defaults accessible
    $.contextMenu.defaults = defaults;
    $.contextMenu.types = types;
// export internal functions - undocumented, for hacking only!
    $.contextMenu.handle = handle;
    $.contextMenu.op = op;
    $.contextMenu.menus = menus;


});


/***/ }),
/* 266 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;( function( factory ) {
	if ( true ) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [ __webpack_require__(0) ], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		factory( jQuery );
	}
} ( function( $ ) {

$.ui = $.ui || {};

return $.ui.version = "1.12.0";

} ) );


/***/ }),
/* 267 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*!
 * jQuery UI Widget 1.12.0
 * http://jqueryui.com
 *
 * Copyright jQuery Foundation and other contributors
 * Released under the MIT license.
 * http://jquery.org/license
 */

//>>label: Widget
//>>group: Core
//>>description: Provides a factory for creating stateful widgets with a common API.
//>>docs: http://api.jqueryui.com/jQuery.widget/
//>>demos: http://jqueryui.com/widget/

( function( factory ) {
	if ( true ) {

		// AMD. Register as an anonymous module.
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [ __webpack_require__(0), __webpack_require__(266) ], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else {

		// Browser globals
		factory( jQuery );
	}
}( function( $ ) {

var widgetUuid = 0;
var widgetSlice = Array.prototype.slice;

$.cleanData = ( function( orig ) {
	return function( elems ) {
		var events, elem, i;
		for ( i = 0; ( elem = elems[ i ] ) != null; i++ ) {
			try {

				// Only trigger remove when necessary to save time
				events = $._data( elem, "events" );
				if ( events && events.remove ) {
					$( elem ).triggerHandler( "remove" );
				}

			// Http://bugs.jquery.com/ticket/8235
			} catch ( e ) {}
		}
		orig( elems );
	};
} )( $.cleanData );

$.widget = function( name, base, prototype ) {
	var existingConstructor, constructor, basePrototype;

	// ProxiedPrototype allows the provided prototype to remain unmodified
	// so that it can be used as a mixin for multiple widgets (#8876)
	var proxiedPrototype = {};

	var namespace = name.split( "." )[ 0 ];
	name = name.split( "." )[ 1 ];
	var fullName = namespace + "-" + name;

	if ( !prototype ) {
		prototype = base;
		base = $.Widget;
	}

	if ( $.isArray( prototype ) ) {
		prototype = $.extend.apply( null, [ {} ].concat( prototype ) );
	}

	// Create selector for plugin
	$.expr[ ":" ][ fullName.toLowerCase() ] = function( elem ) {
		return !!$.data( elem, fullName );
	};

	$[ namespace ] = $[ namespace ] || {};
	existingConstructor = $[ namespace ][ name ];
	constructor = $[ namespace ][ name ] = function( options, element ) {

		// Allow instantiation without "new" keyword
		if ( !this._createWidget ) {
			return new constructor( options, element );
		}

		// Allow instantiation without initializing for simple inheritance
		// must use "new" keyword (the code above always passes args)
		if ( arguments.length ) {
			this._createWidget( options, element );
		}
	};

	// Extend with the existing constructor to carry over any static properties
	$.extend( constructor, existingConstructor, {
		version: prototype.version,

		// Copy the object used to create the prototype in case we need to
		// redefine the widget later
		_proto: $.extend( {}, prototype ),

		// Track widgets that inherit from this widget in case this widget is
		// redefined after a widget inherits from it
		_childConstructors: []
	} );

	basePrototype = new base();

	// We need to make the options hash a property directly on the new instance
	// otherwise we'll modify the options hash on the prototype that we're
	// inheriting from
	basePrototype.options = $.widget.extend( {}, basePrototype.options );
	$.each( prototype, function( prop, value ) {
		if ( !$.isFunction( value ) ) {
			proxiedPrototype[ prop ] = value;
			return;
		}
		proxiedPrototype[ prop ] = ( function() {
			function _super() {
				return base.prototype[ prop ].apply( this, arguments );
			}

			function _superApply( args ) {
				return base.prototype[ prop ].apply( this, args );
			}

			return function() {
				var __super = this._super;
				var __superApply = this._superApply;
				var returnValue;

				this._super = _super;
				this._superApply = _superApply;

				returnValue = value.apply( this, arguments );

				this._super = __super;
				this._superApply = __superApply;

				return returnValue;
			};
		} )();
	} );
	constructor.prototype = $.widget.extend( basePrototype, {

		// TODO: remove support for widgetEventPrefix
		// always use the name + a colon as the prefix, e.g., draggable:start
		// don't prefix for widgets that aren't DOM-based
		widgetEventPrefix: existingConstructor ? ( basePrototype.widgetEventPrefix || name ) : name
	}, proxiedPrototype, {
		constructor: constructor,
		namespace: namespace,
		widgetName: name,
		widgetFullName: fullName
	} );

	// If this widget is being redefined then we need to find all widgets that
	// are inheriting from it and redefine all of them so that they inherit from
	// the new version of this widget. We're essentially trying to replace one
	// level in the prototype chain.
	if ( existingConstructor ) {
		$.each( existingConstructor._childConstructors, function( i, child ) {
			var childPrototype = child.prototype;

			// Redefine the child widget using the same prototype that was
			// originally used, but inherit from the new version of the base
			$.widget( childPrototype.namespace + "." + childPrototype.widgetName, constructor,
				child._proto );
		} );

		// Remove the list of existing child constructors from the old constructor
		// so the old child constructors can be garbage collected
		delete existingConstructor._childConstructors;
	} else {
		base._childConstructors.push( constructor );
	}

	$.widget.bridge( name, constructor );

	return constructor;
};

$.widget.extend = function( target ) {
	var input = widgetSlice.call( arguments, 1 );
	var inputIndex = 0;
	var inputLength = input.length;
	var key;
	var value;

	for ( ; inputIndex < inputLength; inputIndex++ ) {
		for ( key in input[ inputIndex ] ) {
			value = input[ inputIndex ][ key ];
			if ( input[ inputIndex ].hasOwnProperty( key ) && value !== undefined ) {

				// Clone objects
				if ( $.isPlainObject( value ) ) {
					target[ key ] = $.isPlainObject( target[ key ] ) ?
						$.widget.extend( {}, target[ key ], value ) :

						// Don't extend strings, arrays, etc. with objects
						$.widget.extend( {}, value );

				// Copy everything else by reference
				} else {
					target[ key ] = value;
				}
			}
		}
	}
	return target;
};

$.widget.bridge = function( name, object ) {
	var fullName = object.prototype.widgetFullName || name;
	$.fn[ name ] = function( options ) {
		var isMethodCall = typeof options === "string";
		var args = widgetSlice.call( arguments, 1 );
		var returnValue = this;

		if ( isMethodCall ) {
			this.each( function() {
				var methodValue;
				var instance = $.data( this, fullName );

				if ( options === "instance" ) {
					returnValue = instance;
					return false;
				}

				if ( !instance ) {
					return $.error( "cannot call methods on " + name +
						" prior to initialization; " +
						"attempted to call method '" + options + "'" );
				}

				if ( !$.isFunction( instance[ options ] ) || options.charAt( 0 ) === "_" ) {
					return $.error( "no such method '" + options + "' for " + name +
						" widget instance" );
				}

				methodValue = instance[ options ].apply( instance, args );

				if ( methodValue !== instance && methodValue !== undefined ) {
					returnValue = methodValue && methodValue.jquery ?
						returnValue.pushStack( methodValue.get() ) :
						methodValue;
					return false;
				}
			} );
		} else {

			// Allow multiple hashes to be passed on init
			if ( args.length ) {
				options = $.widget.extend.apply( null, [ options ].concat( args ) );
			}

			this.each( function() {
				var instance = $.data( this, fullName );
				if ( instance ) {
					instance.option( options || {} );
					if ( instance._init ) {
						instance._init();
					}
				} else {
					$.data( this, fullName, new object( options, this ) );
				}
			} );
		}

		return returnValue;
	};
};

$.Widget = function( /* options, element */ ) {};
$.Widget._childConstructors = [];

$.Widget.prototype = {
	widgetName: "widget",
	widgetEventPrefix: "",
	defaultElement: "<div>",

	options: {
		classes: {},
		disabled: false,

		// Callbacks
		create: null
	},

	_createWidget: function( options, element ) {
		element = $( element || this.defaultElement || this )[ 0 ];
		this.element = $( element );
		this.uuid = widgetUuid++;
		this.eventNamespace = "." + this.widgetName + this.uuid;

		this.bindings = $();
		this.hoverable = $();
		this.focusable = $();
		this.classesElementLookup = {};

		if ( element !== this ) {
			$.data( element, this.widgetFullName, this );
			this._on( true, this.element, {
				remove: function( event ) {
					if ( event.target === element ) {
						this.destroy();
					}
				}
			} );
			this.document = $( element.style ?

				// Element within the document
				element.ownerDocument :

				// Element is window or document
				element.document || element );
			this.window = $( this.document[ 0 ].defaultView || this.document[ 0 ].parentWindow );
		}

		this.options = $.widget.extend( {},
			this.options,
			this._getCreateOptions(),
			options );

		this._create();

		if ( this.options.disabled ) {
			this._setOptionDisabled( this.options.disabled );
		}

		this._trigger( "create", null, this._getCreateEventData() );
		this._init();
	},

	_getCreateOptions: function() {
		return {};
	},

	_getCreateEventData: $.noop,

	_create: $.noop,

	_init: $.noop,

	destroy: function() {
		var that = this;

		this._destroy();
		$.each( this.classesElementLookup, function( key, value ) {
			that._removeClass( value, key );
		} );

		// We can probably remove the unbind calls in 2.0
		// all event bindings should go through this._on()
		this.element
			.off( this.eventNamespace )
			.removeData( this.widgetFullName );
		this.widget()
			.off( this.eventNamespace )
			.removeAttr( "aria-disabled" );

		// Clean up events and states
		this.bindings.off( this.eventNamespace );
	},

	_destroy: $.noop,

	widget: function() {
		return this.element;
	},

	option: function( key, value ) {
		var options = key;
		var parts;
		var curOption;
		var i;

		if ( arguments.length === 0 ) {

			// Don't return a reference to the internal hash
			return $.widget.extend( {}, this.options );
		}

		if ( typeof key === "string" ) {

			// Handle nested keys, e.g., "foo.bar" => { foo: { bar: ___ } }
			options = {};
			parts = key.split( "." );
			key = parts.shift();
			if ( parts.length ) {
				curOption = options[ key ] = $.widget.extend( {}, this.options[ key ] );
				for ( i = 0; i < parts.length - 1; i++ ) {
					curOption[ parts[ i ] ] = curOption[ parts[ i ] ] || {};
					curOption = curOption[ parts[ i ] ];
				}
				key = parts.pop();
				if ( arguments.length === 1 ) {
					return curOption[ key ] === undefined ? null : curOption[ key ];
				}
				curOption[ key ] = value;
			} else {
				if ( arguments.length === 1 ) {
					return this.options[ key ] === undefined ? null : this.options[ key ];
				}
				options[ key ] = value;
			}
		}

		this._setOptions( options );

		return this;
	},

	_setOptions: function( options ) {
		var key;

		for ( key in options ) {
			this._setOption( key, options[ key ] );
		}

		return this;
	},

	_setOption: function( key, value ) {
		if ( key === "classes" ) {
			this._setOptionClasses( value );
		}

		this.options[ key ] = value;

		if ( key === "disabled" ) {
			this._setOptionDisabled( value );
		}

		return this;
	},

	_setOptionClasses: function( value ) {
		var classKey, elements, currentElements;

		for ( classKey in value ) {
			currentElements = this.classesElementLookup[ classKey ];
			if ( value[ classKey ] === this.options.classes[ classKey ] ||
					!currentElements ||
					!currentElements.length ) {
				continue;
			}

			// We are doing this to create a new jQuery object because the _removeClass() call
			// on the next line is going to destroy the reference to the current elements being
			// tracked. We need to save a copy of this collection so that we can add the new classes
			// below.
			elements = $( currentElements.get() );
			this._removeClass( currentElements, classKey );

			// We don't use _addClass() here, because that uses this.options.classes
			// for generating the string of classes. We want to use the value passed in from
			// _setOption(), this is the new value of the classes option which was passed to
			// _setOption(). We pass this value directly to _classes().
			elements.addClass( this._classes( {
				element: elements,
				keys: classKey,
				classes: value,
				add: true
			} ) );
		}
	},

	_setOptionDisabled: function( value ) {
		this._toggleClass( this.widget(), this.widgetFullName + "-disabled", null, !!value );

		// If the widget is becoming disabled, then nothing is interactive
		if ( value ) {
			this._removeClass( this.hoverable, null, "ui-state-hover" );
			this._removeClass( this.focusable, null, "ui-state-focus" );
		}
	},

	enable: function() {
		return this._setOptions( { disabled: false } );
	},

	disable: function() {
		return this._setOptions( { disabled: true } );
	},

	_classes: function( options ) {
		var full = [];
		var that = this;

		options = $.extend( {
			element: this.element,
			classes: this.options.classes || {}
		}, options );

		function processClassString( classes, checkOption ) {
			var current, i;
			for ( i = 0; i < classes.length; i++ ) {
				current = that.classesElementLookup[ classes[ i ] ] || $();
				if ( options.add ) {
					current = $( $.unique( current.get().concat( options.element.get() ) ) );
				} else {
					current = $( current.not( options.element ).get() );
				}
				that.classesElementLookup[ classes[ i ] ] = current;
				full.push( classes[ i ] );
				if ( checkOption && options.classes[ classes[ i ] ] ) {
					full.push( options.classes[ classes[ i ] ] );
				}
			}
		}

		if ( options.keys ) {
			processClassString( options.keys.match( /\S+/g ) || [], true );
		}
		if ( options.extra ) {
			processClassString( options.extra.match( /\S+/g ) || [] );
		}

		return full.join( " " );
	},

	_removeClass: function( element, keys, extra ) {
		return this._toggleClass( element, keys, extra, false );
	},

	_addClass: function( element, keys, extra ) {
		return this._toggleClass( element, keys, extra, true );
	},

	_toggleClass: function( element, keys, extra, add ) {
		add = ( typeof add === "boolean" ) ? add : extra;
		var shift = ( typeof element === "string" || element === null ),
			options = {
				extra: shift ? keys : extra,
				keys: shift ? element : keys,
				element: shift ? this.element : element,
				add: add
			};
		options.element.toggleClass( this._classes( options ), add );
		return this;
	},

	_on: function( suppressDisabledCheck, element, handlers ) {
		var delegateElement;
		var instance = this;

		// No suppressDisabledCheck flag, shuffle arguments
		if ( typeof suppressDisabledCheck !== "boolean" ) {
			handlers = element;
			element = suppressDisabledCheck;
			suppressDisabledCheck = false;
		}

		// No element argument, shuffle and use this.element
		if ( !handlers ) {
			handlers = element;
			element = this.element;
			delegateElement = this.widget();
		} else {
			element = delegateElement = $( element );
			this.bindings = this.bindings.add( element );
		}

		$.each( handlers, function( event, handler ) {
			function handlerProxy() {

				// Allow widgets to customize the disabled handling
				// - disabled as an array instead of boolean
				// - disabled class as method for disabling individual parts
				if ( !suppressDisabledCheck &&
						( instance.options.disabled === true ||
						$( this ).hasClass( "ui-state-disabled" ) ) ) {
					return;
				}
				return ( typeof handler === "string" ? instance[ handler ] : handler )
					.apply( instance, arguments );
			}

			// Copy the guid so direct unbinding works
			if ( typeof handler !== "string" ) {
				handlerProxy.guid = handler.guid =
					handler.guid || handlerProxy.guid || $.guid++;
			}

			var match = event.match( /^([\w:-]*)\s*(.*)$/ );
			var eventName = match[ 1 ] + instance.eventNamespace;
			var selector = match[ 2 ];

			if ( selector ) {
				delegateElement.on( eventName, selector, handlerProxy );
			} else {
				element.on( eventName, handlerProxy );
			}
		} );
	},

	_off: function( element, eventName ) {
		eventName = ( eventName || "" ).split( " " ).join( this.eventNamespace + " " ) +
			this.eventNamespace;
		element.off( eventName ).off( eventName );

		// Clear the stack to avoid memory leaks (#10056)
		this.bindings = $( this.bindings.not( element ).get() );
		this.focusable = $( this.focusable.not( element ).get() );
		this.hoverable = $( this.hoverable.not( element ).get() );
	},

	_delay: function( handler, delay ) {
		function handlerProxy() {
			return ( typeof handler === "string" ? instance[ handler ] : handler )
				.apply( instance, arguments );
		}
		var instance = this;
		return setTimeout( handlerProxy, delay || 0 );
	},

	_hoverable: function( element ) {
		this.hoverable = this.hoverable.add( element );
		this._on( element, {
			mouseenter: function( event ) {
				this._addClass( $( event.currentTarget ), null, "ui-state-hover" );
			},
			mouseleave: function( event ) {
				this._removeClass( $( event.currentTarget ), null, "ui-state-hover" );
			}
		} );
	},

	_focusable: function( element ) {
		this.focusable = this.focusable.add( element );
		this._on( element, {
			focusin: function( event ) {
				this._addClass( $( event.currentTarget ), null, "ui-state-focus" );
			},
			focusout: function( event ) {
				this._removeClass( $( event.currentTarget ), null, "ui-state-focus" );
			}
		} );
	},

	_trigger: function( type, event, data ) {
		var prop, orig;
		var callback = this.options[ type ];

		data = data || {};
		event = $.Event( event );
		event.type = ( type === this.widgetEventPrefix ?
			type :
			this.widgetEventPrefix + type ).toLowerCase();

		// The original event may come from any element
		// so we need to reset the target on the new event
		event.target = this.element[ 0 ];

		// Copy original event properties over to the new event
		orig = event.originalEvent;
		if ( orig ) {
			for ( prop in orig ) {
				if ( !( prop in event ) ) {
					event[ prop ] = orig[ prop ];
				}
			}
		}

		this.element.trigger( event, data );
		return !( $.isFunction( callback ) &&
			callback.apply( this.element[ 0 ], [ event ].concat( data ) ) === false ||
			event.isDefaultPrevented() );
	}
};

$.each( { show: "fadeIn", hide: "fadeOut" }, function( method, defaultEffect ) {
	$.Widget.prototype[ "_" + method ] = function( element, options, callback ) {
		if ( typeof options === "string" ) {
			options = { effect: options };
		}

		var hasOptions;
		var effectName = !options ?
			method :
			options === true || typeof options === "number" ?
				defaultEffect :
				options.effect || defaultEffect;

		options = options || {};
		if ( typeof options === "number" ) {
			options = { duration: options };
		}

		hasOptions = !$.isEmptyObject( options );
		options.complete = callback;

		if ( options.delay ) {
			element.delay( options.delay );
		}

		if ( hasOptions && $.effects && $.effects.effect[ effectName ] ) {
			element[ method ]( options );
		} else if ( effectName !== method && element[ effectName ] ) {
			element[ effectName ]( options.duration, options.easing, callback );
		} else {
			element.queue( function( next ) {
				$( this )[ method ]();
				if ( callback ) {
					callback.call( element[ 0 ] );
				}
				next();
			} );
		}
	};
} );

return $.widget;

} ) );


/***/ }),
/* 268 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*!
 * jQuery Validation Plugin v1.15.1
 *
 * http://jqueryvalidation.org/
 *
 * Copyright (c) 2016 Jörn Zaefferer
 * Released under the MIT license
 */
(function( factory ) {
	if ( true ) {
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0), __webpack_require__(27)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else if (typeof module === "object" && module.exports) {
		module.exports = factory( require( "jquery" ) );
	} else {
		factory( jQuery );
	}
}(function( $ ) {

( function() {

	function stripHtml( value ) {

		// Remove html tags and space chars
		return value.replace( /<.[^<>]*?>/g, " " ).replace( /&nbsp;|&#160;/gi, " " )

		// Remove punctuation
		.replace( /[.(),;:!?%#$'\"_+=\/\-“”’]*/g, "" );
	}

	$.validator.addMethod( "maxWords", function( value, element, params ) {
		return this.optional( element ) || stripHtml( value ).match( /\b\w+\b/g ).length <= params;
	}, $.validator.format( "Please enter {0} words or less." ) );

	$.validator.addMethod( "minWords", function( value, element, params ) {
		return this.optional( element ) || stripHtml( value ).match( /\b\w+\b/g ).length >= params;
	}, $.validator.format( "Please enter at least {0} words." ) );

	$.validator.addMethod( "rangeWords", function( value, element, params ) {
		var valueStripped = stripHtml( value ),
			regex = /\b\w+\b/g;
		return this.optional( element ) || valueStripped.match( regex ).length >= params[ 0 ] && valueStripped.match( regex ).length <= params[ 1 ];
	}, $.validator.format( "Please enter between {0} and {1} words." ) );

}() );

// Accept a value from a file input based on a required mimetype
$.validator.addMethod( "accept", function( value, element, param ) {

	// Split mime on commas in case we have multiple types we can accept
	var typeParam = typeof param === "string" ? param.replace( /\s/g, "" ) : "image/*",
		optionalValue = this.optional( element ),
		i, file, regex;

	// Element is optional
	if ( optionalValue ) {
		return optionalValue;
	}

	if ( $( element ).attr( "type" ) === "file" ) {

		// Escape string to be used in the regex
		// see: http://stackoverflow.com/questions/3446170/escape-string-for-use-in-javascript-regex
		// Escape also "/*" as "/.*" as a wildcard
		typeParam = typeParam
				.replace( /[\-\[\]\/\{\}\(\)\+\?\.\\\^\$\|]/g, "\\$&" )
				.replace( /,/g, "|" )
				.replace( /\/\*/g, "/.*" );

		// Check if the element has a FileList before checking each file
		if ( element.files && element.files.length ) {
			regex = new RegExp( ".?(" + typeParam + ")$", "i" );
			for ( i = 0; i < element.files.length; i++ ) {
				file = element.files[ i ];

				// Grab the mimetype from the loaded file, verify it matches
				if ( !file.type.match( regex ) ) {
					return false;
				}
			}
		}
	}

	// Either return true because we've validated each file, or because the
	// browser does not support element.files and the FileList feature
	return true;
}, $.validator.format( "Please enter a value with a valid mimetype." ) );

$.validator.addMethod( "alphanumeric", function( value, element ) {
	return this.optional( element ) || /^\w+$/i.test( value );
}, "Letters, numbers, and underscores only please" );

/*
 * Dutch bank account numbers (not 'giro' numbers) have 9 digits
 * and pass the '11 check'.
 * We accept the notation with spaces, as that is common.
 * acceptable: 123456789 or 12 34 56 789
 */
$.validator.addMethod( "bankaccountNL", function( value, element ) {
	if ( this.optional( element ) ) {
		return true;
	}
	if ( !( /^[0-9]{9}|([0-9]{2} ){3}[0-9]{3}$/.test( value ) ) ) {
		return false;
	}

	// Now '11 check'
	var account = value.replace( / /g, "" ), // Remove spaces
		sum = 0,
		len = account.length,
		pos, factor, digit;
	for ( pos = 0; pos < len; pos++ ) {
		factor = len - pos;
		digit = account.substring( pos, pos + 1 );
		sum = sum + factor * digit;
	}
	return sum % 11 === 0;
}, "Please specify a valid bank account number" );

$.validator.addMethod( "bankorgiroaccountNL", function( value, element ) {
	return this.optional( element ) ||
			( $.validator.methods.bankaccountNL.call( this, value, element ) ) ||
			( $.validator.methods.giroaccountNL.call( this, value, element ) );
}, "Please specify a valid bank or giro account number" );

/**
 * BIC is the business identifier code (ISO 9362). This BIC check is not a guarantee for authenticity.
 *
 * BIC pattern: BBBBCCLLbbb (8 or 11 characters long; bbb is optional)
 *
 * Validation is case-insensitive. Please make sure to normalize input yourself.
 *
 * BIC definition in detail:
 * - First 4 characters - bank code (only letters)
 * - Next 2 characters - ISO 3166-1 alpha-2 country code (only letters)
 * - Next 2 characters - location code (letters and digits)
 *   a. shall not start with '0' or '1'
 *   b. second character must be a letter ('O' is not allowed) or digit ('0' for test (therefore not allowed), '1' denoting passive participant, '2' typically reverse-billing)
 * - Last 3 characters - branch code, optional (shall not start with 'X' except in case of 'XXX' for primary office) (letters and digits)
 */
$.validator.addMethod( "bic", function( value, element ) {
    return this.optional( element ) || /^([A-Z]{6}[A-Z2-9][A-NP-Z1-9])(X{3}|[A-WY-Z0-9][A-Z0-9]{2})?$/.test( value.toUpperCase() );
}, "Please specify a valid BIC code" );

/*
 * Código de identificación fiscal ( CIF ) is the tax identification code for Spanish legal entities
 * Further rules can be found in Spanish on http://es.wikipedia.org/wiki/C%C3%B3digo_de_identificaci%C3%B3n_fiscal
 */
$.validator.addMethod( "cifES", function( value ) {
	"use strict";

	var num = [],
		controlDigit, sum, i, count, tmp, secondDigit;

	value = value.toUpperCase();

	// Quick format test
	if ( !value.match( "((^[A-Z]{1}[0-9]{7}[A-Z0-9]{1}$|^[T]{1}[A-Z0-9]{8}$)|^[0-9]{8}[A-Z]{1}$)" ) ) {
		return false;
	}

	for ( i = 0; i < 9; i++ ) {
		num[ i ] = parseInt( value.charAt( i ), 10 );
	}

	// Algorithm for checking CIF codes
	sum = num[ 2 ] + num[ 4 ] + num[ 6 ];
	for ( count = 1; count < 8; count += 2 ) {
		tmp = ( 2 * num[ count ] ).toString();
		secondDigit = tmp.charAt( 1 );

		sum += parseInt( tmp.charAt( 0 ), 10 ) + ( secondDigit === "" ? 0 : parseInt( secondDigit, 10 ) );
	}

	/* The first (position 1) is a letter following the following criteria:
	 *	A. Corporations
	 *	B. LLCs
	 *	C. General partnerships
	 *	D. Companies limited partnerships
	 *	E. Communities of goods
	 *	F. Cooperative Societies
	 *	G. Associations
	 *	H. Communities of homeowners in horizontal property regime
	 *	J. Civil Societies
	 *	K. Old format
	 *	L. Old format
	 *	M. Old format
	 *	N. Nonresident entities
	 *	P. Local authorities
	 *	Q. Autonomous bodies, state or not, and the like, and congregations and religious institutions
	 *	R. Congregations and religious institutions (since 2008 ORDER EHA/451/2008)
	 *	S. Organs of State Administration and regions
	 *	V. Agrarian Transformation
	 *	W. Permanent establishments of non-resident in Spain
	 */
	if ( /^[ABCDEFGHJNPQRSUVW]{1}/.test( value ) ) {
		sum += "";
		controlDigit = 10 - parseInt( sum.charAt( sum.length - 1 ), 10 );
		value += controlDigit;
		return ( num[ 8 ].toString() === String.fromCharCode( 64 + controlDigit ) || num[ 8 ].toString() === value.charAt( value.length - 1 ) );
	}

	return false;

}, "Please specify a valid CIF number." );

/*
 * Brazillian CPF number (Cadastrado de Pessoas Físicas) is the equivalent of a Brazilian tax registration number.
 * CPF numbers have 11 digits in total: 9 numbers followed by 2 check numbers that are being used for validation.
 */
$.validator.addMethod( "cpfBR", function( value ) {

	// Removing special characters from value
	value = value.replace( /([~!@#$%^&*()_+=`{}\[\]\-|\\:;'<>,.\/? ])+/g, "" );

	// Checking value to have 11 digits only
	if ( value.length !== 11 ) {
		return false;
	}

	var sum = 0,
		firstCN, secondCN, checkResult, i;

	firstCN = parseInt( value.substring( 9, 10 ), 10 );
	secondCN = parseInt( value.substring( 10, 11 ), 10 );

	checkResult = function( sum, cn ) {
		var result = ( sum * 10 ) % 11;
		if ( ( result === 10 ) || ( result === 11 ) ) {
			result = 0;
		}
		return ( result === cn );
	};

	// Checking for dump data
	if ( value === "" ||
		value === "00000000000" ||
		value === "11111111111" ||
		value === "22222222222" ||
		value === "33333333333" ||
		value === "44444444444" ||
		value === "55555555555" ||
		value === "66666666666" ||
		value === "77777777777" ||
		value === "88888888888" ||
		value === "99999999999"
	) {
		return false;
	}

	// Step 1 - using first Check Number:
	for ( i = 1; i <= 9; i++ ) {
		sum = sum + parseInt( value.substring( i - 1, i ), 10 ) * ( 11 - i );
	}

	// If first Check Number (CN) is valid, move to Step 2 - using second Check Number:
	if ( checkResult( sum, firstCN ) ) {
		sum = 0;
		for ( i = 1; i <= 10; i++ ) {
			sum = sum + parseInt( value.substring( i - 1, i ), 10 ) * ( 12 - i );
		}
		return checkResult( sum, secondCN );
	}
	return false;

}, "Please specify a valid CPF number" );

// http://jqueryvalidation.org/creditcard-method/
// based on http://en.wikipedia.org/wiki/Luhn_algorithm
$.validator.addMethod( "creditcard", function( value, element ) {
	if ( this.optional( element ) ) {
		return "dependency-mismatch";
	}

	// Accept only spaces, digits and dashes
	if ( /[^0-9 \-]+/.test( value ) ) {
		return false;
	}

	var nCheck = 0,
		nDigit = 0,
		bEven = false,
		n, cDigit;

	value = value.replace( /\D/g, "" );

	// Basing min and max length on
	// http://developer.ean.com/general_info/Valid_Credit_Card_Types
	if ( value.length < 13 || value.length > 19 ) {
		return false;
	}

	for ( n = value.length - 1; n >= 0; n-- ) {
		cDigit = value.charAt( n );
		nDigit = parseInt( cDigit, 10 );
		if ( bEven ) {
			if ( ( nDigit *= 2 ) > 9 ) {
				nDigit -= 9;
			}
		}

		nCheck += nDigit;
		bEven = !bEven;
	}

	return ( nCheck % 10 ) === 0;
}, "Please enter a valid credit card number." );

/* NOTICE: Modified version of Castle.Components.Validator.CreditCardValidator
 * Redistributed under the the Apache License 2.0 at http://www.apache.org/licenses/LICENSE-2.0
 * Valid Types: mastercard, visa, amex, dinersclub, enroute, discover, jcb, unknown, all (overrides all other settings)
 */
$.validator.addMethod( "creditcardtypes", function( value, element, param ) {
	if ( /[^0-9\-]+/.test( value ) ) {
		return false;
	}

	value = value.replace( /\D/g, "" );

	var validTypes = 0x0000;

	if ( param.mastercard ) {
		validTypes |= 0x0001;
	}
	if ( param.visa ) {
		validTypes |= 0x0002;
	}
	if ( param.amex ) {
		validTypes |= 0x0004;
	}
	if ( param.dinersclub ) {
		validTypes |= 0x0008;
	}
	if ( param.enroute ) {
		validTypes |= 0x0010;
	}
	if ( param.discover ) {
		validTypes |= 0x0020;
	}
	if ( param.jcb ) {
		validTypes |= 0x0040;
	}
	if ( param.unknown ) {
		validTypes |= 0x0080;
	}
	if ( param.all ) {
		validTypes = 0x0001 | 0x0002 | 0x0004 | 0x0008 | 0x0010 | 0x0020 | 0x0040 | 0x0080;
	}
	if ( validTypes & 0x0001 && /^(5[12345])/.test( value ) ) { // Mastercard
		return value.length === 16;
	}
	if ( validTypes & 0x0002 && /^(4)/.test( value ) ) { // Visa
		return value.length === 16;
	}
	if ( validTypes & 0x0004 && /^(3[47])/.test( value ) ) { // Amex
		return value.length === 15;
	}
	if ( validTypes & 0x0008 && /^(3(0[012345]|[68]))/.test( value ) ) { // Dinersclub
		return value.length === 14;
	}
	if ( validTypes & 0x0010 && /^(2(014|149))/.test( value ) ) { // Enroute
		return value.length === 15;
	}
	if ( validTypes & 0x0020 && /^(6011)/.test( value ) ) { // Discover
		return value.length === 16;
	}
	if ( validTypes & 0x0040 && /^(3)/.test( value ) ) { // Jcb
		return value.length === 16;
	}
	if ( validTypes & 0x0040 && /^(2131|1800)/.test( value ) ) { // Jcb
		return value.length === 15;
	}
	if ( validTypes & 0x0080 ) { // Unknown
		return true;
	}
	return false;
}, "Please enter a valid credit card number." );

/**
 * Validates currencies with any given symbols by @jameslouiz
 * Symbols can be optional or required. Symbols required by default
 *
 * Usage examples:
 *  currency: ["£", false] - Use false for soft currency validation
 *  currency: ["$", false]
 *  currency: ["RM", false] - also works with text based symbols such as "RM" - Malaysia Ringgit etc
 *
 *  <input class="currencyInput" name="currencyInput">
 *
 * Soft symbol checking
 *  currencyInput: {
 *     currency: ["$", false]
 *  }
 *
 * Strict symbol checking (default)
 *  currencyInput: {
 *     currency: "$"
 *     //OR
 *     currency: ["$", true]
 *  }
 *
 * Multiple Symbols
 *  currencyInput: {
 *     currency: "$,£,¢"
 *  }
 */
$.validator.addMethod( "currency", function( value, element, param ) {
    var isParamString = typeof param === "string",
        symbol = isParamString ? param : param[ 0 ],
        soft = isParamString ? true : param[ 1 ],
        regex;

    symbol = symbol.replace( /,/g, "" );
    symbol = soft ? symbol + "]" : symbol + "]?";
    regex = "^[" + symbol + "([1-9]{1}[0-9]{0,2}(\\,[0-9]{3})*(\\.[0-9]{0,2})?|[1-9]{1}[0-9]{0,}(\\.[0-9]{0,2})?|0(\\.[0-9]{0,2})?|(\\.[0-9]{1,2})?)$";
    regex = new RegExp( regex );
    return this.optional( element ) || regex.test( value );

}, "Please specify a valid currency" );

$.validator.addMethod( "dateFA", function( value, element ) {
	return this.optional( element ) || /^[1-4]\d{3}\/((0?[1-6]\/((3[0-1])|([1-2][0-9])|(0?[1-9])))|((1[0-2]|(0?[7-9]))\/(30|([1-2][0-9])|(0?[1-9]))))$/.test( value );
}, $.validator.messages.date );

/**
 * Return true, if the value is a valid date, also making this formal check dd/mm/yyyy.
 *
 * @example $.validator.methods.date("01/01/1900")
 * @result true
 *
 * @example $.validator.methods.date("01/13/1990")
 * @result false
 *
 * @example $.validator.methods.date("01.01.1900")
 * @result false
 *
 * @example <input name="pippo" class="{dateITA:true}" />
 * @desc Declares an optional input element whose value must be a valid date.
 *
 * @name $.validator.methods.dateITA
 * @type Boolean
 * @cat Plugins/Validate/Methods
 */
$.validator.addMethod( "dateITA", function( value, element ) {
	var check = false,
		re = /^\d{1,2}\/\d{1,2}\/\d{4}$/,
		adata, gg, mm, aaaa, xdata;
	if ( re.test( value ) ) {
		adata = value.split( "/" );
		gg = parseInt( adata[ 0 ], 10 );
		mm = parseInt( adata[ 1 ], 10 );
		aaaa = parseInt( adata[ 2 ], 10 );
		xdata = new Date( Date.UTC( aaaa, mm - 1, gg, 12, 0, 0, 0 ) );
		if ( ( xdata.getUTCFullYear() === aaaa ) && ( xdata.getUTCMonth() === mm - 1 ) && ( xdata.getUTCDate() === gg ) ) {
			check = true;
		} else {
			check = false;
		}
	} else {
		check = false;
	}
	return this.optional( element ) || check;
}, $.validator.messages.date );

$.validator.addMethod( "dateNL", function( value, element ) {
	return this.optional( element ) || /^(0?[1-9]|[12]\d|3[01])[\.\/\-](0?[1-9]|1[012])[\.\/\-]([12]\d)?(\d\d)$/.test( value );
}, $.validator.messages.date );

// Older "accept" file extension method. Old docs: http://docs.jquery.com/Plugins/Validation/Methods/accept
$.validator.addMethod( "extension", function( value, element, param ) {
	param = typeof param === "string" ? param.replace( /,/g, "|" ) : "png|jpe?g|gif";
	return this.optional( element ) || value.match( new RegExp( "\\.(" + param + ")$", "i" ) );
}, $.validator.format( "Please enter a value with a valid extension." ) );

/**
 * Dutch giro account numbers (not bank numbers) have max 7 digits
 */
$.validator.addMethod( "giroaccountNL", function( value, element ) {
	return this.optional( element ) || /^[0-9]{1,7}$/.test( value );
}, "Please specify a valid giro account number" );

/**
 * IBAN is the international bank account number.
 * It has a country - specific format, that is checked here too
 *
 * Validation is case-insensitive. Please make sure to normalize input yourself.
 */
$.validator.addMethod( "iban", function( value, element ) {

	// Some quick simple tests to prevent needless work
	if ( this.optional( element ) ) {
		return true;
	}

	// Remove spaces and to upper case
	var iban = value.replace( / /g, "" ).toUpperCase(),
		ibancheckdigits = "",
		leadingZeroes = true,
		cRest = "",
		cOperator = "",
		countrycode, ibancheck, charAt, cChar, bbanpattern, bbancountrypatterns, ibanregexp, i, p;

	// Check for IBAN code length.
	// It contains:
	// country code ISO 3166-1 - two letters,
	// two check digits,
	// Basic Bank Account Number (BBAN) - up to 30 chars
	var minimalIBANlength = 5;
	if ( iban.length < minimalIBANlength ) {
		return false;
	}

	// Check the country code and find the country specific format
	countrycode = iban.substring( 0, 2 );
	bbancountrypatterns = {
		"AL": "\\d{8}[\\dA-Z]{16}",
		"AD": "\\d{8}[\\dA-Z]{12}",
		"AT": "\\d{16}",
		"AZ": "[\\dA-Z]{4}\\d{20}",
		"BE": "\\d{12}",
		"BH": "[A-Z]{4}[\\dA-Z]{14}",
		"BA": "\\d{16}",
		"BR": "\\d{23}[A-Z][\\dA-Z]",
		"BG": "[A-Z]{4}\\d{6}[\\dA-Z]{8}",
		"CR": "\\d{17}",
		"HR": "\\d{17}",
		"CY": "\\d{8}[\\dA-Z]{16}",
		"CZ": "\\d{20}",
		"DK": "\\d{14}",
		"DO": "[A-Z]{4}\\d{20}",
		"EE": "\\d{16}",
		"FO": "\\d{14}",
		"FI": "\\d{14}",
		"FR": "\\d{10}[\\dA-Z]{11}\\d{2}",
		"GE": "[\\dA-Z]{2}\\d{16}",
		"DE": "\\d{18}",
		"GI": "[A-Z]{4}[\\dA-Z]{15}",
		"GR": "\\d{7}[\\dA-Z]{16}",
		"GL": "\\d{14}",
		"GT": "[\\dA-Z]{4}[\\dA-Z]{20}",
		"HU": "\\d{24}",
		"IS": "\\d{22}",
		"IE": "[\\dA-Z]{4}\\d{14}",
		"IL": "\\d{19}",
		"IT": "[A-Z]\\d{10}[\\dA-Z]{12}",
		"KZ": "\\d{3}[\\dA-Z]{13}",
		"KW": "[A-Z]{4}[\\dA-Z]{22}",
		"LV": "[A-Z]{4}[\\dA-Z]{13}",
		"LB": "\\d{4}[\\dA-Z]{20}",
		"LI": "\\d{5}[\\dA-Z]{12}",
		"LT": "\\d{16}",
		"LU": "\\d{3}[\\dA-Z]{13}",
		"MK": "\\d{3}[\\dA-Z]{10}\\d{2}",
		"MT": "[A-Z]{4}\\d{5}[\\dA-Z]{18}",
		"MR": "\\d{23}",
		"MU": "[A-Z]{4}\\d{19}[A-Z]{3}",
		"MC": "\\d{10}[\\dA-Z]{11}\\d{2}",
		"MD": "[\\dA-Z]{2}\\d{18}",
		"ME": "\\d{18}",
		"NL": "[A-Z]{4}\\d{10}",
		"NO": "\\d{11}",
		"PK": "[\\dA-Z]{4}\\d{16}",
		"PS": "[\\dA-Z]{4}\\d{21}",
		"PL": "\\d{24}",
		"PT": "\\d{21}",
		"RO": "[A-Z]{4}[\\dA-Z]{16}",
		"SM": "[A-Z]\\d{10}[\\dA-Z]{12}",
		"SA": "\\d{2}[\\dA-Z]{18}",
		"RS": "\\d{18}",
		"SK": "\\d{20}",
		"SI": "\\d{15}",
		"ES": "\\d{20}",
		"SE": "\\d{20}",
		"CH": "\\d{5}[\\dA-Z]{12}",
		"TN": "\\d{20}",
		"TR": "\\d{5}[\\dA-Z]{17}",
		"AE": "\\d{3}\\d{16}",
		"GB": "[A-Z]{4}\\d{14}",
		"VG": "[\\dA-Z]{4}\\d{16}"
	};

	bbanpattern = bbancountrypatterns[ countrycode ];

	// As new countries will start using IBAN in the
	// future, we only check if the countrycode is known.
	// This prevents false negatives, while almost all
	// false positives introduced by this, will be caught
	// by the checksum validation below anyway.
	// Strict checking should return FALSE for unknown
	// countries.
	if ( typeof bbanpattern !== "undefined" ) {
		ibanregexp = new RegExp( "^[A-Z]{2}\\d{2}" + bbanpattern + "$", "" );
		if ( !( ibanregexp.test( iban ) ) ) {
			return false; // Invalid country specific format
		}
	}

	// Now check the checksum, first convert to digits
	ibancheck = iban.substring( 4, iban.length ) + iban.substring( 0, 4 );
	for ( i = 0; i < ibancheck.length; i++ ) {
		charAt = ibancheck.charAt( i );
		if ( charAt !== "0" ) {
			leadingZeroes = false;
		}
		if ( !leadingZeroes ) {
			ibancheckdigits += "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ".indexOf( charAt );
		}
	}

	// Calculate the result of: ibancheckdigits % 97
	for ( p = 0; p < ibancheckdigits.length; p++ ) {
		cChar = ibancheckdigits.charAt( p );
		cOperator = "" + cRest + "" + cChar;
		cRest = cOperator % 97;
	}
	return cRest === 1;
}, "Please specify a valid IBAN" );

$.validator.addMethod( "integer", function( value, element ) {
	return this.optional( element ) || /^-?\d+$/.test( value );
}, "A positive or negative non-decimal number please" );

$.validator.addMethod( "ipv4", function( value, element ) {
	return this.optional( element ) || /^(25[0-5]|2[0-4]\d|[01]?\d\d?)\.(25[0-5]|2[0-4]\d|[01]?\d\d?)\.(25[0-5]|2[0-4]\d|[01]?\d\d?)\.(25[0-5]|2[0-4]\d|[01]?\d\d?)$/i.test( value );
}, "Please enter a valid IP v4 address." );

$.validator.addMethod( "ipv6", function( value, element ) {
	return this.optional( element ) || /^((([0-9A-Fa-f]{1,4}:){7}[0-9A-Fa-f]{1,4})|(([0-9A-Fa-f]{1,4}:){6}:[0-9A-Fa-f]{1,4})|(([0-9A-Fa-f]{1,4}:){5}:([0-9A-Fa-f]{1,4}:)?[0-9A-Fa-f]{1,4})|(([0-9A-Fa-f]{1,4}:){4}:([0-9A-Fa-f]{1,4}:){0,2}[0-9A-Fa-f]{1,4})|(([0-9A-Fa-f]{1,4}:){3}:([0-9A-Fa-f]{1,4}:){0,3}[0-9A-Fa-f]{1,4})|(([0-9A-Fa-f]{1,4}:){2}:([0-9A-Fa-f]{1,4}:){0,4}[0-9A-Fa-f]{1,4})|(([0-9A-Fa-f]{1,4}:){6}((\b((25[0-5])|(1\d{2})|(2[0-4]\d)|(\d{1,2}))\b)\.){3}(\b((25[0-5])|(1\d{2})|(2[0-4]\d)|(\d{1,2}))\b))|(([0-9A-Fa-f]{1,4}:){0,5}:((\b((25[0-5])|(1\d{2})|(2[0-4]\d)|(\d{1,2}))\b)\.){3}(\b((25[0-5])|(1\d{2})|(2[0-4]\d)|(\d{1,2}))\b))|(::([0-9A-Fa-f]{1,4}:){0,5}((\b((25[0-5])|(1\d{2})|(2[0-4]\d)|(\d{1,2}))\b)\.){3}(\b((25[0-5])|(1\d{2})|(2[0-4]\d)|(\d{1,2}))\b))|([0-9A-Fa-f]{1,4}::([0-9A-Fa-f]{1,4}:){0,5}[0-9A-Fa-f]{1,4})|(::([0-9A-Fa-f]{1,4}:){0,6}[0-9A-Fa-f]{1,4})|(([0-9A-Fa-f]{1,4}:){1,7}:))$/i.test( value );
}, "Please enter a valid IP v6 address." );

$.validator.addMethod( "lettersonly", function( value, element ) {
	return this.optional( element ) || /^[a-z]+$/i.test( value );
}, "Letters only please" );

$.validator.addMethod( "letterswithbasicpunc", function( value, element ) {
	return this.optional( element ) || /^[a-z\-.,()'"\s]+$/i.test( value );
}, "Letters or punctuation only please" );

$.validator.addMethod( "mobileNL", function( value, element ) {
	return this.optional( element ) || /^((\+|00(\s|\s?\-\s?)?)31(\s|\s?\-\s?)?(\(0\)[\-\s]?)?|0)6((\s|\s?\-\s?)?[0-9]){8}$/.test( value );
}, "Please specify a valid mobile number" );

/* For UK phone functions, do the following server side processing:
 * Compare original input with this RegEx pattern:
 * ^\(?(?:(?:00\)?[\s\-]?\(?|\+)(44)\)?[\s\-]?\(?(?:0\)?[\s\-]?\(?)?|0)([1-9]\d{1,4}\)?[\s\d\-]+)$
 * Extract $1 and set $prefix to '+44<space>' if $1 is '44', otherwise set $prefix to '0'
 * Extract $2 and remove hyphens, spaces and parentheses. Phone number is combined $prefix and $2.
 * A number of very detailed GB telephone number RegEx patterns can also be found at:
 * http://www.aa-asterisk.org.uk/index.php/Regular_Expressions_for_Validating_and_Formatting_GB_Telephone_Numbers
 */
$.validator.addMethod( "mobileUK", function( phone_number, element ) {
	phone_number = phone_number.replace( /\(|\)|\s+|-/g, "" );
	return this.optional( element ) || phone_number.length > 9 &&
		phone_number.match( /^(?:(?:(?:00\s?|\+)44\s?|0)7(?:[1345789]\d{2}|624)\s?\d{3}\s?\d{3})$/ );
}, "Please specify a valid mobile number" );

/*
 * The número de identidad de extranjero ( NIE )is a code used to identify the non-nationals in Spain
 */
$.validator.addMethod( "nieES", function( value ) {
	"use strict";

	value = value.toUpperCase();

	// Basic format test
	if ( !value.match( "((^[A-Z]{1}[0-9]{7}[A-Z0-9]{1}$|^[T]{1}[A-Z0-9]{8}$)|^[0-9]{8}[A-Z]{1}$)" ) ) {
		return false;
	}

	// Test NIE
	//T
	if ( /^[T]{1}/.test( value ) ) {
		return ( value[ 8 ] === /^[T]{1}[A-Z0-9]{8}$/.test( value ) );
	}

	//XYZ
	if ( /^[XYZ]{1}/.test( value ) ) {
		return (
			value[ 8 ] === "TRWAGMYFPDXBNJZSQVHLCKE".charAt(
				value.replace( "X", "0" )
					.replace( "Y", "1" )
					.replace( "Z", "2" )
					.substring( 0, 8 ) % 23
			)
		);
	}

	return false;

}, "Please specify a valid NIE number." );

/*
 * The Número de Identificación Fiscal ( NIF ) is the way tax identification used in Spain for individuals
 */
$.validator.addMethod( "nifES", function( value ) {
	"use strict";

	value = value.toUpperCase();

	// Basic format test
	if ( !value.match( "((^[A-Z]{1}[0-9]{7}[A-Z0-9]{1}$|^[T]{1}[A-Z0-9]{8}$)|^[0-9]{8}[A-Z]{1}$)" ) ) {
		return false;
	}

	// Test NIF
	if ( /^[0-9]{8}[A-Z]{1}$/.test( value ) ) {
		return ( "TRWAGMYFPDXBNJZSQVHLCKE".charAt( value.substring( 8, 0 ) % 23 ) === value.charAt( 8 ) );
	}

	// Test specials NIF (starts with K, L or M)
	if ( /^[KLM]{1}/.test( value ) ) {
		return ( value[ 8 ] === String.fromCharCode( 64 ) );
	}

	return false;

}, "Please specify a valid NIF number." );

$.validator.addMethod( "notEqualTo", function( value, element, param ) {
	return this.optional( element ) || !$.validator.methods.equalTo.call( this, value, element, param );
}, "Please enter a different value, values must not be the same." );

$.validator.addMethod( "nowhitespace", function( value, element ) {
	return this.optional( element ) || /^\S+$/i.test( value );
}, "No white space please" );

/**
* Return true if the field value matches the given format RegExp
*
* @example $.validator.methods.pattern("AR1004",element,/^AR\d{4}$/)
* @result true
*
* @example $.validator.methods.pattern("BR1004",element,/^AR\d{4}$/)
* @result false
*
* @name $.validator.methods.pattern
* @type Boolean
* @cat Plugins/Validate/Methods
*/
$.validator.addMethod( "pattern", function( value, element, param ) {
	if ( this.optional( element ) ) {
		return true;
	}
	if ( typeof param === "string" ) {
		param = new RegExp( "^(?:" + param + ")$" );
	}
	return param.test( value );
}, "Invalid format." );

/**
 * Dutch phone numbers have 10 digits (or 11 and start with +31).
 */
$.validator.addMethod( "phoneNL", function( value, element ) {
	return this.optional( element ) || /^((\+|00(\s|\s?\-\s?)?)31(\s|\s?\-\s?)?(\(0\)[\-\s]?)?|0)[1-9]((\s|\s?\-\s?)?[0-9]){8}$/.test( value );
}, "Please specify a valid phone number." );

/* For UK phone functions, do the following server side processing:
 * Compare original input with this RegEx pattern:
 * ^\(?(?:(?:00\)?[\s\-]?\(?|\+)(44)\)?[\s\-]?\(?(?:0\)?[\s\-]?\(?)?|0)([1-9]\d{1,4}\)?[\s\d\-]+)$
 * Extract $1 and set $prefix to '+44<space>' if $1 is '44', otherwise set $prefix to '0'
 * Extract $2 and remove hyphens, spaces and parentheses. Phone number is combined $prefix and $2.
 * A number of very detailed GB telephone number RegEx patterns can also be found at:
 * http://www.aa-asterisk.org.uk/index.php/Regular_Expressions_for_Validating_and_Formatting_GB_Telephone_Numbers
 */
$.validator.addMethod( "phoneUK", function( phone_number, element ) {
	phone_number = phone_number.replace( /\(|\)|\s+|-/g, "" );
	return this.optional( element ) || phone_number.length > 9 &&
		phone_number.match( /^(?:(?:(?:00\s?|\+)44\s?)|(?:\(?0))(?:\d{2}\)?\s?\d{4}\s?\d{4}|\d{3}\)?\s?\d{3}\s?\d{3,4}|\d{4}\)?\s?(?:\d{5}|\d{3}\s?\d{3})|\d{5}\)?\s?\d{4,5})$/ );
}, "Please specify a valid phone number" );

/**
 * Matches US phone number format
 *
 * where the area code may not start with 1 and the prefix may not start with 1
 * allows '-' or ' ' as a separator and allows parens around area code
 * some people may want to put a '1' in front of their number
 *
 * 1(212)-999-2345 or
 * 212 999 2344 or
 * 212-999-0983
 *
 * but not
 * 111-123-5434
 * and not
 * 212 123 4567
 */
$.validator.addMethod( "phoneUS", function( phone_number, element ) {
	phone_number = phone_number.replace( /\s+/g, "" );
	return this.optional( element ) || phone_number.length > 9 &&
		phone_number.match( /^(\+?1-?)?(\([2-9]([02-9]\d|1[02-9])\)|[2-9]([02-9]\d|1[02-9]))-?[2-9]([02-9]\d|1[02-9])-?\d{4}$/ );
}, "Please specify a valid phone number" );

/* For UK phone functions, do the following server side processing:
 * Compare original input with this RegEx pattern:
 * ^\(?(?:(?:00\)?[\s\-]?\(?|\+)(44)\)?[\s\-]?\(?(?:0\)?[\s\-]?\(?)?|0)([1-9]\d{1,4}\)?[\s\d\-]+)$
 * Extract $1 and set $prefix to '+44<space>' if $1 is '44', otherwise set $prefix to '0'
 * Extract $2 and remove hyphens, spaces and parentheses. Phone number is combined $prefix and $2.
 * A number of very detailed GB telephone number RegEx patterns can also be found at:
 * http://www.aa-asterisk.org.uk/index.php/Regular_Expressions_for_Validating_and_Formatting_GB_Telephone_Numbers
 */

// Matches UK landline + mobile, accepting only 01-3 for landline or 07 for mobile to exclude many premium numbers
$.validator.addMethod( "phonesUK", function( phone_number, element ) {
	phone_number = phone_number.replace( /\(|\)|\s+|-/g, "" );
	return this.optional( element ) || phone_number.length > 9 &&
		phone_number.match( /^(?:(?:(?:00\s?|\+)44\s?|0)(?:1\d{8,9}|[23]\d{9}|7(?:[1345789]\d{8}|624\d{6})))$/ );
}, "Please specify a valid uk phone number" );

/**
 * Matches a valid Canadian Postal Code
 *
 * @example jQuery.validator.methods.postalCodeCA( "H0H 0H0", element )
 * @result true
 *
 * @example jQuery.validator.methods.postalCodeCA( "H0H0H0", element )
 * @result false
 *
 * @name jQuery.validator.methods.postalCodeCA
 * @type Boolean
 * @cat Plugins/Validate/Methods
 */
$.validator.addMethod( "postalCodeCA", function( value, element ) {
	return this.optional( element ) || /^[ABCEGHJKLMNPRSTVXY]\d[ABCEGHJKLMNPRSTVWXYZ] *\d[ABCEGHJKLMNPRSTVWXYZ]\d$/i.test( value );
}, "Please specify a valid postal code" );

/*
* Valida CEPs do brasileiros:
*
* Formatos aceitos:
* 99999-999
* 99.999-999
* 99999999
*/
$.validator.addMethod( "postalcodeBR", function( cep_value, element ) {
	return this.optional( element ) || /^\d{2}.\d{3}-\d{3}?$|^\d{5}-?\d{3}?$/.test( cep_value );
}, "Informe um CEP válido." );

/* Matches Italian postcode (CAP) */
$.validator.addMethod( "postalcodeIT", function( value, element ) {
	return this.optional( element ) || /^\d{5}$/.test( value );
}, "Please specify a valid postal code" );

$.validator.addMethod( "postalcodeNL", function( value, element ) {
	return this.optional( element ) || /^[1-9][0-9]{3}\s?[a-zA-Z]{2}$/.test( value );
}, "Please specify a valid postal code" );

// Matches UK postcode. Does not match to UK Channel Islands that have their own postcodes (non standard UK)
$.validator.addMethod( "postcodeUK", function( value, element ) {
	return this.optional( element ) || /^((([A-PR-UWYZ][0-9])|([A-PR-UWYZ][0-9][0-9])|([A-PR-UWYZ][A-HK-Y][0-9])|([A-PR-UWYZ][A-HK-Y][0-9][0-9])|([A-PR-UWYZ][0-9][A-HJKSTUW])|([A-PR-UWYZ][A-HK-Y][0-9][ABEHMNPRVWXY]))\s?([0-9][ABD-HJLNP-UW-Z]{2})|(GIR)\s?(0AA))$/i.test( value );
}, "Please specify a valid UK postcode" );

/*
 * Lets you say "at least X inputs that match selector Y must be filled."
 *
 * The end result is that neither of these inputs:
 *
 *	<input class="productinfo" name="partnumber">
 *	<input class="productinfo" name="description">
 *
 *	...will validate unless at least one of them is filled.
 *
 * partnumber:	{require_from_group: [1,".productinfo"]},
 * description: {require_from_group: [1,".productinfo"]}
 *
 * options[0]: number of fields that must be filled in the group
 * options[1]: CSS selector that defines the group of conditionally required fields
 */
$.validator.addMethod( "require_from_group", function( value, element, options ) {
	var $fields = $( options[ 1 ], element.form ),
		$fieldsFirst = $fields.eq( 0 ),
		validator = $fieldsFirst.data( "valid_req_grp" ) ? $fieldsFirst.data( "valid_req_grp" ) : $.extend( {}, this ),
		isValid = $fields.filter( function() {
			return validator.elementValue( this );
		} ).length >= options[ 0 ];

	// Store the cloned validator for future validation
	$fieldsFirst.data( "valid_req_grp", validator );

	// If element isn't being validated, run each require_from_group field's validation rules
	if ( !$( element ).data( "being_validated" ) ) {
		$fields.data( "being_validated", true );
		$fields.each( function() {
			validator.element( this );
		} );
		$fields.data( "being_validated", false );
	}
	return isValid;
}, $.validator.format( "Please fill at least {0} of these fields." ) );

/*
 * Lets you say "either at least X inputs that match selector Y must be filled,
 * OR they must all be skipped (left blank)."
 *
 * The end result, is that none of these inputs:
 *
 *	<input class="productinfo" name="partnumber">
 *	<input class="productinfo" name="description">
 *	<input class="productinfo" name="color">
 *
 *	...will validate unless either at least two of them are filled,
 *	OR none of them are.
 *
 * partnumber:	{skip_or_fill_minimum: [2,".productinfo"]},
 * description: {skip_or_fill_minimum: [2,".productinfo"]},
 * color:		{skip_or_fill_minimum: [2,".productinfo"]}
 *
 * options[0]: number of fields that must be filled in the group
 * options[1]: CSS selector that defines the group of conditionally required fields
 *
 */
$.validator.addMethod( "skip_or_fill_minimum", function( value, element, options ) {
	var $fields = $( options[ 1 ], element.form ),
		$fieldsFirst = $fields.eq( 0 ),
		validator = $fieldsFirst.data( "valid_skip" ) ? $fieldsFirst.data( "valid_skip" ) : $.extend( {}, this ),
		numberFilled = $fields.filter( function() {
			return validator.elementValue( this );
		} ).length,
		isValid = numberFilled === 0 || numberFilled >= options[ 0 ];

	// Store the cloned validator for future validation
	$fieldsFirst.data( "valid_skip", validator );

	// If element isn't being validated, run each skip_or_fill_minimum field's validation rules
	if ( !$( element ).data( "being_validated" ) ) {
		$fields.data( "being_validated", true );
		$fields.each( function() {
			validator.element( this );
		} );
		$fields.data( "being_validated", false );
	}
	return isValid;
}, $.validator.format( "Please either skip these fields or fill at least {0} of them." ) );

/* Validates US States and/or Territories by @jdforsythe
 * Can be case insensitive or require capitalization - default is case insensitive
 * Can include US Territories or not - default does not
 * Can include US Military postal abbreviations (AA, AE, AP) - default does not
 *
 * Note: "States" always includes DC (District of Colombia)
 *
 * Usage examples:
 *
 *  This is the default - case insensitive, no territories, no military zones
 *  stateInput: {
 *     caseSensitive: false,
 *     includeTerritories: false,
 *     includeMilitary: false
 *  }
 *
 *  Only allow capital letters, no territories, no military zones
 *  stateInput: {
 *     caseSensitive: false
 *  }
 *
 *  Case insensitive, include territories but not military zones
 *  stateInput: {
 *     includeTerritories: true
 *  }
 *
 *  Only allow capital letters, include territories and military zones
 *  stateInput: {
 *     caseSensitive: true,
 *     includeTerritories: true,
 *     includeMilitary: true
 *  }
 *
 */
$.validator.addMethod( "stateUS", function( value, element, options ) {
	var isDefault = typeof options === "undefined",
		caseSensitive = ( isDefault || typeof options.caseSensitive === "undefined" ) ? false : options.caseSensitive,
		includeTerritories = ( isDefault || typeof options.includeTerritories === "undefined" ) ? false : options.includeTerritories,
		includeMilitary = ( isDefault || typeof options.includeMilitary === "undefined" ) ? false : options.includeMilitary,
		regex;

	if ( !includeTerritories && !includeMilitary ) {
		regex = "^(A[KLRZ]|C[AOT]|D[CE]|FL|GA|HI|I[ADLN]|K[SY]|LA|M[ADEINOST]|N[CDEHJMVY]|O[HKR]|PA|RI|S[CD]|T[NX]|UT|V[AT]|W[AIVY])$";
	} else if ( includeTerritories && includeMilitary ) {
		regex = "^(A[AEKLPRSZ]|C[AOT]|D[CE]|FL|G[AU]|HI|I[ADLN]|K[SY]|LA|M[ADEINOPST]|N[CDEHJMVY]|O[HKR]|P[AR]|RI|S[CD]|T[NX]|UT|V[AIT]|W[AIVY])$";
	} else if ( includeTerritories ) {
		regex = "^(A[KLRSZ]|C[AOT]|D[CE]|FL|G[AU]|HI|I[ADLN]|K[SY]|LA|M[ADEINOPST]|N[CDEHJMVY]|O[HKR]|P[AR]|RI|S[CD]|T[NX]|UT|V[AIT]|W[AIVY])$";
	} else {
		regex = "^(A[AEKLPRZ]|C[AOT]|D[CE]|FL|GA|HI|I[ADLN]|K[SY]|LA|M[ADEINOST]|N[CDEHJMVY]|O[HKR]|PA|RI|S[CD]|T[NX]|UT|V[AT]|W[AIVY])$";
	}

	regex = caseSensitive ? new RegExp( regex ) : new RegExp( regex, "i" );
	return this.optional( element ) || regex.test( value );
}, "Please specify a valid state" );

// TODO check if value starts with <, otherwise don't try stripping anything
$.validator.addMethod( "strippedminlength", function( value, element, param ) {
	return $( value ).text().length >= param;
}, $.validator.format( "Please enter at least {0} characters" ) );

$.validator.addMethod( "time", function( value, element ) {
	return this.optional( element ) || /^([01]\d|2[0-3]|[0-9])(:[0-5]\d){1,2}$/.test( value );
}, "Please enter a valid time, between 00:00 and 23:59" );

$.validator.addMethod( "time12h", function( value, element ) {
	return this.optional( element ) || /^((0?[1-9]|1[012])(:[0-5]\d){1,2}(\ ?[AP]M))$/i.test( value );
}, "Please enter a valid time in 12-hour am/pm format" );

// Same as url, but TLD is optional
$.validator.addMethod( "url2", function( value, element ) {
	return this.optional( element ) || /^(https?|ftp):\/\/(((([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(%[\da-f]{2})|[!\$&'\(\)\*\+,;=]|:)*@)?(((\d|[1-9]\d|1\d\d|2[0-4]\d|25[0-5])\.(\d|[1-9]\d|1\d\d|2[0-4]\d|25[0-5])\.(\d|[1-9]\d|1\d\d|2[0-4]\d|25[0-5])\.(\d|[1-9]\d|1\d\d|2[0-4]\d|25[0-5]))|((([a-z]|\d|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(([a-z]|\d|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])*([a-z]|\d|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])))\.)*(([a-z]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(([a-z]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])*([a-z]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])))\.?)(:\d*)?)(\/((([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(%[\da-f]{2})|[!\$&'\(\)\*\+,;=]|:|@)+(\/(([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(%[\da-f]{2})|[!\$&'\(\)\*\+,;=]|:|@)*)*)?)?(\?((([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(%[\da-f]{2})|[!\$&'\(\)\*\+,;=]|:|@)|[\uE000-\uF8FF]|\/|\?)*)?(#((([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(%[\da-f]{2})|[!\$&'\(\)\*\+,;=]|:|@)|\/|\?)*)?$/i.test( value );
}, $.validator.messages.url );

/**
 * Return true, if the value is a valid vehicle identification number (VIN).
 *
 * Works with all kind of text inputs.
 *
 * @example <input type="text" size="20" name="VehicleID" class="{required:true,vinUS:true}" />
 * @desc Declares a required input element whose value must be a valid vehicle identification number.
 *
 * @name $.validator.methods.vinUS
 * @type Boolean
 * @cat Plugins/Validate/Methods
 */
$.validator.addMethod( "vinUS", function( v ) {
	if ( v.length !== 17 ) {
		return false;
	}

	var LL = [ "A", "B", "C", "D", "E", "F", "G", "H", "J", "K", "L", "M", "N", "P", "R", "S", "T", "U", "V", "W", "X", "Y", "Z" ],
		VL = [ 1, 2, 3, 4, 5, 6, 7, 8, 1, 2, 3, 4, 5, 7, 9, 2, 3, 4, 5, 6, 7, 8, 9 ],
		FL = [ 8, 7, 6, 5, 4, 3, 2, 10, 0, 9, 8, 7, 6, 5, 4, 3, 2 ],
		rs = 0,
		i, n, d, f, cd, cdv;

	for ( i = 0; i < 17; i++ ) {
		f = FL[ i ];
		d = v.slice( i, i + 1 );
		if ( i === 8 ) {
			cdv = d;
		}
		if ( !isNaN( d ) ) {
			d *= f;
		} else {
			for ( n = 0; n < LL.length; n++ ) {
				if ( d.toUpperCase() === LL[ n ] ) {
					d = VL[ n ];
					d *= f;
					if ( isNaN( cdv ) && n === 8 ) {
						cdv = LL[ n ];
					}
					break;
				}
			}
		}
		rs += d;
	}
	cd = rs % 11;
	if ( cd === 10 ) {
		cd = "X";
	}
	if ( cd === cdv ) {
		return true;
	}
	return false;
}, "The specified vehicle identification number (VIN) is invalid." );

$.validator.addMethod( "zipcodeUS", function( value, element ) {
	return this.optional( element ) || /^\d{5}(-\d{4})?$/.test( value );
}, "The specified US ZIP Code is invalid" );

$.validator.addMethod( "ziprange", function( value, element ) {
	return this.optional( element ) || /^90[2-5]\d\{2\}-\d{4}$/.test( value );
}, "Your ZIP-code must be in the range 902xx-xxxx to 905xx-xxxx" );

}));

/***/ }),
/* 269 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*!
 * jQuery.scrollTo
 * Copyright (c) 2007-2015 Ariel Flesler - aflesler<a>gmail<d>com | http://flesler.blogspot.com
 * Licensed under MIT
 * http://flesler.blogspot.com/2007/10/jqueryscrollto.html
 * @projectDescription Lightweight, cross-browser and highly customizable animated scrolling with jQuery
 *  
 * @version 2.1.2
 */
;(function(factory) {
	'use strict';
	if (true) {
		// AMD
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	} else if (typeof module !== 'undefined' && module.exports) {
		// CommonJS
		module.exports = factory(require('jquery'));
	} else {
		// Global
		factory(jQuery);
	}
})(function($) {
	'use strict';

	var $scrollTo = $.scrollTo = function(target, duration, settings) {
		return $(window).scrollTo(target, duration, settings);
	};

	$scrollTo.defaults = {
		axis:'xy',
		duration: 0,
		limit:true
	};

	function isWin(elem) {
		return !elem.nodeName ||
			$.inArray(elem.nodeName.toLowerCase(), ['iframe','#document','html','body']) !== -1;
	}		

	$.fn.scrollTo = function(target, duration, settings) {
		if (typeof duration === 'object') {
			settings = duration;
			duration = 0;
		}
		if (typeof settings === 'function') {
			settings = { onAfter:settings };
		}
		if (target === 'max') {
			target = 9e9;
		}

		settings = $.extend({}, $scrollTo.defaults, settings);
		// Speed is still recognized for backwards compatibility
		duration = duration || settings.duration;
		// Make sure the settings are given right
		var queue = settings.queue && settings.axis.length > 1;
		if (queue) {
			// Let's keep the overall duration
			duration /= 2;
		}
		settings.offset = both(settings.offset);
		settings.over = both(settings.over);

		return this.each(function() {
			// Null target yields nothing, just like jQuery does
			if (target === null) return;

			var win = isWin(this),
				elem = win ? this.contentWindow || window : this,
				$elem = $(elem),
				targ = target, 
				attr = {},
				toff;

			switch (typeof targ) {
				// A number will pass the regex
				case 'number':
				case 'string':
					if (/^([+-]=?)?\d+(\.\d+)?(px|%)?$/.test(targ)) {
						targ = both(targ);
						// We are done
						break;
					}
					// Relative/Absolute selector
					targ = win ? $(targ) : $(targ, elem);
					/* falls through */
				case 'object':
					if (targ.length === 0) return;
					// DOMElement / jQuery
					if (targ.is || targ.style) {
						// Get the real position of the target
						toff = (targ = $(targ)).offset();
					}
			}

			var offset = $.isFunction(settings.offset) && settings.offset(elem, targ) || settings.offset;

			$.each(settings.axis.split(''), function(i, axis) {
				var Pos	= axis === 'x' ? 'Left' : 'Top',
					pos = Pos.toLowerCase(),
					key = 'scroll' + Pos,
					prev = $elem[key](),
					max = $scrollTo.max(elem, axis);

				if (toff) {// jQuery / DOMElement
					attr[key] = toff[pos] + (win ? 0 : prev - $elem.offset()[pos]);

					// If it's a dom element, reduce the margin
					if (settings.margin) {
						attr[key] -= parseInt(targ.css('margin'+Pos), 10) || 0;
						attr[key] -= parseInt(targ.css('border'+Pos+'Width'), 10) || 0;
					}

					attr[key] += offset[pos] || 0;

					if (settings.over[pos]) {
						// Scroll to a fraction of its width/height
						attr[key] += targ[axis === 'x'?'width':'height']() * settings.over[pos];
					}
				} else {
					var val = targ[pos];
					// Handle percentage values
					attr[key] = val.slice && val.slice(-1) === '%' ?
						parseFloat(val) / 100 * max
						: val;
				}

				// Number or 'number'
				if (settings.limit && /^\d+$/.test(attr[key])) {
					// Check the limits
					attr[key] = attr[key] <= 0 ? 0 : Math.min(attr[key], max);
				}

				// Don't waste time animating, if there's no need.
				if (!i && settings.axis.length > 1) {
					if (prev === attr[key]) {
						// No animation needed
						attr = {};
					} else if (queue) {
						// Intermediate animation
						animate(settings.onAfterFirst);
						// Don't animate this axis again in the next iteration.
						attr = {};
					}
				}
			});

			animate(settings.onAfter);

			function animate(callback) {
				var opts = $.extend({}, settings, {
					// The queue setting conflicts with animate()
					// Force it to always be true
					queue: true,
					duration: duration,
					complete: callback && function() {
						callback.call(elem, targ, settings);
					}
				});
				$elem.animate(attr, opts);
			}
		});
	};

	// Max scrolling position, works on quirks mode
	// It only fails (not too badly) on IE, quirks mode.
	$scrollTo.max = function(elem, axis) {
		var Dim = axis === 'x' ? 'Width' : 'Height',
			scroll = 'scroll'+Dim;

		if (!isWin(elem))
			return elem[scroll] - $(elem)[Dim.toLowerCase()]();

		var size = 'client' + Dim,
			doc = elem.ownerDocument || elem.document,
			html = doc.documentElement,
			body = doc.body;

		return Math.max(html[scroll], body[scroll]) - Math.min(html[size], body[size]);
	};

	function both(val) {
		return $.isFunction(val) || $.isPlainObject(val) ? val : { top:val, left:val };
	}

	// Add special hooks so that window scroll properties can be animated
	$.Tween.propHooks.scrollLeft = 
	$.Tween.propHooks.scrollTop = {
		get: function(t) {
			return $(t.elem)[t.prop]();
		},
		set: function(t) {
			var curr = this.get(t);
			// If interrupt is true and user scrolled, stop animating
			if (t.options.interrupt && t._last && t._last !== curr) {
				return $(t.elem).stop();
			}
			var next = Math.round(t.now);
			// Don't waste CPU
			// Browsers don't render floating point scroll
			if (curr !== next) {
				$(t.elem)[t.prop](next);
				t._last = this.get(t);
			}
		}
	};

	// AMD requirement
	return $scrollTo;
});


/***/ }),
/* 270 */
/***/ (function(module, exports, __webpack_require__) {

var map = {
	"./af": 28,
	"./af.js": 28,
	"./ar": 35,
	"./ar-dz": 29,
	"./ar-dz.js": 29,
	"./ar-kw": 30,
	"./ar-kw.js": 30,
	"./ar-ly": 31,
	"./ar-ly.js": 31,
	"./ar-ma": 32,
	"./ar-ma.js": 32,
	"./ar-sa": 33,
	"./ar-sa.js": 33,
	"./ar-tn": 34,
	"./ar-tn.js": 34,
	"./ar.js": 35,
	"./az": 36,
	"./az.js": 36,
	"./be": 37,
	"./be.js": 37,
	"./bg": 38,
	"./bg.js": 38,
	"./bm": 39,
	"./bm.js": 39,
	"./bn": 40,
	"./bn.js": 40,
	"./bo": 41,
	"./bo.js": 41,
	"./br": 42,
	"./br.js": 42,
	"./bs": 43,
	"./bs.js": 43,
	"./ca": 44,
	"./ca.js": 44,
	"./cs": 45,
	"./cs.js": 45,
	"./cv": 46,
	"./cv.js": 46,
	"./cy": 47,
	"./cy.js": 47,
	"./da": 48,
	"./da.js": 48,
	"./de": 51,
	"./de-at": 49,
	"./de-at.js": 49,
	"./de-ch": 50,
	"./de-ch.js": 50,
	"./de.js": 51,
	"./dv": 52,
	"./dv.js": 52,
	"./el": 53,
	"./el.js": 53,
	"./en-au": 54,
	"./en-au.js": 54,
	"./en-ca": 55,
	"./en-ca.js": 55,
	"./en-gb": 56,
	"./en-gb.js": 56,
	"./en-ie": 57,
	"./en-ie.js": 57,
	"./en-nz": 58,
	"./en-nz.js": 58,
	"./eo": 59,
	"./eo.js": 59,
	"./es": 62,
	"./es-do": 60,
	"./es-do.js": 60,
	"./es-us": 61,
	"./es-us.js": 61,
	"./es.js": 62,
	"./et": 63,
	"./et.js": 63,
	"./eu": 64,
	"./eu.js": 64,
	"./fa": 65,
	"./fa.js": 65,
	"./fi": 66,
	"./fi.js": 66,
	"./fo": 67,
	"./fo.js": 67,
	"./fr": 70,
	"./fr-ca": 68,
	"./fr-ca.js": 68,
	"./fr-ch": 69,
	"./fr-ch.js": 69,
	"./fr.js": 70,
	"./fy": 71,
	"./fy.js": 71,
	"./gd": 72,
	"./gd.js": 72,
	"./gl": 73,
	"./gl.js": 73,
	"./gom-latn": 74,
	"./gom-latn.js": 74,
	"./gu": 75,
	"./gu.js": 75,
	"./he": 76,
	"./he.js": 76,
	"./hi": 77,
	"./hi.js": 77,
	"./hr": 78,
	"./hr.js": 78,
	"./hu": 79,
	"./hu.js": 79,
	"./hy-am": 80,
	"./hy-am.js": 80,
	"./id": 81,
	"./id.js": 81,
	"./is": 82,
	"./is.js": 82,
	"./it": 83,
	"./it.js": 83,
	"./ja": 84,
	"./ja.js": 84,
	"./jv": 85,
	"./jv.js": 85,
	"./ka": 86,
	"./ka.js": 86,
	"./kk": 87,
	"./kk.js": 87,
	"./km": 88,
	"./km.js": 88,
	"./kn": 89,
	"./kn.js": 89,
	"./ko": 90,
	"./ko.js": 90,
	"./ky": 91,
	"./ky.js": 91,
	"./lb": 92,
	"./lb.js": 92,
	"./lo": 93,
	"./lo.js": 93,
	"./lt": 94,
	"./lt.js": 94,
	"./lv": 95,
	"./lv.js": 95,
	"./me": 96,
	"./me.js": 96,
	"./mi": 97,
	"./mi.js": 97,
	"./mk": 98,
	"./mk.js": 98,
	"./ml": 99,
	"./ml.js": 99,
	"./mr": 100,
	"./mr.js": 100,
	"./ms": 102,
	"./ms-my": 101,
	"./ms-my.js": 101,
	"./ms.js": 102,
	"./mt": 103,
	"./mt.js": 103,
	"./my": 104,
	"./my.js": 104,
	"./nb": 105,
	"./nb.js": 105,
	"./ne": 106,
	"./ne.js": 106,
	"./nl": 108,
	"./nl-be": 107,
	"./nl-be.js": 107,
	"./nl.js": 108,
	"./nn": 109,
	"./nn.js": 109,
	"./pa-in": 110,
	"./pa-in.js": 110,
	"./pl": 111,
	"./pl.js": 111,
	"./pt": 113,
	"./pt-br": 112,
	"./pt-br.js": 112,
	"./pt.js": 113,
	"./ro": 114,
	"./ro.js": 114,
	"./ru": 115,
	"./ru.js": 115,
	"./sd": 116,
	"./sd.js": 116,
	"./se": 117,
	"./se.js": 117,
	"./si": 118,
	"./si.js": 118,
	"./sk": 119,
	"./sk.js": 119,
	"./sl": 120,
	"./sl.js": 120,
	"./sq": 121,
	"./sq.js": 121,
	"./sr": 123,
	"./sr-cyrl": 122,
	"./sr-cyrl.js": 122,
	"./sr.js": 123,
	"./ss": 124,
	"./ss.js": 124,
	"./sv": 125,
	"./sv.js": 125,
	"./sw": 126,
	"./sw.js": 126,
	"./ta": 127,
	"./ta.js": 127,
	"./te": 128,
	"./te.js": 128,
	"./tet": 129,
	"./tet.js": 129,
	"./th": 130,
	"./th.js": 130,
	"./tl-ph": 131,
	"./tl-ph.js": 131,
	"./tlh": 132,
	"./tlh.js": 132,
	"./tr": 133,
	"./tr.js": 133,
	"./tzl": 134,
	"./tzl.js": 134,
	"./tzm": 136,
	"./tzm-latn": 135,
	"./tzm-latn.js": 135,
	"./tzm.js": 136,
	"./uk": 137,
	"./uk.js": 137,
	"./ur": 138,
	"./ur.js": 138,
	"./uz": 140,
	"./uz-latn": 139,
	"./uz-latn.js": 139,
	"./uz.js": 140,
	"./vi": 141,
	"./vi.js": 141,
	"./x-pseudo": 142,
	"./x-pseudo.js": 142,
	"./yo": 143,
	"./yo.js": 143,
	"./zh-cn": 144,
	"./zh-cn.js": 144,
	"./zh-hk": 145,
	"./zh-hk.js": 145,
	"./zh-tw": 146,
	"./zh-tw.js": 146
};
function webpackContext(req) {
	return __webpack_require__(webpackContextResolve(req));
};
function webpackContextResolve(req) {
	var id = map[req];
	if(!(id + 1)) // check for number or string
		throw new Error("Cannot find module '" + req + "'.");
	return id;
};
webpackContext.keys = function webpackContextKeys() {
	return Object.keys(map);
};
webpackContext.resolve = webpackContextResolve;
module.exports = webpackContext;
webpackContext.id = 270;

/***/ }),
/* 271 */
/***/ (function(module, exports, __webpack_require__) {

var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*
 * qTip2 - Pretty powerful tooltips - v3.0.3
 * http://qtip2.com
 *
 * Copyright (c) 2016 
 * Released under the MIT licenses
 * http://jquery.org/license
 *
 * Date: Wed May 11 2016 10:31 GMT+0100+0100
 * Plugins: tips modal viewport svg imagemap ie6
 * Styles: core basic css3
 */
/*global window: false, jQuery: false, console: false, define: false */

/* Cache window, document, undefined */
(function( window, document, undefined ) {

// Uses AMD or browser globals to create a jQuery plugin.
(function( factory ) {
	"use strict";
	if(true) {
		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
	}
	else if(jQuery && !jQuery.fn.qtip) {
		factory(jQuery);
	}
}
(function($) {
	"use strict"; // Enable ECMAScript "strict" operation for this function. See more: http://ejohn.org/blog/ecmascript-5-strict-mode-json-and-more/
;// Munge the primitives - Paul Irish tip
var TRUE = true,
FALSE = false,
NULL = null,

// Common variables
X = 'x', Y = 'y',
WIDTH = 'width',
HEIGHT = 'height',

// Positioning sides
TOP = 'top',
LEFT = 'left',
BOTTOM = 'bottom',
RIGHT = 'right',
CENTER = 'center',

// Position adjustment types
FLIP = 'flip',
FLIPINVERT = 'flipinvert',
SHIFT = 'shift',

// Shortcut vars
QTIP, PROTOTYPE, CORNER, CHECKS,
PLUGINS = {},
NAMESPACE = 'qtip',
ATTR_HAS = 'data-hasqtip',
ATTR_ID = 'data-qtip-id',
WIDGET = ['ui-widget', 'ui-tooltip'],
SELECTOR = '.'+NAMESPACE,
INACTIVE_EVENTS = 'click dblclick mousedown mouseup mousemove mouseleave mouseenter'.split(' '),

CLASS_FIXED = NAMESPACE+'-fixed',
CLASS_DEFAULT = NAMESPACE + '-default',
CLASS_FOCUS = NAMESPACE + '-focus',
CLASS_HOVER = NAMESPACE + '-hover',
CLASS_DISABLED = NAMESPACE+'-disabled',

replaceSuffix = '_replacedByqTip',
oldtitle = 'oldtitle',
trackingBound,

// Browser detection
BROWSER = {
	/*
	 * IE version detection
	 *
	 * Adapted from: http://ajaxian.com/archives/attack-of-the-ie-conditional-comment
	 * Credit to James Padolsey for the original implemntation!
	 */
	ie: (function() {
		/* eslint-disable no-empty */
		var v, i;
		for (
			v = 4, i = document.createElement('div');
			(i.innerHTML = '<!--[if gt IE ' + v + ']><i></i><![endif]-->') && i.getElementsByTagName('i')[0];
			v+=1
		) {}
		return v > 4 ? v : NaN;
		/* eslint-enable no-empty */
	})(),

	/*
	 * iOS version detection
	 */
	iOS: parseFloat(
		('' + (/CPU.*OS ([0-9_]{1,5})|(CPU like).*AppleWebKit.*Mobile/i.exec(navigator.userAgent) || [0,''])[1])
		.replace('undefined', '3_2').replace('_', '.').replace('_', '')
	) || FALSE
};
;function QTip(target, options, id, attr) {
	// Elements and ID
	this.id = id;
	this.target = target;
	this.tooltip = NULL;
	this.elements = { target: target };

	// Internal constructs
	this._id = NAMESPACE + '-' + id;
	this.timers = { img: {} };
	this.options = options;
	this.plugins = {};

	// Cache object
	this.cache = {
		event: {},
		target: $(),
		disabled: FALSE,
		attr: attr,
		onTooltip: FALSE,
		lastClass: ''
	};

	// Set the initial flags
	this.rendered = this.destroyed = this.disabled = this.waiting =
		this.hiddenDuringWait = this.positioning = this.triggering = FALSE;
}
PROTOTYPE = QTip.prototype;

PROTOTYPE._when = function(deferreds) {
	return $.when.apply($, deferreds);
};

PROTOTYPE.render = function(show) {
	if(this.rendered || this.destroyed) { return this; } // If tooltip has already been rendered, exit

	var self = this,
		options = this.options,
		cache = this.cache,
		elements = this.elements,
		text = options.content.text,
		title = options.content.title,
		button = options.content.button,
		posOptions = options.position,
		deferreds = [];

	// Add ARIA attributes to target
	$.attr(this.target[0], 'aria-describedby', this._id);

	// Create public position object that tracks current position corners
	cache.posClass = this._createPosClass(
		(this.position = { my: posOptions.my, at: posOptions.at }).my
	);

	// Create tooltip element
	this.tooltip = elements.tooltip = $('<div/>', {
		'id': this._id,
		'class': [ NAMESPACE, CLASS_DEFAULT, options.style.classes, cache.posClass ].join(' '),
		'width': options.style.width || '',
		'height': options.style.height || '',
		'tracking': posOptions.target === 'mouse' && posOptions.adjust.mouse,

		/* ARIA specific attributes */
		'role': 'alert',
		'aria-live': 'polite',
		'aria-atomic': FALSE,
		'aria-describedby': this._id + '-content',
		'aria-hidden': TRUE
	})
	.toggleClass(CLASS_DISABLED, this.disabled)
	.attr(ATTR_ID, this.id)
	.data(NAMESPACE, this)
	.appendTo(posOptions.container)
	.append(
		// Create content element
		elements.content = $('<div />', {
			'class': NAMESPACE + '-content',
			'id': this._id + '-content',
			'aria-atomic': TRUE
		})
	);

	// Set rendered flag and prevent redundant reposition calls for now
	this.rendered = -1;
	this.positioning = TRUE;

	// Create title...
	if(title) {
		this._createTitle();

		// Update title only if its not a callback (called in toggle if so)
		if(!$.isFunction(title)) {
			deferreds.push( this._updateTitle(title, FALSE) );
		}
	}

	// Create button
	if(button) { this._createButton(); }

	// Set proper rendered flag and update content if not a callback function (called in toggle)
	if(!$.isFunction(text)) {
		deferreds.push( this._updateContent(text, FALSE) );
	}
	this.rendered = TRUE;

	// Setup widget classes
	this._setWidget();

	// Initialize 'render' plugins
	$.each(PLUGINS, function(name) {
		var instance;
		if(this.initialize === 'render' && (instance = this(self))) {
			self.plugins[name] = instance;
		}
	});

	// Unassign initial events and assign proper events
	this._unassignEvents();
	this._assignEvents();

	// When deferreds have completed
	this._when(deferreds).then(function() {
		// tooltiprender event
		self._trigger('render');

		// Reset flags
		self.positioning = FALSE;

		// Show tooltip if not hidden during wait period
		if(!self.hiddenDuringWait && (options.show.ready || show)) {
			self.toggle(TRUE, cache.event, FALSE);
		}
		self.hiddenDuringWait = FALSE;
	});

	// Expose API
	QTIP.api[this.id] = this;

	return this;
};

PROTOTYPE.destroy = function(immediate) {
	// Set flag the signify destroy is taking place to plugins
	// and ensure it only gets destroyed once!
	if(this.destroyed) { return this.target; }

	function process() {
		if(this.destroyed) { return; }
		this.destroyed = TRUE;

		var target = this.target,
			title = target.attr(oldtitle),
			timer;

		// Destroy tooltip if rendered
		if(this.rendered) {
			this.tooltip.stop(1,0).find('*').remove().end().remove();
		}

		// Destroy all plugins
		$.each(this.plugins, function() {
			this.destroy && this.destroy();
		});

		// Clear timers
		for (timer in this.timers) {
			if (this.timers.hasOwnProperty(timer)) {
				clearTimeout(this.timers[timer]);
			}
		}

		// Remove api object and ARIA attributes
		target.removeData(NAMESPACE)
			.removeAttr(ATTR_ID)
			.removeAttr(ATTR_HAS)
			.removeAttr('aria-describedby');

		// Reset old title attribute if removed
		if(this.options.suppress && title) {
			target.attr('title', title).removeAttr(oldtitle);
		}

		// Remove qTip events associated with this API
		this._unassignEvents();

		// Remove ID from used id objects, and delete object references
		// for better garbage collection and leak protection
		this.options = this.elements = this.cache = this.timers =
			this.plugins = this.mouse = NULL;

		// Delete epoxsed API object
		delete QTIP.api[this.id];
	}

	// If an immediate destroy is needed
	if((immediate !== TRUE || this.triggering === 'hide') && this.rendered) {
		this.tooltip.one('tooltiphidden', $.proxy(process, this));
		!this.triggering && this.hide();
	}

	// If we're not in the process of hiding... process
	else { process.call(this); }

	return this.target;
};
;function invalidOpt(a) {
	return a === NULL || $.type(a) !== 'object';
}

function invalidContent(c) {
	return !($.isFunction(c) || 
            c && c.attr || 
            c.length || 
            $.type(c) === 'object' && (c.jquery || c.then));
}

// Option object sanitizer
function sanitizeOptions(opts) {
	var content, text, ajax, once;

	if(invalidOpt(opts)) { return FALSE; }

	if(invalidOpt(opts.metadata)) {
		opts.metadata = { type: opts.metadata };
	}

	if('content' in opts) {
		content = opts.content;

		if(invalidOpt(content) || content.jquery || content.done) {
			text = invalidContent(content) ? FALSE : content;
			content = opts.content = {
				text: text
			};
		}
		else { text = content.text; }

		// DEPRECATED - Old content.ajax plugin functionality
		// Converts it into the proper Deferred syntax
		if('ajax' in content) {
			ajax = content.ajax;
			once = ajax && ajax.once !== FALSE;
			delete content.ajax;

			content.text = function(event, api) {
				var loading = text || $(this).attr(api.options.content.attr) || 'Loading...',

				deferred = $.ajax(
					$.extend({}, ajax, { context: api })
				)
				.then(ajax.success, NULL, ajax.error)
				.then(function(newContent) {
					if(newContent && once) { api.set('content.text', newContent); }
					return newContent;
				},
				function(xhr, status, error) {
					if(api.destroyed || xhr.status === 0) { return; }
					api.set('content.text', status + ': ' + error);
				});

				return !once ? (api.set('content.text', loading), deferred) : loading;
			};
		}

		if('title' in content) {
			if($.isPlainObject(content.title)) {
				content.button = content.title.button;
				content.title = content.title.text;
			}

			if(invalidContent(content.title || FALSE)) {
				content.title = FALSE;
			}
		}
	}

	if('position' in opts && invalidOpt(opts.position)) {
		opts.position = { my: opts.position, at: opts.position };
	}

	if('show' in opts && invalidOpt(opts.show)) {
		opts.show = opts.show.jquery ? { target: opts.show } :
			opts.show === TRUE ? { ready: TRUE } : { event: opts.show };
	}

	if('hide' in opts && invalidOpt(opts.hide)) {
		opts.hide = opts.hide.jquery ? { target: opts.hide } : { event: opts.hide };
	}

	if('style' in opts && invalidOpt(opts.style)) {
		opts.style = { classes: opts.style };
	}

	// Sanitize plugin options
	$.each(PLUGINS, function() {
		this.sanitize && this.sanitize(opts);
	});

	return opts;
}

// Setup builtin .set() option checks
CHECKS = PROTOTYPE.checks = {
	builtin: {
		// Core checks
		'^id$': function(obj, o, v, prev) {
			var id = v === TRUE ? QTIP.nextid : v,
				newId = NAMESPACE + '-' + id;

			if(id !== FALSE && id.length > 0 && !$('#'+newId).length) {
				this._id = newId;

				if(this.rendered) {
					this.tooltip[0].id = this._id;
					this.elements.content[0].id = this._id + '-content';
					this.elements.title[0].id = this._id + '-title';
				}
			}
			else { obj[o] = prev; }
		},
		'^prerender': function(obj, o, v) {
			v && !this.rendered && this.render(this.options.show.ready);
		},

		// Content checks
		'^content.text$': function(obj, o, v) {
			this._updateContent(v);
		},
		'^content.attr$': function(obj, o, v, prev) {
			if(this.options.content.text === this.target.attr(prev)) {
				this._updateContent( this.target.attr(v) );
			}
		},
		'^content.title$': function(obj, o, v) {
			// Remove title if content is null
			if(!v) { return this._removeTitle(); }

			// If title isn't already created, create it now and update
			v && !this.elements.title && this._createTitle();
			this._updateTitle(v);
		},
		'^content.button$': function(obj, o, v) {
			this._updateButton(v);
		},
		'^content.title.(text|button)$': function(obj, o, v) {
			this.set('content.'+o, v); // Backwards title.text/button compat
		},

		// Position checks
		'^position.(my|at)$': function(obj, o, v){
			if('string' === typeof v) {
				this.position[o] = obj[o] = new CORNER(v, o === 'at');
			}
		},
		'^position.container$': function(obj, o, v){
			this.rendered && this.tooltip.appendTo(v);
		},

		// Show checks
		'^show.ready$': function(obj, o, v) {
			v && (!this.rendered && this.render(TRUE) || this.toggle(TRUE));
		},

		// Style checks
		'^style.classes$': function(obj, o, v, p) {
			this.rendered && this.tooltip.removeClass(p).addClass(v);
		},
		'^style.(width|height)': function(obj, o, v) {
			this.rendered && this.tooltip.css(o, v);
		},
		'^style.widget|content.title': function() {
			this.rendered && this._setWidget();
		},
		'^style.def': function(obj, o, v) {
			this.rendered && this.tooltip.toggleClass(CLASS_DEFAULT, !!v);
		},

		// Events check
		'^events.(render|show|move|hide|focus|blur)$': function(obj, o, v) {
			this.rendered && this.tooltip[($.isFunction(v) ? '' : 'un') + 'bind']('tooltip'+o, v);
		},

		// Properties which require event reassignment
		'^(show|hide|position).(event|target|fixed|inactive|leave|distance|viewport|adjust)': function() {
			if(!this.rendered) { return; }

			// Set tracking flag
			var posOptions = this.options.position;
			this.tooltip.attr('tracking', posOptions.target === 'mouse' && posOptions.adjust.mouse);

			// Reassign events
			this._unassignEvents();
			this._assignEvents();
		}
	}
};

// Dot notation converter
function convertNotation(options, notation) {
	var i = 0, obj, option = options,

	// Split notation into array
	levels = notation.split('.');

	// Loop through
	while(option = option[ levels[i++] ]) {
		if(i < levels.length) { obj = option; }
	}

	return [obj || options, levels.pop()];
}

PROTOTYPE.get = function(notation) {
	if(this.destroyed) { return this; }

	var o = convertNotation(this.options, notation.toLowerCase()),
		result = o[0][ o[1] ];

	return result.precedance ? result.string() : result;
};

function setCallback(notation, args) {
	var category, rule, match;

	for(category in this.checks) {
		if (!this.checks.hasOwnProperty(category)) { continue; }

		for(rule in this.checks[category]) {
			if (!this.checks[category].hasOwnProperty(rule)) { continue; }

			if(match = (new RegExp(rule, 'i')).exec(notation)) {
				args.push(match);

				if(category === 'builtin' || this.plugins[category]) {
					this.checks[category][rule].apply(
						this.plugins[category] || this, args
					);
				}
			}
		}
	}
}

var rmove = /^position\.(my|at|adjust|target|container|viewport)|style|content|show\.ready/i,
	rrender = /^prerender|show\.ready/i;

PROTOTYPE.set = function(option, value) {
	if(this.destroyed) { return this; }

	var rendered = this.rendered,
		reposition = FALSE,
		options = this.options,
		name;

	// Convert singular option/value pair into object form
	if('string' === typeof option) {
		name = option; option = {}; option[name] = value;
	}
	else { option = $.extend({}, option); }

	// Set all of the defined options to their new values
	$.each(option, function(notation, val) {
		if(rendered && rrender.test(notation)) {
			delete option[notation]; return;
		}

		// Set new obj value
		var obj = convertNotation(options, notation.toLowerCase()), previous;
		previous = obj[0][ obj[1] ];
		obj[0][ obj[1] ] = val && val.nodeType ? $(val) : val;

		// Also check if we need to reposition
		reposition = rmove.test(notation) || reposition;

		// Set the new params for the callback
		option[notation] = [obj[0], obj[1], val, previous];
	});

	// Re-sanitize options
	sanitizeOptions(options);

	/*
	 * Execute any valid callbacks for the set options
	 * Also set positioning flag so we don't get loads of redundant repositioning calls.
	 */
	this.positioning = TRUE;
	$.each(option, $.proxy(setCallback, this));
	this.positioning = FALSE;

	// Update position if needed
	if(this.rendered && this.tooltip[0].offsetWidth > 0 && reposition) {
		this.reposition( options.position.target === 'mouse' ? NULL : this.cache.event );
	}

	return this;
};
;PROTOTYPE._update = function(content, element) {
	var self = this,
		cache = this.cache;

	// Make sure tooltip is rendered and content is defined. If not return
	if(!this.rendered || !content) { return FALSE; }

	// Use function to parse content
	if($.isFunction(content)) {
		content = content.call(this.elements.target, cache.event, this) || '';
	}

	// Handle deferred content
	if($.isFunction(content.then)) {
		cache.waiting = TRUE;
		return content.then(function(c) {
			cache.waiting = FALSE;
			return self._update(c, element);
		}, NULL, function(e) {
			return self._update(e, element);
		});
	}

	// If content is null... return false
	if(content === FALSE || !content && content !== '') { return FALSE; }

	// Append new content if its a DOM array and show it if hidden
	if(content.jquery && content.length > 0) {
		element.empty().append(
			content.css({ display: 'block', visibility: 'visible' })
		);
	}

	// Content is a regular string, insert the new content
	else { element.html(content); }

	// Wait for content to be loaded, and reposition
	return this._waitForContent(element).then(function(images) {
		if(self.rendered && self.tooltip[0].offsetWidth > 0) {
			self.reposition(cache.event, !images.length);
		}
	});
};

PROTOTYPE._waitForContent = function(element) {
	var cache = this.cache;

	// Set flag
	cache.waiting = TRUE;

	// If imagesLoaded is included, ensure images have loaded and return promise
	return ( $.fn.imagesLoaded ? element.imagesLoaded() : new $.Deferred().resolve([]) )
		.done(function() { cache.waiting = FALSE; })
		.promise();
};

PROTOTYPE._updateContent = function(content, reposition) {
	this._update(content, this.elements.content, reposition);
};

PROTOTYPE._updateTitle = function(content, reposition) {
	if(this._update(content, this.elements.title, reposition) === FALSE) {
		this._removeTitle(FALSE);
	}
};

PROTOTYPE._createTitle = function()
{
	var elements = this.elements,
		id = this._id+'-title';

	// Destroy previous title element, if present
	if(elements.titlebar) { this._removeTitle(); }

	// Create title bar and title elements
	elements.titlebar = $('<div />', {
		'class': NAMESPACE + '-titlebar ' + (this.options.style.widget ? createWidgetClass('header') : '')
	})
	.append(
		elements.title = $('<div />', {
			'id': id,
			'class': NAMESPACE + '-title',
			'aria-atomic': TRUE
		})
	)
	.insertBefore(elements.content)

	// Button-specific events
	.delegate('.qtip-close', 'mousedown keydown mouseup keyup mouseout', function(event) {
		$(this).toggleClass('ui-state-active ui-state-focus', event.type.substr(-4) === 'down');
	})
	.delegate('.qtip-close', 'mouseover mouseout', function(event){
		$(this).toggleClass('ui-state-hover', event.type === 'mouseover');
	});

	// Create button if enabled
	if(this.options.content.button) { this._createButton(); }
};

PROTOTYPE._removeTitle = function(reposition)
{
	var elements = this.elements;

	if(elements.title) {
		elements.titlebar.remove();
		elements.titlebar = elements.title = elements.button = NULL;

		// Reposition if enabled
		if(reposition !== FALSE) { this.reposition(); }
	}
};
;PROTOTYPE._createPosClass = function(my) {
	return NAMESPACE + '-pos-' + (my || this.options.position.my).abbrev();
};

PROTOTYPE.reposition = function(event, effect) {
	if(!this.rendered || this.positioning || this.destroyed) { return this; }

	// Set positioning flag
	this.positioning = TRUE;

	var cache = this.cache,
		tooltip = this.tooltip,
		posOptions = this.options.position,
		target = posOptions.target,
		my = posOptions.my,
		at = posOptions.at,
		viewport = posOptions.viewport,
		container = posOptions.container,
		adjust = posOptions.adjust,
		method = adjust.method.split(' '),
		tooltipWidth = tooltip.outerWidth(FALSE),
		tooltipHeight = tooltip.outerHeight(FALSE),
		targetWidth = 0,
		targetHeight = 0,
		type = tooltip.css('position'),
		position = { left: 0, top: 0 },
		visible = tooltip[0].offsetWidth > 0,
		isScroll = event && event.type === 'scroll',
		win = $(window),
		doc = container[0].ownerDocument,
		mouse = this.mouse,
		pluginCalculations, offset, adjusted, newClass;

	// Check if absolute position was passed
	if($.isArray(target) && target.length === 2) {
		// Force left top and set position
		at = { x: LEFT, y: TOP };
		position = { left: target[0], top: target[1] };
	}

	// Check if mouse was the target
	else if(target === 'mouse') {
		// Force left top to allow flipping
		at = { x: LEFT, y: TOP };

		// Use the mouse origin that caused the show event, if distance hiding is enabled
		if((!adjust.mouse || this.options.hide.distance) && cache.origin && cache.origin.pageX) {
			event =  cache.origin;
		}

		// Use cached event for resize/scroll events
		else if(!event || event && (event.type === 'resize' || event.type === 'scroll')) {
			event = cache.event;
		}

		// Otherwise, use the cached mouse coordinates if available
		else if(mouse && mouse.pageX) {
			event = mouse;
		}

		// Calculate body and container offset and take them into account below
		if(type !== 'static') { position = container.offset(); }
		if(doc.body.offsetWidth !== (window.innerWidth || doc.documentElement.clientWidth)) {
			offset = $(document.body).offset();
		}

		// Use event coordinates for position
		position = {
			left: event.pageX - position.left + (offset && offset.left || 0),
			top: event.pageY - position.top + (offset && offset.top || 0)
		};

		// Scroll events are a pain, some browsers
		if(adjust.mouse && isScroll && mouse) {
			position.left -= (mouse.scrollX || 0) - win.scrollLeft();
			position.top -= (mouse.scrollY || 0) - win.scrollTop();
		}
	}

	// Target wasn't mouse or absolute...
	else {
		// Check if event targetting is being used
		if(target === 'event') {
			if(event && event.target && event.type !== 'scroll' && event.type !== 'resize') {
				cache.target = $(event.target);
			}
			else if(!event.target) {
				cache.target = this.elements.target;
			}
		}
		else if(target !== 'event'){
			cache.target = $(target.jquery ? target : this.elements.target);
		}
		target = cache.target;

		// Parse the target into a jQuery object and make sure there's an element present
		target = $(target).eq(0);
		if(target.length === 0) { return this; }

		// Check if window or document is the target
		else if(target[0] === document || target[0] === window) {
			targetWidth = BROWSER.iOS ? window.innerWidth : target.width();
			targetHeight = BROWSER.iOS ? window.innerHeight : target.height();

			if(target[0] === window) {
				position = {
					top: (viewport || target).scrollTop(),
					left: (viewport || target).scrollLeft()
				};
			}
		}

		// Check if the target is an <AREA> element
		else if(PLUGINS.imagemap && target.is('area')) {
			pluginCalculations = PLUGINS.imagemap(this, target, at, PLUGINS.viewport ? method : FALSE);
		}

		// Check if the target is an SVG element
		else if(PLUGINS.svg && target && target[0].ownerSVGElement) {
			pluginCalculations = PLUGINS.svg(this, target, at, PLUGINS.viewport ? method : FALSE);
		}

		// Otherwise use regular jQuery methods
		else {
			targetWidth = target.outerWidth(FALSE);
			targetHeight = target.outerHeight(FALSE);
			position = target.offset();
		}

		// Parse returned plugin values into proper variables
		if(pluginCalculations) {
			targetWidth = pluginCalculations.width;
			targetHeight = pluginCalculations.height;
			offset = pluginCalculations.offset;
			position = pluginCalculations.position;
		}

		// Adjust position to take into account offset parents
		position = this.reposition.offset(target, position, container);

		// Adjust for position.fixed tooltips (and also iOS scroll bug in v3.2-4.0 & v4.3-4.3.2)
		if(BROWSER.iOS > 3.1 && BROWSER.iOS < 4.1 ||
			BROWSER.iOS >= 4.3 && BROWSER.iOS < 4.33 ||
			!BROWSER.iOS && type === 'fixed'
		){
			position.left -= win.scrollLeft();
			position.top -= win.scrollTop();
		}

		// Adjust position relative to target
		if(!pluginCalculations || pluginCalculations && pluginCalculations.adjustable !== FALSE) {
			position.left += at.x === RIGHT ? targetWidth : at.x === CENTER ? targetWidth / 2 : 0;
			position.top += at.y === BOTTOM ? targetHeight : at.y === CENTER ? targetHeight / 2 : 0;
		}
	}

	// Adjust position relative to tooltip
	position.left += adjust.x + (my.x === RIGHT ? -tooltipWidth : my.x === CENTER ? -tooltipWidth / 2 : 0);
	position.top += adjust.y + (my.y === BOTTOM ? -tooltipHeight : my.y === CENTER ? -tooltipHeight / 2 : 0);

	// Use viewport adjustment plugin if enabled
	if(PLUGINS.viewport) {
		adjusted = position.adjusted = PLUGINS.viewport(
			this, position, posOptions, targetWidth, targetHeight, tooltipWidth, tooltipHeight
		);

		// Apply offsets supplied by positioning plugin (if used)
		if(offset && adjusted.left) { position.left += offset.left; }
		if(offset && adjusted.top) {  position.top += offset.top; }

		// Apply any new 'my' position
		if(adjusted.my) { this.position.my = adjusted.my; }
	}

	// Viewport adjustment is disabled, set values to zero
	else { position.adjusted = { left: 0, top: 0 }; }

	// Set tooltip position class if it's changed
	if(cache.posClass !== (newClass = this._createPosClass(this.position.my))) {
		cache.posClass = newClass;
		tooltip.removeClass(cache.posClass).addClass(newClass);
	}

	// tooltipmove event
	if(!this._trigger('move', [position, viewport.elem || viewport], event)) { return this; }
	delete position.adjusted;

	// If effect is disabled, target it mouse, no animation is defined or positioning gives NaN out, set CSS directly
	if(effect === FALSE || !visible || isNaN(position.left) || isNaN(position.top) || target === 'mouse' || !$.isFunction(posOptions.effect)) {
		tooltip.css(position);
	}

	// Use custom function if provided
	else if($.isFunction(posOptions.effect)) {
		posOptions.effect.call(tooltip, this, $.extend({}, position));
		tooltip.queue(function(next) {
			// Reset attributes to avoid cross-browser rendering bugs
			$(this).css({ opacity: '', height: '' });
			if(BROWSER.ie) { this.style.removeAttribute('filter'); }

			next();
		});
	}

	// Set positioning flag
	this.positioning = FALSE;

	return this;
};

// Custom (more correct for qTip!) offset calculator
PROTOTYPE.reposition.offset = function(elem, pos, container) {
	if(!container[0]) { return pos; }

	var ownerDocument = $(elem[0].ownerDocument),
		quirks = !!BROWSER.ie && document.compatMode !== 'CSS1Compat',
		parent = container[0],
		scrolled, position, parentOffset, overflow;

	function scroll(e, i) {
		pos.left += i * e.scrollLeft();
		pos.top += i * e.scrollTop();
	}

	// Compensate for non-static containers offset
	do {
		if((position = $.css(parent, 'position')) !== 'static') {
			if(position === 'fixed') {
				parentOffset = parent.getBoundingClientRect();
				scroll(ownerDocument, -1);
			}
			else {
				parentOffset = $(parent).position();
				parentOffset.left += parseFloat($.css(parent, 'borderLeftWidth')) || 0;
				parentOffset.top += parseFloat($.css(parent, 'borderTopWidth')) || 0;
			}

			pos.left -= parentOffset.left + (parseFloat($.css(parent, 'marginLeft')) || 0);
			pos.top -= parentOffset.top + (parseFloat($.css(parent, 'marginTop')) || 0);

			// If this is the first parent element with an overflow of "scroll" or "auto", store it
			if(!scrolled && (overflow = $.css(parent, 'overflow')) !== 'hidden' && overflow !== 'visible') { scrolled = $(parent); }
		}
	}
	while(parent = parent.offsetParent);

	// Compensate for containers scroll if it also has an offsetParent (or in IE quirks mode)
	if(scrolled && (scrolled[0] !== ownerDocument[0] || quirks)) {
		scroll(scrolled, 1);
	}

	return pos;
};

// Corner class
var C = (CORNER = PROTOTYPE.reposition.Corner = function(corner, forceY) {
	corner = ('' + corner).replace(/([A-Z])/, ' $1').replace(/middle/gi, CENTER).toLowerCase();
	this.x = (corner.match(/left|right/i) || corner.match(/center/) || ['inherit'])[0].toLowerCase();
	this.y = (corner.match(/top|bottom|center/i) || ['inherit'])[0].toLowerCase();
	this.forceY = !!forceY;

	var f = corner.charAt(0);
	this.precedance = f === 't' || f === 'b' ? Y : X;
}).prototype;

C.invert = function(z, center) {
	this[z] = this[z] === LEFT ? RIGHT : this[z] === RIGHT ? LEFT : center || this[z];
};

C.string = function(join) {
	var x = this.x, y = this.y;

	var result = x !== y ?
		x === 'center' || y !== 'center' && (this.precedance === Y || this.forceY) ? 
			[y,x] : 
			[x,y] :
		[x];

	return join !== false ? result.join(' ') : result;
};

C.abbrev = function() {
	var result = this.string(false);
	return result[0].charAt(0) + (result[1] && result[1].charAt(0) || '');
};

C.clone = function() {
	return new CORNER( this.string(), this.forceY );
};

;
PROTOTYPE.toggle = function(state, event) {
	var cache = this.cache,
		options = this.options,
		tooltip = this.tooltip;

	// Try to prevent flickering when tooltip overlaps show element
	if(event) {
		if((/over|enter/).test(event.type) && cache.event && (/out|leave/).test(cache.event.type) &&
			options.show.target.add(event.target).length === options.show.target.length &&
			tooltip.has(event.relatedTarget).length) {
			return this;
		}

		// Cache event
		cache.event = $.event.fix(event);
	}

	// If we're currently waiting and we've just hidden... stop it
	this.waiting && !state && (this.hiddenDuringWait = TRUE);

	// Render the tooltip if showing and it isn't already
	if(!this.rendered) { return state ? this.render(1) : this; }
	else if(this.destroyed || this.disabled) { return this; }

	var type = state ? 'show' : 'hide',
		opts = this.options[type],
		posOptions = this.options.position,
		contentOptions = this.options.content,
		width = this.tooltip.css('width'),
		visible = this.tooltip.is(':visible'),
		animate = state || opts.target.length === 1,
		sameTarget = !event || opts.target.length < 2 || cache.target[0] === event.target,
		identicalState, allow, after;

	// Detect state if valid one isn't provided
	if((typeof state).search('boolean|number')) { state = !visible; }

	// Check if the tooltip is in an identical state to the new would-be state
	identicalState = !tooltip.is(':animated') && visible === state && sameTarget;

	// Fire tooltip(show/hide) event and check if destroyed
	allow = !identicalState ? !!this._trigger(type, [90]) : NULL;

	// Check to make sure the tooltip wasn't destroyed in the callback
	if(this.destroyed) { return this; }

	// If the user didn't stop the method prematurely and we're showing the tooltip, focus it
	if(allow !== FALSE && state) { this.focus(event); }

	// If the state hasn't changed or the user stopped it, return early
	if(!allow || identicalState) { return this; }

	// Set ARIA hidden attribute
	$.attr(tooltip[0], 'aria-hidden', !!!state);

	// Execute state specific properties
	if(state) {
		// Store show origin coordinates
		this.mouse && (cache.origin = $.event.fix(this.mouse));

		// Update tooltip content & title if it's a dynamic function
		if($.isFunction(contentOptions.text)) { this._updateContent(contentOptions.text, FALSE); }
		if($.isFunction(contentOptions.title)) { this._updateTitle(contentOptions.title, FALSE); }

		// Cache mousemove events for positioning purposes (if not already tracking)
		if(!trackingBound && posOptions.target === 'mouse' && posOptions.adjust.mouse) {
			$(document).bind('mousemove.'+NAMESPACE, this._storeMouse);
			trackingBound = TRUE;
		}

		// Update the tooltip position (set width first to prevent viewport/max-width issues)
		if(!width) { tooltip.css('width', tooltip.outerWidth(FALSE)); }
		this.reposition(event, arguments[2]);
		if(!width) { tooltip.css('width', ''); }

		// Hide other tooltips if tooltip is solo
		if(!!opts.solo) {
			(typeof opts.solo === 'string' ? $(opts.solo) : $(SELECTOR, opts.solo))
				.not(tooltip).not(opts.target).qtip('hide', new $.Event('tooltipsolo'));
		}
	}
	else {
		// Clear show timer if we're hiding
		clearTimeout(this.timers.show);

		// Remove cached origin on hide
		delete cache.origin;

		// Remove mouse tracking event if not needed (all tracking qTips are hidden)
		if(trackingBound && !$(SELECTOR+'[tracking="true"]:visible', opts.solo).not(tooltip).length) {
			$(document).unbind('mousemove.'+NAMESPACE);
			trackingBound = FALSE;
		}

		// Blur the tooltip
		this.blur(event);
	}

	// Define post-animation, state specific properties
	after = $.proxy(function() {
		if(state) {
			// Prevent antialias from disappearing in IE by removing filter
			if(BROWSER.ie) { tooltip[0].style.removeAttribute('filter'); }

			// Remove overflow setting to prevent tip bugs
			tooltip.css('overflow', '');

			// Autofocus elements if enabled
			if('string' === typeof opts.autofocus) {
				$(this.options.show.autofocus, tooltip).focus();
			}

			// If set, hide tooltip when inactive for delay period
			this.options.show.target.trigger('qtip-'+this.id+'-inactive');
		}
		else {
			// Reset CSS states
			tooltip.css({
				display: '',
				visibility: '',
				opacity: '',
				left: '',
				top: ''
			});
		}

		// tooltipvisible/tooltiphidden events
		this._trigger(state ? 'visible' : 'hidden');
	}, this);

	// If no effect type is supplied, use a simple toggle
	if(opts.effect === FALSE || animate === FALSE) {
		tooltip[ type ]();
		after();
	}

	// Use custom function if provided
	else if($.isFunction(opts.effect)) {
		tooltip.stop(1, 1);
		opts.effect.call(tooltip, this);
		tooltip.queue('fx', function(n) {
			after(); n();
		});
	}

	// Use basic fade function by default
	else { tooltip.fadeTo(90, state ? 1 : 0, after); }

	// If inactive hide method is set, active it
	if(state) { opts.target.trigger('qtip-'+this.id+'-inactive'); }

	return this;
};

PROTOTYPE.show = function(event) { return this.toggle(TRUE, event); };

PROTOTYPE.hide = function(event) { return this.toggle(FALSE, event); };
;PROTOTYPE.focus = function(event) {
	if(!this.rendered || this.destroyed) { return this; }

	var qtips = $(SELECTOR),
		tooltip = this.tooltip,
		curIndex = parseInt(tooltip[0].style.zIndex, 10),
		newIndex = QTIP.zindex + qtips.length;

	// Only update the z-index if it has changed and tooltip is not already focused
	if(!tooltip.hasClass(CLASS_FOCUS)) {
		// tooltipfocus event
		if(this._trigger('focus', [newIndex], event)) {
			// Only update z-index's if they've changed
			if(curIndex !== newIndex) {
				// Reduce our z-index's and keep them properly ordered
				qtips.each(function() {
					if(this.style.zIndex > curIndex) {
						this.style.zIndex = this.style.zIndex - 1;
					}
				});

				// Fire blur event for focused tooltip
				qtips.filter('.' + CLASS_FOCUS).qtip('blur', event);
			}

			// Set the new z-index
			tooltip.addClass(CLASS_FOCUS)[0].style.zIndex = newIndex;
		}
	}

	return this;
};

PROTOTYPE.blur = function(event) {
	if(!this.rendered || this.destroyed) { return this; }

	// Set focused status to FALSE
	this.tooltip.removeClass(CLASS_FOCUS);

	// tooltipblur event
	this._trigger('blur', [ this.tooltip.css('zIndex') ], event);

	return this;
};
;PROTOTYPE.disable = function(state) {
	if(this.destroyed) { return this; }

	// If 'toggle' is passed, toggle the current state
	if(state === 'toggle') {
		state = !(this.rendered ? this.tooltip.hasClass(CLASS_DISABLED) : this.disabled);
	}

	// Disable if no state passed
	else if('boolean' !== typeof state) {
		state = TRUE;
	}

	if(this.rendered) {
		this.tooltip.toggleClass(CLASS_DISABLED, state)
			.attr('aria-disabled', state);
	}

	this.disabled = !!state;

	return this;
};

PROTOTYPE.enable = function() { return this.disable(FALSE); };
;PROTOTYPE._createButton = function()
{
	var self = this,
		elements = this.elements,
		tooltip = elements.tooltip,
		button = this.options.content.button,
		isString = typeof button === 'string',
		close = isString ? button : 'Close tooltip';

	if(elements.button) { elements.button.remove(); }

	// Use custom button if one was supplied by user, else use default
	if(button.jquery) {
		elements.button = button;
	}
	else {
		elements.button = $('<a />', {
			'class': 'qtip-close ' + (this.options.style.widget ? '' : NAMESPACE+'-icon'),
			'title': close,
			'aria-label': close
		})
		.prepend(
			$('<span />', {
				'class': 'ui-icon ui-icon-close',
				'html': '&times;'
			})
		);
	}

	// Create button and setup attributes
	elements.button.appendTo(elements.titlebar || tooltip)
		.attr('role', 'button')
		.click(function(event) {
			if(!tooltip.hasClass(CLASS_DISABLED)) { self.hide(event); }
			return FALSE;
		});
};

PROTOTYPE._updateButton = function(button)
{
	// Make sure tooltip is rendered and if not, return
	if(!this.rendered) { return FALSE; }

	var elem = this.elements.button;
	if(button) { this._createButton(); }
	else { elem.remove(); }
};
;// Widget class creator
function createWidgetClass(cls) {
	return WIDGET.concat('').join(cls ? '-'+cls+' ' : ' ');
}

// Widget class setter method
PROTOTYPE._setWidget = function()
{
	var on = this.options.style.widget,
		elements = this.elements,
		tooltip = elements.tooltip,
		disabled = tooltip.hasClass(CLASS_DISABLED);

	tooltip.removeClass(CLASS_DISABLED);
	CLASS_DISABLED = on ? 'ui-state-disabled' : 'qtip-disabled';
	tooltip.toggleClass(CLASS_DISABLED, disabled);

	tooltip.toggleClass('ui-helper-reset '+createWidgetClass(), on).toggleClass(CLASS_DEFAULT, this.options.style.def && !on);

	if(elements.content) {
		elements.content.toggleClass( createWidgetClass('content'), on);
	}
	if(elements.titlebar) {
		elements.titlebar.toggleClass( createWidgetClass('header'), on);
	}
	if(elements.button) {
		elements.button.toggleClass(NAMESPACE+'-icon', !on);
	}
};
;function delay(callback, duration) {
	// If tooltip has displayed, start hide timer
	if(duration > 0) {
		return setTimeout(
			$.proxy(callback, this), duration
		);
	}
	else{ callback.call(this); }
}

function showMethod(event) {
	if(this.tooltip.hasClass(CLASS_DISABLED)) { return; }

	// Clear hide timers
	clearTimeout(this.timers.show);
	clearTimeout(this.timers.hide);

	// Start show timer
	this.timers.show = delay.call(this,
		function() { this.toggle(TRUE, event); },
		this.options.show.delay
	);
}

function hideMethod(event) {
	if(this.tooltip.hasClass(CLASS_DISABLED) || this.destroyed) { return; }

	// Check if new target was actually the tooltip element
	var relatedTarget = $(event.relatedTarget),
		ontoTooltip = relatedTarget.closest(SELECTOR)[0] === this.tooltip[0],
		ontoTarget = relatedTarget[0] === this.options.show.target[0];

	// Clear timers and stop animation queue
	clearTimeout(this.timers.show);
	clearTimeout(this.timers.hide);

	// Prevent hiding if tooltip is fixed and event target is the tooltip.
	// Or if mouse positioning is enabled and cursor momentarily overlaps
	if(this !== relatedTarget[0] &&
		(this.options.position.target === 'mouse' && ontoTooltip) ||
		this.options.hide.fixed && (
			(/mouse(out|leave|move)/).test(event.type) && (ontoTooltip || ontoTarget))
		)
	{
		/* eslint-disable no-empty */
		try {
			event.preventDefault();
			event.stopImmediatePropagation();
		} catch(e) {}
		/* eslint-enable no-empty */

		return;
	}

	// If tooltip has displayed, start hide timer
	this.timers.hide = delay.call(this,
		function() { this.toggle(FALSE, event); },
		this.options.hide.delay,
		this
	);
}

function inactiveMethod(event) {
	if(this.tooltip.hasClass(CLASS_DISABLED) || !this.options.hide.inactive) { return; }

	// Clear timer
	clearTimeout(this.timers.inactive);

	this.timers.inactive = delay.call(this,
		function(){ this.hide(event); },
		this.options.hide.inactive
	);
}

function repositionMethod(event) {
	if(this.rendered && this.tooltip[0].offsetWidth > 0) { this.reposition(event); }
}

// Store mouse coordinates
PROTOTYPE._storeMouse = function(event) {
	(this.mouse = $.event.fix(event)).type = 'mousemove';
	return this;
};

// Bind events
PROTOTYPE._bind = function(targets, events, method, suffix, context) {
	if(!targets || !method || !events.length) { return; }
	var ns = '.' + this._id + (suffix ? '-'+suffix : '');
	$(targets).bind(
		(events.split ? events : events.join(ns + ' ')) + ns,
		$.proxy(method, context || this)
	);
	return this;
};
PROTOTYPE._unbind = function(targets, suffix) {
	targets && $(targets).unbind('.' + this._id + (suffix ? '-'+suffix : ''));
	return this;
};

// Global delegation helper
function delegate(selector, events, method) {
	$(document.body).delegate(selector,
		(events.split ? events : events.join('.'+NAMESPACE + ' ')) + '.'+NAMESPACE,
		function() {
			var api = QTIP.api[ $.attr(this, ATTR_ID) ];
			api && !api.disabled && method.apply(api, arguments);
		}
	);
}
// Event trigger
PROTOTYPE._trigger = function(type, args, event) {
	var callback = new $.Event('tooltip'+type);
	callback.originalEvent = event && $.extend({}, event) || this.cache.event || NULL;

	this.triggering = type;
	this.tooltip.trigger(callback, [this].concat(args || []));
	this.triggering = FALSE;

	return !callback.isDefaultPrevented();
};

PROTOTYPE._bindEvents = function(showEvents, hideEvents, showTargets, hideTargets, showCallback, hideCallback) {
	// Get tasrgets that lye within both
	var similarTargets = showTargets.filter( hideTargets ).add( hideTargets.filter(showTargets) ),
		toggleEvents = [];

	// If hide and show targets are the same...
	if(similarTargets.length) {

		// Filter identical show/hide events
		$.each(hideEvents, function(i, type) {
			var showIndex = $.inArray(type, showEvents);

			// Both events are identical, remove from both hide and show events
			// and append to toggleEvents
			showIndex > -1 && toggleEvents.push( showEvents.splice( showIndex, 1 )[0] );
		});

		// Toggle events are special case of identical show/hide events, which happen in sequence
		if(toggleEvents.length) {
			// Bind toggle events to the similar targets
			this._bind(similarTargets, toggleEvents, function(event) {
				var state = this.rendered ? this.tooltip[0].offsetWidth > 0 : false;
				(state ? hideCallback : showCallback).call(this, event);
			});

			// Remove the similar targets from the regular show/hide bindings
			showTargets = showTargets.not(similarTargets);
			hideTargets = hideTargets.not(similarTargets);
		}
	}

	// Apply show/hide/toggle events
	this._bind(showTargets, showEvents, showCallback);
	this._bind(hideTargets, hideEvents, hideCallback);
};

PROTOTYPE._assignInitialEvents = function(event) {
	var options = this.options,
		showTarget = options.show.target,
		hideTarget = options.hide.target,
		showEvents = options.show.event ? $.trim('' + options.show.event).split(' ') : [],
		hideEvents = options.hide.event ? $.trim('' + options.hide.event).split(' ') : [];

	// Catch remove/removeqtip events on target element to destroy redundant tooltips
	this._bind(this.elements.target, ['remove', 'removeqtip'], function() {
		this.destroy(true);
	}, 'destroy');

	/*
	 * Make sure hoverIntent functions properly by using mouseleave as a hide event if
	 * mouseenter/mouseout is used for show.event, even if it isn't in the users options.
	 */
	if(/mouse(over|enter)/i.test(options.show.event) && !/mouse(out|leave)/i.test(options.hide.event)) {
		hideEvents.push('mouseleave');
	}

	/*
	 * Also make sure initial mouse targetting works correctly by caching mousemove coords
	 * on show targets before the tooltip has rendered. Also set onTarget when triggered to
	 * keep mouse tracking working.
	 */
	this._bind(showTarget, 'mousemove', function(moveEvent) {
		this._storeMouse(moveEvent);
		this.cache.onTarget = TRUE;
	});

	// Define hoverIntent function
	function hoverIntent(hoverEvent) {
		// Only continue if tooltip isn't disabled
		if(this.disabled || this.destroyed) { return FALSE; }

		// Cache the event data
		this.cache.event = hoverEvent && $.event.fix(hoverEvent);
		this.cache.target = hoverEvent && $(hoverEvent.target);

		// Start the event sequence
		clearTimeout(this.timers.show);
		this.timers.show = delay.call(this,
			function() { this.render(typeof hoverEvent === 'object' || options.show.ready); },
			options.prerender ? 0 : options.show.delay
		);
	}

	// Filter and bind events
	this._bindEvents(showEvents, hideEvents, showTarget, hideTarget, hoverIntent, function() {
		if(!this.timers) { return FALSE; }
		clearTimeout(this.timers.show);
	});

	// Prerendering is enabled, create tooltip now
	if(options.show.ready || options.prerender) { hoverIntent.call(this, event); }
};

// Event assignment method
PROTOTYPE._assignEvents = function() {
	var self = this,
		options = this.options,
		posOptions = options.position,

		tooltip = this.tooltip,
		showTarget = options.show.target,
		hideTarget = options.hide.target,
		containerTarget = posOptions.container,
		viewportTarget = posOptions.viewport,
		documentTarget = $(document),
		windowTarget = $(window),

		showEvents = options.show.event ? $.trim('' + options.show.event).split(' ') : [],
		hideEvents = options.hide.event ? $.trim('' + options.hide.event).split(' ') : [];


	// Assign passed event callbacks
	$.each(options.events, function(name, callback) {
		self._bind(tooltip, name === 'toggle' ? ['tooltipshow','tooltiphide'] : ['tooltip'+name], callback, null, tooltip);
	});

	// Hide tooltips when leaving current window/frame (but not select/option elements)
	if(/mouse(out|leave)/i.test(options.hide.event) && options.hide.leave === 'window') {
		this._bind(documentTarget, ['mouseout', 'blur'], function(event) {
			if(!/select|option/.test(event.target.nodeName) && !event.relatedTarget) {
				this.hide(event);
			}
		});
	}

	// Enable hide.fixed by adding appropriate class
	if(options.hide.fixed) {
		hideTarget = hideTarget.add( tooltip.addClass(CLASS_FIXED) );
	}

	/*
	 * Make sure hoverIntent functions properly by using mouseleave to clear show timer if
	 * mouseenter/mouseout is used for show.event, even if it isn't in the users options.
	 */
	else if(/mouse(over|enter)/i.test(options.show.event)) {
		this._bind(hideTarget, 'mouseleave', function() {
			clearTimeout(this.timers.show);
		});
	}

	// Hide tooltip on document mousedown if unfocus events are enabled
	if(('' + options.hide.event).indexOf('unfocus') > -1) {
		this._bind(containerTarget.closest('html'), ['mousedown', 'touchstart'], function(event) {
			var elem = $(event.target),
				enabled = this.rendered && !this.tooltip.hasClass(CLASS_DISABLED) && this.tooltip[0].offsetWidth > 0,
				isAncestor = elem.parents(SELECTOR).filter(this.tooltip[0]).length > 0;

			if(elem[0] !== this.target[0] && elem[0] !== this.tooltip[0] && !isAncestor &&
				!this.target.has(elem[0]).length && enabled
			) {
				this.hide(event);
			}
		});
	}

	// Check if the tooltip hides when inactive
	if('number' === typeof options.hide.inactive) {
		// Bind inactive method to show target(s) as a custom event
		this._bind(showTarget, 'qtip-'+this.id+'-inactive', inactiveMethod, 'inactive');

		// Define events which reset the 'inactive' event handler
		this._bind(hideTarget.add(tooltip), QTIP.inactiveEvents, inactiveMethod);
	}

	// Filter and bind events
	this._bindEvents(showEvents, hideEvents, showTarget, hideTarget, showMethod, hideMethod);

	// Mouse movement bindings
	this._bind(showTarget.add(tooltip), 'mousemove', function(event) {
		// Check if the tooltip hides when mouse is moved a certain distance
		if('number' === typeof options.hide.distance) {
			var origin = this.cache.origin || {},
				limit = this.options.hide.distance,
				abs = Math.abs;

			// Check if the movement has gone beyond the limit, and hide it if so
			if(abs(event.pageX - origin.pageX) >= limit || abs(event.pageY - origin.pageY) >= limit) {
				this.hide(event);
			}
		}

		// Cache mousemove coords on show targets
		this._storeMouse(event);
	});

	// Mouse positioning events
	if(posOptions.target === 'mouse') {
		// If mouse adjustment is on...
		if(posOptions.adjust.mouse) {
			// Apply a mouseleave event so we don't get problems with overlapping
			if(options.hide.event) {
				// Track if we're on the target or not
				this._bind(showTarget, ['mouseenter', 'mouseleave'], function(event) {
					if(!this.cache) {return FALSE; }
					this.cache.onTarget = event.type === 'mouseenter';
				});
			}

			// Update tooltip position on mousemove
			this._bind(documentTarget, 'mousemove', function(event) {
				// Update the tooltip position only if the tooltip is visible and adjustment is enabled
				if(this.rendered && this.cache.onTarget && !this.tooltip.hasClass(CLASS_DISABLED) && this.tooltip[0].offsetWidth > 0) {
					this.reposition(event);
				}
			});
		}
	}

	// Adjust positions of the tooltip on window resize if enabled
	if(posOptions.adjust.resize || viewportTarget.length) {
		this._bind( $.event.special.resize ? viewportTarget : windowTarget, 'resize', repositionMethod );
	}

	// Adjust tooltip position on scroll of the window or viewport element if present
	if(posOptions.adjust.scroll) {
		this._bind( windowTarget.add(posOptions.container), 'scroll', repositionMethod );
	}
};

// Un-assignment method
PROTOTYPE._unassignEvents = function() {
	var options = this.options,
		showTargets = options.show.target,
		hideTargets = options.hide.target,
		targets = $.grep([
			this.elements.target[0],
			this.rendered && this.tooltip[0],
			options.position.container[0],
			options.position.viewport[0],
			options.position.container.closest('html')[0], // unfocus
			window,
			document
		], function(i) {
			return typeof i === 'object';
		});

	// Add show and hide targets if they're valid
	if(showTargets && showTargets.toArray) {
		targets = targets.concat(showTargets.toArray());
	}
	if(hideTargets && hideTargets.toArray) {
		targets = targets.concat(hideTargets.toArray());
	}

	// Unbind the events
	this._unbind(targets)
		._unbind(targets, 'destroy')
		._unbind(targets, 'inactive');
};

// Apply common event handlers using delegate (avoids excessive .bind calls!)
$(function() {
	delegate(SELECTOR, ['mouseenter', 'mouseleave'], function(event) {
		var state = event.type === 'mouseenter',
			tooltip = $(event.currentTarget),
			target = $(event.relatedTarget || event.target),
			options = this.options;

		// On mouseenter...
		if(state) {
			// Focus the tooltip on mouseenter (z-index stacking)
			this.focus(event);

			// Clear hide timer on tooltip hover to prevent it from closing
			tooltip.hasClass(CLASS_FIXED) && !tooltip.hasClass(CLASS_DISABLED) && clearTimeout(this.timers.hide);
		}

		// On mouseleave...
		else {
			// When mouse tracking is enabled, hide when we leave the tooltip and not onto the show target (if a hide event is set)
			if(options.position.target === 'mouse' && options.position.adjust.mouse &&
				options.hide.event && options.show.target && !target.closest(options.show.target[0]).length) {
				this.hide(event);
			}
		}

		// Add hover class
		tooltip.toggleClass(CLASS_HOVER, state);
	});

	// Define events which reset the 'inactive' event handler
	delegate('['+ATTR_ID+']', INACTIVE_EVENTS, inactiveMethod);
});
;// Initialization method
function init(elem, id, opts) {
	var obj, posOptions, attr, config, title,

	// Setup element references
	docBody = $(document.body),

	// Use document body instead of document element if needed
	newTarget = elem[0] === document ? docBody : elem,

	// Grab metadata from element if plugin is present
	metadata = elem.metadata ? elem.metadata(opts.metadata) : NULL,

	// If metadata type if HTML5, grab 'name' from the object instead, or use the regular data object otherwise
	metadata5 = opts.metadata.type === 'html5' && metadata ? metadata[opts.metadata.name] : NULL,

	// Grab data from metadata.name (or data-qtipopts as fallback) using .data() method,
	html5 = elem.data(opts.metadata.name || 'qtipopts');

	// If we don't get an object returned attempt to parse it manualyl without parseJSON
	/* eslint-disable no-empty */
	try { html5 = typeof html5 === 'string' ? $.parseJSON(html5) : html5; }
	catch(e) {}
	/* eslint-enable no-empty */

	// Merge in and sanitize metadata
	config = $.extend(TRUE, {}, QTIP.defaults, opts,
		typeof html5 === 'object' ? sanitizeOptions(html5) : NULL,
		sanitizeOptions(metadata5 || metadata));

	// Re-grab our positioning options now we've merged our metadata and set id to passed value
	posOptions = config.position;
	config.id = id;

	// Setup missing content if none is detected
	if('boolean' === typeof config.content.text) {
		attr = elem.attr(config.content.attr);

		// Grab from supplied attribute if available
		if(config.content.attr !== FALSE && attr) { config.content.text = attr; }

		// No valid content was found, abort render
		else { return FALSE; }
	}

	// Setup target options
	if(!posOptions.container.length) { posOptions.container = docBody; }
	if(posOptions.target === FALSE) { posOptions.target = newTarget; }
	if(config.show.target === FALSE) { config.show.target = newTarget; }
	if(config.show.solo === TRUE) { config.show.solo = posOptions.container.closest('body'); }
	if(config.hide.target === FALSE) { config.hide.target = newTarget; }
	if(config.position.viewport === TRUE) { config.position.viewport = posOptions.container; }

	// Ensure we only use a single container
	posOptions.container = posOptions.container.eq(0);

	// Convert position corner values into x and y strings
	posOptions.at = new CORNER(posOptions.at, TRUE);
	posOptions.my = new CORNER(posOptions.my);

	// Destroy previous tooltip if overwrite is enabled, or skip element if not
	if(elem.data(NAMESPACE)) {
		if(config.overwrite) {
			elem.qtip('destroy', true);
		}
		else if(config.overwrite === FALSE) {
			return FALSE;
		}
	}

	// Add has-qtip attribute
	elem.attr(ATTR_HAS, id);

	// Remove title attribute and store it if present
	if(config.suppress && (title = elem.attr('title'))) {
		// Final attr call fixes event delegatiom and IE default tooltip showing problem
		elem.removeAttr('title').attr(oldtitle, title).attr('title', '');
	}

	// Initialize the tooltip and add API reference
	obj = new QTip(elem, config, id, !!attr);
	elem.data(NAMESPACE, obj);

	return obj;
}

// jQuery $.fn extension method
QTIP = $.fn.qtip = function(options, notation, newValue)
{
	var command = ('' + options).toLowerCase(), // Parse command
		returned = NULL,
		args = $.makeArray(arguments).slice(1),
		event = args[args.length - 1],
		opts = this[0] ? $.data(this[0], NAMESPACE) : NULL;

	// Check for API request
	if(!arguments.length && opts || command === 'api') {
		return opts;
	}

	// Execute API command if present
	else if('string' === typeof options) {
		this.each(function() {
			var api = $.data(this, NAMESPACE);
			if(!api) { return TRUE; }

			// Cache the event if possible
			if(event && event.timeStamp) { api.cache.event = event; }

			// Check for specific API commands
			if(notation && (command === 'option' || command === 'options')) {
				if(newValue !== undefined || $.isPlainObject(notation)) {
					api.set(notation, newValue);
				}
				else {
					returned = api.get(notation);
					return FALSE;
				}
			}

			// Execute API command
			else if(api[command]) {
				api[command].apply(api, args);
			}
		});

		return returned !== NULL ? returned : this;
	}

	// No API commands. validate provided options and setup qTips
	else if('object' === typeof options || !arguments.length) {
		// Sanitize options first
		opts = sanitizeOptions($.extend(TRUE, {}, options));

		return this.each(function(i) {
			var api, id;

			// Find next available ID, or use custom ID if provided
			id = $.isArray(opts.id) ? opts.id[i] : opts.id;
			id = !id || id === FALSE || id.length < 1 || QTIP.api[id] ? QTIP.nextid++ : id;

			// Initialize the qTip and re-grab newly sanitized options
			api = init($(this), id, opts);
			if(api === FALSE) { return TRUE; }
			else { QTIP.api[id] = api; }

			// Initialize plugins
			$.each(PLUGINS, function() {
				if(this.initialize === 'initialize') { this(api); }
			});

			// Assign initial pre-render events
			api._assignInitialEvents(event);
		});
	}
};

// Expose class
$.qtip = QTip;

// Populated in render method
QTIP.api = {};
;$.each({
	/* Allow other plugins to successfully retrieve the title of an element with a qTip applied */
	attr: function(attr, val) {
		if(this.length) {
			var self = this[0],
				title = 'title',
				api = $.data(self, 'qtip');

			if(attr === title && api && api.options && 'object' === typeof api && 'object' === typeof api.options && api.options.suppress) {
				if(arguments.length < 2) {
					return $.attr(self, oldtitle);
				}

				// If qTip is rendered and title was originally used as content, update it
				if(api && api.options.content.attr === title && api.cache.attr) {
					api.set('content.text', val);
				}

				// Use the regular attr method to set, then cache the result
				return this.attr(oldtitle, val);
			}
		}

		return $.fn['attr'+replaceSuffix].apply(this, arguments);
	},

	/* Allow clone to correctly retrieve cached title attributes */
	clone: function(keepData) {
		// Clone our element using the real clone method
		var elems = $.fn['clone'+replaceSuffix].apply(this, arguments);

		// Grab all elements with an oldtitle set, and change it to regular title attribute, if keepData is false
		if(!keepData) {
			elems.filter('['+oldtitle+']').attr('title', function() {
				return $.attr(this, oldtitle);
			})
			.removeAttr(oldtitle);
		}

		return elems;
	}
}, function(name, func) {
	if(!func || $.fn[name+replaceSuffix]) { return TRUE; }

	var old = $.fn[name+replaceSuffix] = $.fn[name];
	$.fn[name] = function() {
		return func.apply(this, arguments) || old.apply(this, arguments);
	};
});

/* Fire off 'removeqtip' handler in $.cleanData if jQuery UI not present (it already does similar).
 * This snippet is taken directly from jQuery UI source code found here:
 *     http://code.jquery.com/ui/jquery-ui-git.js
 */
if(!$.ui) {
	$['cleanData'+replaceSuffix] = $.cleanData;
	$.cleanData = function( elems ) {
		for(var i = 0, elem; (elem = $( elems[i] )).length; i++) {
			if(elem.attr(ATTR_HAS)) {
				/* eslint-disable no-empty */
				try { elem.triggerHandler('removeqtip'); }
				catch( e ) {}
				/* eslint-enable no-empty */
			}
		}
		$['cleanData'+replaceSuffix].apply(this, arguments);
	};
}
;// qTip version
QTIP.version = '3.0.3';

// Base ID for all qTips
QTIP.nextid = 0;

// Inactive events array
QTIP.inactiveEvents = INACTIVE_EVENTS;

// Base z-index for all qTips
QTIP.zindex = 15000;

// Define configuration defaults
QTIP.defaults = {
	prerender: FALSE,
	id: FALSE,
	overwrite: TRUE,
	suppress: TRUE,
	content: {
		text: TRUE,
		attr: 'title',
		title: FALSE,
		button: FALSE
	},
	position: {
		my: 'top left',
		at: 'bottom right',
		target: FALSE,
		container: FALSE,
		viewport: FALSE,
		adjust: {
			x: 0, y: 0,
			mouse: TRUE,
			scroll: TRUE,
			resize: TRUE,
			method: 'flipinvert flipinvert'
		},
		effect: function(api, pos) {
			$(this).animate(pos, {
				duration: 200,
				queue: FALSE
			});
		}
	},
	show: {
		target: FALSE,
		event: 'mouseenter',
		effect: TRUE,
		delay: 90,
		solo: FALSE,
		ready: FALSE,
		autofocus: FALSE
	},
	hide: {
		target: FALSE,
		event: 'mouseleave',
		effect: TRUE,
		delay: 0,
		fixed: FALSE,
		inactive: FALSE,
		leave: 'window',
		distance: FALSE
	},
	style: {
		classes: '',
		widget: FALSE,
		width: FALSE,
		height: FALSE,
		def: TRUE
	},
	events: {
		render: NULL,
		move: NULL,
		show: NULL,
		hide: NULL,
		toggle: NULL,
		visible: NULL,
		hidden: NULL,
		focus: NULL,
		blur: NULL
	}
};
;var TIP,
createVML,
SCALE,
PIXEL_RATIO,
BACKING_STORE_RATIO,

// Common CSS strings
MARGIN = 'margin',
BORDER = 'border',
COLOR = 'color',
BG_COLOR = 'background-color',
TRANSPARENT = 'transparent',
IMPORTANT = ' !important',

// Check if the browser supports <canvas/> elements
HASCANVAS = !!document.createElement('canvas').getContext,

// Invalid colour values used in parseColours()
INVALID = /rgba?\(0, 0, 0(, 0)?\)|transparent|#123456/i;

// Camel-case method, taken from jQuery source
// http://code.jquery.com/jquery-1.8.0.js
function camel(s) { return s.charAt(0).toUpperCase() + s.slice(1); }

/*
 * Modified from Modernizr's testPropsAll()
 * http://modernizr.com/downloads/modernizr-latest.js
 */
var cssProps = {}, cssPrefixes = ['Webkit', 'O', 'Moz', 'ms'];
function vendorCss(elem, prop) {
	var ucProp = prop.charAt(0).toUpperCase() + prop.slice(1),
		props = (prop + ' ' + cssPrefixes.join(ucProp + ' ') + ucProp).split(' '),
		cur, val, i = 0;

	// If the property has already been mapped...
	if(cssProps[prop]) { return elem.css(cssProps[prop]); }

	while(cur = props[i++]) {
		if((val = elem.css(cur)) !== undefined) {
			cssProps[prop] = cur;
			return val;
		}
	}
}

// Parse a given elements CSS property into an int
function intCss(elem, prop) {
	return Math.ceil(parseFloat(vendorCss(elem, prop)));
}


// VML creation (for IE only)
if(!HASCANVAS) {
	createVML = function(tag, props, style) {
		return '<qtipvml:'+tag+' xmlns="urn:schemas-microsoft.com:vml" class="qtip-vml" '+(props||'')+
			' style="behavior: url(#default#VML); '+(style||'')+ '" />';
	};
}

// Canvas only definitions
else {
	PIXEL_RATIO = window.devicePixelRatio || 1;
	BACKING_STORE_RATIO = (function() {
		var context = document.createElement('canvas').getContext('2d');
		return context.backingStorePixelRatio || context.webkitBackingStorePixelRatio || context.mozBackingStorePixelRatio ||
				context.msBackingStorePixelRatio || context.oBackingStorePixelRatio || 1;
	})();
	SCALE = PIXEL_RATIO / BACKING_STORE_RATIO;
}


function Tip(qtip, options) {
	this._ns = 'tip';
	this.options = options;
	this.offset = options.offset;
	this.size = [ options.width, options.height ];

	// Initialize
	this.qtip = qtip;
	this.init(qtip);
}

$.extend(Tip.prototype, {
	init: function(qtip) {
		var context, tip;

		// Create tip element and prepend to the tooltip
		tip = this.element = qtip.elements.tip = $('<div />', { 'class': NAMESPACE+'-tip' }).prependTo(qtip.tooltip);

		// Create tip drawing element(s)
		if(HASCANVAS) {
			// save() as soon as we create the canvas element so FF2 doesn't bork on our first restore()!
			context = $('<canvas />').appendTo(this.element)[0].getContext('2d');

			// Setup constant parameters
			context.lineJoin = 'miter';
			context.miterLimit = 100000;
			context.save();
		}
		else {
			context = createVML('shape', 'coordorigin="0,0"', 'position:absolute;');
			this.element.html(context + context);

			// Prevent mousing down on the tip since it causes problems with .live() handling in IE due to VML
			qtip._bind( $('*', tip).add(tip), ['click', 'mousedown'], function(event) { event.stopPropagation(); }, this._ns);
		}

		// Bind update events
		qtip._bind(qtip.tooltip, 'tooltipmove', this.reposition, this._ns, this);

		// Create it
		this.create();
	},

	_swapDimensions: function() {
		this.size[0] = this.options.height;
		this.size[1] = this.options.width;
	},
	_resetDimensions: function() {
		this.size[0] = this.options.width;
		this.size[1] = this.options.height;
	},

	_useTitle: function(corner) {
		var titlebar = this.qtip.elements.titlebar;
		return titlebar && (
			corner.y === TOP || corner.y === CENTER && this.element.position().top + this.size[1] / 2 + this.options.offset < titlebar.outerHeight(TRUE)
		);
	},

	_parseCorner: function(corner) {
		var my = this.qtip.options.position.my;

		// Detect corner and mimic properties
		if(corner === FALSE || my === FALSE) {
			corner = FALSE;
		}
		else if(corner === TRUE) {
			corner = new CORNER( my.string() );
		}
		else if(!corner.string) {
			corner = new CORNER(corner);
			corner.fixed = TRUE;
		}

		return corner;
	},

	_parseWidth: function(corner, side, use) {
		var elements = this.qtip.elements,
			prop = BORDER + camel(side) + 'Width';

		return (use ? intCss(use, prop) : 
			intCss(elements.content, prop) ||
			intCss(this._useTitle(corner) && elements.titlebar || elements.content, prop) ||
			intCss(elements.tooltip, prop)
		) || 0;
	},

	_parseRadius: function(corner) {
		var elements = this.qtip.elements,
			prop = BORDER + camel(corner.y) + camel(corner.x) + 'Radius';

		return BROWSER.ie < 9 ? 0 :
			intCss(this._useTitle(corner) && elements.titlebar || elements.content, prop) ||
			intCss(elements.tooltip, prop) || 0;
	},

	_invalidColour: function(elem, prop, compare) {
		var val = elem.css(prop);
		return !val || compare && val === elem.css(compare) || INVALID.test(val) ? FALSE : val;
	},

	_parseColours: function(corner) {
		var elements = this.qtip.elements,
			tip = this.element.css('cssText', ''),
			borderSide = BORDER + camel(corner[ corner.precedance ]) + camel(COLOR),
			colorElem = this._useTitle(corner) && elements.titlebar || elements.content,
			css = this._invalidColour, color = [];

		// Attempt to detect the background colour from various elements, left-to-right precedance
		color[0] = css(tip, BG_COLOR) || css(colorElem, BG_COLOR) || css(elements.content, BG_COLOR) ||
			css(elements.tooltip, BG_COLOR) || tip.css(BG_COLOR);

		// Attempt to detect the correct border side colour from various elements, left-to-right precedance
		color[1] = css(tip, borderSide, COLOR) || css(colorElem, borderSide, COLOR) ||
			css(elements.content, borderSide, COLOR) || css(elements.tooltip, borderSide, COLOR) || elements.tooltip.css(borderSide);

		// Reset background and border colours
		$('*', tip).add(tip).css('cssText', BG_COLOR+':'+TRANSPARENT+IMPORTANT+';'+BORDER+':0'+IMPORTANT+';');

		return color;
	},

	_calculateSize: function(corner) {
		var y = corner.precedance === Y,
			width = this.options.width,
			height = this.options.height,
			isCenter = corner.abbrev() === 'c',
			base = (y ? width: height) * (isCenter ? 0.5 : 1),
			pow = Math.pow,
			round = Math.round,
			bigHyp, ratio, result,

		smallHyp = Math.sqrt( pow(base, 2) + pow(height, 2) ),
		hyp = [
			this.border / base * smallHyp,
			this.border / height * smallHyp
		];

		hyp[2] = Math.sqrt( pow(hyp[0], 2) - pow(this.border, 2) );
		hyp[3] = Math.sqrt( pow(hyp[1], 2) - pow(this.border, 2) );

		bigHyp = smallHyp + hyp[2] + hyp[3] + (isCenter ? 0 : hyp[0]);
		ratio = bigHyp / smallHyp;

		result = [ round(ratio * width), round(ratio * height) ];
		return y ? result : result.reverse();
	},

	// Tip coordinates calculator
	_calculateTip: function(corner, size, scale) {
		scale = scale || 1;
		size = size || this.size;

		var width = size[0] * scale,
			height = size[1] * scale,
			width2 = Math.ceil(width / 2), height2 = Math.ceil(height / 2),

		// Define tip coordinates in terms of height and width values
		tips = {
			br:	[0,0,		width,height,	width,0],
			bl:	[0,0,		width,0,		0,height],
			tr:	[0,height,	width,0,		width,height],
			tl:	[0,0,		0,height,		width,height],
			tc:	[0,height,	width2,0,		width,height],
			bc:	[0,0,		width,0,		width2,height],
			rc:	[0,0,		width,height2,	0,height],
			lc:	[width,0,	width,height,	0,height2]
		};

		// Set common side shapes
		tips.lt = tips.br; tips.rt = tips.bl;
		tips.lb = tips.tr; tips.rb = tips.tl;

		return tips[ corner.abbrev() ];
	},

	// Tip coordinates drawer (canvas)
	_drawCoords: function(context, coords) {
		context.beginPath();
		context.moveTo(coords[0], coords[1]);
		context.lineTo(coords[2], coords[3]);
		context.lineTo(coords[4], coords[5]);
		context.closePath();
	},

	create: function() {
		// Determine tip corner
		var c = this.corner = (HASCANVAS || BROWSER.ie) && this._parseCorner(this.options.corner);

		// If we have a tip corner...
		this.enabled = !!this.corner && this.corner.abbrev() !== 'c';
		if(this.enabled) {
			// Cache it
			this.qtip.cache.corner = c.clone();

			// Create it
			this.update();
		}

		// Toggle tip element
		this.element.toggle(this.enabled);

		return this.corner;
	},

	update: function(corner, position) {
		if(!this.enabled) { return this; }

		var elements = this.qtip.elements,
			tip = this.element,
			inner = tip.children(),
			options = this.options,
			curSize = this.size,
			mimic = options.mimic,
			round = Math.round,
			color, precedance, context,
			coords, bigCoords, translate, newSize, border;

		// Re-determine tip if not already set
		if(!corner) { corner = this.qtip.cache.corner || this.corner; }

		// Use corner property if we detect an invalid mimic value
		if(mimic === FALSE) { mimic = corner; }

		// Otherwise inherit mimic properties from the corner object as necessary
		else {
			mimic = new CORNER(mimic);
			mimic.precedance = corner.precedance;

			if(mimic.x === 'inherit') { mimic.x = corner.x; }
			else if(mimic.y === 'inherit') { mimic.y = corner.y; }
			else if(mimic.x === mimic.y) {
				mimic[ corner.precedance ] = corner[ corner.precedance ];
			}
		}
		precedance = mimic.precedance;

		// Ensure the tip width.height are relative to the tip position
		if(corner.precedance === X) { this._swapDimensions(); }
		else { this._resetDimensions(); }

		// Update our colours
		color = this.color = this._parseColours(corner);

		// Detect border width, taking into account colours
		if(color[1] !== TRANSPARENT) {
			// Grab border width
			border = this.border = this._parseWidth(corner, corner[corner.precedance]);

			// If border width isn't zero, use border color as fill if it's not invalid (1.0 style tips)
			if(options.border && border < 1 && !INVALID.test(color[1])) { color[0] = color[1]; }

			// Set border width (use detected border width if options.border is true)
			this.border = border = options.border !== TRUE ? options.border : border;
		}

		// Border colour was invalid, set border to zero
		else { this.border = border = 0; }

		// Determine tip size
		newSize = this.size = this._calculateSize(corner);
		tip.css({
			width: newSize[0],
			height: newSize[1],
			lineHeight: newSize[1]+'px'
		});

		// Calculate tip translation
		if(corner.precedance === Y) {
			translate = [
				round(mimic.x === LEFT ? border : mimic.x === RIGHT ? newSize[0] - curSize[0] - border : (newSize[0] - curSize[0]) / 2),
				round(mimic.y === TOP ? newSize[1] - curSize[1] : 0)
			];
		}
		else {
			translate = [
				round(mimic.x === LEFT ? newSize[0] - curSize[0] : 0),
				round(mimic.y === TOP ? border : mimic.y === BOTTOM ? newSize[1] - curSize[1] - border : (newSize[1] - curSize[1]) / 2)
			];
		}

		// Canvas drawing implementation
		if(HASCANVAS) {
			// Grab canvas context and clear/save it
			context = inner[0].getContext('2d');
			context.restore(); context.save();
			context.clearRect(0,0,6000,6000);

			// Calculate coordinates
			coords = this._calculateTip(mimic, curSize, SCALE);
			bigCoords = this._calculateTip(mimic, this.size, SCALE);

			// Set the canvas size using calculated size
			inner.attr(WIDTH, newSize[0] * SCALE).attr(HEIGHT, newSize[1] * SCALE);
			inner.css(WIDTH, newSize[0]).css(HEIGHT, newSize[1]);

			// Draw the outer-stroke tip
			this._drawCoords(context, bigCoords);
			context.fillStyle = color[1];
			context.fill();

			// Draw the actual tip
			context.translate(translate[0] * SCALE, translate[1] * SCALE);
			this._drawCoords(context, coords);
			context.fillStyle = color[0];
			context.fill();
		}

		// VML (IE Proprietary implementation)
		else {
			// Calculate coordinates
			coords = this._calculateTip(mimic);

			// Setup coordinates string
			coords = 'm' + coords[0] + ',' + coords[1] + ' l' + coords[2] +
				',' + coords[3] + ' ' + coords[4] + ',' + coords[5] + ' xe';

			// Setup VML-specific offset for pixel-perfection
			translate[2] = border && /^(r|b)/i.test(corner.string()) ?
				BROWSER.ie === 8 ? 2 : 1 : 0;

			// Set initial CSS
			inner.css({
				coordsize: newSize[0]+border + ' ' + newSize[1]+border,
				antialias: ''+(mimic.string().indexOf(CENTER) > -1),
				left: translate[0] - translate[2] * Number(precedance === X),
				top: translate[1] - translate[2] * Number(precedance === Y),
				width: newSize[0] + border,
				height: newSize[1] + border
			})
			.each(function(i) {
				var $this = $(this);

				// Set shape specific attributes
				$this[ $this.prop ? 'prop' : 'attr' ]({
					coordsize: newSize[0]+border + ' ' + newSize[1]+border,
					path: coords,
					fillcolor: color[0],
					filled: !!i,
					stroked: !i
				})
				.toggle(!!(border || i));

				// Check if border is enabled and add stroke element
				!i && $this.html( createVML(
					'stroke', 'weight="'+border*2+'px" color="'+color[1]+'" miterlimit="1000" joinstyle="miter"'
				) );
			});
		}

		// Opera bug #357 - Incorrect tip position
		// https://github.com/Craga89/qTip2/issues/367
		window.opera && setTimeout(function() {
			elements.tip.css({
				display: 'inline-block',
				visibility: 'visible'
			});
		}, 1);

		// Position if needed
		if(position !== FALSE) { this.calculate(corner, newSize); }
	},

	calculate: function(corner, size) {
		if(!this.enabled) { return FALSE; }

		var self = this,
			elements = this.qtip.elements,
			tip = this.element,
			userOffset = this.options.offset,
			position = {},
			precedance, corners;

		// Inherit corner if not provided
		corner = corner || this.corner;
		precedance = corner.precedance;

		// Determine which tip dimension to use for adjustment
		size = size || this._calculateSize(corner);

		// Setup corners and offset array
		corners = [ corner.x, corner.y ];
		if(precedance === X) { corners.reverse(); }

		// Calculate tip position
		$.each(corners, function(i, side) {
			var b, bc, br;

			if(side === CENTER) {
				b = precedance === Y ? LEFT : TOP;
				position[ b ] = '50%';
				position[MARGIN+'-' + b] = -Math.round(size[ precedance === Y ? 0 : 1 ] / 2) + userOffset;
			}
			else {
				b = self._parseWidth(corner, side, elements.tooltip);
				bc = self._parseWidth(corner, side, elements.content);
				br = self._parseRadius(corner);

				position[ side ] = Math.max(-self.border, i ? bc : userOffset + (br > b ? br : -b));
			}
		});

		// Adjust for tip size
		position[ corner[precedance] ] -= size[ precedance === X ? 0 : 1 ];

		// Set and return new position
		tip.css({ margin: '', top: '', bottom: '', left: '', right: '' }).css(position);
		return position;
	},

	reposition: function(event, api, pos) {
		if(!this.enabled) { return; }

		var cache = api.cache,
			newCorner = this.corner.clone(),
			adjust = pos.adjusted,
			method = api.options.position.adjust.method.split(' '),
			horizontal = method[0],
			vertical = method[1] || method[0],
			shift = { left: FALSE, top: FALSE, x: 0, y: 0 },
			offset, css = {}, props;

		function shiftflip(direction, precedance, popposite, side, opposite) {
			// Horizontal - Shift or flip method
			if(direction === SHIFT && newCorner.precedance === precedance && adjust[side] && newCorner[popposite] !== CENTER) {
				newCorner.precedance = newCorner.precedance === X ? Y : X;
			}
			else if(direction !== SHIFT && adjust[side]){
				newCorner[precedance] = newCorner[precedance] === CENTER ?
					adjust[side] > 0 ? side : opposite :
					newCorner[precedance] === side ? opposite : side;
			}
		}

		function shiftonly(xy, side, opposite) {
			if(newCorner[xy] === CENTER) {
				css[MARGIN+'-'+side] = shift[xy] = offset[MARGIN+'-'+side] - adjust[side];
			}
			else {
				props = offset[opposite] !== undefined ?
					[ adjust[side], -offset[side] ] : [ -adjust[side], offset[side] ];

				if( (shift[xy] = Math.max(props[0], props[1])) > props[0] ) {
					pos[side] -= adjust[side];
					shift[side] = FALSE;
				}

				css[ offset[opposite] !== undefined ? opposite : side ] = shift[xy];
			}
		}

		// If our tip position isn't fixed e.g. doesn't adjust with viewport...
		if(this.corner.fixed !== TRUE) {
			// Perform shift/flip adjustments
			shiftflip(horizontal, X, Y, LEFT, RIGHT);
			shiftflip(vertical, Y, X, TOP, BOTTOM);

			// Update and redraw the tip if needed (check cached details of last drawn tip)
			if(newCorner.string() !== cache.corner.string() || cache.cornerTop !== adjust.top || cache.cornerLeft !== adjust.left) {
				this.update(newCorner, FALSE);
			}
		}

		// Setup tip offset properties
		offset = this.calculate(newCorner);

		// Readjust offset object to make it left/top
		if(offset.right !== undefined) { offset.left = -offset.right; }
		if(offset.bottom !== undefined) { offset.top = -offset.bottom; }
		offset.user = this.offset;

		// Perform shift adjustments
		shift.left = horizontal === SHIFT && !!adjust.left;
		if(shift.left) {
			shiftonly(X, LEFT, RIGHT);
		}
		shift.top = vertical === SHIFT && !!adjust.top;
		if(shift.top) {
			shiftonly(Y, TOP, BOTTOM);
		}

		/*
		* If the tip is adjusted in both dimensions, or in a
		* direction that would cause it to be anywhere but the
		* outer border, hide it!
		*/
		this.element.css(css).toggle(
			!(shift.x && shift.y || newCorner.x === CENTER && shift.y || newCorner.y === CENTER && shift.x)
		);

		// Adjust position to accomodate tip dimensions
		pos.left -= offset.left.charAt ? offset.user :
			horizontal !== SHIFT || shift.top || !shift.left && !shift.top ? offset.left + this.border : 0;
		pos.top -= offset.top.charAt ? offset.user :
			vertical !== SHIFT || shift.left || !shift.left && !shift.top ? offset.top + this.border : 0;

		// Cache details
		cache.cornerLeft = adjust.left; cache.cornerTop = adjust.top;
		cache.corner = newCorner.clone();
	},

	destroy: function() {
		// Unbind events
		this.qtip._unbind(this.qtip.tooltip, this._ns);

		// Remove the tip element(s)
		if(this.qtip.elements.tip) {
			this.qtip.elements.tip.find('*')
				.remove().end().remove();
		}
	}
});

TIP = PLUGINS.tip = function(api) {
	return new Tip(api, api.options.style.tip);
};

// Initialize tip on render
TIP.initialize = 'render';

// Setup plugin sanitization options
TIP.sanitize = function(options) {
	if(options.style && 'tip' in options.style) {
		var opts = options.style.tip;
		if(typeof opts !== 'object') { opts = options.style.tip = { corner: opts }; }
		if(!(/string|boolean/i).test(typeof opts.corner)) { opts.corner = TRUE; }
	}
};

// Add new option checks for the plugin
CHECKS.tip = {
	'^position.my|style.tip.(corner|mimic|border)$': function() {
		// Make sure a tip can be drawn
		this.create();

		// Reposition the tooltip
		this.qtip.reposition();
	},
	'^style.tip.(height|width)$': function(obj) {
		// Re-set dimensions and redraw the tip
		this.size = [ obj.width, obj.height ];
		this.update();

		// Reposition the tooltip
		this.qtip.reposition();
	},
	'^content.title|style.(classes|widget)$': function() {
		this.update();
	}
};

// Extend original qTip defaults
$.extend(TRUE, QTIP.defaults, {
	style: {
		tip: {
			corner: TRUE,
			mimic: FALSE,
			width: 6,
			height: 6,
			border: TRUE,
			offset: 0
		}
	}
});
;var MODAL, OVERLAY,
	MODALCLASS = 'qtip-modal',
	MODALSELECTOR = '.'+MODALCLASS;

OVERLAY = function()
{
	var self = this,
		focusableElems = {},
		current,
		prevState,
		elem;

	// Modified code from jQuery UI 1.10.0 source
	// http://code.jquery.com/ui/1.10.0/jquery-ui.js
	function focusable(element) {
		// Use the defined focusable checker when possible
		if($.expr[':'].focusable) { return $.expr[':'].focusable; }

		var isTabIndexNotNaN = !isNaN($.attr(element, 'tabindex')),
			nodeName = element.nodeName && element.nodeName.toLowerCase(),
			map, mapName, img;

		if('area' === nodeName) {
			map = element.parentNode;
			mapName = map.name;
			if(!element.href || !mapName || map.nodeName.toLowerCase() !== 'map') {
				return false;
			}
			img = $('img[usemap=#' + mapName + ']')[0];
			return !!img && img.is(':visible');
		}

		return /input|select|textarea|button|object/.test( nodeName ) ?
			!element.disabled :
			'a' === nodeName ?
				element.href || isTabIndexNotNaN :
				isTabIndexNotNaN
		;
	}

	// Focus inputs using cached focusable elements (see update())
	function focusInputs(blurElems) {
		// Blurring body element in IE causes window.open windows to unfocus!
		if(focusableElems.length < 1 && blurElems.length) { blurElems.not('body').blur(); }

		// Focus the inputs
		else { focusableElems.first().focus(); }
	}

	// Steal focus from elements outside tooltip
	function stealFocus(event) {
		if(!elem.is(':visible')) { return; }

		var target = $(event.target),
			tooltip = current.tooltip,
			container = target.closest(SELECTOR),
			targetOnTop;

		// Determine if input container target is above this
		targetOnTop = container.length < 1 ? FALSE :
			parseInt(container[0].style.zIndex, 10) > parseInt(tooltip[0].style.zIndex, 10);

		// If we're showing a modal, but focus has landed on an input below
		// this modal, divert focus to the first visible input in this modal
		// or if we can't find one... the tooltip itself
		if(!targetOnTop && target.closest(SELECTOR)[0] !== tooltip[0]) {
			focusInputs(target);
		}
	}

	$.extend(self, {
		init: function() {
			// Create document overlay
			elem = self.elem = $('<div />', {
				id: 'qtip-overlay',
				html: '<div></div>',
				mousedown: function() { return FALSE; }
			})
			.hide();

			// Make sure we can't focus anything outside the tooltip
			$(document.body).bind('focusin'+MODALSELECTOR, stealFocus);

			// Apply keyboard "Escape key" close handler
			$(document).bind('keydown'+MODALSELECTOR, function(event) {
				if(current && current.options.show.modal.escape && event.keyCode === 27) {
					current.hide(event);
				}
			});

			// Apply click handler for blur option
			elem.bind('click'+MODALSELECTOR, function(event) {
				if(current && current.options.show.modal.blur) {
					current.hide(event);
				}
			});

			return self;
		},

		update: function(api) {
			// Update current API reference
			current = api;

			// Update focusable elements if enabled
			if(api.options.show.modal.stealfocus !== FALSE) {
				focusableElems = api.tooltip.find('*').filter(function() {
					return focusable(this);
				});
			}
			else { focusableElems = []; }
		},

		toggle: function(api, state, duration) {
			var tooltip = api.tooltip,
				options = api.options.show.modal,
				effect = options.effect,
				type = state ? 'show': 'hide',
				visible = elem.is(':visible'),
				visibleModals = $(MODALSELECTOR).filter(':visible:not(:animated)').not(tooltip);

			// Set active tooltip API reference
			self.update(api);

			// If the modal can steal the focus...
			// Blur the current item and focus anything in the modal we an
			if(state && options.stealfocus !== FALSE) {
				focusInputs( $(':focus') );
			}

			// Toggle backdrop cursor style on show
			elem.toggleClass('blurs', options.blur);

			// Append to body on show
			if(state) {
				elem.appendTo(document.body);
			}

			// Prevent modal from conflicting with show.solo, and don't hide backdrop is other modals are visible
			if(elem.is(':animated') && visible === state && prevState !== FALSE || !state && visibleModals.length) {
				return self;
			}

			// Stop all animations
			elem.stop(TRUE, FALSE);

			// Use custom function if provided
			if($.isFunction(effect)) {
				effect.call(elem, state);
			}

			// If no effect type is supplied, use a simple toggle
			else if(effect === FALSE) {
				elem[ type ]();
			}

			// Use basic fade function
			else {
				elem.fadeTo( parseInt(duration, 10) || 90, state ? 1 : 0, function() {
					if(!state) { elem.hide(); }
				});
			}

			// Reset position and detach from body on hide
			if(!state) {
				elem.queue(function(next) {
					elem.css({ left: '', top: '' });
					if(!$(MODALSELECTOR).length) { elem.detach(); }
					next();
				});
			}

			// Cache the state
			prevState = state;

			// If the tooltip is destroyed, set reference to null
			if(current.destroyed) { current = NULL; }

			return self;
		}
	});

	self.init();
};
OVERLAY = new OVERLAY();

function Modal(api, options) {
	this.options = options;
	this._ns = '-modal';

	this.qtip = api;
	this.init(api);
}

$.extend(Modal.prototype, {
	init: function(qtip) {
		var tooltip = qtip.tooltip;

		// If modal is disabled... return
		if(!this.options.on) { return this; }

		// Set overlay reference
		qtip.elements.overlay = OVERLAY.elem;

		// Add unique attribute so we can grab modal tooltips easily via a SELECTOR, and set z-index
		tooltip.addClass(MODALCLASS).css('z-index', QTIP.modal_zindex + $(MODALSELECTOR).length);

		// Apply our show/hide/focus modal events
		qtip._bind(tooltip, ['tooltipshow', 'tooltiphide'], function(event, api, duration) {
			var oEvent = event.originalEvent;

			// Make sure mouseout doesn't trigger a hide when showing the modal and mousing onto backdrop
			if(event.target === tooltip[0]) {
				if(oEvent && event.type === 'tooltiphide' && /mouse(leave|enter)/.test(oEvent.type) && $(oEvent.relatedTarget).closest(OVERLAY.elem[0]).length) {
					/* eslint-disable no-empty */
					try { event.preventDefault(); }
					catch(e) {}
					/* eslint-enable no-empty */
				}
				else if(!oEvent || oEvent && oEvent.type !== 'tooltipsolo') {
					this.toggle(event, event.type === 'tooltipshow', duration);
				}
			}
		}, this._ns, this);

		// Adjust modal z-index on tooltip focus
		qtip._bind(tooltip, 'tooltipfocus', function(event, api) {
			// If focus was cancelled before it reached us, don't do anything
			if(event.isDefaultPrevented() || event.target !== tooltip[0]) { return; }

			var qtips = $(MODALSELECTOR),

			// Keep the modal's lower than other, regular qtips
			newIndex = QTIP.modal_zindex + qtips.length,
			curIndex = parseInt(tooltip[0].style.zIndex, 10);

			// Set overlay z-index
			OVERLAY.elem[0].style.zIndex = newIndex - 1;

			// Reduce modal z-index's and keep them properly ordered
			qtips.each(function() {
				if(this.style.zIndex > curIndex) {
					this.style.zIndex -= 1;
				}
			});

			// Fire blur event for focused tooltip
			qtips.filter('.' + CLASS_FOCUS).qtip('blur', event.originalEvent);

			// Set the new z-index
			tooltip.addClass(CLASS_FOCUS)[0].style.zIndex = newIndex;

			// Set current
			OVERLAY.update(api);

			// Prevent default handling
			/* eslint-disable no-empty */
			try { event.preventDefault(); }
			catch(e) {}
			/* eslint-enable no-empty */
		}, this._ns, this);

		// Focus any other visible modals when this one hides
		qtip._bind(tooltip, 'tooltiphide', function(event) {
			if(event.target === tooltip[0]) {
				$(MODALSELECTOR).filter(':visible').not(tooltip).last().qtip('focus', event);
			}
		}, this._ns, this);
	},

	toggle: function(event, state, duration) {
		// Make sure default event hasn't been prevented
		if(event && event.isDefaultPrevented()) { return this; }

		// Toggle it
		OVERLAY.toggle(this.qtip, !!state, duration);
	},

	destroy: function() {
		// Remove modal class
		this.qtip.tooltip.removeClass(MODALCLASS);

		// Remove bound events
		this.qtip._unbind(this.qtip.tooltip, this._ns);

		// Delete element reference
		OVERLAY.toggle(this.qtip, FALSE);
		delete this.qtip.elements.overlay;
	}
});


MODAL = PLUGINS.modal = function(api) {
	return new Modal(api, api.options.show.modal);
};

// Setup sanitiztion rules
MODAL.sanitize = function(opts) {
	if(opts.show) {
		if(typeof opts.show.modal !== 'object') { opts.show.modal = { on: !!opts.show.modal }; }
		else if(typeof opts.show.modal.on === 'undefined') { opts.show.modal.on = TRUE; }
	}
};

// Base z-index for all modal tooltips (use qTip core z-index as a base)
/* eslint-disable camelcase */
QTIP.modal_zindex = QTIP.zindex - 200;
/* eslint-enable camelcase */

// Plugin needs to be initialized on render
MODAL.initialize = 'render';

// Setup option set checks
CHECKS.modal = {
	'^show.modal.(on|blur)$': function() {
		// Initialise
		this.destroy();
		this.init();

		// Show the modal if not visible already and tooltip is visible
		this.qtip.elems.overlay.toggle(
			this.qtip.tooltip[0].offsetWidth > 0
		);
	}
};

// Extend original api defaults
$.extend(TRUE, QTIP.defaults, {
	show: {
		modal: {
			on: FALSE,
			effect: TRUE,
			blur: TRUE,
			stealfocus: TRUE,
			escape: TRUE
		}
	}
});
;PLUGINS.viewport = function(api, position, posOptions, targetWidth, targetHeight, elemWidth, elemHeight)
{
	var target = posOptions.target,
		tooltip = api.elements.tooltip,
		my = posOptions.my,
		at = posOptions.at,
		adjust = posOptions.adjust,
		method = adjust.method.split(' '),
		methodX = method[0],
		methodY = method[1] || method[0],
		viewport = posOptions.viewport,
		container = posOptions.container,
		adjusted = { left: 0, top: 0 },
		fixed, newMy, containerOffset, containerStatic,
		viewportWidth, viewportHeight, viewportScroll, viewportOffset;

	// If viewport is not a jQuery element, or it's the window/document, or no adjustment method is used... return
	if(!viewport.jquery || target[0] === window || target[0] === document.body || adjust.method === 'none') {
		return adjusted;
	}

	// Cach container details
	containerOffset = container.offset() || adjusted;
	containerStatic = container.css('position') === 'static';

	// Cache our viewport details
	fixed = tooltip.css('position') === 'fixed';
	viewportWidth = viewport[0] === window ? viewport.width() : viewport.outerWidth(FALSE);
	viewportHeight = viewport[0] === window ? viewport.height() : viewport.outerHeight(FALSE);
	viewportScroll = { left: fixed ? 0 : viewport.scrollLeft(), top: fixed ? 0 : viewport.scrollTop() };
	viewportOffset = viewport.offset() || adjusted;

	// Generic calculation method
	function calculate(side, otherSide, type, adjustment, side1, side2, lengthName, targetLength, elemLength) {
		var initialPos = position[side1],
			mySide = my[side],
			atSide = at[side],
			isShift = type === SHIFT,
			myLength = mySide === side1 ? elemLength : mySide === side2 ? -elemLength : -elemLength / 2,
			atLength = atSide === side1 ? targetLength : atSide === side2 ? -targetLength : -targetLength / 2,
			sideOffset = viewportScroll[side1] + viewportOffset[side1] - (containerStatic ? 0 : containerOffset[side1]),
			overflow1 = sideOffset - initialPos,
			overflow2 = initialPos + elemLength - (lengthName === WIDTH ? viewportWidth : viewportHeight) - sideOffset,
			offset = myLength - (my.precedance === side || mySide === my[otherSide] ? atLength : 0) - (atSide === CENTER ? targetLength / 2 : 0);

		// shift
		if(isShift) {
			offset = (mySide === side1 ? 1 : -1) * myLength;

			// Adjust position but keep it within viewport dimensions
			position[side1] += overflow1 > 0 ? overflow1 : overflow2 > 0 ? -overflow2 : 0;
			position[side1] = Math.max(
				-containerOffset[side1] + viewportOffset[side1],
				initialPos - offset,
				Math.min(
					Math.max(
						-containerOffset[side1] + viewportOffset[side1] + (lengthName === WIDTH ? viewportWidth : viewportHeight),
						initialPos + offset
					),
					position[side1],

					// Make sure we don't adjust complete off the element when using 'center'
					mySide === 'center' ? initialPos - myLength : 1E9
				)
			);

		}

		// flip/flipinvert
		else {
			// Update adjustment amount depending on if using flipinvert or flip
			adjustment *= type === FLIPINVERT ? 2 : 0;

			// Check for overflow on the left/top
			if(overflow1 > 0 && (mySide !== side1 || overflow2 > 0)) {
				position[side1] -= offset + adjustment;
				newMy.invert(side, side1);
			}

			// Check for overflow on the bottom/right
			else if(overflow2 > 0 && (mySide !== side2 || overflow1 > 0)  ) {
				position[side1] -= (mySide === CENTER ? -offset : offset) + adjustment;
				newMy.invert(side, side2);
			}

			// Make sure we haven't made things worse with the adjustment and reset if so
			if(position[side1] < viewportScroll[side1] && -position[side1] > overflow2) {
				position[side1] = initialPos; newMy = my.clone();
			}
		}

		return position[side1] - initialPos;
	}

	// Set newMy if using flip or flipinvert methods
	if(methodX !== 'shift' || methodY !== 'shift') { newMy = my.clone(); }

	// Adjust position based onviewport and adjustment options
	adjusted = {
		left: methodX !== 'none' ? calculate( X, Y, methodX, adjust.x, LEFT, RIGHT, WIDTH, targetWidth, elemWidth ) : 0,
		top: methodY !== 'none' ? calculate( Y, X, methodY, adjust.y, TOP, BOTTOM, HEIGHT, targetHeight, elemHeight ) : 0,
		my: newMy
	};

	return adjusted;
};
;PLUGINS.polys = {
	// POLY area coordinate calculator
	//	Special thanks to Ed Cradock for helping out with this.
	//	Uses a binary search algorithm to find suitable coordinates.
	polygon: function(baseCoords, corner) {
		var result = {
			width: 0, height: 0,
			position: {
				top: 1e10, right: 0,
				bottom: 0, left: 1e10
			},
			adjustable: FALSE
		},
		i = 0, next,
		coords = [],
		compareX = 1, compareY = 1,
		realX = 0, realY = 0,
		newWidth, newHeight;

		// First pass, sanitize coords and determine outer edges
		i = baseCoords.length; 
		while(i--) {
			next = [ parseInt(baseCoords[--i], 10), parseInt(baseCoords[i+1], 10) ];

			if(next[0] > result.position.right){ result.position.right = next[0]; }
			if(next[0] < result.position.left){ result.position.left = next[0]; }
			if(next[1] > result.position.bottom){ result.position.bottom = next[1]; }
			if(next[1] < result.position.top){ result.position.top = next[1]; }

			coords.push(next);
		}

		// Calculate height and width from outer edges
		newWidth = result.width = Math.abs(result.position.right - result.position.left);
		newHeight = result.height = Math.abs(result.position.bottom - result.position.top);

		// If it's the center corner...
		if(corner.abbrev() === 'c') {
			result.position = {
				left: result.position.left + result.width / 2,
				top: result.position.top + result.height / 2
			};
		}
		else {
			// Second pass, use a binary search algorithm to locate most suitable coordinate
			while(newWidth > 0 && newHeight > 0 && compareX > 0 && compareY > 0)
			{
				newWidth = Math.floor(newWidth / 2);
				newHeight = Math.floor(newHeight / 2);

				if(corner.x === LEFT){ compareX = newWidth; }
				else if(corner.x === RIGHT){ compareX = result.width - newWidth; }
				else{ compareX += Math.floor(newWidth / 2); }

				if(corner.y === TOP){ compareY = newHeight; }
				else if(corner.y === BOTTOM){ compareY = result.height - newHeight; }
				else{ compareY += Math.floor(newHeight / 2); }

				i = coords.length;
				while(i--)
				{
					if(coords.length < 2){ break; }

					realX = coords[i][0] - result.position.left;
					realY = coords[i][1] - result.position.top;

					if(
						corner.x === LEFT && realX >= compareX ||
						corner.x === RIGHT && realX <= compareX ||
						corner.x === CENTER && (realX < compareX || realX > result.width - compareX) ||
						corner.y === TOP && realY >= compareY ||
						corner.y === BOTTOM && realY <= compareY ||
						corner.y === CENTER && (realY < compareY || realY > result.height - compareY)) {
						coords.splice(i, 1);
					}
				}
			}
			result.position = { left: coords[0][0], top: coords[0][1] };
		}

		return result;
	},

	rect: function(ax, ay, bx, by) {
		return {
			width: Math.abs(bx - ax),
			height: Math.abs(by - ay),
			position: {
				left: Math.min(ax, bx),
				top: Math.min(ay, by)
			}
		};
	},

	_angles: {
		tc: 3 / 2, tr: 7 / 4, tl: 5 / 4,
		bc: 1 / 2, br: 1 / 4, bl: 3 / 4,
		rc: 2, lc: 1, c: 0
	},
	ellipse: function(cx, cy, rx, ry, corner) {
		var c = PLUGINS.polys._angles[ corner.abbrev() ],
			rxc = c === 0 ? 0 : rx * Math.cos( c * Math.PI ),
			rys = ry * Math.sin( c * Math.PI );

		return {
			width: rx * 2 - Math.abs(rxc),
			height: ry * 2 - Math.abs(rys),
			position: {
				left: cx + rxc,
				top: cy + rys
			},
			adjustable: FALSE
		};
	},
	circle: function(cx, cy, r, corner) {
		return PLUGINS.polys.ellipse(cx, cy, r, r, corner);
	}
};
;PLUGINS.svg = function(api, svg, corner)
{
	var elem = svg[0],
		root = $(elem.ownerSVGElement),
		ownerDocument = elem.ownerDocument,
		strokeWidth2 = (parseInt(svg.css('stroke-width'), 10) || 0) / 2,
		frameOffset, mtx, transformed,
		len, next, i, points,
		result, position;

	// Ascend the parentNode chain until we find an element with getBBox()
	while(!elem.getBBox) { elem = elem.parentNode; }
	if(!elem.getBBox || !elem.parentNode) { return FALSE; }

	// Determine which shape calculation to use
	switch(elem.nodeName) {
		case 'ellipse':
		case 'circle':
			result = PLUGINS.polys.ellipse(
				elem.cx.baseVal.value,
				elem.cy.baseVal.value,
				(elem.rx || elem.r).baseVal.value + strokeWidth2,
				(elem.ry || elem.r).baseVal.value + strokeWidth2,
				corner
			);
		break;

		case 'line':
		case 'polygon':
		case 'polyline':
			// Determine points object (line has none, so mimic using array)
			points = elem.points || [
				{ x: elem.x1.baseVal.value, y: elem.y1.baseVal.value },
				{ x: elem.x2.baseVal.value, y: elem.y2.baseVal.value }
			];

			for(result = [], i = -1, len = points.numberOfItems || points.length; ++i < len;) {
				next = points.getItem ? points.getItem(i) : points[i];
				result.push.apply(result, [next.x, next.y]);
			}

			result = PLUGINS.polys.polygon(result, corner);
		break;

		// Unknown shape or rectangle? Use bounding box
		default:
			result = elem.getBBox();
			result = {
				width: result.width,
				height: result.height,
				position: {
					left: result.x,
					top: result.y
				}
			};
		break;
	}

	// Shortcut assignments
	position = result.position;
	root = root[0];

	// Convert position into a pixel value
	if(root.createSVGPoint) {
		mtx = elem.getScreenCTM();
		points = root.createSVGPoint();

		points.x = position.left;
		points.y = position.top;
		transformed = points.matrixTransform( mtx );
		position.left = transformed.x;
		position.top = transformed.y;
	}

	// Check the element is not in a child document, and if so, adjust for frame elements offset
	if(ownerDocument !== document && api.position.target !== 'mouse') {
		frameOffset = $((ownerDocument.defaultView || ownerDocument.parentWindow).frameElement).offset();
		if(frameOffset) {
			position.left += frameOffset.left;
			position.top += frameOffset.top;
		}
	}

	// Adjust by scroll offset of owner document
	ownerDocument = $(ownerDocument);
	position.left += ownerDocument.scrollLeft();
	position.top += ownerDocument.scrollTop();

	return result;
};
;PLUGINS.imagemap = function(api, area, corner)
{
	if(!area.jquery) { area = $(area); }

	var shape = (area.attr('shape') || 'rect').toLowerCase().replace('poly', 'polygon'),
		image = $('img[usemap="#'+area.parent('map').attr('name')+'"]'),
		coordsString = $.trim(area.attr('coords')),
		coordsArray = coordsString.replace(/,$/, '').split(','),
		imageOffset, coords, i, result, len;

	// If we can't find the image using the map...
	if(!image.length) { return FALSE; }

	// Pass coordinates string if polygon
	if(shape === 'polygon') {
		result = PLUGINS.polys.polygon(coordsArray, corner);
	}

	// Otherwise parse the coordinates and pass them as arguments
	else if(PLUGINS.polys[shape]) {
		for(i = -1, len = coordsArray.length, coords = []; ++i < len;) {
			coords.push( parseInt(coordsArray[i], 10) );
		}

		result = PLUGINS.polys[shape].apply(
			this, coords.concat(corner)
		);
	}

	// If no shapre calculation method was found, return false
	else { return FALSE; }

	// Make sure we account for padding and borders on the image
	imageOffset = image.offset();
	imageOffset.left += Math.ceil((image.outerWidth(FALSE) - image.width()) / 2);
	imageOffset.top += Math.ceil((image.outerHeight(FALSE) - image.height()) / 2);

	// Add image position to offset coordinates
	result.position.left += imageOffset.left;
	result.position.top += imageOffset.top;

	return result;
};
;var IE6,

/*
 * BGIFrame adaption (http://plugins.jquery.com/project/bgiframe)
 * Special thanks to Brandon Aaron
 */
BGIFRAME = '<iframe class="qtip-bgiframe" frameborder="0" tabindex="-1" src="javascript:\'\';" ' +
	' style="display:block; position:absolute; z-index:-1; filter:alpha(opacity=0); ' +
		'-ms-filter:"progid:DXImageTransform.Microsoft.Alpha(Opacity=0)";"></iframe>';

function Ie6(api) {
	this._ns = 'ie6';

	this.qtip = api;
	this.init(api);
}

$.extend(Ie6.prototype, {
	_scroll : function() {
		var overlay = this.qtip.elements.overlay;
		overlay && (overlay[0].style.top = $(window).scrollTop() + 'px');
	},

	init: function(qtip) {
		var tooltip = qtip.tooltip;

		// Create the BGIFrame element if needed
		if($('select, object').length < 1) {
			this.bgiframe = qtip.elements.bgiframe = $(BGIFRAME).appendTo(tooltip);

			// Update BGIFrame on tooltip move
			qtip._bind(tooltip, 'tooltipmove', this.adjustBGIFrame, this._ns, this);
		}

		// redraw() container for width/height calculations
		this.redrawContainer = $('<div/>', { id: NAMESPACE+'-rcontainer' })
			.appendTo(document.body);

		// Fixup modal plugin if present too
		if( qtip.elements.overlay && qtip.elements.overlay.addClass('qtipmodal-ie6fix') ) {
			qtip._bind(window, ['scroll', 'resize'], this._scroll, this._ns, this);
			qtip._bind(tooltip, ['tooltipshow'], this._scroll, this._ns, this);
		}

		// Set dimensions
		this.redraw();
	},

	adjustBGIFrame: function() {
		var tooltip = this.qtip.tooltip,
			dimensions = {
				height: tooltip.outerHeight(FALSE),
				width: tooltip.outerWidth(FALSE)
			},
			plugin = this.qtip.plugins.tip,
			tip = this.qtip.elements.tip,
			tipAdjust, offset;

		// Adjust border offset
		offset = parseInt(tooltip.css('borderLeftWidth'), 10) || 0;
		offset = { left: -offset, top: -offset };

		// Adjust for tips plugin
		if(plugin && tip) {
			tipAdjust = plugin.corner.precedance === 'x' ? [WIDTH, LEFT] : [HEIGHT, TOP];
			offset[ tipAdjust[1] ] -= tip[ tipAdjust[0] ]();
		}

		// Update bgiframe
		this.bgiframe.css(offset).css(dimensions);
	},

	// Max/min width simulator function
	redraw: function() {
		if(this.qtip.rendered < 1 || this.drawing) { return this; }

		var tooltip = this.qtip.tooltip,
			style = this.qtip.options.style,
			container = this.qtip.options.position.container,
			perc, width, max, min;

		// Set drawing flag
		this.qtip.drawing = 1;

		// If tooltip has a set height/width, just set it... like a boss!
		if(style.height) { tooltip.css(HEIGHT, style.height); }
		if(style.width) { tooltip.css(WIDTH, style.width); }

		// Simulate max/min width if not set width present...
		else {
			// Reset width and add fluid class
			tooltip.css(WIDTH, '').appendTo(this.redrawContainer);

			// Grab our tooltip width (add 1 if odd so we don't get wrapping problems.. huzzah!)
			width = tooltip.width();
			if(width % 2 < 1) { width += 1; }

			// Grab our max/min properties
			max = tooltip.css('maxWidth') || '';
			min = tooltip.css('minWidth') || '';

			// Parse into proper pixel values
			perc = (max + min).indexOf('%') > -1 ? container.width() / 100 : 0;
			max = (max.indexOf('%') > -1 ? perc : 1 * parseInt(max, 10)) || width;
			min = (min.indexOf('%') > -1 ? perc : 1 * parseInt(min, 10)) || 0;

			// Determine new dimension size based on max/min/current values
			width = max + min ? Math.min(Math.max(width, min), max) : width;

			// Set the newly calculated width and remvoe fluid class
			tooltip.css(WIDTH, Math.round(width)).appendTo(container);
		}

		// Set drawing flag
		this.drawing = 0;

		return this;
	},

	destroy: function() {
		// Remove iframe
		this.bgiframe && this.bgiframe.remove();

		// Remove bound events
		this.qtip._unbind([window, this.qtip.tooltip], this._ns);
	}
});

IE6 = PLUGINS.ie6 = function(api) {
	// Proceed only if the browser is IE6
	return BROWSER.ie === 6 ? new Ie6(api) : FALSE;
};

IE6.initialize = 'render';

CHECKS.ie6 = {
	'^content|style$': function() {
		this.redraw();
	}
};
;}));
}( window, document ));


/***/ }),
/* 272 */
/***/ (function(module, exports) {

module.exports = function(module) {
	if(!module.webpackPolyfill) {
		module.deprecate = function() {};
		module.paths = [];
		// module.parent = undefined by default
		if(!module.children) module.children = [];
		Object.defineProperty(module, "loaded", {
			enumerable: true,
			get: function() {
				return module.l;
			}
		});
		Object.defineProperty(module, "id", {
			enumerable: true,
			get: function() {
				return module.i;
			}
		});
		module.webpackPolyfill = 1;
	}
	return module;
};


/***/ })
/******/ ]);
});
//# sourceMappingURL=rup.js.map