@@ -0,0 +1,304 @@
/**
* Polyfill of DOMTokenList for IE < 9
* Monkey patch of .add, .remove for IE 10 / 11, Firefox < 26 to support multiple arguments
* Monkey patch of .toggle for IE 10 / 11, Firefox < 24 to support second argument
*/
/*global define: false, module: false */
/*jslint nomen: true */
( function domTokenListModule ( global , definition ) { // non-exporting module magic dance
'use strict' ;
var
amd = 'amd' ,
exports = 'exports' ; // keeps the method names for CommonJS / AMD from being compiled to single character variable
if ( typeof define === 'function' && define [ amd ] ) {
define ( function definer ( ) {
return definition ( global ) ;
} ) ;
} else if ( typeof module === 'function' && module [ exports ] ) {
module [ exports ] = definition ( global ) ;
} else {
definition ( global ) ;
}
} ( this , function domTokenListPolyfill ( global ) {
'use strict' ;
if ( ! global . Element ) {
return ;
}
var
document = global . document ,
id = 0 ,
lists = { } ,
test = document . createElement ( '_' ) ;
/**
* @private
*/
function createMethod ( method ) {
var
original = this . prototype [ method ] ;
this . prototype [ method ] = function override ( ) {
var
counter ,
length ,
token ;
for ( counter = 0 , length = arguments . length ; counter < length ; counter += 1 ) {
token = arguments [ counter ] ;
original . call ( this , token ) ;
}
} ;
}
/**
* @private
* @param {string } token Token to search for
*/
function indexOf ( token ) {
var
arrayPrototype = Array . prototype ,
counter ;
if ( ! ! arrayPrototype . indexOf ) {
return arrayPrototype . indexOf . call ( this , token ) ;
}
counter = this . length - 1 ;
while ( counter > - 1 ) {
if ( this [ counter ] === token ) {
return counter ;
}
counter -= 1 ;
}
return - 1 ;
}
/**
* @private
*/
function newId ( ) {
id += 1 ;
return id ;
}
/**
* @private
*/
function onchange ( ) {
var
classes = this . classes ,
classesString = classes . join ( ' ' ) ;
if ( this . isSVG ) {
this . setAttribute ( 'class' , classesString ) ;
} else {
this . element . className = classesString ;
}
this . list . length = classes . length ;
}
/**
* @param {string } token Token to find
*/
function contains ( token ) {
return indexOf . call ( lists [ this . id ] . classes , token ) !== - 1 ;
}
function add ( ) {
var
counter = 0 ,
item = lists [ this . id ] ,
classes = item . classes ,
length = arguments . length ,
token ,
updated = false ;
while ( counter < length ) {
token = arguments [ counter ] ;
if ( indexOf . call ( classes , token ) === - 1 ) {
classes . push ( token ) ;
updated = true ;
}
counter += 1 ;
}
if ( updated ) {
onchange . call ( item ) ;
}
}
/**
* @param {number } index Index of list to return value
*/
function item ( index ) {
return lists [ this . id ] . classes [ index ] || null ;
}
function remove ( ) {
var
counter = arguments . length - 1 ,
entry = lists [ this . id ] ,
classes = entry . classes ,
index ,
token ,
updated = false ;
while ( counter > - 1 ) {
token = arguments [ counter ] ;
index = indexOf . call ( classes , token ) ;
if ( index !== - 1 ) {
classes . splice ( index , 1 ) ;
updated = true ;
}
counter -= 1 ;
}
if ( updated ) {
onchange . call ( entry ) ;
}
}
function toString ( ) {
var
entry = lists [ this . id ] ;
onchange . call ( entry ) ;
return entry . element . className ;
}
/**
* @param {string } token Token to toggle
* @param {force= } force Flag to force toggle
*/
function toggle ( token , force ) {
var
hasToken = indexOf . call ( lists [ this . id ] . classes , token ) !== - 1 ,
method ;
if ( hasToken ) {
if ( force !== true ) {
method = 'remove' ;
}
} else {
if ( force !== false ) {
method = 'add' ;
}
}
if ( method ) {
this [ method ] ( token ) ;
}
return ( force === true || force === false ) ? force : ! hasToken ;
}
/**
* @constructor
*/
function DOMTokenList ( element ) {
var
className ,
listId ,
isSVG ;
listId = element . domTokenListId ;
if ( listId && ( listId in lists ) ) {
return lists [ listId ] . list ;
}
isSVG = typeof element . className === 'object' ;
className = element . className ;
className = String ( isSVG ? className . baseVal : className ) . replace ( / ^ \s + | \s + $ / , '' ) ;
listId = newId ( ) ;
lists [ listId ] = {
classes : className . length !== 0 ? className . split ( / \s + / ) : [ ] ,
element : element ,
list : this ,
isSVG : isSVG
} ;
this . id = listId ;
this . length = lists [ listId ] . classes . length ;
element . domTokenListId = listId ; // apply id lookup reference to element
}
if ( ! ( 'classList' in test ) ) {
( function ( ) {
var
counter ,
elementPrototype = global . Element . prototype ,
methodList = [ add , contains , item , remove , toString , toggle ] ,
methods = [ 'add' , 'contains' , 'item' , 'remove' , 'toString' , 'toggle' ] ,
propertyDescriptor ,
prototype = DOMTokenList . prototype ;
function get ( ) {
var
thisId = this . domTokenListId ;
return thisId && ( thisId in lists ) ? lists [ thisId ] . list : new DOMTokenList ( this ) ;
}
counter = methods . length - 1 ;
while ( counter > - 1 ) {
prototype [ methods [ counter ] ] = methodList [ counter ] ;
counter -= 1 ;
}
propertyDescriptor = {
get : get ,
configurable : true ,
enumerable : true
} ;
if ( Object . defineProperty ) {
try {
Object . defineProperty ( elementPrototype , 'classList' , propertyDescriptor ) ;
} catch ( ex ) {
if ( ex . number === - 0x7FF5EC54 ) { // IE 8 doesn't like it to be enumerable
propertyDescriptor . enumerable = false ;
Object . defineProperty ( elementPrototype , 'classList' , propertyDescriptor ) ;
}
}
} else if ( Object . prototype . __defineGetter__ ) {
elementPrototype . __defineGetter__ ( 'classList' , propertyDescriptor ) ;
}
global . DOMTokenList = DOMTokenList ;
} ( ) ) ;
} else {
test . classList . add ( 'c1' , 'c2' ) ;
if ( ! test . classList . contains ( 'c2' ) ) { // IE 10 / 11, Firefox < 26
createMethod . call ( global . DOMTokenList , 'add' ) ;
createMethod . call ( global . DOMTokenList , 'remove' ) ;
}
test . classList . toggle ( 'c3' , false ) ;
if ( test . classList . contains ( 'c3' ) ) { // IE 10 / 11, Firefox < 24
global . DOMTokenList . prototype . toggle = ( function ( ) {
var
original = global . DOMTokenList . prototype . toggle ;
return function toggle ( token , force ) {
var
notForce = ! force ;
return ( arguments . length > 1 && ! ( this . contains ( token ) === notForce ) ) ? force : original . call ( this , token ) ;
} ;
} ( ) ) ;
}
test = null ;
}
} ) ) ;