{"version":3,"sources":["material.js","mdlComponentHandler.js","rAF.js","button.js","checkbox.js","menu.patched.js","progress.js","textfield.patched.js","layout.js","ripple.js"],"names":["componentHandler","upgradeDom","optJsClass","optCssClass","upgradeElement","element","upgradeElements","elements","upgradeAllRegistered","registerUpgradedCallback","jsClass","callback","register","config","downgradeElements","nodes","registeredComponents_","createdComponents_","findRegisteredClass_","name","optReplace","i","length","className","getUpgradedListOfElement_","dataUpgraded","getAttribute","split","isElementUpgraded_","indexOf","createEvent_","eventType","bubbles","cancelable","window","CustomEvent","ev","document","createEvent","initEvent","upgradeDomInternal","cssClass","registeredClass","querySelectorAll","n","upgradeElementInternal","Element","Error","upgradingEv","dispatchEvent","defaultPrevented","upgradedList","classesToUpgrade","push","classList","forEach","component","contains","setAttribute","join","instance","classConstructor","j","m","callbacks","widget","upgradedEv","deconstructComponentInternal","componentIndex","splice","upgrades","element_","componentPlace","classAsString","upgradeElementsInternal","Array","isArray","prototype","slice","call","HTMLElement","children","regClass","newConfig","constructor","item","hasOwnProperty","downgradeNode","node","filter","NodeList","Node","ComponentConfigPublic","ComponentConfig","Component","addEventListener","createElement","documentElement","add","Date","now","getTime","vendors","requestAnimationFrame","vp","cancelAnimationFrame","test","navigator","userAgent","lastTime","nextTime","Math","max","setTimeout","clearTimeout","MaterialButton","this","init","Constant_","CssClasses_","RIPPLE_EFFECT","RIPPLE_CONTAINER","RIPPLE","blurHandler_","event","blur","disable","disabled","enable","rippleContainer","rippleElement_","appendChild","boundRippleBlurHandler","bind","boundButtonBlurHandler","MaterialCheckbox","TINY_TIMEOUT","INPUT","BOX_OUTLINE","FOCUS_HELPER","TICK_OUTLINE","RIPPLE_IGNORE_EVENTS","RIPPLE_CENTER","IS_FOCUSED","IS_DISABLED","IS_CHECKED","IS_UPGRADED","onChange_","updateClasses_","onFocus_","onBlur_","remove","onMouseUp_","blur_","checkDisabled","checkToggleState","inputElement_","checked","check","uncheck","querySelector","boxOutline","tickContainer","tickOutline","rippleContainerElement_","boundRippleMouseUp","ripple","boundInputOnChange","boundInputOnFocus","boundInputOnBlur","boundElementMouseUp","MaterialMenu","TRANSITION_DURATION_SECONDS","TRANSITION_DURATION_FRACTION","CLOSE_TIMEOUT","Keycodes_","ENTER","ESCAPE","SPACE","UP_ARROW","DOWN_ARROW","CONTAINER","OUTLINE","ITEM","ITEM_RIPPLE_CONTAINER","IS_VISIBLE","IS_ANIMATING","BOTTOM_LEFT","BOTTOM_RIGHT","TOP_LEFT","TOP_RIGHT","UNALIGNED","dataset","visibleItems_","isNaN","visibleItems","postUrl_","postUrl","itemClickHandler_","itemClickHandler","container","parentElement","insertBefore","removeChild","items","width","getBoundingClientRect","firstItem","containerClone","cloneNode","style","visibility","overflowY","height","offsetHeight","body","scrollbarWidth","offsetWidth","clientWidth","parentNode","overflowX","container_","outline","outline_","forElId","forEl","getElementById","forElement_","handleForClick_","handleForKeyboardEvent_","boundItemKeydown_","handleItemKeyboardEvent_","boundItemClick_","handleItemClick_","tabIndex","evt","rect","forRect","isButtonAbsolutelyPositioned","defaultView","getComputedStyle","position","buttonRight","right","top","offsetTop","left","offsetLeft","bottom","toggle","keyCode","preventDefault","focus","currentIndex","target","e","MouseEvent","click","hide","hasAttribute","stopPropagation","closing_","applyClip_","clip","removeAnimationEndListener_","addAnimationEndListener_","show","containerHeight","transitionDuration","itemDelay","transitionDelay","removeEventListener","removeProperty","MaterialProgress","INDETERMINATE_CLASS","setProgress","p","progressbar_","setBuffer","bufferbar_","auxbar_","el","MaterialTextfield","maxRows","NO_MAX_ROWS","MAX_ROWS_ATTRIBUTE","LABEL","IS_DIRTY","IS_INVALID","HAS_PLACEHOLDER","onKeyDown_","currentRowCount","value","onReset_","checkDirty","isDirty","isRequired","input_","required","checkValidity","checkFocus","Boolean","validity","valid","placeholder","trim","change","label_","parseInt","boundUpdateClassesHandler","boundFocusHandler","boundBlurHandler","boundResetHandler","boundKeyDownHandler","invalid","MaterialLayout","MaterialLayoutTab","tab","tabs","panels","layout","selectTab","href","panel","content_","resetTabState_","resetPanelState_","IS_ACTIVE","tabBar_","JS_RIPPLE_EFFECT","TAB_MANUAL_SWITCH","charAt","MAX_WIDTH","TAB_SCROLL_PIXELS","RESIZE_TIMEOUT","MENU_ICON","CHEVRON_LEFT","CHEVRON_RIGHT","Mode_","STANDARD","SEAMED","WATERFALL","SCROLL","HEADER","DRAWER","CONTENT","DRAWER_BTN","ICON","HEADER_SEAMED","HEADER_WATERFALL","HEADER_SCROLL","FIXED_HEADER","FIXED_DRAWER","OBFUSCATOR","TAB_BAR","TAB_CONTAINER","TAB","TAB_BAR_BUTTON","TAB_BAR_LEFT_BUTTON","TAB_BAR_RIGHT_BUTTON","PANEL","HAS_DRAWER","HAS_TABS","HAS_SCROLLING_HEADER","CASTING_SHADOW","IS_COMPACT","IS_SMALL_SCREEN","IS_DRAWER_OPEN","ON_LARGE_SCREEN","ON_SMALL_SCREEN","matchMedia_","query","matchMedia","contentScrollHandler_","header_","headerVisible","scrollTop","keyboardEventHandler_","drawer_","toggleDrawer","screenSizeHandler_","screenSizeMediaQuery_","matches","obfuscator_","drawerToggleHandler_","type","headerTransitionEndHandler_","headerClickHandler_","tabBar","k","drawerButton","focusedElement","directChildren","childNodes","numChildren","c","child","persisted","mode","drawerButtonIcon","innerHTML","firstChild","obfuscator","addListener","tabContainer","leftButton","leftButtonIcon","textContent","scrollLeft","rightButton","rightButtonIcon","tabUpdateHandler","scrollWidth","windowResizeHandler","resizeTimeoutId_","MaterialRipple","INITIAL_SCALE","INITIAL_SIZE","INITIAL_OPACITY","FINAL_OPACITY","FINAL_SCALE","RIPPLE_EFFECT_IGNORE_EVENTS","downHandler_","boundHeight","boundWidth","rippleSize_","sqrt","ignoringMouseDown_","getFrameCount","setFrameCount","x","y","bound","currentTarget","clientX","clientY","round","undefined","touches","setRippleXY","setRippleStyles","animFrameHandler","upHandler_","detail","recentering","frameCount_","x_","y_","boundDownHandler","boundUpHandler","fC","getRippleElement","newX","newY","start","transformString","scale","offset","webkitTransform","msTransform","transform"],"mappings":"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","file":"material.min.js","sourcesContent":[";(function() {\n\"use strict\";\n\n/**\r\n * @license\r\n * Copyright 2015 Google Inc. All Rights Reserved.\r\n *\r\n * Licensed under the Apache License, Version 2.0 (the \"License\");\r\n * you may not use this file except in compliance with the License.\r\n * You may obtain a copy of the License at\r\n *\r\n * http://www.apache.org/licenses/LICENSE-2.0\r\n *\r\n * Unless required by applicable law or agreed to in writing, software\r\n * distributed under the License is distributed on an \"AS IS\" BASIS,\r\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\r\n * See the License for the specific language governing permissions and\r\n * limitations under the License.\r\n */\r\n/**\r\n * A component handler interface using the revealing module design pattern.\r\n * More details on this design pattern here:\r\n * https://github.com/jasonmayes/mdl-component-design-pattern\r\n *\r\n * @author Jason Mayes.\r\n */\r\n/* exported componentHandler */\r\n\r\n// Pre-defining the componentHandler interface, for closure documentation and\r\n// static verification.\r\nvar componentHandler = {\r\n /**\r\n * Searches existing DOM for elements of our component type and upgrades them\r\n * if they have not already been upgraded.\r\n *\r\n * @param {string=} optJsClass the programatic name of the element class we\r\n * need to create a new instance of.\r\n * @param {string=} optCssClass the name of the CSS class elements of this\r\n * type will have.\r\n */\r\n upgradeDom: function(optJsClass, optCssClass) {},\r\n /**\r\n * Upgrades a specific element rather than all in the DOM.\r\n *\r\n * @param {!Element} element The element we wish to upgrade.\r\n * @param {string=} optJsClass Optional name of the class we want to upgrade\r\n * the element to.\r\n */\r\n upgradeElement: function(element, optJsClass) {},\r\n /**\r\n * Upgrades a specific list of elements rather than all in the DOM.\r\n *\r\n * @param {!Element|!Array|!NodeList|!HTMLCollection} elements\r\n * The elements we wish to upgrade.\r\n */\r\n upgradeElements: function(elements) {},\r\n /**\r\n * Upgrades all registered components found in the current DOM. This is\r\n * automatically called on window load.\r\n */\r\n upgradeAllRegistered: function() {},\r\n /**\r\n * Allows user to be alerted to any upgrades that are performed for a given\r\n * component type\r\n *\r\n * @param {string} jsClass The class name of the MDL component we wish\r\n * to hook into for any upgrades performed.\r\n * @param {function(!HTMLElement)} callback The function to call upon an\r\n * upgrade. This function should expect 1 parameter - the HTMLElement which\r\n * got upgraded.\r\n */\r\n registerUpgradedCallback: function(jsClass, callback) {},\r\n /**\r\n * Registers a class for future use and attempts to upgrade existing DOM.\r\n *\r\n * @param {componentHandler.ComponentConfigPublic} config the registration configuration\r\n */\r\n register: function(config) {},\r\n /**\r\n * Downgrade either a given node, an array of nodes, or a NodeList.\r\n *\r\n * @param {!Node|!Array|!NodeList} nodes\r\n */\r\n downgradeElements: function(nodes) {}\r\n};\r\n\r\ncomponentHandler = (function() {\r\n 'use strict';\r\n\r\n /** @type {!Array} */\r\n var registeredComponents_ = [];\r\n\r\n /** @type {!Array} */\r\n var createdComponents_ = [];\r\n\r\n var componentConfigProperty_ = 'mdlComponentConfigInternal_';\r\n\r\n /**\r\n * Searches registered components for a class we are interested in using.\r\n * Optionally replaces a match with passed object if specified.\r\n *\r\n * @param {string} name The name of a class we want to use.\r\n * @param {componentHandler.ComponentConfig=} optReplace Optional object to replace match with.\r\n * @return {!Object|boolean}\r\n * @private\r\n */\r\n function findRegisteredClass_(name, optReplace) {\r\n for (var i = 0; i < registeredComponents_.length; i++) {\r\n if (registeredComponents_[i].className === name) {\r\n if (typeof optReplace !== 'undefined') {\r\n registeredComponents_[i] = optReplace;\r\n }\r\n return registeredComponents_[i];\r\n }\r\n }\r\n return false;\r\n }\r\n\r\n /**\r\n * Returns an array of the classNames of the upgraded classes on the element.\r\n *\r\n * @param {!Element} element The element to fetch data from.\r\n * @return {!Array}\r\n * @private\r\n */\r\n function getUpgradedListOfElement_(element) {\r\n var dataUpgraded = element.getAttribute('data-upgraded');\r\n // Use `['']` as default value to conform the `,name,name...` style.\r\n return dataUpgraded === null ? [''] : dataUpgraded.split(',');\r\n }\r\n\r\n /**\r\n * Returns true if the given element has already been upgraded for the given\r\n * class.\r\n *\r\n * @param {!Element} element The element we want to check.\r\n * @param {string} jsClass The class to check for.\r\n * @returns {boolean}\r\n * @private\r\n */\r\n function isElementUpgraded_(element, jsClass) {\r\n var upgradedList = getUpgradedListOfElement_(element);\r\n return upgradedList.indexOf(jsClass) !== -1;\r\n }\r\n\r\n /**\r\n * Create an event object.\r\n *\r\n * @param {string} eventType The type name of the event.\r\n * @param {boolean} bubbles Whether the event should bubble up the DOM.\r\n * @param {boolean} cancelable Whether the event can be canceled.\r\n * @returns {!Event}\r\n */\r\n function createEvent_(eventType, bubbles, cancelable) {\r\n if ('CustomEvent' in window && typeof window.CustomEvent === 'function') {\r\n return new CustomEvent(eventType, {\r\n bubbles: bubbles,\r\n cancelable: cancelable\r\n });\r\n } else {\r\n var ev = document.createEvent('Events');\r\n ev.initEvent(eventType, bubbles, cancelable);\r\n return ev;\r\n }\r\n }\r\n\r\n /**\r\n * Searches existing DOM for elements of our component type and upgrades them\r\n * if they have not already been upgraded.\r\n *\r\n * @param {string=} optJsClass the programatic name of the element class we\r\n * need to create a new instance of.\r\n * @param {string=} optCssClass the name of the CSS class elements of this\r\n * type will have.\r\n */\r\n function upgradeDomInternal(optJsClass, optCssClass) {\r\n if (typeof optJsClass === 'undefined' &&\r\n typeof optCssClass === 'undefined') {\r\n for (var i = 0; i < registeredComponents_.length; i++) {\r\n upgradeDomInternal(registeredComponents_[i].className,\r\n registeredComponents_[i].cssClass);\r\n }\r\n } else {\r\n var jsClass = /** @type {string} */ (optJsClass);\r\n if (typeof optCssClass === 'undefined') {\r\n var registeredClass = findRegisteredClass_(jsClass);\r\n if (registeredClass) {\r\n optCssClass = registeredClass.cssClass;\r\n }\r\n }\r\n\r\n var elements = document.querySelectorAll('.' + optCssClass);\r\n for (var n = 0; n < elements.length; n++) {\r\n upgradeElementInternal(elements[n], jsClass);\r\n }\r\n }\r\n }\r\n\r\n /**\r\n * Upgrades a specific element rather than all in the DOM.\r\n *\r\n * @param {!Element} element The element we wish to upgrade.\r\n * @param {string=} optJsClass Optional name of the class we want to upgrade\r\n * the element to.\r\n */\r\n function upgradeElementInternal(element, optJsClass) {\r\n // Verify argument type.\r\n if (!(typeof element === 'object' && element instanceof Element)) {\r\n throw new Error('Invalid argument provided to upgrade MDL element.');\r\n }\r\n // Allow upgrade to be canceled by canceling emitted event.\r\n var upgradingEv = createEvent_('mdl-componentupgrading', true, true);\r\n element.dispatchEvent(upgradingEv);\r\n if (upgradingEv.defaultPrevented) {\r\n return;\r\n }\r\n\r\n var upgradedList = getUpgradedListOfElement_(element);\r\n var classesToUpgrade = [];\r\n // If jsClass is not provided scan the registered components to find the\r\n // ones matching the element's CSS classList.\r\n if (!optJsClass) {\r\n var classList = element.classList;\r\n registeredComponents_.forEach(function(component) {\r\n // Match CSS & Not to be upgraded & Not upgraded.\r\n if (classList.contains(component.cssClass) &&\r\n classesToUpgrade.indexOf(component) === -1 &&\r\n !isElementUpgraded_(element, component.className)) {\r\n classesToUpgrade.push(component);\r\n }\r\n });\r\n } else if (!isElementUpgraded_(element, optJsClass)) {\r\n classesToUpgrade.push(findRegisteredClass_(optJsClass));\r\n }\r\n\r\n // Upgrade the element for each classes.\r\n for (var i = 0, n = classesToUpgrade.length, registeredClass; i < n; i++) {\r\n registeredClass = classesToUpgrade[i];\r\n if (registeredClass) {\r\n // Mark element as upgraded.\r\n upgradedList.push(registeredClass.className);\r\n element.setAttribute('data-upgraded', upgradedList.join(','));\r\n var instance = new registeredClass.classConstructor(element);\r\n instance[componentConfigProperty_] = registeredClass;\r\n createdComponents_.push(instance);\r\n // Call any callbacks the user has registered with this component type.\r\n for (var j = 0, m = registeredClass.callbacks.length; j < m; j++) {\r\n registeredClass.callbacks[j](element);\r\n }\r\n\r\n if (registeredClass.widget) {\r\n // Assign per element instance for control over API\r\n element[registeredClass.className] = instance;\r\n }\r\n } else {\r\n throw new Error(\r\n 'Unable to find a registered component for the given class.');\r\n }\r\n\r\n var upgradedEv = createEvent_('mdl-componentupgraded', true, false);\r\n element.dispatchEvent(upgradedEv);\r\n }\r\n }\r\n\r\n /**\r\n * Upgrades a specific list of elements rather than all in the DOM.\r\n *\r\n * @param {!Element|!Array|!NodeList|!HTMLCollection} elements\r\n * The elements we wish to upgrade.\r\n */\r\n function upgradeElementsInternal(elements) {\r\n if (!Array.isArray(elements)) {\r\n if (elements instanceof Element) {\r\n elements = [elements];\r\n } else {\r\n elements = Array.prototype.slice.call(elements);\r\n }\r\n }\r\n for (var i = 0, n = elements.length, element; i < n; i++) {\r\n element = elements[i];\r\n if (element instanceof HTMLElement) {\r\n upgradeElementInternal(element);\r\n if (element.children.length > 0) {\r\n upgradeElementsInternal(element.children);\r\n }\r\n }\r\n }\r\n }\r\n\r\n /**\r\n * Registers a class for future use and attempts to upgrade existing DOM.\r\n *\r\n * @param {componentHandler.ComponentConfigPublic} config\r\n */\r\n function registerInternal(config) {\r\n // In order to support both Closure-compiled and uncompiled code accessing\r\n // this method, we need to allow for both the dot and array syntax for\r\n // property access. You'll therefore see the `foo.bar || foo['bar']`\r\n // pattern repeated across this method.\r\n var widgetMissing = (typeof config.widget === 'undefined' &&\r\n typeof config['widget'] === 'undefined');\r\n var widget = true;\r\n\r\n if (!widgetMissing) {\r\n widget = config.widget || config['widget'];\r\n }\r\n\r\n var newConfig = /** @type {componentHandler.ComponentConfig} */ ({\r\n classConstructor: config.constructor || config['constructor'],\r\n className: config.classAsString || config['classAsString'],\r\n cssClass: config.cssClass || config['cssClass'],\r\n widget: widget,\r\n callbacks: []\r\n });\r\n\r\n registeredComponents_.forEach(function(item) {\r\n if (item.cssClass === newConfig.cssClass) {\r\n throw new Error('The provided cssClass has already been registered: ' + item.cssClass);\r\n }\r\n if (item.className === newConfig.className) {\r\n throw new Error('The provided className has already been registered');\r\n }\r\n });\r\n\r\n if (config.constructor.prototype\r\n .hasOwnProperty(componentConfigProperty_)) {\r\n throw new Error(\r\n 'MDL component classes must not have ' + componentConfigProperty_ +\r\n ' defined as a property.');\r\n }\r\n\r\n var found = findRegisteredClass_(config.classAsString, newConfig);\r\n\r\n if (!found) {\r\n registeredComponents_.push(newConfig);\r\n }\r\n }\r\n\r\n /**\r\n * Allows user to be alerted to any upgrades that are performed for a given\r\n * component type\r\n *\r\n * @param {string} jsClass The class name of the MDL component we wish\r\n * to hook into for any upgrades performed.\r\n * @param {function(!HTMLElement)} callback The function to call upon an\r\n * upgrade. This function should expect 1 parameter - the HTMLElement which\r\n * got upgraded.\r\n */\r\n function registerUpgradedCallbackInternal(jsClass, callback) {\r\n var regClass = findRegisteredClass_(jsClass);\r\n if (regClass) {\r\n regClass.callbacks.push(callback);\r\n }\r\n }\r\n\r\n /**\r\n * Upgrades all registered components found in the current DOM. This is\r\n * automatically called on window load.\r\n */\r\n function upgradeAllRegisteredInternal() {\r\n for (var n = 0; n < registeredComponents_.length; n++) {\r\n upgradeDomInternal(registeredComponents_[n].className);\r\n }\r\n }\r\n\r\n /**\r\n * Check the component for the downgrade method.\r\n * Execute if found.\r\n * Remove component from createdComponents list.\r\n *\r\n * @param {?componentHandler.Component} component\r\n */\r\n function deconstructComponentInternal(component) {\r\n if (component) {\r\n var componentIndex = createdComponents_.indexOf(component);\r\n createdComponents_.splice(componentIndex, 1);\r\n\r\n var upgrades = component.element_.getAttribute('data-upgraded').split(',');\r\n var componentPlace = upgrades.indexOf(component[componentConfigProperty_].classAsString);\r\n upgrades.splice(componentPlace, 1);\r\n component.element_.setAttribute('data-upgraded', upgrades.join(','));\r\n\r\n var ev = createEvent_('mdl-componentdowngraded', true, false);\r\n component.element_.dispatchEvent(ev);\r\n }\r\n }\r\n\r\n /**\r\n * Downgrade either a given node, an array of nodes, or a NodeList.\r\n *\r\n * @param {!Node|!Array|!NodeList} nodes\r\n */\r\n function downgradeNodesInternal(nodes) {\r\n /**\r\n * Auxiliary function to downgrade a single node.\r\n * @param {!Node} node the node to be downgraded\r\n */\r\n var downgradeNode = function(node) {\r\n createdComponents_.filter(function(item) {\r\n return item.element_ === node;\r\n }).forEach(deconstructComponentInternal);\r\n };\r\n if (nodes instanceof Array || nodes instanceof NodeList) {\r\n for (var n = 0; n < nodes.length; n++) {\r\n downgradeNode(nodes[n]);\r\n }\r\n } else if (nodes instanceof Node) {\r\n downgradeNode(nodes);\r\n } else {\r\n throw new Error('Invalid argument provided to downgrade MDL nodes.');\r\n }\r\n }\r\n\r\n // Now return the functions that should be made public with their publicly\r\n // facing names...\r\n return {\r\n upgradeDom: upgradeDomInternal,\r\n upgradeElement: upgradeElementInternal,\r\n upgradeElements: upgradeElementsInternal,\r\n upgradeAllRegistered: upgradeAllRegisteredInternal,\r\n registerUpgradedCallback: registerUpgradedCallbackInternal,\r\n register: registerInternal,\r\n downgradeElements: downgradeNodesInternal\r\n };\r\n})();\r\n\r\n/**\r\n * Describes the type of a registered component type managed by\r\n * componentHandler. Provided for benefit of the Closure compiler.\r\n *\r\n * @typedef {{\r\n * constructor: Function,\r\n * classAsString: string,\r\n * cssClass: string,\r\n * widget: (string|boolean|undefined)\r\n * }}\r\n */\r\ncomponentHandler.ComponentConfigPublic; // jshint ignore:line\r\n\r\n/**\r\n * Describes the type of a registered component type managed by\r\n * componentHandler. Provided for benefit of the Closure compiler.\r\n *\r\n * @typedef {{\r\n * constructor: !Function,\r\n * className: string,\r\n * cssClass: string,\r\n * widget: (string|boolean),\r\n * callbacks: !Array\r\n * }}\r\n */\r\ncomponentHandler.ComponentConfig; // jshint ignore:line\r\n\r\n/**\r\n * Created component (i.e., upgraded element) type as managed by\r\n * componentHandler. Provided for benefit of the Closure compiler.\r\n *\r\n * @typedef {{\r\n * element_: !HTMLElement,\r\n * className: string,\r\n * classAsString: string,\r\n * cssClass: string,\r\n * widget: string\r\n * }}\r\n */\r\ncomponentHandler.Component; // jshint ignore:line\r\n\r\n// Export all symbols, for the benefit of Closure compiler.\r\n// No effect on uncompiled code.\r\ncomponentHandler['upgradeDom'] = componentHandler.upgradeDom;\r\ncomponentHandler['upgradeElement'] = componentHandler.upgradeElement;\r\ncomponentHandler['upgradeElements'] = componentHandler.upgradeElements;\r\ncomponentHandler['upgradeAllRegistered'] =\r\n componentHandler.upgradeAllRegistered;\r\ncomponentHandler['registerUpgradedCallback'] =\r\n componentHandler.registerUpgradedCallback;\r\ncomponentHandler['register'] = componentHandler.register;\r\ncomponentHandler['downgradeElements'] = componentHandler.downgradeElements;\r\nwindow.componentHandler = componentHandler;\r\nwindow['componentHandler'] = componentHandler;\r\n\r\nwindow.addEventListener('load', function() {\r\n 'use strict';\r\n\r\n /**\r\n * Performs a \"Cutting the mustard\" test. If the browser supports the features\r\n * tested, adds a mdl-js class to the element. It then upgrades all MDL\r\n * components requiring JavaScript.\r\n */\r\n if ('classList' in document.createElement('div') &&\r\n 'querySelector' in document &&\r\n 'addEventListener' in window && Array.prototype.forEach) {\r\n document.documentElement.classList.add('mdl-js');\r\n componentHandler.upgradeAllRegistered();\r\n } else {\r\n /**\r\n * Dummy function to avoid JS errors.\r\n */\r\n componentHandler.upgradeElement = function() {};\r\n /**\r\n * Dummy function to avoid JS errors.\r\n */\r\n componentHandler.register = function() {};\r\n }\r\n});\r\n\n// Source: https://github.com/darius/requestAnimationFrame/blob/master/requestAnimationFrame.js\n// Adapted from https://gist.github.com/paulirish/1579671 which derived from\n// http://paulirish.com/2011/requestanimationframe-for-smart-animating/\n// http://my.opera.com/emoller/blog/2011/12/20/requestanimationframe-for-smart-er-animating\n// requestAnimationFrame polyfill by Erik Möller.\n// Fixes from Paul Irish, Tino Zijdel, Andrew Mao, Klemen Slavič, Darius Bacon\n// MIT license\nif (!Date.now) {\n /**\r\n * Date.now polyfill.\r\n * @return {number} the current Date\r\n */\n Date.now = function () {\n return new Date().getTime();\n };\n Date['now'] = Date.now;\n}\nvar vendors = [\n 'webkit',\n 'moz'\n];\nfor (var i = 0; i < vendors.length && !window.requestAnimationFrame; ++i) {\n var vp = vendors[i];\n window.requestAnimationFrame = window[vp + 'RequestAnimationFrame'];\n window.cancelAnimationFrame = window[vp + 'CancelAnimationFrame'] || window[vp + 'CancelRequestAnimationFrame'];\n window['requestAnimationFrame'] = window.requestAnimationFrame;\n window['cancelAnimationFrame'] = window.cancelAnimationFrame;\n}\nif (/iP(ad|hone|od).*OS 6/.test(window.navigator.userAgent) || !window.requestAnimationFrame || !window.cancelAnimationFrame) {\n var lastTime = 0;\n /**\r\n * requestAnimationFrame polyfill.\r\n * @param {!Function} callback the callback function.\r\n */\n window.requestAnimationFrame = function (callback) {\n var now = Date.now();\n var nextTime = Math.max(lastTime + 16, now);\n return setTimeout(function () {\n callback(lastTime = nextTime);\n }, nextTime - now);\n };\n window.cancelAnimationFrame = clearTimeout;\n window['requestAnimationFrame'] = window.requestAnimationFrame;\n window['cancelAnimationFrame'] = window.cancelAnimationFrame;\n}\n/**\r\n * @license\r\n * Copyright 2015 Google Inc. All Rights Reserved.\r\n *\r\n * Licensed under the Apache License, Version 2.0 (the \"License\");\r\n * you may not use this file except in compliance with the License.\r\n * You may obtain a copy of the License at\r\n *\r\n * http://www.apache.org/licenses/LICENSE-2.0\r\n *\r\n * Unless required by applicable law or agreed to in writing, software\r\n * distributed under the License is distributed on an \"AS IS\" BASIS,\r\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\r\n * See the License for the specific language governing permissions and\r\n * limitations under the License.\r\n */\n/**\r\n * Class constructor for Button MDL component.\r\n * Implements MDL component design pattern defined at:\r\n * https://github.com/jasonmayes/mdl-component-design-pattern\r\n *\r\n * @param {HTMLElement} element The element that will be upgraded.\r\n */\nvar MaterialButton = function MaterialButton(element) {\n this.element_ = element;\n // Initialize instance.\n this.init();\n};\nwindow['MaterialButton'] = MaterialButton;\n/**\r\n * Store constants in one place so they can be updated easily.\r\n *\r\n * @enum {string | number}\r\n * @private\r\n */\nMaterialButton.prototype.Constant_ = {};\n/**\r\n * Store strings for class names defined by this component that are used in\r\n * JavaScript. This allows us to simply change it in one place should we\r\n * decide to modify at a later date.\r\n *\r\n * @enum {string}\r\n * @private\r\n */\nMaterialButton.prototype.CssClasses_ = {\n RIPPLE_EFFECT: 'mdl-js-ripple-effect',\n RIPPLE_CONTAINER: 'mdl-button__ripple-container',\n RIPPLE: 'mdl-ripple'\n};\n/**\r\n * Handle blur of element.\r\n *\r\n * @param {Event} event The event that fired.\r\n * @private\r\n */\nMaterialButton.prototype.blurHandler_ = function (event) {\n if (event) {\n this.element_.blur();\n }\n};\n// Public methods.\n/**\r\n * Disable button.\r\n *\r\n * @public\r\n */\nMaterialButton.prototype.disable = function () {\n this.element_.disabled = true;\n};\nMaterialButton.prototype['disable'] = MaterialButton.prototype.disable;\n/**\r\n * Enable button.\r\n *\r\n * @public\r\n */\nMaterialButton.prototype.enable = function () {\n this.element_.disabled = false;\n};\nMaterialButton.prototype['enable'] = MaterialButton.prototype.enable;\n/**\r\n * Initialize element.\r\n */\nMaterialButton.prototype.init = function () {\n if (this.element_) {\n if (this.element_.classList.contains(this.CssClasses_.RIPPLE_EFFECT)) {\n var rippleContainer = document.createElement('span');\n rippleContainer.classList.add(this.CssClasses_.RIPPLE_CONTAINER);\n this.rippleElement_ = document.createElement('span');\n this.rippleElement_.classList.add(this.CssClasses_.RIPPLE);\n rippleContainer.appendChild(this.rippleElement_);\n this.boundRippleBlurHandler = this.blurHandler_.bind(this);\n this.rippleElement_.addEventListener('mouseup', this.boundRippleBlurHandler);\n this.element_.appendChild(rippleContainer);\n }\n this.boundButtonBlurHandler = this.blurHandler_.bind(this);\n this.element_.addEventListener('mouseup', this.boundButtonBlurHandler);\n this.element_.addEventListener('mouseleave', this.boundButtonBlurHandler);\n }\n};\n// The component registers itself. It can assume componentHandler is available\n// in the global scope.\ncomponentHandler.register({\n constructor: MaterialButton,\n classAsString: 'MaterialButton',\n cssClass: 'mdl-js-button',\n widget: true\n});\n/**\r\n * @license\r\n * Copyright 2015 Google Inc. All Rights Reserved.\r\n *\r\n * Licensed under the Apache License, Version 2.0 (the \"License\");\r\n * you may not use this file except in compliance with the License.\r\n * You may obtain a copy of the License at\r\n *\r\n * http://www.apache.org/licenses/LICENSE-2.0\r\n *\r\n * Unless required by applicable law or agreed to in writing, software\r\n * distributed under the License is distributed on an \"AS IS\" BASIS,\r\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\r\n * See the License for the specific language governing permissions and\r\n * limitations under the License.\r\n */\n/**\r\n * Class constructor for Checkbox MDL component.\r\n * Implements MDL component design pattern defined at:\r\n * https://github.com/jasonmayes/mdl-component-design-pattern\r\n *\r\n * @constructor\r\n * @param {HTMLElement} element The element that will be upgraded.\r\n */\nvar MaterialCheckbox = function MaterialCheckbox(element) {\n this.element_ = element;\n // Initialize instance.\n this.init();\n};\nwindow['MaterialCheckbox'] = MaterialCheckbox;\n/**\r\n * Store constants in one place so they can be updated easily.\r\n *\r\n * @enum {string | number}\r\n * @private\r\n */\nMaterialCheckbox.prototype.Constant_ = { TINY_TIMEOUT: 0.001 };\n/**\r\n * Store strings for class names defined by this component that are used in\r\n * JavaScript. This allows us to simply change it in one place should we\r\n * decide to modify at a later date.\r\n *\r\n * @enum {string}\r\n * @private\r\n */\nMaterialCheckbox.prototype.CssClasses_ = {\n INPUT: 'mdl-checkbox__input',\n BOX_OUTLINE: 'mdl-checkbox__box-outline',\n FOCUS_HELPER: 'mdl-checkbox__focus-helper',\n TICK_OUTLINE: 'mdl-checkbox__tick-outline',\n RIPPLE_EFFECT: 'mdl-js-ripple-effect',\n RIPPLE_IGNORE_EVENTS: 'mdl-js-ripple-effect--ignore-events',\n RIPPLE_CONTAINER: 'mdl-checkbox__ripple-container',\n RIPPLE_CENTER: 'mdl-ripple--center',\n RIPPLE: 'mdl-ripple',\n IS_FOCUSED: 'is-focused',\n IS_DISABLED: 'is-disabled',\n IS_CHECKED: 'is-checked',\n IS_UPGRADED: 'is-upgraded'\n};\n/**\r\n * Handle change of state.\r\n *\r\n * @param {Event} event The event that fired.\r\n * @private\r\n */\nMaterialCheckbox.prototype.onChange_ = function (event) {\n this.updateClasses_();\n};\n/**\r\n * Handle focus of element.\r\n *\r\n * @param {Event} event The event that fired.\r\n * @private\r\n */\nMaterialCheckbox.prototype.onFocus_ = function (event) {\n this.element_.classList.add(this.CssClasses_.IS_FOCUSED);\n};\n/**\r\n * Handle lost focus of element.\r\n *\r\n * @param {Event} event The event that fired.\r\n * @private\r\n */\nMaterialCheckbox.prototype.onBlur_ = function (event) {\n this.element_.classList.remove(this.CssClasses_.IS_FOCUSED);\n};\n/**\r\n * Handle mouseup.\r\n *\r\n * @param {Event} event The event that fired.\r\n * @private\r\n */\nMaterialCheckbox.prototype.onMouseUp_ = function (event) {\n this.blur_();\n};\n/**\r\n * Handle class updates.\r\n *\r\n * @private\r\n */\nMaterialCheckbox.prototype.updateClasses_ = function () {\n this.checkDisabled();\n this.checkToggleState();\n};\n/**\r\n * Add blur.\r\n *\r\n * @private\r\n */\nMaterialCheckbox.prototype.blur_ = function () {\n // TODO: figure out why there's a focus event being fired after our blur,\n // so that we can avoid this hack.\n window.setTimeout(function () {\n this.inputElement_.blur();\n }.bind(this), this.Constant_.TINY_TIMEOUT);\n};\n// Public methods.\n/**\r\n * Check the inputs toggle state and update display.\r\n *\r\n * @public\r\n */\nMaterialCheckbox.prototype.checkToggleState = function () {\n if (this.inputElement_.checked) {\n this.element_.classList.add(this.CssClasses_.IS_CHECKED);\n } else {\n this.element_.classList.remove(this.CssClasses_.IS_CHECKED);\n }\n};\nMaterialCheckbox.prototype['checkToggleState'] = MaterialCheckbox.prototype.checkToggleState;\n/**\r\n * Check the inputs disabled state and update display.\r\n *\r\n * @public\r\n */\nMaterialCheckbox.prototype.checkDisabled = function () {\n if (this.inputElement_.disabled) {\n this.element_.classList.add(this.CssClasses_.IS_DISABLED);\n } else {\n this.element_.classList.remove(this.CssClasses_.IS_DISABLED);\n }\n};\nMaterialCheckbox.prototype['checkDisabled'] = MaterialCheckbox.prototype.checkDisabled;\n/**\r\n * Disable checkbox.\r\n *\r\n * @public\r\n */\nMaterialCheckbox.prototype.disable = function () {\n this.inputElement_.disabled = true;\n this.updateClasses_();\n};\nMaterialCheckbox.prototype['disable'] = MaterialCheckbox.prototype.disable;\n/**\r\n * Enable checkbox.\r\n *\r\n * @public\r\n */\nMaterialCheckbox.prototype.enable = function () {\n this.inputElement_.disabled = false;\n this.updateClasses_();\n};\nMaterialCheckbox.prototype['enable'] = MaterialCheckbox.prototype.enable;\n/**\r\n * Check checkbox.\r\n *\r\n * @public\r\n */\nMaterialCheckbox.prototype.check = function () {\n this.inputElement_.checked = true;\n this.updateClasses_();\n};\nMaterialCheckbox.prototype['check'] = MaterialCheckbox.prototype.check;\n/**\r\n * Uncheck checkbox.\r\n *\r\n * @public\r\n */\nMaterialCheckbox.prototype.uncheck = function () {\n this.inputElement_.checked = false;\n this.updateClasses_();\n};\nMaterialCheckbox.prototype['uncheck'] = MaterialCheckbox.prototype.uncheck;\n/**\r\n * Initialize element.\r\n */\nMaterialCheckbox.prototype.init = function () {\n if (this.element_) {\n this.inputElement_ = this.element_.querySelector('.' + this.CssClasses_.INPUT);\n var boxOutline = document.createElement('span');\n boxOutline.classList.add(this.CssClasses_.BOX_OUTLINE);\n var tickContainer = document.createElement('span');\n tickContainer.classList.add(this.CssClasses_.FOCUS_HELPER);\n var tickOutline = document.createElement('span');\n tickOutline.classList.add(this.CssClasses_.TICK_OUTLINE);\n boxOutline.appendChild(tickOutline);\n this.element_.appendChild(tickContainer);\n this.element_.appendChild(boxOutline);\n if (this.element_.classList.contains(this.CssClasses_.RIPPLE_EFFECT)) {\n this.element_.classList.add(this.CssClasses_.RIPPLE_IGNORE_EVENTS);\n this.rippleContainerElement_ = document.createElement('span');\n this.rippleContainerElement_.classList.add(this.CssClasses_.RIPPLE_CONTAINER);\n this.rippleContainerElement_.classList.add(this.CssClasses_.RIPPLE_EFFECT);\n this.rippleContainerElement_.classList.add(this.CssClasses_.RIPPLE_CENTER);\n this.boundRippleMouseUp = this.onMouseUp_.bind(this);\n this.rippleContainerElement_.addEventListener('mouseup', this.boundRippleMouseUp);\n var ripple = document.createElement('span');\n ripple.classList.add(this.CssClasses_.RIPPLE);\n this.rippleContainerElement_.appendChild(ripple);\n this.element_.appendChild(this.rippleContainerElement_);\n }\n this.boundInputOnChange = this.onChange_.bind(this);\n this.boundInputOnFocus = this.onFocus_.bind(this);\n this.boundInputOnBlur = this.onBlur_.bind(this);\n this.boundElementMouseUp = this.onMouseUp_.bind(this);\n this.inputElement_.addEventListener('change', this.boundInputOnChange);\n this.inputElement_.addEventListener('focus', this.boundInputOnFocus);\n this.inputElement_.addEventListener('blur', this.boundInputOnBlur);\n this.element_.addEventListener('mouseup', this.boundElementMouseUp);\n this.updateClasses_();\n this.element_.classList.add(this.CssClasses_.IS_UPGRADED);\n }\n};\n// The component registers itself. It can assume componentHandler is available\n// in the global scope.\ncomponentHandler.register({\n constructor: MaterialCheckbox,\n classAsString: 'MaterialCheckbox',\n cssClass: 'mdl-js-checkbox',\n widget: true\n});\n/**\r\n * @license\r\n * Copyright 2015 Google Inc. All Rights Reserved.\r\n *\r\n * Licensed under the Apache License, Version 2.0 (the \"License\");\r\n * you may not use this file except in compliance with the License.\r\n * You may obtain a copy of the License at\r\n *\r\n * http://www.apache.org/licenses/LICENSE-2.0\r\n *\r\n * Unless required by applicable law or agreed to in writing, software\r\n * distributed under the License is distributed on an \"AS IS\" BASIS,\r\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\r\n * See the License for the specific language governing permissions and\r\n * limitations under the License.\r\n */\n/**\r\n * Class constructor for dropdown MDL component.\r\n * Implements MDL component design pattern defined at:\r\n * https://github.com/jasonmayes/mdl-component-design-pattern\r\n *\r\n * @constructor\r\n * @param {HTMLElement} element The element that will be upgraded.\r\n */\nvar MaterialMenu = function MaterialMenu(element) {\n this.element_ = element;\n // Initialize instance.\n this.init();\n};\nwindow['MaterialMenu'] = MaterialMenu;\n/**\r\n * Store constants in one place so they can be updated easily.\r\n *\r\n * @enum {string | number}\r\n * @private\r\n */\nMaterialMenu.prototype.Constant_ = {\n // Total duration of the menu animation.\n TRANSITION_DURATION_SECONDS: 0.3,\n // The fraction of the total duration we want to use for menu item animations.\n TRANSITION_DURATION_FRACTION: 0.8,\n // How long the menu stays open after choosing an option (so the user can see\n // the ripple).\n CLOSE_TIMEOUT: 150\n};\n/**\r\n * Keycodes, for code readability.\r\n *\r\n * @enum {number}\r\n * @private\r\n */\nMaterialMenu.prototype.Keycodes_ = {\n ENTER: 13,\n ESCAPE: 27,\n SPACE: 32,\n UP_ARROW: 38,\n DOWN_ARROW: 40\n};\n/**\r\n * Store strings for class names defined by this component that are used in\r\n * JavaScript. This allows us to simply change it in one place should we\r\n * decide to modify at a later date.\r\n *\r\n * @enum {string}\r\n * @private\r\n */\nMaterialMenu.prototype.CssClasses_ = {\n CONTAINER: 'mdl-menu__container',\n OUTLINE: 'mdl-menu__outline',\n ITEM: 'mdl-menu__item',\n ITEM_RIPPLE_CONTAINER: 'mdl-menu__item-ripple-container',\n RIPPLE_EFFECT: 'mdl-js-ripple-effect',\n RIPPLE_IGNORE_EVENTS: 'mdl-js-ripple-effect--ignore-events',\n RIPPLE: 'mdl-ripple',\n // Statuses\n IS_UPGRADED: 'is-upgraded',\n IS_VISIBLE: 'is-visible',\n IS_ANIMATING: 'is-animating',\n // Alignment options\n BOTTOM_LEFT: 'mdl-menu--bottom-left',\n // This is the default.\n BOTTOM_RIGHT: 'mdl-menu--bottom-right',\n TOP_LEFT: 'mdl-menu--top-left',\n TOP_RIGHT: 'mdl-menu--top-right',\n UNALIGNED: 'mdl-menu--unaligned'\n};\n/**\r\n * Initialize element.\r\n */\nMaterialMenu.prototype.init = function () {\n if (this.element_) {\n // Patch by Corigo beginning.\n var dataset = this.element_.dataset;\n if ('visibleItems' in dataset) {\n this.visibleItems_ = !isNaN(dataset.visibleItems) ? dataset.visibleItems : 1;\n }\n if ('postUrl' in dataset) {\n this.postUrl_ = dataset.postUrl;\n }\n if ('itemClickHandler' in dataset) {\n this.itemClickHandler_ = dataset.itemClickHandler;\n }\n // Patch end.\n // Create container for the menu.\n var container = document.createElement('div');\n container.classList.add(this.CssClasses_.CONTAINER);\n this.element_.parentElement.insertBefore(container, this.element_);\n this.element_.parentElement.removeChild(this.element_);\n container.appendChild(this.element_);\n // Patch by Corrigo beginning.\n var items = this.element_.querySelectorAll('.' + this.CssClasses_.ITEM);\n if (this.visibleItems_ < items.length) {\n var width = this.element_.getBoundingClientRect().width, firstItem = this.element_.querySelector('.' + this.CssClasses_.ITEM), containerClone = container.cloneNode(true);\n containerClone.style.visibility = 'visible';\n containerClone.style.overflowY = 'scroll';\n containerClone.style.width = width + 'px';\n containerClone.style.height = firstItem ? firstItem.offsetHeight + 'px' : '0px';\n document.body.appendChild(containerClone);\n var scrollbarWidth = containerClone.offsetWidth - containerClone.clientWidth;\n containerClone.parentNode.removeChild(containerClone);\n container.style.width = width + scrollbarWidth + 'px';\n } else {\n container.style.width = this.element_.getBoundingClientRect().width + 'px';\n }\n container.style.overflowX = 'hidden';\n // Patch end.\n this.container_ = container;\n // Create outline for the menu (shadow and background).\n var outline = document.createElement('div');\n outline.classList.add(this.CssClasses_.OUTLINE);\n this.outline_ = outline;\n container.insertBefore(outline, this.element_);\n // Find the \"for\" element and bind events to it.\n var forElId = this.element_.getAttribute('for') || this.element_.getAttribute('data-mdl-for');\n var forEl = null;\n if (forElId) {\n forEl = document.getElementById(forElId);\n if (forEl) {\n this.forElement_ = forEl;\n forEl.addEventListener('click', this.handleForClick_.bind(this));\n forEl.addEventListener('keydown', this.handleForKeyboardEvent_.bind(this));\n }\n }\n var items = this.element_.querySelectorAll('.' + this.CssClasses_.ITEM);\n this.boundItemKeydown_ = this.handleItemKeyboardEvent_.bind(this);\n // Patch by Corrigo beginning.\n this.boundItemClick_ = this.itemClickHandler_ ? window[this.itemClickHandler_].bind(this) : this.handleItemClick_.bind(this);\n // Patch end.\n for (var i = 0; i < items.length; i++) {\n // Add a listener to each menu item.\n items[i].addEventListener('click', this.boundItemClick_);\n // Add a tab index to each menu item.\n items[i].tabIndex = '-1';\n // Add a keyboard listener to each menu item.\n items[i].addEventListener('keydown', this.boundItemKeydown_);\n }\n // Add ripple classes to each item, if the user has enabled ripples.\n if (this.element_.classList.contains(this.CssClasses_.RIPPLE_EFFECT)) {\n this.element_.classList.add(this.CssClasses_.RIPPLE_IGNORE_EVENTS);\n for (i = 0; i < items.length; i++) {\n var item = items[i];\n var rippleContainer = document.createElement('span');\n rippleContainer.classList.add(this.CssClasses_.ITEM_RIPPLE_CONTAINER);\n var ripple = document.createElement('span');\n ripple.classList.add(this.CssClasses_.RIPPLE);\n rippleContainer.appendChild(ripple);\n item.appendChild(rippleContainer);\n item.classList.add(this.CssClasses_.RIPPLE_EFFECT);\n }\n }\n // Copy alignment classes to the container, so the outline can use them.\n if (this.element_.classList.contains(this.CssClasses_.BOTTOM_LEFT)) {\n this.outline_.classList.add(this.CssClasses_.BOTTOM_LEFT);\n }\n if (this.element_.classList.contains(this.CssClasses_.BOTTOM_RIGHT)) {\n this.outline_.classList.add(this.CssClasses_.BOTTOM_RIGHT);\n }\n if (this.element_.classList.contains(this.CssClasses_.TOP_LEFT)) {\n this.outline_.classList.add(this.CssClasses_.TOP_LEFT);\n }\n if (this.element_.classList.contains(this.CssClasses_.TOP_RIGHT)) {\n this.outline_.classList.add(this.CssClasses_.TOP_RIGHT);\n }\n if (this.element_.classList.contains(this.CssClasses_.UNALIGNED)) {\n this.outline_.classList.add(this.CssClasses_.UNALIGNED);\n }\n container.classList.add(this.CssClasses_.IS_UPGRADED);\n }\n};\n/**\r\n * Handles a click on the \"for\" element, by positioning the menu and then\r\n * toggling it.\r\n *\r\n * @param {Event} evt The event that fired.\r\n * @private\r\n */\nMaterialMenu.prototype.handleForClick_ = function (evt) {\n if (this.element_ && this.forElement_) {\n var rect = this.forElement_.getBoundingClientRect();\n var forRect = this.forElement_.parentElement.getBoundingClientRect();\n // Patch by Corrigo beginning.\n var isButtonAbsolutelyPositioned = document.defaultView.getComputedStyle(this.forElement_).position === 'absolute';\n var buttonRight = document.defaultView.getComputedStyle(this.forElement_).right;\n if (this.element_.classList.contains(this.CssClasses_.UNALIGNED)) {\n } else if (this.element_.classList.contains(this.CssClasses_.BOTTOM_RIGHT)) {\n // Position below the \"for\" element, aligned to its right.\n // Patch by Corrigo beginning.\n this.container_.style.right = isButtonAbsolutelyPositioned ? buttonRight : forRect.right - rect.right + 'px';\n // Patch end.\n this.container_.style.top = this.forElement_.offsetTop + this.forElement_.offsetHeight + 'px';\n } else if (this.element_.classList.contains(this.CssClasses_.TOP_LEFT)) {\n // Position above the \"for\" element, aligned to its left.\n this.container_.style.left = this.forElement_.offsetLeft + 'px';\n this.container_.style.bottom = forRect.bottom - rect.top + 'px';\n } else if (this.element_.classList.contains(this.CssClasses_.TOP_RIGHT)) {\n // Position above the \"for\" element, aligned to its right.\n // Patch by Corrigo beginning.\n this.container_.style.right = isButtonAbsolutelyPositioned ? buttonRight : forRect.right - rect.right + 'px';\n // Patch end.\n this.container_.style.bottom = forRect.bottom - rect.top + 'px';\n } else {\n // Default: position below the \"for\" element, aligned to its left.\n this.container_.style.left = this.forElement_.offsetLeft + 'px';\n this.container_.style.top = this.forElement_.offsetTop + this.forElement_.offsetHeight + 'px';\n }\n }\n this.toggle(evt);\n};\n/**\r\n * Handles a keyboard event on the \"for\" element.\r\n *\r\n * @param {Event} evt The event that fired.\r\n * @private\r\n */\nMaterialMenu.prototype.handleForKeyboardEvent_ = function (evt) {\n if (this.element_ && this.container_ && this.forElement_) {\n var items = this.element_.querySelectorAll('.' + this.CssClasses_.ITEM + ':not([disabled])');\n if (items && items.length > 0 && this.container_.classList.contains(this.CssClasses_.IS_VISIBLE)) {\n if (evt.keyCode === this.Keycodes_.UP_ARROW) {\n evt.preventDefault();\n items[items.length - 1].focus();\n } else if (evt.keyCode === this.Keycodes_.DOWN_ARROW) {\n evt.preventDefault();\n items[0].focus();\n }\n }\n }\n};\n/**\r\n * Handles a keyboard event on an item.\r\n *\r\n * @param {Event} evt The event that fired.\r\n * @private\r\n */\nMaterialMenu.prototype.handleItemKeyboardEvent_ = function (evt) {\n if (this.element_ && this.container_) {\n var items = this.element_.querySelectorAll('.' + this.CssClasses_.ITEM + ':not([disabled])');\n if (items && items.length > 0 && this.container_.classList.contains(this.CssClasses_.IS_VISIBLE)) {\n var currentIndex = Array.prototype.slice.call(items).indexOf(evt.target);\n if (evt.keyCode === this.Keycodes_.UP_ARROW) {\n evt.preventDefault();\n if (currentIndex > 0) {\n items[currentIndex - 1].focus();\n } else {\n items[items.length - 1].focus();\n }\n } else if (evt.keyCode === this.Keycodes_.DOWN_ARROW) {\n evt.preventDefault();\n if (items.length > currentIndex + 1) {\n items[currentIndex + 1].focus();\n } else {\n items[0].focus();\n }\n } else if (evt.keyCode === this.Keycodes_.SPACE || evt.keyCode === this.Keycodes_.ENTER) {\n evt.preventDefault();\n // Send mousedown and mouseup to trigger ripple.\n var e = new MouseEvent('mousedown');\n evt.target.dispatchEvent(e);\n e = new MouseEvent('mouseup');\n evt.target.dispatchEvent(e);\n // Send click.\n evt.target.click();\n } else if (evt.keyCode === this.Keycodes_.ESCAPE) {\n evt.preventDefault();\n this.hide();\n }\n }\n }\n};\n/**\r\n * Handles a click event on an item.\r\n *\r\n * @param {Event} evt The event that fired.\r\n * @private\r\n */\nMaterialMenu.prototype.handleItemClick_ = function (evt) {\n if (evt.target.hasAttribute('disabled')) {\n evt.stopPropagation();\n } else {\n // Wait some time before closing menu, so the user can see the ripple.\n this.closing_ = true;\n window.setTimeout(function (evt) {\n this.hide();\n this.closing_ = false;\n }.bind(this), this.Constant_.CLOSE_TIMEOUT);\n }\n};\n/**\r\n * Calculates the initial clip (for opening the menu) or final clip (for closing\r\n * it), and applies it. This allows us to animate from or to the correct point,\r\n * that is, the point it's aligned to in the \"for\" element.\r\n *\r\n * @param {number} height Height of the clip rectangle\r\n * @param {number} width Width of the clip rectangle\r\n * @private\r\n */\nMaterialMenu.prototype.applyClip_ = function (height, width) {\n if (this.element_.classList.contains(this.CssClasses_.UNALIGNED)) {\n // Do not clip.\n this.element_.style.clip = '';\n } else if (this.element_.classList.contains(this.CssClasses_.BOTTOM_RIGHT)) {\n // Clip to the top right corner of the menu.\n this.element_.style.clip = 'rect(0 ' + width + 'px ' + '0 ' + width + 'px)';\n } else if (this.element_.classList.contains(this.CssClasses_.TOP_LEFT)) {\n // Clip to the bottom left corner of the menu.\n this.element_.style.clip = 'rect(' + height + 'px 0 ' + height + 'px 0)';\n } else if (this.element_.classList.contains(this.CssClasses_.TOP_RIGHT)) {\n // Clip to the bottom right corner of the menu.\n this.element_.style.clip = 'rect(' + height + 'px ' + width + 'px ' + height + 'px ' + width + 'px)';\n } else {\n // Default: do not clip (same as clipping to the top left corner).\n this.element_.style.clip = '';\n }\n};\n/**\r\n * Cleanup function to remove animation listeners.\r\n *\r\n * @param {Event} evt\r\n * @private\r\n */\nMaterialMenu.prototype.removeAnimationEndListener_ = function (evt) {\n evt.target.classList.remove(MaterialMenu.prototype.CssClasses_.IS_ANIMATING);\n};\n/**\r\n * Adds an event listener to clean up after the animation ends.\r\n *\r\n * @private\r\n */\nMaterialMenu.prototype.addAnimationEndListener_ = function () {\n this.element_.addEventListener('transitionend', this.removeAnimationEndListener_);\n this.element_.addEventListener('webkitTransitionEnd', this.removeAnimationEndListener_);\n};\n/**\r\n * Displays the menu.\r\n *\r\n * @public\r\n */\nMaterialMenu.prototype.show = function (evt) {\n if (this.element_ && this.container_ && this.outline_) {\n // Measure the inner element.\n var height = this.element_.getBoundingClientRect().height;\n var width = this.element_.getBoundingClientRect().width;\n // Patch by Corrigo beginning.\n var containerHeight = height;\n if (this.visibleItems_ > 0) {\n var item = this.element_.querySelector('.' + this.CssClasses_.ITEM);\n if (item !== null) {\n containerHeight = item.offsetHeight * this.visibleItems_ + 16;\n }\n }\n // Apply the inner element's size to the container and outline.\n this.container_.style.height = containerHeight + 'px';\n // Patch end.\n this.outline_.style.width = width + 'px';\n this.outline_.style.height = height + 'px';\n var transitionDuration = this.Constant_.TRANSITION_DURATION_SECONDS * this.Constant_.TRANSITION_DURATION_FRACTION;\n // Calculate transition delays for individual menu items, so that they fade\n // in one at a time.\n var items = this.element_.querySelectorAll('.' + this.CssClasses_.ITEM);\n for (var i = 0; i < items.length; i++) {\n var itemDelay = null;\n if (this.element_.classList.contains(this.CssClasses_.TOP_LEFT) || this.element_.classList.contains(this.CssClasses_.TOP_RIGHT)) {\n itemDelay = (height - items[i].offsetTop - items[i].offsetHeight) / height * transitionDuration + 's';\n } else {\n itemDelay = items[i].offsetTop / height * transitionDuration + 's';\n }\n items[i].style.transitionDelay = itemDelay;\n }\n // Apply the initial clip to the text before we start animating.\n this.applyClip_(height, width);\n // Wait for the next frame, turn on animation, and apply the final clip.\n // Also make it visible. This triggers the transitions.\n window.requestAnimationFrame(function () {\n this.element_.classList.add(this.CssClasses_.IS_ANIMATING);\n this.element_.style.clip = 'rect(0 ' + width + 'px ' + height + 'px 0)';\n this.container_.classList.add(this.CssClasses_.IS_VISIBLE);\n }.bind(this));\n // Clean up after the animation is complete.\n this.addAnimationEndListener_();\n // Add a click listener to the document, to close the menu.\n var callback = function (e) {\n // Check to see if the document is processing the same event that\n // displayed the menu in the first place. If so, do nothing.\n // Also check to see if the menu is in the process of closing itself, and\n // do nothing in that case.\n // Also check if the clicked element is a menu item\n // if so, do nothing.\n if (e !== evt && !this.closing_ && e.target.parentNode !== this.element_) {\n document.removeEventListener('click', callback);\n this.hide();\n }\n }.bind(this);\n document.addEventListener('click', callback);\n }\n};\nMaterialMenu.prototype['show'] = MaterialMenu.prototype.show;\n/**\r\n * Hides the menu.\r\n *\r\n * @public\r\n */\nMaterialMenu.prototype.hide = function () {\n if (this.element_ && this.container_ && this.outline_) {\n var items = this.element_.querySelectorAll('.' + this.CssClasses_.ITEM);\n // Remove all transition delays; menu items fade out concurrently.\n for (var i = 0; i < items.length; i++) {\n items[i].style.removeProperty('transition-delay');\n }\n // Measure the inner element.\n var rect = this.element_.getBoundingClientRect();\n var height = rect.height;\n var width = rect.width;\n // Turn on animation, and apply the final clip. Also make invisible.\n // This triggers the transitions.\n this.element_.classList.add(this.CssClasses_.IS_ANIMATING);\n this.applyClip_(height, width);\n this.container_.classList.remove(this.CssClasses_.IS_VISIBLE);\n // Clean up after the animation is complete.\n this.addAnimationEndListener_();\n }\n};\nMaterialMenu.prototype['hide'] = MaterialMenu.prototype.hide;\n/**\r\n * Displays or hides the menu, depending on current state.\r\n *\r\n * @public\r\n */\nMaterialMenu.prototype.toggle = function (evt) {\n if (this.container_.classList.contains(this.CssClasses_.IS_VISIBLE)) {\n this.hide();\n } else {\n this.show(evt);\n }\n};\nMaterialMenu.prototype['toggle'] = MaterialMenu.prototype.toggle;\n// The component registers itself. It can assume componentHandler is available\n// in the global scope.\ncomponentHandler.register({\n constructor: MaterialMenu,\n classAsString: 'MaterialMenu',\n cssClass: 'mdl-js-menu',\n widget: true\n});\n/**\r\n * @license\r\n * Copyright 2015 Google Inc. All Rights Reserved.\r\n *\r\n * Licensed under the Apache License, Version 2.0 (the \"License\");\r\n * you may not use this file except in compliance with the License.\r\n * You may obtain a copy of the License at\r\n *\r\n * http://www.apache.org/licenses/LICENSE-2.0\r\n *\r\n * Unless required by applicable law or agreed to in writing, software\r\n * distributed under the License is distributed on an \"AS IS\" BASIS,\r\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\r\n * See the License for the specific language governing permissions and\r\n * limitations under the License.\r\n */\n/**\r\n * Class constructor for Progress MDL component.\r\n * Implements MDL component design pattern defined at:\r\n * https://github.com/jasonmayes/mdl-component-design-pattern\r\n *\r\n * @constructor\r\n * @param {HTMLElement} element The element that will be upgraded.\r\n */\nvar MaterialProgress = function MaterialProgress(element) {\n this.element_ = element;\n // Initialize instance.\n this.init();\n};\nwindow['MaterialProgress'] = MaterialProgress;\n/**\r\n * Store constants in one place so they can be updated easily.\r\n *\r\n * @enum {string | number}\r\n * @private\r\n */\nMaterialProgress.prototype.Constant_ = {};\n/**\r\n * Store strings for class names defined by this component that are used in\r\n * JavaScript. This allows us to simply change it in one place should we\r\n * decide to modify at a later date.\r\n *\r\n * @enum {string}\r\n * @private\r\n */\nMaterialProgress.prototype.CssClasses_ = { INDETERMINATE_CLASS: 'mdl-progress__indeterminate' };\n/**\r\n * Set the current progress of the progressbar.\r\n *\r\n * @param {number} p Percentage of the progress (0-100)\r\n * @public\r\n */\nMaterialProgress.prototype.setProgress = function (p) {\n if (this.element_.classList.contains(this.CssClasses_.INDETERMINATE_CLASS)) {\n return;\n }\n this.progressbar_.style.width = p + '%';\n};\nMaterialProgress.prototype['setProgress'] = MaterialProgress.prototype.setProgress;\n/**\r\n * Set the current progress of the buffer.\r\n *\r\n * @param {number} p Percentage of the buffer (0-100)\r\n * @public\r\n */\nMaterialProgress.prototype.setBuffer = function (p) {\n this.bufferbar_.style.width = p + '%';\n this.auxbar_.style.width = 100 - p + '%';\n};\nMaterialProgress.prototype['setBuffer'] = MaterialProgress.prototype.setBuffer;\n/**\r\n * Initialize element.\r\n */\nMaterialProgress.prototype.init = function () {\n if (this.element_) {\n var el = document.createElement('div');\n el.className = 'progressbar bar bar1';\n this.element_.appendChild(el);\n this.progressbar_ = el;\n el = document.createElement('div');\n el.className = 'bufferbar bar bar2';\n this.element_.appendChild(el);\n this.bufferbar_ = el;\n el = document.createElement('div');\n el.className = 'auxbar bar bar3';\n this.element_.appendChild(el);\n this.auxbar_ = el;\n this.progressbar_.style.width = '0%';\n this.bufferbar_.style.width = '100%';\n this.auxbar_.style.width = '0%';\n this.element_.classList.add('is-upgraded');\n }\n};\n// The component registers itself. It can assume componentHandler is available\n// in the global scope.\ncomponentHandler.register({\n constructor: MaterialProgress,\n classAsString: 'MaterialProgress',\n cssClass: 'mdl-js-progress',\n widget: true\n});\n/**\r\n * @license\r\n * Copyright 2015 Google Inc. All Rights Reserved.\r\n *\r\n * Licensed under the Apache License, Version 2.0 (the \"License\");\r\n * you may not use this file except in compliance with the License.\r\n * You may obtain a copy of the License at\r\n *\r\n * http://www.apache.org/licenses/LICENSE-2.0\r\n *\r\n * Unless required by applicable law or agreed to in writing, software\r\n * distributed under the License is distributed on an \"AS IS\" BASIS,\r\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\r\n * See the License for the specific language governing permissions and\r\n * limitations under the License.\r\n */\n/**\r\n * Class constructor for Textfield MDL component.\r\n * Implements MDL component design pattern defined at:\r\n * https://github.com/jasonmayes/mdl-component-design-pattern\r\n *\r\n * @constructor\r\n * @param {HTMLElement} element The element that will be upgraded.\r\n */\nvar MaterialTextfield = function MaterialTextfield(element) {\n this.element_ = element;\n this.maxRows = this.Constant_.NO_MAX_ROWS;\n // Initialize instance.\n this.init();\n};\nwindow['MaterialTextfield'] = MaterialTextfield;\n/**\r\n * Store constants in one place so they can be updated easily.\r\n *\r\n * @enum {string | number}\r\n * @private\r\n */\nMaterialTextfield.prototype.Constant_ = {\n NO_MAX_ROWS: -1,\n MAX_ROWS_ATTRIBUTE: 'maxrows'\n};\n/**\r\n * Store strings for class names defined by this component that are used in\r\n * JavaScript. This allows us to simply change it in one place should we\r\n * decide to modify at a later date.\r\n *\r\n * @enum {string}\r\n * @private\r\n */\nMaterialTextfield.prototype.CssClasses_ = {\n LABEL: 'mdl-textfield__label',\n INPUT: 'mdl-textfield__input',\n IS_DIRTY: 'is-dirty',\n IS_FOCUSED: 'is-focused',\n IS_DISABLED: 'is-disabled',\n IS_INVALID: 'is-invalid',\n IS_UPGRADED: 'is-upgraded',\n HAS_PLACEHOLDER: 'has-placeholder'\n};\n/**\r\n * Handle input being entered.\r\n *\r\n * @param {Event} event The event that fired.\r\n * @private\r\n */\nMaterialTextfield.prototype.onKeyDown_ = function (event) {\n var currentRowCount = event.target.value.split('\\n').length;\n if (event.keyCode === 13) {\n if (currentRowCount >= this.maxRows) {\n event.preventDefault();\n }\n }\n};\n/**\r\n * Handle focus.\r\n *\r\n * @param {Event} event The event that fired.\r\n * @private\r\n */\nMaterialTextfield.prototype.onFocus_ = function (event) {\n this.element_.classList.add(this.CssClasses_.IS_FOCUSED);\n};\n/**\r\n * Handle lost focus.\r\n *\r\n * @param {Event} event The event that fired.\r\n * @private\r\n */\nMaterialTextfield.prototype.onBlur_ = function (event) {\n this.element_.classList.remove(this.CssClasses_.IS_FOCUSED);\n};\n/**\r\n * Handle reset event from out side.\r\n *\r\n * @param {Event} event The event that fired.\r\n * @private\r\n */\nMaterialTextfield.prototype.onReset_ = function (event) {\n this.updateClasses_();\n};\n/**\r\n * Handle class updates.\r\n *\r\n * @private\r\n */\nMaterialTextfield.prototype.updateClasses_ = function () {\n this.checkDisabled();\n // Patch by Corrigo starting.\n this.checkDirty();\n var isDirty = this.element_.classList.contains(this.CssClasses_.IS_DIRTY), isRequired = this.input_.required;\n if (!isRequired || isRequired && isDirty) {\n this.checkValidity();\n }\n // Patch end.\n this.checkFocus();\n};\n// Public methods.\n/**\r\n * Check the disabled state and update field accordingly.\r\n *\r\n * @public\r\n */\nMaterialTextfield.prototype.checkDisabled = function () {\n if (this.input_.disabled) {\n this.element_.classList.add(this.CssClasses_.IS_DISABLED);\n } else {\n this.element_.classList.remove(this.CssClasses_.IS_DISABLED);\n }\n};\nMaterialTextfield.prototype['checkDisabled'] = MaterialTextfield.prototype.checkDisabled;\n/**\r\n * Check the focus state and update field accordingly.\r\n *\r\n * @public\r\n */\nMaterialTextfield.prototype.checkFocus = function () {\n if (Boolean(this.element_.querySelector(':focus'))) {\n this.element_.classList.add(this.CssClasses_.IS_FOCUSED);\n } else {\n this.element_.classList.remove(this.CssClasses_.IS_FOCUSED);\n }\n};\nMaterialTextfield.prototype['checkFocus'] = MaterialTextfield.prototype.checkFocus;\n/**\r\n * Check the validity state and update field accordingly.\r\n *\r\n * @public\r\n */\nMaterialTextfield.prototype.checkValidity = function () {\n if (this.input_.validity) {\n if (this.input_.validity.valid) {\n this.element_.classList.remove(this.CssClasses_.IS_INVALID);\n } else {\n this.element_.classList.add(this.CssClasses_.IS_INVALID);\n }\n }\n};\nMaterialTextfield.prototype['checkValidity'] = MaterialTextfield.prototype.checkValidity;\n/**\r\n * Check the dirty state and update field accordingly.\r\n *\r\n * @public\r\n */\nMaterialTextfield.prototype.checkDirty = function () {\n if (this.input_.value && this.input_.value.length > 0 || this.input_.placeholder.trim() !== '') {\n this.element_.classList.add(this.CssClasses_.IS_DIRTY);\n } else {\n this.element_.classList.remove(this.CssClasses_.IS_DIRTY);\n }\n};\nMaterialTextfield.prototype['checkDirty'] = MaterialTextfield.prototype.checkDirty;\n/**\r\n * Disable text field.\r\n *\r\n * @public\r\n */\nMaterialTextfield.prototype.disable = function () {\n this.input_.disabled = true;\n this.updateClasses_();\n};\nMaterialTextfield.prototype['disable'] = MaterialTextfield.prototype.disable;\n/**\r\n * Enable text field.\r\n *\r\n * @public\r\n */\nMaterialTextfield.prototype.enable = function () {\n this.input_.disabled = false;\n this.updateClasses_();\n // Patch by Corrigo starting.\n this.checkValidity(); // End patch.\n};\nMaterialTextfield.prototype['enable'] = MaterialTextfield.prototype.enable;\n/**\r\n * Update text field value.\r\n *\r\n * @param {string} value The value to which to set the control (optional).\r\n * @public\r\n */\nMaterialTextfield.prototype.change = function (value) {\n this.input_.value = value || '';\n this.updateClasses_();\n};\nMaterialTextfield.prototype['change'] = MaterialTextfield.prototype.change;\n/**\r\n * Initialize element.\r\n */\nMaterialTextfield.prototype.init = function () {\n if (this.element_) {\n this.label_ = this.element_.querySelector('.' + this.CssClasses_.LABEL);\n this.input_ = this.element_.querySelector('.' + this.CssClasses_.INPUT);\n if (this.input_) {\n if (this.input_.hasAttribute(this.Constant_.MAX_ROWS_ATTRIBUTE)) {\n this.maxRows = parseInt(this.input_.getAttribute(this.Constant_.MAX_ROWS_ATTRIBUTE), 10);\n if (isNaN(this.maxRows)) {\n this.maxRows = this.Constant_.NO_MAX_ROWS;\n }\n }\n if (this.input_.hasAttribute('placeholder')) {\n this.element_.classList.add(this.CssClasses_.HAS_PLACEHOLDER);\n }\n this.boundUpdateClassesHandler = this.updateClasses_.bind(this);\n this.boundFocusHandler = this.onFocus_.bind(this);\n this.boundBlurHandler = this.onBlur_.bind(this);\n this.boundResetHandler = this.onReset_.bind(this);\n this.input_.addEventListener('input', this.boundUpdateClassesHandler);\n this.input_.addEventListener('focus', this.boundFocusHandler);\n this.input_.addEventListener('blur', this.boundBlurHandler);\n this.input_.addEventListener('reset', this.boundResetHandler);\n if (this.maxRows !== this.Constant_.NO_MAX_ROWS) {\n // TODO: This should handle pasting multi line text.\n // Currently doesn't.\n this.boundKeyDownHandler = this.onKeyDown_.bind(this);\n this.input_.addEventListener('keydown', this.boundKeyDownHandler);\n }\n var invalid = this.element_.classList.contains(this.CssClasses_.IS_INVALID);\n this.updateClasses_();\n this.element_.classList.add(this.CssClasses_.IS_UPGRADED);\n if (invalid) {\n this.element_.classList.add(this.CssClasses_.IS_INVALID);\n }\n if (this.input_.hasAttribute('autofocus')) {\n this.element_.focus();\n this.checkFocus();\n }\n }\n }\n};\n// The component registers itself. It can assume componentHandler is available\n// in the global scope.\ncomponentHandler.register({\n constructor: MaterialTextfield,\n classAsString: 'MaterialTextfield',\n cssClass: 'mdl-js-textfield',\n widget: true\n});\n/**\r\n * @license\r\n * Copyright 2015 Google Inc. All Rights Reserved.\r\n *\r\n * Licensed under the Apache License, Version 2.0 (the \"License\");\r\n * you may not use this file except in compliance with the License.\r\n * You may obtain a copy of the License at\r\n *\r\n * http://www.apache.org/licenses/LICENSE-2.0\r\n *\r\n * Unless required by applicable law or agreed to in writing, software\r\n * distributed under the License is distributed on an \"AS IS\" BASIS,\r\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\r\n * See the License for the specific language governing permissions and\r\n * limitations under the License.\r\n */\n/**\r\n * Class constructor for Layout MDL component.\r\n * Implements MDL component design pattern defined at:\r\n * https://github.com/jasonmayes/mdl-component-design-pattern\r\n *\r\n * @constructor\r\n * @param {HTMLElement} element The element that will be upgraded.\r\n */\nvar MaterialLayout = function MaterialLayout(element) {\n this.element_ = element;\n // Initialize instance.\n this.init();\n};\nwindow['MaterialLayout'] = MaterialLayout;\n/**\r\n * Store constants in one place so they can be updated easily.\r\n *\r\n * @enum {string | number}\r\n * @private\r\n */\nMaterialLayout.prototype.Constant_ = {\n MAX_WIDTH: '(max-width: 1024px)',\n TAB_SCROLL_PIXELS: 100,\n RESIZE_TIMEOUT: 100,\n MENU_ICON: '',\n CHEVRON_LEFT: 'chevron_left',\n CHEVRON_RIGHT: 'chevron_right'\n};\n/**\r\n * Keycodes, for code readability.\r\n *\r\n * @enum {number}\r\n * @private\r\n */\nMaterialLayout.prototype.Keycodes_ = {\n ENTER: 13,\n ESCAPE: 27,\n SPACE: 32\n};\n/**\r\n * Modes.\r\n *\r\n * @enum {number}\r\n * @private\r\n */\nMaterialLayout.prototype.Mode_ = {\n STANDARD: 0,\n SEAMED: 1,\n WATERFALL: 2,\n SCROLL: 3\n};\n/**\r\n * Store strings for class names defined by this component that are used in\r\n * JavaScript. This allows us to simply change it in one place should we\r\n * decide to modify at a later date.\r\n *\r\n * @enum {string}\r\n * @private\r\n */\nMaterialLayout.prototype.CssClasses_ = {\n CONTAINER: 'mdl-layout__container',\n HEADER: 'mdl-layout__header',\n DRAWER: 'mdl-layout__drawer',\n CONTENT: 'mdl-layout__content',\n DRAWER_BTN: 'mdl-layout__drawer-button',\n ICON: 'material-icons',\n JS_RIPPLE_EFFECT: 'mdl-js-ripple-effect',\n RIPPLE_CONTAINER: 'mdl-layout__tab-ripple-container',\n RIPPLE: 'mdl-ripple',\n RIPPLE_IGNORE_EVENTS: 'mdl-js-ripple-effect--ignore-events',\n HEADER_SEAMED: 'mdl-layout__header--seamed',\n HEADER_WATERFALL: 'mdl-layout__header--waterfall',\n HEADER_SCROLL: 'mdl-layout__header--scroll',\n FIXED_HEADER: 'mdl-layout--fixed-header',\n FIXED_DRAWER: 'mdl-layout--fixed-drawer',\n OBFUSCATOR: 'mdl-layout__obfuscator',\n TAB_BAR: 'mdl-layout__tab-bar',\n TAB_CONTAINER: 'mdl-layout__tab-bar-container',\n TAB: 'mdl-layout__tab',\n TAB_BAR_BUTTON: 'mdl-layout__tab-bar-button',\n TAB_BAR_LEFT_BUTTON: 'mdl-layout__tab-bar-left-button',\n TAB_BAR_RIGHT_BUTTON: 'mdl-layout__tab-bar-right-button',\n TAB_MANUAL_SWITCH: 'mdl-layout__tab-manual-switch',\n PANEL: 'mdl-layout__tab-panel',\n HAS_DRAWER: 'has-drawer',\n HAS_TABS: 'has-tabs',\n HAS_SCROLLING_HEADER: 'has-scrolling-header',\n CASTING_SHADOW: 'is-casting-shadow',\n IS_COMPACT: 'is-compact',\n IS_SMALL_SCREEN: 'is-small-screen',\n IS_DRAWER_OPEN: 'is-visible',\n IS_ACTIVE: 'is-active',\n IS_UPGRADED: 'is-upgraded',\n IS_ANIMATING: 'is-animating',\n ON_LARGE_SCREEN: 'mdl-layout--large-screen-only',\n ON_SMALL_SCREEN: 'mdl-layout--small-screen-only'\n};\n/**\r\n * Provide local version of matchMedia. This is needed in order to support\r\n * monkey-patching of matchMedia in the unit tests. Due to peculiarities in\r\n * PhantomJS, it doesn't work to monkey patch window.matchMedia directly.\r\n *\r\n * @private\r\n */\nMaterialLayout.prototype.matchMedia_ = function (query) {\n return window.matchMedia(query);\n};\n/**\r\n * Handles scrolling on the content.\r\n *\r\n * @private\r\n */\nMaterialLayout.prototype.contentScrollHandler_ = function () {\n if (this.header_.classList.contains(this.CssClasses_.IS_ANIMATING)) {\n return;\n }\n var headerVisible = !this.element_.classList.contains(this.CssClasses_.IS_SMALL_SCREEN) || this.element_.classList.contains(this.CssClasses_.FIXED_HEADER);\n if (this.content_.scrollTop > 0 && !this.header_.classList.contains(this.CssClasses_.IS_COMPACT)) {\n this.header_.classList.add(this.CssClasses_.CASTING_SHADOW);\n this.header_.classList.add(this.CssClasses_.IS_COMPACT);\n if (headerVisible) {\n this.header_.classList.add(this.CssClasses_.IS_ANIMATING);\n }\n } else if (this.content_.scrollTop <= 0 && this.header_.classList.contains(this.CssClasses_.IS_COMPACT)) {\n this.header_.classList.remove(this.CssClasses_.CASTING_SHADOW);\n this.header_.classList.remove(this.CssClasses_.IS_COMPACT);\n if (headerVisible) {\n this.header_.classList.add(this.CssClasses_.IS_ANIMATING);\n }\n }\n};\n/**\r\n * Handles a keyboard event on the drawer.\r\n *\r\n * @param {Event} evt The event that fired.\r\n * @private\r\n */\nMaterialLayout.prototype.keyboardEventHandler_ = function (evt) {\n // Only react when the drawer is open.\n if (evt.keyCode === this.Keycodes_.ESCAPE && this.drawer_.classList.contains(this.CssClasses_.IS_DRAWER_OPEN)) {\n this.toggleDrawer();\n }\n};\n/**\r\n * Handles changes in screen size.\r\n *\r\n * @private\r\n */\nMaterialLayout.prototype.screenSizeHandler_ = function () {\n if (this.screenSizeMediaQuery_.matches) {\n this.element_.classList.add(this.CssClasses_.IS_SMALL_SCREEN);\n if (this.drawer_) {\n this.drawer_.setAttribute('aria-hidden', 'true');\n }\n } else {\n this.element_.classList.remove(this.CssClasses_.IS_SMALL_SCREEN);\n // Collapse drawer (if any) when moving to a large screen size.\n if (this.drawer_) {\n this.drawer_.classList.remove(this.CssClasses_.IS_DRAWER_OPEN);\n this.obfuscator_.classList.remove(this.CssClasses_.IS_DRAWER_OPEN);\n if (this.element_.classList.contains(this.CssClasses_.FIXED_DRAWER)) {\n this.drawer_.setAttribute('aria-hidden', 'false');\n }\n }\n }\n};\n/**\r\n * Handles events of drawer button.\r\n *\r\n * @param {Event} evt The event that fired.\r\n * @private\r\n */\nMaterialLayout.prototype.drawerToggleHandler_ = function (evt) {\n if (evt && evt.type === 'keydown') {\n if (evt.keyCode === this.Keycodes_.SPACE || evt.keyCode === this.Keycodes_.ENTER) {\n // prevent scrolling in drawer nav\n evt.preventDefault();\n } else {\n // prevent other keys\n return;\n }\n }\n this.toggleDrawer();\n};\n/**\r\n * Handles (un)setting the `is-animating` class\r\n *\r\n * @private\r\n */\nMaterialLayout.prototype.headerTransitionEndHandler_ = function () {\n this.header_.classList.remove(this.CssClasses_.IS_ANIMATING);\n};\n/**\r\n * Handles expanding the header on click\r\n *\r\n * @private\r\n */\nMaterialLayout.prototype.headerClickHandler_ = function () {\n if (this.header_.classList.contains(this.CssClasses_.IS_COMPACT)) {\n this.header_.classList.remove(this.CssClasses_.IS_COMPACT);\n this.header_.classList.add(this.CssClasses_.IS_ANIMATING);\n }\n};\n/**\r\n * Reset tab state, dropping active classes\r\n *\r\n * @private\r\n */\nMaterialLayout.prototype.resetTabState_ = function (tabBar) {\n for (var k = 0; k < tabBar.length; k++) {\n tabBar[k].classList.remove(this.CssClasses_.IS_ACTIVE);\n }\n};\n/**\r\n * Reset panel state, droping active classes\r\n *\r\n * @private\r\n */\nMaterialLayout.prototype.resetPanelState_ = function (panels) {\n for (var j = 0; j < panels.length; j++) {\n panels[j].classList.remove(this.CssClasses_.IS_ACTIVE);\n }\n};\n/**\r\n * Toggle drawer state\r\n *\r\n * @public\r\n */\nMaterialLayout.prototype.toggleDrawer = function () {\n var drawerButton = this.element_.querySelector('.' + this.CssClasses_.DRAWER_BTN);\n this.drawer_.classList.toggle(this.CssClasses_.IS_DRAWER_OPEN);\n this.obfuscator_.classList.toggle(this.CssClasses_.IS_DRAWER_OPEN);\n // Set accessibility properties.\n if (this.drawer_.classList.contains(this.CssClasses_.IS_DRAWER_OPEN)) {\n this.drawer_.setAttribute('aria-hidden', 'false');\n drawerButton.setAttribute('aria-expanded', 'true');\n } else {\n this.drawer_.setAttribute('aria-hidden', 'true');\n drawerButton.setAttribute('aria-expanded', 'false');\n }\n};\nMaterialLayout.prototype['toggleDrawer'] = MaterialLayout.prototype.toggleDrawer;\n/**\r\n * Initialize element.\r\n */\nMaterialLayout.prototype.init = function () {\n if (this.element_) {\n var container = document.createElement('div');\n container.classList.add(this.CssClasses_.CONTAINER);\n var focusedElement = this.element_.querySelector(':focus');\n this.element_.parentElement.insertBefore(container, this.element_);\n this.element_.parentElement.removeChild(this.element_);\n container.appendChild(this.element_);\n if (focusedElement) {\n focusedElement.focus();\n }\n var directChildren = this.element_.childNodes;\n var numChildren = directChildren.length;\n for (var c = 0; c < numChildren; c++) {\n var child = directChildren[c];\n if (child.classList && child.classList.contains(this.CssClasses_.HEADER)) {\n this.header_ = child;\n }\n if (child.classList && child.classList.contains(this.CssClasses_.DRAWER)) {\n this.drawer_ = child;\n }\n if (child.classList && child.classList.contains(this.CssClasses_.CONTENT)) {\n this.content_ = child;\n }\n }\n window.addEventListener('pageshow', function (e) {\n if (e.persisted) {\n // when page is loaded from back/forward cache\n // trigger repaint to let layout scroll in safari\n this.element_.style.overflowY = 'hidden';\n requestAnimationFrame(function () {\n this.element_.style.overflowY = '';\n }.bind(this));\n }\n }.bind(this), false);\n if (this.header_) {\n this.tabBar_ = this.header_.querySelector('.' + this.CssClasses_.TAB_BAR);\n }\n var mode = this.Mode_.STANDARD;\n if (this.header_) {\n if (this.header_.classList.contains(this.CssClasses_.HEADER_SEAMED)) {\n mode = this.Mode_.SEAMED;\n } else if (this.header_.classList.contains(this.CssClasses_.HEADER_WATERFALL)) {\n mode = this.Mode_.WATERFALL;\n this.header_.addEventListener('transitionend', this.headerTransitionEndHandler_.bind(this));\n this.header_.addEventListener('click', this.headerClickHandler_.bind(this));\n } else if (this.header_.classList.contains(this.CssClasses_.HEADER_SCROLL)) {\n mode = this.Mode_.SCROLL;\n container.classList.add(this.CssClasses_.HAS_SCROLLING_HEADER);\n }\n if (mode === this.Mode_.STANDARD) {\n this.header_.classList.add(this.CssClasses_.CASTING_SHADOW);\n if (this.tabBar_) {\n this.tabBar_.classList.add(this.CssClasses_.CASTING_SHADOW);\n }\n } else if (mode === this.Mode_.SEAMED || mode === this.Mode_.SCROLL) {\n this.header_.classList.remove(this.CssClasses_.CASTING_SHADOW);\n if (this.tabBar_) {\n this.tabBar_.classList.remove(this.CssClasses_.CASTING_SHADOW);\n }\n } else if (mode === this.Mode_.WATERFALL) {\n // Add and remove shadows depending on scroll position.\n // Also add/remove auxiliary class for styling of the compact version of\n // the header.\n this.content_.addEventListener('scroll', this.contentScrollHandler_.bind(this));\n this.contentScrollHandler_();\n }\n }\n // Add drawer toggling button to our layout, if we have an openable drawer.\n if (this.drawer_) {\n var drawerButton = this.element_.querySelector('.' + this.CssClasses_.DRAWER_BTN);\n if (!drawerButton) {\n drawerButton = document.createElement('div');\n drawerButton.setAttribute('aria-expanded', 'false');\n drawerButton.setAttribute('role', 'button');\n drawerButton.setAttribute('tabindex', '0');\n drawerButton.classList.add(this.CssClasses_.DRAWER_BTN);\n var drawerButtonIcon = document.createElement('i');\n drawerButtonIcon.classList.add(this.CssClasses_.ICON);\n drawerButtonIcon.innerHTML = this.Constant_.MENU_ICON;\n drawerButton.appendChild(drawerButtonIcon);\n }\n if (this.drawer_.classList.contains(this.CssClasses_.ON_LARGE_SCREEN)) {\n //If drawer has ON_LARGE_SCREEN class then add it to the drawer toggle button as well.\n drawerButton.classList.add(this.CssClasses_.ON_LARGE_SCREEN);\n } else if (this.drawer_.classList.contains(this.CssClasses_.ON_SMALL_SCREEN)) {\n //If drawer has ON_SMALL_SCREEN class then add it to the drawer toggle button as well.\n drawerButton.classList.add(this.CssClasses_.ON_SMALL_SCREEN);\n }\n drawerButton.addEventListener('click', this.drawerToggleHandler_.bind(this));\n drawerButton.addEventListener('keydown', this.drawerToggleHandler_.bind(this));\n // Add a class if the layout has a drawer, for altering the left padding.\n // Adds the HAS_DRAWER to the elements since this.header_ may or may\n // not be present.\n this.element_.classList.add(this.CssClasses_.HAS_DRAWER);\n // If we have a fixed header, add the button to the header rather than\n // the layout.\n if (this.element_.classList.contains(this.CssClasses_.FIXED_HEADER)) {\n this.header_.insertBefore(drawerButton, this.header_.firstChild);\n } else {\n this.element_.insertBefore(drawerButton, this.content_);\n }\n var obfuscator = document.createElement('div');\n obfuscator.classList.add(this.CssClasses_.OBFUSCATOR);\n this.element_.appendChild(obfuscator);\n obfuscator.addEventListener('click', this.drawerToggleHandler_.bind(this));\n this.obfuscator_ = obfuscator;\n this.drawer_.addEventListener('keydown', this.keyboardEventHandler_.bind(this));\n this.drawer_.setAttribute('aria-hidden', 'true');\n }\n // Keep an eye on screen size, and add/remove auxiliary class for styling\n // of small screens.\n this.screenSizeMediaQuery_ = this.matchMedia_(this.Constant_.MAX_WIDTH);\n this.screenSizeMediaQuery_.addListener(this.screenSizeHandler_.bind(this));\n this.screenSizeHandler_();\n // Initialize tabs, if any.\n if (this.header_ && this.tabBar_) {\n this.element_.classList.add(this.CssClasses_.HAS_TABS);\n var tabContainer = document.createElement('div');\n tabContainer.classList.add(this.CssClasses_.TAB_CONTAINER);\n this.header_.insertBefore(tabContainer, this.tabBar_);\n this.header_.removeChild(this.tabBar_);\n var leftButton = document.createElement('div');\n leftButton.classList.add(this.CssClasses_.TAB_BAR_BUTTON);\n leftButton.classList.add(this.CssClasses_.TAB_BAR_LEFT_BUTTON);\n var leftButtonIcon = document.createElement('i');\n leftButtonIcon.classList.add(this.CssClasses_.ICON);\n leftButtonIcon.textContent = this.Constant_.CHEVRON_LEFT;\n leftButton.appendChild(leftButtonIcon);\n leftButton.addEventListener('click', function () {\n this.tabBar_.scrollLeft -= this.Constant_.TAB_SCROLL_PIXELS;\n }.bind(this));\n var rightButton = document.createElement('div');\n rightButton.classList.add(this.CssClasses_.TAB_BAR_BUTTON);\n rightButton.classList.add(this.CssClasses_.TAB_BAR_RIGHT_BUTTON);\n var rightButtonIcon = document.createElement('i');\n rightButtonIcon.classList.add(this.CssClasses_.ICON);\n rightButtonIcon.textContent = this.Constant_.CHEVRON_RIGHT;\n rightButton.appendChild(rightButtonIcon);\n rightButton.addEventListener('click', function () {\n this.tabBar_.scrollLeft += this.Constant_.TAB_SCROLL_PIXELS;\n }.bind(this));\n tabContainer.appendChild(leftButton);\n tabContainer.appendChild(this.tabBar_);\n tabContainer.appendChild(rightButton);\n // Add and remove tab buttons depending on scroll position and total\n // window size.\n var tabUpdateHandler = function () {\n if (this.tabBar_.scrollLeft > 0) {\n leftButton.classList.add(this.CssClasses_.IS_ACTIVE);\n } else {\n leftButton.classList.remove(this.CssClasses_.IS_ACTIVE);\n }\n if (this.tabBar_.scrollLeft < this.tabBar_.scrollWidth - this.tabBar_.offsetWidth) {\n rightButton.classList.add(this.CssClasses_.IS_ACTIVE);\n } else {\n rightButton.classList.remove(this.CssClasses_.IS_ACTIVE);\n }\n }.bind(this);\n this.tabBar_.addEventListener('scroll', tabUpdateHandler);\n tabUpdateHandler();\n // Update tabs when the window resizes.\n var windowResizeHandler = function () {\n // Use timeouts to make sure it doesn't happen too often.\n if (this.resizeTimeoutId_) {\n clearTimeout(this.resizeTimeoutId_);\n }\n this.resizeTimeoutId_ = setTimeout(function () {\n tabUpdateHandler();\n this.resizeTimeoutId_ = null;\n }.bind(this), this.Constant_.RESIZE_TIMEOUT);\n }.bind(this);\n window.addEventListener('resize', windowResizeHandler);\n if (this.tabBar_.classList.contains(this.CssClasses_.JS_RIPPLE_EFFECT)) {\n this.tabBar_.classList.add(this.CssClasses_.RIPPLE_IGNORE_EVENTS);\n }\n // Select element tabs, document panels\n var tabs = this.tabBar_.querySelectorAll('.' + this.CssClasses_.TAB);\n var panels = this.content_.querySelectorAll('.' + this.CssClasses_.PANEL);\n // Create new tabs for each tab element\n for (var i = 0; i < tabs.length; i++) {\n new MaterialLayoutTab(tabs[i], tabs, panels, this);\n }\n }\n this.element_.classList.add(this.CssClasses_.IS_UPGRADED);\n }\n};\n/**\r\n * Constructor for an individual tab.\r\n *\r\n * @constructor\r\n * @param {HTMLElement} tab The HTML element for the tab.\r\n * @param {!Array} tabs Array with HTML elements for all tabs.\r\n * @param {!Array} panels Array with HTML elements for all panels.\r\n * @param {MaterialLayout} layout The MaterialLayout object that owns the tab.\r\n */\nfunction MaterialLayoutTab(tab, tabs, panels, layout) {\n /**\r\n * Auxiliary method to programmatically select a tab in the UI.\r\n */\n function selectTab() {\n var href = tab.href.split('#')[1];\n var panel = layout.content_.querySelector('#' + href);\n layout.resetTabState_(tabs);\n layout.resetPanelState_(panels);\n tab.classList.add(layout.CssClasses_.IS_ACTIVE);\n panel.classList.add(layout.CssClasses_.IS_ACTIVE);\n }\n if (layout.tabBar_.classList.contains(layout.CssClasses_.JS_RIPPLE_EFFECT)) {\n var rippleContainer = document.createElement('span');\n rippleContainer.classList.add(layout.CssClasses_.RIPPLE_CONTAINER);\n rippleContainer.classList.add(layout.CssClasses_.JS_RIPPLE_EFFECT);\n var ripple = document.createElement('span');\n ripple.classList.add(layout.CssClasses_.RIPPLE);\n rippleContainer.appendChild(ripple);\n tab.appendChild(rippleContainer);\n }\n if (!layout.tabBar_.classList.contains(layout.CssClasses_.TAB_MANUAL_SWITCH)) {\n tab.addEventListener('click', function (e) {\n if (tab.getAttribute('href').charAt(0) === '#') {\n e.preventDefault();\n selectTab();\n }\n });\n }\n tab.show = selectTab;\n}\nwindow['MaterialLayoutTab'] = MaterialLayoutTab;\n// The component registers itself. It can assume componentHandler is available\n// in the global scope.\ncomponentHandler.register({\n constructor: MaterialLayout,\n classAsString: 'MaterialLayout',\n cssClass: 'mdl-js-layout'\n});\n/**\r\n * @license\r\n * Copyright 2015 Google Inc. All Rights Reserved.\r\n *\r\n * Licensed under the Apache License, Version 2.0 (the \"License\");\r\n * you may not use this file except in compliance with the License.\r\n * You may obtain a copy of the License at\r\n *\r\n * http://www.apache.org/licenses/LICENSE-2.0\r\n *\r\n * Unless required by applicable law or agreed to in writing, software\r\n * distributed under the License is distributed on an \"AS IS\" BASIS,\r\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\r\n * See the License for the specific language governing permissions and\r\n * limitations under the License.\r\n */\n/**\r\n * Class constructor for Ripple MDL component.\r\n * Implements MDL component design pattern defined at:\r\n * https://github.com/jasonmayes/mdl-component-design-pattern\r\n *\r\n * @constructor\r\n * @param {HTMLElement} element The element that will be upgraded.\r\n */\nvar MaterialRipple = function MaterialRipple(element) {\n this.element_ = element;\n // Initialize instance.\n this.init();\n};\nwindow['MaterialRipple'] = MaterialRipple;\n/**\r\n * Store constants in one place so they can be updated easily.\r\n *\r\n * @enum {string | number}\r\n * @private\r\n */\nMaterialRipple.prototype.Constant_ = {\n INITIAL_SCALE: 'scale(0.0001, 0.0001)',\n INITIAL_SIZE: '1px',\n INITIAL_OPACITY: '0.4',\n FINAL_OPACITY: '0',\n FINAL_SCALE: ''\n};\n/**\r\n * Store strings for class names defined by this component that are used in\r\n * JavaScript. This allows us to simply change it in one place should we\r\n * decide to modify at a later date.\r\n *\r\n * @enum {string}\r\n * @private\r\n */\nMaterialRipple.prototype.CssClasses_ = {\n RIPPLE_CENTER: 'mdl-ripple--center',\n RIPPLE_EFFECT_IGNORE_EVENTS: 'mdl-js-ripple-effect--ignore-events',\n RIPPLE: 'mdl-ripple',\n IS_ANIMATING: 'is-animating',\n IS_VISIBLE: 'is-visible'\n};\n/**\r\n * Handle mouse / finger down on element.\r\n *\r\n * @param {Event} event The event that fired.\r\n * @private\r\n */\nMaterialRipple.prototype.downHandler_ = function (event) {\n if (!this.rippleElement_.style.width && !this.rippleElement_.style.height) {\n var rect = this.element_.getBoundingClientRect();\n this.boundHeight = rect.height;\n this.boundWidth = rect.width;\n this.rippleSize_ = Math.sqrt(rect.width * rect.width + rect.height * rect.height) * 2 + 2;\n this.rippleElement_.style.width = this.rippleSize_ + 'px';\n this.rippleElement_.style.height = this.rippleSize_ + 'px';\n }\n this.rippleElement_.classList.add(this.CssClasses_.IS_VISIBLE);\n if (event.type === 'mousedown' && this.ignoringMouseDown_) {\n this.ignoringMouseDown_ = false;\n } else {\n if (event.type === 'touchstart') {\n this.ignoringMouseDown_ = true;\n }\n var frameCount = this.getFrameCount();\n if (frameCount > 0) {\n return;\n }\n this.setFrameCount(1);\n var bound = event.currentTarget.getBoundingClientRect();\n var x;\n var y;\n // Check if we are handling a keyboard click.\n if (event.clientX === 0 && event.clientY === 0) {\n x = Math.round(bound.width / 2);\n y = Math.round(bound.height / 2);\n } else {\n var clientX = event.clientX !== undefined ? event.clientX : event.touches[0].clientX;\n var clientY = event.clientY !== undefined ? event.clientY : event.touches[0].clientY;\n x = Math.round(clientX - bound.left);\n y = Math.round(clientY - bound.top);\n }\n this.setRippleXY(x, y);\n this.setRippleStyles(true);\n window.requestAnimationFrame(this.animFrameHandler.bind(this));\n }\n};\n/**\r\n * Handle mouse / finger up on element.\r\n *\r\n * @param {Event} event The event that fired.\r\n * @private\r\n */\nMaterialRipple.prototype.upHandler_ = function (event) {\n // Don't fire for the artificial \"mouseup\" generated by a double-click.\n if (event && event.detail !== 2) {\n // Allow a repaint to occur before removing this class, so the animation\n // shows for tap events, which seem to trigger a mouseup too soon after\n // mousedown.\n window.setTimeout(function () {\n this.rippleElement_.classList.remove(this.CssClasses_.IS_VISIBLE);\n }.bind(this), 0);\n }\n};\n/**\r\n * Initialize element.\r\n */\nMaterialRipple.prototype.init = function () {\n if (this.element_) {\n var recentering = this.element_.classList.contains(this.CssClasses_.RIPPLE_CENTER);\n if (!this.element_.classList.contains(this.CssClasses_.RIPPLE_EFFECT_IGNORE_EVENTS)) {\n this.rippleElement_ = this.element_.querySelector('.' + this.CssClasses_.RIPPLE);\n this.frameCount_ = 0;\n this.rippleSize_ = 0;\n this.x_ = 0;\n this.y_ = 0;\n // Touch start produces a compat mouse down event, which would cause a\n // second ripples. To avoid that, we use this property to ignore the first\n // mouse down after a touch start.\n this.ignoringMouseDown_ = false;\n this.boundDownHandler = this.downHandler_.bind(this);\n this.element_.addEventListener('mousedown', this.boundDownHandler);\n this.element_.addEventListener('touchstart', this.boundDownHandler);\n this.boundUpHandler = this.upHandler_.bind(this);\n this.element_.addEventListener('mouseup', this.boundUpHandler);\n this.element_.addEventListener('mouseleave', this.boundUpHandler);\n this.element_.addEventListener('touchend', this.boundUpHandler);\n this.element_.addEventListener('blur', this.boundUpHandler);\n /**\r\n * Getter for frameCount_.\r\n * @return {number} the frame count.\r\n */\n this.getFrameCount = function () {\n return this.frameCount_;\n };\n /**\r\n * Setter for frameCount_.\r\n * @param {number} fC the frame count.\r\n */\n this.setFrameCount = function (fC) {\n this.frameCount_ = fC;\n };\n /**\r\n * Getter for rippleElement_.\r\n * @return {Element} the ripple element.\r\n */\n this.getRippleElement = function () {\n return this.rippleElement_;\n };\n /**\r\n * Sets the ripple X and Y coordinates.\r\n * @param {number} newX the new X coordinate\r\n * @param {number} newY the new Y coordinate\r\n */\n this.setRippleXY = function (newX, newY) {\n this.x_ = newX;\n this.y_ = newY;\n };\n /**\r\n * Sets the ripple styles.\r\n * @param {boolean} start whether or not this is the start frame.\r\n */\n this.setRippleStyles = function (start) {\n if (this.rippleElement_ !== null) {\n var transformString;\n var scale;\n var size;\n var offset = 'translate(' + this.x_ + 'px, ' + this.y_ + 'px)';\n if (start) {\n scale = this.Constant_.INITIAL_SCALE;\n size = this.Constant_.INITIAL_SIZE;\n } else {\n scale = this.Constant_.FINAL_SCALE;\n size = this.rippleSize_ + 'px';\n if (recentering) {\n offset = 'translate(' + this.boundWidth / 2 + 'px, ' + this.boundHeight / 2 + 'px)';\n }\n }\n transformString = 'translate(-50%, -50%) ' + offset + scale;\n this.rippleElement_.style.webkitTransform = transformString;\n this.rippleElement_.style.msTransform = transformString;\n this.rippleElement_.style.transform = transformString;\n if (start) {\n this.rippleElement_.classList.remove(this.CssClasses_.IS_ANIMATING);\n } else {\n this.rippleElement_.classList.add(this.CssClasses_.IS_ANIMATING);\n }\n }\n };\n /**\r\n * Handles an animation frame.\r\n */\n this.animFrameHandler = function () {\n if (this.frameCount_-- > 0) {\n window.requestAnimationFrame(this.animFrameHandler.bind(this));\n } else {\n this.setRippleStyles(false);\n }\n };\n }\n }\n};\n// The component registers itself. It can assume componentHandler is available\n// in the global scope.\ncomponentHandler.register({\n constructor: MaterialRipple,\n classAsString: 'MaterialRipple',\n cssClass: 'mdl-js-ripple-effect',\n widget: false\n});\n}());\n","/**\r\n * @license\r\n * Copyright 2015 Google Inc. All Rights Reserved.\r\n *\r\n * Licensed under the Apache License, Version 2.0 (the \"License\");\r\n * you may not use this file except in compliance with the License.\r\n * You may obtain a copy of the License at\r\n *\r\n * http://www.apache.org/licenses/LICENSE-2.0\r\n *\r\n * Unless required by applicable law or agreed to in writing, software\r\n * distributed under the License is distributed on an \"AS IS\" BASIS,\r\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\r\n * See the License for the specific language governing permissions and\r\n * limitations under the License.\r\n */\r\n/**\r\n * A component handler interface using the revealing module design pattern.\r\n * More details on this design pattern here:\r\n * https://github.com/jasonmayes/mdl-component-design-pattern\r\n *\r\n * @author Jason Mayes.\r\n */\r\n/* exported componentHandler */\r\n\r\n// Pre-defining the componentHandler interface, for closure documentation and\r\n// static verification.\r\nvar componentHandler = {\r\n /**\r\n * Searches existing DOM for elements of our component type and upgrades them\r\n * if they have not already been upgraded.\r\n *\r\n * @param {string=} optJsClass the programatic name of the element class we\r\n * need to create a new instance of.\r\n * @param {string=} optCssClass the name of the CSS class elements of this\r\n * type will have.\r\n */\r\n upgradeDom: function(optJsClass, optCssClass) {},\r\n /**\r\n * Upgrades a specific element rather than all in the DOM.\r\n *\r\n * @param {!Element} element The element we wish to upgrade.\r\n * @param {string=} optJsClass Optional name of the class we want to upgrade\r\n * the element to.\r\n */\r\n upgradeElement: function(element, optJsClass) {},\r\n /**\r\n * Upgrades a specific list of elements rather than all in the DOM.\r\n *\r\n * @param {!Element|!Array|!NodeList|!HTMLCollection} elements\r\n * The elements we wish to upgrade.\r\n */\r\n upgradeElements: function(elements) {},\r\n /**\r\n * Upgrades all registered components found in the current DOM. This is\r\n * automatically called on window load.\r\n */\r\n upgradeAllRegistered: function() {},\r\n /**\r\n * Allows user to be alerted to any upgrades that are performed for a given\r\n * component type\r\n *\r\n * @param {string} jsClass The class name of the MDL component we wish\r\n * to hook into for any upgrades performed.\r\n * @param {function(!HTMLElement)} callback The function to call upon an\r\n * upgrade. This function should expect 1 parameter - the HTMLElement which\r\n * got upgraded.\r\n */\r\n registerUpgradedCallback: function(jsClass, callback) {},\r\n /**\r\n * Registers a class for future use and attempts to upgrade existing DOM.\r\n *\r\n * @param {componentHandler.ComponentConfigPublic} config the registration configuration\r\n */\r\n register: function(config) {},\r\n /**\r\n * Downgrade either a given node, an array of nodes, or a NodeList.\r\n *\r\n * @param {!Node|!Array|!NodeList} nodes\r\n */\r\n downgradeElements: function(nodes) {}\r\n};\r\n\r\ncomponentHandler = (function() {\r\n 'use strict';\r\n\r\n /** @type {!Array} */\r\n var registeredComponents_ = [];\r\n\r\n /** @type {!Array} */\r\n var createdComponents_ = [];\r\n\r\n var componentConfigProperty_ = 'mdlComponentConfigInternal_';\r\n\r\n /**\r\n * Searches registered components for a class we are interested in using.\r\n * Optionally replaces a match with passed object if specified.\r\n *\r\n * @param {string} name The name of a class we want to use.\r\n * @param {componentHandler.ComponentConfig=} optReplace Optional object to replace match with.\r\n * @return {!Object|boolean}\r\n * @private\r\n */\r\n function findRegisteredClass_(name, optReplace) {\r\n for (var i = 0; i < registeredComponents_.length; i++) {\r\n if (registeredComponents_[i].className === name) {\r\n if (typeof optReplace !== 'undefined') {\r\n registeredComponents_[i] = optReplace;\r\n }\r\n return registeredComponents_[i];\r\n }\r\n }\r\n return false;\r\n }\r\n\r\n /**\r\n * Returns an array of the classNames of the upgraded classes on the element.\r\n *\r\n * @param {!Element} element The element to fetch data from.\r\n * @return {!Array}\r\n * @private\r\n */\r\n function getUpgradedListOfElement_(element) {\r\n var dataUpgraded = element.getAttribute('data-upgraded');\r\n // Use `['']` as default value to conform the `,name,name...` style.\r\n return dataUpgraded === null ? [''] : dataUpgraded.split(',');\r\n }\r\n\r\n /**\r\n * Returns true if the given element has already been upgraded for the given\r\n * class.\r\n *\r\n * @param {!Element} element The element we want to check.\r\n * @param {string} jsClass The class to check for.\r\n * @returns {boolean}\r\n * @private\r\n */\r\n function isElementUpgraded_(element, jsClass) {\r\n var upgradedList = getUpgradedListOfElement_(element);\r\n return upgradedList.indexOf(jsClass) !== -1;\r\n }\r\n\r\n /**\r\n * Create an event object.\r\n *\r\n * @param {string} eventType The type name of the event.\r\n * @param {boolean} bubbles Whether the event should bubble up the DOM.\r\n * @param {boolean} cancelable Whether the event can be canceled.\r\n * @returns {!Event}\r\n */\r\n function createEvent_(eventType, bubbles, cancelable) {\r\n if ('CustomEvent' in window && typeof window.CustomEvent === 'function') {\r\n return new CustomEvent(eventType, {\r\n bubbles: bubbles,\r\n cancelable: cancelable\r\n });\r\n } else {\r\n var ev = document.createEvent('Events');\r\n ev.initEvent(eventType, bubbles, cancelable);\r\n return ev;\r\n }\r\n }\r\n\r\n /**\r\n * Searches existing DOM for elements of our component type and upgrades them\r\n * if they have not already been upgraded.\r\n *\r\n * @param {string=} optJsClass the programatic name of the element class we\r\n * need to create a new instance of.\r\n * @param {string=} optCssClass the name of the CSS class elements of this\r\n * type will have.\r\n */\r\n function upgradeDomInternal(optJsClass, optCssClass) {\r\n if (typeof optJsClass === 'undefined' &&\r\n typeof optCssClass === 'undefined') {\r\n for (var i = 0; i < registeredComponents_.length; i++) {\r\n upgradeDomInternal(registeredComponents_[i].className,\r\n registeredComponents_[i].cssClass);\r\n }\r\n } else {\r\n var jsClass = /** @type {string} */ (optJsClass);\r\n if (typeof optCssClass === 'undefined') {\r\n var registeredClass = findRegisteredClass_(jsClass);\r\n if (registeredClass) {\r\n optCssClass = registeredClass.cssClass;\r\n }\r\n }\r\n\r\n var elements = document.querySelectorAll('.' + optCssClass);\r\n for (var n = 0; n < elements.length; n++) {\r\n upgradeElementInternal(elements[n], jsClass);\r\n }\r\n }\r\n }\r\n\r\n /**\r\n * Upgrades a specific element rather than all in the DOM.\r\n *\r\n * @param {!Element} element The element we wish to upgrade.\r\n * @param {string=} optJsClass Optional name of the class we want to upgrade\r\n * the element to.\r\n */\r\n function upgradeElementInternal(element, optJsClass) {\r\n // Verify argument type.\r\n if (!(typeof element === 'object' && element instanceof Element)) {\r\n throw new Error('Invalid argument provided to upgrade MDL element.');\r\n }\r\n // Allow upgrade to be canceled by canceling emitted event.\r\n var upgradingEv = createEvent_('mdl-componentupgrading', true, true);\r\n element.dispatchEvent(upgradingEv);\r\n if (upgradingEv.defaultPrevented) {\r\n return;\r\n }\r\n\r\n var upgradedList = getUpgradedListOfElement_(element);\r\n var classesToUpgrade = [];\r\n // If jsClass is not provided scan the registered components to find the\r\n // ones matching the element's CSS classList.\r\n if (!optJsClass) {\r\n var classList = element.classList;\r\n registeredComponents_.forEach(function(component) {\r\n // Match CSS & Not to be upgraded & Not upgraded.\r\n if (classList.contains(component.cssClass) &&\r\n classesToUpgrade.indexOf(component) === -1 &&\r\n !isElementUpgraded_(element, component.className)) {\r\n classesToUpgrade.push(component);\r\n }\r\n });\r\n } else if (!isElementUpgraded_(element, optJsClass)) {\r\n classesToUpgrade.push(findRegisteredClass_(optJsClass));\r\n }\r\n\r\n // Upgrade the element for each classes.\r\n for (var i = 0, n = classesToUpgrade.length, registeredClass; i < n; i++) {\r\n registeredClass = classesToUpgrade[i];\r\n if (registeredClass) {\r\n // Mark element as upgraded.\r\n upgradedList.push(registeredClass.className);\r\n element.setAttribute('data-upgraded', upgradedList.join(','));\r\n var instance = new registeredClass.classConstructor(element);\r\n instance[componentConfigProperty_] = registeredClass;\r\n createdComponents_.push(instance);\r\n // Call any callbacks the user has registered with this component type.\r\n for (var j = 0, m = registeredClass.callbacks.length; j < m; j++) {\r\n registeredClass.callbacks[j](element);\r\n }\r\n\r\n if (registeredClass.widget) {\r\n // Assign per element instance for control over API\r\n element[registeredClass.className] = instance;\r\n }\r\n } else {\r\n throw new Error(\r\n 'Unable to find a registered component for the given class.');\r\n }\r\n\r\n var upgradedEv = createEvent_('mdl-componentupgraded', true, false);\r\n element.dispatchEvent(upgradedEv);\r\n }\r\n }\r\n\r\n /**\r\n * Upgrades a specific list of elements rather than all in the DOM.\r\n *\r\n * @param {!Element|!Array|!NodeList|!HTMLCollection} elements\r\n * The elements we wish to upgrade.\r\n */\r\n function upgradeElementsInternal(elements) {\r\n if (!Array.isArray(elements)) {\r\n if (elements instanceof Element) {\r\n elements = [elements];\r\n } else {\r\n elements = Array.prototype.slice.call(elements);\r\n }\r\n }\r\n for (var i = 0, n = elements.length, element; i < n; i++) {\r\n element = elements[i];\r\n if (element instanceof HTMLElement) {\r\n upgradeElementInternal(element);\r\n if (element.children.length > 0) {\r\n upgradeElementsInternal(element.children);\r\n }\r\n }\r\n }\r\n }\r\n\r\n /**\r\n * Registers a class for future use and attempts to upgrade existing DOM.\r\n *\r\n * @param {componentHandler.ComponentConfigPublic} config\r\n */\r\n function registerInternal(config) {\r\n // In order to support both Closure-compiled and uncompiled code accessing\r\n // this method, we need to allow for both the dot and array syntax for\r\n // property access. You'll therefore see the `foo.bar || foo['bar']`\r\n // pattern repeated across this method.\r\n var widgetMissing = (typeof config.widget === 'undefined' &&\r\n typeof config['widget'] === 'undefined');\r\n var widget = true;\r\n\r\n if (!widgetMissing) {\r\n widget = config.widget || config['widget'];\r\n }\r\n\r\n var newConfig = /** @type {componentHandler.ComponentConfig} */ ({\r\n classConstructor: config.constructor || config['constructor'],\r\n className: config.classAsString || config['classAsString'],\r\n cssClass: config.cssClass || config['cssClass'],\r\n widget: widget,\r\n callbacks: []\r\n });\r\n\r\n registeredComponents_.forEach(function(item) {\r\n if (item.cssClass === newConfig.cssClass) {\r\n throw new Error('The provided cssClass has already been registered: ' + item.cssClass);\r\n }\r\n if (item.className === newConfig.className) {\r\n throw new Error('The provided className has already been registered');\r\n }\r\n });\r\n\r\n if (config.constructor.prototype\r\n .hasOwnProperty(componentConfigProperty_)) {\r\n throw new Error(\r\n 'MDL component classes must not have ' + componentConfigProperty_ +\r\n ' defined as a property.');\r\n }\r\n\r\n var found = findRegisteredClass_(config.classAsString, newConfig);\r\n\r\n if (!found) {\r\n registeredComponents_.push(newConfig);\r\n }\r\n }\r\n\r\n /**\r\n * Allows user to be alerted to any upgrades that are performed for a given\r\n * component type\r\n *\r\n * @param {string} jsClass The class name of the MDL component we wish\r\n * to hook into for any upgrades performed.\r\n * @param {function(!HTMLElement)} callback The function to call upon an\r\n * upgrade. This function should expect 1 parameter - the HTMLElement which\r\n * got upgraded.\r\n */\r\n function registerUpgradedCallbackInternal(jsClass, callback) {\r\n var regClass = findRegisteredClass_(jsClass);\r\n if (regClass) {\r\n regClass.callbacks.push(callback);\r\n }\r\n }\r\n\r\n /**\r\n * Upgrades all registered components found in the current DOM. This is\r\n * automatically called on window load.\r\n */\r\n function upgradeAllRegisteredInternal() {\r\n for (var n = 0; n < registeredComponents_.length; n++) {\r\n upgradeDomInternal(registeredComponents_[n].className);\r\n }\r\n }\r\n\r\n /**\r\n * Check the component for the downgrade method.\r\n * Execute if found.\r\n * Remove component from createdComponents list.\r\n *\r\n * @param {?componentHandler.Component} component\r\n */\r\n function deconstructComponentInternal(component) {\r\n if (component) {\r\n var componentIndex = createdComponents_.indexOf(component);\r\n createdComponents_.splice(componentIndex, 1);\r\n\r\n var upgrades = component.element_.getAttribute('data-upgraded').split(',');\r\n var componentPlace = upgrades.indexOf(component[componentConfigProperty_].classAsString);\r\n upgrades.splice(componentPlace, 1);\r\n component.element_.setAttribute('data-upgraded', upgrades.join(','));\r\n\r\n var ev = createEvent_('mdl-componentdowngraded', true, false);\r\n component.element_.dispatchEvent(ev);\r\n }\r\n }\r\n\r\n /**\r\n * Downgrade either a given node, an array of nodes, or a NodeList.\r\n *\r\n * @param {!Node|!Array|!NodeList} nodes\r\n */\r\n function downgradeNodesInternal(nodes) {\r\n /**\r\n * Auxiliary function to downgrade a single node.\r\n * @param {!Node} node the node to be downgraded\r\n */\r\n var downgradeNode = function(node) {\r\n createdComponents_.filter(function(item) {\r\n return item.element_ === node;\r\n }).forEach(deconstructComponentInternal);\r\n };\r\n if (nodes instanceof Array || nodes instanceof NodeList) {\r\n for (var n = 0; n < nodes.length; n++) {\r\n downgradeNode(nodes[n]);\r\n }\r\n } else if (nodes instanceof Node) {\r\n downgradeNode(nodes);\r\n } else {\r\n throw new Error('Invalid argument provided to downgrade MDL nodes.');\r\n }\r\n }\r\n\r\n // Now return the functions that should be made public with their publicly\r\n // facing names...\r\n return {\r\n upgradeDom: upgradeDomInternal,\r\n upgradeElement: upgradeElementInternal,\r\n upgradeElements: upgradeElementsInternal,\r\n upgradeAllRegistered: upgradeAllRegisteredInternal,\r\n registerUpgradedCallback: registerUpgradedCallbackInternal,\r\n register: registerInternal,\r\n downgradeElements: downgradeNodesInternal\r\n };\r\n})();\r\n\r\n/**\r\n * Describes the type of a registered component type managed by\r\n * componentHandler. Provided for benefit of the Closure compiler.\r\n *\r\n * @typedef {{\r\n * constructor: Function,\r\n * classAsString: string,\r\n * cssClass: string,\r\n * widget: (string|boolean|undefined)\r\n * }}\r\n */\r\ncomponentHandler.ComponentConfigPublic; // jshint ignore:line\r\n\r\n/**\r\n * Describes the type of a registered component type managed by\r\n * componentHandler. Provided for benefit of the Closure compiler.\r\n *\r\n * @typedef {{\r\n * constructor: !Function,\r\n * className: string,\r\n * cssClass: string,\r\n * widget: (string|boolean),\r\n * callbacks: !Array\r\n * }}\r\n */\r\ncomponentHandler.ComponentConfig; // jshint ignore:line\r\n\r\n/**\r\n * Created component (i.e., upgraded element) type as managed by\r\n * componentHandler. Provided for benefit of the Closure compiler.\r\n *\r\n * @typedef {{\r\n * element_: !HTMLElement,\r\n * className: string,\r\n * classAsString: string,\r\n * cssClass: string,\r\n * widget: string\r\n * }}\r\n */\r\ncomponentHandler.Component; // jshint ignore:line\r\n\r\n// Export all symbols, for the benefit of Closure compiler.\r\n// No effect on uncompiled code.\r\ncomponentHandler['upgradeDom'] = componentHandler.upgradeDom;\r\ncomponentHandler['upgradeElement'] = componentHandler.upgradeElement;\r\ncomponentHandler['upgradeElements'] = componentHandler.upgradeElements;\r\ncomponentHandler['upgradeAllRegistered'] =\r\n componentHandler.upgradeAllRegistered;\r\ncomponentHandler['registerUpgradedCallback'] =\r\n componentHandler.registerUpgradedCallback;\r\ncomponentHandler['register'] = componentHandler.register;\r\ncomponentHandler['downgradeElements'] = componentHandler.downgradeElements;\r\nwindow.componentHandler = componentHandler;\r\nwindow['componentHandler'] = componentHandler;\r\n\r\nwindow.addEventListener('load', function() {\r\n 'use strict';\r\n\r\n /**\r\n * Performs a \"Cutting the mustard\" test. If the browser supports the features\r\n * tested, adds a mdl-js class to the element. It then upgrades all MDL\r\n * components requiring JavaScript.\r\n */\r\n if ('classList' in document.createElement('div') &&\r\n 'querySelector' in document &&\r\n 'addEventListener' in window && Array.prototype.forEach) {\r\n document.documentElement.classList.add('mdl-js');\r\n componentHandler.upgradeAllRegistered();\r\n } else {\r\n /**\r\n * Dummy function to avoid JS errors.\r\n */\r\n componentHandler.upgradeElement = function() {};\r\n /**\r\n * Dummy function to avoid JS errors.\r\n */\r\n componentHandler.register = function() {};\r\n }\r\n});\r\n","// Source: https://github.com/darius/requestAnimationFrame/blob/master/requestAnimationFrame.js\n// Adapted from https://gist.github.com/paulirish/1579671 which derived from\n// http://paulirish.com/2011/requestanimationframe-for-smart-animating/\n// http://my.opera.com/emoller/blog/2011/12/20/requestanimationframe-for-smart-er-animating\n// requestAnimationFrame polyfill by Erik Möller.\n// Fixes from Paul Irish, Tino Zijdel, Andrew Mao, Klemen Slavič, Darius Bacon\n// MIT license\nif (!Date.now) {\n /**\r\n * Date.now polyfill.\r\n * @return {number} the current Date\r\n */\n Date.now = function () {\n return new Date().getTime();\n };\n Date['now'] = Date.now;\n}\nvar vendors = [\n 'webkit',\n 'moz'\n];\nfor (var i = 0; i < vendors.length && !window.requestAnimationFrame; ++i) {\n var vp = vendors[i];\n window.requestAnimationFrame = window[vp + 'RequestAnimationFrame'];\n window.cancelAnimationFrame = window[vp + 'CancelAnimationFrame'] || window[vp + 'CancelRequestAnimationFrame'];\n window['requestAnimationFrame'] = window.requestAnimationFrame;\n window['cancelAnimationFrame'] = window.cancelAnimationFrame;\n}\nif (/iP(ad|hone|od).*OS 6/.test(window.navigator.userAgent) || !window.requestAnimationFrame || !window.cancelAnimationFrame) {\n var lastTime = 0;\n /**\r\n * requestAnimationFrame polyfill.\r\n * @param {!Function} callback the callback function.\r\n */\n window.requestAnimationFrame = function (callback) {\n var now = Date.now();\n var nextTime = Math.max(lastTime + 16, now);\n return setTimeout(function () {\n callback(lastTime = nextTime);\n }, nextTime - now);\n };\n window.cancelAnimationFrame = clearTimeout;\n window['requestAnimationFrame'] = window.requestAnimationFrame;\n window['cancelAnimationFrame'] = window.cancelAnimationFrame;\n}","/**\r\n * @license\r\n * Copyright 2015 Google Inc. All Rights Reserved.\r\n *\r\n * Licensed under the Apache License, Version 2.0 (the \"License\");\r\n * you may not use this file except in compliance with the License.\r\n * You may obtain a copy of the License at\r\n *\r\n * http://www.apache.org/licenses/LICENSE-2.0\r\n *\r\n * Unless required by applicable law or agreed to in writing, software\r\n * distributed under the License is distributed on an \"AS IS\" BASIS,\r\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\r\n * See the License for the specific language governing permissions and\r\n * limitations under the License.\r\n */\n/**\r\n * Class constructor for Button MDL component.\r\n * Implements MDL component design pattern defined at:\r\n * https://github.com/jasonmayes/mdl-component-design-pattern\r\n *\r\n * @param {HTMLElement} element The element that will be upgraded.\r\n */\nvar MaterialButton = function MaterialButton(element) {\n this.element_ = element;\n // Initialize instance.\n this.init();\n};\nwindow['MaterialButton'] = MaterialButton;\n/**\r\n * Store constants in one place so they can be updated easily.\r\n *\r\n * @enum {string | number}\r\n * @private\r\n */\nMaterialButton.prototype.Constant_ = {};\n/**\r\n * Store strings for class names defined by this component that are used in\r\n * JavaScript. This allows us to simply change it in one place should we\r\n * decide to modify at a later date.\r\n *\r\n * @enum {string}\r\n * @private\r\n */\nMaterialButton.prototype.CssClasses_ = {\n RIPPLE_EFFECT: 'mdl-js-ripple-effect',\n RIPPLE_CONTAINER: 'mdl-button__ripple-container',\n RIPPLE: 'mdl-ripple'\n};\n/**\r\n * Handle blur of element.\r\n *\r\n * @param {Event} event The event that fired.\r\n * @private\r\n */\nMaterialButton.prototype.blurHandler_ = function (event) {\n if (event) {\n this.element_.blur();\n }\n};\n// Public methods.\n/**\r\n * Disable button.\r\n *\r\n * @public\r\n */\nMaterialButton.prototype.disable = function () {\n this.element_.disabled = true;\n};\nMaterialButton.prototype['disable'] = MaterialButton.prototype.disable;\n/**\r\n * Enable button.\r\n *\r\n * @public\r\n */\nMaterialButton.prototype.enable = function () {\n this.element_.disabled = false;\n};\nMaterialButton.prototype['enable'] = MaterialButton.prototype.enable;\n/**\r\n * Initialize element.\r\n */\nMaterialButton.prototype.init = function () {\n if (this.element_) {\n if (this.element_.classList.contains(this.CssClasses_.RIPPLE_EFFECT)) {\n var rippleContainer = document.createElement('span');\n rippleContainer.classList.add(this.CssClasses_.RIPPLE_CONTAINER);\n this.rippleElement_ = document.createElement('span');\n this.rippleElement_.classList.add(this.CssClasses_.RIPPLE);\n rippleContainer.appendChild(this.rippleElement_);\n this.boundRippleBlurHandler = this.blurHandler_.bind(this);\n this.rippleElement_.addEventListener('mouseup', this.boundRippleBlurHandler);\n this.element_.appendChild(rippleContainer);\n }\n this.boundButtonBlurHandler = this.blurHandler_.bind(this);\n this.element_.addEventListener('mouseup', this.boundButtonBlurHandler);\n this.element_.addEventListener('mouseleave', this.boundButtonBlurHandler);\n }\n};\n// The component registers itself. It can assume componentHandler is available\n// in the global scope.\ncomponentHandler.register({\n constructor: MaterialButton,\n classAsString: 'MaterialButton',\n cssClass: 'mdl-js-button',\n widget: true\n});","/**\r\n * @license\r\n * Copyright 2015 Google Inc. All Rights Reserved.\r\n *\r\n * Licensed under the Apache License, Version 2.0 (the \"License\");\r\n * you may not use this file except in compliance with the License.\r\n * You may obtain a copy of the License at\r\n *\r\n * http://www.apache.org/licenses/LICENSE-2.0\r\n *\r\n * Unless required by applicable law or agreed to in writing, software\r\n * distributed under the License is distributed on an \"AS IS\" BASIS,\r\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\r\n * See the License for the specific language governing permissions and\r\n * limitations under the License.\r\n */\n/**\r\n * Class constructor for Checkbox MDL component.\r\n * Implements MDL component design pattern defined at:\r\n * https://github.com/jasonmayes/mdl-component-design-pattern\r\n *\r\n * @constructor\r\n * @param {HTMLElement} element The element that will be upgraded.\r\n */\nvar MaterialCheckbox = function MaterialCheckbox(element) {\n this.element_ = element;\n // Initialize instance.\n this.init();\n};\nwindow['MaterialCheckbox'] = MaterialCheckbox;\n/**\r\n * Store constants in one place so they can be updated easily.\r\n *\r\n * @enum {string | number}\r\n * @private\r\n */\nMaterialCheckbox.prototype.Constant_ = { TINY_TIMEOUT: 0.001 };\n/**\r\n * Store strings for class names defined by this component that are used in\r\n * JavaScript. This allows us to simply change it in one place should we\r\n * decide to modify at a later date.\r\n *\r\n * @enum {string}\r\n * @private\r\n */\nMaterialCheckbox.prototype.CssClasses_ = {\n INPUT: 'mdl-checkbox__input',\n BOX_OUTLINE: 'mdl-checkbox__box-outline',\n FOCUS_HELPER: 'mdl-checkbox__focus-helper',\n TICK_OUTLINE: 'mdl-checkbox__tick-outline',\n RIPPLE_EFFECT: 'mdl-js-ripple-effect',\n RIPPLE_IGNORE_EVENTS: 'mdl-js-ripple-effect--ignore-events',\n RIPPLE_CONTAINER: 'mdl-checkbox__ripple-container',\n RIPPLE_CENTER: 'mdl-ripple--center',\n RIPPLE: 'mdl-ripple',\n IS_FOCUSED: 'is-focused',\n IS_DISABLED: 'is-disabled',\n IS_CHECKED: 'is-checked',\n IS_UPGRADED: 'is-upgraded'\n};\n/**\r\n * Handle change of state.\r\n *\r\n * @param {Event} event The event that fired.\r\n * @private\r\n */\nMaterialCheckbox.prototype.onChange_ = function (event) {\n this.updateClasses_();\n};\n/**\r\n * Handle focus of element.\r\n *\r\n * @param {Event} event The event that fired.\r\n * @private\r\n */\nMaterialCheckbox.prototype.onFocus_ = function (event) {\n this.element_.classList.add(this.CssClasses_.IS_FOCUSED);\n};\n/**\r\n * Handle lost focus of element.\r\n *\r\n * @param {Event} event The event that fired.\r\n * @private\r\n */\nMaterialCheckbox.prototype.onBlur_ = function (event) {\n this.element_.classList.remove(this.CssClasses_.IS_FOCUSED);\n};\n/**\r\n * Handle mouseup.\r\n *\r\n * @param {Event} event The event that fired.\r\n * @private\r\n */\nMaterialCheckbox.prototype.onMouseUp_ = function (event) {\n this.blur_();\n};\n/**\r\n * Handle class updates.\r\n *\r\n * @private\r\n */\nMaterialCheckbox.prototype.updateClasses_ = function () {\n this.checkDisabled();\n this.checkToggleState();\n};\n/**\r\n * Add blur.\r\n *\r\n * @private\r\n */\nMaterialCheckbox.prototype.blur_ = function () {\n // TODO: figure out why there's a focus event being fired after our blur,\n // so that we can avoid this hack.\n window.setTimeout(function () {\n this.inputElement_.blur();\n }.bind(this), this.Constant_.TINY_TIMEOUT);\n};\n// Public methods.\n/**\r\n * Check the inputs toggle state and update display.\r\n *\r\n * @public\r\n */\nMaterialCheckbox.prototype.checkToggleState = function () {\n if (this.inputElement_.checked) {\n this.element_.classList.add(this.CssClasses_.IS_CHECKED);\n } else {\n this.element_.classList.remove(this.CssClasses_.IS_CHECKED);\n }\n};\nMaterialCheckbox.prototype['checkToggleState'] = MaterialCheckbox.prototype.checkToggleState;\n/**\r\n * Check the inputs disabled state and update display.\r\n *\r\n * @public\r\n */\nMaterialCheckbox.prototype.checkDisabled = function () {\n if (this.inputElement_.disabled) {\n this.element_.classList.add(this.CssClasses_.IS_DISABLED);\n } else {\n this.element_.classList.remove(this.CssClasses_.IS_DISABLED);\n }\n};\nMaterialCheckbox.prototype['checkDisabled'] = MaterialCheckbox.prototype.checkDisabled;\n/**\r\n * Disable checkbox.\r\n *\r\n * @public\r\n */\nMaterialCheckbox.prototype.disable = function () {\n this.inputElement_.disabled = true;\n this.updateClasses_();\n};\nMaterialCheckbox.prototype['disable'] = MaterialCheckbox.prototype.disable;\n/**\r\n * Enable checkbox.\r\n *\r\n * @public\r\n */\nMaterialCheckbox.prototype.enable = function () {\n this.inputElement_.disabled = false;\n this.updateClasses_();\n};\nMaterialCheckbox.prototype['enable'] = MaterialCheckbox.prototype.enable;\n/**\r\n * Check checkbox.\r\n *\r\n * @public\r\n */\nMaterialCheckbox.prototype.check = function () {\n this.inputElement_.checked = true;\n this.updateClasses_();\n};\nMaterialCheckbox.prototype['check'] = MaterialCheckbox.prototype.check;\n/**\r\n * Uncheck checkbox.\r\n *\r\n * @public\r\n */\nMaterialCheckbox.prototype.uncheck = function () {\n this.inputElement_.checked = false;\n this.updateClasses_();\n};\nMaterialCheckbox.prototype['uncheck'] = MaterialCheckbox.prototype.uncheck;\n/**\r\n * Initialize element.\r\n */\nMaterialCheckbox.prototype.init = function () {\n if (this.element_) {\n this.inputElement_ = this.element_.querySelector('.' + this.CssClasses_.INPUT);\n var boxOutline = document.createElement('span');\n boxOutline.classList.add(this.CssClasses_.BOX_OUTLINE);\n var tickContainer = document.createElement('span');\n tickContainer.classList.add(this.CssClasses_.FOCUS_HELPER);\n var tickOutline = document.createElement('span');\n tickOutline.classList.add(this.CssClasses_.TICK_OUTLINE);\n boxOutline.appendChild(tickOutline);\n this.element_.appendChild(tickContainer);\n this.element_.appendChild(boxOutline);\n if (this.element_.classList.contains(this.CssClasses_.RIPPLE_EFFECT)) {\n this.element_.classList.add(this.CssClasses_.RIPPLE_IGNORE_EVENTS);\n this.rippleContainerElement_ = document.createElement('span');\n this.rippleContainerElement_.classList.add(this.CssClasses_.RIPPLE_CONTAINER);\n this.rippleContainerElement_.classList.add(this.CssClasses_.RIPPLE_EFFECT);\n this.rippleContainerElement_.classList.add(this.CssClasses_.RIPPLE_CENTER);\n this.boundRippleMouseUp = this.onMouseUp_.bind(this);\n this.rippleContainerElement_.addEventListener('mouseup', this.boundRippleMouseUp);\n var ripple = document.createElement('span');\n ripple.classList.add(this.CssClasses_.RIPPLE);\n this.rippleContainerElement_.appendChild(ripple);\n this.element_.appendChild(this.rippleContainerElement_);\n }\n this.boundInputOnChange = this.onChange_.bind(this);\n this.boundInputOnFocus = this.onFocus_.bind(this);\n this.boundInputOnBlur = this.onBlur_.bind(this);\n this.boundElementMouseUp = this.onMouseUp_.bind(this);\n this.inputElement_.addEventListener('change', this.boundInputOnChange);\n this.inputElement_.addEventListener('focus', this.boundInputOnFocus);\n this.inputElement_.addEventListener('blur', this.boundInputOnBlur);\n this.element_.addEventListener('mouseup', this.boundElementMouseUp);\n this.updateClasses_();\n this.element_.classList.add(this.CssClasses_.IS_UPGRADED);\n }\n};\n// The component registers itself. It can assume componentHandler is available\n// in the global scope.\ncomponentHandler.register({\n constructor: MaterialCheckbox,\n classAsString: 'MaterialCheckbox',\n cssClass: 'mdl-js-checkbox',\n widget: true\n});","/**\r\n * @license\r\n * Copyright 2015 Google Inc. All Rights Reserved.\r\n *\r\n * Licensed under the Apache License, Version 2.0 (the \"License\");\r\n * you may not use this file except in compliance with the License.\r\n * You may obtain a copy of the License at\r\n *\r\n * http://www.apache.org/licenses/LICENSE-2.0\r\n *\r\n * Unless required by applicable law or agreed to in writing, software\r\n * distributed under the License is distributed on an \"AS IS\" BASIS,\r\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\r\n * See the License for the specific language governing permissions and\r\n * limitations under the License.\r\n */\n/**\r\n * Class constructor for dropdown MDL component.\r\n * Implements MDL component design pattern defined at:\r\n * https://github.com/jasonmayes/mdl-component-design-pattern\r\n *\r\n * @constructor\r\n * @param {HTMLElement} element The element that will be upgraded.\r\n */\nvar MaterialMenu = function MaterialMenu(element) {\n this.element_ = element;\n // Initialize instance.\n this.init();\n};\nwindow['MaterialMenu'] = MaterialMenu;\n/**\r\n * Store constants in one place so they can be updated easily.\r\n *\r\n * @enum {string | number}\r\n * @private\r\n */\nMaterialMenu.prototype.Constant_ = {\n // Total duration of the menu animation.\n TRANSITION_DURATION_SECONDS: 0.3,\n // The fraction of the total duration we want to use for menu item animations.\n TRANSITION_DURATION_FRACTION: 0.8,\n // How long the menu stays open after choosing an option (so the user can see\n // the ripple).\n CLOSE_TIMEOUT: 150\n};\n/**\r\n * Keycodes, for code readability.\r\n *\r\n * @enum {number}\r\n * @private\r\n */\nMaterialMenu.prototype.Keycodes_ = {\n ENTER: 13,\n ESCAPE: 27,\n SPACE: 32,\n UP_ARROW: 38,\n DOWN_ARROW: 40\n};\n/**\r\n * Store strings for class names defined by this component that are used in\r\n * JavaScript. This allows us to simply change it in one place should we\r\n * decide to modify at a later date.\r\n *\r\n * @enum {string}\r\n * @private\r\n */\nMaterialMenu.prototype.CssClasses_ = {\n CONTAINER: 'mdl-menu__container',\n OUTLINE: 'mdl-menu__outline',\n ITEM: 'mdl-menu__item',\n ITEM_RIPPLE_CONTAINER: 'mdl-menu__item-ripple-container',\n RIPPLE_EFFECT: 'mdl-js-ripple-effect',\n RIPPLE_IGNORE_EVENTS: 'mdl-js-ripple-effect--ignore-events',\n RIPPLE: 'mdl-ripple',\n // Statuses\n IS_UPGRADED: 'is-upgraded',\n IS_VISIBLE: 'is-visible',\n IS_ANIMATING: 'is-animating',\n // Alignment options\n BOTTOM_LEFT: 'mdl-menu--bottom-left',\n // This is the default.\n BOTTOM_RIGHT: 'mdl-menu--bottom-right',\n TOP_LEFT: 'mdl-menu--top-left',\n TOP_RIGHT: 'mdl-menu--top-right',\n UNALIGNED: 'mdl-menu--unaligned'\n};\n/**\r\n * Initialize element.\r\n */\nMaterialMenu.prototype.init = function () {\n if (this.element_) {\n // Patch by Corigo beginning.\n var dataset = this.element_.dataset;\n if ('visibleItems' in dataset) {\n this.visibleItems_ = !isNaN(dataset.visibleItems) ? dataset.visibleItems : 1;\n }\n if ('postUrl' in dataset) {\n this.postUrl_ = dataset.postUrl;\n }\n if ('itemClickHandler' in dataset) {\n this.itemClickHandler_ = dataset.itemClickHandler;\n }\n // Patch end.\n // Create container for the menu.\n var container = document.createElement('div');\n container.classList.add(this.CssClasses_.CONTAINER);\n this.element_.parentElement.insertBefore(container, this.element_);\n this.element_.parentElement.removeChild(this.element_);\n container.appendChild(this.element_);\n // Patch by Corrigo beginning.\n var items = this.element_.querySelectorAll('.' + this.CssClasses_.ITEM);\n if (this.visibleItems_ < items.length) {\n var width = this.element_.getBoundingClientRect().width, firstItem = this.element_.querySelector('.' + this.CssClasses_.ITEM), containerClone = container.cloneNode(true);\n containerClone.style.visibility = 'visible';\n containerClone.style.overflowY = 'scroll';\n containerClone.style.width = width + 'px';\n containerClone.style.height = firstItem ? firstItem.offsetHeight + 'px' : '0px';\n document.body.appendChild(containerClone);\n var scrollbarWidth = containerClone.offsetWidth - containerClone.clientWidth;\n containerClone.parentNode.removeChild(containerClone);\n container.style.width = width + scrollbarWidth + 'px';\n } else {\n container.style.width = this.element_.getBoundingClientRect().width + 'px';\n }\n container.style.overflowX = 'hidden';\n // Patch end.\n this.container_ = container;\n // Create outline for the menu (shadow and background).\n var outline = document.createElement('div');\n outline.classList.add(this.CssClasses_.OUTLINE);\n this.outline_ = outline;\n container.insertBefore(outline, this.element_);\n // Find the \"for\" element and bind events to it.\n var forElId = this.element_.getAttribute('for') || this.element_.getAttribute('data-mdl-for');\n var forEl = null;\n if (forElId) {\n forEl = document.getElementById(forElId);\n if (forEl) {\n this.forElement_ = forEl;\n forEl.addEventListener('click', this.handleForClick_.bind(this));\n forEl.addEventListener('keydown', this.handleForKeyboardEvent_.bind(this));\n }\n }\n var items = this.element_.querySelectorAll('.' + this.CssClasses_.ITEM);\n this.boundItemKeydown_ = this.handleItemKeyboardEvent_.bind(this);\n // Patch by Corrigo beginning.\n this.boundItemClick_ = this.itemClickHandler_ ? window[this.itemClickHandler_].bind(this) : this.handleItemClick_.bind(this);\n // Patch end.\n for (var i = 0; i < items.length; i++) {\n // Add a listener to each menu item.\n items[i].addEventListener('click', this.boundItemClick_);\n // Add a tab index to each menu item.\n items[i].tabIndex = '-1';\n // Add a keyboard listener to each menu item.\n items[i].addEventListener('keydown', this.boundItemKeydown_);\n }\n // Add ripple classes to each item, if the user has enabled ripples.\n if (this.element_.classList.contains(this.CssClasses_.RIPPLE_EFFECT)) {\n this.element_.classList.add(this.CssClasses_.RIPPLE_IGNORE_EVENTS);\n for (i = 0; i < items.length; i++) {\n var item = items[i];\n var rippleContainer = document.createElement('span');\n rippleContainer.classList.add(this.CssClasses_.ITEM_RIPPLE_CONTAINER);\n var ripple = document.createElement('span');\n ripple.classList.add(this.CssClasses_.RIPPLE);\n rippleContainer.appendChild(ripple);\n item.appendChild(rippleContainer);\n item.classList.add(this.CssClasses_.RIPPLE_EFFECT);\n }\n }\n // Copy alignment classes to the container, so the outline can use them.\n if (this.element_.classList.contains(this.CssClasses_.BOTTOM_LEFT)) {\n this.outline_.classList.add(this.CssClasses_.BOTTOM_LEFT);\n }\n if (this.element_.classList.contains(this.CssClasses_.BOTTOM_RIGHT)) {\n this.outline_.classList.add(this.CssClasses_.BOTTOM_RIGHT);\n }\n if (this.element_.classList.contains(this.CssClasses_.TOP_LEFT)) {\n this.outline_.classList.add(this.CssClasses_.TOP_LEFT);\n }\n if (this.element_.classList.contains(this.CssClasses_.TOP_RIGHT)) {\n this.outline_.classList.add(this.CssClasses_.TOP_RIGHT);\n }\n if (this.element_.classList.contains(this.CssClasses_.UNALIGNED)) {\n this.outline_.classList.add(this.CssClasses_.UNALIGNED);\n }\n container.classList.add(this.CssClasses_.IS_UPGRADED);\n }\n};\n/**\r\n * Handles a click on the \"for\" element, by positioning the menu and then\r\n * toggling it.\r\n *\r\n * @param {Event} evt The event that fired.\r\n * @private\r\n */\nMaterialMenu.prototype.handleForClick_ = function (evt) {\n if (this.element_ && this.forElement_) {\n var rect = this.forElement_.getBoundingClientRect();\n var forRect = this.forElement_.parentElement.getBoundingClientRect();\n // Patch by Corrigo beginning.\n var isButtonAbsolutelyPositioned = document.defaultView.getComputedStyle(this.forElement_).position === 'absolute';\n var buttonRight = document.defaultView.getComputedStyle(this.forElement_).right;\n if (this.element_.classList.contains(this.CssClasses_.UNALIGNED)) {\n } else if (this.element_.classList.contains(this.CssClasses_.BOTTOM_RIGHT)) {\n // Position below the \"for\" element, aligned to its right.\n // Patch by Corrigo beginning.\n this.container_.style.right = isButtonAbsolutelyPositioned ? buttonRight : forRect.right - rect.right + 'px';\n // Patch end.\n this.container_.style.top = this.forElement_.offsetTop + this.forElement_.offsetHeight + 'px';\n } else if (this.element_.classList.contains(this.CssClasses_.TOP_LEFT)) {\n // Position above the \"for\" element, aligned to its left.\n this.container_.style.left = this.forElement_.offsetLeft + 'px';\n this.container_.style.bottom = forRect.bottom - rect.top + 'px';\n } else if (this.element_.classList.contains(this.CssClasses_.TOP_RIGHT)) {\n // Position above the \"for\" element, aligned to its right.\n // Patch by Corrigo beginning.\n this.container_.style.right = isButtonAbsolutelyPositioned ? buttonRight : forRect.right - rect.right + 'px';\n // Patch end.\n this.container_.style.bottom = forRect.bottom - rect.top + 'px';\n } else {\n // Default: position below the \"for\" element, aligned to its left.\n this.container_.style.left = this.forElement_.offsetLeft + 'px';\n this.container_.style.top = this.forElement_.offsetTop + this.forElement_.offsetHeight + 'px';\n }\n }\n this.toggle(evt);\n};\n/**\r\n * Handles a keyboard event on the \"for\" element.\r\n *\r\n * @param {Event} evt The event that fired.\r\n * @private\r\n */\nMaterialMenu.prototype.handleForKeyboardEvent_ = function (evt) {\n if (this.element_ && this.container_ && this.forElement_) {\n var items = this.element_.querySelectorAll('.' + this.CssClasses_.ITEM + ':not([disabled])');\n if (items && items.length > 0 && this.container_.classList.contains(this.CssClasses_.IS_VISIBLE)) {\n if (evt.keyCode === this.Keycodes_.UP_ARROW) {\n evt.preventDefault();\n items[items.length - 1].focus();\n } else if (evt.keyCode === this.Keycodes_.DOWN_ARROW) {\n evt.preventDefault();\n items[0].focus();\n }\n }\n }\n};\n/**\r\n * Handles a keyboard event on an item.\r\n *\r\n * @param {Event} evt The event that fired.\r\n * @private\r\n */\nMaterialMenu.prototype.handleItemKeyboardEvent_ = function (evt) {\n if (this.element_ && this.container_) {\n var items = this.element_.querySelectorAll('.' + this.CssClasses_.ITEM + ':not([disabled])');\n if (items && items.length > 0 && this.container_.classList.contains(this.CssClasses_.IS_VISIBLE)) {\n var currentIndex = Array.prototype.slice.call(items).indexOf(evt.target);\n if (evt.keyCode === this.Keycodes_.UP_ARROW) {\n evt.preventDefault();\n if (currentIndex > 0) {\n items[currentIndex - 1].focus();\n } else {\n items[items.length - 1].focus();\n }\n } else if (evt.keyCode === this.Keycodes_.DOWN_ARROW) {\n evt.preventDefault();\n if (items.length > currentIndex + 1) {\n items[currentIndex + 1].focus();\n } else {\n items[0].focus();\n }\n } else if (evt.keyCode === this.Keycodes_.SPACE || evt.keyCode === this.Keycodes_.ENTER) {\n evt.preventDefault();\n // Send mousedown and mouseup to trigger ripple.\n var e = new MouseEvent('mousedown');\n evt.target.dispatchEvent(e);\n e = new MouseEvent('mouseup');\n evt.target.dispatchEvent(e);\n // Send click.\n evt.target.click();\n } else if (evt.keyCode === this.Keycodes_.ESCAPE) {\n evt.preventDefault();\n this.hide();\n }\n }\n }\n};\n/**\r\n * Handles a click event on an item.\r\n *\r\n * @param {Event} evt The event that fired.\r\n * @private\r\n */\nMaterialMenu.prototype.handleItemClick_ = function (evt) {\n if (evt.target.hasAttribute('disabled')) {\n evt.stopPropagation();\n } else {\n // Wait some time before closing menu, so the user can see the ripple.\n this.closing_ = true;\n window.setTimeout(function (evt) {\n this.hide();\n this.closing_ = false;\n }.bind(this), this.Constant_.CLOSE_TIMEOUT);\n }\n};\n/**\r\n * Calculates the initial clip (for opening the menu) or final clip (for closing\r\n * it), and applies it. This allows us to animate from or to the correct point,\r\n * that is, the point it's aligned to in the \"for\" element.\r\n *\r\n * @param {number} height Height of the clip rectangle\r\n * @param {number} width Width of the clip rectangle\r\n * @private\r\n */\nMaterialMenu.prototype.applyClip_ = function (height, width) {\n if (this.element_.classList.contains(this.CssClasses_.UNALIGNED)) {\n // Do not clip.\n this.element_.style.clip = '';\n } else if (this.element_.classList.contains(this.CssClasses_.BOTTOM_RIGHT)) {\n // Clip to the top right corner of the menu.\n this.element_.style.clip = 'rect(0 ' + width + 'px ' + '0 ' + width + 'px)';\n } else if (this.element_.classList.contains(this.CssClasses_.TOP_LEFT)) {\n // Clip to the bottom left corner of the menu.\n this.element_.style.clip = 'rect(' + height + 'px 0 ' + height + 'px 0)';\n } else if (this.element_.classList.contains(this.CssClasses_.TOP_RIGHT)) {\n // Clip to the bottom right corner of the menu.\n this.element_.style.clip = 'rect(' + height + 'px ' + width + 'px ' + height + 'px ' + width + 'px)';\n } else {\n // Default: do not clip (same as clipping to the top left corner).\n this.element_.style.clip = '';\n }\n};\n/**\r\n * Cleanup function to remove animation listeners.\r\n *\r\n * @param {Event} evt\r\n * @private\r\n */\nMaterialMenu.prototype.removeAnimationEndListener_ = function (evt) {\n evt.target.classList.remove(MaterialMenu.prototype.CssClasses_.IS_ANIMATING);\n};\n/**\r\n * Adds an event listener to clean up after the animation ends.\r\n *\r\n * @private\r\n */\nMaterialMenu.prototype.addAnimationEndListener_ = function () {\n this.element_.addEventListener('transitionend', this.removeAnimationEndListener_);\n this.element_.addEventListener('webkitTransitionEnd', this.removeAnimationEndListener_);\n};\n/**\r\n * Displays the menu.\r\n *\r\n * @public\r\n */\nMaterialMenu.prototype.show = function (evt) {\n if (this.element_ && this.container_ && this.outline_) {\n // Measure the inner element.\n var height = this.element_.getBoundingClientRect().height;\n var width = this.element_.getBoundingClientRect().width;\n // Patch by Corrigo beginning.\n var containerHeight = height;\n if (this.visibleItems_ > 0) {\n var item = this.element_.querySelector('.' + this.CssClasses_.ITEM);\n if (item !== null) {\n containerHeight = item.offsetHeight * this.visibleItems_ + 16;\n }\n }\n // Apply the inner element's size to the container and outline.\n this.container_.style.height = containerHeight + 'px';\n // Patch end.\n this.outline_.style.width = width + 'px';\n this.outline_.style.height = height + 'px';\n var transitionDuration = this.Constant_.TRANSITION_DURATION_SECONDS * this.Constant_.TRANSITION_DURATION_FRACTION;\n // Calculate transition delays for individual menu items, so that they fade\n // in one at a time.\n var items = this.element_.querySelectorAll('.' + this.CssClasses_.ITEM);\n for (var i = 0; i < items.length; i++) {\n var itemDelay = null;\n if (this.element_.classList.contains(this.CssClasses_.TOP_LEFT) || this.element_.classList.contains(this.CssClasses_.TOP_RIGHT)) {\n itemDelay = (height - items[i].offsetTop - items[i].offsetHeight) / height * transitionDuration + 's';\n } else {\n itemDelay = items[i].offsetTop / height * transitionDuration + 's';\n }\n items[i].style.transitionDelay = itemDelay;\n }\n // Apply the initial clip to the text before we start animating.\n this.applyClip_(height, width);\n // Wait for the next frame, turn on animation, and apply the final clip.\n // Also make it visible. This triggers the transitions.\n window.requestAnimationFrame(function () {\n this.element_.classList.add(this.CssClasses_.IS_ANIMATING);\n this.element_.style.clip = 'rect(0 ' + width + 'px ' + height + 'px 0)';\n this.container_.classList.add(this.CssClasses_.IS_VISIBLE);\n }.bind(this));\n // Clean up after the animation is complete.\n this.addAnimationEndListener_();\n // Add a click listener to the document, to close the menu.\n var callback = function (e) {\n // Check to see if the document is processing the same event that\n // displayed the menu in the first place. If so, do nothing.\n // Also check to see if the menu is in the process of closing itself, and\n // do nothing in that case.\n // Also check if the clicked element is a menu item\n // if so, do nothing.\n if (e !== evt && !this.closing_ && e.target.parentNode !== this.element_) {\n document.removeEventListener('click', callback);\n this.hide();\n }\n }.bind(this);\n document.addEventListener('click', callback);\n }\n};\nMaterialMenu.prototype['show'] = MaterialMenu.prototype.show;\n/**\r\n * Hides the menu.\r\n *\r\n * @public\r\n */\nMaterialMenu.prototype.hide = function () {\n if (this.element_ && this.container_ && this.outline_) {\n var items = this.element_.querySelectorAll('.' + this.CssClasses_.ITEM);\n // Remove all transition delays; menu items fade out concurrently.\n for (var i = 0; i < items.length; i++) {\n items[i].style.removeProperty('transition-delay');\n }\n // Measure the inner element.\n var rect = this.element_.getBoundingClientRect();\n var height = rect.height;\n var width = rect.width;\n // Turn on animation, and apply the final clip. Also make invisible.\n // This triggers the transitions.\n this.element_.classList.add(this.CssClasses_.IS_ANIMATING);\n this.applyClip_(height, width);\n this.container_.classList.remove(this.CssClasses_.IS_VISIBLE);\n // Clean up after the animation is complete.\n this.addAnimationEndListener_();\n }\n};\nMaterialMenu.prototype['hide'] = MaterialMenu.prototype.hide;\n/**\r\n * Displays or hides the menu, depending on current state.\r\n *\r\n * @public\r\n */\nMaterialMenu.prototype.toggle = function (evt) {\n if (this.container_.classList.contains(this.CssClasses_.IS_VISIBLE)) {\n this.hide();\n } else {\n this.show(evt);\n }\n};\nMaterialMenu.prototype['toggle'] = MaterialMenu.prototype.toggle;\n// The component registers itself. It can assume componentHandler is available\n// in the global scope.\ncomponentHandler.register({\n constructor: MaterialMenu,\n classAsString: 'MaterialMenu',\n cssClass: 'mdl-js-menu',\n widget: true\n});","/**\r\n * @license\r\n * Copyright 2015 Google Inc. All Rights Reserved.\r\n *\r\n * Licensed under the Apache License, Version 2.0 (the \"License\");\r\n * you may not use this file except in compliance with the License.\r\n * You may obtain a copy of the License at\r\n *\r\n * http://www.apache.org/licenses/LICENSE-2.0\r\n *\r\n * Unless required by applicable law or agreed to in writing, software\r\n * distributed under the License is distributed on an \"AS IS\" BASIS,\r\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\r\n * See the License for the specific language governing permissions and\r\n * limitations under the License.\r\n */\n/**\r\n * Class constructor for Progress MDL component.\r\n * Implements MDL component design pattern defined at:\r\n * https://github.com/jasonmayes/mdl-component-design-pattern\r\n *\r\n * @constructor\r\n * @param {HTMLElement} element The element that will be upgraded.\r\n */\nvar MaterialProgress = function MaterialProgress(element) {\n this.element_ = element;\n // Initialize instance.\n this.init();\n};\nwindow['MaterialProgress'] = MaterialProgress;\n/**\r\n * Store constants in one place so they can be updated easily.\r\n *\r\n * @enum {string | number}\r\n * @private\r\n */\nMaterialProgress.prototype.Constant_ = {};\n/**\r\n * Store strings for class names defined by this component that are used in\r\n * JavaScript. This allows us to simply change it in one place should we\r\n * decide to modify at a later date.\r\n *\r\n * @enum {string}\r\n * @private\r\n */\nMaterialProgress.prototype.CssClasses_ = { INDETERMINATE_CLASS: 'mdl-progress__indeterminate' };\n/**\r\n * Set the current progress of the progressbar.\r\n *\r\n * @param {number} p Percentage of the progress (0-100)\r\n * @public\r\n */\nMaterialProgress.prototype.setProgress = function (p) {\n if (this.element_.classList.contains(this.CssClasses_.INDETERMINATE_CLASS)) {\n return;\n }\n this.progressbar_.style.width = p + '%';\n};\nMaterialProgress.prototype['setProgress'] = MaterialProgress.prototype.setProgress;\n/**\r\n * Set the current progress of the buffer.\r\n *\r\n * @param {number} p Percentage of the buffer (0-100)\r\n * @public\r\n */\nMaterialProgress.prototype.setBuffer = function (p) {\n this.bufferbar_.style.width = p + '%';\n this.auxbar_.style.width = 100 - p + '%';\n};\nMaterialProgress.prototype['setBuffer'] = MaterialProgress.prototype.setBuffer;\n/**\r\n * Initialize element.\r\n */\nMaterialProgress.prototype.init = function () {\n if (this.element_) {\n var el = document.createElement('div');\n el.className = 'progressbar bar bar1';\n this.element_.appendChild(el);\n this.progressbar_ = el;\n el = document.createElement('div');\n el.className = 'bufferbar bar bar2';\n this.element_.appendChild(el);\n this.bufferbar_ = el;\n el = document.createElement('div');\n el.className = 'auxbar bar bar3';\n this.element_.appendChild(el);\n this.auxbar_ = el;\n this.progressbar_.style.width = '0%';\n this.bufferbar_.style.width = '100%';\n this.auxbar_.style.width = '0%';\n this.element_.classList.add('is-upgraded');\n }\n};\n// The component registers itself. It can assume componentHandler is available\n// in the global scope.\ncomponentHandler.register({\n constructor: MaterialProgress,\n classAsString: 'MaterialProgress',\n cssClass: 'mdl-js-progress',\n widget: true\n});","/**\r\n * @license\r\n * Copyright 2015 Google Inc. All Rights Reserved.\r\n *\r\n * Licensed under the Apache License, Version 2.0 (the \"License\");\r\n * you may not use this file except in compliance with the License.\r\n * You may obtain a copy of the License at\r\n *\r\n * http://www.apache.org/licenses/LICENSE-2.0\r\n *\r\n * Unless required by applicable law or agreed to in writing, software\r\n * distributed under the License is distributed on an \"AS IS\" BASIS,\r\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\r\n * See the License for the specific language governing permissions and\r\n * limitations under the License.\r\n */\n/**\r\n * Class constructor for Textfield MDL component.\r\n * Implements MDL component design pattern defined at:\r\n * https://github.com/jasonmayes/mdl-component-design-pattern\r\n *\r\n * @constructor\r\n * @param {HTMLElement} element The element that will be upgraded.\r\n */\nvar MaterialTextfield = function MaterialTextfield(element) {\n this.element_ = element;\n this.maxRows = this.Constant_.NO_MAX_ROWS;\n // Initialize instance.\n this.init();\n};\nwindow['MaterialTextfield'] = MaterialTextfield;\n/**\r\n * Store constants in one place so they can be updated easily.\r\n *\r\n * @enum {string | number}\r\n * @private\r\n */\nMaterialTextfield.prototype.Constant_ = {\n NO_MAX_ROWS: -1,\n MAX_ROWS_ATTRIBUTE: 'maxrows'\n};\n/**\r\n * Store strings for class names defined by this component that are used in\r\n * JavaScript. This allows us to simply change it in one place should we\r\n * decide to modify at a later date.\r\n *\r\n * @enum {string}\r\n * @private\r\n */\nMaterialTextfield.prototype.CssClasses_ = {\n LABEL: 'mdl-textfield__label',\n INPUT: 'mdl-textfield__input',\n IS_DIRTY: 'is-dirty',\n IS_FOCUSED: 'is-focused',\n IS_DISABLED: 'is-disabled',\n IS_INVALID: 'is-invalid',\n IS_UPGRADED: 'is-upgraded',\n HAS_PLACEHOLDER: 'has-placeholder'\n};\n/**\r\n * Handle input being entered.\r\n *\r\n * @param {Event} event The event that fired.\r\n * @private\r\n */\nMaterialTextfield.prototype.onKeyDown_ = function (event) {\n var currentRowCount = event.target.value.split('\\n').length;\n if (event.keyCode === 13) {\n if (currentRowCount >= this.maxRows) {\n event.preventDefault();\n }\n }\n};\n/**\r\n * Handle focus.\r\n *\r\n * @param {Event} event The event that fired.\r\n * @private\r\n */\nMaterialTextfield.prototype.onFocus_ = function (event) {\n this.element_.classList.add(this.CssClasses_.IS_FOCUSED);\n};\n/**\r\n * Handle lost focus.\r\n *\r\n * @param {Event} event The event that fired.\r\n * @private\r\n */\nMaterialTextfield.prototype.onBlur_ = function (event) {\n this.element_.classList.remove(this.CssClasses_.IS_FOCUSED);\n};\n/**\r\n * Handle reset event from out side.\r\n *\r\n * @param {Event} event The event that fired.\r\n * @private\r\n */\nMaterialTextfield.prototype.onReset_ = function (event) {\n this.updateClasses_();\n};\n/**\r\n * Handle class updates.\r\n *\r\n * @private\r\n */\nMaterialTextfield.prototype.updateClasses_ = function () {\n this.checkDisabled();\n // Patch by Corrigo starting.\n this.checkDirty();\n var isDirty = this.element_.classList.contains(this.CssClasses_.IS_DIRTY), isRequired = this.input_.required;\n if (!isRequired || isRequired && isDirty) {\n this.checkValidity();\n }\n // Patch end.\n this.checkFocus();\n};\n// Public methods.\n/**\r\n * Check the disabled state and update field accordingly.\r\n *\r\n * @public\r\n */\nMaterialTextfield.prototype.checkDisabled = function () {\n if (this.input_.disabled) {\n this.element_.classList.add(this.CssClasses_.IS_DISABLED);\n } else {\n this.element_.classList.remove(this.CssClasses_.IS_DISABLED);\n }\n};\nMaterialTextfield.prototype['checkDisabled'] = MaterialTextfield.prototype.checkDisabled;\n/**\r\n * Check the focus state and update field accordingly.\r\n *\r\n * @public\r\n */\nMaterialTextfield.prototype.checkFocus = function () {\n if (Boolean(this.element_.querySelector(':focus'))) {\n this.element_.classList.add(this.CssClasses_.IS_FOCUSED);\n } else {\n this.element_.classList.remove(this.CssClasses_.IS_FOCUSED);\n }\n};\nMaterialTextfield.prototype['checkFocus'] = MaterialTextfield.prototype.checkFocus;\n/**\r\n * Check the validity state and update field accordingly.\r\n *\r\n * @public\r\n */\nMaterialTextfield.prototype.checkValidity = function () {\n if (this.input_.validity) {\n if (this.input_.validity.valid) {\n this.element_.classList.remove(this.CssClasses_.IS_INVALID);\n } else {\n this.element_.classList.add(this.CssClasses_.IS_INVALID);\n }\n }\n};\nMaterialTextfield.prototype['checkValidity'] = MaterialTextfield.prototype.checkValidity;\n/**\r\n * Check the dirty state and update field accordingly.\r\n *\r\n * @public\r\n */\nMaterialTextfield.prototype.checkDirty = function () {\n if (this.input_.value && this.input_.value.length > 0 || this.input_.placeholder.trim() !== '') {\n this.element_.classList.add(this.CssClasses_.IS_DIRTY);\n } else {\n this.element_.classList.remove(this.CssClasses_.IS_DIRTY);\n }\n};\nMaterialTextfield.prototype['checkDirty'] = MaterialTextfield.prototype.checkDirty;\n/**\r\n * Disable text field.\r\n *\r\n * @public\r\n */\nMaterialTextfield.prototype.disable = function () {\n this.input_.disabled = true;\n this.updateClasses_();\n};\nMaterialTextfield.prototype['disable'] = MaterialTextfield.prototype.disable;\n/**\r\n * Enable text field.\r\n *\r\n * @public\r\n */\nMaterialTextfield.prototype.enable = function () {\n this.input_.disabled = false;\n this.updateClasses_();\n // Patch by Corrigo starting.\n this.checkValidity(); // End patch.\n};\nMaterialTextfield.prototype['enable'] = MaterialTextfield.prototype.enable;\n/**\r\n * Update text field value.\r\n *\r\n * @param {string} value The value to which to set the control (optional).\r\n * @public\r\n */\nMaterialTextfield.prototype.change = function (value) {\n this.input_.value = value || '';\n this.updateClasses_();\n};\nMaterialTextfield.prototype['change'] = MaterialTextfield.prototype.change;\n/**\r\n * Initialize element.\r\n */\nMaterialTextfield.prototype.init = function () {\n if (this.element_) {\n this.label_ = this.element_.querySelector('.' + this.CssClasses_.LABEL);\n this.input_ = this.element_.querySelector('.' + this.CssClasses_.INPUT);\n if (this.input_) {\n if (this.input_.hasAttribute(this.Constant_.MAX_ROWS_ATTRIBUTE)) {\n this.maxRows = parseInt(this.input_.getAttribute(this.Constant_.MAX_ROWS_ATTRIBUTE), 10);\n if (isNaN(this.maxRows)) {\n this.maxRows = this.Constant_.NO_MAX_ROWS;\n }\n }\n if (this.input_.hasAttribute('placeholder')) {\n this.element_.classList.add(this.CssClasses_.HAS_PLACEHOLDER);\n }\n this.boundUpdateClassesHandler = this.updateClasses_.bind(this);\n this.boundFocusHandler = this.onFocus_.bind(this);\n this.boundBlurHandler = this.onBlur_.bind(this);\n this.boundResetHandler = this.onReset_.bind(this);\n this.input_.addEventListener('input', this.boundUpdateClassesHandler);\n this.input_.addEventListener('focus', this.boundFocusHandler);\n this.input_.addEventListener('blur', this.boundBlurHandler);\n this.input_.addEventListener('reset', this.boundResetHandler);\n if (this.maxRows !== this.Constant_.NO_MAX_ROWS) {\n // TODO: This should handle pasting multi line text.\n // Currently doesn't.\n this.boundKeyDownHandler = this.onKeyDown_.bind(this);\n this.input_.addEventListener('keydown', this.boundKeyDownHandler);\n }\n var invalid = this.element_.classList.contains(this.CssClasses_.IS_INVALID);\n this.updateClasses_();\n this.element_.classList.add(this.CssClasses_.IS_UPGRADED);\n if (invalid) {\n this.element_.classList.add(this.CssClasses_.IS_INVALID);\n }\n if (this.input_.hasAttribute('autofocus')) {\n this.element_.focus();\n this.checkFocus();\n }\n }\n }\n};\n// The component registers itself. It can assume componentHandler is available\n// in the global scope.\ncomponentHandler.register({\n constructor: MaterialTextfield,\n classAsString: 'MaterialTextfield',\n cssClass: 'mdl-js-textfield',\n widget: true\n});","/**\r\n * @license\r\n * Copyright 2015 Google Inc. All Rights Reserved.\r\n *\r\n * Licensed under the Apache License, Version 2.0 (the \"License\");\r\n * you may not use this file except in compliance with the License.\r\n * You may obtain a copy of the License at\r\n *\r\n * http://www.apache.org/licenses/LICENSE-2.0\r\n *\r\n * Unless required by applicable law or agreed to in writing, software\r\n * distributed under the License is distributed on an \"AS IS\" BASIS,\r\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\r\n * See the License for the specific language governing permissions and\r\n * limitations under the License.\r\n */\n/**\r\n * Class constructor for Layout MDL component.\r\n * Implements MDL component design pattern defined at:\r\n * https://github.com/jasonmayes/mdl-component-design-pattern\r\n *\r\n * @constructor\r\n * @param {HTMLElement} element The element that will be upgraded.\r\n */\nvar MaterialLayout = function MaterialLayout(element) {\n this.element_ = element;\n // Initialize instance.\n this.init();\n};\nwindow['MaterialLayout'] = MaterialLayout;\n/**\r\n * Store constants in one place so they can be updated easily.\r\n *\r\n * @enum {string | number}\r\n * @private\r\n */\nMaterialLayout.prototype.Constant_ = {\n MAX_WIDTH: '(max-width: 1024px)',\n TAB_SCROLL_PIXELS: 100,\n RESIZE_TIMEOUT: 100,\n MENU_ICON: '',\n CHEVRON_LEFT: 'chevron_left',\n CHEVRON_RIGHT: 'chevron_right'\n};\n/**\r\n * Keycodes, for code readability.\r\n *\r\n * @enum {number}\r\n * @private\r\n */\nMaterialLayout.prototype.Keycodes_ = {\n ENTER: 13,\n ESCAPE: 27,\n SPACE: 32\n};\n/**\r\n * Modes.\r\n *\r\n * @enum {number}\r\n * @private\r\n */\nMaterialLayout.prototype.Mode_ = {\n STANDARD: 0,\n SEAMED: 1,\n WATERFALL: 2,\n SCROLL: 3\n};\n/**\r\n * Store strings for class names defined by this component that are used in\r\n * JavaScript. This allows us to simply change it in one place should we\r\n * decide to modify at a later date.\r\n *\r\n * @enum {string}\r\n * @private\r\n */\nMaterialLayout.prototype.CssClasses_ = {\n CONTAINER: 'mdl-layout__container',\n HEADER: 'mdl-layout__header',\n DRAWER: 'mdl-layout__drawer',\n CONTENT: 'mdl-layout__content',\n DRAWER_BTN: 'mdl-layout__drawer-button',\n ICON: 'material-icons',\n JS_RIPPLE_EFFECT: 'mdl-js-ripple-effect',\n RIPPLE_CONTAINER: 'mdl-layout__tab-ripple-container',\n RIPPLE: 'mdl-ripple',\n RIPPLE_IGNORE_EVENTS: 'mdl-js-ripple-effect--ignore-events',\n HEADER_SEAMED: 'mdl-layout__header--seamed',\n HEADER_WATERFALL: 'mdl-layout__header--waterfall',\n HEADER_SCROLL: 'mdl-layout__header--scroll',\n FIXED_HEADER: 'mdl-layout--fixed-header',\n FIXED_DRAWER: 'mdl-layout--fixed-drawer',\n OBFUSCATOR: 'mdl-layout__obfuscator',\n TAB_BAR: 'mdl-layout__tab-bar',\n TAB_CONTAINER: 'mdl-layout__tab-bar-container',\n TAB: 'mdl-layout__tab',\n TAB_BAR_BUTTON: 'mdl-layout__tab-bar-button',\n TAB_BAR_LEFT_BUTTON: 'mdl-layout__tab-bar-left-button',\n TAB_BAR_RIGHT_BUTTON: 'mdl-layout__tab-bar-right-button',\n TAB_MANUAL_SWITCH: 'mdl-layout__tab-manual-switch',\n PANEL: 'mdl-layout__tab-panel',\n HAS_DRAWER: 'has-drawer',\n HAS_TABS: 'has-tabs',\n HAS_SCROLLING_HEADER: 'has-scrolling-header',\n CASTING_SHADOW: 'is-casting-shadow',\n IS_COMPACT: 'is-compact',\n IS_SMALL_SCREEN: 'is-small-screen',\n IS_DRAWER_OPEN: 'is-visible',\n IS_ACTIVE: 'is-active',\n IS_UPGRADED: 'is-upgraded',\n IS_ANIMATING: 'is-animating',\n ON_LARGE_SCREEN: 'mdl-layout--large-screen-only',\n ON_SMALL_SCREEN: 'mdl-layout--small-screen-only'\n};\n/**\r\n * Provide local version of matchMedia. This is needed in order to support\r\n * monkey-patching of matchMedia in the unit tests. Due to peculiarities in\r\n * PhantomJS, it doesn't work to monkey patch window.matchMedia directly.\r\n *\r\n * @private\r\n */\nMaterialLayout.prototype.matchMedia_ = function (query) {\n return window.matchMedia(query);\n};\n/**\r\n * Handles scrolling on the content.\r\n *\r\n * @private\r\n */\nMaterialLayout.prototype.contentScrollHandler_ = function () {\n if (this.header_.classList.contains(this.CssClasses_.IS_ANIMATING)) {\n return;\n }\n var headerVisible = !this.element_.classList.contains(this.CssClasses_.IS_SMALL_SCREEN) || this.element_.classList.contains(this.CssClasses_.FIXED_HEADER);\n if (this.content_.scrollTop > 0 && !this.header_.classList.contains(this.CssClasses_.IS_COMPACT)) {\n this.header_.classList.add(this.CssClasses_.CASTING_SHADOW);\n this.header_.classList.add(this.CssClasses_.IS_COMPACT);\n if (headerVisible) {\n this.header_.classList.add(this.CssClasses_.IS_ANIMATING);\n }\n } else if (this.content_.scrollTop <= 0 && this.header_.classList.contains(this.CssClasses_.IS_COMPACT)) {\n this.header_.classList.remove(this.CssClasses_.CASTING_SHADOW);\n this.header_.classList.remove(this.CssClasses_.IS_COMPACT);\n if (headerVisible) {\n this.header_.classList.add(this.CssClasses_.IS_ANIMATING);\n }\n }\n};\n/**\r\n * Handles a keyboard event on the drawer.\r\n *\r\n * @param {Event} evt The event that fired.\r\n * @private\r\n */\nMaterialLayout.prototype.keyboardEventHandler_ = function (evt) {\n // Only react when the drawer is open.\n if (evt.keyCode === this.Keycodes_.ESCAPE && this.drawer_.classList.contains(this.CssClasses_.IS_DRAWER_OPEN)) {\n this.toggleDrawer();\n }\n};\n/**\r\n * Handles changes in screen size.\r\n *\r\n * @private\r\n */\nMaterialLayout.prototype.screenSizeHandler_ = function () {\n if (this.screenSizeMediaQuery_.matches) {\n this.element_.classList.add(this.CssClasses_.IS_SMALL_SCREEN);\n if (this.drawer_) {\n this.drawer_.setAttribute('aria-hidden', 'true');\n }\n } else {\n this.element_.classList.remove(this.CssClasses_.IS_SMALL_SCREEN);\n // Collapse drawer (if any) when moving to a large screen size.\n if (this.drawer_) {\n this.drawer_.classList.remove(this.CssClasses_.IS_DRAWER_OPEN);\n this.obfuscator_.classList.remove(this.CssClasses_.IS_DRAWER_OPEN);\n if (this.element_.classList.contains(this.CssClasses_.FIXED_DRAWER)) {\n this.drawer_.setAttribute('aria-hidden', 'false');\n }\n }\n }\n};\n/**\r\n * Handles events of drawer button.\r\n *\r\n * @param {Event} evt The event that fired.\r\n * @private\r\n */\nMaterialLayout.prototype.drawerToggleHandler_ = function (evt) {\n if (evt && evt.type === 'keydown') {\n if (evt.keyCode === this.Keycodes_.SPACE || evt.keyCode === this.Keycodes_.ENTER) {\n // prevent scrolling in drawer nav\n evt.preventDefault();\n } else {\n // prevent other keys\n return;\n }\n }\n this.toggleDrawer();\n};\n/**\r\n * Handles (un)setting the `is-animating` class\r\n *\r\n * @private\r\n */\nMaterialLayout.prototype.headerTransitionEndHandler_ = function () {\n this.header_.classList.remove(this.CssClasses_.IS_ANIMATING);\n};\n/**\r\n * Handles expanding the header on click\r\n *\r\n * @private\r\n */\nMaterialLayout.prototype.headerClickHandler_ = function () {\n if (this.header_.classList.contains(this.CssClasses_.IS_COMPACT)) {\n this.header_.classList.remove(this.CssClasses_.IS_COMPACT);\n this.header_.classList.add(this.CssClasses_.IS_ANIMATING);\n }\n};\n/**\r\n * Reset tab state, dropping active classes\r\n *\r\n * @private\r\n */\nMaterialLayout.prototype.resetTabState_ = function (tabBar) {\n for (var k = 0; k < tabBar.length; k++) {\n tabBar[k].classList.remove(this.CssClasses_.IS_ACTIVE);\n }\n};\n/**\r\n * Reset panel state, droping active classes\r\n *\r\n * @private\r\n */\nMaterialLayout.prototype.resetPanelState_ = function (panels) {\n for (var j = 0; j < panels.length; j++) {\n panels[j].classList.remove(this.CssClasses_.IS_ACTIVE);\n }\n};\n/**\r\n * Toggle drawer state\r\n *\r\n * @public\r\n */\nMaterialLayout.prototype.toggleDrawer = function () {\n var drawerButton = this.element_.querySelector('.' + this.CssClasses_.DRAWER_BTN);\n this.drawer_.classList.toggle(this.CssClasses_.IS_DRAWER_OPEN);\n this.obfuscator_.classList.toggle(this.CssClasses_.IS_DRAWER_OPEN);\n // Set accessibility properties.\n if (this.drawer_.classList.contains(this.CssClasses_.IS_DRAWER_OPEN)) {\n this.drawer_.setAttribute('aria-hidden', 'false');\n drawerButton.setAttribute('aria-expanded', 'true');\n } else {\n this.drawer_.setAttribute('aria-hidden', 'true');\n drawerButton.setAttribute('aria-expanded', 'false');\n }\n};\nMaterialLayout.prototype['toggleDrawer'] = MaterialLayout.prototype.toggleDrawer;\n/**\r\n * Initialize element.\r\n */\nMaterialLayout.prototype.init = function () {\n if (this.element_) {\n var container = document.createElement('div');\n container.classList.add(this.CssClasses_.CONTAINER);\n var focusedElement = this.element_.querySelector(':focus');\n this.element_.parentElement.insertBefore(container, this.element_);\n this.element_.parentElement.removeChild(this.element_);\n container.appendChild(this.element_);\n if (focusedElement) {\n focusedElement.focus();\n }\n var directChildren = this.element_.childNodes;\n var numChildren = directChildren.length;\n for (var c = 0; c < numChildren; c++) {\n var child = directChildren[c];\n if (child.classList && child.classList.contains(this.CssClasses_.HEADER)) {\n this.header_ = child;\n }\n if (child.classList && child.classList.contains(this.CssClasses_.DRAWER)) {\n this.drawer_ = child;\n }\n if (child.classList && child.classList.contains(this.CssClasses_.CONTENT)) {\n this.content_ = child;\n }\n }\n window.addEventListener('pageshow', function (e) {\n if (e.persisted) {\n // when page is loaded from back/forward cache\n // trigger repaint to let layout scroll in safari\n this.element_.style.overflowY = 'hidden';\n requestAnimationFrame(function () {\n this.element_.style.overflowY = '';\n }.bind(this));\n }\n }.bind(this), false);\n if (this.header_) {\n this.tabBar_ = this.header_.querySelector('.' + this.CssClasses_.TAB_BAR);\n }\n var mode = this.Mode_.STANDARD;\n if (this.header_) {\n if (this.header_.classList.contains(this.CssClasses_.HEADER_SEAMED)) {\n mode = this.Mode_.SEAMED;\n } else if (this.header_.classList.contains(this.CssClasses_.HEADER_WATERFALL)) {\n mode = this.Mode_.WATERFALL;\n this.header_.addEventListener('transitionend', this.headerTransitionEndHandler_.bind(this));\n this.header_.addEventListener('click', this.headerClickHandler_.bind(this));\n } else if (this.header_.classList.contains(this.CssClasses_.HEADER_SCROLL)) {\n mode = this.Mode_.SCROLL;\n container.classList.add(this.CssClasses_.HAS_SCROLLING_HEADER);\n }\n if (mode === this.Mode_.STANDARD) {\n this.header_.classList.add(this.CssClasses_.CASTING_SHADOW);\n if (this.tabBar_) {\n this.tabBar_.classList.add(this.CssClasses_.CASTING_SHADOW);\n }\n } else if (mode === this.Mode_.SEAMED || mode === this.Mode_.SCROLL) {\n this.header_.classList.remove(this.CssClasses_.CASTING_SHADOW);\n if (this.tabBar_) {\n this.tabBar_.classList.remove(this.CssClasses_.CASTING_SHADOW);\n }\n } else if (mode === this.Mode_.WATERFALL) {\n // Add and remove shadows depending on scroll position.\n // Also add/remove auxiliary class for styling of the compact version of\n // the header.\n this.content_.addEventListener('scroll', this.contentScrollHandler_.bind(this));\n this.contentScrollHandler_();\n }\n }\n // Add drawer toggling button to our layout, if we have an openable drawer.\n if (this.drawer_) {\n var drawerButton = this.element_.querySelector('.' + this.CssClasses_.DRAWER_BTN);\n if (!drawerButton) {\n drawerButton = document.createElement('div');\n drawerButton.setAttribute('aria-expanded', 'false');\n drawerButton.setAttribute('role', 'button');\n drawerButton.setAttribute('tabindex', '0');\n drawerButton.classList.add(this.CssClasses_.DRAWER_BTN);\n var drawerButtonIcon = document.createElement('i');\n drawerButtonIcon.classList.add(this.CssClasses_.ICON);\n drawerButtonIcon.innerHTML = this.Constant_.MENU_ICON;\n drawerButton.appendChild(drawerButtonIcon);\n }\n if (this.drawer_.classList.contains(this.CssClasses_.ON_LARGE_SCREEN)) {\n //If drawer has ON_LARGE_SCREEN class then add it to the drawer toggle button as well.\n drawerButton.classList.add(this.CssClasses_.ON_LARGE_SCREEN);\n } else if (this.drawer_.classList.contains(this.CssClasses_.ON_SMALL_SCREEN)) {\n //If drawer has ON_SMALL_SCREEN class then add it to the drawer toggle button as well.\n drawerButton.classList.add(this.CssClasses_.ON_SMALL_SCREEN);\n }\n drawerButton.addEventListener('click', this.drawerToggleHandler_.bind(this));\n drawerButton.addEventListener('keydown', this.drawerToggleHandler_.bind(this));\n // Add a class if the layout has a drawer, for altering the left padding.\n // Adds the HAS_DRAWER to the elements since this.header_ may or may\n // not be present.\n this.element_.classList.add(this.CssClasses_.HAS_DRAWER);\n // If we have a fixed header, add the button to the header rather than\n // the layout.\n if (this.element_.classList.contains(this.CssClasses_.FIXED_HEADER)) {\n this.header_.insertBefore(drawerButton, this.header_.firstChild);\n } else {\n this.element_.insertBefore(drawerButton, this.content_);\n }\n var obfuscator = document.createElement('div');\n obfuscator.classList.add(this.CssClasses_.OBFUSCATOR);\n this.element_.appendChild(obfuscator);\n obfuscator.addEventListener('click', this.drawerToggleHandler_.bind(this));\n this.obfuscator_ = obfuscator;\n this.drawer_.addEventListener('keydown', this.keyboardEventHandler_.bind(this));\n this.drawer_.setAttribute('aria-hidden', 'true');\n }\n // Keep an eye on screen size, and add/remove auxiliary class for styling\n // of small screens.\n this.screenSizeMediaQuery_ = this.matchMedia_(this.Constant_.MAX_WIDTH);\n this.screenSizeMediaQuery_.addListener(this.screenSizeHandler_.bind(this));\n this.screenSizeHandler_();\n // Initialize tabs, if any.\n if (this.header_ && this.tabBar_) {\n this.element_.classList.add(this.CssClasses_.HAS_TABS);\n var tabContainer = document.createElement('div');\n tabContainer.classList.add(this.CssClasses_.TAB_CONTAINER);\n this.header_.insertBefore(tabContainer, this.tabBar_);\n this.header_.removeChild(this.tabBar_);\n var leftButton = document.createElement('div');\n leftButton.classList.add(this.CssClasses_.TAB_BAR_BUTTON);\n leftButton.classList.add(this.CssClasses_.TAB_BAR_LEFT_BUTTON);\n var leftButtonIcon = document.createElement('i');\n leftButtonIcon.classList.add(this.CssClasses_.ICON);\n leftButtonIcon.textContent = this.Constant_.CHEVRON_LEFT;\n leftButton.appendChild(leftButtonIcon);\n leftButton.addEventListener('click', function () {\n this.tabBar_.scrollLeft -= this.Constant_.TAB_SCROLL_PIXELS;\n }.bind(this));\n var rightButton = document.createElement('div');\n rightButton.classList.add(this.CssClasses_.TAB_BAR_BUTTON);\n rightButton.classList.add(this.CssClasses_.TAB_BAR_RIGHT_BUTTON);\n var rightButtonIcon = document.createElement('i');\n rightButtonIcon.classList.add(this.CssClasses_.ICON);\n rightButtonIcon.textContent = this.Constant_.CHEVRON_RIGHT;\n rightButton.appendChild(rightButtonIcon);\n rightButton.addEventListener('click', function () {\n this.tabBar_.scrollLeft += this.Constant_.TAB_SCROLL_PIXELS;\n }.bind(this));\n tabContainer.appendChild(leftButton);\n tabContainer.appendChild(this.tabBar_);\n tabContainer.appendChild(rightButton);\n // Add and remove tab buttons depending on scroll position and total\n // window size.\n var tabUpdateHandler = function () {\n if (this.tabBar_.scrollLeft > 0) {\n leftButton.classList.add(this.CssClasses_.IS_ACTIVE);\n } else {\n leftButton.classList.remove(this.CssClasses_.IS_ACTIVE);\n }\n if (this.tabBar_.scrollLeft < this.tabBar_.scrollWidth - this.tabBar_.offsetWidth) {\n rightButton.classList.add(this.CssClasses_.IS_ACTIVE);\n } else {\n rightButton.classList.remove(this.CssClasses_.IS_ACTIVE);\n }\n }.bind(this);\n this.tabBar_.addEventListener('scroll', tabUpdateHandler);\n tabUpdateHandler();\n // Update tabs when the window resizes.\n var windowResizeHandler = function () {\n // Use timeouts to make sure it doesn't happen too often.\n if (this.resizeTimeoutId_) {\n clearTimeout(this.resizeTimeoutId_);\n }\n this.resizeTimeoutId_ = setTimeout(function () {\n tabUpdateHandler();\n this.resizeTimeoutId_ = null;\n }.bind(this), this.Constant_.RESIZE_TIMEOUT);\n }.bind(this);\n window.addEventListener('resize', windowResizeHandler);\n if (this.tabBar_.classList.contains(this.CssClasses_.JS_RIPPLE_EFFECT)) {\n this.tabBar_.classList.add(this.CssClasses_.RIPPLE_IGNORE_EVENTS);\n }\n // Select element tabs, document panels\n var tabs = this.tabBar_.querySelectorAll('.' + this.CssClasses_.TAB);\n var panels = this.content_.querySelectorAll('.' + this.CssClasses_.PANEL);\n // Create new tabs for each tab element\n for (var i = 0; i < tabs.length; i++) {\n new MaterialLayoutTab(tabs[i], tabs, panels, this);\n }\n }\n this.element_.classList.add(this.CssClasses_.IS_UPGRADED);\n }\n};\n/**\r\n * Constructor for an individual tab.\r\n *\r\n * @constructor\r\n * @param {HTMLElement} tab The HTML element for the tab.\r\n * @param {!Array} tabs Array with HTML elements for all tabs.\r\n * @param {!Array} panels Array with HTML elements for all panels.\r\n * @param {MaterialLayout} layout The MaterialLayout object that owns the tab.\r\n */\nfunction MaterialLayoutTab(tab, tabs, panels, layout) {\n /**\r\n * Auxiliary method to programmatically select a tab in the UI.\r\n */\n function selectTab() {\n var href = tab.href.split('#')[1];\n var panel = layout.content_.querySelector('#' + href);\n layout.resetTabState_(tabs);\n layout.resetPanelState_(panels);\n tab.classList.add(layout.CssClasses_.IS_ACTIVE);\n panel.classList.add(layout.CssClasses_.IS_ACTIVE);\n }\n if (layout.tabBar_.classList.contains(layout.CssClasses_.JS_RIPPLE_EFFECT)) {\n var rippleContainer = document.createElement('span');\n rippleContainer.classList.add(layout.CssClasses_.RIPPLE_CONTAINER);\n rippleContainer.classList.add(layout.CssClasses_.JS_RIPPLE_EFFECT);\n var ripple = document.createElement('span');\n ripple.classList.add(layout.CssClasses_.RIPPLE);\n rippleContainer.appendChild(ripple);\n tab.appendChild(rippleContainer);\n }\n if (!layout.tabBar_.classList.contains(layout.CssClasses_.TAB_MANUAL_SWITCH)) {\n tab.addEventListener('click', function (e) {\n if (tab.getAttribute('href').charAt(0) === '#') {\n e.preventDefault();\n selectTab();\n }\n });\n }\n tab.show = selectTab;\n}\nwindow['MaterialLayoutTab'] = MaterialLayoutTab;\n// The component registers itself. It can assume componentHandler is available\n// in the global scope.\ncomponentHandler.register({\n constructor: MaterialLayout,\n classAsString: 'MaterialLayout',\n cssClass: 'mdl-js-layout'\n});","/**\r\n * @license\r\n * Copyright 2015 Google Inc. All Rights Reserved.\r\n *\r\n * Licensed under the Apache License, Version 2.0 (the \"License\");\r\n * you may not use this file except in compliance with the License.\r\n * You may obtain a copy of the License at\r\n *\r\n * http://www.apache.org/licenses/LICENSE-2.0\r\n *\r\n * Unless required by applicable law or agreed to in writing, software\r\n * distributed under the License is distributed on an \"AS IS\" BASIS,\r\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\r\n * See the License for the specific language governing permissions and\r\n * limitations under the License.\r\n */\n/**\r\n * Class constructor for Ripple MDL component.\r\n * Implements MDL component design pattern defined at:\r\n * https://github.com/jasonmayes/mdl-component-design-pattern\r\n *\r\n * @constructor\r\n * @param {HTMLElement} element The element that will be upgraded.\r\n */\nvar MaterialRipple = function MaterialRipple(element) {\n this.element_ = element;\n // Initialize instance.\n this.init();\n};\nwindow['MaterialRipple'] = MaterialRipple;\n/**\r\n * Store constants in one place so they can be updated easily.\r\n *\r\n * @enum {string | number}\r\n * @private\r\n */\nMaterialRipple.prototype.Constant_ = {\n INITIAL_SCALE: 'scale(0.0001, 0.0001)',\n INITIAL_SIZE: '1px',\n INITIAL_OPACITY: '0.4',\n FINAL_OPACITY: '0',\n FINAL_SCALE: ''\n};\n/**\r\n * Store strings for class names defined by this component that are used in\r\n * JavaScript. This allows us to simply change it in one place should we\r\n * decide to modify at a later date.\r\n *\r\n * @enum {string}\r\n * @private\r\n */\nMaterialRipple.prototype.CssClasses_ = {\n RIPPLE_CENTER: 'mdl-ripple--center',\n RIPPLE_EFFECT_IGNORE_EVENTS: 'mdl-js-ripple-effect--ignore-events',\n RIPPLE: 'mdl-ripple',\n IS_ANIMATING: 'is-animating',\n IS_VISIBLE: 'is-visible'\n};\n/**\r\n * Handle mouse / finger down on element.\r\n *\r\n * @param {Event} event The event that fired.\r\n * @private\r\n */\nMaterialRipple.prototype.downHandler_ = function (event) {\n if (!this.rippleElement_.style.width && !this.rippleElement_.style.height) {\n var rect = this.element_.getBoundingClientRect();\n this.boundHeight = rect.height;\n this.boundWidth = rect.width;\n this.rippleSize_ = Math.sqrt(rect.width * rect.width + rect.height * rect.height) * 2 + 2;\n this.rippleElement_.style.width = this.rippleSize_ + 'px';\n this.rippleElement_.style.height = this.rippleSize_ + 'px';\n }\n this.rippleElement_.classList.add(this.CssClasses_.IS_VISIBLE);\n if (event.type === 'mousedown' && this.ignoringMouseDown_) {\n this.ignoringMouseDown_ = false;\n } else {\n if (event.type === 'touchstart') {\n this.ignoringMouseDown_ = true;\n }\n var frameCount = this.getFrameCount();\n if (frameCount > 0) {\n return;\n }\n this.setFrameCount(1);\n var bound = event.currentTarget.getBoundingClientRect();\n var x;\n var y;\n // Check if we are handling a keyboard click.\n if (event.clientX === 0 && event.clientY === 0) {\n x = Math.round(bound.width / 2);\n y = Math.round(bound.height / 2);\n } else {\n var clientX = event.clientX !== undefined ? event.clientX : event.touches[0].clientX;\n var clientY = event.clientY !== undefined ? event.clientY : event.touches[0].clientY;\n x = Math.round(clientX - bound.left);\n y = Math.round(clientY - bound.top);\n }\n this.setRippleXY(x, y);\n this.setRippleStyles(true);\n window.requestAnimationFrame(this.animFrameHandler.bind(this));\n }\n};\n/**\r\n * Handle mouse / finger up on element.\r\n *\r\n * @param {Event} event The event that fired.\r\n * @private\r\n */\nMaterialRipple.prototype.upHandler_ = function (event) {\n // Don't fire for the artificial \"mouseup\" generated by a double-click.\n if (event && event.detail !== 2) {\n // Allow a repaint to occur before removing this class, so the animation\n // shows for tap events, which seem to trigger a mouseup too soon after\n // mousedown.\n window.setTimeout(function () {\n this.rippleElement_.classList.remove(this.CssClasses_.IS_VISIBLE);\n }.bind(this), 0);\n }\n};\n/**\r\n * Initialize element.\r\n */\nMaterialRipple.prototype.init = function () {\n if (this.element_) {\n var recentering = this.element_.classList.contains(this.CssClasses_.RIPPLE_CENTER);\n if (!this.element_.classList.contains(this.CssClasses_.RIPPLE_EFFECT_IGNORE_EVENTS)) {\n this.rippleElement_ = this.element_.querySelector('.' + this.CssClasses_.RIPPLE);\n this.frameCount_ = 0;\n this.rippleSize_ = 0;\n this.x_ = 0;\n this.y_ = 0;\n // Touch start produces a compat mouse down event, which would cause a\n // second ripples. To avoid that, we use this property to ignore the first\n // mouse down after a touch start.\n this.ignoringMouseDown_ = false;\n this.boundDownHandler = this.downHandler_.bind(this);\n this.element_.addEventListener('mousedown', this.boundDownHandler);\n this.element_.addEventListener('touchstart', this.boundDownHandler);\n this.boundUpHandler = this.upHandler_.bind(this);\n this.element_.addEventListener('mouseup', this.boundUpHandler);\n this.element_.addEventListener('mouseleave', this.boundUpHandler);\n this.element_.addEventListener('touchend', this.boundUpHandler);\n this.element_.addEventListener('blur', this.boundUpHandler);\n /**\r\n * Getter for frameCount_.\r\n * @return {number} the frame count.\r\n */\n this.getFrameCount = function () {\n return this.frameCount_;\n };\n /**\r\n * Setter for frameCount_.\r\n * @param {number} fC the frame count.\r\n */\n this.setFrameCount = function (fC) {\n this.frameCount_ = fC;\n };\n /**\r\n * Getter for rippleElement_.\r\n * @return {Element} the ripple element.\r\n */\n this.getRippleElement = function () {\n return this.rippleElement_;\n };\n /**\r\n * Sets the ripple X and Y coordinates.\r\n * @param {number} newX the new X coordinate\r\n * @param {number} newY the new Y coordinate\r\n */\n this.setRippleXY = function (newX, newY) {\n this.x_ = newX;\n this.y_ = newY;\n };\n /**\r\n * Sets the ripple styles.\r\n * @param {boolean} start whether or not this is the start frame.\r\n */\n this.setRippleStyles = function (start) {\n if (this.rippleElement_ !== null) {\n var transformString;\n var scale;\n var size;\n var offset = 'translate(' + this.x_ + 'px, ' + this.y_ + 'px)';\n if (start) {\n scale = this.Constant_.INITIAL_SCALE;\n size = this.Constant_.INITIAL_SIZE;\n } else {\n scale = this.Constant_.FINAL_SCALE;\n size = this.rippleSize_ + 'px';\n if (recentering) {\n offset = 'translate(' + this.boundWidth / 2 + 'px, ' + this.boundHeight / 2 + 'px)';\n }\n }\n transformString = 'translate(-50%, -50%) ' + offset + scale;\n this.rippleElement_.style.webkitTransform = transformString;\n this.rippleElement_.style.msTransform = transformString;\n this.rippleElement_.style.transform = transformString;\n if (start) {\n this.rippleElement_.classList.remove(this.CssClasses_.IS_ANIMATING);\n } else {\n this.rippleElement_.classList.add(this.CssClasses_.IS_ANIMATING);\n }\n }\n };\n /**\r\n * Handles an animation frame.\r\n */\n this.animFrameHandler = function () {\n if (this.frameCount_-- > 0) {\n window.requestAnimationFrame(this.animFrameHandler.bind(this));\n } else {\n this.setRippleStyles(false);\n }\n };\n }\n }\n};\n// The component registers itself. It can assume componentHandler is available\n// in the global scope.\ncomponentHandler.register({\n constructor: MaterialRipple,\n classAsString: 'MaterialRipple',\n cssClass: 'mdl-js-ripple-effect',\n widget: false\n});"]}