· 8 years ago · Mar 08, 2018, 12:28 PM
1<!doctype html>
2<html lang="en" dir="ltr">
3<head>
4
5<meta charset="utf-8">
6
7<head>
8 <meta charset="utf-8">
9 <meta http-equiv="X-UA-Compatible" content="IE=edge">
10 <meta name="viewport" content="width=device-width, initial-scale=1.0, maximum-scale=2, minimum-scale=1.0, user-scalable=1">
11
12 <link rel="apple-touch-icon" sizes="180x180" href="/apple-touch-icon.png">
13 <link rel="icon" type="image/png" sizes="32x32" href="/favicon-32x32.png">
14 <link rel="icon" type="image/png" sizes="16x16" href="/favicon-16x16.png">
15 <link rel="manifest" href="/manifest.json">
16 <link rel="mask-icon" href="/safari-pinned-tab.svg" color="#373737">
17 <meta name="theme-color" content="#373737">
18 <meta name="version" content="5.5.2">
19
20
21 <!-- head title -->
22 <title>Tiger und Drache - Toradora! - Neue Folgen Staffel 1 Folge 1 im Online-Stream | WATCHBOX</title> <!-- /head title -->
23
24 <!-- head meta -->
25 <meta name="description" content="Spannende Episoden der 1. Staffel von â–º Toradora! - Neue Folgen und viele weitere Serien aus dem Genre â–º Anime kostenlos im Online-Stream bei WATCHBOX.">
26<meta name="robots" content="index,follow">
27<meta property="og:type" content="article">
28<meta property="og:url" content="https://www.watchbox.de/serien/toradora-15561/staffel-1/tiger-und-drache-387850.html">
29<meta property="og:title" content="Tiger und Drache - Toradora! - Neue Folgen Staffel 1 Folge 1 im Online-Stream">
30<meta property="og:description" content="Spannende Episoden der 1. Staffel von â–º Toradora! - Neue Folgen und viele weitere Serien aus dem Genre â–º Anime kostenlos im Online-Stream bei WATCHBOX.">
31<meta property="og:site_name" content="watchbox.de">
32<meta property="og:locale" content="de_DE">
33<meta property="og:image" content="https://aiswatchbox-a.akamaihd.net/watchbox/format/15561/26-1/1920x1080/480/toradora-neue-folgen.jpg">
34<meta property="og:image:secure_url" content="//aiswatchbox-a.akamaihd.net/watchbox/format/15561/26-1/1920x1080/480/toradora-neue-folgen.jpg">
35<meta property="al:ios:url" content="clipfish://video/387850">
36<meta property="al:ios:app_store_id" content="402493202">
37<meta property="al:ios:app_name" content="WATCHBOX">
38<meta property="al:android:url" content="clipfish://video/387850">
39<meta property="al:android:package" content="com.rtli.clipfish">
40<meta property="al:android:app_name" content="WATCHBOX">
41<meta property="test-country" content="DE">
42<meta name="keywords" content="Toradora!, Anime, TV NOW, WATCHBOX bei TV NOW, Serie, Anime, Schule, Schülerin, Liebe, Schüler, Freundschaft, video, gratis, kostenlos, Anime, dub, deutsche Fassung, deutsch, Stream, Serie, Anime-Stream, Online-Stream">
43 <meta property="fb:app_id" content="114293468607049">
44<meta property="fb:pages" content="30348199168">
45<meta property="article:publisher" content="https://www.facebook.com/WATCHBOX">
46<meta property="article:author" content="https://www.facebook.com/WATCHBOX">
47<meta name="twitter:card" content="summary">
48<meta name="twitter:site" content="@WATCHBOX">
49<meta name="twitter:title" content="Tiger und Drache - Toradora! - Neue Folgen Staffel 1 Folge 1 im Online-Stream">
50<meta name="twitter:description" content="Spannende Episoden der 1. Staffel von â–º Toradora! - Neue Folgen und viele weitere Serien aus dem Genre â–º Anime kostenlos im Online-Stream bei WATCHBOX.">
51<meta name="twitter:image" content="https://aiswatchbox-a.akamaihd.net/watchbox/format/15561/26-1/1920x1080/480/toradora-neue-folgen.jpg">
52 <!-- /head meta -->
53
54
55 <!-- ga opt-out cookie-->
56 <script id="facebook-jssdk" src="//connect.facebook.net/de_DE/sdk.js"></script><script id="tc_script_42_1" type="text/javascript" defer="" async="" src="//trck.spoteffects.net/analytics/spef.min.js"></script><script async="" src="//www.google-analytics.com/analytics.js"></script><script id="twitter-wjs" src="https://platform.twitter.com/widgets.js"></script><script src="https://connect.facebook.net/signals/config/1553267744893843?v=2.8.12&r=stable" async=""></script><script async="" src="https://connect.facebook.net/en_US/fbevents.js"></script><script type="application/javascript">
57 var gaProperty = 'UA-1928982-7';
58 var disableStr = 'ga-disable-' + gaProperty;
59 if (document.cookie.indexOf(disableStr + '=true') > -1) {
60 window[disableStr] = true;
61 }
62
63 function gaOptout() {
64 document.cookie = disableStr + '=true; expires=Thu, 31 Dec 2099 23:59:59 UTC; path=/';
65 window[disableStr] = true;
66 alert('Google Analytics wurde deaktiviert');
67 }
68 </script>
69 <!-- /ga opt-out cookie-->
70
71 <!-- global const -->
72 <script type="application/javascript">
73 var APP_DEVICE_CLASS = "desktop";
74 var APP_ENV = "production";
75 var APP_VERSION = "5.5.2";
76
77
78 var FB_APP_ID = '114293468607049';
79 var API_URL = 'https://api.watchbox.de';
80 var API_VERSION = 'v1';
81 </script>
82 <!-- /global const -->
83
84
85 <!-- head link -->
86 <link href="/videoplayer/cbc-videoplayer-5.5.2.css" media="screen" rel="stylesheet" type="text/css">
87<link href="https://www.watchbox.de/serien/toradora-15561/staffel-1/tiger-und-drache-387850.html" rel="canonical">
88<link href="/css/responsive-5.5.2.css" media="screen" rel="stylesheet" type="text/css"> <!-- /head link -->
89
90 <!-- head style -->
91 <!-- /head style -->
92
93 <!-- head script -->
94 <script type="text/javascript" src="/js/css-helpers-5.5.2.js"></script> <script type="text/javascript" src="https://script.ioam.de/iam.js"> </script>
95
96<script id="ipadcontrol" async="" type="text/javascript" src="//bilder-a.akamaihd.net/ip/js/ipdvdc/ipdvdc.min.js">
97$AC.loadConfig({"autoDetection":true,"nuggadID":131801462,"ivw":"\/watchbox\/formate\/toradora\/home","admeta":{"domain":"bilder-a.akamaihd.net","path":"\/ip\/","file":"vc-meta.xml"}});
98</script>
99<script type="text/javascript">
100(function(c){var b={cache:{},addValue:function(a,c){b.cache[a]=c},getValue:function(a){return"undefined"===typeof b.cache[a]?null:b.cache[a]}};c.Valueholder=b})(window.RTLi||(window.RTLi={}));
101RTLi.Valueholder.addValue("videoplaza_share", null);
102RTLi.Valueholder.addValue("ivw_initial", "\/watchbox\/formate\/toradora\/home");
103</script>
104<script type="text/javascript">
105
106 var videoAdsParams = {
107 admeta: "http:\/\/bilder-a.akamaihd.net\/ip\/vc-meta.xml",
108 adclasses: "30,150,240,99999",
109 /* Klasse 0 : -0:29, Klasse 1 : 0:30-2:29, Klasse 2: 2:30-3:59, Klasse 3 : 4:00- (99999) */
110 adconfig: "1,1,0,0,0,0,0,0; 1,1,1,0,0,0,1,1; 1,1,1,0,0,0,1,1; 2,1,1,2,0,0,1,1;",
111 // @deprecated
112 adcall: "",
113 getAdcall: function() { return ""; },
114 };
115
116</script><script type="text/javascript">
117//<![CDATA[
118var ivw = '\/watchbox\/formate\/toradora\/home';
119var _initialIVW = '\/watchbox\/formate\/toradora\/home';
120if ((typeof iam_data === 'object') && (typeof iam_data.cp === 'string')) {
121 var agof2 = iam_data.cp;
122}
123if ((typeof iam_data === 'object') && (typeof iam_data.st === 'string') && _szmAngebot === '') {
124 var _szmAngebot = iam_data.st;
125}
126//]]>
127</script>
128 <!-- bugsnag -->
129 <script src="//d2wy8f7a9ursnm.cloudfront.net/bugsnag-3.min.js" data-apikey="d2f5d9379f6b9bf6718bfec240188632"></script>
130 <script>
131 if (window.location.hostname.match(/staging.watchbox.de|abnahme\./i)) {
132 Bugsnag.releaseStage = "staging";
133 }
134 else if (null !== window.location.hostname.match(/box.rtlnm.de|dev\./i)) {
135 Bugsnag.releaseStage = "staging";
136 }
137 else {
138 Bugsnag.releaseStage = "production";
139 }
140 Bugsnag.notifyReleaseStages = ["staging", "production"];
141 Bugsnag.endpoint = "https://notify-bugs-fra1.rtl.de/js";
142 Bugsnag.appVersion = APP_VERSION;
143 Bugsnag.beforeNotify = function(payload) {
144 // Only notify Scripts by CBC
145 if (typeof payload.file !== "undefined") {
146 if (payload.file.match(/cbc-videoplayer-smartclip/i) !== null) {
147 return false;
148 }
149
150 var matchExternalError = payload.message.match(/Exception thrown and not caught/i);
151 var matchExternalScript = payload.stacktrace.match(/main.js/i);
152 if (matchExternalError && matchExternalScript) {
153 payload.name = "WatchboxError";
154 payload.metaData.groupingHash = "Exception thrown and not caught fkrom main.js";
155 }
156
157 var matchTracking = payload.message.match(/'trackEvent' of undefined|tracking is not defined/i);
158 if (matchTracking) {
159 payload.name = "WatchboxError";
160 payload.metaData.groupingHash = "trackEventOfUndefined";
161 }
162
163 var match = payload.file.match(/watchbox.de|box.rtlnm.de|static-fra.de/i);
164 return !!(match && match[0].length > 0);
165 }
166 return false;
167 };
168 </script>
169 <!-- /bugsnag -->
170
171 <!-- Videoplayer Tracking -->
172 <script src="https://cdn-gl.imrworldwide.com/novms/js/2/ggcmb510.js"></script>
173 <script src="https://cdn.static-fra.de/lib/rtli/rtli-js-tracking/build/RTLiVideotracking.min.js"></script>
174 <!-- /Videoplayer Tracking -->
175
176 <!-- Optimizely -->
177 <script src="https://cdn.optimizely.com/js/8320120834.js"></script><iframe src="https://a4240511539.cdn.optimizely.com/client_storage/a4240511539.html" hidden="" aria-hidden="true" tabindex="-1"></iframe> <!-- /Optimizely -->
178
179 <!-- Facebook Pixel Code -->
180 <script>
181 !function(f, b, e, v, n, t, s) {
182 if (f.fbq) return;
183 n = f.fbq = function() {
184 n.callMethod ?
185 n.callMethod.apply(n, arguments) : n.queue.push(arguments)
186 };
187 if (!f._fbq) f._fbq = n;
188 n.push = n;
189 n.loaded = !0;
190 n.version = '2.0';
191 n.queue = [];
192 t = b.createElement(e);
193 t.async = !0;
194 t.src = v;
195 s = b.getElementsByTagName(e)[0];
196 s.parentNode.insertBefore(t, s)
197 }(window, document, 'script',
198 'https://connect.facebook.net/en_US/fbevents.js');
199 fbq('init', '1553267744893843');
200 fbq('track', 'PageView');
201 </script>
202 <noscript>
203 <img height="1" width="1" src="https://www.facebook.com/tr?id=1553267744893843&ev=PageView&noscript=1"/>
204 </noscript>
205 <!-- End Facebook Pixel Code -->
206
207 <!-- /head script -->
208
209 <!-- Google Search Gallery Markup-->
210 <script type="application/ld+json">{
211 "@context": "http://schema.org",
212 "@type": "Organization",
213 "url": "https://www.watchbox.de",
214 "logo": "https://www.watchbox.de/images/watchbox_logo_1920x1080.jpg"
215 }</script>
216 <!-- /Google Search Gallery Markup -->
217
218 <!-- Tag Commander dataLayer/tc_vars-->
219 <script>
220 var tc_vars = {"page_ivw_level_1":"watchbox","page_ivw_level_2":"formate","page_ivw_level_3":"toradora","page_ivw_level_4":"home","env_device":"Online","user_country":"DE","agof2_belegungseinheit":"dbrsowf_ten_wbtoradora"};
221
222 try {
223 var wbcookies = document.cookie.split(";");
224 for (var wbi = 0; wbi < wbcookies.length; wbi++) {
225 var wbcookie = wbcookies[wbi];
226 while (wbcookie.charAt(0) === " ") {
227 wbcookie = wbcookie.substring(1);
228 }
229 if (wbcookie.indexOf("watchbox_auth=") === 0) {
230 tc_vars.userID = JSON.parse(decodeURIComponent(wbcookie.split("=", 2)[1])).id;
231 tc_vars.isLoggedIn = "Ja";
232 }
233 }
234 } catch (e) {
235 window.cookieError = { message: "Fehler beim auslesen des Cookie", stacktrace: e };
236 tc_vars.userID = undefined;
237 }
238
239
240 </script>
241 <!-- /Tag Commander dataLayer/tc_vars-->
242<script type="text/javascript" async="" src="https://bilder-a.akamaihd.net/ip/js/ipdvdc/blockadblock.min.js"></script><script type="text/javascript" async="" id="nuggad_131801462" src="https://ip-s.nuggad.net/rc?nuggn=2059506885&nuggsid=131801462"></script><script type="text/javascript" async="" id="technical_service" src="https://www.technical-service.net/get"></script><style type="text/css">.fb_hidden{position:absolute;top:-10000px;z-index:10001}.fb_reposition{overflow:hidden;position:relative}.fb_invisible{display:none}.fb_reset{background:none;border:0;border-spacing:0;color:#000;cursor:auto;direction:ltr;font-family:"lucida grande", tahoma, verdana, arial, sans-serif;font-size:11px;font-style:normal;font-variant:normal;font-weight:normal;letter-spacing:normal;line-height:1;margin:0;overflow:visible;padding:0;text-align:left;text-decoration:none;text-indent:0;text-shadow:none;text-transform:none;visibility:visible;white-space:normal;word-spacing:normal}.fb_reset>div{overflow:hidden}.fb_link img{border:none}@keyframes fb_transform{from{opacity:0;transform:scale(.95)}to{opacity:1;transform:scale(1)}}.fb_animate{animation:fb_transform .3s forwards}
243.fb_dialog{background:rgba(82, 82, 82, .7);position:absolute;top:-10000px;z-index:10001}.fb_reset .fb_dialog_legacy{overflow:visible}.fb_dialog_advanced{padding:10px;border-radius:8px}.fb_dialog_content{background:#fff;color:#333}.fb_dialog_close_icon{background:url(https://static.xx.fbcdn.net/rsrc.php/v3/yq/r/IE9JII6Z1Ys.png) no-repeat scroll 0 0 transparent;cursor:pointer;display:block;height:15px;position:absolute;right:18px;top:17px;width:15px}.fb_dialog_mobile .fb_dialog_close_icon{top:5px;left:5px;right:auto}.fb_dialog_padding{background-color:transparent;position:absolute;width:1px;z-index:-1}.fb_dialog_close_icon:hover{background:url(https://static.xx.fbcdn.net/rsrc.php/v3/yq/r/IE9JII6Z1Ys.png) no-repeat scroll 0 -15px transparent}.fb_dialog_close_icon:active{background:url(https://static.xx.fbcdn.net/rsrc.php/v3/yq/r/IE9JII6Z1Ys.png) no-repeat scroll 0 -30px transparent}.fb_dialog_loader{background-color:#f6f7f9;border:1px solid #606060;font-size:24px;padding:20px}.fb_dialog_top_left,.fb_dialog_top_right,.fb_dialog_bottom_left,.fb_dialog_bottom_right{height:10px;width:10px;overflow:hidden;position:absolute}.fb_dialog_top_left{background:url(https://static.xx.fbcdn.net/rsrc.php/v3/ye/r/8YeTNIlTZjm.png) no-repeat 0 0;left:-10px;top:-10px}.fb_dialog_top_right{background:url(https://static.xx.fbcdn.net/rsrc.php/v3/ye/r/8YeTNIlTZjm.png) no-repeat 0 -10px;right:-10px;top:-10px}.fb_dialog_bottom_left{background:url(https://static.xx.fbcdn.net/rsrc.php/v3/ye/r/8YeTNIlTZjm.png) no-repeat 0 -20px;bottom:-10px;left:-10px}.fb_dialog_bottom_right{background:url(https://static.xx.fbcdn.net/rsrc.php/v3/ye/r/8YeTNIlTZjm.png) no-repeat 0 -30px;right:-10px;bottom:-10px}.fb_dialog_vert_left,.fb_dialog_vert_right,.fb_dialog_horiz_top,.fb_dialog_horiz_bottom{position:absolute;background:#525252;filter:alpha(opacity=70);opacity:.7}.fb_dialog_vert_left,.fb_dialog_vert_right{width:10px;height:100%}.fb_dialog_vert_left{margin-left:-10px}.fb_dialog_vert_right{right:0;margin-right:-10px}.fb_dialog_horiz_top,.fb_dialog_horiz_bottom{width:100%;height:10px}.fb_dialog_horiz_top{margin-top:-10px}.fb_dialog_horiz_bottom{bottom:0;margin-bottom:-10px}.fb_dialog_iframe{line-height:0}.fb_dialog_content .dialog_title{background:#6d84b4;border:1px solid #365899;color:#fff;font-size:14px;font-weight:bold;margin:0}.fb_dialog_content .dialog_title>span{background:url(https://static.xx.fbcdn.net/rsrc.php/v3/yd/r/Cou7n-nqK52.gif) no-repeat 5px 50%;float:left;padding:5px 0 7px 26px}body.fb_hidden{-webkit-transform:none;height:100%;margin:0;overflow:visible;position:absolute;top:-10000px;left:0;width:100%}.fb_dialog.fb_dialog_mobile.loading{background:url(https://static.xx.fbcdn.net/rsrc.php/v3/ya/r/3rhSv5V8j3o.gif) white no-repeat 50% 50%;min-height:100%;min-width:100%;overflow:hidden;position:absolute;top:0;z-index:10001}.fb_dialog.fb_dialog_mobile.loading.centered{width:auto;height:auto;min-height:initial;min-width:initial;background:none}.fb_dialog.fb_dialog_mobile.loading.centered #fb_dialog_loader_spinner{width:100%}.fb_dialog.fb_dialog_mobile.loading.centered .fb_dialog_content{background:none}.loading.centered #fb_dialog_loader_close{color:#fff;display:block;padding-top:20px;clear:both;font-size:18px}#fb-root #fb_dialog_ipad_overlay{background:rgba(0, 0, 0, .45);position:absolute;bottom:0;left:0;right:0;top:0;width:100%;min-height:100%;z-index:10000}#fb-root #fb_dialog_ipad_overlay.hidden{display:none}.fb_dialog.fb_dialog_mobile.loading iframe{visibility:hidden}.fb_dialog_content .dialog_header{-webkit-box-shadow:white 0 1px 1px -1px inset;background:-webkit-gradient(linear, 0% 0%, 0% 100%, from(#738ABA), to(#2C4987));border-bottom:1px solid;border-color:#1d4088;color:#fff;font:14px Helvetica, sans-serif;font-weight:bold;text-overflow:ellipsis;text-shadow:rgba(0, 30, 84, .296875) 0 -1px 0;vertical-align:middle;white-space:nowrap}.fb_dialog_content .dialog_header table{-webkit-font-smoothing:subpixel-antialiased;height:43px;width:100%}.fb_dialog_content .dialog_header td.header_left{font-size:12px;padding-left:5px;vertical-align:middle;width:60px}.fb_dialog_content .dialog_header td.header_right{font-size:12px;padding-right:5px;vertical-align:middle;width:60px}.fb_dialog_content .touchable_button{background:-webkit-gradient(linear, 0% 0%, 0% 100%, from(#4966A6), color-stop(.5, #355492), to(#2A4887));border:1px solid #29487d;-webkit-background-clip:padding-box;-webkit-border-radius:3px;-webkit-box-shadow:rgba(0, 0, 0, .117188) 0 1px 1px inset, rgba(255, 255, 255, .167969) 0 1px 0;display:inline-block;margin-top:3px;max-width:85px;line-height:18px;padding:4px 12px;position:relative}.fb_dialog_content .dialog_header .touchable_button input{border:none;background:none;color:#fff;font:12px Helvetica, sans-serif;font-weight:bold;margin:2px -12px;padding:2px 6px 3px 6px;text-shadow:rgba(0, 30, 84, .296875) 0 -1px 0}.fb_dialog_content .dialog_header .header_center{color:#fff;font-size:16px;font-weight:bold;line-height:18px;text-align:center;vertical-align:middle}.fb_dialog_content .dialog_content{background:url(https://static.xx.fbcdn.net/rsrc.php/v3/y9/r/jKEcVPZFk-2.gif) no-repeat 50% 50%;border:1px solid #555;border-bottom:0;border-top:0;height:150px}.fb_dialog_content .dialog_footer{background:#f6f7f9;border:1px solid #555;border-top-color:#ccc;height:40px}#fb_dialog_loader_close{float:left}.fb_dialog.fb_dialog_mobile .fb_dialog_close_button{text-shadow:rgba(0, 30, 84, .296875) 0 -1px 0}.fb_dialog.fb_dialog_mobile .fb_dialog_close_icon{visibility:hidden}#fb_dialog_loader_spinner{animation:rotateSpinner 1.2s linear infinite;background-color:transparent;background-image:url(https://static.xx.fbcdn.net/rsrc.php/v3/yD/r/t-wz8gw1xG1.png);background-repeat:no-repeat;background-position:50% 50%;height:24px;width:24px}@keyframes rotateSpinner{0%{transform:rotate(0deg)}100%{transform:rotate(360deg)}}
244.fb_iframe_widget{display:inline-block;position:relative}.fb_iframe_widget span{display:inline-block;position:relative;text-align:justify}.fb_iframe_widget iframe{position:absolute}.fb_iframe_widget_fluid_desktop,.fb_iframe_widget_fluid_desktop span,.fb_iframe_widget_fluid_desktop iframe{max-width:100%}.fb_iframe_widget_fluid_desktop iframe{min-width:220px;position:relative}.fb_iframe_widget_lift{z-index:1}.fb_hide_iframes iframe{position:relative;left:-10000px}.fb_iframe_widget_loader{position:relative;display:inline-block}.fb_iframe_widget_fluid{display:inline}.fb_iframe_widget_fluid span{width:100%}.fb_iframe_widget_loader iframe{min-height:32px;z-index:2;zoom:1}.fb_iframe_widget_loader .FB_Loader{background:url(https://static.xx.fbcdn.net/rsrc.php/v3/y9/r/jKEcVPZFk-2.gif) no-repeat;height:32px;width:32px;margin-left:-16px;position:absolute;left:50%;z-index:4}
245.fb_customer_chat_bounce_in{animation-duration:250ms;animation-name:fb_bounce_in}.fb_customer_chat_bounce_out{animation-duration:250ms;animation-name:fb_fade_out}.fb_invisible_flow{display:inherit;height:0;overflow-x:hidden;width:0}.fb_mobile_overlay_active{background-color:#fff;height:100%;overflow:hidden;position:fixed;visibility:hidden;width:100%}@keyframes fb_fade_out{from{opacity:1}to{opacity:0}}@keyframes fb_bounce_in{0%{opacity:0;transform:scale(.8, .8);transform-origin:100% 100%}10%{opacity:.1}20%{opacity:.2}30%{opacity:.3}40%{opacity:.4}50%{opacity:.5}60%{opacity:.6}70%{opacity:.7}80%{opacity:.8;transform:scale(1.03, 1.03)}90{opacity:.9}100%{opacity:1;transform:scale(1, 1)}}</style><script type="text/javascript">/*!
246 * jQuery JavaScript Library v3.3.1
247 * https://jquery.com/
248 *
249 * Includes Sizzle.js
250 * https://sizzlejs.com/
251 *
252 * Copyright JS Foundation and other contributors
253 * Released under the MIT license
254 * https://jquery.org/license
255 *
256 * Date: 2018-01-20T17:24Z
257 */
258( function( global, factory ) {
259
260 "use strict";
261
262 if ( typeof module === "object" && typeof module.exports === "object" ) {
263
264 // For CommonJS and CommonJS-like environments where a proper `window`
265 // is present, execute the factory and get jQuery.
266 // For environments that do not have a `window` with a `document`
267 // (such as Node.js), expose a factory as module.exports.
268 // This accentuates the need for the creation of a real `window`.
269 // e.g. var jQuery = require("jquery")(window);
270 // See ticket #14549 for more info.
271 module.exports = global.document ?
272 factory( global, true ) :
273 function( w ) {
274 if ( !w.document ) {
275 throw new Error( "jQuery requires a window with a document" );
276 }
277 return factory( w );
278 };
279 } else {
280 factory( global );
281 }
282
283// Pass this if window is not defined yet
284} )( typeof window !== "undefined" ? window : this, function( window, noGlobal ) {
285
286// Edge <= 12 - 13+, Firefox <=18 - 45+, IE 10 - 11, Safari 5.1 - 9+, iOS 6 - 9.1
287// throw exceptions when non-strict code (e.g., ASP.NET 4.5) accesses strict mode
288// arguments.callee.caller (trac-13335). But as of jQuery 3.0 (2016), strict mode should be common
289// enough that all such attempts are guarded in a try block.
290"use strict";
291
292var arr = [];
293
294var document = window.document;
295
296var getProto = Object.getPrototypeOf;
297
298var slice = arr.slice;
299
300var concat = arr.concat;
301
302var push = arr.push;
303
304var indexOf = arr.indexOf;
305
306var class2type = {};
307
308var toString = class2type.toString;
309
310var hasOwn = class2type.hasOwnProperty;
311
312var fnToString = hasOwn.toString;
313
314var ObjectFunctionString = fnToString.call( Object );
315
316var support = {};
317
318var isFunction = function isFunction( obj ) {
319
320 // Support: Chrome <=57, Firefox <=52
321 // In some browsers, typeof returns "function" for HTML <object> elements
322 // (i.e., `typeof document.createElement( "object" ) === "function"`).
323 // We don't want to classify *any* DOM node as a function.
324 return typeof obj === "function" && typeof obj.nodeType !== "number";
325 };
326
327
328var isWindow = function isWindow( obj ) {
329 return obj != null && obj === obj.window;
330 };
331
332
333
334
335 var preservedScriptAttributes = {
336 type: true,
337 src: true,
338 noModule: true
339 };
340
341 function DOMEval( code, doc, node ) {
342 doc = doc || document;
343
344 var i,
345 script = doc.createElement( "script" );
346
347 script.text = code;
348 if ( node ) {
349 for ( i in preservedScriptAttributes ) {
350 if ( node[ i ] ) {
351 script[ i ] = node[ i ];
352 }
353 }
354 }
355 doc.head.appendChild( script ).parentNode.removeChild( script );
356 }
357
358
359function toType( obj ) {
360 if ( obj == null ) {
361 return obj + "";
362 }
363
364 // Support: Android <=2.3 only (functionish RegExp)
365 return typeof obj === "object" || typeof obj === "function" ?
366 class2type[ toString.call( obj ) ] || "object" :
367 typeof obj;
368}
369/* global Symbol */
370// Defining this global in .eslintrc.json would create a danger of using the global
371// unguarded in another place, it seems safer to define global only for this module
372
373
374
375var
376 version = "3.3.1",
377
378 // Define a local copy of jQuery
379 jQuery = function( selector, context ) {
380
381 // The jQuery object is actually just the init constructor 'enhanced'
382 // Need init if jQuery is called (just allow error to be thrown if not included)
383 return new jQuery.fn.init( selector, context );
384 },
385
386 // Support: Android <=4.0 only
387 // Make sure we trim BOM and NBSP
388 rtrim = /^[\s\uFEFF\xA0]+|[\s\uFEFF\xA0]+$/g;
389
390jQuery.fn = jQuery.prototype = {
391
392 // The current version of jQuery being used
393 jquery: version,
394
395 constructor: jQuery,
396
397 // The default length of a jQuery object is 0
398 length: 0,
399
400 toArray: function() {
401 return slice.call( this );
402 },
403
404 // Get the Nth element in the matched element set OR
405 // Get the whole matched element set as a clean array
406 get: function( num ) {
407
408 // Return all the elements in a clean array
409 if ( num == null ) {
410 return slice.call( this );
411 }
412
413 // Return just the one element from the set
414 return num < 0 ? this[ num + this.length ] : this[ num ];
415 },
416
417 // Take an array of elements and push it onto the stack
418 // (returning the new matched element set)
419 pushStack: function( elems ) {
420
421 // Build a new jQuery matched element set
422 var ret = jQuery.merge( this.constructor(), elems );
423
424 // Add the old object onto the stack (as a reference)
425 ret.prevObject = this;
426
427 // Return the newly-formed element set
428 return ret;
429 },
430
431 // Execute a callback for every element in the matched set.
432 each: function( callback ) {
433 return jQuery.each( this, callback );
434 },
435
436 map: function( callback ) {
437 return this.pushStack( jQuery.map( this, function( elem, i ) {
438 return callback.call( elem, i, elem );
439 } ) );
440 },
441
442 slice: function() {
443 return this.pushStack( slice.apply( this, arguments ) );
444 },
445
446 first: function() {
447 return this.eq( 0 );
448 },
449
450 last: function() {
451 return this.eq( -1 );
452 },
453
454 eq: function( i ) {
455 var len = this.length,
456 j = +i + ( i < 0 ? len : 0 );
457 return this.pushStack( j >= 0 && j < len ? [ this[ j ] ] : [] );
458 },
459
460 end: function() {
461 return this.prevObject || this.constructor();
462 },
463
464 // For internal use only.
465 // Behaves like an Array's method, not like a jQuery method.
466 push: push,
467 sort: arr.sort,
468 splice: arr.splice
469};
470
471jQuery.extend = jQuery.fn.extend = function() {
472 var options, name, src, copy, copyIsArray, clone,
473 target = arguments[ 0 ] || {},
474 i = 1,
475 length = arguments.length,
476 deep = false;
477
478 // Handle a deep copy situation
479 if ( typeof target === "boolean" ) {
480 deep = target;
481
482 // Skip the boolean and the target
483 target = arguments[ i ] || {};
484 i++;
485 }
486
487 // Handle case when target is a string or something (possible in deep copy)
488 if ( typeof target !== "object" && !isFunction( target ) ) {
489 target = {};
490 }
491
492 // Extend jQuery itself if only one argument is passed
493 if ( i === length ) {
494 target = this;
495 i--;
496 }
497
498 for ( ; i < length; i++ ) {
499
500 // Only deal with non-null/undefined values
501 if ( ( options = arguments[ i ] ) != null ) {
502
503 // Extend the base object
504 for ( name in options ) {
505 src = target[ name ];
506 copy = options[ name ];
507
508 // Prevent never-ending loop
509 if ( target === copy ) {
510 continue;
511 }
512
513 // Recurse if we're merging plain objects or arrays
514 if ( deep && copy && ( jQuery.isPlainObject( copy ) ||
515 ( copyIsArray = Array.isArray( copy ) ) ) ) {
516
517 if ( copyIsArray ) {
518 copyIsArray = false;
519 clone = src && Array.isArray( src ) ? src : [];
520
521 } else {
522 clone = src && jQuery.isPlainObject( src ) ? src : {};
523 }
524
525 // Never move original objects, clone them
526 target[ name ] = jQuery.extend( deep, clone, copy );
527
528 // Don't bring in undefined values
529 } else if ( copy !== undefined ) {
530 target[ name ] = copy;
531 }
532 }
533 }
534 }
535
536 // Return the modified object
537 return target;
538};
539
540jQuery.extend( {
541
542 // Unique for each copy of jQuery on the page
543 expando: "jQuery" + ( version + Math.random() ).replace( /\D/g, "" ),
544
545 // Assume jQuery is ready without the ready module
546 isReady: true,
547
548 error: function( msg ) {
549 throw new Error( msg );
550 },
551
552 noop: function() {},
553
554 isPlainObject: function( obj ) {
555 var proto, Ctor;
556
557 // Detect obvious negatives
558 // Use toString instead of jQuery.type to catch host objects
559 if ( !obj || toString.call( obj ) !== "[object Object]" ) {
560 return false;
561 }
562
563 proto = getProto( obj );
564
565 // Objects with no prototype (e.g., `Object.create( null )`) are plain
566 if ( !proto ) {
567 return true;
568 }
569
570 // Objects with prototype are plain iff they were constructed by a global Object function
571 Ctor = hasOwn.call( proto, "constructor" ) && proto.constructor;
572 return typeof Ctor === "function" && fnToString.call( Ctor ) === ObjectFunctionString;
573 },
574
575 isEmptyObject: function( obj ) {
576
577 /* eslint-disable no-unused-vars */
578 // See https://github.com/eslint/eslint/issues/6125
579 var name;
580
581 for ( name in obj ) {
582 return false;
583 }
584 return true;
585 },
586
587 // Evaluates a script in a global context
588 globalEval: function( code ) {
589 DOMEval( code );
590 },
591
592 each: function( obj, callback ) {
593 var length, i = 0;
594
595 if ( isArrayLike( obj ) ) {
596 length = obj.length;
597 for ( ; i < length; i++ ) {
598 if ( callback.call( obj[ i ], i, obj[ i ] ) === false ) {
599 break;
600 }
601 }
602 } else {
603 for ( i in obj ) {
604 if ( callback.call( obj[ i ], i, obj[ i ] ) === false ) {
605 break;
606 }
607 }
608 }
609
610 return obj;
611 },
612
613 // Support: Android <=4.0 only
614 trim: function( text ) {
615 return text == null ?
616 "" :
617 ( text + "" ).replace( rtrim, "" );
618 },
619
620 // results is for internal usage only
621 makeArray: function( arr, results ) {
622 var ret = results || [];
623
624 if ( arr != null ) {
625 if ( isArrayLike( Object( arr ) ) ) {
626 jQuery.merge( ret,
627 typeof arr === "string" ?
628 [ arr ] : arr
629 );
630 } else {
631 push.call( ret, arr );
632 }
633 }
634
635 return ret;
636 },
637
638 inArray: function( elem, arr, i ) {
639 return arr == null ? -1 : indexOf.call( arr, elem, i );
640 },
641
642 // Support: Android <=4.0 only, PhantomJS 1 only
643 // push.apply(_, arraylike) throws on ancient WebKit
644 merge: function( first, second ) {
645 var len = +second.length,
646 j = 0,
647 i = first.length;
648
649 for ( ; j < len; j++ ) {
650 first[ i++ ] = second[ j ];
651 }
652
653 first.length = i;
654
655 return first;
656 },
657
658 grep: function( elems, callback, invert ) {
659 var callbackInverse,
660 matches = [],
661 i = 0,
662 length = elems.length,
663 callbackExpect = !invert;
664
665 // Go through the array, only saving the items
666 // that pass the validator function
667 for ( ; i < length; i++ ) {
668 callbackInverse = !callback( elems[ i ], i );
669 if ( callbackInverse !== callbackExpect ) {
670 matches.push( elems[ i ] );
671 }
672 }
673
674 return matches;
675 },
676
677 // arg is for internal usage only
678 map: function( elems, callback, arg ) {
679 var length, value,
680 i = 0,
681 ret = [];
682
683 // Go through the array, translating each of the items to their new values
684 if ( isArrayLike( elems ) ) {
685 length = elems.length;
686 for ( ; i < length; i++ ) {
687 value = callback( elems[ i ], i, arg );
688
689 if ( value != null ) {
690 ret.push( value );
691 }
692 }
693
694 // Go through every key on the object,
695 } else {
696 for ( i in elems ) {
697 value = callback( elems[ i ], i, arg );
698
699 if ( value != null ) {
700 ret.push( value );
701 }
702 }
703 }
704
705 // Flatten any nested arrays
706 return concat.apply( [], ret );
707 },
708
709 // A global GUID counter for objects
710 guid: 1,
711
712 // jQuery.support is not used in Core but other projects attach their
713 // properties to it so it needs to exist.
714 support: support
715} );
716
717if ( typeof Symbol === "function" ) {
718 jQuery.fn[ Symbol.iterator ] = arr[ Symbol.iterator ];
719}
720
721// Populate the class2type map
722jQuery.each( "Boolean Number String Function Array Date RegExp Object Error Symbol".split( " " ),
723function( i, name ) {
724 class2type[ "[object " + name + "]" ] = name.toLowerCase();
725} );
726
727function isArrayLike( obj ) {
728
729 // Support: real iOS 8.2 only (not reproducible in simulator)
730 // `in` check used to prevent JIT error (gh-2145)
731 // hasOwn isn't used here due to false negatives
732 // regarding Nodelist length in IE
733 var length = !!obj && "length" in obj && obj.length,
734 type = toType( obj );
735
736 if ( isFunction( obj ) || isWindow( obj ) ) {
737 return false;
738 }
739
740 return type === "array" || length === 0 ||
741 typeof length === "number" && length > 0 && ( length - 1 ) in obj;
742}
743var Sizzle =
744/*!
745 * Sizzle CSS Selector Engine v2.3.3
746 * https://sizzlejs.com/
747 *
748 * Copyright jQuery Foundation and other contributors
749 * Released under the MIT license
750 * http://jquery.org/license
751 *
752 * Date: 2016-08-08
753 */
754(function( window ) {
755
756var i,
757 support,
758 Expr,
759 getText,
760 isXML,
761 tokenize,
762 compile,
763 select,
764 outermostContext,
765 sortInput,
766 hasDuplicate,
767
768 // Local document vars
769 setDocument,
770 document,
771 docElem,
772 documentIsHTML,
773 rbuggyQSA,
774 rbuggyMatches,
775 matches,
776 contains,
777
778 // Instance-specific data
779 expando = "sizzle" + 1 * new Date(),
780 preferredDoc = window.document,
781 dirruns = 0,
782 done = 0,
783 classCache = createCache(),
784 tokenCache = createCache(),
785 compilerCache = createCache(),
786 sortOrder = function( a, b ) {
787 if ( a === b ) {
788 hasDuplicate = true;
789 }
790 return 0;
791 },
792
793 // Instance methods
794 hasOwn = ({}).hasOwnProperty,
795 arr = [],
796 pop = arr.pop,
797 push_native = arr.push,
798 push = arr.push,
799 slice = arr.slice,
800 // Use a stripped-down indexOf as it's faster than native
801 // https://jsperf.com/thor-indexof-vs-for/5
802 indexOf = function( list, elem ) {
803 var i = 0,
804 len = list.length;
805 for ( ; i < len; i++ ) {
806 if ( list[i] === elem ) {
807 return i;
808 }
809 }
810 return -1;
811 },
812
813 booleans = "checked|selected|async|autofocus|autoplay|controls|defer|disabled|hidden|ismap|loop|multiple|open|readonly|required|scoped",
814
815 // Regular expressions
816
817 // http://www.w3.org/TR/css3-selectors/#whitespace
818 whitespace = "[\\x20\\t\\r\\n\\f]",
819
820 // http://www.w3.org/TR/CSS21/syndata.html#value-def-identifier
821 identifier = "(?:\\\\.|[\\w-]|[^\0-\\xa0])+",
822
823 // Attribute selectors: http://www.w3.org/TR/selectors/#attribute-selectors
824 attributes = "\\[" + whitespace + "*(" + identifier + ")(?:" + whitespace +
825 // Operator (capture 2)
826 "*([*^$|!~]?=)" + whitespace +
827 // "Attribute values must be CSS identifiers [capture 5] or strings [capture 3 or capture 4]"
828 "*(?:'((?:\\\\.|[^\\\\'])*)'|\"((?:\\\\.|[^\\\\\"])*)\"|(" + identifier + "))|)" + whitespace +
829 "*\\]",
830
831 pseudos = ":(" + identifier + ")(?:\\((" +
832 // To reduce the number of selectors needing tokenize in the preFilter, prefer arguments:
833 // 1. quoted (capture 3; capture 4 or capture 5)
834 "('((?:\\\\.|[^\\\\'])*)'|\"((?:\\\\.|[^\\\\\"])*)\")|" +
835 // 2. simple (capture 6)
836 "((?:\\\\.|[^\\\\()[\\]]|" + attributes + ")*)|" +
837 // 3. anything else (capture 2)
838 ".*" +
839 ")\\)|)",
840
841 // Leading and non-escaped trailing whitespace, capturing some non-whitespace characters preceding the latter
842 rwhitespace = new RegExp( whitespace + "+", "g" ),
843 rtrim = new RegExp( "^" + whitespace + "+|((?:^|[^\\\\])(?:\\\\.)*)" + whitespace + "+$", "g" ),
844
845 rcomma = new RegExp( "^" + whitespace + "*," + whitespace + "*" ),
846 rcombinators = new RegExp( "^" + whitespace + "*([>+~]|" + whitespace + ")" + whitespace + "*" ),
847
848 rattributeQuotes = new RegExp( "=" + whitespace + "*([^\\]'\"]*?)" + whitespace + "*\\]", "g" ),
849
850 rpseudo = new RegExp( pseudos ),
851 ridentifier = new RegExp( "^" + identifier + "$" ),
852
853 matchExpr = {
854 "ID": new RegExp( "^#(" + identifier + ")" ),
855 "CLASS": new RegExp( "^\\.(" + identifier + ")" ),
856 "TAG": new RegExp( "^(" + identifier + "|[*])" ),
857 "ATTR": new RegExp( "^" + attributes ),
858 "PSEUDO": new RegExp( "^" + pseudos ),
859 "CHILD": new RegExp( "^:(only|first|last|nth|nth-last)-(child|of-type)(?:\\(" + whitespace +
860 "*(even|odd|(([+-]|)(\\d*)n|)" + whitespace + "*(?:([+-]|)" + whitespace +
861 "*(\\d+)|))" + whitespace + "*\\)|)", "i" ),
862 "bool": new RegExp( "^(?:" + booleans + ")$", "i" ),
863 // For use in libraries implementing .is()
864 // We use this for POS matching in `select`
865 "needsContext": new RegExp( "^" + whitespace + "*[>+~]|:(even|odd|eq|gt|lt|nth|first|last)(?:\\(" +
866 whitespace + "*((?:-\\d)?\\d*)" + whitespace + "*\\)|)(?=[^-]|$)", "i" )
867 },
868
869 rinputs = /^(?:input|select|textarea|button)$/i,
870 rheader = /^h\d$/i,
871
872 rnative = /^[^{]+\{\s*\[native \w/,
873
874 // Easily-parseable/retrievable ID or TAG or CLASS selectors
875 rquickExpr = /^(?:#([\w-]+)|(\w+)|\.([\w-]+))$/,
876
877 rsibling = /[+~]/,
878
879 // CSS escapes
880 // http://www.w3.org/TR/CSS21/syndata.html#escaped-characters
881 runescape = new RegExp( "\\\\([\\da-f]{1,6}" + whitespace + "?|(" + whitespace + ")|.)", "ig" ),
882 funescape = function( _, escaped, escapedWhitespace ) {
883 var high = "0x" + escaped - 0x10000;
884 // NaN means non-codepoint
885 // Support: Firefox<24
886 // Workaround erroneous numeric interpretation of +"0x"
887 return high !== high || escapedWhitespace ?
888 escaped :
889 high < 0 ?
890 // BMP codepoint
891 String.fromCharCode( high + 0x10000 ) :
892 // Supplemental Plane codepoint (surrogate pair)
893 String.fromCharCode( high >> 10 | 0xD800, high & 0x3FF | 0xDC00 );
894 },
895
896 // CSS string/identifier serialization
897 // https://drafts.csswg.org/cssom/#common-serializing-idioms
898 rcssescape = /([\0-\x1f\x7f]|^-?\d)|^-$|[^\0-\x1f\x7f-\uFFFF\w-]/g,
899 fcssescape = function( ch, asCodePoint ) {
900 if ( asCodePoint ) {
901
902 // U+0000 NULL becomes U+FFFD REPLACEMENT CHARACTER
903 if ( ch === "\0" ) {
904 return "\uFFFD";
905 }
906
907 // Control characters and (dependent upon position) numbers get escaped as code points
908 return ch.slice( 0, -1 ) + "\\" + ch.charCodeAt( ch.length - 1 ).toString( 16 ) + " ";
909 }
910
911 // Other potentially-special ASCII characters get backslash-escaped
912 return "\\" + ch;
913 },
914
915 // Used for iframes
916 // See setDocument()
917 // Removing the function wrapper causes a "Permission Denied"
918 // error in IE
919 unloadHandler = function() {
920 setDocument();
921 },
922
923 disabledAncestor = addCombinator(
924 function( elem ) {
925 return elem.disabled === true && ("form" in elem || "label" in elem);
926 },
927 { dir: "parentNode", next: "legend" }
928 );
929
930// Optimize for push.apply( _, NodeList )
931try {
932 push.apply(
933 (arr = slice.call( preferredDoc.childNodes )),
934 preferredDoc.childNodes
935 );
936 // Support: Android<4.0
937 // Detect silently failing push.apply
938 arr[ preferredDoc.childNodes.length ].nodeType;
939} catch ( e ) {
940 push = { apply: arr.length ?
941
942 // Leverage slice if possible
943 function( target, els ) {
944 push_native.apply( target, slice.call(els) );
945 } :
946
947 // Support: IE<9
948 // Otherwise append directly
949 function( target, els ) {
950 var j = target.length,
951 i = 0;
952 // Can't trust NodeList.length
953 while ( (target[j++] = els[i++]) ) {}
954 target.length = j - 1;
955 }
956 };
957}
958
959function Sizzle( selector, context, results, seed ) {
960 var m, i, elem, nid, match, groups, newSelector,
961 newContext = context && context.ownerDocument,
962
963 // nodeType defaults to 9, since context defaults to document
964 nodeType = context ? context.nodeType : 9;
965
966 results = results || [];
967
968 // Return early from calls with invalid selector or context
969 if ( typeof selector !== "string" || !selector ||
970 nodeType !== 1 && nodeType !== 9 && nodeType !== 11 ) {
971
972 return results;
973 }
974
975 // Try to shortcut find operations (as opposed to filters) in HTML documents
976 if ( !seed ) {
977
978 if ( ( context ? context.ownerDocument || context : preferredDoc ) !== document ) {
979 setDocument( context );
980 }
981 context = context || document;
982
983 if ( documentIsHTML ) {
984
985 // If the selector is sufficiently simple, try using a "get*By*" DOM method
986 // (excepting DocumentFragment context, where the methods don't exist)
987 if ( nodeType !== 11 && (match = rquickExpr.exec( selector )) ) {
988
989 // ID selector
990 if ( (m = match[1]) ) {
991
992 // Document context
993 if ( nodeType === 9 ) {
994 if ( (elem = context.getElementById( m )) ) {
995
996 // Support: IE, Opera, Webkit
997 // TODO: identify versions
998 // getElementById can match elements by name instead of ID
999 if ( elem.id === m ) {
1000 results.push( elem );
1001 return results;
1002 }
1003 } else {
1004 return results;
1005 }
1006
1007 // Element context
1008 } else {
1009
1010 // Support: IE, Opera, Webkit
1011 // TODO: identify versions
1012 // getElementById can match elements by name instead of ID
1013 if ( newContext && (elem = newContext.getElementById( m )) &&
1014 contains( context, elem ) &&
1015 elem.id === m ) {
1016
1017 results.push( elem );
1018 return results;
1019 }
1020 }
1021
1022 // Type selector
1023 } else if ( match[2] ) {
1024 push.apply( results, context.getElementsByTagName( selector ) );
1025 return results;
1026
1027 // Class selector
1028 } else if ( (m = match[3]) && support.getElementsByClassName &&
1029 context.getElementsByClassName ) {
1030
1031 push.apply( results, context.getElementsByClassName( m ) );
1032 return results;
1033 }
1034 }
1035
1036 // Take advantage of querySelectorAll
1037 if ( support.qsa &&
1038 !compilerCache[ selector + " " ] &&
1039 (!rbuggyQSA || !rbuggyQSA.test( selector )) ) {
1040
1041 if ( nodeType !== 1 ) {
1042 newContext = context;
1043 newSelector = selector;
1044
1045 // qSA looks outside Element context, which is not what we want
1046 // Thanks to Andrew Dupont for this workaround technique
1047 // Support: IE <=8
1048 // Exclude object elements
1049 } else if ( context.nodeName.toLowerCase() !== "object" ) {
1050
1051 // Capture the context ID, setting it first if necessary
1052 if ( (nid = context.getAttribute( "id" )) ) {
1053 nid = nid.replace( rcssescape, fcssescape );
1054 } else {
1055 context.setAttribute( "id", (nid = expando) );
1056 }
1057
1058 // Prefix every selector in the list
1059 groups = tokenize( selector );
1060 i = groups.length;
1061 while ( i-- ) {
1062 groups[i] = "#" + nid + " " + toSelector( groups[i] );
1063 }
1064 newSelector = groups.join( "," );
1065
1066 // Expand context for sibling selectors
1067 newContext = rsibling.test( selector ) && testContext( context.parentNode ) ||
1068 context;
1069 }
1070
1071 if ( newSelector ) {
1072 try {
1073 push.apply( results,
1074 newContext.querySelectorAll( newSelector )
1075 );
1076 return results;
1077 } catch ( qsaError ) {
1078 } finally {
1079 if ( nid === expando ) {
1080 context.removeAttribute( "id" );
1081 }
1082 }
1083 }
1084 }
1085 }
1086 }
1087
1088 // All others
1089 return select( selector.replace( rtrim, "$1" ), context, results, seed );
1090}
1091
1092/**
1093 * Create key-value caches of limited size
1094 * @returns {function(string, object)} Returns the Object data after storing it on itself with
1095 * property name the (space-suffixed) string and (if the cache is larger than Expr.cacheLength)
1096 * deleting the oldest entry
1097 */
1098function createCache() {
1099 var keys = [];
1100
1101 function cache( key, value ) {
1102 // Use (key + " ") to avoid collision with native prototype properties (see Issue #157)
1103 if ( keys.push( key + " " ) > Expr.cacheLength ) {
1104 // Only keep the most recent entries
1105 delete cache[ keys.shift() ];
1106 }
1107 return (cache[ key + " " ] = value);
1108 }
1109 return cache;
1110}
1111
1112/**
1113 * Mark a function for special use by Sizzle
1114 * @param {Function} fn The function to mark
1115 */
1116function markFunction( fn ) {
1117 fn[ expando ] = true;
1118 return fn;
1119}
1120
1121/**
1122 * Support testing using an element
1123 * @param {Function} fn Passed the created element and returns a boolean result
1124 */
1125function assert( fn ) {
1126 var el = document.createElement("fieldset");
1127
1128 try {
1129 return !!fn( el );
1130 } catch (e) {
1131 return false;
1132 } finally {
1133 // Remove from its parent by default
1134 if ( el.parentNode ) {
1135 el.parentNode.removeChild( el );
1136 }
1137 // release memory in IE
1138 el = null;
1139 }
1140}
1141
1142/**
1143 * Adds the same handler for all of the specified attrs
1144 * @param {String} attrs Pipe-separated list of attributes
1145 * @param {Function} handler The method that will be applied
1146 */
1147function addHandle( attrs, handler ) {
1148 var arr = attrs.split("|"),
1149 i = arr.length;
1150
1151 while ( i-- ) {
1152 Expr.attrHandle[ arr[i] ] = handler;
1153 }
1154}
1155
1156/**
1157 * Checks document order of two siblings
1158 * @param {Element} a
1159 * @param {Element} b
1160 * @returns {Number} Returns less than 0 if a precedes b, greater than 0 if a follows b
1161 */
1162function siblingCheck( a, b ) {
1163 var cur = b && a,
1164 diff = cur && a.nodeType === 1 && b.nodeType === 1 &&
1165 a.sourceIndex - b.sourceIndex;
1166
1167 // Use IE sourceIndex if available on both nodes
1168 if ( diff ) {
1169 return diff;
1170 }
1171
1172 // Check if b follows a
1173 if ( cur ) {
1174 while ( (cur = cur.nextSibling) ) {
1175 if ( cur === b ) {
1176 return -1;
1177 }
1178 }
1179 }
1180
1181 return a ? 1 : -1;
1182}
1183
1184/**
1185 * Returns a function to use in pseudos for input types
1186 * @param {String} type
1187 */
1188function createInputPseudo( type ) {
1189 return function( elem ) {
1190 var name = elem.nodeName.toLowerCase();
1191 return name === "input" && elem.type === type;
1192 };
1193}
1194
1195/**
1196 * Returns a function to use in pseudos for buttons
1197 * @param {String} type
1198 */
1199function createButtonPseudo( type ) {
1200 return function( elem ) {
1201 var name = elem.nodeName.toLowerCase();
1202 return (name === "input" || name === "button") && elem.type === type;
1203 };
1204}
1205
1206/**
1207 * Returns a function to use in pseudos for :enabled/:disabled
1208 * @param {Boolean} disabled true for :disabled; false for :enabled
1209 */
1210function createDisabledPseudo( disabled ) {
1211
1212 // Known :disabled false positives: fieldset[disabled] > legend:nth-of-type(n+2) :can-disable
1213 return function( elem ) {
1214
1215 // Only certain elements can match :enabled or :disabled
1216 // https://html.spec.whatwg.org/multipage/scripting.html#selector-enabled
1217 // https://html.spec.whatwg.org/multipage/scripting.html#selector-disabled
1218 if ( "form" in elem ) {
1219
1220 // Check for inherited disabledness on relevant non-disabled elements:
1221 // * listed form-associated elements in a disabled fieldset
1222 // https://html.spec.whatwg.org/multipage/forms.html#category-listed
1223 // https://html.spec.whatwg.org/multipage/forms.html#concept-fe-disabled
1224 // * option elements in a disabled optgroup
1225 // https://html.spec.whatwg.org/multipage/forms.html#concept-option-disabled
1226 // All such elements have a "form" property.
1227 if ( elem.parentNode && elem.disabled === false ) {
1228
1229 // Option elements defer to a parent optgroup if present
1230 if ( "label" in elem ) {
1231 if ( "label" in elem.parentNode ) {
1232 return elem.parentNode.disabled === disabled;
1233 } else {
1234 return elem.disabled === disabled;
1235 }
1236 }
1237
1238 // Support: IE 6 - 11
1239 // Use the isDisabled shortcut property to check for disabled fieldset ancestors
1240 return elem.isDisabled === disabled ||
1241
1242 // Where there is no isDisabled, check manually
1243 /* jshint -W018 */
1244 elem.isDisabled !== !disabled &&
1245 disabledAncestor( elem ) === disabled;
1246 }
1247
1248 return elem.disabled === disabled;
1249
1250 // Try to winnow out elements that can't be disabled before trusting the disabled property.
1251 // Some victims get caught in our net (label, legend, menu, track), but it shouldn't
1252 // even exist on them, let alone have a boolean value.
1253 } else if ( "label" in elem ) {
1254 return elem.disabled === disabled;
1255 }
1256
1257 // Remaining elements are neither :enabled nor :disabled
1258 return false;
1259 };
1260}
1261
1262/**
1263 * Returns a function to use in pseudos for positionals
1264 * @param {Function} fn
1265 */
1266function createPositionalPseudo( fn ) {
1267 return markFunction(function( argument ) {
1268 argument = +argument;
1269 return markFunction(function( seed, matches ) {
1270 var j,
1271 matchIndexes = fn( [], seed.length, argument ),
1272 i = matchIndexes.length;
1273
1274 // Match elements found at the specified indexes
1275 while ( i-- ) {
1276 if ( seed[ (j = matchIndexes[i]) ] ) {
1277 seed[j] = !(matches[j] = seed[j]);
1278 }
1279 }
1280 });
1281 });
1282}
1283
1284/**
1285 * Checks a node for validity as a Sizzle context
1286 * @param {Element|Object=} context
1287 * @returns {Element|Object|Boolean} The input node if acceptable, otherwise a falsy value
1288 */
1289function testContext( context ) {
1290 return context && typeof context.getElementsByTagName !== "undefined" && context;
1291}
1292
1293// Expose support vars for convenience
1294support = Sizzle.support = {};
1295
1296/**
1297 * Detects XML nodes
1298 * @param {Element|Object} elem An element or a document
1299 * @returns {Boolean} True iff elem is a non-HTML XML node
1300 */
1301isXML = Sizzle.isXML = function( elem ) {
1302 // documentElement is verified for cases where it doesn't yet exist
1303 // (such as loading iframes in IE - #4833)
1304 var documentElement = elem && (elem.ownerDocument || elem).documentElement;
1305 return documentElement ? documentElement.nodeName !== "HTML" : false;
1306};
1307
1308/**
1309 * Sets document-related variables once based on the current document
1310 * @param {Element|Object} [doc] An element or document object to use to set the document
1311 * @returns {Object} Returns the current document
1312 */
1313setDocument = Sizzle.setDocument = function( node ) {
1314 var hasCompare, subWindow,
1315 doc = node ? node.ownerDocument || node : preferredDoc;
1316
1317 // Return early if doc is invalid or already selected
1318 if ( doc === document || doc.nodeType !== 9 || !doc.documentElement ) {
1319 return document;
1320 }
1321
1322 // Update global variables
1323 document = doc;
1324 docElem = document.documentElement;
1325 documentIsHTML = !isXML( document );
1326
1327 // Support: IE 9-11, Edge
1328 // Accessing iframe documents after unload throws "permission denied" errors (jQuery #13936)
1329 if ( preferredDoc !== document &&
1330 (subWindow = document.defaultView) && subWindow.top !== subWindow ) {
1331
1332 // Support: IE 11, Edge
1333 if ( subWindow.addEventListener ) {
1334 subWindow.addEventListener( "unload", unloadHandler, false );
1335
1336 // Support: IE 9 - 10 only
1337 } else if ( subWindow.attachEvent ) {
1338 subWindow.attachEvent( "onunload", unloadHandler );
1339 }
1340 }
1341
1342 /* Attributes
1343 ---------------------------------------------------------------------- */
1344
1345 // Support: IE<8
1346 // Verify that getAttribute really returns attributes and not properties
1347 // (excepting IE8 booleans)
1348 support.attributes = assert(function( el ) {
1349 el.className = "i";
1350 return !el.getAttribute("className");
1351 });
1352
1353 /* getElement(s)By*
1354 ---------------------------------------------------------------------- */
1355
1356 // Check if getElementsByTagName("*") returns only elements
1357 support.getElementsByTagName = assert(function( el ) {
1358 el.appendChild( document.createComment("") );
1359 return !el.getElementsByTagName("*").length;
1360 });
1361
1362 // Support: IE<9
1363 support.getElementsByClassName = rnative.test( document.getElementsByClassName );
1364
1365 // Support: IE<10
1366 // Check if getElementById returns elements by name
1367 // The broken getElementById methods don't pick up programmatically-set names,
1368 // so use a roundabout getElementsByName test
1369 support.getById = assert(function( el ) {
1370 docElem.appendChild( el ).id = expando;
1371 return !document.getElementsByName || !document.getElementsByName( expando ).length;
1372 });
1373
1374 // ID filter and find
1375 if ( support.getById ) {
1376 Expr.filter["ID"] = function( id ) {
1377 var attrId = id.replace( runescape, funescape );
1378 return function( elem ) {
1379 return elem.getAttribute("id") === attrId;
1380 };
1381 };
1382 Expr.find["ID"] = function( id, context ) {
1383 if ( typeof context.getElementById !== "undefined" && documentIsHTML ) {
1384 var elem = context.getElementById( id );
1385 return elem ? [ elem ] : [];
1386 }
1387 };
1388 } else {
1389 Expr.filter["ID"] = function( id ) {
1390 var attrId = id.replace( runescape, funescape );
1391 return function( elem ) {
1392 var node = typeof elem.getAttributeNode !== "undefined" &&
1393 elem.getAttributeNode("id");
1394 return node && node.value === attrId;
1395 };
1396 };
1397
1398 // Support: IE 6 - 7 only
1399 // getElementById is not reliable as a find shortcut
1400 Expr.find["ID"] = function( id, context ) {
1401 if ( typeof context.getElementById !== "undefined" && documentIsHTML ) {
1402 var node, i, elems,
1403 elem = context.getElementById( id );
1404
1405 if ( elem ) {
1406
1407 // Verify the id attribute
1408 node = elem.getAttributeNode("id");
1409 if ( node && node.value === id ) {
1410 return [ elem ];
1411 }
1412
1413 // Fall back on getElementsByName
1414 elems = context.getElementsByName( id );
1415 i = 0;
1416 while ( (elem = elems[i++]) ) {
1417 node = elem.getAttributeNode("id");
1418 if ( node && node.value === id ) {
1419 return [ elem ];
1420 }
1421 }
1422 }
1423
1424 return [];
1425 }
1426 };
1427 }
1428
1429 // Tag
1430 Expr.find["TAG"] = support.getElementsByTagName ?
1431 function( tag, context ) {
1432 if ( typeof context.getElementsByTagName !== "undefined" ) {
1433 return context.getElementsByTagName( tag );
1434
1435 // DocumentFragment nodes don't have gEBTN
1436 } else if ( support.qsa ) {
1437 return context.querySelectorAll( tag );
1438 }
1439 } :
1440
1441 function( tag, context ) {
1442 var elem,
1443 tmp = [],
1444 i = 0,
1445 // By happy coincidence, a (broken) gEBTN appears on DocumentFragment nodes too
1446 results = context.getElementsByTagName( tag );
1447
1448 // Filter out possible comments
1449 if ( tag === "*" ) {
1450 while ( (elem = results[i++]) ) {
1451 if ( elem.nodeType === 1 ) {
1452 tmp.push( elem );
1453 }
1454 }
1455
1456 return tmp;
1457 }
1458 return results;
1459 };
1460
1461 // Class
1462 Expr.find["CLASS"] = support.getElementsByClassName && function( className, context ) {
1463 if ( typeof context.getElementsByClassName !== "undefined" && documentIsHTML ) {
1464 return context.getElementsByClassName( className );
1465 }
1466 };
1467
1468 /* QSA/matchesSelector
1469 ---------------------------------------------------------------------- */
1470
1471 // QSA and matchesSelector support
1472
1473 // matchesSelector(:active) reports false when true (IE9/Opera 11.5)
1474 rbuggyMatches = [];
1475
1476 // qSa(:focus) reports false when true (Chrome 21)
1477 // We allow this because of a bug in IE8/9 that throws an error
1478 // whenever `document.activeElement` is accessed on an iframe
1479 // So, we allow :focus to pass through QSA all the time to avoid the IE error
1480 // See https://bugs.jquery.com/ticket/13378
1481 rbuggyQSA = [];
1482
1483 if ( (support.qsa = rnative.test( document.querySelectorAll )) ) {
1484 // Build QSA regex
1485 // Regex strategy adopted from Diego Perini
1486 assert(function( el ) {
1487 // Select is set to empty string on purpose
1488 // This is to test IE's treatment of not explicitly
1489 // setting a boolean content attribute,
1490 // since its presence should be enough
1491 // https://bugs.jquery.com/ticket/12359
1492 docElem.appendChild( el ).innerHTML = "<a id='" + expando + "'></a>" +
1493 "<select id='" + expando + "-\r\\' msallowcapture=''>" +
1494 "<option selected=''></option></select>";
1495
1496 // Support: IE8, Opera 11-12.16
1497 // Nothing should be selected when empty strings follow ^= or $= or *=
1498 // The test attribute must be unknown in Opera but "safe" for WinRT
1499 // https://msdn.microsoft.com/en-us/library/ie/hh465388.aspx#attribute_section
1500 if ( el.querySelectorAll("[msallowcapture^='']").length ) {
1501 rbuggyQSA.push( "[*^$]=" + whitespace + "*(?:''|\"\")" );
1502 }
1503
1504 // Support: IE8
1505 // Boolean attributes and "value" are not treated correctly
1506 if ( !el.querySelectorAll("[selected]").length ) {
1507 rbuggyQSA.push( "\\[" + whitespace + "*(?:value|" + booleans + ")" );
1508 }
1509
1510 // Support: Chrome<29, Android<4.4, Safari<7.0+, iOS<7.0+, PhantomJS<1.9.8+
1511 if ( !el.querySelectorAll( "[id~=" + expando + "-]" ).length ) {
1512 rbuggyQSA.push("~=");
1513 }
1514
1515 // Webkit/Opera - :checked should return selected option elements
1516 // http://www.w3.org/TR/2011/REC-css3-selectors-20110929/#checked
1517 // IE8 throws error here and will not see later tests
1518 if ( !el.querySelectorAll(":checked").length ) {
1519 rbuggyQSA.push(":checked");
1520 }
1521
1522 // Support: Safari 8+, iOS 8+
1523 // https://bugs.webkit.org/show_bug.cgi?id=136851
1524 // In-page `selector#id sibling-combinator selector` fails
1525 if ( !el.querySelectorAll( "a#" + expando + "+*" ).length ) {
1526 rbuggyQSA.push(".#.+[+~]");
1527 }
1528 });
1529
1530 assert(function( el ) {
1531 el.innerHTML = "<a href='' disabled='disabled'></a>" +
1532 "<select disabled='disabled'><option/></select>";
1533
1534 // Support: Windows 8 Native Apps
1535 // The type and name attributes are restricted during .innerHTML assignment
1536 var input = document.createElement("input");
1537 input.setAttribute( "type", "hidden" );
1538 el.appendChild( input ).setAttribute( "name", "D" );
1539
1540 // Support: IE8
1541 // Enforce case-sensitivity of name attribute
1542 if ( el.querySelectorAll("[name=d]").length ) {
1543 rbuggyQSA.push( "name" + whitespace + "*[*^$|!~]?=" );
1544 }
1545
1546 // FF 3.5 - :enabled/:disabled and hidden elements (hidden elements are still enabled)
1547 // IE8 throws error here and will not see later tests
1548 if ( el.querySelectorAll(":enabled").length !== 2 ) {
1549 rbuggyQSA.push( ":enabled", ":disabled" );
1550 }
1551
1552 // Support: IE9-11+
1553 // IE's :disabled selector does not pick up the children of disabled fieldsets
1554 docElem.appendChild( el ).disabled = true;
1555 if ( el.querySelectorAll(":disabled").length !== 2 ) {
1556 rbuggyQSA.push( ":enabled", ":disabled" );
1557 }
1558
1559 // Opera 10-11 does not throw on post-comma invalid pseudos
1560 el.querySelectorAll("*,:x");
1561 rbuggyQSA.push(",.*:");
1562 });
1563 }
1564
1565 if ( (support.matchesSelector = rnative.test( (matches = docElem.matches ||
1566 docElem.webkitMatchesSelector ||
1567 docElem.mozMatchesSelector ||
1568 docElem.oMatchesSelector ||
1569 docElem.msMatchesSelector) )) ) {
1570
1571 assert(function( el ) {
1572 // Check to see if it's possible to do matchesSelector
1573 // on a disconnected node (IE 9)
1574 support.disconnectedMatch = matches.call( el, "*" );
1575
1576 // This should fail with an exception
1577 // Gecko does not error, returns false instead
1578 matches.call( el, "[s!='']:x" );
1579 rbuggyMatches.push( "!=", pseudos );
1580 });
1581 }
1582
1583 rbuggyQSA = rbuggyQSA.length && new RegExp( rbuggyQSA.join("|") );
1584 rbuggyMatches = rbuggyMatches.length && new RegExp( rbuggyMatches.join("|") );
1585
1586 /* Contains
1587 ---------------------------------------------------------------------- */
1588 hasCompare = rnative.test( docElem.compareDocumentPosition );
1589
1590 // Element contains another
1591 // Purposefully self-exclusive
1592 // As in, an element does not contain itself
1593 contains = hasCompare || rnative.test( docElem.contains ) ?
1594 function( a, b ) {
1595 var adown = a.nodeType === 9 ? a.documentElement : a,
1596 bup = b && b.parentNode;
1597 return a === bup || !!( bup && bup.nodeType === 1 && (
1598 adown.contains ?
1599 adown.contains( bup ) :
1600 a.compareDocumentPosition && a.compareDocumentPosition( bup ) & 16
1601 ));
1602 } :
1603 function( a, b ) {
1604 if ( b ) {
1605 while ( (b = b.parentNode) ) {
1606 if ( b === a ) {
1607 return true;
1608 }
1609 }
1610 }
1611 return false;
1612 };
1613
1614 /* Sorting
1615 ---------------------------------------------------------------------- */
1616
1617 // Document order sorting
1618 sortOrder = hasCompare ?
1619 function( a, b ) {
1620
1621 // Flag for duplicate removal
1622 if ( a === b ) {
1623 hasDuplicate = true;
1624 return 0;
1625 }
1626
1627 // Sort on method existence if only one input has compareDocumentPosition
1628 var compare = !a.compareDocumentPosition - !b.compareDocumentPosition;
1629 if ( compare ) {
1630 return compare;
1631 }
1632
1633 // Calculate position if both inputs belong to the same document
1634 compare = ( a.ownerDocument || a ) === ( b.ownerDocument || b ) ?
1635 a.compareDocumentPosition( b ) :
1636
1637 // Otherwise we know they are disconnected
1638 1;
1639
1640 // Disconnected nodes
1641 if ( compare & 1 ||
1642 (!support.sortDetached && b.compareDocumentPosition( a ) === compare) ) {
1643
1644 // Choose the first element that is related to our preferred document
1645 if ( a === document || a.ownerDocument === preferredDoc && contains(preferredDoc, a) ) {
1646 return -1;
1647 }
1648 if ( b === document || b.ownerDocument === preferredDoc && contains(preferredDoc, b) ) {
1649 return 1;
1650 }
1651
1652 // Maintain original order
1653 return sortInput ?
1654 ( indexOf( sortInput, a ) - indexOf( sortInput, b ) ) :
1655 0;
1656 }
1657
1658 return compare & 4 ? -1 : 1;
1659 } :
1660 function( a, b ) {
1661 // Exit early if the nodes are identical
1662 if ( a === b ) {
1663 hasDuplicate = true;
1664 return 0;
1665 }
1666
1667 var cur,
1668 i = 0,
1669 aup = a.parentNode,
1670 bup = b.parentNode,
1671 ap = [ a ],
1672 bp = [ b ];
1673
1674 // Parentless nodes are either documents or disconnected
1675 if ( !aup || !bup ) {
1676 return a === document ? -1 :
1677 b === document ? 1 :
1678 aup ? -1 :
1679 bup ? 1 :
1680 sortInput ?
1681 ( indexOf( sortInput, a ) - indexOf( sortInput, b ) ) :
1682 0;
1683
1684 // If the nodes are siblings, we can do a quick check
1685 } else if ( aup === bup ) {
1686 return siblingCheck( a, b );
1687 }
1688
1689 // Otherwise we need full lists of their ancestors for comparison
1690 cur = a;
1691 while ( (cur = cur.parentNode) ) {
1692 ap.unshift( cur );
1693 }
1694 cur = b;
1695 while ( (cur = cur.parentNode) ) {
1696 bp.unshift( cur );
1697 }
1698
1699 // Walk down the tree looking for a discrepancy
1700 while ( ap[i] === bp[i] ) {
1701 i++;
1702 }
1703
1704 return i ?
1705 // Do a sibling check if the nodes have a common ancestor
1706 siblingCheck( ap[i], bp[i] ) :
1707
1708 // Otherwise nodes in our document sort first
1709 ap[i] === preferredDoc ? -1 :
1710 bp[i] === preferredDoc ? 1 :
1711 0;
1712 };
1713
1714 return document;
1715};
1716
1717Sizzle.matches = function( expr, elements ) {
1718 return Sizzle( expr, null, null, elements );
1719};
1720
1721Sizzle.matchesSelector = function( elem, expr ) {
1722 // Set document vars if needed
1723 if ( ( elem.ownerDocument || elem ) !== document ) {
1724 setDocument( elem );
1725 }
1726
1727 // Make sure that attribute selectors are quoted
1728 expr = expr.replace( rattributeQuotes, "='$1']" );
1729
1730 if ( support.matchesSelector && documentIsHTML &&
1731 !compilerCache[ expr + " " ] &&
1732 ( !rbuggyMatches || !rbuggyMatches.test( expr ) ) &&
1733 ( !rbuggyQSA || !rbuggyQSA.test( expr ) ) ) {
1734
1735 try {
1736 var ret = matches.call( elem, expr );
1737
1738 // IE 9's matchesSelector returns false on disconnected nodes
1739 if ( ret || support.disconnectedMatch ||
1740 // As well, disconnected nodes are said to be in a document
1741 // fragment in IE 9
1742 elem.document && elem.document.nodeType !== 11 ) {
1743 return ret;
1744 }
1745 } catch (e) {}
1746 }
1747
1748 return Sizzle( expr, document, null, [ elem ] ).length > 0;
1749};
1750
1751Sizzle.contains = function( context, elem ) {
1752 // Set document vars if needed
1753 if ( ( context.ownerDocument || context ) !== document ) {
1754 setDocument( context );
1755 }
1756 return contains( context, elem );
1757};
1758
1759Sizzle.attr = function( elem, name ) {
1760 // Set document vars if needed
1761 if ( ( elem.ownerDocument || elem ) !== document ) {
1762 setDocument( elem );
1763 }
1764
1765 var fn = Expr.attrHandle[ name.toLowerCase() ],
1766 // Don't get fooled by Object.prototype properties (jQuery #13807)
1767 val = fn && hasOwn.call( Expr.attrHandle, name.toLowerCase() ) ?
1768 fn( elem, name, !documentIsHTML ) :
1769 undefined;
1770
1771 return val !== undefined ?
1772 val :
1773 support.attributes || !documentIsHTML ?
1774 elem.getAttribute( name ) :
1775 (val = elem.getAttributeNode(name)) && val.specified ?
1776 val.value :
1777 null;
1778};
1779
1780Sizzle.escape = function( sel ) {
1781 return (sel + "").replace( rcssescape, fcssescape );
1782};
1783
1784Sizzle.error = function( msg ) {
1785 throw new Error( "Syntax error, unrecognized expression: " + msg );
1786};
1787
1788/**
1789 * Document sorting and removing duplicates
1790 * @param {ArrayLike} results
1791 */
1792Sizzle.uniqueSort = function( results ) {
1793 var elem,
1794 duplicates = [],
1795 j = 0,
1796 i = 0;
1797
1798 // Unless we *know* we can detect duplicates, assume their presence
1799 hasDuplicate = !support.detectDuplicates;
1800 sortInput = !support.sortStable && results.slice( 0 );
1801 results.sort( sortOrder );
1802
1803 if ( hasDuplicate ) {
1804 while ( (elem = results[i++]) ) {
1805 if ( elem === results[ i ] ) {
1806 j = duplicates.push( i );
1807 }
1808 }
1809 while ( j-- ) {
1810 results.splice( duplicates[ j ], 1 );
1811 }
1812 }
1813
1814 // Clear input after sorting to release objects
1815 // See https://github.com/jquery/sizzle/pull/225
1816 sortInput = null;
1817
1818 return results;
1819};
1820
1821/**
1822 * Utility function for retrieving the text value of an array of DOM nodes
1823 * @param {Array|Element} elem
1824 */
1825getText = Sizzle.getText = function( elem ) {
1826 var node,
1827 ret = "",
1828 i = 0,
1829 nodeType = elem.nodeType;
1830
1831 if ( !nodeType ) {
1832 // If no nodeType, this is expected to be an array
1833 while ( (node = elem[i++]) ) {
1834 // Do not traverse comment nodes
1835 ret += getText( node );
1836 }
1837 } else if ( nodeType === 1 || nodeType === 9 || nodeType === 11 ) {
1838 // Use textContent for elements
1839 // innerText usage removed for consistency of new lines (jQuery #11153)
1840 if ( typeof elem.textContent === "string" ) {
1841 return elem.textContent;
1842 } else {
1843 // Traverse its children
1844 for ( elem = elem.firstChild; elem; elem = elem.nextSibling ) {
1845 ret += getText( elem );
1846 }
1847 }
1848 } else if ( nodeType === 3 || nodeType === 4 ) {
1849 return elem.nodeValue;
1850 }
1851 // Do not include comment or processing instruction nodes
1852
1853 return ret;
1854};
1855
1856Expr = Sizzle.selectors = {
1857
1858 // Can be adjusted by the user
1859 cacheLength: 50,
1860
1861 createPseudo: markFunction,
1862
1863 match: matchExpr,
1864
1865 attrHandle: {},
1866
1867 find: {},
1868
1869 relative: {
1870 ">": { dir: "parentNode", first: true },
1871 " ": { dir: "parentNode" },
1872 "+": { dir: "previousSibling", first: true },
1873 "~": { dir: "previousSibling" }
1874 },
1875
1876 preFilter: {
1877 "ATTR": function( match ) {
1878 match[1] = match[1].replace( runescape, funescape );
1879
1880 // Move the given value to match[3] whether quoted or unquoted
1881 match[3] = ( match[3] || match[4] || match[5] || "" ).replace( runescape, funescape );
1882
1883 if ( match[2] === "~=" ) {
1884 match[3] = " " + match[3] + " ";
1885 }
1886
1887 return match.slice( 0, 4 );
1888 },
1889
1890 "CHILD": function( match ) {
1891 /* matches from matchExpr["CHILD"]
1892 1 type (only|nth|...)
1893 2 what (child|of-type)
1894 3 argument (even|odd|\d*|\d*n([+-]\d+)?|...)
1895 4 xn-component of xn+y argument ([+-]?\d*n|)
1896 5 sign of xn-component
1897 6 x of xn-component
1898 7 sign of y-component
1899 8 y of y-component
1900 */
1901 match[1] = match[1].toLowerCase();
1902
1903 if ( match[1].slice( 0, 3 ) === "nth" ) {
1904 // nth-* requires argument
1905 if ( !match[3] ) {
1906 Sizzle.error( match[0] );
1907 }
1908
1909 // numeric x and y parameters for Expr.filter.CHILD
1910 // remember that false/true cast respectively to 0/1
1911 match[4] = +( match[4] ? match[5] + (match[6] || 1) : 2 * ( match[3] === "even" || match[3] === "odd" ) );
1912 match[5] = +( ( match[7] + match[8] ) || match[3] === "odd" );
1913
1914 // other types prohibit arguments
1915 } else if ( match[3] ) {
1916 Sizzle.error( match[0] );
1917 }
1918
1919 return match;
1920 },
1921
1922 "PSEUDO": function( match ) {
1923 var excess,
1924 unquoted = !match[6] && match[2];
1925
1926 if ( matchExpr["CHILD"].test( match[0] ) ) {
1927 return null;
1928 }
1929
1930 // Accept quoted arguments as-is
1931 if ( match[3] ) {
1932 match[2] = match[4] || match[5] || "";
1933
1934 // Strip excess characters from unquoted arguments
1935 } else if ( unquoted && rpseudo.test( unquoted ) &&
1936 // Get excess from tokenize (recursively)
1937 (excess = tokenize( unquoted, true )) &&
1938 // advance to the next closing parenthesis
1939 (excess = unquoted.indexOf( ")", unquoted.length - excess ) - unquoted.length) ) {
1940
1941 // excess is a negative index
1942 match[0] = match[0].slice( 0, excess );
1943 match[2] = unquoted.slice( 0, excess );
1944 }
1945
1946 // Return only captures needed by the pseudo filter method (type and argument)
1947 return match.slice( 0, 3 );
1948 }
1949 },
1950
1951 filter: {
1952
1953 "TAG": function( nodeNameSelector ) {
1954 var nodeName = nodeNameSelector.replace( runescape, funescape ).toLowerCase();
1955 return nodeNameSelector === "*" ?
1956 function() { return true; } :
1957 function( elem ) {
1958 return elem.nodeName && elem.nodeName.toLowerCase() === nodeName;
1959 };
1960 },
1961
1962 "CLASS": function( className ) {
1963 var pattern = classCache[ className + " " ];
1964
1965 return pattern ||
1966 (pattern = new RegExp( "(^|" + whitespace + ")" + className + "(" + whitespace + "|$)" )) &&
1967 classCache( className, function( elem ) {
1968 return pattern.test( typeof elem.className === "string" && elem.className || typeof elem.getAttribute !== "undefined" && elem.getAttribute("class") || "" );
1969 });
1970 },
1971
1972 "ATTR": function( name, operator, check ) {
1973 return function( elem ) {
1974 var result = Sizzle.attr( elem, name );
1975
1976 if ( result == null ) {
1977 return operator === "!=";
1978 }
1979 if ( !operator ) {
1980 return true;
1981 }
1982
1983 result += "";
1984
1985 return operator === "=" ? result === check :
1986 operator === "!=" ? result !== check :
1987 operator === "^=" ? check && result.indexOf( check ) === 0 :
1988 operator === "*=" ? check && result.indexOf( check ) > -1 :
1989 operator === "$=" ? check && result.slice( -check.length ) === check :
1990 operator === "~=" ? ( " " + result.replace( rwhitespace, " " ) + " " ).indexOf( check ) > -1 :
1991 operator === "|=" ? result === check || result.slice( 0, check.length + 1 ) === check + "-" :
1992 false;
1993 };
1994 },
1995
1996 "CHILD": function( type, what, argument, first, last ) {
1997 var simple = type.slice( 0, 3 ) !== "nth",
1998 forward = type.slice( -4 ) !== "last",
1999 ofType = what === "of-type";
2000
2001 return first === 1 && last === 0 ?
2002
2003 // Shortcut for :nth-*(n)
2004 function( elem ) {
2005 return !!elem.parentNode;
2006 } :
2007
2008 function( elem, context, xml ) {
2009 var cache, uniqueCache, outerCache, node, nodeIndex, start,
2010 dir = simple !== forward ? "nextSibling" : "previousSibling",
2011 parent = elem.parentNode,
2012 name = ofType && elem.nodeName.toLowerCase(),
2013 useCache = !xml && !ofType,
2014 diff = false;
2015
2016 if ( parent ) {
2017
2018 // :(first|last|only)-(child|of-type)
2019 if ( simple ) {
2020 while ( dir ) {
2021 node = elem;
2022 while ( (node = node[ dir ]) ) {
2023 if ( ofType ?
2024 node.nodeName.toLowerCase() === name :
2025 node.nodeType === 1 ) {
2026
2027 return false;
2028 }
2029 }
2030 // Reverse direction for :only-* (if we haven't yet done so)
2031 start = dir = type === "only" && !start && "nextSibling";
2032 }
2033 return true;
2034 }
2035
2036 start = [ forward ? parent.firstChild : parent.lastChild ];
2037
2038 // non-xml :nth-child(...) stores cache data on `parent`
2039 if ( forward && useCache ) {
2040
2041 // Seek `elem` from a previously-cached index
2042
2043 // ...in a gzip-friendly way
2044 node = parent;
2045 outerCache = node[ expando ] || (node[ expando ] = {});
2046
2047 // Support: IE <9 only
2048 // Defend against cloned attroperties (jQuery gh-1709)
2049 uniqueCache = outerCache[ node.uniqueID ] ||
2050 (outerCache[ node.uniqueID ] = {});
2051
2052 cache = uniqueCache[ type ] || [];
2053 nodeIndex = cache[ 0 ] === dirruns && cache[ 1 ];
2054 diff = nodeIndex && cache[ 2 ];
2055 node = nodeIndex && parent.childNodes[ nodeIndex ];
2056
2057 while ( (node = ++nodeIndex && node && node[ dir ] ||
2058
2059 // Fallback to seeking `elem` from the start
2060 (diff = nodeIndex = 0) || start.pop()) ) {
2061
2062 // When found, cache indexes on `parent` and break
2063 if ( node.nodeType === 1 && ++diff && node === elem ) {
2064 uniqueCache[ type ] = [ dirruns, nodeIndex, diff ];
2065 break;
2066 }
2067 }
2068
2069 } else {
2070 // Use previously-cached element index if available
2071 if ( useCache ) {
2072 // ...in a gzip-friendly way
2073 node = elem;
2074 outerCache = node[ expando ] || (node[ expando ] = {});
2075
2076 // Support: IE <9 only
2077 // Defend against cloned attroperties (jQuery gh-1709)
2078 uniqueCache = outerCache[ node.uniqueID ] ||
2079 (outerCache[ node.uniqueID ] = {});
2080
2081 cache = uniqueCache[ type ] || [];
2082 nodeIndex = cache[ 0 ] === dirruns && cache[ 1 ];
2083 diff = nodeIndex;
2084 }
2085
2086 // xml :nth-child(...)
2087 // or :nth-last-child(...) or :nth(-last)?-of-type(...)
2088 if ( diff === false ) {
2089 // Use the same loop as above to seek `elem` from the start
2090 while ( (node = ++nodeIndex && node && node[ dir ] ||
2091 (diff = nodeIndex = 0) || start.pop()) ) {
2092
2093 if ( ( ofType ?
2094 node.nodeName.toLowerCase() === name :
2095 node.nodeType === 1 ) &&
2096 ++diff ) {
2097
2098 // Cache the index of each encountered element
2099 if ( useCache ) {
2100 outerCache = node[ expando ] || (node[ expando ] = {});
2101
2102 // Support: IE <9 only
2103 // Defend against cloned attroperties (jQuery gh-1709)
2104 uniqueCache = outerCache[ node.uniqueID ] ||
2105 (outerCache[ node.uniqueID ] = {});
2106
2107 uniqueCache[ type ] = [ dirruns, diff ];
2108 }
2109
2110 if ( node === elem ) {
2111 break;
2112 }
2113 }
2114 }
2115 }
2116 }
2117
2118 // Incorporate the offset, then check against cycle size
2119 diff -= last;
2120 return diff === first || ( diff % first === 0 && diff / first >= 0 );
2121 }
2122 };
2123 },
2124
2125 "PSEUDO": function( pseudo, argument ) {
2126 // pseudo-class names are case-insensitive
2127 // http://www.w3.org/TR/selectors/#pseudo-classes
2128 // Prioritize by case sensitivity in case custom pseudos are added with uppercase letters
2129 // Remember that setFilters inherits from pseudos
2130 var args,
2131 fn = Expr.pseudos[ pseudo ] || Expr.setFilters[ pseudo.toLowerCase() ] ||
2132 Sizzle.error( "unsupported pseudo: " + pseudo );
2133
2134 // The user may use createPseudo to indicate that
2135 // arguments are needed to create the filter function
2136 // just as Sizzle does
2137 if ( fn[ expando ] ) {
2138 return fn( argument );
2139 }
2140
2141 // But maintain support for old signatures
2142 if ( fn.length > 1 ) {
2143 args = [ pseudo, pseudo, "", argument ];
2144 return Expr.setFilters.hasOwnProperty( pseudo.toLowerCase() ) ?
2145 markFunction(function( seed, matches ) {
2146 var idx,
2147 matched = fn( seed, argument ),
2148 i = matched.length;
2149 while ( i-- ) {
2150 idx = indexOf( seed, matched[i] );
2151 seed[ idx ] = !( matches[ idx ] = matched[i] );
2152 }
2153 }) :
2154 function( elem ) {
2155 return fn( elem, 0, args );
2156 };
2157 }
2158
2159 return fn;
2160 }
2161 },
2162
2163 pseudos: {
2164 // Potentially complex pseudos
2165 "not": markFunction(function( selector ) {
2166 // Trim the selector passed to compile
2167 // to avoid treating leading and trailing
2168 // spaces as combinators
2169 var input = [],
2170 results = [],
2171 matcher = compile( selector.replace( rtrim, "$1" ) );
2172
2173 return matcher[ expando ] ?
2174 markFunction(function( seed, matches, context, xml ) {
2175 var elem,
2176 unmatched = matcher( seed, null, xml, [] ),
2177 i = seed.length;
2178
2179 // Match elements unmatched by `matcher`
2180 while ( i-- ) {
2181 if ( (elem = unmatched[i]) ) {
2182 seed[i] = !(matches[i] = elem);
2183 }
2184 }
2185 }) :
2186 function( elem, context, xml ) {
2187 input[0] = elem;
2188 matcher( input, null, xml, results );
2189 // Don't keep the element (issue #299)
2190 input[0] = null;
2191 return !results.pop();
2192 };
2193 }),
2194
2195 "has": markFunction(function( selector ) {
2196 return function( elem ) {
2197 return Sizzle( selector, elem ).length > 0;
2198 };
2199 }),
2200
2201 "contains": markFunction(function( text ) {
2202 text = text.replace( runescape, funescape );
2203 return function( elem ) {
2204 return ( elem.textContent || elem.innerText || getText( elem ) ).indexOf( text ) > -1;
2205 };
2206 }),
2207
2208 // "Whether an element is represented by a :lang() selector
2209 // is based solely on the element's language value
2210 // being equal to the identifier C,
2211 // or beginning with the identifier C immediately followed by "-".
2212 // The matching of C against the element's language value is performed case-insensitively.
2213 // The identifier C does not have to be a valid language name."
2214 // http://www.w3.org/TR/selectors/#lang-pseudo
2215 "lang": markFunction( function( lang ) {
2216 // lang value must be a valid identifier
2217 if ( !ridentifier.test(lang || "") ) {
2218 Sizzle.error( "unsupported lang: " + lang );
2219 }
2220 lang = lang.replace( runescape, funescape ).toLowerCase();
2221 return function( elem ) {
2222 var elemLang;
2223 do {
2224 if ( (elemLang = documentIsHTML ?
2225 elem.lang :
2226 elem.getAttribute("xml:lang") || elem.getAttribute("lang")) ) {
2227
2228 elemLang = elemLang.toLowerCase();
2229 return elemLang === lang || elemLang.indexOf( lang + "-" ) === 0;
2230 }
2231 } while ( (elem = elem.parentNode) && elem.nodeType === 1 );
2232 return false;
2233 };
2234 }),
2235
2236 // Miscellaneous
2237 "target": function( elem ) {
2238 var hash = window.location && window.location.hash;
2239 return hash && hash.slice( 1 ) === elem.id;
2240 },
2241
2242 "root": function( elem ) {
2243 return elem === docElem;
2244 },
2245
2246 "focus": function( elem ) {
2247 return elem === document.activeElement && (!document.hasFocus || document.hasFocus()) && !!(elem.type || elem.href || ~elem.tabIndex);
2248 },
2249
2250 // Boolean properties
2251 "enabled": createDisabledPseudo( false ),
2252 "disabled": createDisabledPseudo( true ),
2253
2254 "checked": function( elem ) {
2255 // In CSS3, :checked should return both checked and selected elements
2256 // http://www.w3.org/TR/2011/REC-css3-selectors-20110929/#checked
2257 var nodeName = elem.nodeName.toLowerCase();
2258 return (nodeName === "input" && !!elem.checked) || (nodeName === "option" && !!elem.selected);
2259 },
2260
2261 "selected": function( elem ) {
2262 // Accessing this property makes selected-by-default
2263 // options in Safari work properly
2264 if ( elem.parentNode ) {
2265 elem.parentNode.selectedIndex;
2266 }
2267
2268 return elem.selected === true;
2269 },
2270
2271 // Contents
2272 "empty": function( elem ) {
2273 // http://www.w3.org/TR/selectors/#empty-pseudo
2274 // :empty is negated by element (1) or content nodes (text: 3; cdata: 4; entity ref: 5),
2275 // but not by others (comment: 8; processing instruction: 7; etc.)
2276 // nodeType < 6 works because attributes (2) do not appear as children
2277 for ( elem = elem.firstChild; elem; elem = elem.nextSibling ) {
2278 if ( elem.nodeType < 6 ) {
2279 return false;
2280 }
2281 }
2282 return true;
2283 },
2284
2285 "parent": function( elem ) {
2286 return !Expr.pseudos["empty"]( elem );
2287 },
2288
2289 // Element/input types
2290 "header": function( elem ) {
2291 return rheader.test( elem.nodeName );
2292 },
2293
2294 "input": function( elem ) {
2295 return rinputs.test( elem.nodeName );
2296 },
2297
2298 "button": function( elem ) {
2299 var name = elem.nodeName.toLowerCase();
2300 return name === "input" && elem.type === "button" || name === "button";
2301 },
2302
2303 "text": function( elem ) {
2304 var attr;
2305 return elem.nodeName.toLowerCase() === "input" &&
2306 elem.type === "text" &&
2307
2308 // Support: IE<8
2309 // New HTML5 attribute values (e.g., "search") appear with elem.type === "text"
2310 ( (attr = elem.getAttribute("type")) == null || attr.toLowerCase() === "text" );
2311 },
2312
2313 // Position-in-collection
2314 "first": createPositionalPseudo(function() {
2315 return [ 0 ];
2316 }),
2317
2318 "last": createPositionalPseudo(function( matchIndexes, length ) {
2319 return [ length - 1 ];
2320 }),
2321
2322 "eq": createPositionalPseudo(function( matchIndexes, length, argument ) {
2323 return [ argument < 0 ? argument + length : argument ];
2324 }),
2325
2326 "even": createPositionalPseudo(function( matchIndexes, length ) {
2327 var i = 0;
2328 for ( ; i < length; i += 2 ) {
2329 matchIndexes.push( i );
2330 }
2331 return matchIndexes;
2332 }),
2333
2334 "odd": createPositionalPseudo(function( matchIndexes, length ) {
2335 var i = 1;
2336 for ( ; i < length; i += 2 ) {
2337 matchIndexes.push( i );
2338 }
2339 return matchIndexes;
2340 }),
2341
2342 "lt": createPositionalPseudo(function( matchIndexes, length, argument ) {
2343 var i = argument < 0 ? argument + length : argument;
2344 for ( ; --i >= 0; ) {
2345 matchIndexes.push( i );
2346 }
2347 return matchIndexes;
2348 }),
2349
2350 "gt": createPositionalPseudo(function( matchIndexes, length, argument ) {
2351 var i = argument < 0 ? argument + length : argument;
2352 for ( ; ++i < length; ) {
2353 matchIndexes.push( i );
2354 }
2355 return matchIndexes;
2356 })
2357 }
2358};
2359
2360Expr.pseudos["nth"] = Expr.pseudos["eq"];
2361
2362// Add button/input type pseudos
2363for ( i in { radio: true, checkbox: true, file: true, password: true, image: true } ) {
2364 Expr.pseudos[ i ] = createInputPseudo( i );
2365}
2366for ( i in { submit: true, reset: true } ) {
2367 Expr.pseudos[ i ] = createButtonPseudo( i );
2368}
2369
2370// Easy API for creating new setFilters
2371function setFilters() {}
2372setFilters.prototype = Expr.filters = Expr.pseudos;
2373Expr.setFilters = new setFilters();
2374
2375tokenize = Sizzle.tokenize = function( selector, parseOnly ) {
2376 var matched, match, tokens, type,
2377 soFar, groups, preFilters,
2378 cached = tokenCache[ selector + " " ];
2379
2380 if ( cached ) {
2381 return parseOnly ? 0 : cached.slice( 0 );
2382 }
2383
2384 soFar = selector;
2385 groups = [];
2386 preFilters = Expr.preFilter;
2387
2388 while ( soFar ) {
2389
2390 // Comma and first run
2391 if ( !matched || (match = rcomma.exec( soFar )) ) {
2392 if ( match ) {
2393 // Don't consume trailing commas as valid
2394 soFar = soFar.slice( match[0].length ) || soFar;
2395 }
2396 groups.push( (tokens = []) );
2397 }
2398
2399 matched = false;
2400
2401 // Combinators
2402 if ( (match = rcombinators.exec( soFar )) ) {
2403 matched = match.shift();
2404 tokens.push({
2405 value: matched,
2406 // Cast descendant combinators to space
2407 type: match[0].replace( rtrim, " " )
2408 });
2409 soFar = soFar.slice( matched.length );
2410 }
2411
2412 // Filters
2413 for ( type in Expr.filter ) {
2414 if ( (match = matchExpr[ type ].exec( soFar )) && (!preFilters[ type ] ||
2415 (match = preFilters[ type ]( match ))) ) {
2416 matched = match.shift();
2417 tokens.push({
2418 value: matched,
2419 type: type,
2420 matches: match
2421 });
2422 soFar = soFar.slice( matched.length );
2423 }
2424 }
2425
2426 if ( !matched ) {
2427 break;
2428 }
2429 }
2430
2431 // Return the length of the invalid excess
2432 // if we're just parsing
2433 // Otherwise, throw an error or return tokens
2434 return parseOnly ?
2435 soFar.length :
2436 soFar ?
2437 Sizzle.error( selector ) :
2438 // Cache the tokens
2439 tokenCache( selector, groups ).slice( 0 );
2440};
2441
2442function toSelector( tokens ) {
2443 var i = 0,
2444 len = tokens.length,
2445 selector = "";
2446 for ( ; i < len; i++ ) {
2447 selector += tokens[i].value;
2448 }
2449 return selector;
2450}
2451
2452function addCombinator( matcher, combinator, base ) {
2453 var dir = combinator.dir,
2454 skip = combinator.next,
2455 key = skip || dir,
2456 checkNonElements = base && key === "parentNode",
2457 doneName = done++;
2458
2459 return combinator.first ?
2460 // Check against closest ancestor/preceding element
2461 function( elem, context, xml ) {
2462 while ( (elem = elem[ dir ]) ) {
2463 if ( elem.nodeType === 1 || checkNonElements ) {
2464 return matcher( elem, context, xml );
2465 }
2466 }
2467 return false;
2468 } :
2469
2470 // Check against all ancestor/preceding elements
2471 function( elem, context, xml ) {
2472 var oldCache, uniqueCache, outerCache,
2473 newCache = [ dirruns, doneName ];
2474
2475 // We can't set arbitrary data on XML nodes, so they don't benefit from combinator caching
2476 if ( xml ) {
2477 while ( (elem = elem[ dir ]) ) {
2478 if ( elem.nodeType === 1 || checkNonElements ) {
2479 if ( matcher( elem, context, xml ) ) {
2480 return true;
2481 }
2482 }
2483 }
2484 } else {
2485 while ( (elem = elem[ dir ]) ) {
2486 if ( elem.nodeType === 1 || checkNonElements ) {
2487 outerCache = elem[ expando ] || (elem[ expando ] = {});
2488
2489 // Support: IE <9 only
2490 // Defend against cloned attroperties (jQuery gh-1709)
2491 uniqueCache = outerCache[ elem.uniqueID ] || (outerCache[ elem.uniqueID ] = {});
2492
2493 if ( skip && skip === elem.nodeName.toLowerCase() ) {
2494 elem = elem[ dir ] || elem;
2495 } else if ( (oldCache = uniqueCache[ key ]) &&
2496 oldCache[ 0 ] === dirruns && oldCache[ 1 ] === doneName ) {
2497
2498 // Assign to newCache so results back-propagate to previous elements
2499 return (newCache[ 2 ] = oldCache[ 2 ]);
2500 } else {
2501 // Reuse newcache so results back-propagate to previous elements
2502 uniqueCache[ key ] = newCache;
2503
2504 // A match means we're done; a fail means we have to keep checking
2505 if ( (newCache[ 2 ] = matcher( elem, context, xml )) ) {
2506 return true;
2507 }
2508 }
2509 }
2510 }
2511 }
2512 return false;
2513 };
2514}
2515
2516function elementMatcher( matchers ) {
2517 return matchers.length > 1 ?
2518 function( elem, context, xml ) {
2519 var i = matchers.length;
2520 while ( i-- ) {
2521 if ( !matchers[i]( elem, context, xml ) ) {
2522 return false;
2523 }
2524 }
2525 return true;
2526 } :
2527 matchers[0];
2528}
2529
2530function multipleContexts( selector, contexts, results ) {
2531 var i = 0,
2532 len = contexts.length;
2533 for ( ; i < len; i++ ) {
2534 Sizzle( selector, contexts[i], results );
2535 }
2536 return results;
2537}
2538
2539function condense( unmatched, map, filter, context, xml ) {
2540 var elem,
2541 newUnmatched = [],
2542 i = 0,
2543 len = unmatched.length,
2544 mapped = map != null;
2545
2546 for ( ; i < len; i++ ) {
2547 if ( (elem = unmatched[i]) ) {
2548 if ( !filter || filter( elem, context, xml ) ) {
2549 newUnmatched.push( elem );
2550 if ( mapped ) {
2551 map.push( i );
2552 }
2553 }
2554 }
2555 }
2556
2557 return newUnmatched;
2558}
2559
2560function setMatcher( preFilter, selector, matcher, postFilter, postFinder, postSelector ) {
2561 if ( postFilter && !postFilter[ expando ] ) {
2562 postFilter = setMatcher( postFilter );
2563 }
2564 if ( postFinder && !postFinder[ expando ] ) {
2565 postFinder = setMatcher( postFinder, postSelector );
2566 }
2567 return markFunction(function( seed, results, context, xml ) {
2568 var temp, i, elem,
2569 preMap = [],
2570 postMap = [],
2571 preexisting = results.length,
2572
2573 // Get initial elements from seed or context
2574 elems = seed || multipleContexts( selector || "*", context.nodeType ? [ context ] : context, [] ),
2575
2576 // Prefilter to get matcher input, preserving a map for seed-results synchronization
2577 matcherIn = preFilter && ( seed || !selector ) ?
2578 condense( elems, preMap, preFilter, context, xml ) :
2579 elems,
2580
2581 matcherOut = matcher ?
2582 // If we have a postFinder, or filtered seed, or non-seed postFilter or preexisting results,
2583 postFinder || ( seed ? preFilter : preexisting || postFilter ) ?
2584
2585 // ...intermediate processing is necessary
2586 [] :
2587
2588 // ...otherwise use results directly
2589 results :
2590 matcherIn;
2591
2592 // Find primary matches
2593 if ( matcher ) {
2594 matcher( matcherIn, matcherOut, context, xml );
2595 }
2596
2597 // Apply postFilter
2598 if ( postFilter ) {
2599 temp = condense( matcherOut, postMap );
2600 postFilter( temp, [], context, xml );
2601
2602 // Un-match failing elements by moving them back to matcherIn
2603 i = temp.length;
2604 while ( i-- ) {
2605 if ( (elem = temp[i]) ) {
2606 matcherOut[ postMap[i] ] = !(matcherIn[ postMap[i] ] = elem);
2607 }
2608 }
2609 }
2610
2611 if ( seed ) {
2612 if ( postFinder || preFilter ) {
2613 if ( postFinder ) {
2614 // Get the final matcherOut by condensing this intermediate into postFinder contexts
2615 temp = [];
2616 i = matcherOut.length;
2617 while ( i-- ) {
2618 if ( (elem = matcherOut[i]) ) {
2619 // Restore matcherIn since elem is not yet a final match
2620 temp.push( (matcherIn[i] = elem) );
2621 }
2622 }
2623 postFinder( null, (matcherOut = []), temp, xml );
2624 }
2625
2626 // Move matched elements from seed to results to keep them synchronized
2627 i = matcherOut.length;
2628 while ( i-- ) {
2629 if ( (elem = matcherOut[i]) &&
2630 (temp = postFinder ? indexOf( seed, elem ) : preMap[i]) > -1 ) {
2631
2632 seed[temp] = !(results[temp] = elem);
2633 }
2634 }
2635 }
2636
2637 // Add elements to results, through postFinder if defined
2638 } else {
2639 matcherOut = condense(
2640 matcherOut === results ?
2641 matcherOut.splice( preexisting, matcherOut.length ) :
2642 matcherOut
2643 );
2644 if ( postFinder ) {
2645 postFinder( null, results, matcherOut, xml );
2646 } else {
2647 push.apply( results, matcherOut );
2648 }
2649 }
2650 });
2651}
2652
2653function matcherFromTokens( tokens ) {
2654 var checkContext, matcher, j,
2655 len = tokens.length,
2656 leadingRelative = Expr.relative[ tokens[0].type ],
2657 implicitRelative = leadingRelative || Expr.relative[" "],
2658 i = leadingRelative ? 1 : 0,
2659
2660 // The foundational matcher ensures that elements are reachable from top-level context(s)
2661 matchContext = addCombinator( function( elem ) {
2662 return elem === checkContext;
2663 }, implicitRelative, true ),
2664 matchAnyContext = addCombinator( function( elem ) {
2665 return indexOf( checkContext, elem ) > -1;
2666 }, implicitRelative, true ),
2667 matchers = [ function( elem, context, xml ) {
2668 var ret = ( !leadingRelative && ( xml || context !== outermostContext ) ) || (
2669 (checkContext = context).nodeType ?
2670 matchContext( elem, context, xml ) :
2671 matchAnyContext( elem, context, xml ) );
2672 // Avoid hanging onto element (issue #299)
2673 checkContext = null;
2674 return ret;
2675 } ];
2676
2677 for ( ; i < len; i++ ) {
2678 if ( (matcher = Expr.relative[ tokens[i].type ]) ) {
2679 matchers = [ addCombinator(elementMatcher( matchers ), matcher) ];
2680 } else {
2681 matcher = Expr.filter[ tokens[i].type ].apply( null, tokens[i].matches );
2682
2683 // Return special upon seeing a positional matcher
2684 if ( matcher[ expando ] ) {
2685 // Find the next relative operator (if any) for proper handling
2686 j = ++i;
2687 for ( ; j < len; j++ ) {
2688 if ( Expr.relative[ tokens[j].type ] ) {
2689 break;
2690 }
2691 }
2692 return setMatcher(
2693 i > 1 && elementMatcher( matchers ),
2694 i > 1 && toSelector(
2695 // If the preceding token was a descendant combinator, insert an implicit any-element `*`
2696 tokens.slice( 0, i - 1 ).concat({ value: tokens[ i - 2 ].type === " " ? "*" : "" })
2697 ).replace( rtrim, "$1" ),
2698 matcher,
2699 i < j && matcherFromTokens( tokens.slice( i, j ) ),
2700 j < len && matcherFromTokens( (tokens = tokens.slice( j )) ),
2701 j < len && toSelector( tokens )
2702 );
2703 }
2704 matchers.push( matcher );
2705 }
2706 }
2707
2708 return elementMatcher( matchers );
2709}
2710
2711function matcherFromGroupMatchers( elementMatchers, setMatchers ) {
2712 var bySet = setMatchers.length > 0,
2713 byElement = elementMatchers.length > 0,
2714 superMatcher = function( seed, context, xml, results, outermost ) {
2715 var elem, j, matcher,
2716 matchedCount = 0,
2717 i = "0",
2718 unmatched = seed && [],
2719 setMatched = [],
2720 contextBackup = outermostContext,
2721 // We must always have either seed elements or outermost context
2722 elems = seed || byElement && Expr.find["TAG"]( "*", outermost ),
2723 // Use integer dirruns iff this is the outermost matcher
2724 dirrunsUnique = (dirruns += contextBackup == null ? 1 : Math.random() || 0.1),
2725 len = elems.length;
2726
2727 if ( outermost ) {
2728 outermostContext = context === document || context || outermost;
2729 }
2730
2731 // Add elements passing elementMatchers directly to results
2732 // Support: IE<9, Safari
2733 // Tolerate NodeList properties (IE: "length"; Safari: <number>) matching elements by id
2734 for ( ; i !== len && (elem = elems[i]) != null; i++ ) {
2735 if ( byElement && elem ) {
2736 j = 0;
2737 if ( !context && elem.ownerDocument !== document ) {
2738 setDocument( elem );
2739 xml = !documentIsHTML;
2740 }
2741 while ( (matcher = elementMatchers[j++]) ) {
2742 if ( matcher( elem, context || document, xml) ) {
2743 results.push( elem );
2744 break;
2745 }
2746 }
2747 if ( outermost ) {
2748 dirruns = dirrunsUnique;
2749 }
2750 }
2751
2752 // Track unmatched elements for set filters
2753 if ( bySet ) {
2754 // They will have gone through all possible matchers
2755 if ( (elem = !matcher && elem) ) {
2756 matchedCount--;
2757 }
2758
2759 // Lengthen the array for every element, matched or not
2760 if ( seed ) {
2761 unmatched.push( elem );
2762 }
2763 }
2764 }
2765
2766 // `i` is now the count of elements visited above, and adding it to `matchedCount`
2767 // makes the latter nonnegative.
2768 matchedCount += i;
2769
2770 // Apply set filters to unmatched elements
2771 // NOTE: This can be skipped if there are no unmatched elements (i.e., `matchedCount`
2772 // equals `i`), unless we didn't visit _any_ elements in the above loop because we have
2773 // no element matchers and no seed.
2774 // Incrementing an initially-string "0" `i` allows `i` to remain a string only in that
2775 // case, which will result in a "00" `matchedCount` that differs from `i` but is also
2776 // numerically zero.
2777 if ( bySet && i !== matchedCount ) {
2778 j = 0;
2779 while ( (matcher = setMatchers[j++]) ) {
2780 matcher( unmatched, setMatched, context, xml );
2781 }
2782
2783 if ( seed ) {
2784 // Reintegrate element matches to eliminate the need for sorting
2785 if ( matchedCount > 0 ) {
2786 while ( i-- ) {
2787 if ( !(unmatched[i] || setMatched[i]) ) {
2788 setMatched[i] = pop.call( results );
2789 }
2790 }
2791 }
2792
2793 // Discard index placeholder values to get only actual matches
2794 setMatched = condense( setMatched );
2795 }
2796
2797 // Add matches to results
2798 push.apply( results, setMatched );
2799
2800 // Seedless set matches succeeding multiple successful matchers stipulate sorting
2801 if ( outermost && !seed && setMatched.length > 0 &&
2802 ( matchedCount + setMatchers.length ) > 1 ) {
2803
2804 Sizzle.uniqueSort( results );
2805 }
2806 }
2807
2808 // Override manipulation of globals by nested matchers
2809 if ( outermost ) {
2810 dirruns = dirrunsUnique;
2811 outermostContext = contextBackup;
2812 }
2813
2814 return unmatched;
2815 };
2816
2817 return bySet ?
2818 markFunction( superMatcher ) :
2819 superMatcher;
2820}
2821
2822compile = Sizzle.compile = function( selector, match /* Internal Use Only */ ) {
2823 var i,
2824 setMatchers = [],
2825 elementMatchers = [],
2826 cached = compilerCache[ selector + " " ];
2827
2828 if ( !cached ) {
2829 // Generate a function of recursive functions that can be used to check each element
2830 if ( !match ) {
2831 match = tokenize( selector );
2832 }
2833 i = match.length;
2834 while ( i-- ) {
2835 cached = matcherFromTokens( match[i] );
2836 if ( cached[ expando ] ) {
2837 setMatchers.push( cached );
2838 } else {
2839 elementMatchers.push( cached );
2840 }
2841 }
2842
2843 // Cache the compiled function
2844 cached = compilerCache( selector, matcherFromGroupMatchers( elementMatchers, setMatchers ) );
2845
2846 // Save selector and tokenization
2847 cached.selector = selector;
2848 }
2849 return cached;
2850};
2851
2852/**
2853 * A low-level selection function that works with Sizzle's compiled
2854 * selector functions
2855 * @param {String|Function} selector A selector or a pre-compiled
2856 * selector function built with Sizzle.compile
2857 * @param {Element} context
2858 * @param {Array} [results]
2859 * @param {Array} [seed] A set of elements to match against
2860 */
2861select = Sizzle.select = function( selector, context, results, seed ) {
2862 var i, tokens, token, type, find,
2863 compiled = typeof selector === "function" && selector,
2864 match = !seed && tokenize( (selector = compiled.selector || selector) );
2865
2866 results = results || [];
2867
2868 // Try to minimize operations if there is only one selector in the list and no seed
2869 // (the latter of which guarantees us context)
2870 if ( match.length === 1 ) {
2871
2872 // Reduce context if the leading compound selector is an ID
2873 tokens = match[0] = match[0].slice( 0 );
2874 if ( tokens.length > 2 && (token = tokens[0]).type === "ID" &&
2875 context.nodeType === 9 && documentIsHTML && Expr.relative[ tokens[1].type ] ) {
2876
2877 context = ( Expr.find["ID"]( token.matches[0].replace(runescape, funescape), context ) || [] )[0];
2878 if ( !context ) {
2879 return results;
2880
2881 // Precompiled matchers will still verify ancestry, so step up a level
2882 } else if ( compiled ) {
2883 context = context.parentNode;
2884 }
2885
2886 selector = selector.slice( tokens.shift().value.length );
2887 }
2888
2889 // Fetch a seed set for right-to-left matching
2890 i = matchExpr["needsContext"].test( selector ) ? 0 : tokens.length;
2891 while ( i-- ) {
2892 token = tokens[i];
2893
2894 // Abort if we hit a combinator
2895 if ( Expr.relative[ (type = token.type) ] ) {
2896 break;
2897 }
2898 if ( (find = Expr.find[ type ]) ) {
2899 // Search, expanding context for leading sibling combinators
2900 if ( (seed = find(
2901 token.matches[0].replace( runescape, funescape ),
2902 rsibling.test( tokens[0].type ) && testContext( context.parentNode ) || context
2903 )) ) {
2904
2905 // If seed is empty or no tokens remain, we can return early
2906 tokens.splice( i, 1 );
2907 selector = seed.length && toSelector( tokens );
2908 if ( !selector ) {
2909 push.apply( results, seed );
2910 return results;
2911 }
2912
2913 break;
2914 }
2915 }
2916 }
2917 }
2918
2919 // Compile and execute a filtering function if one is not provided
2920 // Provide `match` to avoid retokenization if we modified the selector above
2921 ( compiled || compile( selector, match ) )(
2922 seed,
2923 context,
2924 !documentIsHTML,
2925 results,
2926 !context || rsibling.test( selector ) && testContext( context.parentNode ) || context
2927 );
2928 return results;
2929};
2930
2931// One-time assignments
2932
2933// Sort stability
2934support.sortStable = expando.split("").sort( sortOrder ).join("") === expando;
2935
2936// Support: Chrome 14-35+
2937// Always assume duplicates if they aren't passed to the comparison function
2938support.detectDuplicates = !!hasDuplicate;
2939
2940// Initialize against the default document
2941setDocument();
2942
2943// Support: Webkit<537.32 - Safari 6.0.3/Chrome 25 (fixed in Chrome 27)
2944// Detached nodes confoundingly follow *each other*
2945support.sortDetached = assert(function( el ) {
2946 // Should return 1, but returns 4 (following)
2947 return el.compareDocumentPosition( document.createElement("fieldset") ) & 1;
2948});
2949
2950// Support: IE<8
2951// Prevent attribute/property "interpolation"
2952// https://msdn.microsoft.com/en-us/library/ms536429%28VS.85%29.aspx
2953if ( !assert(function( el ) {
2954 el.innerHTML = "<a href='#'></a>";
2955 return el.firstChild.getAttribute("href") === "#" ;
2956}) ) {
2957 addHandle( "type|href|height|width", function( elem, name, isXML ) {
2958 if ( !isXML ) {
2959 return elem.getAttribute( name, name.toLowerCase() === "type" ? 1 : 2 );
2960 }
2961 });
2962}
2963
2964// Support: IE<9
2965// Use defaultValue in place of getAttribute("value")
2966if ( !support.attributes || !assert(function( el ) {
2967 el.innerHTML = "<input/>";
2968 el.firstChild.setAttribute( "value", "" );
2969 return el.firstChild.getAttribute( "value" ) === "";
2970}) ) {
2971 addHandle( "value", function( elem, name, isXML ) {
2972 if ( !isXML && elem.nodeName.toLowerCase() === "input" ) {
2973 return elem.defaultValue;
2974 }
2975 });
2976}
2977
2978// Support: IE<9
2979// Use getAttributeNode to fetch booleans when getAttribute lies
2980if ( !assert(function( el ) {
2981 return el.getAttribute("disabled") == null;
2982}) ) {
2983 addHandle( booleans, function( elem, name, isXML ) {
2984 var val;
2985 if ( !isXML ) {
2986 return elem[ name ] === true ? name.toLowerCase() :
2987 (val = elem.getAttributeNode( name )) && val.specified ?
2988 val.value :
2989 null;
2990 }
2991 });
2992}
2993
2994return Sizzle;
2995
2996})( window );
2997
2998
2999
3000jQuery.find = Sizzle;
3001jQuery.expr = Sizzle.selectors;
3002
3003// Deprecated
3004jQuery.expr[ ":" ] = jQuery.expr.pseudos;
3005jQuery.uniqueSort = jQuery.unique = Sizzle.uniqueSort;
3006jQuery.text = Sizzle.getText;
3007jQuery.isXMLDoc = Sizzle.isXML;
3008jQuery.contains = Sizzle.contains;
3009jQuery.escapeSelector = Sizzle.escape;
3010
3011
3012
3013
3014var dir = function( elem, dir, until ) {
3015 var matched = [],
3016 truncate = until !== undefined;
3017
3018 while ( ( elem = elem[ dir ] ) && elem.nodeType !== 9 ) {
3019 if ( elem.nodeType === 1 ) {
3020 if ( truncate && jQuery( elem ).is( until ) ) {
3021 break;
3022 }
3023 matched.push( elem );
3024 }
3025 }
3026 return matched;
3027};
3028
3029
3030var siblings = function( n, elem ) {
3031 var matched = [];
3032
3033 for ( ; n; n = n.nextSibling ) {
3034 if ( n.nodeType === 1 && n !== elem ) {
3035 matched.push( n );
3036 }
3037 }
3038
3039 return matched;
3040};
3041
3042
3043var rneedsContext = jQuery.expr.match.needsContext;
3044
3045
3046
3047function nodeName( elem, name ) {
3048
3049 return elem.nodeName && elem.nodeName.toLowerCase() === name.toLowerCase();
3050
3051};
3052var rsingleTag = ( /^<([a-z][^\/\0>:\x20\t\r\n\f]*)[\x20\t\r\n\f]*\/?>(?:<\/\1>|)$/i );
3053
3054
3055
3056// Implement the identical functionality for filter and not
3057function winnow( elements, qualifier, not ) {
3058 if ( isFunction( qualifier ) ) {
3059 return jQuery.grep( elements, function( elem, i ) {
3060 return !!qualifier.call( elem, i, elem ) !== not;
3061 } );
3062 }
3063
3064 // Single element
3065 if ( qualifier.nodeType ) {
3066 return jQuery.grep( elements, function( elem ) {
3067 return ( elem === qualifier ) !== not;
3068 } );
3069 }
3070
3071 // Arraylike of elements (jQuery, arguments, Array)
3072 if ( typeof qualifier !== "string" ) {
3073 return jQuery.grep( elements, function( elem ) {
3074 return ( indexOf.call( qualifier, elem ) > -1 ) !== not;
3075 } );
3076 }
3077
3078 // Filtered directly for both simple and complex selectors
3079 return jQuery.filter( qualifier, elements, not );
3080}
3081
3082jQuery.filter = function( expr, elems, not ) {
3083 var elem = elems[ 0 ];
3084
3085 if ( not ) {
3086 expr = ":not(" + expr + ")";
3087 }
3088
3089 if ( elems.length === 1 && elem.nodeType === 1 ) {
3090 return jQuery.find.matchesSelector( elem, expr ) ? [ elem ] : [];
3091 }
3092
3093 return jQuery.find.matches( expr, jQuery.grep( elems, function( elem ) {
3094 return elem.nodeType === 1;
3095 } ) );
3096};
3097
3098jQuery.fn.extend( {
3099 find: function( selector ) {
3100 var i, ret,
3101 len = this.length,
3102 self = this;
3103
3104 if ( typeof selector !== "string" ) {
3105 return this.pushStack( jQuery( selector ).filter( function() {
3106 for ( i = 0; i < len; i++ ) {
3107 if ( jQuery.contains( self[ i ], this ) ) {
3108 return true;
3109 }
3110 }
3111 } ) );
3112 }
3113
3114 ret = this.pushStack( [] );
3115
3116 for ( i = 0; i < len; i++ ) {
3117 jQuery.find( selector, self[ i ], ret );
3118 }
3119
3120 return len > 1 ? jQuery.uniqueSort( ret ) : ret;
3121 },
3122 filter: function( selector ) {
3123 return this.pushStack( winnow( this, selector || [], false ) );
3124 },
3125 not: function( selector ) {
3126 return this.pushStack( winnow( this, selector || [], true ) );
3127 },
3128 is: function( selector ) {
3129 return !!winnow(
3130 this,
3131
3132 // If this is a positional/relative selector, check membership in the returned set
3133 // so $("p:first").is("p:last") won't return true for a doc with two "p".
3134 typeof selector === "string" && rneedsContext.test( selector ) ?
3135 jQuery( selector ) :
3136 selector || [],
3137 false
3138 ).length;
3139 }
3140} );
3141
3142
3143// Initialize a jQuery object
3144
3145
3146// A central reference to the root jQuery(document)
3147var rootjQuery,
3148
3149 // A simple way to check for HTML strings
3150 // Prioritize #id over <tag> to avoid XSS via location.hash (#9521)
3151 // Strict HTML recognition (#11290: must start with <)
3152 // Shortcut simple #id case for speed
3153 rquickExpr = /^(?:\s*(<[\w\W]+>)[^>]*|#([\w-]+))$/,
3154
3155 init = jQuery.fn.init = function( selector, context, root ) {
3156 var match, elem;
3157
3158 // HANDLE: $(""), $(null), $(undefined), $(false)
3159 if ( !selector ) {
3160 return this;
3161 }
3162
3163 // Method init() accepts an alternate rootjQuery
3164 // so migrate can support jQuery.sub (gh-2101)
3165 root = root || rootjQuery;
3166
3167 // Handle HTML strings
3168 if ( typeof selector === "string" ) {
3169 if ( selector[ 0 ] === "<" &&
3170 selector[ selector.length - 1 ] === ">" &&
3171 selector.length >= 3 ) {
3172
3173 // Assume that strings that start and end with <> are HTML and skip the regex check
3174 match = [ null, selector, null ];
3175
3176 } else {
3177 match = rquickExpr.exec( selector );
3178 }
3179
3180 // Match html or make sure no context is specified for #id
3181 if ( match && ( match[ 1 ] || !context ) ) {
3182
3183 // HANDLE: $(html) -> $(array)
3184 if ( match[ 1 ] ) {
3185 context = context instanceof jQuery ? context[ 0 ] : context;
3186
3187 // Option to run scripts is true for back-compat
3188 // Intentionally let the error be thrown if parseHTML is not present
3189 jQuery.merge( this, jQuery.parseHTML(
3190 match[ 1 ],
3191 context && context.nodeType ? context.ownerDocument || context : document,
3192 true
3193 ) );
3194
3195 // HANDLE: $(html, props)
3196 if ( rsingleTag.test( match[ 1 ] ) && jQuery.isPlainObject( context ) ) {
3197 for ( match in context ) {
3198
3199 // Properties of context are called as methods if possible
3200 if ( isFunction( this[ match ] ) ) {
3201 this[ match ]( context[ match ] );
3202
3203 // ...and otherwise set as attributes
3204 } else {
3205 this.attr( match, context[ match ] );
3206 }
3207 }
3208 }
3209
3210 return this;
3211
3212 // HANDLE: $(#id)
3213 } else {
3214 elem = document.getElementById( match[ 2 ] );
3215
3216 if ( elem ) {
3217
3218 // Inject the element directly into the jQuery object
3219 this[ 0 ] = elem;
3220 this.length = 1;
3221 }
3222 return this;
3223 }
3224
3225 // HANDLE: $(expr, $(...))
3226 } else if ( !context || context.jquery ) {
3227 return ( context || root ).find( selector );
3228
3229 // HANDLE: $(expr, context)
3230 // (which is just equivalent to: $(context).find(expr)
3231 } else {
3232 return this.constructor( context ).find( selector );
3233 }
3234
3235 // HANDLE: $(DOMElement)
3236 } else if ( selector.nodeType ) {
3237 this[ 0 ] = selector;
3238 this.length = 1;
3239 return this;
3240
3241 // HANDLE: $(function)
3242 // Shortcut for document ready
3243 } else if ( isFunction( selector ) ) {
3244 return root.ready !== undefined ?
3245 root.ready( selector ) :
3246
3247 // Execute immediately if ready is not present
3248 selector( jQuery );
3249 }
3250
3251 return jQuery.makeArray( selector, this );
3252 };
3253
3254// Give the init function the jQuery prototype for later instantiation
3255init.prototype = jQuery.fn;
3256
3257// Initialize central reference
3258rootjQuery = jQuery( document );
3259
3260
3261var rparentsprev = /^(?:parents|prev(?:Until|All))/,
3262
3263 // Methods guaranteed to produce a unique set when starting from a unique set
3264 guaranteedUnique = {
3265 children: true,
3266 contents: true,
3267 next: true,
3268 prev: true
3269 };
3270
3271jQuery.fn.extend( {
3272 has: function( target ) {
3273 var targets = jQuery( target, this ),
3274 l = targets.length;
3275
3276 return this.filter( function() {
3277 var i = 0;
3278 for ( ; i < l; i++ ) {
3279 if ( jQuery.contains( this, targets[ i ] ) ) {
3280 return true;
3281 }
3282 }
3283 } );
3284 },
3285
3286 closest: function( selectors, context ) {
3287 var cur,
3288 i = 0,
3289 l = this.length,
3290 matched = [],
3291 targets = typeof selectors !== "string" && jQuery( selectors );
3292
3293 // Positional selectors never match, since there's no _selection_ context
3294 if ( !rneedsContext.test( selectors ) ) {
3295 for ( ; i < l; i++ ) {
3296 for ( cur = this[ i ]; cur && cur !== context; cur = cur.parentNode ) {
3297
3298 // Always skip document fragments
3299 if ( cur.nodeType < 11 && ( targets ?
3300 targets.index( cur ) > -1 :
3301
3302 // Don't pass non-elements to Sizzle
3303 cur.nodeType === 1 &&
3304 jQuery.find.matchesSelector( cur, selectors ) ) ) {
3305
3306 matched.push( cur );
3307 break;
3308 }
3309 }
3310 }
3311 }
3312
3313 return this.pushStack( matched.length > 1 ? jQuery.uniqueSort( matched ) : matched );
3314 },
3315
3316 // Determine the position of an element within the set
3317 index: function( elem ) {
3318
3319 // No argument, return index in parent
3320 if ( !elem ) {
3321 return ( this[ 0 ] && this[ 0 ].parentNode ) ? this.first().prevAll().length : -1;
3322 }
3323
3324 // Index in selector
3325 if ( typeof elem === "string" ) {
3326 return indexOf.call( jQuery( elem ), this[ 0 ] );
3327 }
3328
3329 // Locate the position of the desired element
3330 return indexOf.call( this,
3331
3332 // If it receives a jQuery object, the first element is used
3333 elem.jquery ? elem[ 0 ] : elem
3334 );
3335 },
3336
3337 add: function( selector, context ) {
3338 return this.pushStack(
3339 jQuery.uniqueSort(
3340 jQuery.merge( this.get(), jQuery( selector, context ) )
3341 )
3342 );
3343 },
3344
3345 addBack: function( selector ) {
3346 return this.add( selector == null ?
3347 this.prevObject : this.prevObject.filter( selector )
3348 );
3349 }
3350} );
3351
3352function sibling( cur, dir ) {
3353 while ( ( cur = cur[ dir ] ) && cur.nodeType !== 1 ) {}
3354 return cur;
3355}
3356
3357jQuery.each( {
3358 parent: function( elem ) {
3359 var parent = elem.parentNode;
3360 return parent && parent.nodeType !== 11 ? parent : null;
3361 },
3362 parents: function( elem ) {
3363 return dir( elem, "parentNode" );
3364 },
3365 parentsUntil: function( elem, i, until ) {
3366 return dir( elem, "parentNode", until );
3367 },
3368 next: function( elem ) {
3369 return sibling( elem, "nextSibling" );
3370 },
3371 prev: function( elem ) {
3372 return sibling( elem, "previousSibling" );
3373 },
3374 nextAll: function( elem ) {
3375 return dir( elem, "nextSibling" );
3376 },
3377 prevAll: function( elem ) {
3378 return dir( elem, "previousSibling" );
3379 },
3380 nextUntil: function( elem, i, until ) {
3381 return dir( elem, "nextSibling", until );
3382 },
3383 prevUntil: function( elem, i, until ) {
3384 return dir( elem, "previousSibling", until );
3385 },
3386 siblings: function( elem ) {
3387 return siblings( ( elem.parentNode || {} ).firstChild, elem );
3388 },
3389 children: function( elem ) {
3390 return siblings( elem.firstChild );
3391 },
3392 contents: function( elem ) {
3393 if ( nodeName( elem, "iframe" ) ) {
3394 return elem.contentDocument;
3395 }
3396
3397 // Support: IE 9 - 11 only, iOS 7 only, Android Browser <=4.3 only
3398 // Treat the template element as a regular one in browsers that
3399 // don't support it.
3400 if ( nodeName( elem, "template" ) ) {
3401 elem = elem.content || elem;
3402 }
3403
3404 return jQuery.merge( [], elem.childNodes );
3405 }
3406}, function( name, fn ) {
3407 jQuery.fn[ name ] = function( until, selector ) {
3408 var matched = jQuery.map( this, fn, until );
3409
3410 if ( name.slice( -5 ) !== "Until" ) {
3411 selector = until;
3412 }
3413
3414 if ( selector && typeof selector === "string" ) {
3415 matched = jQuery.filter( selector, matched );
3416 }
3417
3418 if ( this.length > 1 ) {
3419
3420 // Remove duplicates
3421 if ( !guaranteedUnique[ name ] ) {
3422 jQuery.uniqueSort( matched );
3423 }
3424
3425 // Reverse order for parents* and prev-derivatives
3426 if ( rparentsprev.test( name ) ) {
3427 matched.reverse();
3428 }
3429 }
3430
3431 return this.pushStack( matched );
3432 };
3433} );
3434var rnothtmlwhite = ( /[^\x20\t\r\n\f]+/g );
3435
3436
3437
3438// Convert String-formatted options into Object-formatted ones
3439function createOptions( options ) {
3440 var object = {};
3441 jQuery.each( options.match( rnothtmlwhite ) || [], function( _, flag ) {
3442 object[ flag ] = true;
3443 } );
3444 return object;
3445}
3446
3447/*
3448 * Create a callback list using the following parameters:
3449 *
3450 * options: an optional list of space-separated options that will change how
3451 * the callback list behaves or a more traditional option object
3452 *
3453 * By default a callback list will act like an event callback list and can be
3454 * "fired" multiple times.
3455 *
3456 * Possible options:
3457 *
3458 * once: will ensure the callback list can only be fired once (like a Deferred)
3459 *
3460 * memory: will keep track of previous values and will call any callback added
3461 * after the list has been fired right away with the latest "memorized"
3462 * values (like a Deferred)
3463 *
3464 * unique: will ensure a callback can only be added once (no duplicate in the list)
3465 *
3466 * stopOnFalse: interrupt callings when a callback returns false
3467 *
3468 */
3469jQuery.Callbacks = function( options ) {
3470
3471 // Convert options from String-formatted to Object-formatted if needed
3472 // (we check in cache first)
3473 options = typeof options === "string" ?
3474 createOptions( options ) :
3475 jQuery.extend( {}, options );
3476
3477 var // Flag to know if list is currently firing
3478 firing,
3479
3480 // Last fire value for non-forgettable lists
3481 memory,
3482
3483 // Flag to know if list was already fired
3484 fired,
3485
3486 // Flag to prevent firing
3487 locked,
3488
3489 // Actual callback list
3490 list = [],
3491
3492 // Queue of execution data for repeatable lists
3493 queue = [],
3494
3495 // Index of currently firing callback (modified by add/remove as needed)
3496 firingIndex = -1,
3497
3498 // Fire callbacks
3499 fire = function() {
3500
3501 // Enforce single-firing
3502 locked = locked || options.once;
3503
3504 // Execute callbacks for all pending executions,
3505 // respecting firingIndex overrides and runtime changes
3506 fired = firing = true;
3507 for ( ; queue.length; firingIndex = -1 ) {
3508 memory = queue.shift();
3509 while ( ++firingIndex < list.length ) {
3510
3511 // Run callback and check for early termination
3512 if ( list[ firingIndex ].apply( memory[ 0 ], memory[ 1 ] ) === false &&
3513 options.stopOnFalse ) {
3514
3515 // Jump to end and forget the data so .add doesn't re-fire
3516 firingIndex = list.length;
3517 memory = false;
3518 }
3519 }
3520 }
3521
3522 // Forget the data if we're done with it
3523 if ( !options.memory ) {
3524 memory = false;
3525 }
3526
3527 firing = false;
3528
3529 // Clean up if we're done firing for good
3530 if ( locked ) {
3531
3532 // Keep an empty list if we have data for future add calls
3533 if ( memory ) {
3534 list = [];
3535
3536 // Otherwise, this object is spent
3537 } else {
3538 list = "";
3539 }
3540 }
3541 },
3542
3543 // Actual Callbacks object
3544 self = {
3545
3546 // Add a callback or a collection of callbacks to the list
3547 add: function() {
3548 if ( list ) {
3549
3550 // If we have memory from a past run, we should fire after adding
3551 if ( memory && !firing ) {
3552 firingIndex = list.length - 1;
3553 queue.push( memory );
3554 }
3555
3556 ( function add( args ) {
3557 jQuery.each( args, function( _, arg ) {
3558 if ( isFunction( arg ) ) {
3559 if ( !options.unique || !self.has( arg ) ) {
3560 list.push( arg );
3561 }
3562 } else if ( arg && arg.length && toType( arg ) !== "string" ) {
3563
3564 // Inspect recursively
3565 add( arg );
3566 }
3567 } );
3568 } )( arguments );
3569
3570 if ( memory && !firing ) {
3571 fire();
3572 }
3573 }
3574 return this;
3575 },
3576
3577 // Remove a callback from the list
3578 remove: function() {
3579 jQuery.each( arguments, function( _, arg ) {
3580 var index;
3581 while ( ( index = jQuery.inArray( arg, list, index ) ) > -1 ) {
3582 list.splice( index, 1 );
3583
3584 // Handle firing indexes
3585 if ( index <= firingIndex ) {
3586 firingIndex--;
3587 }
3588 }
3589 } );
3590 return this;
3591 },
3592
3593 // Check if a given callback is in the list.
3594 // If no argument is given, return whether or not list has callbacks attached.
3595 has: function( fn ) {
3596 return fn ?
3597 jQuery.inArray( fn, list ) > -1 :
3598 list.length > 0;
3599 },
3600
3601 // Remove all callbacks from the list
3602 empty: function() {
3603 if ( list ) {
3604 list = [];
3605 }
3606 return this;
3607 },
3608
3609 // Disable .fire and .add
3610 // Abort any current/pending executions
3611 // Clear all callbacks and values
3612 disable: function() {
3613 locked = queue = [];
3614 list = memory = "";
3615 return this;
3616 },
3617 disabled: function() {
3618 return !list;
3619 },
3620
3621 // Disable .fire
3622 // Also disable .add unless we have memory (since it would have no effect)
3623 // Abort any pending executions
3624 lock: function() {
3625 locked = queue = [];
3626 if ( !memory && !firing ) {
3627 list = memory = "";
3628 }
3629 return this;
3630 },
3631 locked: function() {
3632 return !!locked;
3633 },
3634
3635 // Call all callbacks with the given context and arguments
3636 fireWith: function( context, args ) {
3637 if ( !locked ) {
3638 args = args || [];
3639 args = [ context, args.slice ? args.slice() : args ];
3640 queue.push( args );
3641 if ( !firing ) {
3642 fire();
3643 }
3644 }
3645 return this;
3646 },
3647
3648 // Call all the callbacks with the given arguments
3649 fire: function() {
3650 self.fireWith( this, arguments );
3651 return this;
3652 },
3653
3654 // To know if the callbacks have already been called at least once
3655 fired: function() {
3656 return !!fired;
3657 }
3658 };
3659
3660 return self;
3661};
3662
3663
3664function Identity( v ) {
3665 return v;
3666}
3667function Thrower( ex ) {
3668 throw ex;
3669}
3670
3671function adoptValue( value, resolve, reject, noValue ) {
3672 var method;
3673
3674 try {
3675
3676 // Check for promise aspect first to privilege synchronous behavior
3677 if ( value && isFunction( ( method = value.promise ) ) ) {
3678 method.call( value ).done( resolve ).fail( reject );
3679
3680 // Other thenables
3681 } else if ( value && isFunction( ( method = value.then ) ) ) {
3682 method.call( value, resolve, reject );
3683
3684 // Other non-thenables
3685 } else {
3686
3687 // Control `resolve` arguments by letting Array#slice cast boolean `noValue` to integer:
3688 // * false: [ value ].slice( 0 ) => resolve( value )
3689 // * true: [ value ].slice( 1 ) => resolve()
3690 resolve.apply( undefined, [ value ].slice( noValue ) );
3691 }
3692
3693 // For Promises/A+, convert exceptions into rejections
3694 // Since jQuery.when doesn't unwrap thenables, we can skip the extra checks appearing in
3695 // Deferred#then to conditionally suppress rejection.
3696 } catch ( value ) {
3697
3698 // Support: Android 4.0 only
3699 // Strict mode functions invoked without .call/.apply get global-object context
3700 reject.apply( undefined, [ value ] );
3701 }
3702}
3703
3704jQuery.extend( {
3705
3706 Deferred: function( func ) {
3707 var tuples = [
3708
3709 // action, add listener, callbacks,
3710 // ... .then handlers, argument index, [final state]
3711 [ "notify", "progress", jQuery.Callbacks( "memory" ),
3712 jQuery.Callbacks( "memory" ), 2 ],
3713 [ "resolve", "done", jQuery.Callbacks( "once memory" ),
3714 jQuery.Callbacks( "once memory" ), 0, "resolved" ],
3715 [ "reject", "fail", jQuery.Callbacks( "once memory" ),
3716 jQuery.Callbacks( "once memory" ), 1, "rejected" ]
3717 ],
3718 state = "pending",
3719 promise = {
3720 state: function() {
3721 return state;
3722 },
3723 always: function() {
3724 deferred.done( arguments ).fail( arguments );
3725 return this;
3726 },
3727 "catch": function( fn ) {
3728 return promise.then( null, fn );
3729 },
3730
3731 // Keep pipe for back-compat
3732 pipe: function( /* fnDone, fnFail, fnProgress */ ) {
3733 var fns = arguments;
3734
3735 return jQuery.Deferred( function( newDefer ) {
3736 jQuery.each( tuples, function( i, tuple ) {
3737
3738 // Map tuples (progress, done, fail) to arguments (done, fail, progress)
3739 var fn = isFunction( fns[ tuple[ 4 ] ] ) && fns[ tuple[ 4 ] ];
3740
3741 // deferred.progress(function() { bind to newDefer or newDefer.notify })
3742 // deferred.done(function() { bind to newDefer or newDefer.resolve })
3743 // deferred.fail(function() { bind to newDefer or newDefer.reject })
3744 deferred[ tuple[ 1 ] ]( function() {
3745 var returned = fn && fn.apply( this, arguments );
3746 if ( returned && isFunction( returned.promise ) ) {
3747 returned.promise()
3748 .progress( newDefer.notify )
3749 .done( newDefer.resolve )
3750 .fail( newDefer.reject );
3751 } else {
3752 newDefer[ tuple[ 0 ] + "With" ](
3753 this,
3754 fn ? [ returned ] : arguments
3755 );
3756 }
3757 } );
3758 } );
3759 fns = null;
3760 } ).promise();
3761 },
3762 then: function( onFulfilled, onRejected, onProgress ) {
3763 var maxDepth = 0;
3764 function resolve( depth, deferred, handler, special ) {
3765 return function() {
3766 var that = this,
3767 args = arguments,
3768 mightThrow = function() {
3769 var returned, then;
3770
3771 // Support: Promises/A+ section 2.3.3.3.3
3772 // https://promisesaplus.com/#point-59
3773 // Ignore double-resolution attempts
3774 if ( depth < maxDepth ) {
3775 return;
3776 }
3777
3778 returned = handler.apply( that, args );
3779
3780 // Support: Promises/A+ section 2.3.1
3781 // https://promisesaplus.com/#point-48
3782 if ( returned === deferred.promise() ) {
3783 throw new TypeError( "Thenable self-resolution" );
3784 }
3785
3786 // Support: Promises/A+ sections 2.3.3.1, 3.5
3787 // https://promisesaplus.com/#point-54
3788 // https://promisesaplus.com/#point-75
3789 // Retrieve `then` only once
3790 then = returned &&
3791
3792 // Support: Promises/A+ section 2.3.4
3793 // https://promisesaplus.com/#point-64
3794 // Only check objects and functions for thenability
3795 ( typeof returned === "object" ||
3796 typeof returned === "function" ) &&
3797 returned.then;
3798
3799 // Handle a returned thenable
3800 if ( isFunction( then ) ) {
3801
3802 // Special processors (notify) just wait for resolution
3803 if ( special ) {
3804 then.call(
3805 returned,
3806 resolve( maxDepth, deferred, Identity, special ),
3807 resolve( maxDepth, deferred, Thrower, special )
3808 );
3809
3810 // Normal processors (resolve) also hook into progress
3811 } else {
3812
3813 // ...and disregard older resolution values
3814 maxDepth++;
3815
3816 then.call(
3817 returned,
3818 resolve( maxDepth, deferred, Identity, special ),
3819 resolve( maxDepth, deferred, Thrower, special ),
3820 resolve( maxDepth, deferred, Identity,
3821 deferred.notifyWith )
3822 );
3823 }
3824
3825 // Handle all other returned values
3826 } else {
3827
3828 // Only substitute handlers pass on context
3829 // and multiple values (non-spec behavior)
3830 if ( handler !== Identity ) {
3831 that = undefined;
3832 args = [ returned ];
3833 }
3834
3835 // Process the value(s)
3836 // Default process is resolve
3837 ( special || deferred.resolveWith )( that, args );
3838 }
3839 },
3840
3841 // Only normal processors (resolve) catch and reject exceptions
3842 process = special ?
3843 mightThrow :
3844 function() {
3845 try {
3846 mightThrow();
3847 } catch ( e ) {
3848
3849 if ( jQuery.Deferred.exceptionHook ) {
3850 jQuery.Deferred.exceptionHook( e,
3851 process.stackTrace );
3852 }
3853
3854 // Support: Promises/A+ section 2.3.3.3.4.1
3855 // https://promisesaplus.com/#point-61
3856 // Ignore post-resolution exceptions
3857 if ( depth + 1 >= maxDepth ) {
3858
3859 // Only substitute handlers pass on context
3860 // and multiple values (non-spec behavior)
3861 if ( handler !== Thrower ) {
3862 that = undefined;
3863 args = [ e ];
3864 }
3865
3866 deferred.rejectWith( that, args );
3867 }
3868 }
3869 };
3870
3871 // Support: Promises/A+ section 2.3.3.3.1
3872 // https://promisesaplus.com/#point-57
3873 // Re-resolve promises immediately to dodge false rejection from
3874 // subsequent errors
3875 if ( depth ) {
3876 process();
3877 } else {
3878
3879 // Call an optional hook to record the stack, in case of exception
3880 // since it's otherwise lost when execution goes async
3881 if ( jQuery.Deferred.getStackHook ) {
3882 process.stackTrace = jQuery.Deferred.getStackHook();
3883 }
3884 window.setTimeout( process );
3885 }
3886 };
3887 }
3888
3889 return jQuery.Deferred( function( newDefer ) {
3890
3891 // progress_handlers.add( ... )
3892 tuples[ 0 ][ 3 ].add(
3893 resolve(
3894 0,
3895 newDefer,
3896 isFunction( onProgress ) ?
3897 onProgress :
3898 Identity,
3899 newDefer.notifyWith
3900 )
3901 );
3902
3903 // fulfilled_handlers.add( ... )
3904 tuples[ 1 ][ 3 ].add(
3905 resolve(
3906 0,
3907 newDefer,
3908 isFunction( onFulfilled ) ?
3909 onFulfilled :
3910 Identity
3911 )
3912 );
3913
3914 // rejected_handlers.add( ... )
3915 tuples[ 2 ][ 3 ].add(
3916 resolve(
3917 0,
3918 newDefer,
3919 isFunction( onRejected ) ?
3920 onRejected :
3921 Thrower
3922 )
3923 );
3924 } ).promise();
3925 },
3926
3927 // Get a promise for this deferred
3928 // If obj is provided, the promise aspect is added to the object
3929 promise: function( obj ) {
3930 return obj != null ? jQuery.extend( obj, promise ) : promise;
3931 }
3932 },
3933 deferred = {};
3934
3935 // Add list-specific methods
3936 jQuery.each( tuples, function( i, tuple ) {
3937 var list = tuple[ 2 ],
3938 stateString = tuple[ 5 ];
3939
3940 // promise.progress = list.add
3941 // promise.done = list.add
3942 // promise.fail = list.add
3943 promise[ tuple[ 1 ] ] = list.add;
3944
3945 // Handle state
3946 if ( stateString ) {
3947 list.add(
3948 function() {
3949
3950 // state = "resolved" (i.e., fulfilled)
3951 // state = "rejected"
3952 state = stateString;
3953 },
3954
3955 // rejected_callbacks.disable
3956 // fulfilled_callbacks.disable
3957 tuples[ 3 - i ][ 2 ].disable,
3958
3959 // rejected_handlers.disable
3960 // fulfilled_handlers.disable
3961 tuples[ 3 - i ][ 3 ].disable,
3962
3963 // progress_callbacks.lock
3964 tuples[ 0 ][ 2 ].lock,
3965
3966 // progress_handlers.lock
3967 tuples[ 0 ][ 3 ].lock
3968 );
3969 }
3970
3971 // progress_handlers.fire
3972 // fulfilled_handlers.fire
3973 // rejected_handlers.fire
3974 list.add( tuple[ 3 ].fire );
3975
3976 // deferred.notify = function() { deferred.notifyWith(...) }
3977 // deferred.resolve = function() { deferred.resolveWith(...) }
3978 // deferred.reject = function() { deferred.rejectWith(...) }
3979 deferred[ tuple[ 0 ] ] = function() {
3980 deferred[ tuple[ 0 ] + "With" ]( this === deferred ? undefined : this, arguments );
3981 return this;
3982 };
3983
3984 // deferred.notifyWith = list.fireWith
3985 // deferred.resolveWith = list.fireWith
3986 // deferred.rejectWith = list.fireWith
3987 deferred[ tuple[ 0 ] + "With" ] = list.fireWith;
3988 } );
3989
3990 // Make the deferred a promise
3991 promise.promise( deferred );
3992
3993 // Call given func if any
3994 if ( func ) {
3995 func.call( deferred, deferred );
3996 }
3997
3998 // All done!
3999 return deferred;
4000 },
4001
4002 // Deferred helper
4003 when: function( singleValue ) {
4004 var
4005
4006 // count of uncompleted subordinates
4007 remaining = arguments.length,
4008
4009 // count of unprocessed arguments
4010 i = remaining,
4011
4012 // subordinate fulfillment data
4013 resolveContexts = Array( i ),
4014 resolveValues = slice.call( arguments ),
4015
4016 // the master Deferred
4017 master = jQuery.Deferred(),
4018
4019 // subordinate callback factory
4020 updateFunc = function( i ) {
4021 return function( value ) {
4022 resolveContexts[ i ] = this;
4023 resolveValues[ i ] = arguments.length > 1 ? slice.call( arguments ) : value;
4024 if ( !( --remaining ) ) {
4025 master.resolveWith( resolveContexts, resolveValues );
4026 }
4027 };
4028 };
4029
4030 // Single- and empty arguments are adopted like Promise.resolve
4031 if ( remaining <= 1 ) {
4032 adoptValue( singleValue, master.done( updateFunc( i ) ).resolve, master.reject,
4033 !remaining );
4034
4035 // Use .then() to unwrap secondary thenables (cf. gh-3000)
4036 if ( master.state() === "pending" ||
4037 isFunction( resolveValues[ i ] && resolveValues[ i ].then ) ) {
4038
4039 return master.then();
4040 }
4041 }
4042
4043 // Multiple arguments are aggregated like Promise.all array elements
4044 while ( i-- ) {
4045 adoptValue( resolveValues[ i ], updateFunc( i ), master.reject );
4046 }
4047
4048 return master.promise();
4049 }
4050} );
4051
4052
4053// These usually indicate a programmer mistake during development,
4054// warn about them ASAP rather than swallowing them by default.
4055var rerrorNames = /^(Eval|Internal|Range|Reference|Syntax|Type|URI)Error$/;
4056
4057jQuery.Deferred.exceptionHook = function( error, stack ) {
4058
4059 // Support: IE 8 - 9 only
4060 // Console exists when dev tools are open, which can happen at any time
4061 if ( window.console && window.console.warn && error && rerrorNames.test( error.name ) ) {
4062 window.console.warn( "jQuery.Deferred exception: " + error.message, error.stack, stack );
4063 }
4064};
4065
4066
4067
4068
4069jQuery.readyException = function( error ) {
4070 window.setTimeout( function() {
4071 throw error;
4072 } );
4073};
4074
4075
4076
4077
4078// The deferred used on DOM ready
4079var readyList = jQuery.Deferred();
4080
4081jQuery.fn.ready = function( fn ) {
4082
4083 readyList
4084 .then( fn )
4085
4086 // Wrap jQuery.readyException in a function so that the lookup
4087 // happens at the time of error handling instead of callback
4088 // registration.
4089 .catch( function( error ) {
4090 jQuery.readyException( error );
4091 } );
4092
4093 return this;
4094};
4095
4096jQuery.extend( {
4097
4098 // Is the DOM ready to be used? Set to true once it occurs.
4099 isReady: false,
4100
4101 // A counter to track how many items to wait for before
4102 // the ready event fires. See #6781
4103 readyWait: 1,
4104
4105 // Handle when the DOM is ready
4106 ready: function( wait ) {
4107
4108 // Abort if there are pending holds or we're already ready
4109 if ( wait === true ? --jQuery.readyWait : jQuery.isReady ) {
4110 return;
4111 }
4112
4113 // Remember that the DOM is ready
4114 jQuery.isReady = true;
4115
4116 // If a normal DOM Ready event fired, decrement, and wait if need be
4117 if ( wait !== true && --jQuery.readyWait > 0 ) {
4118 return;
4119 }
4120
4121 // If there are functions bound, to execute
4122 readyList.resolveWith( document, [ jQuery ] );
4123 }
4124} );
4125
4126jQuery.ready.then = readyList.then;
4127
4128// The ready event handler and self cleanup method
4129function completed() {
4130 document.removeEventListener( "DOMContentLoaded", completed );
4131 window.removeEventListener( "load", completed );
4132 jQuery.ready();
4133}
4134
4135// Catch cases where $(document).ready() is called
4136// after the browser event has already occurred.
4137// Support: IE <=9 - 10 only
4138// Older IE sometimes signals "interactive" too soon
4139if ( document.readyState === "complete" ||
4140 ( document.readyState !== "loading" && !document.documentElement.doScroll ) ) {
4141
4142 // Handle it asynchronously to allow scripts the opportunity to delay ready
4143 window.setTimeout( jQuery.ready );
4144
4145} else {
4146
4147 // Use the handy event callback
4148 document.addEventListener( "DOMContentLoaded", completed );
4149
4150 // A fallback to window.onload, that will always work
4151 window.addEventListener( "load", completed );
4152}
4153
4154
4155
4156
4157// Multifunctional method to get and set values of a collection
4158// The value/s can optionally be executed if it's a function
4159var access = function( elems, fn, key, value, chainable, emptyGet, raw ) {
4160 var i = 0,
4161 len = elems.length,
4162 bulk = key == null;
4163
4164 // Sets many values
4165 if ( toType( key ) === "object" ) {
4166 chainable = true;
4167 for ( i in key ) {
4168 access( elems, fn, i, key[ i ], true, emptyGet, raw );
4169 }
4170
4171 // Sets one value
4172 } else if ( value !== undefined ) {
4173 chainable = true;
4174
4175 if ( !isFunction( value ) ) {
4176 raw = true;
4177 }
4178
4179 if ( bulk ) {
4180
4181 // Bulk operations run against the entire set
4182 if ( raw ) {
4183 fn.call( elems, value );
4184 fn = null;
4185
4186 // ...except when executing function values
4187 } else {
4188 bulk = fn;
4189 fn = function( elem, key, value ) {
4190 return bulk.call( jQuery( elem ), value );
4191 };
4192 }
4193 }
4194
4195 if ( fn ) {
4196 for ( ; i < len; i++ ) {
4197 fn(
4198 elems[ i ], key, raw ?
4199 value :
4200 value.call( elems[ i ], i, fn( elems[ i ], key ) )
4201 );
4202 }
4203 }
4204 }
4205
4206 if ( chainable ) {
4207 return elems;
4208 }
4209
4210 // Gets
4211 if ( bulk ) {
4212 return fn.call( elems );
4213 }
4214
4215 return len ? fn( elems[ 0 ], key ) : emptyGet;
4216};
4217
4218
4219// Matches dashed string for camelizing
4220var rmsPrefix = /^-ms-/,
4221 rdashAlpha = /-([a-z])/g;
4222
4223// Used by camelCase as callback to replace()
4224function fcamelCase( all, letter ) {
4225 return letter.toUpperCase();
4226}
4227
4228// Convert dashed to camelCase; used by the css and data modules
4229// Support: IE <=9 - 11, Edge 12 - 15
4230// Microsoft forgot to hump their vendor prefix (#9572)
4231function camelCase( string ) {
4232 return string.replace( rmsPrefix, "ms-" ).replace( rdashAlpha, fcamelCase );
4233}
4234var acceptData = function( owner ) {
4235
4236 // Accepts only:
4237 // - Node
4238 // - Node.ELEMENT_NODE
4239 // - Node.DOCUMENT_NODE
4240 // - Object
4241 // - Any
4242 return owner.nodeType === 1 || owner.nodeType === 9 || !( +owner.nodeType );
4243};
4244
4245
4246
4247
4248function Data() {
4249 this.expando = jQuery.expando + Data.uid++;
4250}
4251
4252Data.uid = 1;
4253
4254Data.prototype = {
4255
4256 cache: function( owner ) {
4257
4258 // Check if the owner object already has a cache
4259 var value = owner[ this.expando ];
4260
4261 // If not, create one
4262 if ( !value ) {
4263 value = {};
4264
4265 // We can accept data for non-element nodes in modern browsers,
4266 // but we should not, see #8335.
4267 // Always return an empty object.
4268 if ( acceptData( owner ) ) {
4269
4270 // If it is a node unlikely to be stringify-ed or looped over
4271 // use plain assignment
4272 if ( owner.nodeType ) {
4273 owner[ this.expando ] = value;
4274
4275 // Otherwise secure it in a non-enumerable property
4276 // configurable must be true to allow the property to be
4277 // deleted when data is removed
4278 } else {
4279 Object.defineProperty( owner, this.expando, {
4280 value: value,
4281 configurable: true
4282 } );
4283 }
4284 }
4285 }
4286
4287 return value;
4288 },
4289 set: function( owner, data, value ) {
4290 var prop,
4291 cache = this.cache( owner );
4292
4293 // Handle: [ owner, key, value ] args
4294 // Always use camelCase key (gh-2257)
4295 if ( typeof data === "string" ) {
4296 cache[ camelCase( data ) ] = value;
4297
4298 // Handle: [ owner, { properties } ] args
4299 } else {
4300
4301 // Copy the properties one-by-one to the cache object
4302 for ( prop in data ) {
4303 cache[ camelCase( prop ) ] = data[ prop ];
4304 }
4305 }
4306 return cache;
4307 },
4308 get: function( owner, key ) {
4309 return key === undefined ?
4310 this.cache( owner ) :
4311
4312 // Always use camelCase key (gh-2257)
4313 owner[ this.expando ] && owner[ this.expando ][ camelCase( key ) ];
4314 },
4315 access: function( owner, key, value ) {
4316
4317 // In cases where either:
4318 //
4319 // 1. No key was specified
4320 // 2. A string key was specified, but no value provided
4321 //
4322 // Take the "read" path and allow the get method to determine
4323 // which value to return, respectively either:
4324 //
4325 // 1. The entire cache object
4326 // 2. The data stored at the key
4327 //
4328 if ( key === undefined ||
4329 ( ( key && typeof key === "string" ) && value === undefined ) ) {
4330
4331 return this.get( owner, key );
4332 }
4333
4334 // When the key is not a string, or both a key and value
4335 // are specified, set or extend (existing objects) with either:
4336 //
4337 // 1. An object of properties
4338 // 2. A key and value
4339 //
4340 this.set( owner, key, value );
4341
4342 // Since the "set" path can have two possible entry points
4343 // return the expected data based on which path was taken[*]
4344 return value !== undefined ? value : key;
4345 },
4346 remove: function( owner, key ) {
4347 var i,
4348 cache = owner[ this.expando ];
4349
4350 if ( cache === undefined ) {
4351 return;
4352 }
4353
4354 if ( key !== undefined ) {
4355
4356 // Support array or space separated string of keys
4357 if ( Array.isArray( key ) ) {
4358
4359 // If key is an array of keys...
4360 // We always set camelCase keys, so remove that.
4361 key = key.map( camelCase );
4362 } else {
4363 key = camelCase( key );
4364
4365 // If a key with the spaces exists, use it.
4366 // Otherwise, create an array by matching non-whitespace
4367 key = key in cache ?
4368 [ key ] :
4369 ( key.match( rnothtmlwhite ) || [] );
4370 }
4371
4372 i = key.length;
4373
4374 while ( i-- ) {
4375 delete cache[ key[ i ] ];
4376 }
4377 }
4378
4379 // Remove the expando if there's no more data
4380 if ( key === undefined || jQuery.isEmptyObject( cache ) ) {
4381
4382 // Support: Chrome <=35 - 45
4383 // Webkit & Blink performance suffers when deleting properties
4384 // from DOM nodes, so set to undefined instead
4385 // https://bugs.chromium.org/p/chromium/issues/detail?id=378607 (bug restricted)
4386 if ( owner.nodeType ) {
4387 owner[ this.expando ] = undefined;
4388 } else {
4389 delete owner[ this.expando ];
4390 }
4391 }
4392 },
4393 hasData: function( owner ) {
4394 var cache = owner[ this.expando ];
4395 return cache !== undefined && !jQuery.isEmptyObject( cache );
4396 }
4397};
4398var dataPriv = new Data();
4399
4400var dataUser = new Data();
4401
4402
4403
4404// Implementation Summary
4405//
4406// 1. Enforce API surface and semantic compatibility with 1.9.x branch
4407// 2. Improve the module's maintainability by reducing the storage
4408// paths to a single mechanism.
4409// 3. Use the same single mechanism to support "private" and "user" data.
4410// 4. _Never_ expose "private" data to user code (TODO: Drop _data, _removeData)
4411// 5. Avoid exposing implementation details on user objects (eg. expando properties)
4412// 6. Provide a clear path for implementation upgrade to WeakMap in 2014
4413
4414var rbrace = /^(?:\{[\w\W]*\}|\[[\w\W]*\])$/,
4415 rmultiDash = /[A-Z]/g;
4416
4417function getData( data ) {
4418 if ( data === "true" ) {
4419 return true;
4420 }
4421
4422 if ( data === "false" ) {
4423 return false;
4424 }
4425
4426 if ( data === "null" ) {
4427 return null;
4428 }
4429
4430 // Only convert to a number if it doesn't change the string
4431 if ( data === +data + "" ) {
4432 return +data;
4433 }
4434
4435 if ( rbrace.test( data ) ) {
4436 return JSON.parse( data );
4437 }
4438
4439 return data;
4440}
4441
4442function dataAttr( elem, key, data ) {
4443 var name;
4444
4445 // If nothing was found internally, try to fetch any
4446 // data from the HTML5 data-* attribute
4447 if ( data === undefined && elem.nodeType === 1 ) {
4448 name = "data-" + key.replace( rmultiDash, "-$&" ).toLowerCase();
4449 data = elem.getAttribute( name );
4450
4451 if ( typeof data === "string" ) {
4452 try {
4453 data = getData( data );
4454 } catch ( e ) {}
4455
4456 // Make sure we set the data so it isn't changed later
4457 dataUser.set( elem, key, data );
4458 } else {
4459 data = undefined;
4460 }
4461 }
4462 return data;
4463}
4464
4465jQuery.extend( {
4466 hasData: function( elem ) {
4467 return dataUser.hasData( elem ) || dataPriv.hasData( elem );
4468 },
4469
4470 data: function( elem, name, data ) {
4471 return dataUser.access( elem, name, data );
4472 },
4473
4474 removeData: function( elem, name ) {
4475 dataUser.remove( elem, name );
4476 },
4477
4478 // TODO: Now that all calls to _data and _removeData have been replaced
4479 // with direct calls to dataPriv methods, these can be deprecated.
4480 _data: function( elem, name, data ) {
4481 return dataPriv.access( elem, name, data );
4482 },
4483
4484 _removeData: function( elem, name ) {
4485 dataPriv.remove( elem, name );
4486 }
4487} );
4488
4489jQuery.fn.extend( {
4490 data: function( key, value ) {
4491 var i, name, data,
4492 elem = this[ 0 ],
4493 attrs = elem && elem.attributes;
4494
4495 // Gets all values
4496 if ( key === undefined ) {
4497 if ( this.length ) {
4498 data = dataUser.get( elem );
4499
4500 if ( elem.nodeType === 1 && !dataPriv.get( elem, "hasDataAttrs" ) ) {
4501 i = attrs.length;
4502 while ( i-- ) {
4503
4504 // Support: IE 11 only
4505 // The attrs elements can be null (#14894)
4506 if ( attrs[ i ] ) {
4507 name = attrs[ i ].name;
4508 if ( name.indexOf( "data-" ) === 0 ) {
4509 name = camelCase( name.slice( 5 ) );
4510 dataAttr( elem, name, data[ name ] );
4511 }
4512 }
4513 }
4514 dataPriv.set( elem, "hasDataAttrs", true );
4515 }
4516 }
4517
4518 return data;
4519 }
4520
4521 // Sets multiple values
4522 if ( typeof key === "object" ) {
4523 return this.each( function() {
4524 dataUser.set( this, key );
4525 } );
4526 }
4527
4528 return access( this, function( value ) {
4529 var data;
4530
4531 // The calling jQuery object (element matches) is not empty
4532 // (and therefore has an element appears at this[ 0 ]) and the
4533 // `value` parameter was not undefined. An empty jQuery object
4534 // will result in `undefined` for elem = this[ 0 ] which will
4535 // throw an exception if an attempt to read a data cache is made.
4536 if ( elem && value === undefined ) {
4537
4538 // Attempt to get data from the cache
4539 // The key will always be camelCased in Data
4540 data = dataUser.get( elem, key );
4541 if ( data !== undefined ) {
4542 return data;
4543 }
4544
4545 // Attempt to "discover" the data in
4546 // HTML5 custom data-* attrs
4547 data = dataAttr( elem, key );
4548 if ( data !== undefined ) {
4549 return data;
4550 }
4551
4552 // We tried really hard, but the data doesn't exist.
4553 return;
4554 }
4555
4556 // Set the data...
4557 this.each( function() {
4558
4559 // We always store the camelCased key
4560 dataUser.set( this, key, value );
4561 } );
4562 }, null, value, arguments.length > 1, null, true );
4563 },
4564
4565 removeData: function( key ) {
4566 return this.each( function() {
4567 dataUser.remove( this, key );
4568 } );
4569 }
4570} );
4571
4572
4573jQuery.extend( {
4574 queue: function( elem, type, data ) {
4575 var queue;
4576
4577 if ( elem ) {
4578 type = ( type || "fx" ) + "queue";
4579 queue = dataPriv.get( elem, type );
4580
4581 // Speed up dequeue by getting out quickly if this is just a lookup
4582 if ( data ) {
4583 if ( !queue || Array.isArray( data ) ) {
4584 queue = dataPriv.access( elem, type, jQuery.makeArray( data ) );
4585 } else {
4586 queue.push( data );
4587 }
4588 }
4589 return queue || [];
4590 }
4591 },
4592
4593 dequeue: function( elem, type ) {
4594 type = type || "fx";
4595
4596 var queue = jQuery.queue( elem, type ),
4597 startLength = queue.length,
4598 fn = queue.shift(),
4599 hooks = jQuery._queueHooks( elem, type ),
4600 next = function() {
4601 jQuery.dequeue( elem, type );
4602 };
4603
4604 // If the fx queue is dequeued, always remove the progress sentinel
4605 if ( fn === "inprogress" ) {
4606 fn = queue.shift();
4607 startLength--;
4608 }
4609
4610 if ( fn ) {
4611
4612 // Add a progress sentinel to prevent the fx queue from being
4613 // automatically dequeued
4614 if ( type === "fx" ) {
4615 queue.unshift( "inprogress" );
4616 }
4617
4618 // Clear up the last queue stop function
4619 delete hooks.stop;
4620 fn.call( elem, next, hooks );
4621 }
4622
4623 if ( !startLength && hooks ) {
4624 hooks.empty.fire();
4625 }
4626 },
4627
4628 // Not public - generate a queueHooks object, or return the current one
4629 _queueHooks: function( elem, type ) {
4630 var key = type + "queueHooks";
4631 return dataPriv.get( elem, key ) || dataPriv.access( elem, key, {
4632 empty: jQuery.Callbacks( "once memory" ).add( function() {
4633 dataPriv.remove( elem, [ type + "queue", key ] );
4634 } )
4635 } );
4636 }
4637} );
4638
4639jQuery.fn.extend( {
4640 queue: function( type, data ) {
4641 var setter = 2;
4642
4643 if ( typeof type !== "string" ) {
4644 data = type;
4645 type = "fx";
4646 setter--;
4647 }
4648
4649 if ( arguments.length < setter ) {
4650 return jQuery.queue( this[ 0 ], type );
4651 }
4652
4653 return data === undefined ?
4654 this :
4655 this.each( function() {
4656 var queue = jQuery.queue( this, type, data );
4657
4658 // Ensure a hooks for this queue
4659 jQuery._queueHooks( this, type );
4660
4661 if ( type === "fx" && queue[ 0 ] !== "inprogress" ) {
4662 jQuery.dequeue( this, type );
4663 }
4664 } );
4665 },
4666 dequeue: function( type ) {
4667 return this.each( function() {
4668 jQuery.dequeue( this, type );
4669 } );
4670 },
4671 clearQueue: function( type ) {
4672 return this.queue( type || "fx", [] );
4673 },
4674
4675 // Get a promise resolved when queues of a certain type
4676 // are emptied (fx is the type by default)
4677 promise: function( type, obj ) {
4678 var tmp,
4679 count = 1,
4680 defer = jQuery.Deferred(),
4681 elements = this,
4682 i = this.length,
4683 resolve = function() {
4684 if ( !( --count ) ) {
4685 defer.resolveWith( elements, [ elements ] );
4686 }
4687 };
4688
4689 if ( typeof type !== "string" ) {
4690 obj = type;
4691 type = undefined;
4692 }
4693 type = type || "fx";
4694
4695 while ( i-- ) {
4696 tmp = dataPriv.get( elements[ i ], type + "queueHooks" );
4697 if ( tmp && tmp.empty ) {
4698 count++;
4699 tmp.empty.add( resolve );
4700 }
4701 }
4702 resolve();
4703 return defer.promise( obj );
4704 }
4705} );
4706var pnum = ( /[+-]?(?:\d*\.|)\d+(?:[eE][+-]?\d+|)/ ).source;
4707
4708var rcssNum = new RegExp( "^(?:([+-])=|)(" + pnum + ")([a-z%]*)$", "i" );
4709
4710
4711var cssExpand = [ "Top", "Right", "Bottom", "Left" ];
4712
4713var isHiddenWithinTree = function( elem, el ) {
4714
4715 // isHiddenWithinTree might be called from jQuery#filter function;
4716 // in that case, element will be second argument
4717 elem = el || elem;
4718
4719 // Inline style trumps all
4720 return elem.style.display === "none" ||
4721 elem.style.display === "" &&
4722
4723 // Otherwise, check computed style
4724 // Support: Firefox <=43 - 45
4725 // Disconnected elements can have computed display: none, so first confirm that elem is
4726 // in the document.
4727 jQuery.contains( elem.ownerDocument, elem ) &&
4728
4729 jQuery.css( elem, "display" ) === "none";
4730 };
4731
4732var swap = function( elem, options, callback, args ) {
4733 var ret, name,
4734 old = {};
4735
4736 // Remember the old values, and insert the new ones
4737 for ( name in options ) {
4738 old[ name ] = elem.style[ name ];
4739 elem.style[ name ] = options[ name ];
4740 }
4741
4742 ret = callback.apply( elem, args || [] );
4743
4744 // Revert the old values
4745 for ( name in options ) {
4746 elem.style[ name ] = old[ name ];
4747 }
4748
4749 return ret;
4750};
4751
4752
4753
4754
4755function adjustCSS( elem, prop, valueParts, tween ) {
4756 var adjusted, scale,
4757 maxIterations = 20,
4758 currentValue = tween ?
4759 function() {
4760 return tween.cur();
4761 } :
4762 function() {
4763 return jQuery.css( elem, prop, "" );
4764 },
4765 initial = currentValue(),
4766 unit = valueParts && valueParts[ 3 ] || ( jQuery.cssNumber[ prop ] ? "" : "px" ),
4767
4768 // Starting value computation is required for potential unit mismatches
4769 initialInUnit = ( jQuery.cssNumber[ prop ] || unit !== "px" && +initial ) &&
4770 rcssNum.exec( jQuery.css( elem, prop ) );
4771
4772 if ( initialInUnit && initialInUnit[ 3 ] !== unit ) {
4773
4774 // Support: Firefox <=54
4775 // Halve the iteration target value to prevent interference from CSS upper bounds (gh-2144)
4776 initial = initial / 2;
4777
4778 // Trust units reported by jQuery.css
4779 unit = unit || initialInUnit[ 3 ];
4780
4781 // Iteratively approximate from a nonzero starting point
4782 initialInUnit = +initial || 1;
4783
4784 while ( maxIterations-- ) {
4785
4786 // Evaluate and update our best guess (doubling guesses that zero out).
4787 // Finish if the scale equals or crosses 1 (making the old*new product non-positive).
4788 jQuery.style( elem, prop, initialInUnit + unit );
4789 if ( ( 1 - scale ) * ( 1 - ( scale = currentValue() / initial || 0.5 ) ) <= 0 ) {
4790 maxIterations = 0;
4791 }
4792 initialInUnit = initialInUnit / scale;
4793
4794 }
4795
4796 initialInUnit = initialInUnit * 2;
4797 jQuery.style( elem, prop, initialInUnit + unit );
4798
4799 // Make sure we update the tween properties later on
4800 valueParts = valueParts || [];
4801 }
4802
4803 if ( valueParts ) {
4804 initialInUnit = +initialInUnit || +initial || 0;
4805
4806 // Apply relative offset (+=/-=) if specified
4807 adjusted = valueParts[ 1 ] ?
4808 initialInUnit + ( valueParts[ 1 ] + 1 ) * valueParts[ 2 ] :
4809 +valueParts[ 2 ];
4810 if ( tween ) {
4811 tween.unit = unit;
4812 tween.start = initialInUnit;
4813 tween.end = adjusted;
4814 }
4815 }
4816 return adjusted;
4817}
4818
4819
4820var defaultDisplayMap = {};
4821
4822function getDefaultDisplay( elem ) {
4823 var temp,
4824 doc = elem.ownerDocument,
4825 nodeName = elem.nodeName,
4826 display = defaultDisplayMap[ nodeName ];
4827
4828 if ( display ) {
4829 return display;
4830 }
4831
4832 temp = doc.body.appendChild( doc.createElement( nodeName ) );
4833 display = jQuery.css( temp, "display" );
4834
4835 temp.parentNode.removeChild( temp );
4836
4837 if ( display === "none" ) {
4838 display = "block";
4839 }
4840 defaultDisplayMap[ nodeName ] = display;
4841
4842 return display;
4843}
4844
4845function showHide( elements, show ) {
4846 var display, elem,
4847 values = [],
4848 index = 0,
4849 length = elements.length;
4850
4851 // Determine new display value for elements that need to change
4852 for ( ; index < length; index++ ) {
4853 elem = elements[ index ];
4854 if ( !elem.style ) {
4855 continue;
4856 }
4857
4858 display = elem.style.display;
4859 if ( show ) {
4860
4861 // Since we force visibility upon cascade-hidden elements, an immediate (and slow)
4862 // check is required in this first loop unless we have a nonempty display value (either
4863 // inline or about-to-be-restored)
4864 if ( display === "none" ) {
4865 values[ index ] = dataPriv.get( elem, "display" ) || null;
4866 if ( !values[ index ] ) {
4867 elem.style.display = "";
4868 }
4869 }
4870 if ( elem.style.display === "" && isHiddenWithinTree( elem ) ) {
4871 values[ index ] = getDefaultDisplay( elem );
4872 }
4873 } else {
4874 if ( display !== "none" ) {
4875 values[ index ] = "none";
4876
4877 // Remember what we're overwriting
4878 dataPriv.set( elem, "display", display );
4879 }
4880 }
4881 }
4882
4883 // Set the display of the elements in a second loop to avoid constant reflow
4884 for ( index = 0; index < length; index++ ) {
4885 if ( values[ index ] != null ) {
4886 elements[ index ].style.display = values[ index ];
4887 }
4888 }
4889
4890 return elements;
4891}
4892
4893jQuery.fn.extend( {
4894 show: function() {
4895 return showHide( this, true );
4896 },
4897 hide: function() {
4898 return showHide( this );
4899 },
4900 toggle: function( state ) {
4901 if ( typeof state === "boolean" ) {
4902 return state ? this.show() : this.hide();
4903 }
4904
4905 return this.each( function() {
4906 if ( isHiddenWithinTree( this ) ) {
4907 jQuery( this ).show();
4908 } else {
4909 jQuery( this ).hide();
4910 }
4911 } );
4912 }
4913} );
4914var rcheckableType = ( /^(?:checkbox|radio)$/i );
4915
4916var rtagName = ( /<([a-z][^\/\0>\x20\t\r\n\f]+)/i );
4917
4918var rscriptType = ( /^$|^module$|\/(?:java|ecma)script/i );
4919
4920
4921
4922// We have to close these tags to support XHTML (#13200)
4923var wrapMap = {
4924
4925 // Support: IE <=9 only
4926 option: [ 1, "<select multiple='multiple'>", "</select>" ],
4927
4928 // XHTML parsers do not magically insert elements in the
4929 // same way that tag soup parsers do. So we cannot shorten
4930 // this by omitting <tbody> or other required elements.
4931 thead: [ 1, "<table>", "</table>" ],
4932 col: [ 2, "<table><colgroup>", "</colgroup></table>" ],
4933 tr: [ 2, "<table><tbody>", "</tbody></table>" ],
4934 td: [ 3, "<table><tbody><tr>", "</tr></tbody></table>" ],
4935
4936 _default: [ 0, "", "" ]
4937};
4938
4939// Support: IE <=9 only
4940wrapMap.optgroup = wrapMap.option;
4941
4942wrapMap.tbody = wrapMap.tfoot = wrapMap.colgroup = wrapMap.caption = wrapMap.thead;
4943wrapMap.th = wrapMap.td;
4944
4945
4946function getAll( context, tag ) {
4947
4948 // Support: IE <=9 - 11 only
4949 // Use typeof to avoid zero-argument method invocation on host objects (#15151)
4950 var ret;
4951
4952 if ( typeof context.getElementsByTagName !== "undefined" ) {
4953 ret = context.getElementsByTagName( tag || "*" );
4954
4955 } else if ( typeof context.querySelectorAll !== "undefined" ) {
4956 ret = context.querySelectorAll( tag || "*" );
4957
4958 } else {
4959 ret = [];
4960 }
4961
4962 if ( tag === undefined || tag && nodeName( context, tag ) ) {
4963 return jQuery.merge( [ context ], ret );
4964 }
4965
4966 return ret;
4967}
4968
4969
4970// Mark scripts as having already been evaluated
4971function setGlobalEval( elems, refElements ) {
4972 var i = 0,
4973 l = elems.length;
4974
4975 for ( ; i < l; i++ ) {
4976 dataPriv.set(
4977 elems[ i ],
4978 "globalEval",
4979 !refElements || dataPriv.get( refElements[ i ], "globalEval" )
4980 );
4981 }
4982}
4983
4984
4985var rhtml = /<|&#?\w+;/;
4986
4987function buildFragment( elems, context, scripts, selection, ignored ) {
4988 var elem, tmp, tag, wrap, contains, j,
4989 fragment = context.createDocumentFragment(),
4990 nodes = [],
4991 i = 0,
4992 l = elems.length;
4993
4994 for ( ; i < l; i++ ) {
4995 elem = elems[ i ];
4996
4997 if ( elem || elem === 0 ) {
4998
4999 // Add nodes directly
5000 if ( toType( elem ) === "object" ) {
5001
5002 // Support: Android <=4.0 only, PhantomJS 1 only
5003 // push.apply(_, arraylike) throws on ancient WebKit
5004 jQuery.merge( nodes, elem.nodeType ? [ elem ] : elem );
5005
5006 // Convert non-html into a text node
5007 } else if ( !rhtml.test( elem ) ) {
5008 nodes.push( context.createTextNode( elem ) );
5009
5010 // Convert html into DOM nodes
5011 } else {
5012 tmp = tmp || fragment.appendChild( context.createElement( "div" ) );
5013
5014 // Deserialize a standard representation
5015 tag = ( rtagName.exec( elem ) || [ "", "" ] )[ 1 ].toLowerCase();
5016 wrap = wrapMap[ tag ] || wrapMap._default;
5017 tmp.innerHTML = wrap[ 1 ] + jQuery.htmlPrefilter( elem ) + wrap[ 2 ];
5018
5019 // Descend through wrappers to the right content
5020 j = wrap[ 0 ];
5021 while ( j-- ) {
5022 tmp = tmp.lastChild;
5023 }
5024
5025 // Support: Android <=4.0 only, PhantomJS 1 only
5026 // push.apply(_, arraylike) throws on ancient WebKit
5027 jQuery.merge( nodes, tmp.childNodes );
5028
5029 // Remember the top-level container
5030 tmp = fragment.firstChild;
5031
5032 // Ensure the created nodes are orphaned (#12392)
5033 tmp.textContent = "";
5034 }
5035 }
5036 }
5037
5038 // Remove wrapper from fragment
5039 fragment.textContent = "";
5040
5041 i = 0;
5042 while ( ( elem = nodes[ i++ ] ) ) {
5043
5044 // Skip elements already in the context collection (trac-4087)
5045 if ( selection && jQuery.inArray( elem, selection ) > -1 ) {
5046 if ( ignored ) {
5047 ignored.push( elem );
5048 }
5049 continue;
5050 }
5051
5052 contains = jQuery.contains( elem.ownerDocument, elem );
5053
5054 // Append to fragment
5055 tmp = getAll( fragment.appendChild( elem ), "script" );
5056
5057 // Preserve script evaluation history
5058 if ( contains ) {
5059 setGlobalEval( tmp );
5060 }
5061
5062 // Capture executables
5063 if ( scripts ) {
5064 j = 0;
5065 while ( ( elem = tmp[ j++ ] ) ) {
5066 if ( rscriptType.test( elem.type || "" ) ) {
5067 scripts.push( elem );
5068 }
5069 }
5070 }
5071 }
5072
5073 return fragment;
5074}
5075
5076
5077( function() {
5078 var fragment = document.createDocumentFragment(),
5079 div = fragment.appendChild( document.createElement( "div" ) ),
5080 input = document.createElement( "input" );
5081
5082 // Support: Android 4.0 - 4.3 only
5083 // Check state lost if the name is set (#11217)
5084 // Support: Windows Web Apps (WWA)
5085 // `name` and `type` must use .setAttribute for WWA (#14901)
5086 input.setAttribute( "type", "radio" );
5087 input.setAttribute( "checked", "checked" );
5088 input.setAttribute( "name", "t" );
5089
5090 div.appendChild( input );
5091
5092 // Support: Android <=4.1 only
5093 // Older WebKit doesn't clone checked state correctly in fragments
5094 support.checkClone = div.cloneNode( true ).cloneNode( true ).lastChild.checked;
5095
5096 // Support: IE <=11 only
5097 // Make sure textarea (and checkbox) defaultValue is properly cloned
5098 div.innerHTML = "<textarea>x</textarea>";
5099 support.noCloneChecked = !!div.cloneNode( true ).lastChild.defaultValue;
5100} )();
5101var documentElement = document.documentElement;
5102
5103
5104
5105var
5106 rkeyEvent = /^key/,
5107 rmouseEvent = /^(?:mouse|pointer|contextmenu|drag|drop)|click/,
5108 rtypenamespace = /^([^.]*)(?:\.(.+)|)/;
5109
5110function returnTrue() {
5111 return true;
5112}
5113
5114function returnFalse() {
5115 return false;
5116}
5117
5118// Support: IE <=9 only
5119// See #13393 for more info
5120function safeActiveElement() {
5121 try {
5122 return document.activeElement;
5123 } catch ( err ) { }
5124}
5125
5126function on( elem, types, selector, data, fn, one ) {
5127 var origFn, type;
5128
5129 // Types can be a map of types/handlers
5130 if ( typeof types === "object" ) {
5131
5132 // ( types-Object, selector, data )
5133 if ( typeof selector !== "string" ) {
5134
5135 // ( types-Object, data )
5136 data = data || selector;
5137 selector = undefined;
5138 }
5139 for ( type in types ) {
5140 on( elem, type, selector, data, types[ type ], one );
5141 }
5142 return elem;
5143 }
5144
5145 if ( data == null && fn == null ) {
5146
5147 // ( types, fn )
5148 fn = selector;
5149 data = selector = undefined;
5150 } else if ( fn == null ) {
5151 if ( typeof selector === "string" ) {
5152
5153 // ( types, selector, fn )
5154 fn = data;
5155 data = undefined;
5156 } else {
5157
5158 // ( types, data, fn )
5159 fn = data;
5160 data = selector;
5161 selector = undefined;
5162 }
5163 }
5164 if ( fn === false ) {
5165 fn = returnFalse;
5166 } else if ( !fn ) {
5167 return elem;
5168 }
5169
5170 if ( one === 1 ) {
5171 origFn = fn;
5172 fn = function( event ) {
5173
5174 // Can use an empty set, since event contains the info
5175 jQuery().off( event );
5176 return origFn.apply( this, arguments );
5177 };
5178
5179 // Use same guid so caller can remove using origFn
5180 fn.guid = origFn.guid || ( origFn.guid = jQuery.guid++ );
5181 }
5182 return elem.each( function() {
5183 jQuery.event.add( this, types, fn, data, selector );
5184 } );
5185}
5186
5187/*
5188 * Helper functions for managing events -- not part of the public interface.
5189 * Props to Dean Edwards' addEvent library for many of the ideas.
5190 */
5191jQuery.event = {
5192
5193 global: {},
5194
5195 add: function( elem, types, handler, data, selector ) {
5196
5197 var handleObjIn, eventHandle, tmp,
5198 events, t, handleObj,
5199 special, handlers, type, namespaces, origType,
5200 elemData = dataPriv.get( elem );
5201
5202 // Don't attach events to noData or text/comment nodes (but allow plain objects)
5203 if ( !elemData ) {
5204 return;
5205 }
5206
5207 // Caller can pass in an object of custom data in lieu of the handler
5208 if ( handler.handler ) {
5209 handleObjIn = handler;
5210 handler = handleObjIn.handler;
5211 selector = handleObjIn.selector;
5212 }
5213
5214 // Ensure that invalid selectors throw exceptions at attach time
5215 // Evaluate against documentElement in case elem is a non-element node (e.g., document)
5216 if ( selector ) {
5217 jQuery.find.matchesSelector( documentElement, selector );
5218 }
5219
5220 // Make sure that the handler has a unique ID, used to find/remove it later
5221 if ( !handler.guid ) {
5222 handler.guid = jQuery.guid++;
5223 }
5224
5225 // Init the element's event structure and main handler, if this is the first
5226 if ( !( events = elemData.events ) ) {
5227 events = elemData.events = {};
5228 }
5229 if ( !( eventHandle = elemData.handle ) ) {
5230 eventHandle = elemData.handle = function( e ) {
5231
5232 // Discard the second event of a jQuery.event.trigger() and
5233 // when an event is called after a page has unloaded
5234 return typeof jQuery !== "undefined" && jQuery.event.triggered !== e.type ?
5235 jQuery.event.dispatch.apply( elem, arguments ) : undefined;
5236 };
5237 }
5238
5239 // Handle multiple events separated by a space
5240 types = ( types || "" ).match( rnothtmlwhite ) || [ "" ];
5241 t = types.length;
5242 while ( t-- ) {
5243 tmp = rtypenamespace.exec( types[ t ] ) || [];
5244 type = origType = tmp[ 1 ];
5245 namespaces = ( tmp[ 2 ] || "" ).split( "." ).sort();
5246
5247 // There *must* be a type, no attaching namespace-only handlers
5248 if ( !type ) {
5249 continue;
5250 }
5251
5252 // If event changes its type, use the special event handlers for the changed type
5253 special = jQuery.event.special[ type ] || {};
5254
5255 // If selector defined, determine special event api type, otherwise given type
5256 type = ( selector ? special.delegateType : special.bindType ) || type;
5257
5258 // Update special based on newly reset type
5259 special = jQuery.event.special[ type ] || {};
5260
5261 // handleObj is passed to all event handlers
5262 handleObj = jQuery.extend( {
5263 type: type,
5264 origType: origType,
5265 data: data,
5266 handler: handler,
5267 guid: handler.guid,
5268 selector: selector,
5269 needsContext: selector && jQuery.expr.match.needsContext.test( selector ),
5270 namespace: namespaces.join( "." )
5271 }, handleObjIn );
5272
5273 // Init the event handler queue if we're the first
5274 if ( !( handlers = events[ type ] ) ) {
5275 handlers = events[ type ] = [];
5276 handlers.delegateCount = 0;
5277
5278 // Only use addEventListener if the special events handler returns false
5279 if ( !special.setup ||
5280 special.setup.call( elem, data, namespaces, eventHandle ) === false ) {
5281
5282 if ( elem.addEventListener ) {
5283 elem.addEventListener( type, eventHandle );
5284 }
5285 }
5286 }
5287
5288 if ( special.add ) {
5289 special.add.call( elem, handleObj );
5290
5291 if ( !handleObj.handler.guid ) {
5292 handleObj.handler.guid = handler.guid;
5293 }
5294 }
5295
5296 // Add to the element's handler list, delegates in front
5297 if ( selector ) {
5298 handlers.splice( handlers.delegateCount++, 0, handleObj );
5299 } else {
5300 handlers.push( handleObj );
5301 }
5302
5303 // Keep track of which events have ever been used, for event optimization
5304 jQuery.event.global[ type ] = true;
5305 }
5306
5307 },
5308
5309 // Detach an event or set of events from an element
5310 remove: function( elem, types, handler, selector, mappedTypes ) {
5311
5312 var j, origCount, tmp,
5313 events, t, handleObj,
5314 special, handlers, type, namespaces, origType,
5315 elemData = dataPriv.hasData( elem ) && dataPriv.get( elem );
5316
5317 if ( !elemData || !( events = elemData.events ) ) {
5318 return;
5319 }
5320
5321 // Once for each type.namespace in types; type may be omitted
5322 types = ( types || "" ).match( rnothtmlwhite ) || [ "" ];
5323 t = types.length;
5324 while ( t-- ) {
5325 tmp = rtypenamespace.exec( types[ t ] ) || [];
5326 type = origType = tmp[ 1 ];
5327 namespaces = ( tmp[ 2 ] || "" ).split( "." ).sort();
5328
5329 // Unbind all events (on this namespace, if provided) for the element
5330 if ( !type ) {
5331 for ( type in events ) {
5332 jQuery.event.remove( elem, type + types[ t ], handler, selector, true );
5333 }
5334 continue;
5335 }
5336
5337 special = jQuery.event.special[ type ] || {};
5338 type = ( selector ? special.delegateType : special.bindType ) || type;
5339 handlers = events[ type ] || [];
5340 tmp = tmp[ 2 ] &&
5341 new RegExp( "(^|\\.)" + namespaces.join( "\\.(?:.*\\.|)" ) + "(\\.|$)" );
5342
5343 // Remove matching events
5344 origCount = j = handlers.length;
5345 while ( j-- ) {
5346 handleObj = handlers[ j ];
5347
5348 if ( ( mappedTypes || origType === handleObj.origType ) &&
5349 ( !handler || handler.guid === handleObj.guid ) &&
5350 ( !tmp || tmp.test( handleObj.namespace ) ) &&
5351 ( !selector || selector === handleObj.selector ||
5352 selector === "**" && handleObj.selector ) ) {
5353 handlers.splice( j, 1 );
5354
5355 if ( handleObj.selector ) {
5356 handlers.delegateCount--;
5357 }
5358 if ( special.remove ) {
5359 special.remove.call( elem, handleObj );
5360 }
5361 }
5362 }
5363
5364 // Remove generic event handler if we removed something and no more handlers exist
5365 // (avoids potential for endless recursion during removal of special event handlers)
5366 if ( origCount && !handlers.length ) {
5367 if ( !special.teardown ||
5368 special.teardown.call( elem, namespaces, elemData.handle ) === false ) {
5369
5370 jQuery.removeEvent( elem, type, elemData.handle );
5371 }
5372
5373 delete events[ type ];
5374 }
5375 }
5376
5377 // Remove data and the expando if it's no longer used
5378 if ( jQuery.isEmptyObject( events ) ) {
5379 dataPriv.remove( elem, "handle events" );
5380 }
5381 },
5382
5383 dispatch: function( nativeEvent ) {
5384
5385 // Make a writable jQuery.Event from the native event object
5386 var event = jQuery.event.fix( nativeEvent );
5387
5388 var i, j, ret, matched, handleObj, handlerQueue,
5389 args = new Array( arguments.length ),
5390 handlers = ( dataPriv.get( this, "events" ) || {} )[ event.type ] || [],
5391 special = jQuery.event.special[ event.type ] || {};
5392
5393 // Use the fix-ed jQuery.Event rather than the (read-only) native event
5394 args[ 0 ] = event;
5395
5396 for ( i = 1; i < arguments.length; i++ ) {
5397 args[ i ] = arguments[ i ];
5398 }
5399
5400 event.delegateTarget = this;
5401
5402 // Call the preDispatch hook for the mapped type, and let it bail if desired
5403 if ( special.preDispatch && special.preDispatch.call( this, event ) === false ) {
5404 return;
5405 }
5406
5407 // Determine handlers
5408 handlerQueue = jQuery.event.handlers.call( this, event, handlers );
5409
5410 // Run delegates first; they may want to stop propagation beneath us
5411 i = 0;
5412 while ( ( matched = handlerQueue[ i++ ] ) && !event.isPropagationStopped() ) {
5413 event.currentTarget = matched.elem;
5414
5415 j = 0;
5416 while ( ( handleObj = matched.handlers[ j++ ] ) &&
5417 !event.isImmediatePropagationStopped() ) {
5418
5419 // Triggered event must either 1) have no namespace, or 2) have namespace(s)
5420 // a subset or equal to those in the bound event (both can have no namespace).
5421 if ( !event.rnamespace || event.rnamespace.test( handleObj.namespace ) ) {
5422
5423 event.handleObj = handleObj;
5424 event.data = handleObj.data;
5425
5426 ret = ( ( jQuery.event.special[ handleObj.origType ] || {} ).handle ||
5427 handleObj.handler ).apply( matched.elem, args );
5428
5429 if ( ret !== undefined ) {
5430 if ( ( event.result = ret ) === false ) {
5431 event.preventDefault();
5432 event.stopPropagation();
5433 }
5434 }
5435 }
5436 }
5437 }
5438
5439 // Call the postDispatch hook for the mapped type
5440 if ( special.postDispatch ) {
5441 special.postDispatch.call( this, event );
5442 }
5443
5444 return event.result;
5445 },
5446
5447 handlers: function( event, handlers ) {
5448 var i, handleObj, sel, matchedHandlers, matchedSelectors,
5449 handlerQueue = [],
5450 delegateCount = handlers.delegateCount,
5451 cur = event.target;
5452
5453 // Find delegate handlers
5454 if ( delegateCount &&
5455
5456 // Support: IE <=9
5457 // Black-hole SVG <use> instance trees (trac-13180)
5458 cur.nodeType &&
5459
5460 // Support: Firefox <=42
5461 // Suppress spec-violating clicks indicating a non-primary pointer button (trac-3861)
5462 // https://www.w3.org/TR/DOM-Level-3-Events/#event-type-click
5463 // Support: IE 11 only
5464 // ...but not arrow key "clicks" of radio inputs, which can have `button` -1 (gh-2343)
5465 !( event.type === "click" && event.button >= 1 ) ) {
5466
5467 for ( ; cur !== this; cur = cur.parentNode || this ) {
5468
5469 // Don't check non-elements (#13208)
5470 // Don't process clicks on disabled elements (#6911, #8165, #11382, #11764)
5471 if ( cur.nodeType === 1 && !( event.type === "click" && cur.disabled === true ) ) {
5472 matchedHandlers = [];
5473 matchedSelectors = {};
5474 for ( i = 0; i < delegateCount; i++ ) {
5475 handleObj = handlers[ i ];
5476
5477 // Don't conflict with Object.prototype properties (#13203)
5478 sel = handleObj.selector + " ";
5479
5480 if ( matchedSelectors[ sel ] === undefined ) {
5481 matchedSelectors[ sel ] = handleObj.needsContext ?
5482 jQuery( sel, this ).index( cur ) > -1 :
5483 jQuery.find( sel, this, null, [ cur ] ).length;
5484 }
5485 if ( matchedSelectors[ sel ] ) {
5486 matchedHandlers.push( handleObj );
5487 }
5488 }
5489 if ( matchedHandlers.length ) {
5490 handlerQueue.push( { elem: cur, handlers: matchedHandlers } );
5491 }
5492 }
5493 }
5494 }
5495
5496 // Add the remaining (directly-bound) handlers
5497 cur = this;
5498 if ( delegateCount < handlers.length ) {
5499 handlerQueue.push( { elem: cur, handlers: handlers.slice( delegateCount ) } );
5500 }
5501
5502 return handlerQueue;
5503 },
5504
5505 addProp: function( name, hook ) {
5506 Object.defineProperty( jQuery.Event.prototype, name, {
5507 enumerable: true,
5508 configurable: true,
5509
5510 get: isFunction( hook ) ?
5511 function() {
5512 if ( this.originalEvent ) {
5513 return hook( this.originalEvent );
5514 }
5515 } :
5516 function() {
5517 if ( this.originalEvent ) {
5518 return this.originalEvent[ name ];
5519 }
5520 },
5521
5522 set: function( value ) {
5523 Object.defineProperty( this, name, {
5524 enumerable: true,
5525 configurable: true,
5526 writable: true,
5527 value: value
5528 } );
5529 }
5530 } );
5531 },
5532
5533 fix: function( originalEvent ) {
5534 return originalEvent[ jQuery.expando ] ?
5535 originalEvent :
5536 new jQuery.Event( originalEvent );
5537 },
5538
5539 special: {
5540 load: {
5541
5542 // Prevent triggered image.load events from bubbling to window.load
5543 noBubble: true
5544 },
5545 focus: {
5546
5547 // Fire native event if possible so blur/focus sequence is correct
5548 trigger: function() {
5549 if ( this !== safeActiveElement() && this.focus ) {
5550 this.focus();
5551 return false;
5552 }
5553 },
5554 delegateType: "focusin"
5555 },
5556 blur: {
5557 trigger: function() {
5558 if ( this === safeActiveElement() && this.blur ) {
5559 this.blur();
5560 return false;
5561 }
5562 },
5563 delegateType: "focusout"
5564 },
5565 click: {
5566
5567 // For checkbox, fire native event so checked state will be right
5568 trigger: function() {
5569 if ( this.type === "checkbox" && this.click && nodeName( this, "input" ) ) {
5570 this.click();
5571 return false;
5572 }
5573 },
5574
5575 // For cross-browser consistency, don't fire native .click() on links
5576 _default: function( event ) {
5577 return nodeName( event.target, "a" );
5578 }
5579 },
5580
5581 beforeunload: {
5582 postDispatch: function( event ) {
5583
5584 // Support: Firefox 20+
5585 // Firefox doesn't alert if the returnValue field is not set.
5586 if ( event.result !== undefined && event.originalEvent ) {
5587 event.originalEvent.returnValue = event.result;
5588 }
5589 }
5590 }
5591 }
5592};
5593
5594jQuery.removeEvent = function( elem, type, handle ) {
5595
5596 // This "if" is needed for plain objects
5597 if ( elem.removeEventListener ) {
5598 elem.removeEventListener( type, handle );
5599 }
5600};
5601
5602jQuery.Event = function( src, props ) {
5603
5604 // Allow instantiation without the 'new' keyword
5605 if ( !( this instanceof jQuery.Event ) ) {
5606 return new jQuery.Event( src, props );
5607 }
5608
5609 // Event object
5610 if ( src && src.type ) {
5611 this.originalEvent = src;
5612 this.type = src.type;
5613
5614 // Events bubbling up the document may have been marked as prevented
5615 // by a handler lower down the tree; reflect the correct value.
5616 this.isDefaultPrevented = src.defaultPrevented ||
5617 src.defaultPrevented === undefined &&
5618
5619 // Support: Android <=2.3 only
5620 src.returnValue === false ?
5621 returnTrue :
5622 returnFalse;
5623
5624 // Create target properties
5625 // Support: Safari <=6 - 7 only
5626 // Target should not be a text node (#504, #13143)
5627 this.target = ( src.target && src.target.nodeType === 3 ) ?
5628 src.target.parentNode :
5629 src.target;
5630
5631 this.currentTarget = src.currentTarget;
5632 this.relatedTarget = src.relatedTarget;
5633
5634 // Event type
5635 } else {
5636 this.type = src;
5637 }
5638
5639 // Put explicitly provided properties onto the event object
5640 if ( props ) {
5641 jQuery.extend( this, props );
5642 }
5643
5644 // Create a timestamp if incoming event doesn't have one
5645 this.timeStamp = src && src.timeStamp || Date.now();
5646
5647 // Mark it as fixed
5648 this[ jQuery.expando ] = true;
5649};
5650
5651// jQuery.Event is based on DOM3 Events as specified by the ECMAScript Language Binding
5652// https://www.w3.org/TR/2003/WD-DOM-Level-3-Events-20030331/ecma-script-binding.html
5653jQuery.Event.prototype = {
5654 constructor: jQuery.Event,
5655 isDefaultPrevented: returnFalse,
5656 isPropagationStopped: returnFalse,
5657 isImmediatePropagationStopped: returnFalse,
5658 isSimulated: false,
5659
5660 preventDefault: function() {
5661 var e = this.originalEvent;
5662
5663 this.isDefaultPrevented = returnTrue;
5664
5665 if ( e && !this.isSimulated ) {
5666 e.preventDefault();
5667 }
5668 },
5669 stopPropagation: function() {
5670 var e = this.originalEvent;
5671
5672 this.isPropagationStopped = returnTrue;
5673
5674 if ( e && !this.isSimulated ) {
5675 e.stopPropagation();
5676 }
5677 },
5678 stopImmediatePropagation: function() {
5679 var e = this.originalEvent;
5680
5681 this.isImmediatePropagationStopped = returnTrue;
5682
5683 if ( e && !this.isSimulated ) {
5684 e.stopImmediatePropagation();
5685 }
5686
5687 this.stopPropagation();
5688 }
5689};
5690
5691// Includes all common event props including KeyEvent and MouseEvent specific props
5692jQuery.each( {
5693 altKey: true,
5694 bubbles: true,
5695 cancelable: true,
5696 changedTouches: true,
5697 ctrlKey: true,
5698 detail: true,
5699 eventPhase: true,
5700 metaKey: true,
5701 pageX: true,
5702 pageY: true,
5703 shiftKey: true,
5704 view: true,
5705 "char": true,
5706 charCode: true,
5707 key: true,
5708 keyCode: true,
5709 button: true,
5710 buttons: true,
5711 clientX: true,
5712 clientY: true,
5713 offsetX: true,
5714 offsetY: true,
5715 pointerId: true,
5716 pointerType: true,
5717 screenX: true,
5718 screenY: true,
5719 targetTouches: true,
5720 toElement: true,
5721 touches: true,
5722
5723 which: function( event ) {
5724 var button = event.button;
5725
5726 // Add which for key events
5727 if ( event.which == null && rkeyEvent.test( event.type ) ) {
5728 return event.charCode != null ? event.charCode : event.keyCode;
5729 }
5730
5731 // Add which for click: 1 === left; 2 === middle; 3 === right
5732 if ( !event.which && button !== undefined && rmouseEvent.test( event.type ) ) {
5733 if ( button & 1 ) {
5734 return 1;
5735 }
5736
5737 if ( button & 2 ) {
5738 return 3;
5739 }
5740
5741 if ( button & 4 ) {
5742 return 2;
5743 }
5744
5745 return 0;
5746 }
5747
5748 return event.which;
5749 }
5750}, jQuery.event.addProp );
5751
5752// Create mouseenter/leave events using mouseover/out and event-time checks
5753// so that event delegation works in jQuery.
5754// Do the same for pointerenter/pointerleave and pointerover/pointerout
5755//
5756// Support: Safari 7 only
5757// Safari sends mouseenter too often; see:
5758// https://bugs.chromium.org/p/chromium/issues/detail?id=470258
5759// for the description of the bug (it existed in older Chrome versions as well).
5760jQuery.each( {
5761 mouseenter: "mouseover",
5762 mouseleave: "mouseout",
5763 pointerenter: "pointerover",
5764 pointerleave: "pointerout"
5765}, function( orig, fix ) {
5766 jQuery.event.special[ orig ] = {
5767 delegateType: fix,
5768 bindType: fix,
5769
5770 handle: function( event ) {
5771 var ret,
5772 target = this,
5773 related = event.relatedTarget,
5774 handleObj = event.handleObj;
5775
5776 // For mouseenter/leave call the handler if related is outside the target.
5777 // NB: No relatedTarget if the mouse left/entered the browser window
5778 if ( !related || ( related !== target && !jQuery.contains( target, related ) ) ) {
5779 event.type = handleObj.origType;
5780 ret = handleObj.handler.apply( this, arguments );
5781 event.type = fix;
5782 }
5783 return ret;
5784 }
5785 };
5786} );
5787
5788jQuery.fn.extend( {
5789
5790 on: function( types, selector, data, fn ) {
5791 return on( this, types, selector, data, fn );
5792 },
5793 one: function( types, selector, data, fn ) {
5794 return on( this, types, selector, data, fn, 1 );
5795 },
5796 off: function( types, selector, fn ) {
5797 var handleObj, type;
5798 if ( types && types.preventDefault && types.handleObj ) {
5799
5800 // ( event ) dispatched jQuery.Event
5801 handleObj = types.handleObj;
5802 jQuery( types.delegateTarget ).off(
5803 handleObj.namespace ?
5804 handleObj.origType + "." + handleObj.namespace :
5805 handleObj.origType,
5806 handleObj.selector,
5807 handleObj.handler
5808 );
5809 return this;
5810 }
5811 if ( typeof types === "object" ) {
5812
5813 // ( types-object [, selector] )
5814 for ( type in types ) {
5815 this.off( type, selector, types[ type ] );
5816 }
5817 return this;
5818 }
5819 if ( selector === false || typeof selector === "function" ) {
5820
5821 // ( types [, fn] )
5822 fn = selector;
5823 selector = undefined;
5824 }
5825 if ( fn === false ) {
5826 fn = returnFalse;
5827 }
5828 return this.each( function() {
5829 jQuery.event.remove( this, types, fn, selector );
5830 } );
5831 }
5832} );
5833
5834
5835var
5836
5837 /* eslint-disable max-len */
5838
5839 // See https://github.com/eslint/eslint/issues/3229
5840 rxhtmlTag = /<(?!area|br|col|embed|hr|img|input|link|meta|param)(([a-z][^\/\0>\x20\t\r\n\f]*)[^>]*)\/>/gi,
5841
5842 /* eslint-enable */
5843
5844 // Support: IE <=10 - 11, Edge 12 - 13 only
5845 // In IE/Edge using regex groups here causes severe slowdowns.
5846 // See https://connect.microsoft.com/IE/feedback/details/1736512/
5847 rnoInnerhtml = /<script|<style|<link/i,
5848
5849 // checked="checked" or checked
5850 rchecked = /checked\s*(?:[^=]|=\s*.checked.)/i,
5851 rcleanScript = /^\s*<!(?:\[CDATA\[|--)|(?:\]\]|--)>\s*$/g;
5852
5853// Prefer a tbody over its parent table for containing new rows
5854function manipulationTarget( elem, content ) {
5855 if ( nodeName( elem, "table" ) &&
5856 nodeName( content.nodeType !== 11 ? content : content.firstChild, "tr" ) ) {
5857
5858 return jQuery( elem ).children( "tbody" )[ 0 ] || elem;
5859 }
5860
5861 return elem;
5862}
5863
5864// Replace/restore the type attribute of script elements for safe DOM manipulation
5865function disableScript( elem ) {
5866 elem.type = ( elem.getAttribute( "type" ) !== null ) + "/" + elem.type;
5867 return elem;
5868}
5869function restoreScript( elem ) {
5870 if ( ( elem.type || "" ).slice( 0, 5 ) === "true/" ) {
5871 elem.type = elem.type.slice( 5 );
5872 } else {
5873 elem.removeAttribute( "type" );
5874 }
5875
5876 return elem;
5877}
5878
5879function cloneCopyEvent( src, dest ) {
5880 var i, l, type, pdataOld, pdataCur, udataOld, udataCur, events;
5881
5882 if ( dest.nodeType !== 1 ) {
5883 return;
5884 }
5885
5886 // 1. Copy private data: events, handlers, etc.
5887 if ( dataPriv.hasData( src ) ) {
5888 pdataOld = dataPriv.access( src );
5889 pdataCur = dataPriv.set( dest, pdataOld );
5890 events = pdataOld.events;
5891
5892 if ( events ) {
5893 delete pdataCur.handle;
5894 pdataCur.events = {};
5895
5896 for ( type in events ) {
5897 for ( i = 0, l = events[ type ].length; i < l; i++ ) {
5898 jQuery.event.add( dest, type, events[ type ][ i ] );
5899 }
5900 }
5901 }
5902 }
5903
5904 // 2. Copy user data
5905 if ( dataUser.hasData( src ) ) {
5906 udataOld = dataUser.access( src );
5907 udataCur = jQuery.extend( {}, udataOld );
5908
5909 dataUser.set( dest, udataCur );
5910 }
5911}
5912
5913// Fix IE bugs, see support tests
5914function fixInput( src, dest ) {
5915 var nodeName = dest.nodeName.toLowerCase();
5916
5917 // Fails to persist the checked state of a cloned checkbox or radio button.
5918 if ( nodeName === "input" && rcheckableType.test( src.type ) ) {
5919 dest.checked = src.checked;
5920
5921 // Fails to return the selected option to the default selected state when cloning options
5922 } else if ( nodeName === "input" || nodeName === "textarea" ) {
5923 dest.defaultValue = src.defaultValue;
5924 }
5925}
5926
5927function domManip( collection, args, callback, ignored ) {
5928
5929 // Flatten any nested arrays
5930 args = concat.apply( [], args );
5931
5932 var fragment, first, scripts, hasScripts, node, doc,
5933 i = 0,
5934 l = collection.length,
5935 iNoClone = l - 1,
5936 value = args[ 0 ],
5937 valueIsFunction = isFunction( value );
5938
5939 // We can't cloneNode fragments that contain checked, in WebKit
5940 if ( valueIsFunction ||
5941 ( l > 1 && typeof value === "string" &&
5942 !support.checkClone && rchecked.test( value ) ) ) {
5943 return collection.each( function( index ) {
5944 var self = collection.eq( index );
5945 if ( valueIsFunction ) {
5946 args[ 0 ] = value.call( this, index, self.html() );
5947 }
5948 domManip( self, args, callback, ignored );
5949 } );
5950 }
5951
5952 if ( l ) {
5953 fragment = buildFragment( args, collection[ 0 ].ownerDocument, false, collection, ignored );
5954 first = fragment.firstChild;
5955
5956 if ( fragment.childNodes.length === 1 ) {
5957 fragment = first;
5958 }
5959
5960 // Require either new content or an interest in ignored elements to invoke the callback
5961 if ( first || ignored ) {
5962 scripts = jQuery.map( getAll( fragment, "script" ), disableScript );
5963 hasScripts = scripts.length;
5964
5965 // Use the original fragment for the last item
5966 // instead of the first because it can end up
5967 // being emptied incorrectly in certain situations (#8070).
5968 for ( ; i < l; i++ ) {
5969 node = fragment;
5970
5971 if ( i !== iNoClone ) {
5972 node = jQuery.clone( node, true, true );
5973
5974 // Keep references to cloned scripts for later restoration
5975 if ( hasScripts ) {
5976
5977 // Support: Android <=4.0 only, PhantomJS 1 only
5978 // push.apply(_, arraylike) throws on ancient WebKit
5979 jQuery.merge( scripts, getAll( node, "script" ) );
5980 }
5981 }
5982
5983 callback.call( collection[ i ], node, i );
5984 }
5985
5986 if ( hasScripts ) {
5987 doc = scripts[ scripts.length - 1 ].ownerDocument;
5988
5989 // Reenable scripts
5990 jQuery.map( scripts, restoreScript );
5991
5992 // Evaluate executable scripts on first document insertion
5993 for ( i = 0; i < hasScripts; i++ ) {
5994 node = scripts[ i ];
5995 if ( rscriptType.test( node.type || "" ) &&
5996 !dataPriv.access( node, "globalEval" ) &&
5997 jQuery.contains( doc, node ) ) {
5998
5999 if ( node.src && ( node.type || "" ).toLowerCase() !== "module" ) {
6000
6001 // Optional AJAX dependency, but won't run scripts if not present
6002 if ( jQuery._evalUrl ) {
6003 jQuery._evalUrl( node.src );
6004 }
6005 } else {
6006 DOMEval( node.textContent.replace( rcleanScript, "" ), doc, node );
6007 }
6008 }
6009 }
6010 }
6011 }
6012 }
6013
6014 return collection;
6015}
6016
6017function remove( elem, selector, keepData ) {
6018 var node,
6019 nodes = selector ? jQuery.filter( selector, elem ) : elem,
6020 i = 0;
6021
6022 for ( ; ( node = nodes[ i ] ) != null; i++ ) {
6023 if ( !keepData && node.nodeType === 1 ) {
6024 jQuery.cleanData( getAll( node ) );
6025 }
6026
6027 if ( node.parentNode ) {
6028 if ( keepData && jQuery.contains( node.ownerDocument, node ) ) {
6029 setGlobalEval( getAll( node, "script" ) );
6030 }
6031 node.parentNode.removeChild( node );
6032 }
6033 }
6034
6035 return elem;
6036}
6037
6038jQuery.extend( {
6039 htmlPrefilter: function( html ) {
6040 return html.replace( rxhtmlTag, "<$1></$2>" );
6041 },
6042
6043 clone: function( elem, dataAndEvents, deepDataAndEvents ) {
6044 var i, l, srcElements, destElements,
6045 clone = elem.cloneNode( true ),
6046 inPage = jQuery.contains( elem.ownerDocument, elem );
6047
6048 // Fix IE cloning issues
6049 if ( !support.noCloneChecked && ( elem.nodeType === 1 || elem.nodeType === 11 ) &&
6050 !jQuery.isXMLDoc( elem ) ) {
6051
6052 // We eschew Sizzle here for performance reasons: https://jsperf.com/getall-vs-sizzle/2
6053 destElements = getAll( clone );
6054 srcElements = getAll( elem );
6055
6056 for ( i = 0, l = srcElements.length; i < l; i++ ) {
6057 fixInput( srcElements[ i ], destElements[ i ] );
6058 }
6059 }
6060
6061 // Copy the events from the original to the clone
6062 if ( dataAndEvents ) {
6063 if ( deepDataAndEvents ) {
6064 srcElements = srcElements || getAll( elem );
6065 destElements = destElements || getAll( clone );
6066
6067 for ( i = 0, l = srcElements.length; i < l; i++ ) {
6068 cloneCopyEvent( srcElements[ i ], destElements[ i ] );
6069 }
6070 } else {
6071 cloneCopyEvent( elem, clone );
6072 }
6073 }
6074
6075 // Preserve script evaluation history
6076 destElements = getAll( clone, "script" );
6077 if ( destElements.length > 0 ) {
6078 setGlobalEval( destElements, !inPage && getAll( elem, "script" ) );
6079 }
6080
6081 // Return the cloned set
6082 return clone;
6083 },
6084
6085 cleanData: function( elems ) {
6086 var data, elem, type,
6087 special = jQuery.event.special,
6088 i = 0;
6089
6090 for ( ; ( elem = elems[ i ] ) !== undefined; i++ ) {
6091 if ( acceptData( elem ) ) {
6092 if ( ( data = elem[ dataPriv.expando ] ) ) {
6093 if ( data.events ) {
6094 for ( type in data.events ) {
6095 if ( special[ type ] ) {
6096 jQuery.event.remove( elem, type );
6097
6098 // This is a shortcut to avoid jQuery.event.remove's overhead
6099 } else {
6100 jQuery.removeEvent( elem, type, data.handle );
6101 }
6102 }
6103 }
6104
6105 // Support: Chrome <=35 - 45+
6106 // Assign undefined instead of using delete, see Data#remove
6107 elem[ dataPriv.expando ] = undefined;
6108 }
6109 if ( elem[ dataUser.expando ] ) {
6110
6111 // Support: Chrome <=35 - 45+
6112 // Assign undefined instead of using delete, see Data#remove
6113 elem[ dataUser.expando ] = undefined;
6114 }
6115 }
6116 }
6117 }
6118} );
6119
6120jQuery.fn.extend( {
6121 detach: function( selector ) {
6122 return remove( this, selector, true );
6123 },
6124
6125 remove: function( selector ) {
6126 return remove( this, selector );
6127 },
6128
6129 text: function( value ) {
6130 return access( this, function( value ) {
6131 return value === undefined ?
6132 jQuery.text( this ) :
6133 this.empty().each( function() {
6134 if ( this.nodeType === 1 || this.nodeType === 11 || this.nodeType === 9 ) {
6135 this.textContent = value;
6136 }
6137 } );
6138 }, null, value, arguments.length );
6139 },
6140
6141 append: function() {
6142 return domManip( this, arguments, function( elem ) {
6143 if ( this.nodeType === 1 || this.nodeType === 11 || this.nodeType === 9 ) {
6144 var target = manipulationTarget( this, elem );
6145 target.appendChild( elem );
6146 }
6147 } );
6148 },
6149
6150 prepend: function() {
6151 return domManip( this, arguments, function( elem ) {
6152 if ( this.nodeType === 1 || this.nodeType === 11 || this.nodeType === 9 ) {
6153 var target = manipulationTarget( this, elem );
6154 target.insertBefore( elem, target.firstChild );
6155 }
6156 } );
6157 },
6158
6159 before: function() {
6160 return domManip( this, arguments, function( elem ) {
6161 if ( this.parentNode ) {
6162 this.parentNode.insertBefore( elem, this );
6163 }
6164 } );
6165 },
6166
6167 after: function() {
6168 return domManip( this, arguments, function( elem ) {
6169 if ( this.parentNode ) {
6170 this.parentNode.insertBefore( elem, this.nextSibling );
6171 }
6172 } );
6173 },
6174
6175 empty: function() {
6176 var elem,
6177 i = 0;
6178
6179 for ( ; ( elem = this[ i ] ) != null; i++ ) {
6180 if ( elem.nodeType === 1 ) {
6181
6182 // Prevent memory leaks
6183 jQuery.cleanData( getAll( elem, false ) );
6184
6185 // Remove any remaining nodes
6186 elem.textContent = "";
6187 }
6188 }
6189
6190 return this;
6191 },
6192
6193 clone: function( dataAndEvents, deepDataAndEvents ) {
6194 dataAndEvents = dataAndEvents == null ? false : dataAndEvents;
6195 deepDataAndEvents = deepDataAndEvents == null ? dataAndEvents : deepDataAndEvents;
6196
6197 return this.map( function() {
6198 return jQuery.clone( this, dataAndEvents, deepDataAndEvents );
6199 } );
6200 },
6201
6202 html: function( value ) {
6203 return access( this, function( value ) {
6204 var elem = this[ 0 ] || {},
6205 i = 0,
6206 l = this.length;
6207
6208 if ( value === undefined && elem.nodeType === 1 ) {
6209 return elem.innerHTML;
6210 }
6211
6212 // See if we can take a shortcut and just use innerHTML
6213 if ( typeof value === "string" && !rnoInnerhtml.test( value ) &&
6214 !wrapMap[ ( rtagName.exec( value ) || [ "", "" ] )[ 1 ].toLowerCase() ] ) {
6215
6216 value = jQuery.htmlPrefilter( value );
6217
6218 try {
6219 for ( ; i < l; i++ ) {
6220 elem = this[ i ] || {};
6221
6222 // Remove element nodes and prevent memory leaks
6223 if ( elem.nodeType === 1 ) {
6224 jQuery.cleanData( getAll( elem, false ) );
6225 elem.innerHTML = value;
6226 }
6227 }
6228
6229 elem = 0;
6230
6231 // If using innerHTML throws an exception, use the fallback method
6232 } catch ( e ) {}
6233 }
6234
6235 if ( elem ) {
6236 this.empty().append( value );
6237 }
6238 }, null, value, arguments.length );
6239 },
6240
6241 replaceWith: function() {
6242 var ignored = [];
6243
6244 // Make the changes, replacing each non-ignored context element with the new content
6245 return domManip( this, arguments, function( elem ) {
6246 var parent = this.parentNode;
6247
6248 if ( jQuery.inArray( this, ignored ) < 0 ) {
6249 jQuery.cleanData( getAll( this ) );
6250 if ( parent ) {
6251 parent.replaceChild( elem, this );
6252 }
6253 }
6254
6255 // Force callback invocation
6256 }, ignored );
6257 }
6258} );
6259
6260jQuery.each( {
6261 appendTo: "append",
6262 prependTo: "prepend",
6263 insertBefore: "before",
6264 insertAfter: "after",
6265 replaceAll: "replaceWith"
6266}, function( name, original ) {
6267 jQuery.fn[ name ] = function( selector ) {
6268 var elems,
6269 ret = [],
6270 insert = jQuery( selector ),
6271 last = insert.length - 1,
6272 i = 0;
6273
6274 for ( ; i <= last; i++ ) {
6275 elems = i === last ? this : this.clone( true );
6276 jQuery( insert[ i ] )[ original ]( elems );
6277
6278 // Support: Android <=4.0 only, PhantomJS 1 only
6279 // .get() because push.apply(_, arraylike) throws on ancient WebKit
6280 push.apply( ret, elems.get() );
6281 }
6282
6283 return this.pushStack( ret );
6284 };
6285} );
6286var rnumnonpx = new RegExp( "^(" + pnum + ")(?!px)[a-z%]+$", "i" );
6287
6288var getStyles = function( elem ) {
6289
6290 // Support: IE <=11 only, Firefox <=30 (#15098, #14150)
6291 // IE throws on elements created in popups
6292 // FF meanwhile throws on frame elements through "defaultView.getComputedStyle"
6293 var view = elem.ownerDocument.defaultView;
6294
6295 if ( !view || !view.opener ) {
6296 view = window;
6297 }
6298
6299 return view.getComputedStyle( elem );
6300 };
6301
6302var rboxStyle = new RegExp( cssExpand.join( "|" ), "i" );
6303
6304
6305
6306( function() {
6307
6308 // Executing both pixelPosition & boxSizingReliable tests require only one layout
6309 // so they're executed at the same time to save the second computation.
6310 function computeStyleTests() {
6311
6312 // This is a singleton, we need to execute it only once
6313 if ( !div ) {
6314 return;
6315 }
6316
6317 container.style.cssText = "position:absolute;left:-11111px;width:60px;" +
6318 "margin-top:1px;padding:0;border:0";
6319 div.style.cssText =
6320 "position:relative;display:block;box-sizing:border-box;overflow:scroll;" +
6321 "margin:auto;border:1px;padding:1px;" +
6322 "width:60%;top:1%";
6323 documentElement.appendChild( container ).appendChild( div );
6324
6325 var divStyle = window.getComputedStyle( div );
6326 pixelPositionVal = divStyle.top !== "1%";
6327
6328 // Support: Android 4.0 - 4.3 only, Firefox <=3 - 44
6329 reliableMarginLeftVal = roundPixelMeasures( divStyle.marginLeft ) === 12;
6330
6331 // Support: Android 4.0 - 4.3 only, Safari <=9.1 - 10.1, iOS <=7.0 - 9.3
6332 // Some styles come back with percentage values, even though they shouldn't
6333 div.style.right = "60%";
6334 pixelBoxStylesVal = roundPixelMeasures( divStyle.right ) === 36;
6335
6336 // Support: IE 9 - 11 only
6337 // Detect misreporting of content dimensions for box-sizing:border-box elements
6338 boxSizingReliableVal = roundPixelMeasures( divStyle.width ) === 36;
6339
6340 // Support: IE 9 only
6341 // Detect overflow:scroll screwiness (gh-3699)
6342 div.style.position = "absolute";
6343 scrollboxSizeVal = div.offsetWidth === 36 || "absolute";
6344
6345 documentElement.removeChild( container );
6346
6347 // Nullify the div so it wouldn't be stored in the memory and
6348 // it will also be a sign that checks already performed
6349 div = null;
6350 }
6351
6352 function roundPixelMeasures( measure ) {
6353 return Math.round( parseFloat( measure ) );
6354 }
6355
6356 var pixelPositionVal, boxSizingReliableVal, scrollboxSizeVal, pixelBoxStylesVal,
6357 reliableMarginLeftVal,
6358 container = document.createElement( "div" ),
6359 div = document.createElement( "div" );
6360
6361 // Finish early in limited (non-browser) environments
6362 if ( !div.style ) {
6363 return;
6364 }
6365
6366 // Support: IE <=9 - 11 only
6367 // Style of cloned element affects source element cloned (#8908)
6368 div.style.backgroundClip = "content-box";
6369 div.cloneNode( true ).style.backgroundClip = "";
6370 support.clearCloneStyle = div.style.backgroundClip === "content-box";
6371
6372 jQuery.extend( support, {
6373 boxSizingReliable: function() {
6374 computeStyleTests();
6375 return boxSizingReliableVal;
6376 },
6377 pixelBoxStyles: function() {
6378 computeStyleTests();
6379 return pixelBoxStylesVal;
6380 },
6381 pixelPosition: function() {
6382 computeStyleTests();
6383 return pixelPositionVal;
6384 },
6385 reliableMarginLeft: function() {
6386 computeStyleTests();
6387 return reliableMarginLeftVal;
6388 },
6389 scrollboxSize: function() {
6390 computeStyleTests();
6391 return scrollboxSizeVal;
6392 }
6393 } );
6394} )();
6395
6396
6397function curCSS( elem, name, computed ) {
6398 var width, minWidth, maxWidth, ret,
6399
6400 // Support: Firefox 51+
6401 // Retrieving style before computed somehow
6402 // fixes an issue with getting wrong values
6403 // on detached elements
6404 style = elem.style;
6405
6406 computed = computed || getStyles( elem );
6407
6408 // getPropertyValue is needed for:
6409 // .css('filter') (IE 9 only, #12537)
6410 // .css('--customProperty) (#3144)
6411 if ( computed ) {
6412 ret = computed.getPropertyValue( name ) || computed[ name ];
6413
6414 if ( ret === "" && !jQuery.contains( elem.ownerDocument, elem ) ) {
6415 ret = jQuery.style( elem, name );
6416 }
6417
6418 // A tribute to the "awesome hack by Dean Edwards"
6419 // Android Browser returns percentage for some values,
6420 // but width seems to be reliably pixels.
6421 // This is against the CSSOM draft spec:
6422 // https://drafts.csswg.org/cssom/#resolved-values
6423 if ( !support.pixelBoxStyles() && rnumnonpx.test( ret ) && rboxStyle.test( name ) ) {
6424
6425 // Remember the original values
6426 width = style.width;
6427 minWidth = style.minWidth;
6428 maxWidth = style.maxWidth;
6429
6430 // Put in the new values to get a computed value out
6431 style.minWidth = style.maxWidth = style.width = ret;
6432 ret = computed.width;
6433
6434 // Revert the changed values
6435 style.width = width;
6436 style.minWidth = minWidth;
6437 style.maxWidth = maxWidth;
6438 }
6439 }
6440
6441 return ret !== undefined ?
6442
6443 // Support: IE <=9 - 11 only
6444 // IE returns zIndex value as an integer.
6445 ret + "" :
6446 ret;
6447}
6448
6449
6450function addGetHookIf( conditionFn, hookFn ) {
6451
6452 // Define the hook, we'll check on the first run if it's really needed.
6453 return {
6454 get: function() {
6455 if ( conditionFn() ) {
6456
6457 // Hook not needed (or it's not possible to use it due
6458 // to missing dependency), remove it.
6459 delete this.get;
6460 return;
6461 }
6462
6463 // Hook needed; redefine it so that the support test is not executed again.
6464 return ( this.get = hookFn ).apply( this, arguments );
6465 }
6466 };
6467}
6468
6469
6470var
6471
6472 // Swappable if display is none or starts with table
6473 // except "table", "table-cell", or "table-caption"
6474 // See here for display values: https://developer.mozilla.org/en-US/docs/CSS/display
6475 rdisplayswap = /^(none|table(?!-c[ea]).+)/,
6476 rcustomProp = /^--/,
6477 cssShow = { position: "absolute", visibility: "hidden", display: "block" },
6478 cssNormalTransform = {
6479 letterSpacing: "0",
6480 fontWeight: "400"
6481 },
6482
6483 cssPrefixes = [ "Webkit", "Moz", "ms" ],
6484 emptyStyle = document.createElement( "div" ).style;
6485
6486// Return a css property mapped to a potentially vendor prefixed property
6487function vendorPropName( name ) {
6488
6489 // Shortcut for names that are not vendor prefixed
6490 if ( name in emptyStyle ) {
6491 return name;
6492 }
6493
6494 // Check for vendor prefixed names
6495 var capName = name[ 0 ].toUpperCase() + name.slice( 1 ),
6496 i = cssPrefixes.length;
6497
6498 while ( i-- ) {
6499 name = cssPrefixes[ i ] + capName;
6500 if ( name in emptyStyle ) {
6501 return name;
6502 }
6503 }
6504}
6505
6506// Return a property mapped along what jQuery.cssProps suggests or to
6507// a vendor prefixed property.
6508function finalPropName( name ) {
6509 var ret = jQuery.cssProps[ name ];
6510 if ( !ret ) {
6511 ret = jQuery.cssProps[ name ] = vendorPropName( name ) || name;
6512 }
6513 return ret;
6514}
6515
6516function setPositiveNumber( elem, value, subtract ) {
6517
6518 // Any relative (+/-) values have already been
6519 // normalized at this point
6520 var matches = rcssNum.exec( value );
6521 return matches ?
6522
6523 // Guard against undefined "subtract", e.g., when used as in cssHooks
6524 Math.max( 0, matches[ 2 ] - ( subtract || 0 ) ) + ( matches[ 3 ] || "px" ) :
6525 value;
6526}
6527
6528function boxModelAdjustment( elem, dimension, box, isBorderBox, styles, computedVal ) {
6529 var i = dimension === "width" ? 1 : 0,
6530 extra = 0,
6531 delta = 0;
6532
6533 // Adjustment may not be necessary
6534 if ( box === ( isBorderBox ? "border" : "content" ) ) {
6535 return 0;
6536 }
6537
6538 for ( ; i < 4; i += 2 ) {
6539
6540 // Both box models exclude margin
6541 if ( box === "margin" ) {
6542 delta += jQuery.css( elem, box + cssExpand[ i ], true, styles );
6543 }
6544
6545 // If we get here with a content-box, we're seeking "padding" or "border" or "margin"
6546 if ( !isBorderBox ) {
6547
6548 // Add padding
6549 delta += jQuery.css( elem, "padding" + cssExpand[ i ], true, styles );
6550
6551 // For "border" or "margin", add border
6552 if ( box !== "padding" ) {
6553 delta += jQuery.css( elem, "border" + cssExpand[ i ] + "Width", true, styles );
6554
6555 // But still keep track of it otherwise
6556 } else {
6557 extra += jQuery.css( elem, "border" + cssExpand[ i ] + "Width", true, styles );
6558 }
6559
6560 // If we get here with a border-box (content + padding + border), we're seeking "content" or
6561 // "padding" or "margin"
6562 } else {
6563
6564 // For "content", subtract padding
6565 if ( box === "content" ) {
6566 delta -= jQuery.css( elem, "padding" + cssExpand[ i ], true, styles );
6567 }
6568
6569 // For "content" or "padding", subtract border
6570 if ( box !== "margin" ) {
6571 delta -= jQuery.css( elem, "border" + cssExpand[ i ] + "Width", true, styles );
6572 }
6573 }
6574 }
6575
6576 // Account for positive content-box scroll gutter when requested by providing computedVal
6577 if ( !isBorderBox && computedVal >= 0 ) {
6578
6579 // offsetWidth/offsetHeight is a rounded sum of content, padding, scroll gutter, and border
6580 // Assuming integer scroll gutter, subtract the rest and round down
6581 delta += Math.max( 0, Math.ceil(
6582 elem[ "offset" + dimension[ 0 ].toUpperCase() + dimension.slice( 1 ) ] -
6583 computedVal -
6584 delta -
6585 extra -
6586 0.5
6587 ) );
6588 }
6589
6590 return delta;
6591}
6592
6593function getWidthOrHeight( elem, dimension, extra ) {
6594
6595 // Start with computed style
6596 var styles = getStyles( elem ),
6597 val = curCSS( elem, dimension, styles ),
6598 isBorderBox = jQuery.css( elem, "boxSizing", false, styles ) === "border-box",
6599 valueIsBorderBox = isBorderBox;
6600
6601 // Support: Firefox <=54
6602 // Return a confounding non-pixel value or feign ignorance, as appropriate.
6603 if ( rnumnonpx.test( val ) ) {
6604 if ( !extra ) {
6605 return val;
6606 }
6607 val = "auto";
6608 }
6609
6610 // Check for style in case a browser which returns unreliable values
6611 // for getComputedStyle silently falls back to the reliable elem.style
6612 valueIsBorderBox = valueIsBorderBox &&
6613 ( support.boxSizingReliable() || val === elem.style[ dimension ] );
6614
6615 // Fall back to offsetWidth/offsetHeight when value is "auto"
6616 // This happens for inline elements with no explicit setting (gh-3571)
6617 // Support: Android <=4.1 - 4.3 only
6618 // Also use offsetWidth/offsetHeight for misreported inline dimensions (gh-3602)
6619 if ( val === "auto" ||
6620 !parseFloat( val ) && jQuery.css( elem, "display", false, styles ) === "inline" ) {
6621
6622 val = elem[ "offset" + dimension[ 0 ].toUpperCase() + dimension.slice( 1 ) ];
6623
6624 // offsetWidth/offsetHeight provide border-box values
6625 valueIsBorderBox = true;
6626 }
6627
6628 // Normalize "" and auto
6629 val = parseFloat( val ) || 0;
6630
6631 // Adjust for the element's box model
6632 return ( val +
6633 boxModelAdjustment(
6634 elem,
6635 dimension,
6636 extra || ( isBorderBox ? "border" : "content" ),
6637 valueIsBorderBox,
6638 styles,
6639
6640 // Provide the current computed size to request scroll gutter calculation (gh-3589)
6641 val
6642 )
6643 ) + "px";
6644}
6645
6646jQuery.extend( {
6647
6648 // Add in style property hooks for overriding the default
6649 // behavior of getting and setting a style property
6650 cssHooks: {
6651 opacity: {
6652 get: function( elem, computed ) {
6653 if ( computed ) {
6654
6655 // We should always get a number back from opacity
6656 var ret = curCSS( elem, "opacity" );
6657 return ret === "" ? "1" : ret;
6658 }
6659 }
6660 }
6661 },
6662
6663 // Don't automatically add "px" to these possibly-unitless properties
6664 cssNumber: {
6665 "animationIterationCount": true,
6666 "columnCount": true,
6667 "fillOpacity": true,
6668 "flexGrow": true,
6669 "flexShrink": true,
6670 "fontWeight": true,
6671 "lineHeight": true,
6672 "opacity": true,
6673 "order": true,
6674 "orphans": true,
6675 "widows": true,
6676 "zIndex": true,
6677 "zoom": true
6678 },
6679
6680 // Add in properties whose names you wish to fix before
6681 // setting or getting the value
6682 cssProps: {},
6683
6684 // Get and set the style property on a DOM Node
6685 style: function( elem, name, value, extra ) {
6686
6687 // Don't set styles on text and comment nodes
6688 if ( !elem || elem.nodeType === 3 || elem.nodeType === 8 || !elem.style ) {
6689 return;
6690 }
6691
6692 // Make sure that we're working with the right name
6693 var ret, type, hooks,
6694 origName = camelCase( name ),
6695 isCustomProp = rcustomProp.test( name ),
6696 style = elem.style;
6697
6698 // Make sure that we're working with the right name. We don't
6699 // want to query the value if it is a CSS custom property
6700 // since they are user-defined.
6701 if ( !isCustomProp ) {
6702 name = finalPropName( origName );
6703 }
6704
6705 // Gets hook for the prefixed version, then unprefixed version
6706 hooks = jQuery.cssHooks[ name ] || jQuery.cssHooks[ origName ];
6707
6708 // Check if we're setting a value
6709 if ( value !== undefined ) {
6710 type = typeof value;
6711
6712 // Convert "+=" or "-=" to relative numbers (#7345)
6713 if ( type === "string" && ( ret = rcssNum.exec( value ) ) && ret[ 1 ] ) {
6714 value = adjustCSS( elem, name, ret );
6715
6716 // Fixes bug #9237
6717 type = "number";
6718 }
6719
6720 // Make sure that null and NaN values aren't set (#7116)
6721 if ( value == null || value !== value ) {
6722 return;
6723 }
6724
6725 // If a number was passed in, add the unit (except for certain CSS properties)
6726 if ( type === "number" ) {
6727 value += ret && ret[ 3 ] || ( jQuery.cssNumber[ origName ] ? "" : "px" );
6728 }
6729
6730 // background-* props affect original clone's values
6731 if ( !support.clearCloneStyle && value === "" && name.indexOf( "background" ) === 0 ) {
6732 style[ name ] = "inherit";
6733 }
6734
6735 // If a hook was provided, use that value, otherwise just set the specified value
6736 if ( !hooks || !( "set" in hooks ) ||
6737 ( value = hooks.set( elem, value, extra ) ) !== undefined ) {
6738
6739 if ( isCustomProp ) {
6740 style.setProperty( name, value );
6741 } else {
6742 style[ name ] = value;
6743 }
6744 }
6745
6746 } else {
6747
6748 // If a hook was provided get the non-computed value from there
6749 if ( hooks && "get" in hooks &&
6750 ( ret = hooks.get( elem, false, extra ) ) !== undefined ) {
6751
6752 return ret;
6753 }
6754
6755 // Otherwise just get the value from the style object
6756 return style[ name ];
6757 }
6758 },
6759
6760 css: function( elem, name, extra, styles ) {
6761 var val, num, hooks,
6762 origName = camelCase( name ),
6763 isCustomProp = rcustomProp.test( name );
6764
6765 // Make sure that we're working with the right name. We don't
6766 // want to modify the value if it is a CSS custom property
6767 // since they are user-defined.
6768 if ( !isCustomProp ) {
6769 name = finalPropName( origName );
6770 }
6771
6772 // Try prefixed name followed by the unprefixed name
6773 hooks = jQuery.cssHooks[ name ] || jQuery.cssHooks[ origName ];
6774
6775 // If a hook was provided get the computed value from there
6776 if ( hooks && "get" in hooks ) {
6777 val = hooks.get( elem, true, extra );
6778 }
6779
6780 // Otherwise, if a way to get the computed value exists, use that
6781 if ( val === undefined ) {
6782 val = curCSS( elem, name, styles );
6783 }
6784
6785 // Convert "normal" to computed value
6786 if ( val === "normal" && name in cssNormalTransform ) {
6787 val = cssNormalTransform[ name ];
6788 }
6789
6790 // Make numeric if forced or a qualifier was provided and val looks numeric
6791 if ( extra === "" || extra ) {
6792 num = parseFloat( val );
6793 return extra === true || isFinite( num ) ? num || 0 : val;
6794 }
6795
6796 return val;
6797 }
6798} );
6799
6800jQuery.each( [ "height", "width" ], function( i, dimension ) {
6801 jQuery.cssHooks[ dimension ] = {
6802 get: function( elem, computed, extra ) {
6803 if ( computed ) {
6804
6805 // Certain elements can have dimension info if we invisibly show them
6806 // but it must have a current display style that would benefit
6807 return rdisplayswap.test( jQuery.css( elem, "display" ) ) &&
6808
6809 // Support: Safari 8+
6810 // Table columns in Safari have non-zero offsetWidth & zero
6811 // getBoundingClientRect().width unless display is changed.
6812 // Support: IE <=11 only
6813 // Running getBoundingClientRect on a disconnected node
6814 // in IE throws an error.
6815 ( !elem.getClientRects().length || !elem.getBoundingClientRect().width ) ?
6816 swap( elem, cssShow, function() {
6817 return getWidthOrHeight( elem, dimension, extra );
6818 } ) :
6819 getWidthOrHeight( elem, dimension, extra );
6820 }
6821 },
6822
6823 set: function( elem, value, extra ) {
6824 var matches,
6825 styles = getStyles( elem ),
6826 isBorderBox = jQuery.css( elem, "boxSizing", false, styles ) === "border-box",
6827 subtract = extra && boxModelAdjustment(
6828 elem,
6829 dimension,
6830 extra,
6831 isBorderBox,
6832 styles
6833 );
6834
6835 // Account for unreliable border-box dimensions by comparing offset* to computed and
6836 // faking a content-box to get border and padding (gh-3699)
6837 if ( isBorderBox && support.scrollboxSize() === styles.position ) {
6838 subtract -= Math.ceil(
6839 elem[ "offset" + dimension[ 0 ].toUpperCase() + dimension.slice( 1 ) ] -
6840 parseFloat( styles[ dimension ] ) -
6841 boxModelAdjustment( elem, dimension, "border", false, styles ) -
6842 0.5
6843 );
6844 }
6845
6846 // Convert to pixels if value adjustment is needed
6847 if ( subtract && ( matches = rcssNum.exec( value ) ) &&
6848 ( matches[ 3 ] || "px" ) !== "px" ) {
6849
6850 elem.style[ dimension ] = value;
6851 value = jQuery.css( elem, dimension );
6852 }
6853
6854 return setPositiveNumber( elem, value, subtract );
6855 }
6856 };
6857} );
6858
6859jQuery.cssHooks.marginLeft = addGetHookIf( support.reliableMarginLeft,
6860 function( elem, computed ) {
6861 if ( computed ) {
6862 return ( parseFloat( curCSS( elem, "marginLeft" ) ) ||
6863 elem.getBoundingClientRect().left -
6864 swap( elem, { marginLeft: 0 }, function() {
6865 return elem.getBoundingClientRect().left;
6866 } )
6867 ) + "px";
6868 }
6869 }
6870);
6871
6872// These hooks are used by animate to expand properties
6873jQuery.each( {
6874 margin: "",
6875 padding: "",
6876 border: "Width"
6877}, function( prefix, suffix ) {
6878 jQuery.cssHooks[ prefix + suffix ] = {
6879 expand: function( value ) {
6880 var i = 0,
6881 expanded = {},
6882
6883 // Assumes a single number if not a string
6884 parts = typeof value === "string" ? value.split( " " ) : [ value ];
6885
6886 for ( ; i < 4; i++ ) {
6887 expanded[ prefix + cssExpand[ i ] + suffix ] =
6888 parts[ i ] || parts[ i - 2 ] || parts[ 0 ];
6889 }
6890
6891 return expanded;
6892 }
6893 };
6894
6895 if ( prefix !== "margin" ) {
6896 jQuery.cssHooks[ prefix + suffix ].set = setPositiveNumber;
6897 }
6898} );
6899
6900jQuery.fn.extend( {
6901 css: function( name, value ) {
6902 return access( this, function( elem, name, value ) {
6903 var styles, len,
6904 map = {},
6905 i = 0;
6906
6907 if ( Array.isArray( name ) ) {
6908 styles = getStyles( elem );
6909 len = name.length;
6910
6911 for ( ; i < len; i++ ) {
6912 map[ name[ i ] ] = jQuery.css( elem, name[ i ], false, styles );
6913 }
6914
6915 return map;
6916 }
6917
6918 return value !== undefined ?
6919 jQuery.style( elem, name, value ) :
6920 jQuery.css( elem, name );
6921 }, name, value, arguments.length > 1 );
6922 }
6923} );
6924
6925
6926function Tween( elem, options, prop, end, easing ) {
6927 return new Tween.prototype.init( elem, options, prop, end, easing );
6928}
6929jQuery.Tween = Tween;
6930
6931Tween.prototype = {
6932 constructor: Tween,
6933 init: function( elem, options, prop, end, easing, unit ) {
6934 this.elem = elem;
6935 this.prop = prop;
6936 this.easing = easing || jQuery.easing._default;
6937 this.options = options;
6938 this.start = this.now = this.cur();
6939 this.end = end;
6940 this.unit = unit || ( jQuery.cssNumber[ prop ] ? "" : "px" );
6941 },
6942 cur: function() {
6943 var hooks = Tween.propHooks[ this.prop ];
6944
6945 return hooks && hooks.get ?
6946 hooks.get( this ) :
6947 Tween.propHooks._default.get( this );
6948 },
6949 run: function( percent ) {
6950 var eased,
6951 hooks = Tween.propHooks[ this.prop ];
6952
6953 if ( this.options.duration ) {
6954 this.pos = eased = jQuery.easing[ this.easing ](
6955 percent, this.options.duration * percent, 0, 1, this.options.duration
6956 );
6957 } else {
6958 this.pos = eased = percent;
6959 }
6960 this.now = ( this.end - this.start ) * eased + this.start;
6961
6962 if ( this.options.step ) {
6963 this.options.step.call( this.elem, this.now, this );
6964 }
6965
6966 if ( hooks && hooks.set ) {
6967 hooks.set( this );
6968 } else {
6969 Tween.propHooks._default.set( this );
6970 }
6971 return this;
6972 }
6973};
6974
6975Tween.prototype.init.prototype = Tween.prototype;
6976
6977Tween.propHooks = {
6978 _default: {
6979 get: function( tween ) {
6980 var result;
6981
6982 // Use a property on the element directly when it is not a DOM element,
6983 // or when there is no matching style property that exists.
6984 if ( tween.elem.nodeType !== 1 ||
6985 tween.elem[ tween.prop ] != null && tween.elem.style[ tween.prop ] == null ) {
6986 return tween.elem[ tween.prop ];
6987 }
6988
6989 // Passing an empty string as a 3rd parameter to .css will automatically
6990 // attempt a parseFloat and fallback to a string if the parse fails.
6991 // Simple values such as "10px" are parsed to Float;
6992 // complex values such as "rotate(1rad)" are returned as-is.
6993 result = jQuery.css( tween.elem, tween.prop, "" );
6994
6995 // Empty strings, null, undefined and "auto" are converted to 0.
6996 return !result || result === "auto" ? 0 : result;
6997 },
6998 set: function( tween ) {
6999
7000 // Use step hook for back compat.
7001 // Use cssHook if its there.
7002 // Use .style if available and use plain properties where available.
7003 if ( jQuery.fx.step[ tween.prop ] ) {
7004 jQuery.fx.step[ tween.prop ]( tween );
7005 } else if ( tween.elem.nodeType === 1 &&
7006 ( tween.elem.style[ jQuery.cssProps[ tween.prop ] ] != null ||
7007 jQuery.cssHooks[ tween.prop ] ) ) {
7008 jQuery.style( tween.elem, tween.prop, tween.now + tween.unit );
7009 } else {
7010 tween.elem[ tween.prop ] = tween.now;
7011 }
7012 }
7013 }
7014};
7015
7016// Support: IE <=9 only
7017// Panic based approach to setting things on disconnected nodes
7018Tween.propHooks.scrollTop = Tween.propHooks.scrollLeft = {
7019 set: function( tween ) {
7020 if ( tween.elem.nodeType && tween.elem.parentNode ) {
7021 tween.elem[ tween.prop ] = tween.now;
7022 }
7023 }
7024};
7025
7026jQuery.easing = {
7027 linear: function( p ) {
7028 return p;
7029 },
7030 swing: function( p ) {
7031 return 0.5 - Math.cos( p * Math.PI ) / 2;
7032 },
7033 _default: "swing"
7034};
7035
7036jQuery.fx = Tween.prototype.init;
7037
7038// Back compat <1.8 extension point
7039jQuery.fx.step = {};
7040
7041
7042
7043
7044var
7045 fxNow, inProgress,
7046 rfxtypes = /^(?:toggle|show|hide)$/,
7047 rrun = /queueHooks$/;
7048
7049function schedule() {
7050 if ( inProgress ) {
7051 if ( document.hidden === false && window.requestAnimationFrame ) {
7052 window.requestAnimationFrame( schedule );
7053 } else {
7054 window.setTimeout( schedule, jQuery.fx.interval );
7055 }
7056
7057 jQuery.fx.tick();
7058 }
7059}
7060
7061// Animations created synchronously will run synchronously
7062function createFxNow() {
7063 window.setTimeout( function() {
7064 fxNow = undefined;
7065 } );
7066 return ( fxNow = Date.now() );
7067}
7068
7069// Generate parameters to create a standard animation
7070function genFx( type, includeWidth ) {
7071 var which,
7072 i = 0,
7073 attrs = { height: type };
7074
7075 // If we include width, step value is 1 to do all cssExpand values,
7076 // otherwise step value is 2 to skip over Left and Right
7077 includeWidth = includeWidth ? 1 : 0;
7078 for ( ; i < 4; i += 2 - includeWidth ) {
7079 which = cssExpand[ i ];
7080 attrs[ "margin" + which ] = attrs[ "padding" + which ] = type;
7081 }
7082
7083 if ( includeWidth ) {
7084 attrs.opacity = attrs.width = type;
7085 }
7086
7087 return attrs;
7088}
7089
7090function createTween( value, prop, animation ) {
7091 var tween,
7092 collection = ( Animation.tweeners[ prop ] || [] ).concat( Animation.tweeners[ "*" ] ),
7093 index = 0,
7094 length = collection.length;
7095 for ( ; index < length; index++ ) {
7096 if ( ( tween = collection[ index ].call( animation, prop, value ) ) ) {
7097
7098 // We're done with this property
7099 return tween;
7100 }
7101 }
7102}
7103
7104function defaultPrefilter( elem, props, opts ) {
7105 var prop, value, toggle, hooks, oldfire, propTween, restoreDisplay, display,
7106 isBox = "width" in props || "height" in props,
7107 anim = this,
7108 orig = {},
7109 style = elem.style,
7110 hidden = elem.nodeType && isHiddenWithinTree( elem ),
7111 dataShow = dataPriv.get( elem, "fxshow" );
7112
7113 // Queue-skipping animations hijack the fx hooks
7114 if ( !opts.queue ) {
7115 hooks = jQuery._queueHooks( elem, "fx" );
7116 if ( hooks.unqueued == null ) {
7117 hooks.unqueued = 0;
7118 oldfire = hooks.empty.fire;
7119 hooks.empty.fire = function() {
7120 if ( !hooks.unqueued ) {
7121 oldfire();
7122 }
7123 };
7124 }
7125 hooks.unqueued++;
7126
7127 anim.always( function() {
7128
7129 // Ensure the complete handler is called before this completes
7130 anim.always( function() {
7131 hooks.unqueued--;
7132 if ( !jQuery.queue( elem, "fx" ).length ) {
7133 hooks.empty.fire();
7134 }
7135 } );
7136 } );
7137 }
7138
7139 // Detect show/hide animations
7140 for ( prop in props ) {
7141 value = props[ prop ];
7142 if ( rfxtypes.test( value ) ) {
7143 delete props[ prop ];
7144 toggle = toggle || value === "toggle";
7145 if ( value === ( hidden ? "hide" : "show" ) ) {
7146
7147 // Pretend to be hidden if this is a "show" and
7148 // there is still data from a stopped show/hide
7149 if ( value === "show" && dataShow && dataShow[ prop ] !== undefined ) {
7150 hidden = true;
7151
7152 // Ignore all other no-op show/hide data
7153 } else {
7154 continue;
7155 }
7156 }
7157 orig[ prop ] = dataShow && dataShow[ prop ] || jQuery.style( elem, prop );
7158 }
7159 }
7160
7161 // Bail out if this is a no-op like .hide().hide()
7162 propTween = !jQuery.isEmptyObject( props );
7163 if ( !propTween && jQuery.isEmptyObject( orig ) ) {
7164 return;
7165 }
7166
7167 // Restrict "overflow" and "display" styles during box animations
7168 if ( isBox && elem.nodeType === 1 ) {
7169
7170 // Support: IE <=9 - 11, Edge 12 - 15
7171 // Record all 3 overflow attributes because IE does not infer the shorthand
7172 // from identically-valued overflowX and overflowY and Edge just mirrors
7173 // the overflowX value there.
7174 opts.overflow = [ style.overflow, style.overflowX, style.overflowY ];
7175
7176 // Identify a display type, preferring old show/hide data over the CSS cascade
7177 restoreDisplay = dataShow && dataShow.display;
7178 if ( restoreDisplay == null ) {
7179 restoreDisplay = dataPriv.get( elem, "display" );
7180 }
7181 display = jQuery.css( elem, "display" );
7182 if ( display === "none" ) {
7183 if ( restoreDisplay ) {
7184 display = restoreDisplay;
7185 } else {
7186
7187 // Get nonempty value(s) by temporarily forcing visibility
7188 showHide( [ elem ], true );
7189 restoreDisplay = elem.style.display || restoreDisplay;
7190 display = jQuery.css( elem, "display" );
7191 showHide( [ elem ] );
7192 }
7193 }
7194
7195 // Animate inline elements as inline-block
7196 if ( display === "inline" || display === "inline-block" && restoreDisplay != null ) {
7197 if ( jQuery.css( elem, "float" ) === "none" ) {
7198
7199 // Restore the original display value at the end of pure show/hide animations
7200 if ( !propTween ) {
7201 anim.done( function() {
7202 style.display = restoreDisplay;
7203 } );
7204 if ( restoreDisplay == null ) {
7205 display = style.display;
7206 restoreDisplay = display === "none" ? "" : display;
7207 }
7208 }
7209 style.display = "inline-block";
7210 }
7211 }
7212 }
7213
7214 if ( opts.overflow ) {
7215 style.overflow = "hidden";
7216 anim.always( function() {
7217 style.overflow = opts.overflow[ 0 ];
7218 style.overflowX = opts.overflow[ 1 ];
7219 style.overflowY = opts.overflow[ 2 ];
7220 } );
7221 }
7222
7223 // Implement show/hide animations
7224 propTween = false;
7225 for ( prop in orig ) {
7226
7227 // General show/hide setup for this element animation
7228 if ( !propTween ) {
7229 if ( dataShow ) {
7230 if ( "hidden" in dataShow ) {
7231 hidden = dataShow.hidden;
7232 }
7233 } else {
7234 dataShow = dataPriv.access( elem, "fxshow", { display: restoreDisplay } );
7235 }
7236
7237 // Store hidden/visible for toggle so `.stop().toggle()` "reverses"
7238 if ( toggle ) {
7239 dataShow.hidden = !hidden;
7240 }
7241
7242 // Show elements before animating them
7243 if ( hidden ) {
7244 showHide( [ elem ], true );
7245 }
7246
7247 /* eslint-disable no-loop-func */
7248
7249 anim.done( function() {
7250
7251 /* eslint-enable no-loop-func */
7252
7253 // The final step of a "hide" animation is actually hiding the element
7254 if ( !hidden ) {
7255 showHide( [ elem ] );
7256 }
7257 dataPriv.remove( elem, "fxshow" );
7258 for ( prop in orig ) {
7259 jQuery.style( elem, prop, orig[ prop ] );
7260 }
7261 } );
7262 }
7263
7264 // Per-property setup
7265 propTween = createTween( hidden ? dataShow[ prop ] : 0, prop, anim );
7266 if ( !( prop in dataShow ) ) {
7267 dataShow[ prop ] = propTween.start;
7268 if ( hidden ) {
7269 propTween.end = propTween.start;
7270 propTween.start = 0;
7271 }
7272 }
7273 }
7274}
7275
7276function propFilter( props, specialEasing ) {
7277 var index, name, easing, value, hooks;
7278
7279 // camelCase, specialEasing and expand cssHook pass
7280 for ( index in props ) {
7281 name = camelCase( index );
7282 easing = specialEasing[ name ];
7283 value = props[ index ];
7284 if ( Array.isArray( value ) ) {
7285 easing = value[ 1 ];
7286 value = props[ index ] = value[ 0 ];
7287 }
7288
7289 if ( index !== name ) {
7290 props[ name ] = value;
7291 delete props[ index ];
7292 }
7293
7294 hooks = jQuery.cssHooks[ name ];
7295 if ( hooks && "expand" in hooks ) {
7296 value = hooks.expand( value );
7297 delete props[ name ];
7298
7299 // Not quite $.extend, this won't overwrite existing keys.
7300 // Reusing 'index' because we have the correct "name"
7301 for ( index in value ) {
7302 if ( !( index in props ) ) {
7303 props[ index ] = value[ index ];
7304 specialEasing[ index ] = easing;
7305 }
7306 }
7307 } else {
7308 specialEasing[ name ] = easing;
7309 }
7310 }
7311}
7312
7313function Animation( elem, properties, options ) {
7314 var result,
7315 stopped,
7316 index = 0,
7317 length = Animation.prefilters.length,
7318 deferred = jQuery.Deferred().always( function() {
7319
7320 // Don't match elem in the :animated selector
7321 delete tick.elem;
7322 } ),
7323 tick = function() {
7324 if ( stopped ) {
7325 return false;
7326 }
7327 var currentTime = fxNow || createFxNow(),
7328 remaining = Math.max( 0, animation.startTime + animation.duration - currentTime ),
7329
7330 // Support: Android 2.3 only
7331 // Archaic crash bug won't allow us to use `1 - ( 0.5 || 0 )` (#12497)
7332 temp = remaining / animation.duration || 0,
7333 percent = 1 - temp,
7334 index = 0,
7335 length = animation.tweens.length;
7336
7337 for ( ; index < length; index++ ) {
7338 animation.tweens[ index ].run( percent );
7339 }
7340
7341 deferred.notifyWith( elem, [ animation, percent, remaining ] );
7342
7343 // If there's more to do, yield
7344 if ( percent < 1 && length ) {
7345 return remaining;
7346 }
7347
7348 // If this was an empty animation, synthesize a final progress notification
7349 if ( !length ) {
7350 deferred.notifyWith( elem, [ animation, 1, 0 ] );
7351 }
7352
7353 // Resolve the animation and report its conclusion
7354 deferred.resolveWith( elem, [ animation ] );
7355 return false;
7356 },
7357 animation = deferred.promise( {
7358 elem: elem,
7359 props: jQuery.extend( {}, properties ),
7360 opts: jQuery.extend( true, {
7361 specialEasing: {},
7362 easing: jQuery.easing._default
7363 }, options ),
7364 originalProperties: properties,
7365 originalOptions: options,
7366 startTime: fxNow || createFxNow(),
7367 duration: options.duration,
7368 tweens: [],
7369 createTween: function( prop, end ) {
7370 var tween = jQuery.Tween( elem, animation.opts, prop, end,
7371 animation.opts.specialEasing[ prop ] || animation.opts.easing );
7372 animation.tweens.push( tween );
7373 return tween;
7374 },
7375 stop: function( gotoEnd ) {
7376 var index = 0,
7377
7378 // If we are going to the end, we want to run all the tweens
7379 // otherwise we skip this part
7380 length = gotoEnd ? animation.tweens.length : 0;
7381 if ( stopped ) {
7382 return this;
7383 }
7384 stopped = true;
7385 for ( ; index < length; index++ ) {
7386 animation.tweens[ index ].run( 1 );
7387 }
7388
7389 // Resolve when we played the last frame; otherwise, reject
7390 if ( gotoEnd ) {
7391 deferred.notifyWith( elem, [ animation, 1, 0 ] );
7392 deferred.resolveWith( elem, [ animation, gotoEnd ] );
7393 } else {
7394 deferred.rejectWith( elem, [ animation, gotoEnd ] );
7395 }
7396 return this;
7397 }
7398 } ),
7399 props = animation.props;
7400
7401 propFilter( props, animation.opts.specialEasing );
7402
7403 for ( ; index < length; index++ ) {
7404 result = Animation.prefilters[ index ].call( animation, elem, props, animation.opts );
7405 if ( result ) {
7406 if ( isFunction( result.stop ) ) {
7407 jQuery._queueHooks( animation.elem, animation.opts.queue ).stop =
7408 result.stop.bind( result );
7409 }
7410 return result;
7411 }
7412 }
7413
7414 jQuery.map( props, createTween, animation );
7415
7416 if ( isFunction( animation.opts.start ) ) {
7417 animation.opts.start.call( elem, animation );
7418 }
7419
7420 // Attach callbacks from options
7421 animation
7422 .progress( animation.opts.progress )
7423 .done( animation.opts.done, animation.opts.complete )
7424 .fail( animation.opts.fail )
7425 .always( animation.opts.always );
7426
7427 jQuery.fx.timer(
7428 jQuery.extend( tick, {
7429 elem: elem,
7430 anim: animation,
7431 queue: animation.opts.queue
7432 } )
7433 );
7434
7435 return animation;
7436}
7437
7438jQuery.Animation = jQuery.extend( Animation, {
7439
7440 tweeners: {
7441 "*": [ function( prop, value ) {
7442 var tween = this.createTween( prop, value );
7443 adjustCSS( tween.elem, prop, rcssNum.exec( value ), tween );
7444 return tween;
7445 } ]
7446 },
7447
7448 tweener: function( props, callback ) {
7449 if ( isFunction( props ) ) {
7450 callback = props;
7451 props = [ "*" ];
7452 } else {
7453 props = props.match( rnothtmlwhite );
7454 }
7455
7456 var prop,
7457 index = 0,
7458 length = props.length;
7459
7460 for ( ; index < length; index++ ) {
7461 prop = props[ index ];
7462 Animation.tweeners[ prop ] = Animation.tweeners[ prop ] || [];
7463 Animation.tweeners[ prop ].unshift( callback );
7464 }
7465 },
7466
7467 prefilters: [ defaultPrefilter ],
7468
7469 prefilter: function( callback, prepend ) {
7470 if ( prepend ) {
7471 Animation.prefilters.unshift( callback );
7472 } else {
7473 Animation.prefilters.push( callback );
7474 }
7475 }
7476} );
7477
7478jQuery.speed = function( speed, easing, fn ) {
7479 var opt = speed && typeof speed === "object" ? jQuery.extend( {}, speed ) : {
7480 complete: fn || !fn && easing ||
7481 isFunction( speed ) && speed,
7482 duration: speed,
7483 easing: fn && easing || easing && !isFunction( easing ) && easing
7484 };
7485
7486 // Go to the end state if fx are off
7487 if ( jQuery.fx.off ) {
7488 opt.duration = 0;
7489
7490 } else {
7491 if ( typeof opt.duration !== "number" ) {
7492 if ( opt.duration in jQuery.fx.speeds ) {
7493 opt.duration = jQuery.fx.speeds[ opt.duration ];
7494
7495 } else {
7496 opt.duration = jQuery.fx.speeds._default;
7497 }
7498 }
7499 }
7500
7501 // Normalize opt.queue - true/undefined/null -> "fx"
7502 if ( opt.queue == null || opt.queue === true ) {
7503 opt.queue = "fx";
7504 }
7505
7506 // Queueing
7507 opt.old = opt.complete;
7508
7509 opt.complete = function() {
7510 if ( isFunction( opt.old ) ) {
7511 opt.old.call( this );
7512 }
7513
7514 if ( opt.queue ) {
7515 jQuery.dequeue( this, opt.queue );
7516 }
7517 };
7518
7519 return opt;
7520};
7521
7522jQuery.fn.extend( {
7523 fadeTo: function( speed, to, easing, callback ) {
7524
7525 // Show any hidden elements after setting opacity to 0
7526 return this.filter( isHiddenWithinTree ).css( "opacity", 0 ).show()
7527
7528 // Animate to the value specified
7529 .end().animate( { opacity: to }, speed, easing, callback );
7530 },
7531 animate: function( prop, speed, easing, callback ) {
7532 var empty = jQuery.isEmptyObject( prop ),
7533 optall = jQuery.speed( speed, easing, callback ),
7534 doAnimation = function() {
7535
7536 // Operate on a copy of prop so per-property easing won't be lost
7537 var anim = Animation( this, jQuery.extend( {}, prop ), optall );
7538
7539 // Empty animations, or finishing resolves immediately
7540 if ( empty || dataPriv.get( this, "finish" ) ) {
7541 anim.stop( true );
7542 }
7543 };
7544 doAnimation.finish = doAnimation;
7545
7546 return empty || optall.queue === false ?
7547 this.each( doAnimation ) :
7548 this.queue( optall.queue, doAnimation );
7549 },
7550 stop: function( type, clearQueue, gotoEnd ) {
7551 var stopQueue = function( hooks ) {
7552 var stop = hooks.stop;
7553 delete hooks.stop;
7554 stop( gotoEnd );
7555 };
7556
7557 if ( typeof type !== "string" ) {
7558 gotoEnd = clearQueue;
7559 clearQueue = type;
7560 type = undefined;
7561 }
7562 if ( clearQueue && type !== false ) {
7563 this.queue( type || "fx", [] );
7564 }
7565
7566 return this.each( function() {
7567 var dequeue = true,
7568 index = type != null && type + "queueHooks",
7569 timers = jQuery.timers,
7570 data = dataPriv.get( this );
7571
7572 if ( index ) {
7573 if ( data[ index ] && data[ index ].stop ) {
7574 stopQueue( data[ index ] );
7575 }
7576 } else {
7577 for ( index in data ) {
7578 if ( data[ index ] && data[ index ].stop && rrun.test( index ) ) {
7579 stopQueue( data[ index ] );
7580 }
7581 }
7582 }
7583
7584 for ( index = timers.length; index--; ) {
7585 if ( timers[ index ].elem === this &&
7586 ( type == null || timers[ index ].queue === type ) ) {
7587
7588 timers[ index ].anim.stop( gotoEnd );
7589 dequeue = false;
7590 timers.splice( index, 1 );
7591 }
7592 }
7593
7594 // Start the next in the queue if the last step wasn't forced.
7595 // Timers currently will call their complete callbacks, which
7596 // will dequeue but only if they were gotoEnd.
7597 if ( dequeue || !gotoEnd ) {
7598 jQuery.dequeue( this, type );
7599 }
7600 } );
7601 },
7602 finish: function( type ) {
7603 if ( type !== false ) {
7604 type = type || "fx";
7605 }
7606 return this.each( function() {
7607 var index,
7608 data = dataPriv.get( this ),
7609 queue = data[ type + "queue" ],
7610 hooks = data[ type + "queueHooks" ],
7611 timers = jQuery.timers,
7612 length = queue ? queue.length : 0;
7613
7614 // Enable finishing flag on private data
7615 data.finish = true;
7616
7617 // Empty the queue first
7618 jQuery.queue( this, type, [] );
7619
7620 if ( hooks && hooks.stop ) {
7621 hooks.stop.call( this, true );
7622 }
7623
7624 // Look for any active animations, and finish them
7625 for ( index = timers.length; index--; ) {
7626 if ( timers[ index ].elem === this && timers[ index ].queue === type ) {
7627 timers[ index ].anim.stop( true );
7628 timers.splice( index, 1 );
7629 }
7630 }
7631
7632 // Look for any animations in the old queue and finish them
7633 for ( index = 0; index < length; index++ ) {
7634 if ( queue[ index ] && queue[ index ].finish ) {
7635 queue[ index ].finish.call( this );
7636 }
7637 }
7638
7639 // Turn off finishing flag
7640 delete data.finish;
7641 } );
7642 }
7643} );
7644
7645jQuery.each( [ "toggle", "show", "hide" ], function( i, name ) {
7646 var cssFn = jQuery.fn[ name ];
7647 jQuery.fn[ name ] = function( speed, easing, callback ) {
7648 return speed == null || typeof speed === "boolean" ?
7649 cssFn.apply( this, arguments ) :
7650 this.animate( genFx( name, true ), speed, easing, callback );
7651 };
7652} );
7653
7654// Generate shortcuts for custom animations
7655jQuery.each( {
7656 slideDown: genFx( "show" ),
7657 slideUp: genFx( "hide" ),
7658 slideToggle: genFx( "toggle" ),
7659 fadeIn: { opacity: "show" },
7660 fadeOut: { opacity: "hide" },
7661 fadeToggle: { opacity: "toggle" }
7662}, function( name, props ) {
7663 jQuery.fn[ name ] = function( speed, easing, callback ) {
7664 return this.animate( props, speed, easing, callback );
7665 };
7666} );
7667
7668jQuery.timers = [];
7669jQuery.fx.tick = function() {
7670 var timer,
7671 i = 0,
7672 timers = jQuery.timers;
7673
7674 fxNow = Date.now();
7675
7676 for ( ; i < timers.length; i++ ) {
7677 timer = timers[ i ];
7678
7679 // Run the timer and safely remove it when done (allowing for external removal)
7680 if ( !timer() && timers[ i ] === timer ) {
7681 timers.splice( i--, 1 );
7682 }
7683 }
7684
7685 if ( !timers.length ) {
7686 jQuery.fx.stop();
7687 }
7688 fxNow = undefined;
7689};
7690
7691jQuery.fx.timer = function( timer ) {
7692 jQuery.timers.push( timer );
7693 jQuery.fx.start();
7694};
7695
7696jQuery.fx.interval = 13;
7697jQuery.fx.start = function() {
7698 if ( inProgress ) {
7699 return;
7700 }
7701
7702 inProgress = true;
7703 schedule();
7704};
7705
7706jQuery.fx.stop = function() {
7707 inProgress = null;
7708};
7709
7710jQuery.fx.speeds = {
7711 slow: 600,
7712 fast: 200,
7713
7714 // Default speed
7715 _default: 400
7716};
7717
7718
7719// Based off of the plugin by Clint Helfers, with permission.
7720// https://web.archive.org/web/20100324014747/http://blindsignals.com/index.php/2009/07/jquery-delay/
7721jQuery.fn.delay = function( time, type ) {
7722 time = jQuery.fx ? jQuery.fx.speeds[ time ] || time : time;
7723 type = type || "fx";
7724
7725 return this.queue( type, function( next, hooks ) {
7726 var timeout = window.setTimeout( next, time );
7727 hooks.stop = function() {
7728 window.clearTimeout( timeout );
7729 };
7730 } );
7731};
7732
7733
7734( function() {
7735 var input = document.createElement( "input" ),
7736 select = document.createElement( "select" ),
7737 opt = select.appendChild( document.createElement( "option" ) );
7738
7739 input.type = "checkbox";
7740
7741 // Support: Android <=4.3 only
7742 // Default value for a checkbox should be "on"
7743 support.checkOn = input.value !== "";
7744
7745 // Support: IE <=11 only
7746 // Must access selectedIndex to make default options select
7747 support.optSelected = opt.selected;
7748
7749 // Support: IE <=11 only
7750 // An input loses its value after becoming a radio
7751 input = document.createElement( "input" );
7752 input.value = "t";
7753 input.type = "radio";
7754 support.radioValue = input.value === "t";
7755} )();
7756
7757
7758var boolHook,
7759 attrHandle = jQuery.expr.attrHandle;
7760
7761jQuery.fn.extend( {
7762 attr: function( name, value ) {
7763 return access( this, jQuery.attr, name, value, arguments.length > 1 );
7764 },
7765
7766 removeAttr: function( name ) {
7767 return this.each( function() {
7768 jQuery.removeAttr( this, name );
7769 } );
7770 }
7771} );
7772
7773jQuery.extend( {
7774 attr: function( elem, name, value ) {
7775 var ret, hooks,
7776 nType = elem.nodeType;
7777
7778 // Don't get/set attributes on text, comment and attribute nodes
7779 if ( nType === 3 || nType === 8 || nType === 2 ) {
7780 return;
7781 }
7782
7783 // Fallback to prop when attributes are not supported
7784 if ( typeof elem.getAttribute === "undefined" ) {
7785 return jQuery.prop( elem, name, value );
7786 }
7787
7788 // Attribute hooks are determined by the lowercase version
7789 // Grab necessary hook if one is defined
7790 if ( nType !== 1 || !jQuery.isXMLDoc( elem ) ) {
7791 hooks = jQuery.attrHooks[ name.toLowerCase() ] ||
7792 ( jQuery.expr.match.bool.test( name ) ? boolHook : undefined );
7793 }
7794
7795 if ( value !== undefined ) {
7796 if ( value === null ) {
7797 jQuery.removeAttr( elem, name );
7798 return;
7799 }
7800
7801 if ( hooks && "set" in hooks &&
7802 ( ret = hooks.set( elem, value, name ) ) !== undefined ) {
7803 return ret;
7804 }
7805
7806 elem.setAttribute( name, value + "" );
7807 return value;
7808 }
7809
7810 if ( hooks && "get" in hooks && ( ret = hooks.get( elem, name ) ) !== null ) {
7811 return ret;
7812 }
7813
7814 ret = jQuery.find.attr( elem, name );
7815
7816 // Non-existent attributes return null, we normalize to undefined
7817 return ret == null ? undefined : ret;
7818 },
7819
7820 attrHooks: {
7821 type: {
7822 set: function( elem, value ) {
7823 if ( !support.radioValue && value === "radio" &&
7824 nodeName( elem, "input" ) ) {
7825 var val = elem.value;
7826 elem.setAttribute( "type", value );
7827 if ( val ) {
7828 elem.value = val;
7829 }
7830 return value;
7831 }
7832 }
7833 }
7834 },
7835
7836 removeAttr: function( elem, value ) {
7837 var name,
7838 i = 0,
7839
7840 // Attribute names can contain non-HTML whitespace characters
7841 // https://html.spec.whatwg.org/multipage/syntax.html#attributes-2
7842 attrNames = value && value.match( rnothtmlwhite );
7843
7844 if ( attrNames && elem.nodeType === 1 ) {
7845 while ( ( name = attrNames[ i++ ] ) ) {
7846 elem.removeAttribute( name );
7847 }
7848 }
7849 }
7850} );
7851
7852// Hooks for boolean attributes
7853boolHook = {
7854 set: function( elem, value, name ) {
7855 if ( value === false ) {
7856
7857 // Remove boolean attributes when set to false
7858 jQuery.removeAttr( elem, name );
7859 } else {
7860 elem.setAttribute( name, name );
7861 }
7862 return name;
7863 }
7864};
7865
7866jQuery.each( jQuery.expr.match.bool.source.match( /\w+/g ), function( i, name ) {
7867 var getter = attrHandle[ name ] || jQuery.find.attr;
7868
7869 attrHandle[ name ] = function( elem, name, isXML ) {
7870 var ret, handle,
7871 lowercaseName = name.toLowerCase();
7872
7873 if ( !isXML ) {
7874
7875 // Avoid an infinite loop by temporarily removing this function from the getter
7876 handle = attrHandle[ lowercaseName ];
7877 attrHandle[ lowercaseName ] = ret;
7878 ret = getter( elem, name, isXML ) != null ?
7879 lowercaseName :
7880 null;
7881 attrHandle[ lowercaseName ] = handle;
7882 }
7883 return ret;
7884 };
7885} );
7886
7887
7888
7889
7890var rfocusable = /^(?:input|select|textarea|button)$/i,
7891 rclickable = /^(?:a|area)$/i;
7892
7893jQuery.fn.extend( {
7894 prop: function( name, value ) {
7895 return access( this, jQuery.prop, name, value, arguments.length > 1 );
7896 },
7897
7898 removeProp: function( name ) {
7899 return this.each( function() {
7900 delete this[ jQuery.propFix[ name ] || name ];
7901 } );
7902 }
7903} );
7904
7905jQuery.extend( {
7906 prop: function( elem, name, value ) {
7907 var ret, hooks,
7908 nType = elem.nodeType;
7909
7910 // Don't get/set properties on text, comment and attribute nodes
7911 if ( nType === 3 || nType === 8 || nType === 2 ) {
7912 return;
7913 }
7914
7915 if ( nType !== 1 || !jQuery.isXMLDoc( elem ) ) {
7916
7917 // Fix name and attach hooks
7918 name = jQuery.propFix[ name ] || name;
7919 hooks = jQuery.propHooks[ name ];
7920 }
7921
7922 if ( value !== undefined ) {
7923 if ( hooks && "set" in hooks &&
7924 ( ret = hooks.set( elem, value, name ) ) !== undefined ) {
7925 return ret;
7926 }
7927
7928 return ( elem[ name ] = value );
7929 }
7930
7931 if ( hooks && "get" in hooks && ( ret = hooks.get( elem, name ) ) !== null ) {
7932 return ret;
7933 }
7934
7935 return elem[ name ];
7936 },
7937
7938 propHooks: {
7939 tabIndex: {
7940 get: function( elem ) {
7941
7942 // Support: IE <=9 - 11 only
7943 // elem.tabIndex doesn't always return the
7944 // correct value when it hasn't been explicitly set
7945 // https://web.archive.org/web/20141116233347/http://fluidproject.org/blog/2008/01/09/getting-setting-and-removing-tabindex-values-with-javascript/
7946 // Use proper attribute retrieval(#12072)
7947 var tabindex = jQuery.find.attr( elem, "tabindex" );
7948
7949 if ( tabindex ) {
7950 return parseInt( tabindex, 10 );
7951 }
7952
7953 if (
7954 rfocusable.test( elem.nodeName ) ||
7955 rclickable.test( elem.nodeName ) &&
7956 elem.href
7957 ) {
7958 return 0;
7959 }
7960
7961 return -1;
7962 }
7963 }
7964 },
7965
7966 propFix: {
7967 "for": "htmlFor",
7968 "class": "className"
7969 }
7970} );
7971
7972// Support: IE <=11 only
7973// Accessing the selectedIndex property
7974// forces the browser to respect setting selected
7975// on the option
7976// The getter ensures a default option is selected
7977// when in an optgroup
7978// eslint rule "no-unused-expressions" is disabled for this code
7979// since it considers such accessions noop
7980if ( !support.optSelected ) {
7981 jQuery.propHooks.selected = {
7982 get: function( elem ) {
7983
7984 /* eslint no-unused-expressions: "off" */
7985
7986 var parent = elem.parentNode;
7987 if ( parent && parent.parentNode ) {
7988 parent.parentNode.selectedIndex;
7989 }
7990 return null;
7991 },
7992 set: function( elem ) {
7993
7994 /* eslint no-unused-expressions: "off" */
7995
7996 var parent = elem.parentNode;
7997 if ( parent ) {
7998 parent.selectedIndex;
7999
8000 if ( parent.parentNode ) {
8001 parent.parentNode.selectedIndex;
8002 }
8003 }
8004 }
8005 };
8006}
8007
8008jQuery.each( [
8009 "tabIndex",
8010 "readOnly",
8011 "maxLength",
8012 "cellSpacing",
8013 "cellPadding",
8014 "rowSpan",
8015 "colSpan",
8016 "useMap",
8017 "frameBorder",
8018 "contentEditable"
8019], function() {
8020 jQuery.propFix[ this.toLowerCase() ] = this;
8021} );
8022
8023
8024
8025
8026 // Strip and collapse whitespace according to HTML spec
8027 // https://infra.spec.whatwg.org/#strip-and-collapse-ascii-whitespace
8028 function stripAndCollapse( value ) {
8029 var tokens = value.match( rnothtmlwhite ) || [];
8030 return tokens.join( " " );
8031 }
8032
8033
8034function getClass( elem ) {
8035 return elem.getAttribute && elem.getAttribute( "class" ) || "";
8036}
8037
8038function classesToArray( value ) {
8039 if ( Array.isArray( value ) ) {
8040 return value;
8041 }
8042 if ( typeof value === "string" ) {
8043 return value.match( rnothtmlwhite ) || [];
8044 }
8045 return [];
8046}
8047
8048jQuery.fn.extend( {
8049 addClass: function( value ) {
8050 var classes, elem, cur, curValue, clazz, j, finalValue,
8051 i = 0;
8052
8053 if ( isFunction( value ) ) {
8054 return this.each( function( j ) {
8055 jQuery( this ).addClass( value.call( this, j, getClass( this ) ) );
8056 } );
8057 }
8058
8059 classes = classesToArray( value );
8060
8061 if ( classes.length ) {
8062 while ( ( elem = this[ i++ ] ) ) {
8063 curValue = getClass( elem );
8064 cur = elem.nodeType === 1 && ( " " + stripAndCollapse( curValue ) + " " );
8065
8066 if ( cur ) {
8067 j = 0;
8068 while ( ( clazz = classes[ j++ ] ) ) {
8069 if ( cur.indexOf( " " + clazz + " " ) < 0 ) {
8070 cur += clazz + " ";
8071 }
8072 }
8073
8074 // Only assign if different to avoid unneeded rendering.
8075 finalValue = stripAndCollapse( cur );
8076 if ( curValue !== finalValue ) {
8077 elem.setAttribute( "class", finalValue );
8078 }
8079 }
8080 }
8081 }
8082
8083 return this;
8084 },
8085
8086 removeClass: function( value ) {
8087 var classes, elem, cur, curValue, clazz, j, finalValue,
8088 i = 0;
8089
8090 if ( isFunction( value ) ) {
8091 return this.each( function( j ) {
8092 jQuery( this ).removeClass( value.call( this, j, getClass( this ) ) );
8093 } );
8094 }
8095
8096 if ( !arguments.length ) {
8097 return this.attr( "class", "" );
8098 }
8099
8100 classes = classesToArray( value );
8101
8102 if ( classes.length ) {
8103 while ( ( elem = this[ i++ ] ) ) {
8104 curValue = getClass( elem );
8105
8106 // This expression is here for better compressibility (see addClass)
8107 cur = elem.nodeType === 1 && ( " " + stripAndCollapse( curValue ) + " " );
8108
8109 if ( cur ) {
8110 j = 0;
8111 while ( ( clazz = classes[ j++ ] ) ) {
8112
8113 // Remove *all* instances
8114 while ( cur.indexOf( " " + clazz + " " ) > -1 ) {
8115 cur = cur.replace( " " + clazz + " ", " " );
8116 }
8117 }
8118
8119 // Only assign if different to avoid unneeded rendering.
8120 finalValue = stripAndCollapse( cur );
8121 if ( curValue !== finalValue ) {
8122 elem.setAttribute( "class", finalValue );
8123 }
8124 }
8125 }
8126 }
8127
8128 return this;
8129 },
8130
8131 toggleClass: function( value, stateVal ) {
8132 var type = typeof value,
8133 isValidValue = type === "string" || Array.isArray( value );
8134
8135 if ( typeof stateVal === "boolean" && isValidValue ) {
8136 return stateVal ? this.addClass( value ) : this.removeClass( value );
8137 }
8138
8139 if ( isFunction( value ) ) {
8140 return this.each( function( i ) {
8141 jQuery( this ).toggleClass(
8142 value.call( this, i, getClass( this ), stateVal ),
8143 stateVal
8144 );
8145 } );
8146 }
8147
8148 return this.each( function() {
8149 var className, i, self, classNames;
8150
8151 if ( isValidValue ) {
8152
8153 // Toggle individual class names
8154 i = 0;
8155 self = jQuery( this );
8156 classNames = classesToArray( value );
8157
8158 while ( ( className = classNames[ i++ ] ) ) {
8159
8160 // Check each className given, space separated list
8161 if ( self.hasClass( className ) ) {
8162 self.removeClass( className );
8163 } else {
8164 self.addClass( className );
8165 }
8166 }
8167
8168 // Toggle whole class name
8169 } else if ( value === undefined || type === "boolean" ) {
8170 className = getClass( this );
8171 if ( className ) {
8172
8173 // Store className if set
8174 dataPriv.set( this, "__className__", className );
8175 }
8176
8177 // If the element has a class name or if we're passed `false`,
8178 // then remove the whole classname (if there was one, the above saved it).
8179 // Otherwise bring back whatever was previously saved (if anything),
8180 // falling back to the empty string if nothing was stored.
8181 if ( this.setAttribute ) {
8182 this.setAttribute( "class",
8183 className || value === false ?
8184 "" :
8185 dataPriv.get( this, "__className__" ) || ""
8186 );
8187 }
8188 }
8189 } );
8190 },
8191
8192 hasClass: function( selector ) {
8193 var className, elem,
8194 i = 0;
8195
8196 className = " " + selector + " ";
8197 while ( ( elem = this[ i++ ] ) ) {
8198 if ( elem.nodeType === 1 &&
8199 ( " " + stripAndCollapse( getClass( elem ) ) + " " ).indexOf( className ) > -1 ) {
8200 return true;
8201 }
8202 }
8203
8204 return false;
8205 }
8206} );
8207
8208
8209
8210
8211var rreturn = /\r/g;
8212
8213jQuery.fn.extend( {
8214 val: function( value ) {
8215 var hooks, ret, valueIsFunction,
8216 elem = this[ 0 ];
8217
8218 if ( !arguments.length ) {
8219 if ( elem ) {
8220 hooks = jQuery.valHooks[ elem.type ] ||
8221 jQuery.valHooks[ elem.nodeName.toLowerCase() ];
8222
8223 if ( hooks &&
8224 "get" in hooks &&
8225 ( ret = hooks.get( elem, "value" ) ) !== undefined
8226 ) {
8227 return ret;
8228 }
8229
8230 ret = elem.value;
8231
8232 // Handle most common string cases
8233 if ( typeof ret === "string" ) {
8234 return ret.replace( rreturn, "" );
8235 }
8236
8237 // Handle cases where value is null/undef or number
8238 return ret == null ? "" : ret;
8239 }
8240
8241 return;
8242 }
8243
8244 valueIsFunction = isFunction( value );
8245
8246 return this.each( function( i ) {
8247 var val;
8248
8249 if ( this.nodeType !== 1 ) {
8250 return;
8251 }
8252
8253 if ( valueIsFunction ) {
8254 val = value.call( this, i, jQuery( this ).val() );
8255 } else {
8256 val = value;
8257 }
8258
8259 // Treat null/undefined as ""; convert numbers to string
8260 if ( val == null ) {
8261 val = "";
8262
8263 } else if ( typeof val === "number" ) {
8264 val += "";
8265
8266 } else if ( Array.isArray( val ) ) {
8267 val = jQuery.map( val, function( value ) {
8268 return value == null ? "" : value + "";
8269 } );
8270 }
8271
8272 hooks = jQuery.valHooks[ this.type ] || jQuery.valHooks[ this.nodeName.toLowerCase() ];
8273
8274 // If set returns undefined, fall back to normal setting
8275 if ( !hooks || !( "set" in hooks ) || hooks.set( this, val, "value" ) === undefined ) {
8276 this.value = val;
8277 }
8278 } );
8279 }
8280} );
8281
8282jQuery.extend( {
8283 valHooks: {
8284 option: {
8285 get: function( elem ) {
8286
8287 var val = jQuery.find.attr( elem, "value" );
8288 return val != null ?
8289 val :
8290
8291 // Support: IE <=10 - 11 only
8292 // option.text throws exceptions (#14686, #14858)
8293 // Strip and collapse whitespace
8294 // https://html.spec.whatwg.org/#strip-and-collapse-whitespace
8295 stripAndCollapse( jQuery.text( elem ) );
8296 }
8297 },
8298 select: {
8299 get: function( elem ) {
8300 var value, option, i,
8301 options = elem.options,
8302 index = elem.selectedIndex,
8303 one = elem.type === "select-one",
8304 values = one ? null : [],
8305 max = one ? index + 1 : options.length;
8306
8307 if ( index < 0 ) {
8308 i = max;
8309
8310 } else {
8311 i = one ? index : 0;
8312 }
8313
8314 // Loop through all the selected options
8315 for ( ; i < max; i++ ) {
8316 option = options[ i ];
8317
8318 // Support: IE <=9 only
8319 // IE8-9 doesn't update selected after form reset (#2551)
8320 if ( ( option.selected || i === index ) &&
8321
8322 // Don't return options that are disabled or in a disabled optgroup
8323 !option.disabled &&
8324 ( !option.parentNode.disabled ||
8325 !nodeName( option.parentNode, "optgroup" ) ) ) {
8326
8327 // Get the specific value for the option
8328 value = jQuery( option ).val();
8329
8330 // We don't need an array for one selects
8331 if ( one ) {
8332 return value;
8333 }
8334
8335 // Multi-Selects return an array
8336 values.push( value );
8337 }
8338 }
8339
8340 return values;
8341 },
8342
8343 set: function( elem, value ) {
8344 var optionSet, option,
8345 options = elem.options,
8346 values = jQuery.makeArray( value ),
8347 i = options.length;
8348
8349 while ( i-- ) {
8350 option = options[ i ];
8351
8352 /* eslint-disable no-cond-assign */
8353
8354 if ( option.selected =
8355 jQuery.inArray( jQuery.valHooks.option.get( option ), values ) > -1
8356 ) {
8357 optionSet = true;
8358 }
8359
8360 /* eslint-enable no-cond-assign */
8361 }
8362
8363 // Force browsers to behave consistently when non-matching value is set
8364 if ( !optionSet ) {
8365 elem.selectedIndex = -1;
8366 }
8367 return values;
8368 }
8369 }
8370 }
8371} );
8372
8373// Radios and checkboxes getter/setter
8374jQuery.each( [ "radio", "checkbox" ], function() {
8375 jQuery.valHooks[ this ] = {
8376 set: function( elem, value ) {
8377 if ( Array.isArray( value ) ) {
8378 return ( elem.checked = jQuery.inArray( jQuery( elem ).val(), value ) > -1 );
8379 }
8380 }
8381 };
8382 if ( !support.checkOn ) {
8383 jQuery.valHooks[ this ].get = function( elem ) {
8384 return elem.getAttribute( "value" ) === null ? "on" : elem.value;
8385 };
8386 }
8387} );
8388
8389
8390
8391
8392// Return jQuery for attributes-only inclusion
8393
8394
8395support.focusin = "onfocusin" in window;
8396
8397
8398var rfocusMorph = /^(?:focusinfocus|focusoutblur)$/,
8399 stopPropagationCallback = function( e ) {
8400 e.stopPropagation();
8401 };
8402
8403jQuery.extend( jQuery.event, {
8404
8405 trigger: function( event, data, elem, onlyHandlers ) {
8406
8407 var i, cur, tmp, bubbleType, ontype, handle, special, lastElement,
8408 eventPath = [ elem || document ],
8409 type = hasOwn.call( event, "type" ) ? event.type : event,
8410 namespaces = hasOwn.call( event, "namespace" ) ? event.namespace.split( "." ) : [];
8411
8412 cur = lastElement = tmp = elem = elem || document;
8413
8414 // Don't do events on text and comment nodes
8415 if ( elem.nodeType === 3 || elem.nodeType === 8 ) {
8416 return;
8417 }
8418
8419 // focus/blur morphs to focusin/out; ensure we're not firing them right now
8420 if ( rfocusMorph.test( type + jQuery.event.triggered ) ) {
8421 return;
8422 }
8423
8424 if ( type.indexOf( "." ) > -1 ) {
8425
8426 // Namespaced trigger; create a regexp to match event type in handle()
8427 namespaces = type.split( "." );
8428 type = namespaces.shift();
8429 namespaces.sort();
8430 }
8431 ontype = type.indexOf( ":" ) < 0 && "on" + type;
8432
8433 // Caller can pass in a jQuery.Event object, Object, or just an event type string
8434 event = event[ jQuery.expando ] ?
8435 event :
8436 new jQuery.Event( type, typeof event === "object" && event );
8437
8438 // Trigger bitmask: & 1 for native handlers; & 2 for jQuery (always true)
8439 event.isTrigger = onlyHandlers ? 2 : 3;
8440 event.namespace = namespaces.join( "." );
8441 event.rnamespace = event.namespace ?
8442 new RegExp( "(^|\\.)" + namespaces.join( "\\.(?:.*\\.|)" ) + "(\\.|$)" ) :
8443 null;
8444
8445 // Clean up the event in case it is being reused
8446 event.result = undefined;
8447 if ( !event.target ) {
8448 event.target = elem;
8449 }
8450
8451 // Clone any incoming data and prepend the event, creating the handler arg list
8452 data = data == null ?
8453 [ event ] :
8454 jQuery.makeArray( data, [ event ] );
8455
8456 // Allow special events to draw outside the lines
8457 special = jQuery.event.special[ type ] || {};
8458 if ( !onlyHandlers && special.trigger && special.trigger.apply( elem, data ) === false ) {
8459 return;
8460 }
8461
8462 // Determine event propagation path in advance, per W3C events spec (#9951)
8463 // Bubble up to document, then to window; watch for a global ownerDocument var (#9724)
8464 if ( !onlyHandlers && !special.noBubble && !isWindow( elem ) ) {
8465
8466 bubbleType = special.delegateType || type;
8467 if ( !rfocusMorph.test( bubbleType + type ) ) {
8468 cur = cur.parentNode;
8469 }
8470 for ( ; cur; cur = cur.parentNode ) {
8471 eventPath.push( cur );
8472 tmp = cur;
8473 }
8474
8475 // Only add window if we got to document (e.g., not plain obj or detached DOM)
8476 if ( tmp === ( elem.ownerDocument || document ) ) {
8477 eventPath.push( tmp.defaultView || tmp.parentWindow || window );
8478 }
8479 }
8480
8481 // Fire handlers on the event path
8482 i = 0;
8483 while ( ( cur = eventPath[ i++ ] ) && !event.isPropagationStopped() ) {
8484 lastElement = cur;
8485 event.type = i > 1 ?
8486 bubbleType :
8487 special.bindType || type;
8488
8489 // jQuery handler
8490 handle = ( dataPriv.get( cur, "events" ) || {} )[ event.type ] &&
8491 dataPriv.get( cur, "handle" );
8492 if ( handle ) {
8493 handle.apply( cur, data );
8494 }
8495
8496 // Native handler
8497 handle = ontype && cur[ ontype ];
8498 if ( handle && handle.apply && acceptData( cur ) ) {
8499 event.result = handle.apply( cur, data );
8500 if ( event.result === false ) {
8501 event.preventDefault();
8502 }
8503 }
8504 }
8505 event.type = type;
8506
8507 // If nobody prevented the default action, do it now
8508 if ( !onlyHandlers && !event.isDefaultPrevented() ) {
8509
8510 if ( ( !special._default ||
8511 special._default.apply( eventPath.pop(), data ) === false ) &&
8512 acceptData( elem ) ) {
8513
8514 // Call a native DOM method on the target with the same name as the event.
8515 // Don't do default actions on window, that's where global variables be (#6170)
8516 if ( ontype && isFunction( elem[ type ] ) && !isWindow( elem ) ) {
8517
8518 // Don't re-trigger an onFOO event when we call its FOO() method
8519 tmp = elem[ ontype ];
8520
8521 if ( tmp ) {
8522 elem[ ontype ] = null;
8523 }
8524
8525 // Prevent re-triggering of the same event, since we already bubbled it above
8526 jQuery.event.triggered = type;
8527
8528 if ( event.isPropagationStopped() ) {
8529 lastElement.addEventListener( type, stopPropagationCallback );
8530 }
8531
8532 elem[ type ]();
8533
8534 if ( event.isPropagationStopped() ) {
8535 lastElement.removeEventListener( type, stopPropagationCallback );
8536 }
8537
8538 jQuery.event.triggered = undefined;
8539
8540 if ( tmp ) {
8541 elem[ ontype ] = tmp;
8542 }
8543 }
8544 }
8545 }
8546
8547 return event.result;
8548 },
8549
8550 // Piggyback on a donor event to simulate a different one
8551 // Used only for `focus(in | out)` events
8552 simulate: function( type, elem, event ) {
8553 var e = jQuery.extend(
8554 new jQuery.Event(),
8555 event,
8556 {
8557 type: type,
8558 isSimulated: true
8559 }
8560 );
8561
8562 jQuery.event.trigger( e, null, elem );
8563 }
8564
8565} );
8566
8567jQuery.fn.extend( {
8568
8569 trigger: function( type, data ) {
8570 return this.each( function() {
8571 jQuery.event.trigger( type, data, this );
8572 } );
8573 },
8574 triggerHandler: function( type, data ) {
8575 var elem = this[ 0 ];
8576 if ( elem ) {
8577 return jQuery.event.trigger( type, data, elem, true );
8578 }
8579 }
8580} );
8581
8582
8583// Support: Firefox <=44
8584// Firefox doesn't have focus(in | out) events
8585// Related ticket - https://bugzilla.mozilla.org/show_bug.cgi?id=687787
8586//
8587// Support: Chrome <=48 - 49, Safari <=9.0 - 9.1
8588// focus(in | out) events fire after focus & blur events,
8589// which is spec violation - http://www.w3.org/TR/DOM-Level-3-Events/#events-focusevent-event-order
8590// Related ticket - https://bugs.chromium.org/p/chromium/issues/detail?id=449857
8591if ( !support.focusin ) {
8592 jQuery.each( { focus: "focusin", blur: "focusout" }, function( orig, fix ) {
8593
8594 // Attach a single capturing handler on the document while someone wants focusin/focusout
8595 var handler = function( event ) {
8596 jQuery.event.simulate( fix, event.target, jQuery.event.fix( event ) );
8597 };
8598
8599 jQuery.event.special[ fix ] = {
8600 setup: function() {
8601 var doc = this.ownerDocument || this,
8602 attaches = dataPriv.access( doc, fix );
8603
8604 if ( !attaches ) {
8605 doc.addEventListener( orig, handler, true );
8606 }
8607 dataPriv.access( doc, fix, ( attaches || 0 ) + 1 );
8608 },
8609 teardown: function() {
8610 var doc = this.ownerDocument || this,
8611 attaches = dataPriv.access( doc, fix ) - 1;
8612
8613 if ( !attaches ) {
8614 doc.removeEventListener( orig, handler, true );
8615 dataPriv.remove( doc, fix );
8616
8617 } else {
8618 dataPriv.access( doc, fix, attaches );
8619 }
8620 }
8621 };
8622 } );
8623}
8624var location = window.location;
8625
8626var nonce = Date.now();
8627
8628var rquery = ( /\?/ );
8629
8630
8631
8632// Cross-browser xml parsing
8633jQuery.parseXML = function( data ) {
8634 var xml;
8635 if ( !data || typeof data !== "string" ) {
8636 return null;
8637 }
8638
8639 // Support: IE 9 - 11 only
8640 // IE throws on parseFromString with invalid input.
8641 try {
8642 xml = ( new window.DOMParser() ).parseFromString( data, "text/xml" );
8643 } catch ( e ) {
8644 xml = undefined;
8645 }
8646
8647 if ( !xml || xml.getElementsByTagName( "parsererror" ).length ) {
8648 jQuery.error( "Invalid XML: " + data );
8649 }
8650 return xml;
8651};
8652
8653
8654var
8655 rbracket = /\[\]$/,
8656 rCRLF = /\r?\n/g,
8657 rsubmitterTypes = /^(?:submit|button|image|reset|file)$/i,
8658 rsubmittable = /^(?:input|select|textarea|keygen)/i;
8659
8660function buildParams( prefix, obj, traditional, add ) {
8661 var name;
8662
8663 if ( Array.isArray( obj ) ) {
8664
8665 // Serialize array item.
8666 jQuery.each( obj, function( i, v ) {
8667 if ( traditional || rbracket.test( prefix ) ) {
8668
8669 // Treat each array item as a scalar.
8670 add( prefix, v );
8671
8672 } else {
8673
8674 // Item is non-scalar (array or object), encode its numeric index.
8675 buildParams(
8676 prefix + "[" + ( typeof v === "object" && v != null ? i : "" ) + "]",
8677 v,
8678 traditional,
8679 add
8680 );
8681 }
8682 } );
8683
8684 } else if ( !traditional && toType( obj ) === "object" ) {
8685
8686 // Serialize object item.
8687 for ( name in obj ) {
8688 buildParams( prefix + "[" + name + "]", obj[ name ], traditional, add );
8689 }
8690
8691 } else {
8692
8693 // Serialize scalar item.
8694 add( prefix, obj );
8695 }
8696}
8697
8698// Serialize an array of form elements or a set of
8699// key/values into a query string
8700jQuery.param = function( a, traditional ) {
8701 var prefix,
8702 s = [],
8703 add = function( key, valueOrFunction ) {
8704
8705 // If value is a function, invoke it and use its return value
8706 var value = isFunction( valueOrFunction ) ?
8707 valueOrFunction() :
8708 valueOrFunction;
8709
8710 s[ s.length ] = encodeURIComponent( key ) + "=" +
8711 encodeURIComponent( value == null ? "" : value );
8712 };
8713
8714 // If an array was passed in, assume that it is an array of form elements.
8715 if ( Array.isArray( a ) || ( a.jquery && !jQuery.isPlainObject( a ) ) ) {
8716
8717 // Serialize the form elements
8718 jQuery.each( a, function() {
8719 add( this.name, this.value );
8720 } );
8721
8722 } else {
8723
8724 // If traditional, encode the "old" way (the way 1.3.2 or older
8725 // did it), otherwise encode params recursively.
8726 for ( prefix in a ) {
8727 buildParams( prefix, a[ prefix ], traditional, add );
8728 }
8729 }
8730
8731 // Return the resulting serialization
8732 return s.join( "&" );
8733};
8734
8735jQuery.fn.extend( {
8736 serialize: function() {
8737 return jQuery.param( this.serializeArray() );
8738 },
8739 serializeArray: function() {
8740 return this.map( function() {
8741
8742 // Can add propHook for "elements" to filter or add form elements
8743 var elements = jQuery.prop( this, "elements" );
8744 return elements ? jQuery.makeArray( elements ) : this;
8745 } )
8746 .filter( function() {
8747 var type = this.type;
8748
8749 // Use .is( ":disabled" ) so that fieldset[disabled] works
8750 return this.name && !jQuery( this ).is( ":disabled" ) &&
8751 rsubmittable.test( this.nodeName ) && !rsubmitterTypes.test( type ) &&
8752 ( this.checked || !rcheckableType.test( type ) );
8753 } )
8754 .map( function( i, elem ) {
8755 var val = jQuery( this ).val();
8756
8757 if ( val == null ) {
8758 return null;
8759 }
8760
8761 if ( Array.isArray( val ) ) {
8762 return jQuery.map( val, function( val ) {
8763 return { name: elem.name, value: val.replace( rCRLF, "\r\n" ) };
8764 } );
8765 }
8766
8767 return { name: elem.name, value: val.replace( rCRLF, "\r\n" ) };
8768 } ).get();
8769 }
8770} );
8771
8772
8773var
8774 r20 = /%20/g,
8775 rhash = /#.*$/,
8776 rantiCache = /([?&])_=[^&]*/,
8777 rheaders = /^(.*?):[ \t]*([^\r\n]*)$/mg,
8778
8779 // #7653, #8125, #8152: local protocol detection
8780 rlocalProtocol = /^(?:about|app|app-storage|.+-extension|file|res|widget):$/,
8781 rnoContent = /^(?:GET|HEAD)$/,
8782 rprotocol = /^\/\//,
8783
8784 /* Prefilters
8785 * 1) They are useful to introduce custom dataTypes (see ajax/jsonp.js for an example)
8786 * 2) These are called:
8787 * - BEFORE asking for a transport
8788 * - AFTER param serialization (s.data is a string if s.processData is true)
8789 * 3) key is the dataType
8790 * 4) the catchall symbol "*" can be used
8791 * 5) execution will start with transport dataType and THEN continue down to "*" if needed
8792 */
8793 prefilters = {},
8794
8795 /* Transports bindings
8796 * 1) key is the dataType
8797 * 2) the catchall symbol "*" can be used
8798 * 3) selection will start with transport dataType and THEN go to "*" if needed
8799 */
8800 transports = {},
8801
8802 // Avoid comment-prolog char sequence (#10098); must appease lint and evade compression
8803 allTypes = "*/".concat( "*" ),
8804
8805 // Anchor tag for parsing the document origin
8806 originAnchor = document.createElement( "a" );
8807 originAnchor.href = location.href;
8808
8809// Base "constructor" for jQuery.ajaxPrefilter and jQuery.ajaxTransport
8810function addToPrefiltersOrTransports( structure ) {
8811
8812 // dataTypeExpression is optional and defaults to "*"
8813 return function( dataTypeExpression, func ) {
8814
8815 if ( typeof dataTypeExpression !== "string" ) {
8816 func = dataTypeExpression;
8817 dataTypeExpression = "*";
8818 }
8819
8820 var dataType,
8821 i = 0,
8822 dataTypes = dataTypeExpression.toLowerCase().match( rnothtmlwhite ) || [];
8823
8824 if ( isFunction( func ) ) {
8825
8826 // For each dataType in the dataTypeExpression
8827 while ( ( dataType = dataTypes[ i++ ] ) ) {
8828
8829 // Prepend if requested
8830 if ( dataType[ 0 ] === "+" ) {
8831 dataType = dataType.slice( 1 ) || "*";
8832 ( structure[ dataType ] = structure[ dataType ] || [] ).unshift( func );
8833
8834 // Otherwise append
8835 } else {
8836 ( structure[ dataType ] = structure[ dataType ] || [] ).push( func );
8837 }
8838 }
8839 }
8840 };
8841}
8842
8843// Base inspection function for prefilters and transports
8844function inspectPrefiltersOrTransports( structure, options, originalOptions, jqXHR ) {
8845
8846 var inspected = {},
8847 seekingTransport = ( structure === transports );
8848
8849 function inspect( dataType ) {
8850 var selected;
8851 inspected[ dataType ] = true;
8852 jQuery.each( structure[ dataType ] || [], function( _, prefilterOrFactory ) {
8853 var dataTypeOrTransport = prefilterOrFactory( options, originalOptions, jqXHR );
8854 if ( typeof dataTypeOrTransport === "string" &&
8855 !seekingTransport && !inspected[ dataTypeOrTransport ] ) {
8856
8857 options.dataTypes.unshift( dataTypeOrTransport );
8858 inspect( dataTypeOrTransport );
8859 return false;
8860 } else if ( seekingTransport ) {
8861 return !( selected = dataTypeOrTransport );
8862 }
8863 } );
8864 return selected;
8865 }
8866
8867 return inspect( options.dataTypes[ 0 ] ) || !inspected[ "*" ] && inspect( "*" );
8868}
8869
8870// A special extend for ajax options
8871// that takes "flat" options (not to be deep extended)
8872// Fixes #9887
8873function ajaxExtend( target, src ) {
8874 var key, deep,
8875 flatOptions = jQuery.ajaxSettings.flatOptions || {};
8876
8877 for ( key in src ) {
8878 if ( src[ key ] !== undefined ) {
8879 ( flatOptions[ key ] ? target : ( deep || ( deep = {} ) ) )[ key ] = src[ key ];
8880 }
8881 }
8882 if ( deep ) {
8883 jQuery.extend( true, target, deep );
8884 }
8885
8886 return target;
8887}
8888
8889/* Handles responses to an ajax request:
8890 * - finds the right dataType (mediates between content-type and expected dataType)
8891 * - returns the corresponding response
8892 */
8893function ajaxHandleResponses( s, jqXHR, responses ) {
8894
8895 var ct, type, finalDataType, firstDataType,
8896 contents = s.contents,
8897 dataTypes = s.dataTypes;
8898
8899 // Remove auto dataType and get content-type in the process
8900 while ( dataTypes[ 0 ] === "*" ) {
8901 dataTypes.shift();
8902 if ( ct === undefined ) {
8903 ct = s.mimeType || jqXHR.getResponseHeader( "Content-Type" );
8904 }
8905 }
8906
8907 // Check if we're dealing with a known content-type
8908 if ( ct ) {
8909 for ( type in contents ) {
8910 if ( contents[ type ] && contents[ type ].test( ct ) ) {
8911 dataTypes.unshift( type );
8912 break;
8913 }
8914 }
8915 }
8916
8917 // Check to see if we have a response for the expected dataType
8918 if ( dataTypes[ 0 ] in responses ) {
8919 finalDataType = dataTypes[ 0 ];
8920 } else {
8921
8922 // Try convertible dataTypes
8923 for ( type in responses ) {
8924 if ( !dataTypes[ 0 ] || s.converters[ type + " " + dataTypes[ 0 ] ] ) {
8925 finalDataType = type;
8926 break;
8927 }
8928 if ( !firstDataType ) {
8929 firstDataType = type;
8930 }
8931 }
8932
8933 // Or just use first one
8934 finalDataType = finalDataType || firstDataType;
8935 }
8936
8937 // If we found a dataType
8938 // We add the dataType to the list if needed
8939 // and return the corresponding response
8940 if ( finalDataType ) {
8941 if ( finalDataType !== dataTypes[ 0 ] ) {
8942 dataTypes.unshift( finalDataType );
8943 }
8944 return responses[ finalDataType ];
8945 }
8946}
8947
8948/* Chain conversions given the request and the original response
8949 * Also sets the responseXXX fields on the jqXHR instance
8950 */
8951function ajaxConvert( s, response, jqXHR, isSuccess ) {
8952 var conv2, current, conv, tmp, prev,
8953 converters = {},
8954
8955 // Work with a copy of dataTypes in case we need to modify it for conversion
8956 dataTypes = s.dataTypes.slice();
8957
8958 // Create converters map with lowercased keys
8959 if ( dataTypes[ 1 ] ) {
8960 for ( conv in s.converters ) {
8961 converters[ conv.toLowerCase() ] = s.converters[ conv ];
8962 }
8963 }
8964
8965 current = dataTypes.shift();
8966
8967 // Convert to each sequential dataType
8968 while ( current ) {
8969
8970 if ( s.responseFields[ current ] ) {
8971 jqXHR[ s.responseFields[ current ] ] = response;
8972 }
8973
8974 // Apply the dataFilter if provided
8975 if ( !prev && isSuccess && s.dataFilter ) {
8976 response = s.dataFilter( response, s.dataType );
8977 }
8978
8979 prev = current;
8980 current = dataTypes.shift();
8981
8982 if ( current ) {
8983
8984 // There's only work to do if current dataType is non-auto
8985 if ( current === "*" ) {
8986
8987 current = prev;
8988
8989 // Convert response if prev dataType is non-auto and differs from current
8990 } else if ( prev !== "*" && prev !== current ) {
8991
8992 // Seek a direct converter
8993 conv = converters[ prev + " " + current ] || converters[ "* " + current ];
8994
8995 // If none found, seek a pair
8996 if ( !conv ) {
8997 for ( conv2 in converters ) {
8998
8999 // If conv2 outputs current
9000 tmp = conv2.split( " " );
9001 if ( tmp[ 1 ] === current ) {
9002
9003 // If prev can be converted to accepted input
9004 conv = converters[ prev + " " + tmp[ 0 ] ] ||
9005 converters[ "* " + tmp[ 0 ] ];
9006 if ( conv ) {
9007
9008 // Condense equivalence converters
9009 if ( conv === true ) {
9010 conv = converters[ conv2 ];
9011
9012 // Otherwise, insert the intermediate dataType
9013 } else if ( converters[ conv2 ] !== true ) {
9014 current = tmp[ 0 ];
9015 dataTypes.unshift( tmp[ 1 ] );
9016 }
9017 break;
9018 }
9019 }
9020 }
9021 }
9022
9023 // Apply converter (if not an equivalence)
9024 if ( conv !== true ) {
9025
9026 // Unless errors are allowed to bubble, catch and return them
9027 if ( conv && s.throws ) {
9028 response = conv( response );
9029 } else {
9030 try {
9031 response = conv( response );
9032 } catch ( e ) {
9033 return {
9034 state: "parsererror",
9035 error: conv ? e : "No conversion from " + prev + " to " + current
9036 };
9037 }
9038 }
9039 }
9040 }
9041 }
9042 }
9043
9044 return { state: "success", data: response };
9045}
9046
9047jQuery.extend( {
9048
9049 // Counter for holding the number of active queries
9050 active: 0,
9051
9052 // Last-Modified header cache for next request
9053 lastModified: {},
9054 etag: {},
9055
9056 ajaxSettings: {
9057 url: location.href,
9058 type: "GET",
9059 isLocal: rlocalProtocol.test( location.protocol ),
9060 global: true,
9061 processData: true,
9062 async: true,
9063 contentType: "application/x-www-form-urlencoded; charset=UTF-8",
9064
9065 /*
9066 timeout: 0,
9067 data: null,
9068 dataType: null,
9069 username: null,
9070 password: null,
9071 cache: null,
9072 throws: false,
9073 traditional: false,
9074 headers: {},
9075 */
9076
9077 accepts: {
9078 "*": allTypes,
9079 text: "text/plain",
9080 html: "text/html",
9081 xml: "application/xml, text/xml",
9082 json: "application/json, text/javascript"
9083 },
9084
9085 contents: {
9086 xml: /\bxml\b/,
9087 html: /\bhtml/,
9088 json: /\bjson\b/
9089 },
9090
9091 responseFields: {
9092 xml: "responseXML",
9093 text: "responseText",
9094 json: "responseJSON"
9095 },
9096
9097 // Data converters
9098 // Keys separate source (or catchall "*") and destination types with a single space
9099 converters: {
9100
9101 // Convert anything to text
9102 "* text": String,
9103
9104 // Text to html (true = no transformation)
9105 "text html": true,
9106
9107 // Evaluate text as a json expression
9108 "text json": JSON.parse,
9109
9110 // Parse text as xml
9111 "text xml": jQuery.parseXML
9112 },
9113
9114 // For options that shouldn't be deep extended:
9115 // you can add your own custom options here if
9116 // and when you create one that shouldn't be
9117 // deep extended (see ajaxExtend)
9118 flatOptions: {
9119 url: true,
9120 context: true
9121 }
9122 },
9123
9124 // Creates a full fledged settings object into target
9125 // with both ajaxSettings and settings fields.
9126 // If target is omitted, writes into ajaxSettings.
9127 ajaxSetup: function( target, settings ) {
9128 return settings ?
9129
9130 // Building a settings object
9131 ajaxExtend( ajaxExtend( target, jQuery.ajaxSettings ), settings ) :
9132
9133 // Extending ajaxSettings
9134 ajaxExtend( jQuery.ajaxSettings, target );
9135 },
9136
9137 ajaxPrefilter: addToPrefiltersOrTransports( prefilters ),
9138 ajaxTransport: addToPrefiltersOrTransports( transports ),
9139
9140 // Main method
9141 ajax: function( url, options ) {
9142
9143 // If url is an object, simulate pre-1.5 signature
9144 if ( typeof url === "object" ) {
9145 options = url;
9146 url = undefined;
9147 }
9148
9149 // Force options to be an object
9150 options = options || {};
9151
9152 var transport,
9153
9154 // URL without anti-cache param
9155 cacheURL,
9156
9157 // Response headers
9158 responseHeadersString,
9159 responseHeaders,
9160
9161 // timeout handle
9162 timeoutTimer,
9163
9164 // Url cleanup var
9165 urlAnchor,
9166
9167 // Request state (becomes false upon send and true upon completion)
9168 completed,
9169
9170 // To know if global events are to be dispatched
9171 fireGlobals,
9172
9173 // Loop variable
9174 i,
9175
9176 // uncached part of the url
9177 uncached,
9178
9179 // Create the final options object
9180 s = jQuery.ajaxSetup( {}, options ),
9181
9182 // Callbacks context
9183 callbackContext = s.context || s,
9184
9185 // Context for global events is callbackContext if it is a DOM node or jQuery collection
9186 globalEventContext = s.context &&
9187 ( callbackContext.nodeType || callbackContext.jquery ) ?
9188 jQuery( callbackContext ) :
9189 jQuery.event,
9190
9191 // Deferreds
9192 deferred = jQuery.Deferred(),
9193 completeDeferred = jQuery.Callbacks( "once memory" ),
9194
9195 // Status-dependent callbacks
9196 statusCode = s.statusCode || {},
9197
9198 // Headers (they are sent all at once)
9199 requestHeaders = {},
9200 requestHeadersNames = {},
9201
9202 // Default abort message
9203 strAbort = "canceled",
9204
9205 // Fake xhr
9206 jqXHR = {
9207 readyState: 0,
9208
9209 // Builds headers hashtable if needed
9210 getResponseHeader: function( key ) {
9211 var match;
9212 if ( completed ) {
9213 if ( !responseHeaders ) {
9214 responseHeaders = {};
9215 while ( ( match = rheaders.exec( responseHeadersString ) ) ) {
9216 responseHeaders[ match[ 1 ].toLowerCase() ] = match[ 2 ];
9217 }
9218 }
9219 match = responseHeaders[ key.toLowerCase() ];
9220 }
9221 return match == null ? null : match;
9222 },
9223
9224 // Raw string
9225 getAllResponseHeaders: function() {
9226 return completed ? responseHeadersString : null;
9227 },
9228
9229 // Caches the header
9230 setRequestHeader: function( name, value ) {
9231 if ( completed == null ) {
9232 name = requestHeadersNames[ name.toLowerCase() ] =
9233 requestHeadersNames[ name.toLowerCase() ] || name;
9234 requestHeaders[ name ] = value;
9235 }
9236 return this;
9237 },
9238
9239 // Overrides response content-type header
9240 overrideMimeType: function( type ) {
9241 if ( completed == null ) {
9242 s.mimeType = type;
9243 }
9244 return this;
9245 },
9246
9247 // Status-dependent callbacks
9248 statusCode: function( map ) {
9249 var code;
9250 if ( map ) {
9251 if ( completed ) {
9252
9253 // Execute the appropriate callbacks
9254 jqXHR.always( map[ jqXHR.status ] );
9255 } else {
9256
9257 // Lazy-add the new callbacks in a way that preserves old ones
9258 for ( code in map ) {
9259 statusCode[ code ] = [ statusCode[ code ], map[ code ] ];
9260 }
9261 }
9262 }
9263 return this;
9264 },
9265
9266 // Cancel the request
9267 abort: function( statusText ) {
9268 var finalText = statusText || strAbort;
9269 if ( transport ) {
9270 transport.abort( finalText );
9271 }
9272 done( 0, finalText );
9273 return this;
9274 }
9275 };
9276
9277 // Attach deferreds
9278 deferred.promise( jqXHR );
9279
9280 // Add protocol if not provided (prefilters might expect it)
9281 // Handle falsy url in the settings object (#10093: consistency with old signature)
9282 // We also use the url parameter if available
9283 s.url = ( ( url || s.url || location.href ) + "" )
9284 .replace( rprotocol, location.protocol + "//" );
9285
9286 // Alias method option to type as per ticket #12004
9287 s.type = options.method || options.type || s.method || s.type;
9288
9289 // Extract dataTypes list
9290 s.dataTypes = ( s.dataType || "*" ).toLowerCase().match( rnothtmlwhite ) || [ "" ];
9291
9292 // A cross-domain request is in order when the origin doesn't match the current origin.
9293 if ( s.crossDomain == null ) {
9294 urlAnchor = document.createElement( "a" );
9295
9296 // Support: IE <=8 - 11, Edge 12 - 15
9297 // IE throws exception on accessing the href property if url is malformed,
9298 // e.g. http://example.com:80x/
9299 try {
9300 urlAnchor.href = s.url;
9301
9302 // Support: IE <=8 - 11 only
9303 // Anchor's host property isn't correctly set when s.url is relative
9304 urlAnchor.href = urlAnchor.href;
9305 s.crossDomain = originAnchor.protocol + "//" + originAnchor.host !==
9306 urlAnchor.protocol + "//" + urlAnchor.host;
9307 } catch ( e ) {
9308
9309 // If there is an error parsing the URL, assume it is crossDomain,
9310 // it can be rejected by the transport if it is invalid
9311 s.crossDomain = true;
9312 }
9313 }
9314
9315 // Convert data if not already a string
9316 if ( s.data && s.processData && typeof s.data !== "string" ) {
9317 s.data = jQuery.param( s.data, s.traditional );
9318 }
9319
9320 // Apply prefilters
9321 inspectPrefiltersOrTransports( prefilters, s, options, jqXHR );
9322
9323 // If request was aborted inside a prefilter, stop there
9324 if ( completed ) {
9325 return jqXHR;
9326 }
9327
9328 // We can fire global events as of now if asked to
9329 // Don't fire events if jQuery.event is undefined in an AMD-usage scenario (#15118)
9330 fireGlobals = jQuery.event && s.global;
9331
9332 // Watch for a new set of requests
9333 if ( fireGlobals && jQuery.active++ === 0 ) {
9334 jQuery.event.trigger( "ajaxStart" );
9335 }
9336
9337 // Uppercase the type
9338 s.type = s.type.toUpperCase();
9339
9340 // Determine if request has content
9341 s.hasContent = !rnoContent.test( s.type );
9342
9343 // Save the URL in case we're toying with the If-Modified-Since
9344 // and/or If-None-Match header later on
9345 // Remove hash to simplify url manipulation
9346 cacheURL = s.url.replace( rhash, "" );
9347
9348 // More options handling for requests with no content
9349 if ( !s.hasContent ) {
9350
9351 // Remember the hash so we can put it back
9352 uncached = s.url.slice( cacheURL.length );
9353
9354 // If data is available and should be processed, append data to url
9355 if ( s.data && ( s.processData || typeof s.data === "string" ) ) {
9356 cacheURL += ( rquery.test( cacheURL ) ? "&" : "?" ) + s.data;
9357
9358 // #9682: remove data so that it's not used in an eventual retry
9359 delete s.data;
9360 }
9361
9362 // Add or update anti-cache param if needed
9363 if ( s.cache === false ) {
9364 cacheURL = cacheURL.replace( rantiCache, "$1" );
9365 uncached = ( rquery.test( cacheURL ) ? "&" : "?" ) + "_=" + ( nonce++ ) + uncached;
9366 }
9367
9368 // Put hash and anti-cache on the URL that will be requested (gh-1732)
9369 s.url = cacheURL + uncached;
9370
9371 // Change '%20' to '+' if this is encoded form body content (gh-2658)
9372 } else if ( s.data && s.processData &&
9373 ( s.contentType || "" ).indexOf( "application/x-www-form-urlencoded" ) === 0 ) {
9374 s.data = s.data.replace( r20, "+" );
9375 }
9376
9377 // Set the If-Modified-Since and/or If-None-Match header, if in ifModified mode.
9378 if ( s.ifModified ) {
9379 if ( jQuery.lastModified[ cacheURL ] ) {
9380 jqXHR.setRequestHeader( "If-Modified-Since", jQuery.lastModified[ cacheURL ] );
9381 }
9382 if ( jQuery.etag[ cacheURL ] ) {
9383 jqXHR.setRequestHeader( "If-None-Match", jQuery.etag[ cacheURL ] );
9384 }
9385 }
9386
9387 // Set the correct header, if data is being sent
9388 if ( s.data && s.hasContent && s.contentType !== false || options.contentType ) {
9389 jqXHR.setRequestHeader( "Content-Type", s.contentType );
9390 }
9391
9392 // Set the Accepts header for the server, depending on the dataType
9393 jqXHR.setRequestHeader(
9394 "Accept",
9395 s.dataTypes[ 0 ] && s.accepts[ s.dataTypes[ 0 ] ] ?
9396 s.accepts[ s.dataTypes[ 0 ] ] +
9397 ( s.dataTypes[ 0 ] !== "*" ? ", " + allTypes + "; q=0.01" : "" ) :
9398 s.accepts[ "*" ]
9399 );
9400
9401 // Check for headers option
9402 for ( i in s.headers ) {
9403 jqXHR.setRequestHeader( i, s.headers[ i ] );
9404 }
9405
9406 // Allow custom headers/mimetypes and early abort
9407 if ( s.beforeSend &&
9408 ( s.beforeSend.call( callbackContext, jqXHR, s ) === false || completed ) ) {
9409
9410 // Abort if not done already and return
9411 return jqXHR.abort();
9412 }
9413
9414 // Aborting is no longer a cancellation
9415 strAbort = "abort";
9416
9417 // Install callbacks on deferreds
9418 completeDeferred.add( s.complete );
9419 jqXHR.done( s.success );
9420 jqXHR.fail( s.error );
9421
9422 // Get transport
9423 transport = inspectPrefiltersOrTransports( transports, s, options, jqXHR );
9424
9425 // If no transport, we auto-abort
9426 if ( !transport ) {
9427 done( -1, "No Transport" );
9428 } else {
9429 jqXHR.readyState = 1;
9430
9431 // Send global event
9432 if ( fireGlobals ) {
9433 globalEventContext.trigger( "ajaxSend", [ jqXHR, s ] );
9434 }
9435
9436 // If request was aborted inside ajaxSend, stop there
9437 if ( completed ) {
9438 return jqXHR;
9439 }
9440
9441 // Timeout
9442 if ( s.async && s.timeout > 0 ) {
9443 timeoutTimer = window.setTimeout( function() {
9444 jqXHR.abort( "timeout" );
9445 }, s.timeout );
9446 }
9447
9448 try {
9449 completed = false;
9450 transport.send( requestHeaders, done );
9451 } catch ( e ) {
9452
9453 // Rethrow post-completion exceptions
9454 if ( completed ) {
9455 throw e;
9456 }
9457
9458 // Propagate others as results
9459 done( -1, e );
9460 }
9461 }
9462
9463 // Callback for when everything is done
9464 function done( status, nativeStatusText, responses, headers ) {
9465 var isSuccess, success, error, response, modified,
9466 statusText = nativeStatusText;
9467
9468 // Ignore repeat invocations
9469 if ( completed ) {
9470 return;
9471 }
9472
9473 completed = true;
9474
9475 // Clear timeout if it exists
9476 if ( timeoutTimer ) {
9477 window.clearTimeout( timeoutTimer );
9478 }
9479
9480 // Dereference transport for early garbage collection
9481 // (no matter how long the jqXHR object will be used)
9482 transport = undefined;
9483
9484 // Cache response headers
9485 responseHeadersString = headers || "";
9486
9487 // Set readyState
9488 jqXHR.readyState = status > 0 ? 4 : 0;
9489
9490 // Determine if successful
9491 isSuccess = status >= 200 && status < 300 || status === 304;
9492
9493 // Get response data
9494 if ( responses ) {
9495 response = ajaxHandleResponses( s, jqXHR, responses );
9496 }
9497
9498 // Convert no matter what (that way responseXXX fields are always set)
9499 response = ajaxConvert( s, response, jqXHR, isSuccess );
9500
9501 // If successful, handle type chaining
9502 if ( isSuccess ) {
9503
9504 // Set the If-Modified-Since and/or If-None-Match header, if in ifModified mode.
9505 if ( s.ifModified ) {
9506 modified = jqXHR.getResponseHeader( "Last-Modified" );
9507 if ( modified ) {
9508 jQuery.lastModified[ cacheURL ] = modified;
9509 }
9510 modified = jqXHR.getResponseHeader( "etag" );
9511 if ( modified ) {
9512 jQuery.etag[ cacheURL ] = modified;
9513 }
9514 }
9515
9516 // if no content
9517 if ( status === 204 || s.type === "HEAD" ) {
9518 statusText = "nocontent";
9519
9520 // if not modified
9521 } else if ( status === 304 ) {
9522 statusText = "notmodified";
9523
9524 // If we have data, let's convert it
9525 } else {
9526 statusText = response.state;
9527 success = response.data;
9528 error = response.error;
9529 isSuccess = !error;
9530 }
9531 } else {
9532
9533 // Extract error from statusText and normalize for non-aborts
9534 error = statusText;
9535 if ( status || !statusText ) {
9536 statusText = "error";
9537 if ( status < 0 ) {
9538 status = 0;
9539 }
9540 }
9541 }
9542
9543 // Set data for the fake xhr object
9544 jqXHR.status = status;
9545 jqXHR.statusText = ( nativeStatusText || statusText ) + "";
9546
9547 // Success/Error
9548 if ( isSuccess ) {
9549 deferred.resolveWith( callbackContext, [ success, statusText, jqXHR ] );
9550 } else {
9551 deferred.rejectWith( callbackContext, [ jqXHR, statusText, error ] );
9552 }
9553
9554 // Status-dependent callbacks
9555 jqXHR.statusCode( statusCode );
9556 statusCode = undefined;
9557
9558 if ( fireGlobals ) {
9559 globalEventContext.trigger( isSuccess ? "ajaxSuccess" : "ajaxError",
9560 [ jqXHR, s, isSuccess ? success : error ] );
9561 }
9562
9563 // Complete
9564 completeDeferred.fireWith( callbackContext, [ jqXHR, statusText ] );
9565
9566 if ( fireGlobals ) {
9567 globalEventContext.trigger( "ajaxComplete", [ jqXHR, s ] );
9568
9569 // Handle the global AJAX counter
9570 if ( !( --jQuery.active ) ) {
9571 jQuery.event.trigger( "ajaxStop" );
9572 }
9573 }
9574 }
9575
9576 return jqXHR;
9577 },
9578
9579 getJSON: function( url, data, callback ) {
9580 return jQuery.get( url, data, callback, "json" );
9581 },
9582
9583 getScript: function( url, callback ) {
9584 return jQuery.get( url, undefined, callback, "script" );
9585 }
9586} );
9587
9588jQuery.each( [ "get", "post" ], function( i, method ) {
9589 jQuery[ method ] = function( url, data, callback, type ) {
9590
9591 // Shift arguments if data argument was omitted
9592 if ( isFunction( data ) ) {
9593 type = type || callback;
9594 callback = data;
9595 data = undefined;
9596 }
9597
9598 // The url can be an options object (which then must have .url)
9599 return jQuery.ajax( jQuery.extend( {
9600 url: url,
9601 type: method,
9602 dataType: type,
9603 data: data,
9604 success: callback
9605 }, jQuery.isPlainObject( url ) && url ) );
9606 };
9607} );
9608
9609
9610jQuery._evalUrl = function( url ) {
9611 return jQuery.ajax( {
9612 url: url,
9613
9614 // Make this explicit, since user can override this through ajaxSetup (#11264)
9615 type: "GET",
9616 dataType: "script",
9617 cache: true,
9618 async: false,
9619 global: false,
9620 "throws": true
9621 } );
9622};
9623
9624
9625jQuery.fn.extend( {
9626 wrapAll: function( html ) {
9627 var wrap;
9628
9629 if ( this[ 0 ] ) {
9630 if ( isFunction( html ) ) {
9631 html = html.call( this[ 0 ] );
9632 }
9633
9634 // The elements to wrap the target around
9635 wrap = jQuery( html, this[ 0 ].ownerDocument ).eq( 0 ).clone( true );
9636
9637 if ( this[ 0 ].parentNode ) {
9638 wrap.insertBefore( this[ 0 ] );
9639 }
9640
9641 wrap.map( function() {
9642 var elem = this;
9643
9644 while ( elem.firstElementChild ) {
9645 elem = elem.firstElementChild;
9646 }
9647
9648 return elem;
9649 } ).append( this );
9650 }
9651
9652 return this;
9653 },
9654
9655 wrapInner: function( html ) {
9656 if ( isFunction( html ) ) {
9657 return this.each( function( i ) {
9658 jQuery( this ).wrapInner( html.call( this, i ) );
9659 } );
9660 }
9661
9662 return this.each( function() {
9663 var self = jQuery( this ),
9664 contents = self.contents();
9665
9666 if ( contents.length ) {
9667 contents.wrapAll( html );
9668
9669 } else {
9670 self.append( html );
9671 }
9672 } );
9673 },
9674
9675 wrap: function( html ) {
9676 var htmlIsFunction = isFunction( html );
9677
9678 return this.each( function( i ) {
9679 jQuery( this ).wrapAll( htmlIsFunction ? html.call( this, i ) : html );
9680 } );
9681 },
9682
9683 unwrap: function( selector ) {
9684 this.parent( selector ).not( "body" ).each( function() {
9685 jQuery( this ).replaceWith( this.childNodes );
9686 } );
9687 return this;
9688 }
9689} );
9690
9691
9692jQuery.expr.pseudos.hidden = function( elem ) {
9693 return !jQuery.expr.pseudos.visible( elem );
9694};
9695jQuery.expr.pseudos.visible = function( elem ) {
9696 return !!( elem.offsetWidth || elem.offsetHeight || elem.getClientRects().length );
9697};
9698
9699
9700
9701
9702jQuery.ajaxSettings.xhr = function() {
9703 try {
9704 return new window.XMLHttpRequest();
9705 } catch ( e ) {}
9706};
9707
9708var xhrSuccessStatus = {
9709
9710 // File protocol always yields status code 0, assume 200
9711 0: 200,
9712
9713 // Support: IE <=9 only
9714 // #1450: sometimes IE returns 1223 when it should be 204
9715 1223: 204
9716 },
9717 xhrSupported = jQuery.ajaxSettings.xhr();
9718
9719support.cors = !!xhrSupported && ( "withCredentials" in xhrSupported );
9720support.ajax = xhrSupported = !!xhrSupported;
9721
9722jQuery.ajaxTransport( function( options ) {
9723 var callback, errorCallback;
9724
9725 // Cross domain only allowed if supported through XMLHttpRequest
9726 if ( support.cors || xhrSupported && !options.crossDomain ) {
9727 return {
9728 send: function( headers, complete ) {
9729 var i,
9730 xhr = options.xhr();
9731
9732 xhr.open(
9733 options.type,
9734 options.url,
9735 options.async,
9736 options.username,
9737 options.password
9738 );
9739
9740 // Apply custom fields if provided
9741 if ( options.xhrFields ) {
9742 for ( i in options.xhrFields ) {
9743 xhr[ i ] = options.xhrFields[ i ];
9744 }
9745 }
9746
9747 // Override mime type if needed
9748 if ( options.mimeType && xhr.overrideMimeType ) {
9749 xhr.overrideMimeType( options.mimeType );
9750 }
9751
9752 // X-Requested-With header
9753 // For cross-domain requests, seeing as conditions for a preflight are
9754 // akin to a jigsaw puzzle, we simply never set it to be sure.
9755 // (it can always be set on a per-request basis or even using ajaxSetup)
9756 // For same-domain requests, won't change header if already provided.
9757 if ( !options.crossDomain && !headers[ "X-Requested-With" ] ) {
9758 headers[ "X-Requested-With" ] = "XMLHttpRequest";
9759 }
9760
9761 // Set headers
9762 for ( i in headers ) {
9763 xhr.setRequestHeader( i, headers[ i ] );
9764 }
9765
9766 // Callback
9767 callback = function( type ) {
9768 return function() {
9769 if ( callback ) {
9770 callback = errorCallback = xhr.onload =
9771 xhr.onerror = xhr.onabort = xhr.ontimeout =
9772 xhr.onreadystatechange = null;
9773
9774 if ( type === "abort" ) {
9775 xhr.abort();
9776 } else if ( type === "error" ) {
9777
9778 // Support: IE <=9 only
9779 // On a manual native abort, IE9 throws
9780 // errors on any property access that is not readyState
9781 if ( typeof xhr.status !== "number" ) {
9782 complete( 0, "error" );
9783 } else {
9784 complete(
9785
9786 // File: protocol always yields status 0; see #8605, #14207
9787 xhr.status,
9788 xhr.statusText
9789 );
9790 }
9791 } else {
9792 complete(
9793 xhrSuccessStatus[ xhr.status ] || xhr.status,
9794 xhr.statusText,
9795
9796 // Support: IE <=9 only
9797 // IE9 has no XHR2 but throws on binary (trac-11426)
9798 // For XHR2 non-text, let the caller handle it (gh-2498)
9799 ( xhr.responseType || "text" ) !== "text" ||
9800 typeof xhr.responseText !== "string" ?
9801 { binary: xhr.response } :
9802 { text: xhr.responseText },
9803 xhr.getAllResponseHeaders()
9804 );
9805 }
9806 }
9807 };
9808 };
9809
9810 // Listen to events
9811 xhr.onload = callback();
9812 errorCallback = xhr.onerror = xhr.ontimeout = callback( "error" );
9813
9814 // Support: IE 9 only
9815 // Use onreadystatechange to replace onabort
9816 // to handle uncaught aborts
9817 if ( xhr.onabort !== undefined ) {
9818 xhr.onabort = errorCallback;
9819 } else {
9820 xhr.onreadystatechange = function() {
9821
9822 // Check readyState before timeout as it changes
9823 if ( xhr.readyState === 4 ) {
9824
9825 // Allow onerror to be called first,
9826 // but that will not handle a native abort
9827 // Also, save errorCallback to a variable
9828 // as xhr.onerror cannot be accessed
9829 window.setTimeout( function() {
9830 if ( callback ) {
9831 errorCallback();
9832 }
9833 } );
9834 }
9835 };
9836 }
9837
9838 // Create the abort callback
9839 callback = callback( "abort" );
9840
9841 try {
9842
9843 // Do send the request (this may raise an exception)
9844 xhr.send( options.hasContent && options.data || null );
9845 } catch ( e ) {
9846
9847 // #14683: Only rethrow if this hasn't been notified as an error yet
9848 if ( callback ) {
9849 throw e;
9850 }
9851 }
9852 },
9853
9854 abort: function() {
9855 if ( callback ) {
9856 callback();
9857 }
9858 }
9859 };
9860 }
9861} );
9862
9863
9864
9865
9866// Prevent auto-execution of scripts when no explicit dataType was provided (See gh-2432)
9867jQuery.ajaxPrefilter( function( s ) {
9868 if ( s.crossDomain ) {
9869 s.contents.script = false;
9870 }
9871} );
9872
9873// Install script dataType
9874jQuery.ajaxSetup( {
9875 accepts: {
9876 script: "text/javascript, application/javascript, " +
9877 "application/ecmascript, application/x-ecmascript"
9878 },
9879 contents: {
9880 script: /\b(?:java|ecma)script\b/
9881 },
9882 converters: {
9883 "text script": function( text ) {
9884 jQuery.globalEval( text );
9885 return text;
9886 }
9887 }
9888} );
9889
9890// Handle cache's special case and crossDomain
9891jQuery.ajaxPrefilter( "script", function( s ) {
9892 if ( s.cache === undefined ) {
9893 s.cache = false;
9894 }
9895 if ( s.crossDomain ) {
9896 s.type = "GET";
9897 }
9898} );
9899
9900// Bind script tag hack transport
9901jQuery.ajaxTransport( "script", function( s ) {
9902
9903 // This transport only deals with cross domain requests
9904 if ( s.crossDomain ) {
9905 var script, callback;
9906 return {
9907 send: function( _, complete ) {
9908 script = jQuery( "<script>" ).prop( {
9909 charset: s.scriptCharset,
9910 src: s.url
9911 } ).on(
9912 "load error",
9913 callback = function( evt ) {
9914 script.remove();
9915 callback = null;
9916 if ( evt ) {
9917 complete( evt.type === "error" ? 404 : 200, evt.type );
9918 }
9919 }
9920 );
9921
9922 // Use native DOM manipulation to avoid our domManip AJAX trickery
9923 document.head.appendChild( script[ 0 ] );
9924 },
9925 abort: function() {
9926 if ( callback ) {
9927 callback();
9928 }
9929 }
9930 };
9931 }
9932} );
9933
9934
9935
9936
9937var oldCallbacks = [],
9938 rjsonp = /(=)\?(?=&|$)|\?\?/;
9939
9940// Default jsonp settings
9941jQuery.ajaxSetup( {
9942 jsonp: "callback",
9943 jsonpCallback: function() {
9944 var callback = oldCallbacks.pop() || ( jQuery.expando + "_" + ( nonce++ ) );
9945 this[ callback ] = true;
9946 return callback;
9947 }
9948} );
9949
9950// Detect, normalize options and install callbacks for jsonp requests
9951jQuery.ajaxPrefilter( "json jsonp", function( s, originalSettings, jqXHR ) {
9952
9953 var callbackName, overwritten, responseContainer,
9954 jsonProp = s.jsonp !== false && ( rjsonp.test( s.url ) ?
9955 "url" :
9956 typeof s.data === "string" &&
9957 ( s.contentType || "" )
9958 .indexOf( "application/x-www-form-urlencoded" ) === 0 &&
9959 rjsonp.test( s.data ) && "data"
9960 );
9961
9962 // Handle iff the expected data type is "jsonp" or we have a parameter to set
9963 if ( jsonProp || s.dataTypes[ 0 ] === "jsonp" ) {
9964
9965 // Get callback name, remembering preexisting value associated with it
9966 callbackName = s.jsonpCallback = isFunction( s.jsonpCallback ) ?
9967 s.jsonpCallback() :
9968 s.jsonpCallback;
9969
9970 // Insert callback into url or form data
9971 if ( jsonProp ) {
9972 s[ jsonProp ] = s[ jsonProp ].replace( rjsonp, "$1" + callbackName );
9973 } else if ( s.jsonp !== false ) {
9974 s.url += ( rquery.test( s.url ) ? "&" : "?" ) + s.jsonp + "=" + callbackName;
9975 }
9976
9977 // Use data converter to retrieve json after script execution
9978 s.converters[ "script json" ] = function() {
9979 if ( !responseContainer ) {
9980 jQuery.error( callbackName + " was not called" );
9981 }
9982 return responseContainer[ 0 ];
9983 };
9984
9985 // Force json dataType
9986 s.dataTypes[ 0 ] = "json";
9987
9988 // Install callback
9989 overwritten = window[ callbackName ];
9990 window[ callbackName ] = function() {
9991 responseContainer = arguments;
9992 };
9993
9994 // Clean-up function (fires after converters)
9995 jqXHR.always( function() {
9996
9997 // If previous value didn't exist - remove it
9998 if ( overwritten === undefined ) {
9999 jQuery( window ).removeProp( callbackName );
10000
10001 // Otherwise restore preexisting value
10002 } else {
10003 window[ callbackName ] = overwritten;
10004 }
10005
10006 // Save back as free
10007 if ( s[ callbackName ] ) {
10008
10009 // Make sure that re-using the options doesn't screw things around
10010 s.jsonpCallback = originalSettings.jsonpCallback;
10011
10012 // Save the callback name for future use
10013 oldCallbacks.push( callbackName );
10014 }
10015
10016 // Call if it was a function and we have a response
10017 if ( responseContainer && isFunction( overwritten ) ) {
10018 overwritten( responseContainer[ 0 ] );
10019 }
10020
10021 responseContainer = overwritten = undefined;
10022 } );
10023
10024 // Delegate to script
10025 return "script";
10026 }
10027} );
10028
10029
10030
10031
10032// Support: Safari 8 only
10033// In Safari 8 documents created via document.implementation.createHTMLDocument
10034// collapse sibling forms: the second one becomes a child of the first one.
10035// Because of that, this security measure has to be disabled in Safari 8.
10036// https://bugs.webkit.org/show_bug.cgi?id=137337
10037support.createHTMLDocument = ( function() {
10038 var body = document.implementation.createHTMLDocument( "" ).body;
10039 body.innerHTML = "<form></form><form></form>";
10040 return body.childNodes.length === 2;
10041} )();
10042
10043
10044// Argument "data" should be string of html
10045// context (optional): If specified, the fragment will be created in this context,
10046// defaults to document
10047// keepScripts (optional): If true, will include scripts passed in the html string
10048jQuery.parseHTML = function( data, context, keepScripts ) {
10049 if ( typeof data !== "string" ) {
10050 return [];
10051 }
10052 if ( typeof context === "boolean" ) {
10053 keepScripts = context;
10054 context = false;
10055 }
10056
10057 var base, parsed, scripts;
10058
10059 if ( !context ) {
10060
10061 // Stop scripts or inline event handlers from being executed immediately
10062 // by using document.implementation
10063 if ( support.createHTMLDocument ) {
10064 context = document.implementation.createHTMLDocument( "" );
10065
10066 // Set the base href for the created document
10067 // so any parsed elements with URLs
10068 // are based on the document's URL (gh-2965)
10069 base = context.createElement( "base" );
10070 base.href = document.location.href;
10071 context.head.appendChild( base );
10072 } else {
10073 context = document;
10074 }
10075 }
10076
10077 parsed = rsingleTag.exec( data );
10078 scripts = !keepScripts && [];
10079
10080 // Single tag
10081 if ( parsed ) {
10082 return [ context.createElement( parsed[ 1 ] ) ];
10083 }
10084
10085 parsed = buildFragment( [ data ], context, scripts );
10086
10087 if ( scripts && scripts.length ) {
10088 jQuery( scripts ).remove();
10089 }
10090
10091 return jQuery.merge( [], parsed.childNodes );
10092};
10093
10094
10095/**
10096 * Load a url into a page
10097 */
10098jQuery.fn.load = function( url, params, callback ) {
10099 var selector, type, response,
10100 self = this,
10101 off = url.indexOf( " " );
10102
10103 if ( off > -1 ) {
10104 selector = stripAndCollapse( url.slice( off ) );
10105 url = url.slice( 0, off );
10106 }
10107
10108 // If it's a function
10109 if ( isFunction( params ) ) {
10110
10111 // We assume that it's the callback
10112 callback = params;
10113 params = undefined;
10114
10115 // Otherwise, build a param string
10116 } else if ( params && typeof params === "object" ) {
10117 type = "POST";
10118 }
10119
10120 // If we have elements to modify, make the request
10121 if ( self.length > 0 ) {
10122 jQuery.ajax( {
10123 url: url,
10124
10125 // If "type" variable is undefined, then "GET" method will be used.
10126 // Make value of this field explicit since
10127 // user can override it through ajaxSetup method
10128 type: type || "GET",
10129 dataType: "html",
10130 data: params
10131 } ).done( function( responseText ) {
10132
10133 // Save response for use in complete callback
10134 response = arguments;
10135
10136 self.html( selector ?
10137
10138 // If a selector was specified, locate the right elements in a dummy div
10139 // Exclude scripts to avoid IE 'Permission Denied' errors
10140 jQuery( "<div>" ).append( jQuery.parseHTML( responseText ) ).find( selector ) :
10141
10142 // Otherwise use the full result
10143 responseText );
10144
10145 // If the request succeeds, this function gets "data", "status", "jqXHR"
10146 // but they are ignored because response was set above.
10147 // If it fails, this function gets "jqXHR", "status", "error"
10148 } ).always( callback && function( jqXHR, status ) {
10149 self.each( function() {
10150 callback.apply( this, response || [ jqXHR.responseText, status, jqXHR ] );
10151 } );
10152 } );
10153 }
10154
10155 return this;
10156};
10157
10158
10159
10160
10161// Attach a bunch of functions for handling common AJAX events
10162jQuery.each( [
10163 "ajaxStart",
10164 "ajaxStop",
10165 "ajaxComplete",
10166 "ajaxError",
10167 "ajaxSuccess",
10168 "ajaxSend"
10169], function( i, type ) {
10170 jQuery.fn[ type ] = function( fn ) {
10171 return this.on( type, fn );
10172 };
10173} );
10174
10175
10176
10177
10178jQuery.expr.pseudos.animated = function( elem ) {
10179 return jQuery.grep( jQuery.timers, function( fn ) {
10180 return elem === fn.elem;
10181 } ).length;
10182};
10183
10184
10185
10186
10187jQuery.offset = {
10188 setOffset: function( elem, options, i ) {
10189 var curPosition, curLeft, curCSSTop, curTop, curOffset, curCSSLeft, calculatePosition,
10190 position = jQuery.css( elem, "position" ),
10191 curElem = jQuery( elem ),
10192 props = {};
10193
10194 // Set position first, in-case top/left are set even on static elem
10195 if ( position === "static" ) {
10196 elem.style.position = "relative";
10197 }
10198
10199 curOffset = curElem.offset();
10200 curCSSTop = jQuery.css( elem, "top" );
10201 curCSSLeft = jQuery.css( elem, "left" );
10202 calculatePosition = ( position === "absolute" || position === "fixed" ) &&
10203 ( curCSSTop + curCSSLeft ).indexOf( "auto" ) > -1;
10204
10205 // Need to be able to calculate position if either
10206 // top or left is auto and position is either absolute or fixed
10207 if ( calculatePosition ) {
10208 curPosition = curElem.position();
10209 curTop = curPosition.top;
10210 curLeft = curPosition.left;
10211
10212 } else {
10213 curTop = parseFloat( curCSSTop ) || 0;
10214 curLeft = parseFloat( curCSSLeft ) || 0;
10215 }
10216
10217 if ( isFunction( options ) ) {
10218
10219 // Use jQuery.extend here to allow modification of coordinates argument (gh-1848)
10220 options = options.call( elem, i, jQuery.extend( {}, curOffset ) );
10221 }
10222
10223 if ( options.top != null ) {
10224 props.top = ( options.top - curOffset.top ) + curTop;
10225 }
10226 if ( options.left != null ) {
10227 props.left = ( options.left - curOffset.left ) + curLeft;
10228 }
10229
10230 if ( "using" in options ) {
10231 options.using.call( elem, props );
10232
10233 } else {
10234 curElem.css( props );
10235 }
10236 }
10237};
10238
10239jQuery.fn.extend( {
10240
10241 // offset() relates an element's border box to the document origin
10242 offset: function( options ) {
10243
10244 // Preserve chaining for setter
10245 if ( arguments.length ) {
10246 return options === undefined ?
10247 this :
10248 this.each( function( i ) {
10249 jQuery.offset.setOffset( this, options, i );
10250 } );
10251 }
10252
10253 var rect, win,
10254 elem = this[ 0 ];
10255
10256 if ( !elem ) {
10257 return;
10258 }
10259
10260 // Return zeros for disconnected and hidden (display: none) elements (gh-2310)
10261 // Support: IE <=11 only
10262 // Running getBoundingClientRect on a
10263 // disconnected node in IE throws an error
10264 if ( !elem.getClientRects().length ) {
10265 return { top: 0, left: 0 };
10266 }
10267
10268 // Get document-relative position by adding viewport scroll to viewport-relative gBCR
10269 rect = elem.getBoundingClientRect();
10270 win = elem.ownerDocument.defaultView;
10271 return {
10272 top: rect.top + win.pageYOffset,
10273 left: rect.left + win.pageXOffset
10274 };
10275 },
10276
10277 // position() relates an element's margin box to its offset parent's padding box
10278 // This corresponds to the behavior of CSS absolute positioning
10279 position: function() {
10280 if ( !this[ 0 ] ) {
10281 return;
10282 }
10283
10284 var offsetParent, offset, doc,
10285 elem = this[ 0 ],
10286 parentOffset = { top: 0, left: 0 };
10287
10288 // position:fixed elements are offset from the viewport, which itself always has zero offset
10289 if ( jQuery.css( elem, "position" ) === "fixed" ) {
10290
10291 // Assume position:fixed implies availability of getBoundingClientRect
10292 offset = elem.getBoundingClientRect();
10293
10294 } else {
10295 offset = this.offset();
10296
10297 // Account for the *real* offset parent, which can be the document or its root element
10298 // when a statically positioned element is identified
10299 doc = elem.ownerDocument;
10300 offsetParent = elem.offsetParent || doc.documentElement;
10301 while ( offsetParent &&
10302 ( offsetParent === doc.body || offsetParent === doc.documentElement ) &&
10303 jQuery.css( offsetParent, "position" ) === "static" ) {
10304
10305 offsetParent = offsetParent.parentNode;
10306 }
10307 if ( offsetParent && offsetParent !== elem && offsetParent.nodeType === 1 ) {
10308
10309 // Incorporate borders into its offset, since they are outside its content origin
10310 parentOffset = jQuery( offsetParent ).offset();
10311 parentOffset.top += jQuery.css( offsetParent, "borderTopWidth", true );
10312 parentOffset.left += jQuery.css( offsetParent, "borderLeftWidth", true );
10313 }
10314 }
10315
10316 // Subtract parent offsets and element margins
10317 return {
10318 top: offset.top - parentOffset.top - jQuery.css( elem, "marginTop", true ),
10319 left: offset.left - parentOffset.left - jQuery.css( elem, "marginLeft", true )
10320 };
10321 },
10322
10323 // This method will return documentElement in the following cases:
10324 // 1) For the element inside the iframe without offsetParent, this method will return
10325 // documentElement of the parent window
10326 // 2) For the hidden or detached element
10327 // 3) For body or html element, i.e. in case of the html node - it will return itself
10328 //
10329 // but those exceptions were never presented as a real life use-cases
10330 // and might be considered as more preferable results.
10331 //
10332 // This logic, however, is not guaranteed and can change at any point in the future
10333 offsetParent: function() {
10334 return this.map( function() {
10335 var offsetParent = this.offsetParent;
10336
10337 while ( offsetParent && jQuery.css( offsetParent, "position" ) === "static" ) {
10338 offsetParent = offsetParent.offsetParent;
10339 }
10340
10341 return offsetParent || documentElement;
10342 } );
10343 }
10344} );
10345
10346// Create scrollLeft and scrollTop methods
10347jQuery.each( { scrollLeft: "pageXOffset", scrollTop: "pageYOffset" }, function( method, prop ) {
10348 var top = "pageYOffset" === prop;
10349
10350 jQuery.fn[ method ] = function( val ) {
10351 return access( this, function( elem, method, val ) {
10352
10353 // Coalesce documents and windows
10354 var win;
10355 if ( isWindow( elem ) ) {
10356 win = elem;
10357 } else if ( elem.nodeType === 9 ) {
10358 win = elem.defaultView;
10359 }
10360
10361 if ( val === undefined ) {
10362 return win ? win[ prop ] : elem[ method ];
10363 }
10364
10365 if ( win ) {
10366 win.scrollTo(
10367 !top ? val : win.pageXOffset,
10368 top ? val : win.pageYOffset
10369 );
10370
10371 } else {
10372 elem[ method ] = val;
10373 }
10374 }, method, val, arguments.length );
10375 };
10376} );
10377
10378// Support: Safari <=7 - 9.1, Chrome <=37 - 49
10379// Add the top/left cssHooks using jQuery.fn.position
10380// Webkit bug: https://bugs.webkit.org/show_bug.cgi?id=29084
10381// Blink bug: https://bugs.chromium.org/p/chromium/issues/detail?id=589347
10382// getComputedStyle returns percent when specified for top/left/bottom/right;
10383// rather than make the css module depend on the offset module, just check for it here
10384jQuery.each( [ "top", "left" ], function( i, prop ) {
10385 jQuery.cssHooks[ prop ] = addGetHookIf( support.pixelPosition,
10386 function( elem, computed ) {
10387 if ( computed ) {
10388 computed = curCSS( elem, prop );
10389
10390 // If curCSS returns percentage, fallback to offset
10391 return rnumnonpx.test( computed ) ?
10392 jQuery( elem ).position()[ prop ] + "px" :
10393 computed;
10394 }
10395 }
10396 );
10397} );
10398
10399
10400// Create innerHeight, innerWidth, height, width, outerHeight and outerWidth methods
10401jQuery.each( { Height: "height", Width: "width" }, function( name, type ) {
10402 jQuery.each( { padding: "inner" + name, content: type, "": "outer" + name },
10403 function( defaultExtra, funcName ) {
10404
10405 // Margin is only for outerHeight, outerWidth
10406 jQuery.fn[ funcName ] = function( margin, value ) {
10407 var chainable = arguments.length && ( defaultExtra || typeof margin !== "boolean" ),
10408 extra = defaultExtra || ( margin === true || value === true ? "margin" : "border" );
10409
10410 return access( this, function( elem, type, value ) {
10411 var doc;
10412
10413 if ( isWindow( elem ) ) {
10414
10415 // $( window ).outerWidth/Height return w/h including scrollbars (gh-1729)
10416 return funcName.indexOf( "outer" ) === 0 ?
10417 elem[ "inner" + name ] :
10418 elem.document.documentElement[ "client" + name ];
10419 }
10420
10421 // Get document width or height
10422 if ( elem.nodeType === 9 ) {
10423 doc = elem.documentElement;
10424
10425 // Either scroll[Width/Height] or offset[Width/Height] or client[Width/Height],
10426 // whichever is greatest
10427 return Math.max(
10428 elem.body[ "scroll" + name ], doc[ "scroll" + name ],
10429 elem.body[ "offset" + name ], doc[ "offset" + name ],
10430 doc[ "client" + name ]
10431 );
10432 }
10433
10434 return value === undefined ?
10435
10436 // Get width or height on the element, requesting but not forcing parseFloat
10437 jQuery.css( elem, type, extra ) :
10438
10439 // Set width or height on the element
10440 jQuery.style( elem, type, value, extra );
10441 }, type, chainable ? margin : undefined, chainable );
10442 };
10443 } );
10444} );
10445
10446
10447jQuery.each( ( "blur focus focusin focusout resize scroll click dblclick " +
10448 "mousedown mouseup mousemove mouseover mouseout mouseenter mouseleave " +
10449 "change select submit keydown keypress keyup contextmenu" ).split( " " ),
10450 function( i, name ) {
10451
10452 // Handle event binding
10453 jQuery.fn[ name ] = function( data, fn ) {
10454 return arguments.length > 0 ?
10455 this.on( name, null, data, fn ) :
10456 this.trigger( name );
10457 };
10458} );
10459
10460jQuery.fn.extend( {
10461 hover: function( fnOver, fnOut ) {
10462 return this.mouseenter( fnOver ).mouseleave( fnOut || fnOver );
10463 }
10464} );
10465
10466
10467
10468
10469jQuery.fn.extend( {
10470
10471 bind: function( types, data, fn ) {
10472 return this.on( types, null, data, fn );
10473 },
10474 unbind: function( types, fn ) {
10475 return this.off( types, null, fn );
10476 },
10477
10478 delegate: function( selector, types, data, fn ) {
10479 return this.on( types, selector, data, fn );
10480 },
10481 undelegate: function( selector, types, fn ) {
10482
10483 // ( namespace ) or ( selector, types [, fn] )
10484 return arguments.length === 1 ?
10485 this.off( selector, "**" ) :
10486 this.off( types, selector || "**", fn );
10487 }
10488} );
10489
10490// Bind a function to a context, optionally partially applying any
10491// arguments.
10492// jQuery.proxy is deprecated to promote standards (specifically Function#bind)
10493// However, it is not slated for removal any time soon
10494jQuery.proxy = function( fn, context ) {
10495 var tmp, args, proxy;
10496
10497 if ( typeof context === "string" ) {
10498 tmp = fn[ context ];
10499 context = fn;
10500 fn = tmp;
10501 }
10502
10503 // Quick check to determine if target is callable, in the spec
10504 // this throws a TypeError, but we will just return undefined.
10505 if ( !isFunction( fn ) ) {
10506 return undefined;
10507 }
10508
10509 // Simulated bind
10510 args = slice.call( arguments, 2 );
10511 proxy = function() {
10512 return fn.apply( context || this, args.concat( slice.call( arguments ) ) );
10513 };
10514
10515 // Set the guid of unique handler to the same of original handler, so it can be removed
10516 proxy.guid = fn.guid = fn.guid || jQuery.guid++;
10517
10518 return proxy;
10519};
10520
10521jQuery.holdReady = function( hold ) {
10522 if ( hold ) {
10523 jQuery.readyWait++;
10524 } else {
10525 jQuery.ready( true );
10526 }
10527};
10528jQuery.isArray = Array.isArray;
10529jQuery.parseJSON = JSON.parse;
10530jQuery.nodeName = nodeName;
10531jQuery.isFunction = isFunction;
10532jQuery.isWindow = isWindow;
10533jQuery.camelCase = camelCase;
10534jQuery.type = toType;
10535
10536jQuery.now = Date.now;
10537
10538jQuery.isNumeric = function( obj ) {
10539
10540 // As of jQuery 3.0, isNumeric is limited to
10541 // strings and numbers (primitives or objects)
10542 // that can be coerced to finite numbers (gh-2662)
10543 var type = jQuery.type( obj );
10544 return ( type === "number" || type === "string" ) &&
10545
10546 // parseFloat NaNs numeric-cast false positives ("")
10547 // ...but misinterprets leading-number strings, particularly hex literals ("0x...")
10548 // subtraction forces infinities to NaN
10549 !isNaN( obj - parseFloat( obj ) );
10550};
10551
10552
10553
10554
10555// Register as a named AMD module, since jQuery can be concatenated with other
10556// files that may use define, but not via a proper concatenation script that
10557// understands anonymous AMD modules. A named AMD is safest and most robust
10558// way to register. Lowercase jquery is used because AMD module names are
10559// derived from file names, and jQuery is normally delivered in a lowercase
10560// file name. Do this after creating the global so that if an AMD module wants
10561// to call noConflict to hide this version of jQuery, it will work.
10562
10563// Note that for maximum portability, libraries that are not jQuery should
10564// declare themselves as anonymous modules, and avoid setting a global if an
10565// AMD loader is present. jQuery is a special case. For more information, see
10566// https://github.com/jrburke/requirejs/wiki/Updating-existing-libraries#wiki-anon
10567
10568if ( typeof define === "function" && define.amd ) {
10569 define( "jquery", [], function() {
10570 return jQuery;
10571 } );
10572}
10573
10574
10575
10576
10577var
10578
10579 // Map over jQuery in case of overwrite
10580 _jQuery = window.jQuery,
10581
10582 // Map over the $ in case of overwrite
10583 _$ = window.$;
10584
10585jQuery.noConflict = function( deep ) {
10586 if ( window.$ === jQuery ) {
10587 window.$ = _$;
10588 }
10589
10590 if ( deep && window.jQuery === jQuery ) {
10591 window.jQuery = _jQuery;
10592 }
10593
10594 return jQuery;
10595};
10596
10597// Expose jQuery and $ identifiers, even in AMD
10598// (#7102#comment:10, https://github.com/jquery/jquery/pull/557)
10599// and CommonJS for browser emulators (#13566)
10600if ( !noGlobal ) {
10601 window.jQuery = window.$ = jQuery;
10602}
10603
10604
10605
10606
10607return jQuery;
10608} );
10609//# sourceURL=/Users/viktoria/node_modules/jquery/dist/jquery.js</script></head>
10610
10611
10612</head>
10613<body>
10614<body class="body loaded"><div class="cc_banner-wrapper "><div class="cc_banner cc_container cc_container--open"><a href="#null" data-cc-event="click:dismiss" target="_blank" class="cc_btn cc_btn_accept_all">Einverstanden</a><p class="cc_message">Cookies erleichtern unter anderem die Bereitstellung unserer Dienste und helfen uns bei der Ausspielung von redaktionellen und werblichen Inhalten sowie der Analyse des Nutzerverhaltens. Mit der Nutzung unserer Dienste erklären Sie sich damit einverstanden, dass wir Cookies verwenden. <a data-cc-if="options.link" target="_self" class="cc_more_info" href="/datenschutzerklaerung">Mehr Infos</a></p><a class="cc_logo" target="_blank" href="http://silktide.com/cookieconsent">Cookie Consent plugin for the EU cookie law</a></div></div>
10615<script type="text/javascript" async="" src="//cdn.tagcommander.com/3513/tc_RTLInteractive_7.js"></script>
10616
10617<div id="fb-root" class=" fb_reset"><div style="position: absolute; top: -10000px; height: 0px; width: 0px;"><div><iframe name="fb_xdm_frame_https" frameborder="0" allowtransparency="true" allowfullscreen="true" scrolling="no" id="fb_xdm_frame_https" aria-hidden="true" title="Facebook Cross Domain Communication Frame" tabindex="-1" src="https://staticxx.facebook.com/connect/xd_arbiter/r/Ms1VZf1Vg1J.js?version=42#channel=f33cc10ed53eb84&origin=https%3A%2F%2Fwww.watchbox.de" style="border: none;"></iframe></div></div><div style="position: absolute; top: -10000px; height: 0px; width: 0px;"><div></div></div></div>
10618<svg style="position: absolute; width: 0; height: 0; overflow: hidden;" version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
10619 <defs>
10620 <symbol id="wb-running" viewBox="0 0 49 32">
10621 <title>running</title>
10622 <path fill="#ff0" style="fill: var(--color1, #ff0)" d="M0.021 17.516v12.92l49.406-17.192v-12.886z"></path>
10623 <path fill="#373737" style="fill: var(--color2, #373737)" d="M4.948 23.718l1.206-0.413v0.758l-2.205 0.758v-4.238l0.999-0.345v3.48z"></path>
10624 <path fill="#373737" style="fill: var(--color2, #373737)" d="M8.324 22.512l-0.723 0.241-0.138 0.827-0.999 0.345 0.861-4.513 1.275-0.448 0.896 3.928-1.034 0.345-0.138-0.724zM7.842 18.033v0.792l-0.723 0.241v-0.792l0.723-0.241zM8.255 21.823l-0.31-1.929-0.276 2.136 0.586-0.207zM8.807 17.688v0.792l-0.723 0.241v-0.792l0.723-0.241z"></path>
10625 <path fill="#373737" style="fill: var(--color2, #373737)" d="M12.459 17.654v3.101c0 0.379-0.069 0.655-0.172 0.861-0.207 0.345-0.586 0.62-1.103 0.792-0.379 0.138-0.655 0.172-0.896 0.103-0.172-0.034-0.276-0.138-0.345-0.241-0.069-0.138-0.103-0.31-0.103-0.586v-3.101l0.999-0.345v3.101c0 0.172 0.034 0.31 0.069 0.345 0.034 0.069 0.138 0.069 0.241 0.034s0.207-0.103 0.241-0.207c0.034-0.103 0.069-0.207 0.069-0.413v-3.101l0.999-0.345z"></path>
10626 <path fill="#373737" style="fill: var(--color2, #373737)" d="M14.043 18.791l0.999-0.345v0.724l-0.999 0.345v1.792l-0.999 0.345v-4.238l2.136-0.724v0.758l-1.137 0.379v0.965z"></path>
10627 <path fill="#373737" style="fill: var(--color2, #373737)" d="M17.42 16.655v3.48l-0.999 0.345v-3.48l-0.896 0.31v-0.758l2.791-0.965v0.758l-0.896 0.31z"></path>
10628 <path fill="#373737" opacity="0.5" style="fill: var(--color2, #373737)" d="M40.676 7.387v4.1l1.654-2.584z"></path>
10629 <path fill="#373737" opacity="0.75" style="fill: var(--color2, #373737)" d="M42.847 6.594v4.134l1.688-2.618z"></path>
10630 <path fill="#373737" style="fill: var(--color2, #373737)" d="M45.052 5.871v4.134l1.654-2.618z"></path>
10631 <path fill="#373737" style="fill: var(--color2, #373737)" d="M21.52 16.276l1.378-0.482v2.308l-0.93 0.31v-0.207c-0.172 0.241-0.413 0.413-0.689 0.517-0.172 0.069-0.31 0.069-0.448 0.069s-0.241-0.069-0.345-0.138c-0.138-0.138-0.207-0.379-0.207-0.758v-1.964c0-0.413 0.069-0.758 0.241-0.965 0.241-0.31 0.586-0.586 1.102-0.758 0.482-0.172 0.861-0.138 1.068 0.069 0.138 0.138 0.207 0.379 0.207 0.689v0.276l-0.999 0.345v-0.413c0-0.241-0.103-0.345-0.31-0.241-0.138 0.034-0.207 0.103-0.276 0.207-0.034 0.103-0.069 0.276-0.069 0.551v1.688c0 0.207 0.034 0.345 0.034 0.379s0 0.069 0.034 0.103c0.069 0.069 0.138 0.103 0.276 0.069 0.207-0.069 0.31-0.241 0.31-0.551v-0.482l-0.379 0.138v-0.758z"></path>
10632 <path fill="#373737" style="fill: var(--color2, #373737)" d="M24.483 15.001l1.068-0.379v0.758l-1.068 0.379v1.068l1.309-0.448v0.758l-2.308 0.792v-4.238l2.171-0.758v0.758l-1.171 0.413v0.896z"></path>
10633 <path fill="#373737" style="fill: var(--color2, #373737)" d="M27.274 14.794v1.792l-0.999 0.345v-4.238l1.516-0.517c0.31-0.103 0.551-0.138 0.689-0.103 0.241 0.069 0.379 0.345 0.379 0.792 0 0.345-0.069 0.62-0.172 0.827-0.069 0.103-0.172 0.207-0.345 0.31 0.172 0.034 0.31 0.069 0.379 0.172 0.034 0.069 0.069 0.138 0.103 0.241s0.034 0.207 0.034 0.276v0.896c0 0.138 0 0.276 0.034 0.413l-1.034 0.345v-1.206c0-0.103 0-0.207-0.034-0.31s-0.069-0.138-0.138-0.172c-0.069-0.034-0.172 0-0.31 0.034 0 0.069-0.034 0.103-0.103 0.103zM27.274 14.105l0.172-0.069c0.138-0.069 0.241-0.103 0.31-0.172 0.069-0.103 0.138-0.276 0.138-0.517 0-0.207-0.034-0.31-0.069-0.379s-0.138-0.069-0.276 0l-0.241 0.069v1.068z"></path>
10634 <path fill="#373737" style="fill: var(--color2, #373737)" d="M31.133 14.484l-0.724 0.241-0.138 0.827-0.999 0.345 0.861-4.513 1.275-0.448 0.896 3.928-1.034 0.345-0.138-0.723zM31.064 13.795l-0.31-1.929-0.276 2.136 0.586-0.207z"></path>
10635 <path fill="#373737" style="fill: var(--color2, #373737)" d="M32.648 10.522l1.413-0.482c0.379-0.138 0.655-0.138 0.861-0.069 0.172 0.069 0.276 0.276 0.31 0.586 0.034 0.172 0.034 0.655 0.034 1.413 0 0.413 0 0.689-0.034 0.861 0 0.172-0.034 0.31-0.069 0.448-0.069 0.241-0.172 0.413-0.345 0.551-0.172 0.172-0.413 0.31-0.724 0.413l-1.447 0.517v-4.238zM33.613 13.726l0.138-0.034c0.241-0.069 0.379-0.207 0.448-0.345 0.034-0.069 0.034-0.172 0.069-0.276s0-0.413 0.034-0.896c0-0.655-0.034-1.034-0.034-1.137s-0.034-0.172-0.069-0.241c-0.069-0.069-0.172-0.069-0.345 0l-0.172 0.069v2.86z"></path>
10636 <path fill="#373737" style="fill: var(--color2, #373737)" d="M36.817 10.729l1.068-0.379v0.758l-1.068 0.379v1.068l1.309-0.448v0.758l-2.308 0.792v-4.238l2.171-0.758v0.758l-1.171 0.413v0.896z"></path>
10637 </symbol>
10638 <symbol id="wb-spinner" viewBox="0 0 32 32">
10639 <title>spinner</title>
10640 <path d="M20 0v12l4.485-4.485c2.266 2.267 3.515 5.28 3.515 8.485s-1.248 6.219-3.515 8.485c-2.267 2.266-5.28 3.515-8.485 3.515s-6.219-1.248-8.485-3.515c-2.266-2.267-3.515-5.28-3.515-8.485s1.248-6.219 3.515-8.485c0.189-0.189 0.384-0.371 0.583-0.545l-2.634-3.010c-3.349 2.933-5.464 7.24-5.464 12.041 0 8.837 7.163 16 16 16s16-7.163 16-16c0-4.418-1.791-8.418-4.687-11.313l4.687-4.687h-12z"></path>
10641 </symbol>
10642 <symbol id="wb-delete" viewBox="0 0 32 32">
10643 <title>delete</title>
10644 <path d="M16 0c-8.96 0-16 7.040-16 16s7.040 16 16 16 16-7.040 16-16-7.040-16-16-16zM25.6 22.4l-3.2 3.2-6.4-6.4-6.4 6.4-3.2-3.2 6.4-6.4-6.4-6.4 3.2-3.2 6.4 6.4 6.4-6.4 3.2 3.2-6.4 6.4 6.4 6.4z"></path>
10645 </symbol>
10646 <symbol id="wb-logout" viewBox="0 0 32 32">
10647 <title>logout</title>
10648 <path d="M16 0v0c-8.889 0-16 7.111-16 16v0c0 8.889 7.111 16 16 16v0c8.889 0 16-7.111 16-16v0c0-8.889-7.111-16-16-16zM14.756 7.822c0-0.711 0.533-1.244 1.244-1.244 0.356 0 0.711 0.178 0.889 0.356s0.356 0.533 0.356 0.889v0.533c0 2.844 0 5.689 0 8.533 0 0.711-0.533 1.244-1.244 1.244v0c-0.711 0-1.244-0.533-1.244-1.244 0-1.067 0-2.133 0-3.2 0-0.533 0-0.889 0-1.422v-0.178c0-0.356 0-0.711 0-0.889 0-1.244 0-2.311 0-3.378zM17.6 25.244c-4.8 0.889-9.422-2.311-10.311-7.111 0 0 0 0 0 0-0.533-3.022 0.178-5.689 2.311-8 0.356-0.178 0.711-0.356 1.067-0.356s0.533 0.178 0.889 0.356c0.178 0.178 0.178 0.533 0.356 0.889 0 0.356-0.178 0.711-0.356 0.889-1.067 1.067-1.6 2.133-1.778 3.556-0.533 3.556 1.956 6.756 5.511 7.289s6.756-1.956 7.289-5.511c0.178-1.956-0.356-3.733-1.778-5.333-0.356-0.356-0.533-0.889-0.356-1.244 0.178-0.711 0.889-1.067 1.6-0.889 0.178 0 0.356 0.178 0.533 0.356 1.6 1.6 2.311 3.378 2.667 5.511 0 0.178 0 0.356 0 0.533 0 0 0 0.178 0 0.178-0.356 4.444-3.378 8-7.644 8.889z"></path>
10649 </symbol>
10650 <symbol id="wb-cog" viewBox="0 0 32 32">
10651 <title>cog</title>
10652 <path d="M12.978 0.245l-0.711 4.089c-0.711 0.356-1.422 0.533-1.956 0.889l-3.378-2.311-4.267 4.267 2.311 3.378c-0.356 0.711-0.711 1.422-0.889 1.956l-4.089 0.533v6.222l4.089 0.711c0.356 0.711 0.533 1.422 0.889 1.956l-2.311 3.378 4.267 4.267 3.378-2.311c0.711 0.356 1.422 0.711 1.956 0.889l0.711 4.089h6.222l0.711-4.089c0.711-0.356 1.422-0.533 1.956-0.889l3.378 2.311 4.267-4.267-2.311-3.378c0.356-0.711 0.711-1.422 0.889-1.956l3.911-1.067v-6.222l-4.089-0.711c-0.356-0.711-0.533-1.422-0.889-1.956l2.311-3.378-4.267-4.267-3.378 2.311c-0.711-0.356-1.422-0.711-1.956-0.889l-0.711-4.089-6.044 0.533zM16 8.423c4.089 0 7.644 3.556 7.644 7.644s-3.556 7.644-7.644 7.644-7.644-3.556-7.644-7.644 3.378-7.644 7.644-7.644zM16 10.023c-3.378 0-6.222 2.667-6.222 6.222 0 3.378 2.667 6.222 6.222 6.222 3.378 0 6.222-2.667 6.222-6.222-0.356-3.556-3.022-6.222-6.222-6.222z"></path>
10653 </symbol>
10654 <symbol id="wb-mail" viewBox="0 0 52 32">
10655 <title>mail</title>
10656 <path d="M0.582 0.11c-0.291 0-0.582 0.291-0.582 0.582v1.745l26.182 18.618 26.182-18.618v-1.745c0-0.291-0.291-0.582-0.582-0.582h-51.2zM0 5.346v26.182c0 0.291 0.291 0.582 0.582 0.582h50.909c0.291 0 0.582-0.291 0.582-0.582v-26.182l-25.309 18.036c-0.291 0.291-1.164 0.291-1.455 0l-25.309-18.036z"></path>
10657 </symbol>
10658 <symbol id="wb-edit" viewBox="0 0 32 32">
10659 <title>edit</title>
10660 <path d="M24.711 0.067l-3.733 3.733 7.289 7.289 3.733-3.733-7.289-7.289zM19.733 4.867l-16.533 16.356 7.289 7.289 16.533-16.533-7.289-7.111zM2.133 22.823l-2.133 9.244 9.244-2.133-7.111-7.111z"></path>
10661 </symbol>
10662 <symbol id="wb-cancel" viewBox="0 0 32 32">
10663 <title>cancel</title>
10664 <path d="M16 0c-8.889 0-16 7.111-16 16s7.111 16 16 16 16-7.111 16-16-7.111-16-16-16zM16 4.978c6.222 0 11.022 4.978 11.022 11.022 0 2.133-0.711 4.089-1.778 5.867l-15.111-15.111c1.6-1.244 3.556-1.778 5.867-1.778zM16 27.022c-6.222 0-11.022-4.978-11.022-11.022 0-2.133 0.711-4.089 1.778-5.867l15.111 15.111c-1.778 1.067-3.733 1.778-5.867 1.778z"></path>
10665 </symbol>
10666 <symbol id="wb-rating" viewBox="0 0 32 32">
10667 <title>rating</title>
10668 <path d="M16 0l4.945 10.473 11.055 1.745-8 8.291 1.891 11.491-9.891-5.382-9.891 5.382 1.891-11.491-8-8.291 11.2-1.745z"></path>
10669 </symbol>
10670 <symbol id="wb-whatsapp" viewBox="0 0 32 32">
10671 <title>whatsapp</title>
10672 <path d="M27.2 4.655c-2.909-3.055-6.836-4.655-11.2-4.655-8.727 0-15.855 7.127-15.855 15.855 0 2.764 0.727 5.527 2.182 8l-2.327 8.145 8.436-2.182c2.327 1.309 4.945 2.036 7.564 2.036v0 0c8.727 0 16-7.127 16-15.855-0.145-4.364-1.745-8.291-4.8-11.345zM16 29.091v0c-2.327 0-4.8-0.582-6.691-1.891l-0.436-0.291-4.945 1.309 1.309-4.8-0.436-0.436c-1.309-2.182-1.891-4.509-1.891-6.982 0-7.418 5.818-13.236 13.091-13.236 3.491 0 6.836 1.309 9.309 3.782s3.927 5.818 3.927 9.309c0 7.273-5.964 13.236-13.236 13.236zM23.273 19.055c-0.436-0.291-2.327-1.164-2.764-1.309s-0.582-0.291-0.873 0.291c-0.291 0.436-1.018 1.309-1.309 1.6s-0.436 0.291-0.873 0.145c-0.436-0.291-1.6-0.582-3.2-2.036-1.164-1.018-2.036-2.327-2.182-2.764-0.291-0.436 0-0.582 0.145-0.873 0.145-0.145 0.436-0.436 0.582-0.727 0.291-0.145 0.291-0.291 0.436-0.436 0.145-0.291 0.145-0.436 0-0.727s-0.873-2.182-1.309-3.055c-0.291-0.727-0.436-0.582-0.727-0.582s-0.436 0-0.727 0-0.727 0-1.164 0.436c-0.291 0.436-1.309 1.455-1.309 3.2 0 2.036 1.309 3.782 1.6 4.073s2.764 4.218 6.691 5.964c1.018 0.436 1.745 0.582 2.182 0.873 1.018 0.291 1.891 0.291 2.473 0.145 0.727-0.145 2.327-1.018 2.764-1.891s0.436-1.745 0.291-1.891c-0.145 0-0.291-0.145-0.727-0.436z"></path>
10673 </symbol>
10674 <symbol id="wb-close" viewBox="0 0 32 32">
10675 <title>close</title>
10676 <path d="M29.653 24.96l-9.173-8.96 9.173-8.96-4.693-4.693-8.96 9.173-8.96-9.173-4.693 4.693 9.173 8.96-9.173 8.96 4.693 4.693 8.96-9.173 8.96 9.173z"></path>
10677 </symbol>
10678 <symbol id="wb-alert" viewBox="0 0 38 32">
10679 <title>alert</title>
10680 <path d="M37.271 29.176l-17.129-28.424c-0.376-0.753-1.506-0.941-2.259-0.565-0.188 0.188-0.376 0.376-0.565 0.565l-17.129 28.424c-0.565 0.753-0.376 2.071 0.565 2.447 0.376 0.188 0.565 0.376 0.941 0.376h34.259c0.941 0 1.694-0.753 1.506-1.882 0.188-0.376 0-0.753-0.188-0.941zM20.706 26.353h-3.765v-3.765h3.765v3.765zM20.706 18.824h-3.765v-7.529h3.765v7.529z"></path>
10681 </symbol>
10682 <symbol id="wb-logo" viewBox="0 0 46 32">
10683 <title>logo</title>
10684 <path fill="#ff0" style="fill: var(--color1, #ff0)" d="M0 13.509v2.924l1.516-0.46 1.191 7.147 4.115-1.218c0 0 0.704-2.87 0.758-4.115 0.108 1.164 0.677 3.682 0.677 3.682l4.44-1.272 0.623-10.64-3.438 1.002c0 0-0.298 4.981-0.298 6.146 0-1.164-1.002-5.767-1.002-5.767l-2.626 0.785c0 0-0.975 5.198-0.975 6.389 0-1.164-0.406-5.956-0.406-5.956l-4.575 1.354zM18.112 13.888l-0.893 0.271c0-0.108 0.325-2.22 0.325-2.328 0-0.19 0.108-1.056 0.108-1.056s0.108 0.785 0.108 0.975c0.027 0.108 0.352 2.058 0.352 2.139zM21.902 17.516l-1.706-9.936-4.873 1.435-1.489 0.46v2.924l0.92-0.271-1.3 7.905 3.357-1.002c0 0 0.217-1.597 0.271-2.653l1.137-0.325c0.054 0.866 0.298 2.464 0.298 2.464l3.384-1.002zM26.558 8.663l1.787-0.514v-2.951l-7.039 2.085v2.924l1.787-0.514v7.499l3.465-1.029v-7.499zM32.379 11.371c-0.054-0.217-0.081-1.002-0.081-2.22 0-0.677 0.027-1.57 0.081-2.003 0.027-0.217 0.162-0.433 0.406-0.487 0.271-0.081 0.406 0.027 0.406 0.244 0 0.298 0.027 0.812 0.027 1.191l3.303-0.975c0-0.704 0-1.272-0.054-1.651-0.135-1.733-1.327-2.382-3.628-1.706-2.274 0.677-3.547 2.030-3.844 3.411-0.189 0.893-0.271 2.003-0.271 3.086 0 1.137 0.054 2.707 0.406 3.384 0.406 0.92 1.435 1.435 3.601 0.785 2.464-0.731 3.628-2.22 3.79-3.682 0.027-0.406 0.027-1.11 0.027-1.814l-3.303 0.975c0 0.541 0 0.893-0.054 1.191-0.027 0.271-0.135 0.406-0.379 0.487-0.217 0.108-0.352 0.027-0.433-0.217zM46.024 2.924v-2.924l-1.191 0.352-3.411 1.002v3.844l-0.948 0.298v-3.871l-3.276 0.975v10.423l3.276-0.975v-3.79l0.948-0.298v3.817l3.411-1.002v-7.499l1.191-0.352z"></path>
10685 <path fill="#ff0" style="fill: var(--color1, #ff0)" d="M17.002 27.452c0 0.244 0 0.406-0.027 0.569-0.027 0.189-0.135 0.298-0.325 0.352l-0.623 0.189v-1.597l0.65-0.189c0.135-0.054 0.271-0.054 0.325 0.162 0 0.135 0 0.271 0 0.514zM16.948 23.58c0 0.325 0 0.46-0.027 0.596-0.027 0.217-0.244 0.352-0.325 0.379l-0.569 0.162v-1.651l0.569-0.162c0.135-0.054 0.271-0.027 0.325 0.054 0 0.135 0.027 0.325 0.027 0.623zM18.734 24.799c0.65-0.244 1.029-0.596 1.3-1.002 0.352-0.569 0.46-1.272 0.46-2.085 0-0.758-0.189-1.218-0.541-1.489-0.433-0.325-1.137-0.406-2.355-0.027l-3.465 1.056-2.382 0.704v2.924l0.893-0.271v7.472l4.9-1.489c1.272-0.379 2.112-0.893 2.545-1.516 0.433-0.569 0.623-1.354 0.623-2.301 0-0.758-0.081-1.354-0.487-1.678-0.325-0.298-0.785-0.46-1.489-0.298zM25.584 22.904c0 0.975-0.027 1.733-0.108 2.274-0.027 0.217-0.162 0.433-0.433 0.514-0.298 0.081-0.379-0.054-0.406-0.244-0.081-0.541-0.108-1.245-0.108-2.22 0-0.948 0.027-1.76 0.054-2.085 0.054-0.379 0.135-0.569 0.46-0.677s0.406 0.081 0.46 0.352c0.081 0.352 0.081 1.191 0.081 2.085zM28.86 19.059c-0.325-1.354-1.489-2.003-3.817-1.272-2.599 0.785-3.547 2.328-3.817 3.79-0.108 0.623-0.108 1.3-0.108 2.653 0 1.57 0.027 2.409 0.135 2.897 0.244 1.462 1.435 2.003 3.79 1.3 2.382-0.731 3.547-2.058 3.817-3.79 0.108-0.623 0.162-1.354 0.162-2.897 0-1.408 0-2.058-0.162-2.68zM37.008 14.349l0.027-0.054-2.22 0.677-0.162 0.054-1.029 0.298-0.677 1.895-0.677-1.489-3.655 1.11 2.355 4.277-2.491 6.118 3.655-1.11 0.623-1.678 0.623 1.299 3.655-1.11-2.355-4.169 1.083-2.897 1.218-0.352v-2.87z"></path>
10686 <path fill="#fff" style="fill: var(--color2, #fff)" d="M7.337 24.717l3.167 2.68-3.14 3.898z"></path>
10687 </symbol>
10688 <symbol id="wb-more_highlight" viewBox="0 0 28 32">
10689 <title>more_highlight</title>
10690 <path fill="#ff0" style="fill: var(--color1, #ff0)" d="M0 8.731v23.269l27.676-8.783v-23.217l-27.676 8.731z"></path>
10691 <path fill="#373737" style="fill: var(--color3, #373737)" d="M17.297 13.591v4.506l3.459-0.999v-4.51l-3.459 1.003z"></path>
10692 <path fill="#373737" style="fill: var(--color3, #373737)" d="M12.108 15.226v4.437l3.459-1.003v-4.441l-3.459 1.008z"></path>
10693 <path fill="#373737" style="fill: var(--color3, #373737)" d="M6.919 16.856v4.363l3.459-0.999v-4.368l-3.459 1.003z"></path>
10694 </symbol>
10695 <symbol id="wb-more" viewBox="0 0 28 32">
10696 <title>more</title>
10697 <path fill="#fff" style="fill: var(--color2, #fff)" d="M0 8.735v23.265l27.676-8.778v-23.222z"></path>
10698 <path fill="#373737" style="fill: var(--color3, #373737)" d="M17.297 13.578v4.497l3.459-0.995v-4.497z"></path>
10699 <path fill="#373737" style="fill: var(--color3, #373737)" d="M12.108 15.222v4.454l3.459-0.995v-4.454z"></path>
10700 <path fill="#373737" style="fill: var(--color3, #373737)" d="M6.919 16.865v4.368l3.459-0.995v-4.368z"></path>
10701 </symbol>
10702 <symbol id="wb-overview" viewBox="0 0 28 32">
10703 <title>overview</title>
10704 <path fill="#fff" style="fill: var(--color2, #fff)" d="M0 8.735v23.265l27.676-8.778v-23.222z"></path>
10705 <path fill="#373737" style="fill: var(--color3, #373737)" d="M17.297 15.914v4.541l3.459-0.995v-4.541z"></path>
10706 <path fill="#373737" style="fill: var(--color3, #373737)" d="M12.108 17.557v4.454l3.459-0.995v-4.454z"></path>
10707 <path fill="#373737" style="fill: var(--color3, #373737)" d="M6.919 19.2v4.368l3.459-0.995v-4.368z"></path>
10708 <path fill="#373737" style="fill: var(--color3, #373737)" d="M17.297 9.297v4.497l3.459-0.995v-4.497z"></path>
10709 <path fill="#373737" style="fill: var(--color3, #373737)" d="M12.108 10.941v4.411l3.459-0.995v-4.411z"></path>
10710 <path fill="#373737" style="fill: var(--color3, #373737)" d="M6.919 12.584v4.368l3.459-1.038v-4.368z"></path>
10711 </symbol>
10712 <symbol id="wb-overview_highlight" viewBox="0 0 28 32">
10713 <title>overview_highlight</title>
10714 <path fill="#ff0" style="fill: var(--color1, #ff0)" d="M0 8.731v23.269l27.676-8.783v-23.217l-27.676 8.731z"></path>
10715 <path fill="#373737" style="fill: var(--color3, #373737)" d="M17.297 15.935v4.506l3.459-0.999v-4.515l-3.459 1.008z"></path>
10716 <path fill="#373737" style="fill: var(--color3, #373737)" d="M12.108 17.565v4.437l3.459-0.999v-4.441l-3.459 1.003z"></path>
10717 <path fill="#373737" style="fill: var(--color3, #373737)" d="M6.919 19.2v4.363l3.459-0.999v-4.368l-3.459 1.003z"></path>
10718 <path fill="#373737" style="fill: var(--color3, #373737)" d="M17.297 9.302v4.506l3.459-0.999v-4.515l-3.459 1.008z"></path>
10719 <path fill="#373737" style="fill: var(--color3, #373737)" d="M12.108 10.932v4.437l3.459-0.999v-4.441l-3.459 1.003z"></path>
10720 <path fill="#373737" style="fill: var(--color3, #373737)" d="M6.919 12.566v4.363l3.459-0.999v-4.372l-3.459 1.008z"></path>
10721 </symbol>
10722 <symbol id="wb-play2" viewBox="0 0 28 32">
10723 <title>play2</title>
10724 <path fill="#fff" style="fill: var(--color2, #fff)" d="M0 8.735v23.265l27.676-8.778v-23.222z"></path>
10725 <path fill="#373737" style="fill: var(--color3, #373737)" d="M12.065 8.432v16.735l6.746-10.551z"></path>
10726 </symbol>
10727 <symbol id="wb-play_highlighted" viewBox="0 0 28 32">
10728 <title>play_highlighted</title>
10729 <path fill="#ff0" style="fill: var(--color1, #ff0)" d="M0 8.731v23.269l27.676-8.783v-23.217l-27.676 8.731z"></path>
10730 <path fill="#373737" style="fill: var(--color3, #373737)" d="M12.048 8.411v16.739l6.759-10.538-6.759-6.201z"></path>
10731 </symbol>
10732 <symbol id="wb-series" viewBox="0 0 36 32">
10733 <title>series</title>
10734 <path fill="#ff0" style="fill: var(--color1, #ff0)" d="M0 12.314v19.686l35.556-12.32v-19.68l-35.556 12.314z"></path>
10735 <path fill="#373737" style="fill: var(--color3, #373737)" d="M8.942 22.756c-1.511 0.527-2.246 0.219-2.37-0.664 0-0.124-0.041-0.492-0.036-0.741l1.76-0.61c0.002 0.165 0.017 0.324 0.044 0.48 0.057 0.178 0.27 0.213 0.661 0.077s0.593-0.367 0.593-0.747-0.136-0.498-0.806-0.593c-0.178 0-0.593-0.089-0.782-0.113-0.895-0.107-1.44-0.29-1.428-1.476s0.913-2.281 2.406-2.803 2.133-0.071 2.281 0.782c0.031 0.206 0.050 0.446 0.053 0.689l-1.742 0.596c0-0.015 0.001-0.032 0.001-0.050 0-0.133-0.013-0.263-0.038-0.389-0.051-0.189-0.223-0.254-0.591-0.124-0.468 0.166-0.593 0.385-0.593 0.664 0 0.409 0.308 0.51 0.936 0.533 0.196 0 0.593 0.071 0.747 0.077 0.877 0.071 1.333 0.444 1.321 1.541-0.024 1.268-0.853 2.317-2.418 2.868z"></path>
10736 <path fill="#373737" style="fill: var(--color3, #373737)" d="M11.959 21.588l0.095-7.022 4.196-1.47v1.636l-2.465 0.853v1.067l2.329-0.818v1.588l-2.364 0.824v1.12l2.465-0.865v1.606z"></path>
10737 <path fill="#373737" style="fill: var(--color3, #373737)" d="M21.511 14.649c-0.123 0.323-0.328 0.592-0.588 0.791l1.003 2.64-1.813 0.646-0.818-2.287-0.699 0.243-0.036 2.59-1.73 0.593 0.095-7.022 3.052-1.073c0.676-0.237 1.15-0.172 1.416 0.136 0.223 0.325 0.357 0.728 0.357 1.161 0 0.082-0.005 0.162-0.014 0.241 0.001 0.011 0.002 0.035 0.002 0.059 0 0.46-0.083 0.901-0.234 1.309zM19.935 13.665c-0.077-0.136-0.225-0.184-0.427-0.113l-0.841 0.296v1.375l0.889-0.32c0.152-0.061 0.274-0.171 0.348-0.31 0.066-0.146 0.107-0.312 0.114-0.487-0.002-0.161-0.034-0.312-0.092-0.449z"></path>
10738 <path fill="#373737" style="fill: var(--color3, #373737)" d="M22.489 17.89l0.095-7.022 1.831-0.646-0.119 7.028z"></path>
10739 <path fill="#373737" style="fill: var(--color3, #373737)" d="M25.114 16.972l0.095-7.022 4.196-1.47v1.636l-2.441 0.859v1.067l2.329-0.818v1.588l-2.388 0.818v1.12l2.465-0.865v1.606z"></path>
10740 </symbol>
10741 <symbol id="wb-remove" viewBox="0 0 32 32">
10742 <title>remove</title>
10743 <path d="M0 12.8h32v6.4h-32v-6.4z"></path>
10744 </symbol>
10745 <symbol id="wb-item-toggle" viewBox="0 0 61 32">
10746 <title>item-toggle</title>
10747 <path d="M30.545 31.373l-29.586-24.075 5.801-6.671 23.785 19.724 23.785-19.724 5.801 6.671z"></path>
10748 </symbol>
10749 <symbol id="wb-next" viewBox="0 0 14 32">
10750 <title>next</title>
10751 <path d="M1.533 31.993l-1.53-1.391 11.264-14.602-11.264-14.602 1.53-1.391 12.377 15.993z"></path>
10752 </symbol>
10753 <symbol id="wb-check" viewBox="0 0 45 32">
10754 <title>check</title>
10755 <path d="M38.532 0l-19.101 19.101-13.065-13.065-6.367 6.367 19.597 19.597 25.468-25.468-6.532-6.532z"></path>
10756 </symbol>
10757 <symbol id="wb-add" viewBox="0 0 32 32">
10758 <title>add</title>
10759 <path d="M32 12.8h-12.8v-12.8h-6.4v12.8h-12.8v6.4h12.8v12.8h6.4v-12.8h12.8z"></path>
10760 </symbol>
10761 <symbol id="wb-play" viewBox="0 0 18 32">
10762 <title>play</title>
10763 <path d="M17.778 16l-17.778 16v-32z"></path>
10764 </symbol>
10765 <symbol id="wb-search" viewBox="0 0 32 32">
10766 <title>search</title>
10767 <path d="M29.594 25.882l-6.584-6.542-0.106-0.149c1.286-1.912 2.053-4.266 2.053-6.799 0-0.003 0-0.006 0-0.009 0-0.012 0-0.027 0-0.041 0-6.867-5.567-12.434-12.434-12.434s-12.434 5.567-12.434 12.434c0 6.867 5.567 12.434 12.434 12.434 2.542 0 4.905-0.763 6.874-2.072l0.050 0.135 6.584 6.542c0.878 0.896 1.801 1.738 2.769 2.526l3.156-3.526c-0.106-0.202-2.191-2.34-2.361-2.5zM12.501 20.563c-4.452-0.024-8.052-3.639-8.052-8.094 0-4.471 3.624-8.095 8.095-8.095s8.095 3.624 8.095 8.094c-0.030 4.459-3.652 8.063-8.116 8.063-0.008 0-0.015 0-0.023-0z"></path>
10768 </symbol>
10769 <symbol id="wb-user" viewBox="0 0 34 32">
10770 <title>user</title>
10771 <path d="M17.589 16.405c4.095 0 7.465-3.669 7.465-8.201 0-6.281-3.327-8.201-7.465-8.201s-7.465 1.92-7.465 8.201c0 4.532 3.327 8.201 7.465 8.201z"></path>
10772 <path d="M34.13 31.996s-4.372-11.112-4.756-11.304l-5.801-2.847c-0.128-0.064-3.978 1.824-5.983 1.824s-5.855-1.888-5.993-1.824l-5.801 2.847c-0.384 0.192-5.791 11.304-5.791 11.304z"></path>
10773 </symbol>
10774 <symbol id="wb-menu" viewBox="0 0 43 32">
10775 <title>menu</title>
10776 <path d="M0.005 0.004h42.657v6.399h-42.657v-6.399z"></path>
10777 <path d="M0.005 12.801h42.657v6.399h-42.657v-6.399z"></path>
10778 <path d="M0.005 25.598h42.657v6.399h-42.657v-6.399z"></path>
10779 </symbol>
10780 <symbol id="wb-twitter" viewBox="0 0 39 32">
10781 <title>twitter</title>
10782 <path d="M39.393 3.788c-1.349 0.626-2.914 1.085-4.556 1.298 1.594-1.014 2.851-2.58 3.455-4.44-1.463 0.859-3.186 1.561-5.025 1.948-1.582-1.543-3.669-2.515-5.983-2.515-4.438 0-8.040 3.575-8.084 8.002 0.001 0.658 0.078 1.293 0.22 1.903-6.748-0.404-12.673-3.606-16.645-8.466-0.725 1.126-1.134 2.531-1.134 4.032 0 2.786 1.409 5.243 3.554 6.697-1.32-0.020-2.575-0.388-3.668-1.008l0.040 0.125c0.008 3.911 2.788 7.17 6.479 7.919-0.593 0.194-1.334 0.303-2.1 0.309-0.004 0-0.006 0-0.007 0-0.539 0-1.066-0.052-1.576-0.152 1.119 3.242 4.081 5.549 7.592 5.625-2.721 2.15-6.208 3.448-9.999 3.448-0.013 0-0.025 0-0.038-0-0.69-0.014-1.354-0.065-2.007-0.154 3.584 2.287 7.861 3.641 12.455 3.641 0.010 0 0.021 0 0.031-0 14.862 0 22.986-12.317 22.986-22.988v-1.045c1.591-1.153 2.931-2.539 3.999-4.122z"></path>
10783 </symbol>
10784 <symbol id="wb-facebook" viewBox="0 0 15 32">
10785 <title>facebook</title>
10786 <path d="M3.221 6.203v4.396h-3.221v5.382h3.221v16.019h6.632v-16.006h4.447s0.417-2.527 0.619-5.407h-5.053v-3.689c0.134-0.725 0.752-1.27 1.501-1.289l3.615-0v-5.609h-4.965c-6.948 0-6.797 5.394-6.797 6.203z"></path>
10787 </symbol>
10788 <symbol id="wb-instagram" viewBox="0 0 32 32">
10789 <title>instagram</title>
10790 <path d="M16.006 2.883c4.275 0 4.784 0 6.462 0.099 1.069 0.012 2.088 0.211 3.031 0.567 0.663 0.264 1.277 0.687 1.776 1.22 0.538 0.504 0.961 1.118 1.234 1.808 0.347 0.915 0.547 1.934 0.558 2.999 0.075 1.695 0.099 2.192 0.099 6.467s0 4.784-0.099 6.462c-0.012 1.069-0.211 2.088-0.567 3.031-0.53 1.336-1.615 2.422-2.976 2.959-0.917 0.348-1.937 0.548-3.001 0.559-1.695 0.075-2.192 0.099-6.467 0.099s-4.784 0-6.462-0.099c-1.069-0.012-2.088-0.211-3.031-0.567-0.663-0.264-1.277-0.687-1.776-1.22-0.538-0.504-0.961-1.118-1.234-1.808-0.347-0.915-0.547-1.934-0.558-2.999-0.075-1.695-0.099-2.192-0.099-6.467s0-4.784 0.099-6.462c0.012-1.069 0.211-2.088 0.567-3.031 0.264-0.663 0.687-1.277 1.22-1.776 0.504-0.538 1.118-0.961 1.808-1.234 0.915-0.347 1.934-0.547 2.999-0.558 1.695-0.075 2.192-0.099 6.467-0.099zM16.056-0.050c-4.399 0.050-4.946 0.050-6.649 0.149-1.405 0.029-2.737 0.3-3.97 0.773-1.028 0.395-1.973 1.021-2.752 1.811-0.792 0.781-1.418 1.726-1.822 2.781-0.464 1.206-0.735 2.539-0.764 3.931-0.1 1.715-0.1 2.262-0.1 6.611s0 4.896 0.099 6.599c0.029 1.405 0.3 2.737 0.773 3.97 0.399 1.029 1.029 1.974 1.823 2.752 0.78 0.797 1.726 1.427 2.781 1.835 1.206 0.464 2.539 0.735 3.931 0.764 1.715 0.075 2.262 0.1 6.611 0.1s4.896 0 6.599-0.099c1.405-0.029 2.737-0.3 3.97-0.773 2.079-0.822 3.756-2.499 4.585-4.602 0.465-1.208 0.736-2.541 0.765-3.933 0.075-1.715 0.1-2.262 0.1-6.611s0-4.896-0.099-6.599c-0.029-1.405-0.3-2.737-0.773-3.97-0.399-1.029-1.029-1.974-1.823-2.752-0.788-0.795-1.742-1.421-2.806-1.823-1.206-0.464-2.539-0.735-3.931-0.763-1.715-0.1-2.262-0.1-6.599-0.1z"></path>
10791 <path d="M16.006 7.779c-4.537 0-8.214 3.678-8.214 8.214s3.678 8.214 8.214 8.214c4.537 0 8.214-3.678 8.214-8.214s-3.678-8.214-8.214-8.214zM16.006 21.325c-2.944 0-5.331-2.387-5.331-5.331s2.387-5.331 5.331-5.331c2.944 0 5.331 2.387 5.331 5.331 0 0.004 0 0.008 0 0.012 0 2.944-2.387 5.331-5.331 5.331 0 0 0 0 0 0z"></path>
10792 <path d="M26.47 7.456c0 1.064-0.862 1.926-1.926 1.926s-1.926-0.862-1.926-1.926c0-1.064 0.862-1.926 1.926-1.926s1.926 0.862 1.926 1.926z"></path>
10793 </symbol>
10794 </defs>
10795</svg>
10796
10797<div class="page-load-indicator js-page-load-container" style="animation: unset;">
10798 <div class="page-load-indicator__logo">
10799 <svg class="header__logo" aria-hidden="true">
10800 <use xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="#wb-logo"></use>
10801 </svg>
10802 </div>
10803</div>
10804
10805<div class="page-wrapper">
10806
10807<header class="header js-header header_shrink_for_video">
10808
10809 <div class="header__container">
10810 <a title="Watchbox" href="/" aria-label="Watchbox Home">
10811 <svg class="header__logo" aria-hidden="true">
10812 <title>Watchbox</title>
10813 <use xlink:href="#wb-logo"></use>
10814 </svg>
10815 </a>
10816
10817
10818<ul class="navigation header__navigation">
10819 <li class="navigation__item navigation__item_active">
10820 <a class="navigation-link text_navigation-link" href="/" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'top', 'startseite', null, null, null, event);">
10821 Startseite
10822 </a>
10823 </li>
10824 <li class="navigation__item navigation__item_stack navigation-stoebern">
10825 <a class="navigation-link text_navigation-link" href="/browse/" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'top', 'stöbern', null, null, null, event);">
10826 Stöbern
10827 </a>
10828
10829 <div class="navigation-stoebern__content js-navi-stoebern">
10830 <svg class="navigation-link__icon text_navigation-link" role="img">
10831 <title>Stöbern</title>
10832 <use xlink:href="#wb-item-toggle"></use>
10833 </svg>
10834
10835<div class="stoebern-overlay js-stoebern-overlay">
10836 <a class="stoebern-overlay__all text_flyout-link-large" href="/browse/">
10837 Alle Durchstöbern <svg class="icon" aria-hidden="true"><use xlink:href="#wb-item-toggle"></use></svg>
10838 </a>
10839
10840 <div class="stoebern-overlay__list">
10841
10842<ul class="genre-list">
10843
10844<li class="genre-list__item">
10845 <a class="text_flyout-link-small" href="/anime/" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'top', 'stöbern I Anime', null, null, null, event);">
10846 Anime </a>
10847</li>
10848<li class="genre-list__item">
10849 <a class="text_flyout-link-small" href="/british/" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'top', 'stöbern I British', null, null, null, event);">
10850 British </a>
10851</li>
10852<li class="genre-list__item">
10853 <a class="text_flyout-link-small" href="/science-fiction/" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'top', 'stöbern I Science Fiction', null, null, null, event);">
10854 Science Fiction </a>
10855</li>
10856<li class="genre-list__item">
10857 <a class="text_flyout-link-small" href="/horror/" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'top', 'stöbern I Horror', null, null, null, event);">
10858 Horror </a>
10859</li>
10860<li class="genre-list__item">
10861 <a class="text_flyout-link-small" href="/independent/" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'top', 'stöbern I Independent', null, null, null, event);">
10862 Independent </a>
10863</li>
10864<li class="genre-list__item">
10865 <a class="text_flyout-link-small" href="/komoedie/" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'top', 'stöbern I Komödie', null, null, null, event);">
10866 Komödie </a>
10867</li>
10868<li class="genre-list__item">
10869 <a class="text_flyout-link-small" href="/thriller/" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'top', 'stöbern I Thriller', null, null, null, event);">
10870 Thriller </a>
10871</li>
10872<li class="genre-list__item">
10873 <a class="text_flyout-link-small" href="/show/" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'top', 'stöbern I Show', null, null, null, event);">
10874 Show </a>
10875</li>
10876<li class="genre-list__item">
10877 <a class="text_flyout-link-small" href="/erotik/" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'top', 'stöbern I Erotik', null, null, null, event);">
10878 Erotik </a>
10879</li>
10880<li class="genre-list__item">
10881 <a class="text_flyout-link-small" href="/animation/" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'top', 'stöbern I Animation', null, null, null, event);">
10882 Animation </a>
10883</li>
10884<li class="genre-list__item">
10885 <a class="text_flyout-link-small" href="/action/" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'top', 'stöbern I Action', null, null, null, event);">
10886 Action </a>
10887</li>
10888<li class="genre-list__item">
10889 <a class="text_flyout-link-small" href="/drama/" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'top', 'stöbern I Drama', null, null, null, event);">
10890 Drama </a>
10891</li>
10892<li class="genre-list__item">
10893 <a class="text_flyout-link-small" href="/romantik/" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'top', 'stöbern I Romantik', null, null, null, event);">
10894 Romantik </a>
10895</li>
10896<li class="genre-list__item">
10897 <a class="text_flyout-link-small" href="/trash/" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'top', 'stöbern I Trash', null, null, null, event);">
10898 Trash </a>
10899</li>
10900<li class="genre-list__item">
10901 <a class="text_flyout-link-small" href="/asian/" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'top', 'stöbern I Asian', null, null, null, event);">
10902 Asian </a>
10903</li></ul>
10904 <svg viewBox="0 0 1 1" class="svg-line" aria-hidden="true">
10905 <path d="M0 0 L1 1"></path>
10906 </svg>
10907
10908 <ul class="collection-list text_flyout-link-small">
10909 <li class="collection-list__item">
10910 <a href="/filme/neu/">Neue Filme</a>
10911 </li>
10912 <li class="collection-list__item">
10913 <a href="/serien/neu/">Neue Serien</a>
10914 </li>
10915 <li class="collection-list__item">
10916 <a href="/filme/">Beliebte Filme</a>
10917 </li>
10918 <li class="collection-list__item">
10919 <a href="/serien/">Beliebte Serien</a>
10920 </li>
10921 </ul> </div>
10922
10923 <a class="stoebern-overlay__genres text_flyout-sublink" href="/genres/">
10924 Alle Genres
10925 <svg class="icon" aria-hidden="true">
10926 <use xlink:href="#wb-item-toggle"></use>
10927 </svg>
10928 </a>
10929</div> </div>
10930 </li>
10931 <li class="navigation__item">
10932 <a class="navigation-link text_navigation-link" href="/meine-liste" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'top', 'meine_liste', null, null, null, event);">
10933 Meine Liste
10934 </a>
10935 </li>
10936</ul>
10937
10938
10939
10940<ul class="icon-bar header__icon-bar">
10941 <li class="icon-bar__section icon-bar__section_social-media">
10942 <a class="icon-bar__social-media-link navigation-link" href="https://www.facebook.com/WATCHBOX" aria-label="Facebook">
10943 <svg class="icon icon_facebook"><use xlink:href="#wb-facebook"></use></svg>
10944 </a>
10945 <a class="icon-bar__social-media-link navigation-link" href="https://www.twitter.com/WATCHBOX" aria-label="Twitter">
10946 <svg class="icon icon_twitter"><use xlink:href="#wb-twitter"></use></svg>
10947 </a>
10948 <a class="icon-bar__social-media-link navigation-link" href="https://www.instagram.com/watchbox_de" aria-label="Instagram">
10949 <svg class="icon icon_instagram"><use xlink:href="#wb-instagram"></use></svg>
10950 </a>
10951</li>
10952
10953 <li class="icon-bar__section icon-bar__section_search">
10954 <a class="navigation-link navigation-link_baseline js-search-toggle" aria-label="Suche">
10955 <svg class="icon icon_search js-hide-on-search" aria-hidden="true">
10956 <use xlink:href="#wb-search"></use>
10957 </svg>
10958 <svg class="icon icon_search js-show-on-search" aria-hidden="true" style="display: none;">
10959 <use xlink:href="#wb-close"></use>
10960 </svg>
10961 </a>
10962 </li>
10963
10964 <li class="icon-bar__section icon-bar__section_user">
10965 <div class="js-iconbar-userinfo"><button class="navigation-link navigation-link_baseline js-login-overlay-open">
10966 <svg class="icon icon_user" aria-hidden="true"><use xlink:href="#wb-user"></use></svg>
10967 <span class="icon-bar__user-name text_navigation-link navigation-link__text">Anmelden</span>
10968 </button></div>
10969
10970 <div id="login-overlay" class="login-overlay login-overlay_dark">
10971 <div class="login">
10972 <div class="login__title">
10973 <div class="login__title__text text_page-title">Login</div>
10974 <button class="login__btn-close js-login-overlay-close">
10975 <svg class="icon" aria-hidden="true">
10976 <use xlink:href="#wb-close"></use>
10977 </svg>
10978 </button>
10979 </div>
10980
10981 <form method="post" action="/login" class="form login__form">
10982 <input type="hidden" name="lasturl" value="/serien/toradora-15561/staffel-1/tiger-und-drache-387850.html">
10983
10984 <div class="form-field form-field_block ">
10985 <label class="form-field__label text_login-input-box" for="email-overlay">E-Mail-Adresse:*</label>
10986 <input class="form-field__input text_paragraph js-form-field__input" placeholder="E-Mail-Adresse" value="" type="email" tabindex="1" name="email" id="email-overlay" maxlength="" minlength="" required="">
10987
10988 <span class="form-field__reset-button js-form-field__reset">
10989 <svg><use xlink:href="#wb-delete"></use></svg>
10990 </span>
10991
10992 <span class="form-field__input-border"></span>
10993
10994 </div>
10995 <div class="form-field form-field_block ">
10996 <label class="form-field__label text_login-input-box" for="password-overlay">Passwort:*</label>
10997 <input class="form-field__input text_paragraph js-form-field__input" value="" type="password" tabindex="2" name="password" id="password-overlay" maxlength="18" minlength="6" required="">
10998
10999 <span class="form-field__reset-button js-form-field__reset">
11000 <svg><use xlink:href="#wb-delete"></use></svg>
11001 </span>
11002
11003 <span class="form-field__input-border"></span>
11004
11005 </div>
11006 <div class="form-field form-field_center">
11007
11008<button class="button button_dark" type="submit" tabindex="3"><div class="button-wrapper">
11009
11010
11011 <div class="button__text text_button-large-title">
11012 Anmelden </div>
11013
11014</div>
11015</button> </div>
11016 </form>
11017
11018
11019 <div class="login__password">
11020 <a href="/passwort-vergessen" class="link text_link">
11021 Passwort vergessen?
11022 </a>
11023 </div>
11024
11025 <div class="separator"></div>
11026
11027 <div class="login__register">
11028 <div class="text_button-small-title login__register-text">Du hast noch kein Profil bei WATCHBOX?</div>
11029 <p class="text_paragraph">
11030 <a href="/registrieren" class="link text_link login__register-link-text">
11031 Hier kannst du dich kostenlos registrieren!
11032 </a>
11033 </p>
11034 </div>
11035</div>
11036 </div>
11037
11038 </li>
11039
11040 <li class="icon-bar__section icon-bar__section_menu">
11041 <button class="navigation-link navigation-link_baseline js-menu-button" aria-hidden="true">
11042 <svg class="icon icon_menu">
11043 <use xlink:href="#wb-menu"></use>
11044 </svg>
11045 </button>
11046
11047
11048<div class="menu js-menu">
11049 <div class="menu-wrapper">
11050 <a class="menu__link text_flyout-link-large" href="/" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'top', 'startseite', null, null, null, event);">
11051 Startseite
11052 </a>
11053
11054 <a class="menu__link text_flyout-link-large" href="/meine-liste" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'top', 'meine_liste', null, null, null, event);">
11055 Meine Liste
11056 </a>
11057
11058 <a class="menu__link text_flyout-link-large" href="/browse/" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'top', 'stöbern', null, null, null, event);">
11059 Stöbern
11060 </a>
11061
11062 <div class="menu__list">
11063
11064<ul class="genre-list">
11065
11066<li class="genre-list__item">
11067 <a class="text_flyout-link-small" href="/anime/" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'top', 'stöbern I Anime', null, null, null, event);">
11068 Anime </a>
11069</li>
11070<li class="genre-list__item">
11071 <a class="text_flyout-link-small" href="/british/" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'top', 'stöbern I British', null, null, null, event);">
11072 British </a>
11073</li>
11074<li class="genre-list__item">
11075 <a class="text_flyout-link-small" href="/science-fiction/" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'top', 'stöbern I Science Fiction', null, null, null, event);">
11076 Science Fiction </a>
11077</li>
11078<li class="genre-list__item">
11079 <a class="text_flyout-link-small" href="/horror/" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'top', 'stöbern I Horror', null, null, null, event);">
11080 Horror </a>
11081</li>
11082<li class="genre-list__item">
11083 <a class="text_flyout-link-small" href="/independent/" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'top', 'stöbern I Independent', null, null, null, event);">
11084 Independent </a>
11085</li>
11086<li class="genre-list__item">
11087 <a class="text_flyout-link-small" href="/komoedie/" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'top', 'stöbern I Komödie', null, null, null, event);">
11088 Komödie </a>
11089</li>
11090<li class="genre-list__item">
11091 <a class="text_flyout-link-small" href="/thriller/" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'top', 'stöbern I Thriller', null, null, null, event);">
11092 Thriller </a>
11093</li>
11094<li class="genre-list__item">
11095 <a class="text_flyout-link-small" href="/show/" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'top', 'stöbern I Show', null, null, null, event);">
11096 Show </a>
11097</li>
11098<li class="genre-list__item">
11099 <a class="text_flyout-link-small" href="/erotik/" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'top', 'stöbern I Erotik', null, null, null, event);">
11100 Erotik </a>
11101</li>
11102<li class="genre-list__item">
11103 <a class="text_flyout-link-small" href="/animation/" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'top', 'stöbern I Animation', null, null, null, event);">
11104 Animation </a>
11105</li>
11106<li class="genre-list__item">
11107 <a class="text_flyout-link-small" href="/action/" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'top', 'stöbern I Action', null, null, null, event);">
11108 Action </a>
11109</li>
11110<li class="genre-list__item">
11111 <a class="text_flyout-link-small" href="/drama/" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'top', 'stöbern I Drama', null, null, null, event);">
11112 Drama </a>
11113</li>
11114<li class="genre-list__item">
11115 <a class="text_flyout-link-small" href="/romantik/" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'top', 'stöbern I Romantik', null, null, null, event);">
11116 Romantik </a>
11117</li>
11118<li class="genre-list__item">
11119 <a class="text_flyout-link-small" href="/trash/" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'top', 'stöbern I Trash', null, null, null, event);">
11120 Trash </a>
11121</li>
11122<li class="genre-list__item">
11123 <a class="text_flyout-link-small" href="/asian/" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'top', 'stöbern I Asian', null, null, null, event);">
11124 Asian </a>
11125</li></ul>
11126 <a class="menu__genres text_flyout-sublink" href="/genres/">
11127 Alle Genres
11128 <svg class="icon" aria-hidden="true"><use xlink:href="#wb-item-toggle"></use></svg>
11129 </a>
11130
11131 <svg viewBox="0 0 1 1" class="menu__line" aria-hidden="true">
11132 <path d="M0 0 L1 1"></path>
11133 </svg>
11134
11135 <ul class="collection-list text_flyout-link-small">
11136 <li class="collection-list__item">
11137 <a href="/filme/neu/">Neue Filme</a>
11138 </li>
11139 <li class="collection-list__item">
11140 <a href="/serien/neu/">Neue Serien</a>
11141 </li>
11142 <li class="collection-list__item">
11143 <a href="/filme/">Beliebte Filme</a>
11144 </li>
11145 <li class="collection-list__item">
11146 <a href="/serien/">Beliebte Serien</a>
11147 </li>
11148 </ul> </div>
11149
11150
11151 <svg viewBox="0 0 1 1" class="menu__line" aria-hidden="true">
11152 <path d="M0 0 L1 1"></path>
11153 </svg>
11154
11155 <ul class="menu__social-media">
11156 <li class="icon-bar__section icon-bar__section_social-media">
11157 <a class="icon-bar__social-media-link navigation-link" href="https://www.facebook.com/WATCHBOX" aria-label="Facebook">
11158 <svg class="icon icon_facebook"><use xlink:href="#wb-facebook"></use></svg>
11159 </a>
11160 <a class="icon-bar__social-media-link navigation-link" href="https://www.twitter.com/WATCHBOX" aria-label="Twitter">
11161 <svg class="icon icon_twitter"><use xlink:href="#wb-twitter"></use></svg>
11162 </a>
11163 <a class="icon-bar__social-media-link navigation-link" href="https://www.instagram.com/watchbox_de" aria-label="Instagram">
11164 <svg class="icon icon_instagram"><use xlink:href="#wb-instagram"></use></svg>
11165 </a>
11166</li>
11167 </ul>
11168 </div>
11169</div> </li>
11170</ul>
11171 </div>
11172 <!-- MISSING Google Universal Analytics tracking id --></header>
11173 <main>
11174
11175
11176<script type="application/ld+json">{"@context":"http:\/\/schema.org","@type":"VideoObject","name":"Tiger und Drache","description":"Palmtop Tiger trifft auf Highschool-Drachen - Wenn aus Gegnern Verb\u00fcndete werden...","thumbnailUrl":"https:\/\/aiswatchbox-a.akamaihd.net\/watchbox\/format\/15561\/26-1\/767x400\/480\/toradora-neue-folgen.jpg","uploadDate":"2018-02-28 06:02:00","duration":"T0H24M3S","embedURL":"https:\/\/www.watchbox.de\/googlebot\/player\/tiger-und-drache-387850.html"}</script>
11177
11178<article class="row">
11179 <section class="episode-player">
11180
11181 <div id="player" class="videoplayer"></div>
11182
11183
11184
11185
11186<nav class="season-panel-wrapper " data-load-data-container="5aa12c13e8bb2" data-reload="false" data-formatname="serien/toradora" data-formatid="15561">
11187 <ul class="season-panel js-season-panel">
11188 <li data-title="staffel-1" data-season-number="1" class="season-panel__item season-panel__item_active">
11189 <a href="/serien/toradora-15561/staffel-1/" class="season-panel__item-text text_tab-link-active">
11190 staffel 1 </a>
11191 </li>
11192 </ul>
11193</nav>
11194
11195<div data-role="swiper" class="teaserset__teasers load-container wb-swiper" id="5aa12c13e8bb2">
11196 <button class="slick-arrow slick-prev slick-disabled" style="">
11197 <svg class="icon " aria-hidden="true">
11198 <use xlink:href="#wb-next"></use>
11199 </svg>
11200 </button>
11201
11202 <div class="swiper-container swiper-container-horizontal swiper-container-free-mode">
11203 <div class="swiper-wrapper js-button-set-from-image-height">
11204 <section class="swiper-slide slick-active" style="width: 302px; margin-right: 10px;">
11205
11206<a class="teaserset__teaser teaser js-teaser-item teaser_season-tab teaser_landscape" onclick="tracking.tagCommanderTrackEvent('gaProductClick', 'Enhanced Ecommerce', 'Product Click', null, null,{
11207 'list':'',
11208 'productClick':{
11209 'name': 'Tiger\x20und\x20Drache',
11210 'id': '15561',
11211 'category': 'Serie',
11212 'brand': 'Anime,\x20Romantik',
11213 'position': ''
11214 }
11215 },null, event)" data-asset-id="15561" data-asset-title="Tiger und Drache" data-asset-list="" data-asset-type="format" data-asset-position="" data-asset-genre="Anime, Romantik" data-format-type="series" data-movie-id="387850" href="/serien/toradora-15561/staffel-1/tiger-und-drache-387850.html">
11216
11217 <div class="teaser__image js-image">
11218 <img class="swiper-lazy text_image-alt-tag swiper-lazy-loaded" aria-hidden="true" alt="Tiger und Drache" itemprop="" srcset="//aiswatchbox-a.akamaihd.net/watchbox/movie/387850/495x278/tiger-und-drache.jpg 495w, //aiswatchbox-a.akamaihd.net/watchbox/movie/387850/378x213/tiger-und-drache.jpg 378w, //aiswatchbox-a.akamaihd.net/watchbox/movie/387850/319x179/tiger-und-drache.jpg 319w, //aiswatchbox-a.akamaihd.net/watchbox/movie/387850/352x198/tiger-und-drache.jpg 352w" src="//aiswatchbox-a.akamaihd.net/watchbox/movie/387850/495x278/tiger-und-drache.jpg">
11219 </div>
11220
11221 <div class="teaser__overlay js-teaser-overlay">
11222 <div class="js-teaser-series teaser__series teaser__series_landscape">
11223 <svg class="icon icon-series" role="img">
11224 <use xlink:href="#wb-series"><title>Serie</title></use>
11225 </svg>
11226 </div>
11227
11228 <div class="js-progress-bar teaser__progressbar teaser__progressbar_series"></div>
11229
11230 <div class="teaser__season-info text_genre-tag js-teaser-season-info">
11231 Staffel 1, Episode 1 </div>
11232 <div class="teaser__header text_teaser-landscape-title js-teaser-headline">
11233 Tiger und Drache </div>
11234 </div>
11235
11236 <div class="teaser__hover teaser__hover_landscape">
11237 <svg class="icon teaser__play" role="img">
11238 <title>Abspielen</title>
11239 <use xlink:href="#wb-play_highlighted" xlink:title="Abspielen"><title>Abspielen</title></use>
11240 </svg>
11241
11242 <div class="teaser__gradient"></div>
11243
11244 <div class="teaser__content">
11245 <div class="text_teaser-landscape-meta">
11246 24 Min. | Japan | 2008 | FSK 12 </div>
11247 <div class="teaser__description text_teaser-landscape-description">
11248 Palmtop Tiger trifft auf Highschool-Drachen - Wenn aus Gegnern Verbündete werden... </div>
11249 <div class="teaser__buttons">
11250
11251<button class="button button_small js-teaser-button-toggle-add"><div class="button-wrapper">
11252
11253 <div class="button__icon" aria-hidden="true">
11254 <svg>
11255 <use xlink:href="#wb-add"></use>
11256 </svg>
11257 </div>
11258
11259 <div class="button__text text_button-small-title">
11260 Meine Liste </div>
11261
11262</div>
11263</button> </div>
11264 </div>
11265 </div>
11266</a>
11267 </section>
11268 <section class="swiper-slide swiper-slide-next" style="width: 302px; margin-right: 10px;">
11269
11270<a class="teaserset__teaser teaser js-teaser-item teaser_season-tab teaser_landscape" onclick="tracking.tagCommanderTrackEvent('gaProductClick', 'Enhanced Ecommerce', 'Product Click', null, null,{
11271 'list':'',
11272 'productClick':{
11273 'name': 'Ryuuji\x20und\x20Taiga',
11274 'id': '15561',
11275 'category': 'Serie',
11276 'brand': 'Anime,\x20Romantik',
11277 'position': ''
11278 }
11279 },null, event)" data-asset-id="15561" data-asset-title="Ryuuji und Taiga" data-asset-list="" data-asset-type="format" data-asset-position="" data-asset-genre="Anime, Romantik" data-format-type="series" data-movie-id="387820" href="/serien/toradora-15561/staffel-1/ryuuji-und-taiga-387820.html">
11280
11281 <div class="teaser__image js-image">
11282 <img class="swiper-lazy text_image-alt-tag swiper-lazy-loaded" aria-hidden="true" alt="Ryuuji und Taiga" itemprop="" srcset="//aiswatchbox-a.akamaihd.net/watchbox/movie/387820/495x278/ryuuji-und-taiga.jpg 495w, //aiswatchbox-a.akamaihd.net/watchbox/movie/387820/378x213/ryuuji-und-taiga.jpg 378w, //aiswatchbox-a.akamaihd.net/watchbox/movie/387820/319x179/ryuuji-und-taiga.jpg 319w, //aiswatchbox-a.akamaihd.net/watchbox/movie/387820/352x198/ryuuji-und-taiga.jpg 352w" src="//aiswatchbox-a.akamaihd.net/watchbox/movie/387820/495x278/ryuuji-und-taiga.jpg">
11283 </div>
11284
11285 <div class="teaser__overlay js-teaser-overlay">
11286 <div class="js-teaser-series teaser__series teaser__series_landscape">
11287 <svg class="icon icon-series" role="img">
11288 <use xlink:href="#wb-series"><title>Serie</title></use>
11289 </svg>
11290 </div>
11291
11292 <div class="js-progress-bar teaser__progressbar teaser__progressbar_series"></div>
11293
11294 <div class="teaser__season-info text_genre-tag js-teaser-season-info">
11295 Staffel 1, Episode 2 </div>
11296 <div class="teaser__header text_teaser-landscape-title js-teaser-headline">
11297 Ryuuji und Taiga </div>
11298 </div>
11299
11300 <div class="teaser__hover teaser__hover_landscape">
11301 <svg class="icon teaser__play" role="img">
11302 <title>Abspielen</title>
11303 <use xlink:href="#wb-play_highlighted" xlink:title="Abspielen"><title>Abspielen</title></use>
11304 </svg>
11305
11306 <div class="teaser__gradient"></div>
11307
11308 <div class="teaser__content">
11309 <div class="text_teaser-landscape-meta">
11310 22 Min. | Japan | 2008 | FSK 12 </div>
11311 <div class="teaser__description text_teaser-landscape-description">
11312 Palmtop Tiger trifft auf Highschool-Drachen - Wenn aus Gegnern Verbündete werden... </div>
11313 <div class="teaser__buttons">
11314
11315<button class="button button_small js-teaser-button-toggle-add"><div class="button-wrapper">
11316
11317 <div class="button__icon" aria-hidden="true">
11318 <svg>
11319 <use xlink:href="#wb-add"></use>
11320 </svg>
11321 </div>
11322
11323 <div class="button__text text_button-small-title">
11324 Meine Liste </div>
11325
11326</div>
11327</button> </div>
11328 </div>
11329 </div>
11330</a>
11331 </section>
11332 <section class="swiper-slide" style="width: 302px; margin-right: 10px;">
11333
11334<a class="teaserset__teaser teaser js-teaser-item teaser_season-tab teaser_landscape" onclick="tracking.tagCommanderTrackEvent('gaProductClick', 'Enhanced Ecommerce', 'Product Click', null, null,{
11335 'list':'',
11336 'productClick':{
11337 'name': 'Dein\x20Song',
11338 'id': '15561',
11339 'category': 'Serie',
11340 'brand': 'Anime,\x20Romantik',
11341 'position': ''
11342 }
11343 },null, event)" data-asset-id="15561" data-asset-title="Dein Song" data-asset-list="" data-asset-type="format" data-asset-position="" data-asset-genre="Anime, Romantik" data-format-type="series" data-movie-id="387832" href="/serien/toradora-15561/staffel-1/dein-song-387832.html">
11344
11345 <div class="teaser__image js-image">
11346 <img class="swiper-lazy text_image-alt-tag swiper-lazy-loaded" aria-hidden="true" alt="Dein Song" itemprop="" srcset="//aiswatchbox-a.akamaihd.net/watchbox/movie/387832/495x278/dein-song.jpg 495w, //aiswatchbox-a.akamaihd.net/watchbox/movie/387832/378x213/dein-song.jpg 378w, //aiswatchbox-a.akamaihd.net/watchbox/movie/387832/319x179/dein-song.jpg 319w, //aiswatchbox-a.akamaihd.net/watchbox/movie/387832/352x198/dein-song.jpg 352w" src="//aiswatchbox-a.akamaihd.net/watchbox/movie/387832/495x278/dein-song.jpg">
11347 </div>
11348
11349 <div class="teaser__overlay js-teaser-overlay">
11350 <div class="js-teaser-series teaser__series teaser__series_landscape">
11351 <svg class="icon icon-series" role="img">
11352 <use xlink:href="#wb-series"><title>Serie</title></use>
11353 </svg>
11354 </div>
11355
11356 <div class="js-progress-bar teaser__progressbar teaser__progressbar_series"></div>
11357
11358 <div class="teaser__season-info text_genre-tag js-teaser-season-info">
11359 Staffel 1, Episode 3 </div>
11360 <div class="teaser__header text_teaser-landscape-title js-teaser-headline">
11361 Dein Song </div>
11362 </div>
11363
11364 <div class="teaser__hover teaser__hover_landscape">
11365 <svg class="icon teaser__play" role="img">
11366 <title>Abspielen</title>
11367 <use xlink:href="#wb-play_highlighted" xlink:title="Abspielen"><title>Abspielen</title></use>
11368 </svg>
11369
11370 <div class="teaser__gradient"></div>
11371
11372 <div class="teaser__content">
11373 <div class="text_teaser-landscape-meta">
11374 22 Min. | Japan | 2008 | FSK 12 </div>
11375 <div class="teaser__description text_teaser-landscape-description">
11376 Palmtop Tiger trifft auf Highschool-Drachen - Wenn aus Gegnern Verbündete werden... </div>
11377 <div class="teaser__buttons">
11378
11379<button class="button button_small js-teaser-button-toggle-add"><div class="button-wrapper">
11380
11381 <div class="button__icon" aria-hidden="true">
11382 <svg>
11383 <use xlink:href="#wb-add"></use>
11384 </svg>
11385 </div>
11386
11387 <div class="button__text text_button-small-title">
11388 Meine Liste </div>
11389
11390</div>
11391</button> </div>
11392 </div>
11393 </div>
11394</a>
11395 </section>
11396 <section class="swiper-slide" style="width: 302px; margin-right: 10px;">
11397
11398<a class="teaserset__teaser teaser js-teaser-item teaser_season-tab teaser_landscape" onclick="tracking.tagCommanderTrackEvent('gaProductClick', 'Enhanced Ecommerce', 'Product Click', null, null,{
11399 'list':'',
11400 'productClick':{
11401 'name': 'Das\x20Gesicht\x20von\x20damals',
11402 'id': '15561',
11403 'category': 'Serie',
11404 'brand': 'Anime,\x20Romantik',
11405 'position': ''
11406 }
11407 },null, event)" data-asset-id="15561" data-asset-title="Das Gesicht von damals" data-asset-list="" data-asset-type="format" data-asset-position="" data-asset-genre="Anime, Romantik" data-format-type="series" data-movie-id="387828" href="/serien/toradora-15561/staffel-1/das-gesicht-von-damals-387828.html">
11408
11409 <div class="teaser__image js-image">
11410 <img data-src="//aiswatchbox-a.akamaihd.net/watchbox/movie/387828/495x278/das-gesicht-von-damals.jpg" data-srcset="//aiswatchbox-a.akamaihd.net/watchbox/movie/387828/495x278/das-gesicht-von-damals.jpg 495w, //aiswatchbox-a.akamaihd.net/watchbox/movie/387828/378x213/das-gesicht-von-damals.jpg 378w, //aiswatchbox-a.akamaihd.net/watchbox/movie/387828/319x179/das-gesicht-von-damals.jpg 319w, //aiswatchbox-a.akamaihd.net/watchbox/movie/387828/352x198/das-gesicht-von-damals.jpg 352w" class=" swiper-lazy text_image-alt-tag" aria-hidden="true" alt="Das Gesicht von damals" itemprop=""> <div class="swiper-lazy-preloader swiper-lazy-preloader-white"></div>
11411 </div>
11412
11413 <div class="teaser__overlay js-teaser-overlay">
11414 <div class="js-teaser-series teaser__series teaser__series_landscape">
11415 <svg class="icon icon-series" role="img">
11416 <use xlink:href="#wb-series"><title>Serie</title></use>
11417 </svg>
11418 </div>
11419
11420 <div class="js-progress-bar teaser__progressbar teaser__progressbar_series"></div>
11421
11422 <div class="teaser__season-info text_genre-tag js-teaser-season-info">
11423 Staffel 1, Episode 4 </div>
11424 <div class="teaser__header text_teaser-landscape-title js-teaser-headline">
11425 Das Gesicht von damals </div>
11426 </div>
11427
11428 <div class="teaser__hover teaser__hover_landscape">
11429 <svg class="icon teaser__play" role="img">
11430 <title>Abspielen</title>
11431 <use xlink:href="#wb-play_highlighted" xlink:title="Abspielen"><title>Abspielen</title></use>
11432 </svg>
11433
11434 <div class="teaser__gradient"></div>
11435
11436 <div class="teaser__content">
11437 <div class="text_teaser-landscape-meta">
11438 22 Min. | Japan | 2008 | FSK 12 </div>
11439 <div class="teaser__description text_teaser-landscape-description">
11440 Palmtop Tiger trifft auf Highschool-Drachen - Wenn aus Gegnern Verbündete werden... </div>
11441 <div class="teaser__buttons">
11442
11443<button class="button button_small js-teaser-button-toggle-add"><div class="button-wrapper">
11444
11445 <div class="button__icon" aria-hidden="true">
11446 <svg>
11447 <use xlink:href="#wb-add"></use>
11448 </svg>
11449 </div>
11450
11451 <div class="button__text text_button-small-title">
11452 Meine Liste </div>
11453
11454</div>
11455</button> </div>
11456 </div>
11457 </div>
11458</a>
11459 </section>
11460 <section class="swiper-slide" style="width: 302px; margin-right: 10px;">
11461
11462<a class="teaserset__teaser teaser js-teaser-item teaser_season-tab teaser_landscape" onclick="tracking.tagCommanderTrackEvent('gaProductClick', 'Enhanced Ecommerce', 'Product Click', null, null,{
11463 'list':'',
11464 'productClick':{
11465 'name': 'Ami\x20Kawashima',
11466 'id': '15561',
11467 'category': 'Serie',
11468 'brand': 'Anime,\x20Romantik',
11469 'position': ''
11470 }
11471 },null, event)" data-asset-id="15561" data-asset-title="Ami Kawashima" data-asset-list="" data-asset-type="format" data-asset-position="" data-asset-genre="Anime, Romantik" data-format-type="series" data-movie-id="387878" href="/serien/toradora-15561/staffel-1/ami-kawashima-387878.html">
11472
11473 <div class="teaser__image js-image">
11474 <img data-src="//aiswatchbox-a.akamaihd.net/watchbox/movie/387878/495x278/ami-kawashima.jpg" data-srcset="//aiswatchbox-a.akamaihd.net/watchbox/movie/387878/495x278/ami-kawashima.jpg 495w, //aiswatchbox-a.akamaihd.net/watchbox/movie/387878/378x213/ami-kawashima.jpg 378w, //aiswatchbox-a.akamaihd.net/watchbox/movie/387878/319x179/ami-kawashima.jpg 319w, //aiswatchbox-a.akamaihd.net/watchbox/movie/387878/352x198/ami-kawashima.jpg 352w" class=" swiper-lazy text_image-alt-tag" aria-hidden="true" alt="Ami Kawashima" itemprop=""> <div class="swiper-lazy-preloader swiper-lazy-preloader-white"></div>
11475 </div>
11476
11477 <div class="teaser__overlay js-teaser-overlay">
11478 <div class="js-teaser-series teaser__series teaser__series_landscape">
11479 <svg class="icon icon-series" role="img">
11480 <use xlink:href="#wb-series"><title>Serie</title></use>
11481 </svg>
11482 </div>
11483
11484 <div class="js-progress-bar teaser__progressbar teaser__progressbar_series"></div>
11485
11486 <div class="teaser__season-info text_genre-tag js-teaser-season-info">
11487 Staffel 1, Episode 5 </div>
11488 <div class="teaser__header text_teaser-landscape-title js-teaser-headline">
11489 Ami Kawashima </div>
11490 </div>
11491
11492 <div class="teaser__hover teaser__hover_landscape">
11493 <svg class="icon teaser__play" role="img">
11494 <title>Abspielen</title>
11495 <use xlink:href="#wb-play_highlighted" xlink:title="Abspielen"><title>Abspielen</title></use>
11496 </svg>
11497
11498 <div class="teaser__gradient"></div>
11499
11500 <div class="teaser__content">
11501 <div class="text_teaser-landscape-meta">
11502 22 Min. | Japan | 2008 | FSK 12 </div>
11503 <div class="teaser__description text_teaser-landscape-description">
11504 Palmtop Tiger trifft auf Highschool-Drachen - Wenn aus Gegnern Verbündete werden... </div>
11505 <div class="teaser__buttons">
11506
11507<button class="button button_small js-teaser-button-toggle-add"><div class="button-wrapper">
11508
11509 <div class="button__icon" aria-hidden="true">
11510 <svg>
11511 <use xlink:href="#wb-add"></use>
11512 </svg>
11513 </div>
11514
11515 <div class="button__text text_button-small-title">
11516 Meine Liste </div>
11517
11518</div>
11519</button> </div>
11520 </div>
11521 </div>
11522</a>
11523 </section>
11524 <section class="swiper-slide" style="width: 302px; margin-right: 10px;">
11525
11526<a class="teaserset__teaser teaser js-teaser-item teaser_season-tab teaser_landscape" onclick="tracking.tagCommanderTrackEvent('gaProductClick', 'Enhanced Ecommerce', 'Product Click', null, null,{
11527 'list':'',
11528 'productClick':{
11529 'name': 'Wahres\x20Gesicht',
11530 'id': '15561',
11531 'category': 'Serie',
11532 'brand': 'Anime,\x20Romantik',
11533 'position': ''
11534 }
11535 },null, event)" data-asset-id="15561" data-asset-title="Wahres Gesicht" data-asset-list="" data-asset-type="format" data-asset-position="" data-asset-genre="Anime, Romantik" data-format-type="series" data-movie-id="387834" href="/serien/toradora-15561/staffel-1/wahres-gesicht-387834.html">
11536
11537 <div class="teaser__image js-image">
11538 <img data-src="//aiswatchbox-a.akamaihd.net/watchbox/movie/387834/495x278/wahres-gesicht.jpg" data-srcset="//aiswatchbox-a.akamaihd.net/watchbox/movie/387834/495x278/wahres-gesicht.jpg 495w, //aiswatchbox-a.akamaihd.net/watchbox/movie/387834/378x213/wahres-gesicht.jpg 378w, //aiswatchbox-a.akamaihd.net/watchbox/movie/387834/319x179/wahres-gesicht.jpg 319w, //aiswatchbox-a.akamaihd.net/watchbox/movie/387834/352x198/wahres-gesicht.jpg 352w" class=" swiper-lazy text_image-alt-tag" aria-hidden="true" alt="Wahres Gesicht" itemprop=""> <div class="swiper-lazy-preloader swiper-lazy-preloader-white"></div>
11539 </div>
11540
11541 <div class="teaser__overlay js-teaser-overlay">
11542 <div class="js-teaser-series teaser__series teaser__series_landscape">
11543 <svg class="icon icon-series" role="img">
11544 <use xlink:href="#wb-series"><title>Serie</title></use>
11545 </svg>
11546 </div>
11547
11548 <div class="js-progress-bar teaser__progressbar teaser__progressbar_series"></div>
11549
11550 <div class="teaser__season-info text_genre-tag js-teaser-season-info">
11551 Staffel 1, Episode 6 </div>
11552 <div class="teaser__header text_teaser-landscape-title js-teaser-headline">
11553 Wahres Gesicht </div>
11554 </div>
11555
11556 <div class="teaser__hover teaser__hover_landscape">
11557 <svg class="icon teaser__play" role="img">
11558 <title>Abspielen</title>
11559 <use xlink:href="#wb-play_highlighted" xlink:title="Abspielen"><title>Abspielen</title></use>
11560 </svg>
11561
11562 <div class="teaser__gradient"></div>
11563
11564 <div class="teaser__content">
11565 <div class="text_teaser-landscape-meta">
11566 22 Min. | Japan | 2008 | FSK 12 </div>
11567 <div class="teaser__description text_teaser-landscape-description">
11568 Palmtop Tiger trifft auf Highschool-Drachen - Wenn aus Gegnern Verbündete werden... </div>
11569 <div class="teaser__buttons">
11570
11571<button class="button button_small js-teaser-button-toggle-add"><div class="button-wrapper">
11572
11573 <div class="button__icon" aria-hidden="true">
11574 <svg>
11575 <use xlink:href="#wb-add"></use>
11576 </svg>
11577 </div>
11578
11579 <div class="button__text text_button-small-title">
11580 Meine Liste </div>
11581
11582</div>
11583</button> </div>
11584 </div>
11585 </div>
11586</a>
11587 </section>
11588 <section class="swiper-slide" style="width: 302px; margin-right: 10px;">
11589
11590<a class="teaserset__teaser teaser js-teaser-item teaser_season-tab teaser_landscape" onclick="tracking.tagCommanderTrackEvent('gaProductClick', 'Enhanced Ecommerce', 'Product Click', null, null,{
11591 'list':'',
11592 'productClick':{
11593 'name': 'Schwimmbader\u00F6ffnung',
11594 'id': '15561',
11595 'category': 'Serie',
11596 'brand': 'Anime,\x20Romantik',
11597 'position': ''
11598 }
11599 },null, event)" data-asset-id="15561" data-asset-title="Schwimmbaderöffnung" data-asset-list="" data-asset-type="format" data-asset-position="" data-asset-genre="Anime, Romantik" data-format-type="series" data-movie-id="387844" href="/serien/toradora-15561/staffel-1/schwimmbaderoeffnung-387844.html">
11600
11601 <div class="teaser__image js-image">
11602 <img data-src="//aiswatchbox-a.akamaihd.net/watchbox/movie/387844/495x278/schwimmbaderoeffnung.jpg" data-srcset="//aiswatchbox-a.akamaihd.net/watchbox/movie/387844/495x278/schwimmbaderoeffnung.jpg 495w, //aiswatchbox-a.akamaihd.net/watchbox/movie/387844/378x213/schwimmbaderoeffnung.jpg 378w, //aiswatchbox-a.akamaihd.net/watchbox/movie/387844/319x179/schwimmbaderoeffnung.jpg 319w, //aiswatchbox-a.akamaihd.net/watchbox/movie/387844/352x198/schwimmbaderoeffnung.jpg 352w" class=" swiper-lazy text_image-alt-tag" aria-hidden="true" alt="Schwimmbaderöffnung" itemprop=""> <div class="swiper-lazy-preloader swiper-lazy-preloader-white"></div>
11603 </div>
11604
11605 <div class="teaser__overlay js-teaser-overlay">
11606 <div class="js-teaser-series teaser__series teaser__series_landscape">
11607 <svg class="icon icon-series" role="img">
11608 <use xlink:href="#wb-series"><title>Serie</title></use>
11609 </svg>
11610 </div>
11611
11612 <div class="js-progress-bar teaser__progressbar teaser__progressbar_series"></div>
11613
11614 <div class="teaser__season-info text_genre-tag js-teaser-season-info">
11615 Staffel 1, Episode 7 </div>
11616 <div class="teaser__header text_teaser-landscape-title js-teaser-headline">
11617 Schwimmbaderöffnung </div>
11618 </div>
11619
11620 <div class="teaser__hover teaser__hover_landscape">
11621 <svg class="icon teaser__play" role="img">
11622 <title>Abspielen</title>
11623 <use xlink:href="#wb-play_highlighted" xlink:title="Abspielen"><title>Abspielen</title></use>
11624 </svg>
11625
11626 <div class="teaser__gradient"></div>
11627
11628 <div class="teaser__content">
11629 <div class="text_teaser-landscape-meta">
11630 22 Min. | Japan | 2008 | FSK 12 </div>
11631 <div class="teaser__description text_teaser-landscape-description">
11632 Palmtop Tiger trifft auf Highschool-Drachen - Wenn aus Gegnern Verbündete werden... </div>
11633 <div class="teaser__buttons">
11634
11635<button class="button button_small js-teaser-button-toggle-add"><div class="button-wrapper">
11636
11637 <div class="button__icon" aria-hidden="true">
11638 <svg>
11639 <use xlink:href="#wb-add"></use>
11640 </svg>
11641 </div>
11642
11643 <div class="button__text text_button-small-title">
11644 Meine Liste </div>
11645
11646</div>
11647</button> </div>
11648 </div>
11649 </div>
11650</a>
11651 </section>
11652 <section class="swiper-slide" style="width: 302px; margin-right: 10px;">
11653
11654<a class="teaserset__teaser teaser js-teaser-item teaser_season-tab teaser_landscape" onclick="tracking.tagCommanderTrackEvent('gaProductClick', 'Enhanced Ecommerce', 'Product Click', null, null,{
11655 'list':'',
11656 'productClick':{
11657 'name': 'Taiga\x20vs.\x20Ami',
11658 'id': '15561',
11659 'category': 'Serie',
11660 'brand': 'Anime,\x20Romantik',
11661 'position': ''
11662 }
11663 },null, event)" data-asset-id="15561" data-asset-title="Taiga vs. Ami" data-asset-list="" data-asset-type="format" data-asset-position="" data-asset-genre="Anime, Romantik" data-format-type="series" data-movie-id="387846" href="/serien/toradora-15561/staffel-1/taiga-vs-ami-387846.html">
11664
11665 <div class="teaser__image js-image">
11666 <img data-src="//aiswatchbox-a.akamaihd.net/watchbox/movie/387846/495x278/taiga-vs-ami.jpg" data-srcset="//aiswatchbox-a.akamaihd.net/watchbox/movie/387846/495x278/taiga-vs-ami.jpg 495w, //aiswatchbox-a.akamaihd.net/watchbox/movie/387846/378x213/taiga-vs-ami.jpg 378w, //aiswatchbox-a.akamaihd.net/watchbox/movie/387846/319x179/taiga-vs-ami.jpg 319w, //aiswatchbox-a.akamaihd.net/watchbox/movie/387846/352x198/taiga-vs-ami.jpg 352w" class=" swiper-lazy text_image-alt-tag" aria-hidden="true" alt="Taiga vs. Ami" itemprop=""> <div class="swiper-lazy-preloader swiper-lazy-preloader-white"></div>
11667 </div>
11668
11669 <div class="teaser__overlay js-teaser-overlay">
11670 <div class="js-teaser-series teaser__series teaser__series_landscape">
11671 <svg class="icon icon-series" role="img">
11672 <use xlink:href="#wb-series"><title>Serie</title></use>
11673 </svg>
11674 </div>
11675
11676 <div class="js-progress-bar teaser__progressbar teaser__progressbar_series"></div>
11677
11678 <div class="teaser__season-info text_genre-tag js-teaser-season-info">
11679 Staffel 1, Episode 8 </div>
11680 <div class="teaser__header text_teaser-landscape-title js-teaser-headline">
11681 Taiga vs. Ami </div>
11682 </div>
11683
11684 <div class="teaser__hover teaser__hover_landscape">
11685 <svg class="icon teaser__play" role="img">
11686 <title>Abspielen</title>
11687 <use xlink:href="#wb-play_highlighted" xlink:title="Abspielen"><title>Abspielen</title></use>
11688 </svg>
11689
11690 <div class="teaser__gradient"></div>
11691
11692 <div class="teaser__content">
11693 <div class="text_teaser-landscape-meta">
11694 22 Min. | Japan | 2008 | FSK 12 </div>
11695 <div class="teaser__description text_teaser-landscape-description">
11696 Palmtop Tiger trifft auf Highschool-Drachen - Wenn aus Gegnern Verbündete werden... </div>
11697 <div class="teaser__buttons">
11698
11699<button class="button button_small js-teaser-button-toggle-add"><div class="button-wrapper">
11700
11701 <div class="button__icon" aria-hidden="true">
11702 <svg>
11703 <use xlink:href="#wb-add"></use>
11704 </svg>
11705 </div>
11706
11707 <div class="button__text text_button-small-title">
11708 Meine Liste </div>
11709
11710</div>
11711</button> </div>
11712 </div>
11713 </div>
11714</a>
11715 </section>
11716 <section class="swiper-slide" style="width: 302px; margin-right: 10px;">
11717
11718<a class="teaserset__teaser teaser js-teaser-item teaser_season-tab teaser_landscape" onclick="tracking.tagCommanderTrackEvent('gaProductClick', 'Enhanced Ecommerce', 'Product Click', null, null,{
11719 'list':'',
11720 'productClick':{
11721 'name': 'Das\x20Strandhaus',
11722 'id': '15561',
11723 'category': 'Serie',
11724 'brand': 'Anime,\x20Romantik',
11725 'position': ''
11726 }
11727 },null, event)" data-asset-id="15561" data-asset-title="Das Strandhaus" data-asset-list="" data-asset-type="format" data-asset-position="" data-asset-genre="Anime, Romantik" data-format-type="series" data-movie-id="387882" href="/serien/toradora-15561/staffel-1/das-strandhaus-387882.html">
11728
11729 <div class="teaser__image js-image">
11730 <img data-src="//aiswatchbox-a.akamaihd.net/watchbox/movie/387882/495x278/das-strandhaus.jpg" data-srcset="//aiswatchbox-a.akamaihd.net/watchbox/movie/387882/495x278/das-strandhaus.jpg 495w, //aiswatchbox-a.akamaihd.net/watchbox/movie/387882/378x213/das-strandhaus.jpg 378w, //aiswatchbox-a.akamaihd.net/watchbox/movie/387882/319x179/das-strandhaus.jpg 319w, //aiswatchbox-a.akamaihd.net/watchbox/movie/387882/352x198/das-strandhaus.jpg 352w" class=" swiper-lazy text_image-alt-tag" aria-hidden="true" alt="Das Strandhaus" itemprop=""> <div class="swiper-lazy-preloader swiper-lazy-preloader-white"></div>
11731 </div>
11732
11733 <div class="teaser__overlay js-teaser-overlay">
11734 <div class="js-teaser-series teaser__series teaser__series_landscape">
11735 <svg class="icon icon-series" role="img">
11736 <use xlink:href="#wb-series"><title>Serie</title></use>
11737 </svg>
11738 </div>
11739
11740 <div class="js-progress-bar teaser__progressbar teaser__progressbar_series"></div>
11741
11742 <div class="teaser__season-info text_genre-tag js-teaser-season-info">
11743 Staffel 1, Episode 9 </div>
11744 <div class="teaser__header text_teaser-landscape-title js-teaser-headline">
11745 Das Strandhaus </div>
11746 </div>
11747
11748 <div class="teaser__hover teaser__hover_landscape">
11749 <svg class="icon teaser__play" role="img">
11750 <title>Abspielen</title>
11751 <use xlink:href="#wb-play_highlighted" xlink:title="Abspielen"><title>Abspielen</title></use>
11752 </svg>
11753
11754 <div class="teaser__gradient"></div>
11755
11756 <div class="teaser__content">
11757 <div class="text_teaser-landscape-meta">
11758 22 Min. | Japan | 2008 | FSK 12 </div>
11759 <div class="teaser__description text_teaser-landscape-description">
11760 Palmtop Tiger trifft auf Highschool-Drachen - Wenn aus Gegnern Verbündete werden... </div>
11761 <div class="teaser__buttons">
11762
11763<button class="button button_small js-teaser-button-toggle-add"><div class="button-wrapper">
11764
11765 <div class="button__icon" aria-hidden="true">
11766 <svg>
11767 <use xlink:href="#wb-add"></use>
11768 </svg>
11769 </div>
11770
11771 <div class="button__text text_button-small-title">
11772 Meine Liste </div>
11773
11774</div>
11775</button> </div>
11776 </div>
11777 </div>
11778</a>
11779 </section>
11780 <section class="swiper-slide" style="width: 302px; margin-right: 10px;">
11781
11782<a class="teaserset__teaser teaser js-teaser-item teaser_season-tab teaser_landscape" onclick="tracking.tagCommanderTrackEvent('gaProductClick', 'Enhanced Ecommerce', 'Product Click', null, null,{
11783 'list':'',
11784 'productClick':{
11785 'name': 'Feuerwerk',
11786 'id': '15561',
11787 'category': 'Serie',
11788 'brand': 'Anime,\x20Romantik',
11789 'position': ''
11790 }
11791 },null, event)" data-asset-id="15561" data-asset-title="Feuerwerk" data-asset-list="" data-asset-type="format" data-asset-position="" data-asset-genre="Anime, Romantik" data-format-type="series" data-movie-id="387848" href="/serien/toradora-15561/staffel-1/feuerwerk-387848.html">
11792
11793 <div class="teaser__image js-image">
11794 <img data-src="//aiswatchbox-a.akamaihd.net/watchbox/movie/387848/495x278/feuerwerk.jpg" data-srcset="//aiswatchbox-a.akamaihd.net/watchbox/movie/387848/495x278/feuerwerk.jpg 495w, //aiswatchbox-a.akamaihd.net/watchbox/movie/387848/378x213/feuerwerk.jpg 378w, //aiswatchbox-a.akamaihd.net/watchbox/movie/387848/319x179/feuerwerk.jpg 319w, //aiswatchbox-a.akamaihd.net/watchbox/movie/387848/352x198/feuerwerk.jpg 352w" class=" swiper-lazy text_image-alt-tag" aria-hidden="true" alt="Feuerwerk" itemprop=""> <div class="swiper-lazy-preloader swiper-lazy-preloader-white"></div>
11795 </div>
11796
11797 <div class="teaser__overlay js-teaser-overlay">
11798 <div class="js-teaser-series teaser__series teaser__series_landscape">
11799 <svg class="icon icon-series" role="img">
11800 <use xlink:href="#wb-series"><title>Serie</title></use>
11801 </svg>
11802 </div>
11803
11804 <div class="js-progress-bar teaser__progressbar teaser__progressbar_series"></div>
11805
11806 <div class="teaser__season-info text_genre-tag js-teaser-season-info">
11807 Staffel 1, Episode 10 </div>
11808 <div class="teaser__header text_teaser-landscape-title js-teaser-headline">
11809 Feuerwerk </div>
11810 </div>
11811
11812 <div class="teaser__hover teaser__hover_landscape">
11813 <svg class="icon teaser__play" role="img">
11814 <title>Abspielen</title>
11815 <use xlink:href="#wb-play_highlighted" xlink:title="Abspielen"><title>Abspielen</title></use>
11816 </svg>
11817
11818 <div class="teaser__gradient"></div>
11819
11820 <div class="teaser__content">
11821 <div class="text_teaser-landscape-meta">
11822 22 Min. | Japan | 2008 | FSK 12 </div>
11823 <div class="teaser__description text_teaser-landscape-description">
11824 Palmtop Tiger trifft auf Highschool-Drachen - Wenn aus Gegnern Verbündete werden... </div>
11825 <div class="teaser__buttons">
11826
11827<button class="button button_small js-teaser-button-toggle-add"><div class="button-wrapper">
11828
11829 <div class="button__icon" aria-hidden="true">
11830 <svg>
11831 <use xlink:href="#wb-add"></use>
11832 </svg>
11833 </div>
11834
11835 <div class="button__text text_button-small-title">
11836 Meine Liste </div>
11837
11838</div>
11839</button> </div>
11840 </div>
11841 </div>
11842</a>
11843 </section>
11844 <section class="swiper-slide" style="width: 302px; margin-right: 10px;">
11845
11846<a class="teaserset__teaser teaser js-teaser-item teaser_season-tab teaser_landscape" onclick="tracking.tagCommanderTrackEvent('gaProductClick', 'Enhanced Ecommerce', 'Product Click', null, null,{
11847 'list':'',
11848 'productClick':{
11849 'name': 'Das\x20Oohashi\x20Kulturfest\x20\x28Teil\x201\x29',
11850 'id': '15561',
11851 'category': 'Serie',
11852 'brand': 'Anime,\x20Romantik',
11853 'position': ''
11854 }
11855 },null, event)" data-asset-id="15561" data-asset-title="Das Oohashi Kulturfest (Teil 1)" data-asset-list="" data-asset-type="format" data-asset-position="" data-asset-genre="Anime, Romantik" data-format-type="series" data-movie-id="409960" href="/serien/toradora-15561/staffel-1/das-oohashi-kulturfest-teil-1-409960.html">
11856
11857 <div class="teaser__image js-image">
11858 <img data-src="//aiswatchbox-a.akamaihd.net/watchbox/movie/409960/495x278/das-oohashi-kulturfest-teil-1.jpg" data-srcset="//aiswatchbox-a.akamaihd.net/watchbox/movie/409960/495x278/das-oohashi-kulturfest-teil-1.jpg 495w, //aiswatchbox-a.akamaihd.net/watchbox/movie/409960/378x213/das-oohashi-kulturfest-teil-1.jpg 378w, //aiswatchbox-a.akamaihd.net/watchbox/movie/409960/319x179/das-oohashi-kulturfest-teil-1.jpg 319w, //aiswatchbox-a.akamaihd.net/watchbox/movie/409960/352x198/das-oohashi-kulturfest-teil-1.jpg 352w" class=" swiper-lazy text_image-alt-tag" aria-hidden="true" alt="Das Oohashi Kulturfest (Teil 1)" itemprop=""> <div class="swiper-lazy-preloader swiper-lazy-preloader-white"></div>
11859 </div>
11860
11861 <div class="teaser__overlay js-teaser-overlay">
11862 <div class="js-teaser-series teaser__series teaser__series_landscape">
11863 <svg class="icon icon-series" role="img">
11864 <use xlink:href="#wb-series"><title>Serie</title></use>
11865 </svg>
11866 </div>
11867
11868 <div class="js-progress-bar teaser__progressbar teaser__progressbar_series"></div>
11869
11870 <div class="teaser__season-info text_genre-tag js-teaser-season-info">
11871 Staffel 1, Episode 11 </div>
11872 <div class="teaser__header text_teaser-landscape-title js-teaser-headline">
11873 Das Oohashi Kulturfest (Teil 1) </div>
11874 </div>
11875
11876 <div class="teaser__hover teaser__hover_landscape">
11877 <svg class="icon teaser__play" role="img">
11878 <title>Abspielen</title>
11879 <use xlink:href="#wb-play_highlighted" xlink:title="Abspielen"><title>Abspielen</title></use>
11880 </svg>
11881
11882 <div class="teaser__gradient"></div>
11883
11884 <div class="teaser__content">
11885 <div class="text_teaser-landscape-meta">
11886 23 Min. | Japan | 2008 | FSK 12 </div>
11887 <div class="teaser__description text_teaser-landscape-description">
11888 Palmtop Tiger trifft auf Highschool-Drachen - Wenn aus Gegnern Verbündete werden... </div>
11889 <div class="teaser__buttons">
11890
11891<button class="button button_small js-teaser-button-toggle-add"><div class="button-wrapper">
11892
11893 <div class="button__icon" aria-hidden="true">
11894 <svg>
11895 <use xlink:href="#wb-add"></use>
11896 </svg>
11897 </div>
11898
11899 <div class="button__text text_button-small-title">
11900 Meine Liste </div>
11901
11902</div>
11903</button> </div>
11904 </div>
11905 </div>
11906</a>
11907 </section>
11908 <section class="swiper-slide" style="width: 302px; margin-right: 10px;">
11909
11910<a class="teaserset__teaser teaser js-teaser-item teaser_season-tab teaser_landscape" onclick="tracking.tagCommanderTrackEvent('gaProductClick', 'Enhanced Ecommerce', 'Product Click', null, null,{
11911 'list':'',
11912 'productClick':{
11913 'name': 'Das\x20Oohashi\x20Kulturfest\x20\x28Teil\x202\x29',
11914 'id': '15561',
11915 'category': 'Serie',
11916 'brand': 'Anime,\x20Romantik',
11917 'position': ''
11918 }
11919 },null, event)" data-asset-id="15561" data-asset-title="Das Oohashi Kulturfest (Teil 2)" data-asset-list="" data-asset-type="format" data-asset-position="" data-asset-genre="Anime, Romantik" data-format-type="series" data-movie-id="409966" href="/serien/toradora-15561/staffel-1/das-oohashi-kulturfest-teil-2-409966.html">
11920
11921 <div class="teaser__image js-image">
11922 <img data-src="//aiswatchbox-a.akamaihd.net/watchbox/movie/409966/495x278/das-oohashi-kulturfest-teil-2.jpg" data-srcset="//aiswatchbox-a.akamaihd.net/watchbox/movie/409966/495x278/das-oohashi-kulturfest-teil-2.jpg 495w, //aiswatchbox-a.akamaihd.net/watchbox/movie/409966/378x213/das-oohashi-kulturfest-teil-2.jpg 378w, //aiswatchbox-a.akamaihd.net/watchbox/movie/409966/319x179/das-oohashi-kulturfest-teil-2.jpg 319w, //aiswatchbox-a.akamaihd.net/watchbox/movie/409966/352x198/das-oohashi-kulturfest-teil-2.jpg 352w" class=" swiper-lazy text_image-alt-tag" aria-hidden="true" alt="Das Oohashi Kulturfest (Teil 2)" itemprop=""> <div class="swiper-lazy-preloader swiper-lazy-preloader-white"></div>
11923 </div>
11924
11925 <div class="teaser__overlay js-teaser-overlay">
11926 <div class="js-teaser-series teaser__series teaser__series_landscape">
11927 <svg class="icon icon-series" role="img">
11928 <use xlink:href="#wb-series"><title>Serie</title></use>
11929 </svg>
11930 </div>
11931
11932 <div class="js-progress-bar teaser__progressbar teaser__progressbar_series"></div>
11933
11934 <div class="teaser__season-info text_genre-tag js-teaser-season-info">
11935 Staffel 1, Episode 12 </div>
11936 <div class="teaser__header text_teaser-landscape-title js-teaser-headline">
11937 Das Oohashi Kulturfest (Teil 2) </div>
11938 </div>
11939
11940 <div class="teaser__hover teaser__hover_landscape">
11941 <svg class="icon teaser__play" role="img">
11942 <title>Abspielen</title>
11943 <use xlink:href="#wb-play_highlighted" xlink:title="Abspielen"><title>Abspielen</title></use>
11944 </svg>
11945
11946 <div class="teaser__gradient"></div>
11947
11948 <div class="teaser__content">
11949 <div class="text_teaser-landscape-meta">
11950 23 Min. | Japan | 2008 | FSK 12 </div>
11951 <div class="teaser__description text_teaser-landscape-description">
11952 Palmtop Tiger trifft auf Highschool-Drachen - Wenn aus Gegnern Verbündete werden... </div>
11953 <div class="teaser__buttons">
11954
11955<button class="button button_small js-teaser-button-toggle-add"><div class="button-wrapper">
11956
11957 <div class="button__icon" aria-hidden="true">
11958 <svg>
11959 <use xlink:href="#wb-add"></use>
11960 </svg>
11961 </div>
11962
11963 <div class="button__text text_button-small-title">
11964 Meine Liste </div>
11965
11966</div>
11967</button> </div>
11968 </div>
11969 </div>
11970</a>
11971 </section>
11972 <section class="swiper-slide" style="width: 302px; margin-right: 10px;">
11973
11974<a class="teaserset__teaser teaser js-teaser-item teaser_season-tab teaser_landscape" onclick="tracking.tagCommanderTrackEvent('gaProductClick', 'Enhanced Ecommerce', 'Product Click', null, null,{
11975 'list':'',
11976 'productClick':{
11977 'name': 'Das\x20Oohashi\x20Kulturfest\x20\x28Teil\x203\x29',
11978 'id': '15561',
11979 'category': 'Serie',
11980 'brand': 'Anime,\x20Romantik',
11981 'position': ''
11982 }
11983 },null, event)" data-asset-id="15561" data-asset-title="Das Oohashi Kulturfest (Teil 3)" data-asset-list="" data-asset-type="format" data-asset-position="" data-asset-genre="Anime, Romantik" data-format-type="series" data-movie-id="409942" href="/serien/toradora-15561/staffel-1/das-oohashi-kulturfest-teil-3-409942.html">
11984
11985 <div class="teaser__image js-image">
11986 <img data-src="//aiswatchbox-a.akamaihd.net/watchbox/movie/409942/495x278/das-oohashi-kulturfest-teil-3.jpg" data-srcset="//aiswatchbox-a.akamaihd.net/watchbox/movie/409942/495x278/das-oohashi-kulturfest-teil-3.jpg 495w, //aiswatchbox-a.akamaihd.net/watchbox/movie/409942/378x213/das-oohashi-kulturfest-teil-3.jpg 378w, //aiswatchbox-a.akamaihd.net/watchbox/movie/409942/319x179/das-oohashi-kulturfest-teil-3.jpg 319w, //aiswatchbox-a.akamaihd.net/watchbox/movie/409942/352x198/das-oohashi-kulturfest-teil-3.jpg 352w" class=" swiper-lazy text_image-alt-tag" aria-hidden="true" alt="Das Oohashi Kulturfest (Teil 3)" itemprop=""> <div class="swiper-lazy-preloader swiper-lazy-preloader-white"></div>
11987 </div>
11988
11989 <div class="teaser__overlay js-teaser-overlay">
11990 <div class="js-teaser-series teaser__series teaser__series_landscape">
11991 <svg class="icon icon-series" role="img">
11992 <use xlink:href="#wb-series"><title>Serie</title></use>
11993 </svg>
11994 </div>
11995
11996 <div class="js-progress-bar teaser__progressbar teaser__progressbar_series"></div>
11997
11998 <div class="teaser__season-info text_genre-tag js-teaser-season-info">
11999 Staffel 1, Episode 13 </div>
12000 <div class="teaser__header text_teaser-landscape-title js-teaser-headline">
12001 Das Oohashi Kulturfest (Teil 3) </div>
12002 </div>
12003
12004 <div class="teaser__hover teaser__hover_landscape">
12005 <svg class="icon teaser__play" role="img">
12006 <title>Abspielen</title>
12007 <use xlink:href="#wb-play_highlighted" xlink:title="Abspielen"><title>Abspielen</title></use>
12008 </svg>
12009
12010 <div class="teaser__gradient"></div>
12011
12012 <div class="teaser__content">
12013 <div class="text_teaser-landscape-meta">
12014 23 Min. | Japan | 2008 | FSK 12 </div>
12015 <div class="teaser__description text_teaser-landscape-description">
12016 Palmtop Tiger trifft auf Highschool-Drachen - Wenn aus Gegnern Verbündete werden... </div>
12017 <div class="teaser__buttons">
12018
12019<button class="button button_small js-teaser-button-toggle-add"><div class="button-wrapper">
12020
12021 <div class="button__icon" aria-hidden="true">
12022 <svg>
12023 <use xlink:href="#wb-add"></use>
12024 </svg>
12025 </div>
12026
12027 <div class="button__text text_button-small-title">
12028 Meine Liste </div>
12029
12030</div>
12031</button> </div>
12032 </div>
12033 </div>
12034</a>
12035 </section>
12036 <section class="swiper-slide" style="width: 302px; margin-right: 10px;">
12037
12038<a class="teaserset__teaser teaser js-teaser-item teaser_season-tab teaser_landscape" onclick="tracking.tagCommanderTrackEvent('gaProductClick', 'Enhanced Ecommerce', 'Product Click', null, null,{
12039 'list':'',
12040 'productClick':{
12041 'name': 'Der\x20Gl\u00FCckstiger',
12042 'id': '15561',
12043 'category': 'Serie',
12044 'brand': 'Anime,\x20Romantik',
12045 'position': ''
12046 }
12047 },null, event)" data-asset-id="15561" data-asset-title="Der Glückstiger" data-asset-list="" data-asset-type="format" data-asset-position="" data-asset-genre="Anime, Romantik" data-format-type="series" data-movie-id="410714" href="/serien/toradora-15561/staffel-1/der-glueckstiger-410714.html">
12048
12049 <div class="teaser__image js-image">
12050 <img data-src="//aiswatchbox-a.akamaihd.net/watchbox/movie/410714/495x278/der-glueckstiger.jpg" data-srcset="//aiswatchbox-a.akamaihd.net/watchbox/movie/410714/495x278/der-glueckstiger.jpg 495w, //aiswatchbox-a.akamaihd.net/watchbox/movie/410714/378x213/der-glueckstiger.jpg 378w, //aiswatchbox-a.akamaihd.net/watchbox/movie/410714/319x179/der-glueckstiger.jpg 319w, //aiswatchbox-a.akamaihd.net/watchbox/movie/410714/352x198/der-glueckstiger.jpg 352w" class=" swiper-lazy text_image-alt-tag" aria-hidden="true" alt="Der Glückstiger" itemprop=""> <div class="swiper-lazy-preloader swiper-lazy-preloader-white"></div>
12051 </div>
12052
12053 <div class="teaser__overlay js-teaser-overlay">
12054 <div class="js-teaser-series teaser__series teaser__series_landscape">
12055 <svg class="icon icon-series" role="img">
12056 <use xlink:href="#wb-series"><title>Serie</title></use>
12057 </svg>
12058 </div>
12059
12060 <div class="js-progress-bar teaser__progressbar teaser__progressbar_series"></div>
12061
12062 <div class="teaser__season-info text_genre-tag js-teaser-season-info">
12063 Staffel 1, Episode 14 </div>
12064 <div class="teaser__header text_teaser-landscape-title js-teaser-headline">
12065 Der Glückstiger </div>
12066 </div>
12067
12068 <div class="teaser__hover teaser__hover_landscape">
12069 <svg class="icon teaser__play" role="img">
12070 <title>Abspielen</title>
12071 <use xlink:href="#wb-play_highlighted" xlink:title="Abspielen"><title>Abspielen</title></use>
12072 </svg>
12073
12074 <div class="teaser__gradient"></div>
12075
12076 <div class="teaser__content">
12077 <div class="text_teaser-landscape-meta">
12078 23 Min. | Japan | 2008 | FSK 12 </div>
12079 <div class="teaser__description text_teaser-landscape-description">
12080 Palmtop Tiger trifft auf Highschool-Drachen - Wenn aus Gegnern Verbündete werden... </div>
12081 <div class="teaser__buttons">
12082
12083<button class="button button_small js-teaser-button-toggle-add"><div class="button-wrapper">
12084
12085 <div class="button__icon" aria-hidden="true">
12086 <svg>
12087 <use xlink:href="#wb-add"></use>
12088 </svg>
12089 </div>
12090
12091 <div class="button__text text_button-small-title">
12092 Meine Liste </div>
12093
12094</div>
12095</button> </div>
12096 </div>
12097 </div>
12098</a>
12099 </section>
12100 <section class="swiper-slide" style="width: 302px; margin-right: 10px;">
12101
12102<a class="teaserset__teaser teaser js-teaser-item teaser_season-tab teaser_landscape" onclick="tracking.tagCommanderTrackEvent('gaProductClick', 'Enhanced Ecommerce', 'Product Click', null, null,{
12103 'list':'',
12104 'productClick':{
12105 'name': 'Weit\x20entfernte\x20Sterne',
12106 'id': '15561',
12107 'category': 'Serie',
12108 'brand': 'Anime,\x20Romantik',
12109 'position': ''
12110 }
12111 },null, event)" data-asset-id="15561" data-asset-title="Weit entfernte Sterne" data-asset-list="" data-asset-type="format" data-asset-position="" data-asset-genre="Anime, Romantik" data-format-type="series" data-movie-id="409938" href="/serien/toradora-15561/staffel-1/weit-entfernte-sterne-409938.html">
12112
12113 <div class="teaser__image js-image">
12114 <img data-src="//aiswatchbox-a.akamaihd.net/watchbox/movie/409938/495x278/weit-entfernte-sterne.jpg" data-srcset="//aiswatchbox-a.akamaihd.net/watchbox/movie/409938/495x278/weit-entfernte-sterne.jpg 495w, //aiswatchbox-a.akamaihd.net/watchbox/movie/409938/378x213/weit-entfernte-sterne.jpg 378w, //aiswatchbox-a.akamaihd.net/watchbox/movie/409938/319x179/weit-entfernte-sterne.jpg 319w, //aiswatchbox-a.akamaihd.net/watchbox/movie/409938/352x198/weit-entfernte-sterne.jpg 352w" class=" swiper-lazy text_image-alt-tag" aria-hidden="true" alt="Weit entfernte Sterne" itemprop=""> <div class="swiper-lazy-preloader swiper-lazy-preloader-white"></div>
12115 </div>
12116
12117 <div class="teaser__overlay js-teaser-overlay">
12118 <div class="js-teaser-series teaser__series teaser__series_landscape">
12119 <svg class="icon icon-series" role="img">
12120 <use xlink:href="#wb-series"><title>Serie</title></use>
12121 </svg>
12122 </div>
12123
12124 <div class="js-progress-bar teaser__progressbar teaser__progressbar_series"></div>
12125
12126 <div class="teaser__season-info text_genre-tag js-teaser-season-info">
12127 Staffel 1, Episode 15 </div>
12128 <div class="teaser__header text_teaser-landscape-title js-teaser-headline">
12129 Weit entfernte Sterne </div>
12130 </div>
12131
12132 <div class="teaser__hover teaser__hover_landscape">
12133 <svg class="icon teaser__play" role="img">
12134 <title>Abspielen</title>
12135 <use xlink:href="#wb-play_highlighted" xlink:title="Abspielen"><title>Abspielen</title></use>
12136 </svg>
12137
12138 <div class="teaser__gradient"></div>
12139
12140 <div class="teaser__content">
12141 <div class="text_teaser-landscape-meta">
12142 23 Min. | Japan | 2008 | FSK 12 </div>
12143 <div class="teaser__description text_teaser-landscape-description">
12144 Palmtop Tiger trifft auf Highschool-Drachen - Wenn aus Gegnern Verbündete werden... </div>
12145 <div class="teaser__buttons">
12146
12147<button class="button button_small js-teaser-button-toggle-add"><div class="button-wrapper">
12148
12149 <div class="button__icon" aria-hidden="true">
12150 <svg>
12151 <use xlink:href="#wb-add"></use>
12152 </svg>
12153 </div>
12154
12155 <div class="button__text text_button-small-title">
12156 Meine Liste </div>
12157
12158</div>
12159</button> </div>
12160 </div>
12161 </div>
12162</a>
12163 </section>
12164 <section class="swiper-slide" style="width: 302px; margin-right: 10px;">
12165
12166<a class="teaserset__teaser teaser js-teaser-item teaser_season-tab teaser_landscape" onclick="tracking.tagCommanderTrackEvent('gaProductClick', 'Enhanced Ecommerce', 'Product Click', null, null,{
12167 'list':'',
12168 'productClick':{
12169 'name': 'Ein\x20Schritt\x20nach\x20vorn',
12170 'id': '15561',
12171 'category': 'Serie',
12172 'brand': 'Anime,\x20Romantik',
12173 'position': ''
12174 }
12175 },null, event)" data-asset-id="15561" data-asset-title="Ein Schritt nach vorn" data-asset-list="" data-asset-type="format" data-asset-position="" data-asset-genre="Anime, Romantik" data-format-type="series" data-movie-id="409944" href="/serien/toradora-15561/staffel-1/ein-schritt-nach-vorn-409944.html">
12176
12177 <div class="teaser__image js-image">
12178 <img data-src="//aiswatchbox-a.akamaihd.net/watchbox/movie/409944/495x278/ein-schritt-nach-vorn.jpg" data-srcset="//aiswatchbox-a.akamaihd.net/watchbox/movie/409944/495x278/ein-schritt-nach-vorn.jpg 495w, //aiswatchbox-a.akamaihd.net/watchbox/movie/409944/378x213/ein-schritt-nach-vorn.jpg 378w, //aiswatchbox-a.akamaihd.net/watchbox/movie/409944/319x179/ein-schritt-nach-vorn.jpg 319w, //aiswatchbox-a.akamaihd.net/watchbox/movie/409944/352x198/ein-schritt-nach-vorn.jpg 352w" class=" swiper-lazy text_image-alt-tag" aria-hidden="true" alt="Ein Schritt nach vorn" itemprop=""> <div class="swiper-lazy-preloader swiper-lazy-preloader-white"></div>
12179 </div>
12180
12181 <div class="teaser__overlay js-teaser-overlay">
12182 <div class="js-teaser-series teaser__series teaser__series_landscape">
12183 <svg class="icon icon-series" role="img">
12184 <use xlink:href="#wb-series"><title>Serie</title></use>
12185 </svg>
12186 </div>
12187
12188 <div class="js-progress-bar teaser__progressbar teaser__progressbar_series"></div>
12189
12190 <div class="teaser__season-info text_genre-tag js-teaser-season-info">
12191 Staffel 1, Episode 16 </div>
12192 <div class="teaser__header text_teaser-landscape-title js-teaser-headline">
12193 Ein Schritt nach vorn </div>
12194 </div>
12195
12196 <div class="teaser__hover teaser__hover_landscape">
12197 <svg class="icon teaser__play" role="img">
12198 <title>Abspielen</title>
12199 <use xlink:href="#wb-play_highlighted" xlink:title="Abspielen"><title>Abspielen</title></use>
12200 </svg>
12201
12202 <div class="teaser__gradient"></div>
12203
12204 <div class="teaser__content">
12205 <div class="text_teaser-landscape-meta">
12206 23 Min. | Japan | 2008 | FSK 12 </div>
12207 <div class="teaser__description text_teaser-landscape-description">
12208 Palmtop Tiger trifft auf Highschool-Drachen - Wenn aus Gegnern Verbündete werden... </div>
12209 <div class="teaser__buttons">
12210
12211<button class="button button_small js-teaser-button-toggle-add"><div class="button-wrapper">
12212
12213 <div class="button__icon" aria-hidden="true">
12214 <svg>
12215 <use xlink:href="#wb-add"></use>
12216 </svg>
12217 </div>
12218
12219 <div class="button__text text_button-small-title">
12220 Meine Liste </div>
12221
12222</div>
12223</button> </div>
12224 </div>
12225 </div>
12226</a>
12227 </section>
12228 <section class="swiper-slide" style="width: 302px; margin-right: 10px;">
12229
12230<a class="teaserset__teaser teaser js-teaser-item teaser_season-tab teaser_landscape" onclick="tracking.tagCommanderTrackEvent('gaProductClick', 'Enhanced Ecommerce', 'Product Click', null, null,{
12231 'list':'',
12232 'productClick':{
12233 'name': 'Schrei\x20nach\x20Liebe',
12234 'id': '15561',
12235 'category': 'Serie',
12236 'brand': 'Anime,\x20Romantik',
12237 'position': ''
12238 }
12239 },null, event)" data-asset-id="15561" data-asset-title="Schrei nach Liebe" data-asset-list="" data-asset-type="format" data-asset-position="" data-asset-genre="Anime, Romantik" data-format-type="series" data-movie-id="409946" href="/serien/toradora-15561/staffel-1/schrei-nach-liebe-409946.html">
12240
12241 <div class="teaser__image js-image">
12242 <img data-src="//aiswatchbox-a.akamaihd.net/watchbox/movie/409946/495x278/schrei-nach-liebe.jpg" data-srcset="//aiswatchbox-a.akamaihd.net/watchbox/movie/409946/495x278/schrei-nach-liebe.jpg 495w, //aiswatchbox-a.akamaihd.net/watchbox/movie/409946/378x213/schrei-nach-liebe.jpg 378w, //aiswatchbox-a.akamaihd.net/watchbox/movie/409946/319x179/schrei-nach-liebe.jpg 319w, //aiswatchbox-a.akamaihd.net/watchbox/movie/409946/352x198/schrei-nach-liebe.jpg 352w" class=" swiper-lazy text_image-alt-tag" aria-hidden="true" alt="Schrei nach Liebe" itemprop=""> <div class="swiper-lazy-preloader swiper-lazy-preloader-white"></div>
12243 </div>
12244
12245 <div class="teaser__overlay js-teaser-overlay">
12246 <div class="js-teaser-series teaser__series teaser__series_landscape">
12247 <svg class="icon icon-series" role="img">
12248 <use xlink:href="#wb-series"><title>Serie</title></use>
12249 </svg>
12250 </div>
12251
12252 <div class="js-progress-bar teaser__progressbar teaser__progressbar_series"></div>
12253
12254 <div class="teaser__season-info text_genre-tag js-teaser-season-info">
12255 Staffel 1, Episode 17 </div>
12256 <div class="teaser__header text_teaser-landscape-title js-teaser-headline">
12257 Schrei nach Liebe </div>
12258 </div>
12259
12260 <div class="teaser__hover teaser__hover_landscape">
12261 <svg class="icon teaser__play" role="img">
12262 <title>Abspielen</title>
12263 <use xlink:href="#wb-play_highlighted" xlink:title="Abspielen"><title>Abspielen</title></use>
12264 </svg>
12265
12266 <div class="teaser__gradient"></div>
12267
12268 <div class="teaser__content">
12269 <div class="text_teaser-landscape-meta">
12270 23 Min. | Japan | 2008 | FSK 12 </div>
12271 <div class="teaser__description text_teaser-landscape-description">
12272 Palmtop Tiger trifft auf Highschool-Drachen - Wenn aus Gegnern Verbündete werden... </div>
12273 <div class="teaser__buttons">
12274
12275<button class="button button_small js-teaser-button-toggle-add"><div class="button-wrapper">
12276
12277 <div class="button__icon" aria-hidden="true">
12278 <svg>
12279 <use xlink:href="#wb-add"></use>
12280 </svg>
12281 </div>
12282
12283 <div class="button__text text_button-small-title">
12284 Meine Liste </div>
12285
12286</div>
12287</button> </div>
12288 </div>
12289 </div>
12290</a>
12291 </section>
12292 <section class="swiper-slide" style="width: 302px; margin-right: 10px;">
12293
12294<a class="teaserset__teaser teaser js-teaser-item teaser_season-tab teaser_landscape" onclick="tracking.tagCommanderTrackEvent('gaProductClick', 'Enhanced Ecommerce', 'Product Click', null, null,{
12295 'list':'',
12296 'productClick':{
12297 'name': 'Unterm\x20Tannenbaum',
12298 'id': '15561',
12299 'category': 'Serie',
12300 'brand': 'Anime,\x20Romantik',
12301 'position': ''
12302 }
12303 },null, event)" data-asset-id="15561" data-asset-title="Unterm Tannenbaum" data-asset-list="" data-asset-type="format" data-asset-position="" data-asset-genre="Anime, Romantik" data-format-type="series" data-movie-id="409972" href="/serien/toradora-15561/staffel-1/unterm-tannenbaum-409972.html">
12304
12305 <div class="teaser__image js-image">
12306 <img data-src="//aiswatchbox-a.akamaihd.net/watchbox/movie/409972/495x278/unterm-tannenbaum.jpg" data-srcset="//aiswatchbox-a.akamaihd.net/watchbox/movie/409972/495x278/unterm-tannenbaum.jpg 495w, //aiswatchbox-a.akamaihd.net/watchbox/movie/409972/378x213/unterm-tannenbaum.jpg 378w, //aiswatchbox-a.akamaihd.net/watchbox/movie/409972/319x179/unterm-tannenbaum.jpg 319w, //aiswatchbox-a.akamaihd.net/watchbox/movie/409972/352x198/unterm-tannenbaum.jpg 352w" class=" swiper-lazy text_image-alt-tag" aria-hidden="true" alt="Unterm Tannenbaum" itemprop=""> <div class="swiper-lazy-preloader swiper-lazy-preloader-white"></div>
12307 </div>
12308
12309 <div class="teaser__overlay js-teaser-overlay">
12310 <div class="js-teaser-series teaser__series teaser__series_landscape">
12311 <svg class="icon icon-series" role="img">
12312 <use xlink:href="#wb-series"><title>Serie</title></use>
12313 </svg>
12314 </div>
12315
12316 <div class="js-progress-bar teaser__progressbar teaser__progressbar_series"></div>
12317
12318 <div class="teaser__season-info text_genre-tag js-teaser-season-info">
12319 Staffel 1, Episode 18 </div>
12320 <div class="teaser__header text_teaser-landscape-title js-teaser-headline">
12321 Unterm Tannenbaum </div>
12322 </div>
12323
12324 <div class="teaser__hover teaser__hover_landscape">
12325 <svg class="icon teaser__play" role="img">
12326 <title>Abspielen</title>
12327 <use xlink:href="#wb-play_highlighted" xlink:title="Abspielen"><title>Abspielen</title></use>
12328 </svg>
12329
12330 <div class="teaser__gradient"></div>
12331
12332 <div class="teaser__content">
12333 <div class="text_teaser-landscape-meta">
12334 23 Min. | Japan | 2008 | FSK 12 </div>
12335 <div class="teaser__description text_teaser-landscape-description">
12336 Palmtop Tiger trifft auf Highschool-Drachen - Wenn aus Gegnern Verbündete werden... </div>
12337 <div class="teaser__buttons">
12338
12339<button class="button button_small js-teaser-button-toggle-add"><div class="button-wrapper">
12340
12341 <div class="button__icon" aria-hidden="true">
12342 <svg>
12343 <use xlink:href="#wb-add"></use>
12344 </svg>
12345 </div>
12346
12347 <div class="button__text text_button-small-title">
12348 Meine Liste </div>
12349
12350</div>
12351</button> </div>
12352 </div>
12353 </div>
12354</a>
12355 </section>
12356 <section class="swiper-slide" style="width: 302px; margin-right: 10px;">
12357
12358<a class="teaserset__teaser teaser js-teaser-item teaser_season-tab teaser_landscape" onclick="tracking.tagCommanderTrackEvent('gaProductClick', 'Enhanced Ecommerce', 'Product Click', null, null,{
12359 'list':'',
12360 'productClick':{
12361 'name': 'Die\x20Weihnachtsfeier',
12362 'id': '15561',
12363 'category': 'Serie',
12364 'brand': 'Anime,\x20Romantik',
12365 'position': ''
12366 }
12367 },null, event)" data-asset-id="15561" data-asset-title="Die Weihnachtsfeier" data-asset-list="" data-asset-type="format" data-asset-position="" data-asset-genre="Anime, Romantik" data-format-type="series" data-movie-id="409948" href="/serien/toradora-15561/staffel-1/die-weihnachtsfeier-409948.html">
12368
12369 <div class="teaser__image js-image">
12370 <img data-src="//aiswatchbox-a.akamaihd.net/watchbox/movie/409948/495x278/die-weihnachtsfeier.jpg" data-srcset="//aiswatchbox-a.akamaihd.net/watchbox/movie/409948/495x278/die-weihnachtsfeier.jpg 495w, //aiswatchbox-a.akamaihd.net/watchbox/movie/409948/378x213/die-weihnachtsfeier.jpg 378w, //aiswatchbox-a.akamaihd.net/watchbox/movie/409948/319x179/die-weihnachtsfeier.jpg 319w, //aiswatchbox-a.akamaihd.net/watchbox/movie/409948/352x198/die-weihnachtsfeier.jpg 352w" class=" swiper-lazy text_image-alt-tag" aria-hidden="true" alt="Die Weihnachtsfeier" itemprop=""> <div class="swiper-lazy-preloader swiper-lazy-preloader-white"></div>
12371 </div>
12372
12373 <div class="teaser__overlay js-teaser-overlay">
12374 <div class="js-teaser-series teaser__series teaser__series_landscape">
12375 <svg class="icon icon-series" role="img">
12376 <use xlink:href="#wb-series"><title>Serie</title></use>
12377 </svg>
12378 </div>
12379
12380 <div class="js-progress-bar teaser__progressbar teaser__progressbar_series"></div>
12381
12382 <div class="teaser__season-info text_genre-tag js-teaser-season-info">
12383 Staffel 1, Episode 19 </div>
12384 <div class="teaser__header text_teaser-landscape-title js-teaser-headline">
12385 Die Weihnachtsfeier </div>
12386 </div>
12387
12388 <div class="teaser__hover teaser__hover_landscape">
12389 <svg class="icon teaser__play" role="img">
12390 <title>Abspielen</title>
12391 <use xlink:href="#wb-play_highlighted" xlink:title="Abspielen"><title>Abspielen</title></use>
12392 </svg>
12393
12394 <div class="teaser__gradient"></div>
12395
12396 <div class="teaser__content">
12397 <div class="text_teaser-landscape-meta">
12398 23 Min. | Japan | 2008 | FSK 12 </div>
12399 <div class="teaser__description text_teaser-landscape-description">
12400 Palmtop Tiger trifft auf Highschool-Drachen - Wenn aus Gegnern Verbündete werden... </div>
12401 <div class="teaser__buttons">
12402
12403<button class="button button_small js-teaser-button-toggle-add"><div class="button-wrapper">
12404
12405 <div class="button__icon" aria-hidden="true">
12406 <svg>
12407 <use xlink:href="#wb-add"></use>
12408 </svg>
12409 </div>
12410
12411 <div class="button__text text_button-small-title">
12412 Meine Liste </div>
12413
12414</div>
12415</button> </div>
12416 </div>
12417 </div>
12418</a>
12419 </section>
12420 <section class="swiper-slide" style="width: 302px; margin-right: 10px;">
12421
12422<a class="teaserset__teaser teaser js-teaser-item teaser_season-tab teaser_landscape" onclick="tracking.tagCommanderTrackEvent('gaProductClick', 'Enhanced Ecommerce', 'Product Click', null, null,{
12423 'list':'',
12424 'productClick':{
12425 'name': 'F\u00FCr\x20immer\x20so',
12426 'id': '15561',
12427 'category': 'Serie',
12428 'brand': 'Anime,\x20Romantik',
12429 'position': ''
12430 }
12431 },null, event)" data-asset-id="15561" data-asset-title="Für immer so" data-asset-list="" data-asset-type="format" data-asset-position="" data-asset-genre="Anime, Romantik" data-format-type="series" data-movie-id="409968" href="/serien/toradora-15561/staffel-1/fuer-immer-so-409968.html">
12432
12433 <div class="teaser__image js-image">
12434 <img data-src="//aiswatchbox-a.akamaihd.net/watchbox/movie/409968/495x278/fuer-immer-so.jpg" data-srcset="//aiswatchbox-a.akamaihd.net/watchbox/movie/409968/495x278/fuer-immer-so.jpg 495w, //aiswatchbox-a.akamaihd.net/watchbox/movie/409968/378x213/fuer-immer-so.jpg 378w, //aiswatchbox-a.akamaihd.net/watchbox/movie/409968/319x179/fuer-immer-so.jpg 319w, //aiswatchbox-a.akamaihd.net/watchbox/movie/409968/352x198/fuer-immer-so.jpg 352w" class=" swiper-lazy text_image-alt-tag" aria-hidden="true" alt="Für immer so" itemprop=""> <div class="swiper-lazy-preloader swiper-lazy-preloader-white"></div>
12435 </div>
12436
12437 <div class="teaser__overlay js-teaser-overlay">
12438 <div class="js-teaser-series teaser__series teaser__series_landscape">
12439 <svg class="icon icon-series" role="img">
12440 <use xlink:href="#wb-series"><title>Serie</title></use>
12441 </svg>
12442 </div>
12443
12444 <div class="js-progress-bar teaser__progressbar teaser__progressbar_series"></div>
12445
12446 <div class="teaser__season-info text_genre-tag js-teaser-season-info">
12447 Staffel 1, Episode 20 </div>
12448 <div class="teaser__header text_teaser-landscape-title js-teaser-headline">
12449 Für immer so </div>
12450 </div>
12451
12452 <div class="teaser__hover teaser__hover_landscape">
12453 <svg class="icon teaser__play" role="img">
12454 <title>Abspielen</title>
12455 <use xlink:href="#wb-play_highlighted" xlink:title="Abspielen"><title>Abspielen</title></use>
12456 </svg>
12457
12458 <div class="teaser__gradient"></div>
12459
12460 <div class="teaser__content">
12461 <div class="text_teaser-landscape-meta">
12462 23 Min. | Japan | 2008 | FSK 12 </div>
12463 <div class="teaser__description text_teaser-landscape-description">
12464 Palmtop Tiger trifft auf Highschool-Drachen - Wenn aus Gegnern Verbündete werden... </div>
12465 <div class="teaser__buttons">
12466
12467<button class="button button_small js-teaser-button-toggle-add"><div class="button-wrapper">
12468
12469 <div class="button__icon" aria-hidden="true">
12470 <svg>
12471 <use xlink:href="#wb-add"></use>
12472 </svg>
12473 </div>
12474
12475 <div class="button__text text_button-small-title">
12476 Meine Liste </div>
12477
12478</div>
12479</button> </div>
12480 </div>
12481 </div>
12482</a>
12483 </section>
12484 <section class="swiper-slide" style="width: 302px; margin-right: 10px;">
12485
12486<a class="teaserset__teaser teaser js-teaser-item teaser_season-tab teaser_landscape" onclick="tracking.tagCommanderTrackEvent('gaProductClick', 'Enhanced Ecommerce', 'Product Click', null, null,{
12487 'list':'',
12488 'productClick':{
12489 'name': 'Was\x20auch\x20geschieht',
12490 'id': '15561',
12491 'category': 'Serie',
12492 'brand': 'Anime,\x20Romantik',
12493 'position': ''
12494 }
12495 },null, event)" data-asset-id="15561" data-asset-title="Was auch geschieht" data-asset-list="" data-asset-type="format" data-asset-position="" data-asset-genre="Anime, Romantik" data-format-type="series" data-movie-id="417130" href="/serien/toradora-15561/staffel-1/was-auch-geschieht-417130.html">
12496
12497 <div class="teaser__image js-image">
12498 <img data-src="//aiswatchbox-a.akamaihd.net/watchbox/movie/417130/495x278/was-auch-geschieht.jpg" data-srcset="//aiswatchbox-a.akamaihd.net/watchbox/movie/417130/495x278/was-auch-geschieht.jpg 495w, //aiswatchbox-a.akamaihd.net/watchbox/movie/417130/378x213/was-auch-geschieht.jpg 378w, //aiswatchbox-a.akamaihd.net/watchbox/movie/417130/319x179/was-auch-geschieht.jpg 319w, //aiswatchbox-a.akamaihd.net/watchbox/movie/417130/352x198/was-auch-geschieht.jpg 352w" class=" swiper-lazy text_image-alt-tag" aria-hidden="true" alt="Was auch geschieht" itemprop=""> <div class="swiper-lazy-preloader swiper-lazy-preloader-white"></div>
12499 </div>
12500
12501 <div class="teaser__overlay js-teaser-overlay">
12502 <div class="js-teaser-series teaser__series teaser__series_landscape">
12503 <svg class="icon icon-series" role="img">
12504 <use xlink:href="#wb-series"><title>Serie</title></use>
12505 </svg>
12506 </div>
12507
12508 <div class="js-progress-bar teaser__progressbar teaser__progressbar_series"></div>
12509
12510 <div class="teaser__season-info text_genre-tag js-teaser-season-info">
12511 Staffel 1, Episode 21 </div>
12512 <div class="teaser__header text_teaser-landscape-title js-teaser-headline">
12513 Was auch geschieht </div>
12514 </div>
12515
12516 <div class="teaser__hover teaser__hover_landscape">
12517 <svg class="icon teaser__play" role="img">
12518 <title>Abspielen</title>
12519 <use xlink:href="#wb-play_highlighted" xlink:title="Abspielen"><title>Abspielen</title></use>
12520 </svg>
12521
12522 <div class="teaser__gradient"></div>
12523
12524 <div class="teaser__content">
12525 <div class="text_teaser-landscape-meta">
12526 22 Min. | Japan | 2008 | FSK 12 </div>
12527 <div class="teaser__description text_teaser-landscape-description">
12528 Palmtop Tiger trifft auf Highschool-Drachen - Wenn aus Gegnern Verbündete werden... </div>
12529 <div class="teaser__buttons">
12530
12531<button class="button button_small js-teaser-button-toggle-add"><div class="button-wrapper">
12532
12533 <div class="button__icon" aria-hidden="true">
12534 <svg>
12535 <use xlink:href="#wb-add"></use>
12536 </svg>
12537 </div>
12538
12539 <div class="button__text text_button-small-title">
12540 Meine Liste </div>
12541
12542</div>
12543</button> </div>
12544 </div>
12545 </div>
12546</a>
12547 </section>
12548 <section class="swiper-slide" style="width: 302px; margin-right: 10px;">
12549
12550<a class="teaserset__teaser teaser js-teaser-item teaser_season-tab teaser_landscape" onclick="tracking.tagCommanderTrackEvent('gaProductClick', 'Enhanced Ecommerce', 'Product Click', null, null,{
12551 'list':'',
12552 'productClick':{
12553 'name': 'Die\x20Welt\x20mit\x20dir',
12554 'id': '15561',
12555 'category': 'Serie',
12556 'brand': 'Anime,\x20Romantik',
12557 'position': ''
12558 }
12559 },null, event)" data-asset-id="15561" data-asset-title="Die Welt mit dir" data-asset-list="" data-asset-type="format" data-asset-position="" data-asset-genre="Anime, Romantik" data-format-type="series" data-movie-id="417172" href="/serien/toradora-15561/staffel-1/die-welt-mit-dir-417172.html">
12560
12561 <div class="teaser__image js-image">
12562 <img data-src="//aiswatchbox-a.akamaihd.net/watchbox/movie/417172/495x278/die-welt-mit-dir.jpg" data-srcset="//aiswatchbox-a.akamaihd.net/watchbox/movie/417172/495x278/die-welt-mit-dir.jpg 495w, //aiswatchbox-a.akamaihd.net/watchbox/movie/417172/378x213/die-welt-mit-dir.jpg 378w, //aiswatchbox-a.akamaihd.net/watchbox/movie/417172/319x179/die-welt-mit-dir.jpg 319w, //aiswatchbox-a.akamaihd.net/watchbox/movie/417172/352x198/die-welt-mit-dir.jpg 352w" class=" swiper-lazy text_image-alt-tag" aria-hidden="true" alt="Die Welt mit dir" itemprop=""> <div class="swiper-lazy-preloader swiper-lazy-preloader-white"></div>
12563 </div>
12564
12565 <div class="teaser__overlay js-teaser-overlay">
12566 <div class="js-teaser-series teaser__series teaser__series_landscape">
12567 <svg class="icon icon-series" role="img">
12568 <use xlink:href="#wb-series"><title>Serie</title></use>
12569 </svg>
12570 </div>
12571
12572 <div class="js-progress-bar teaser__progressbar teaser__progressbar_series"></div>
12573
12574 <div class="teaser__season-info text_genre-tag js-teaser-season-info">
12575 Staffel 1, Episode 22 </div>
12576 <div class="teaser__header text_teaser-landscape-title js-teaser-headline">
12577 Die Welt mit dir </div>
12578 </div>
12579
12580 <div class="teaser__hover teaser__hover_landscape">
12581 <svg class="icon teaser__play" role="img">
12582 <title>Abspielen</title>
12583 <use xlink:href="#wb-play_highlighted" xlink:title="Abspielen"><title>Abspielen</title></use>
12584 </svg>
12585
12586 <div class="teaser__gradient"></div>
12587
12588 <div class="teaser__content">
12589 <div class="text_teaser-landscape-meta">
12590 22 Min. | Japan | 2008 | FSK 12 </div>
12591 <div class="teaser__description text_teaser-landscape-description">
12592 Palmtop Tiger trifft auf Highschool-Drachen - Wenn aus Gegnern Verbündete werden... </div>
12593 <div class="teaser__buttons">
12594
12595<button class="button button_small js-teaser-button-toggle-add"><div class="button-wrapper">
12596
12597 <div class="button__icon" aria-hidden="true">
12598 <svg>
12599 <use xlink:href="#wb-add"></use>
12600 </svg>
12601 </div>
12602
12603 <div class="button__text text_button-small-title">
12604 Meine Liste </div>
12605
12606</div>
12607</button> </div>
12608 </div>
12609 </div>
12610</a>
12611 </section>
12612 <section class="swiper-slide" style="width: 302px; margin-right: 10px;">
12613
12614<a class="teaserset__teaser teaser js-teaser-item teaser_season-tab teaser_landscape" onclick="tracking.tagCommanderTrackEvent('gaProductClick', 'Enhanced Ecommerce', 'Product Click', null, null,{
12615 'list':'',
12616 'productClick':{
12617 'name': 'Unser\x20Weg',
12618 'id': '15561',
12619 'category': 'Serie',
12620 'brand': 'Anime,\x20Romantik',
12621 'position': ''
12622 }
12623 },null, event)" data-asset-id="15561" data-asset-title="Unser Weg" data-asset-list="" data-asset-type="format" data-asset-position="" data-asset-genre="Anime, Romantik" data-format-type="series" data-movie-id="417178" href="/serien/toradora-15561/staffel-1/unser-weg-417178.html">
12624
12625 <div class="teaser__image js-image">
12626 <img data-src="//aiswatchbox-a.akamaihd.net/watchbox/movie/417178/495x278/unser-weg.jpg" data-srcset="//aiswatchbox-a.akamaihd.net/watchbox/movie/417178/495x278/unser-weg.jpg 495w, //aiswatchbox-a.akamaihd.net/watchbox/movie/417178/378x213/unser-weg.jpg 378w, //aiswatchbox-a.akamaihd.net/watchbox/movie/417178/319x179/unser-weg.jpg 319w, //aiswatchbox-a.akamaihd.net/watchbox/movie/417178/352x198/unser-weg.jpg 352w" class=" swiper-lazy text_image-alt-tag" aria-hidden="true" alt="Unser Weg" itemprop=""> <div class="swiper-lazy-preloader swiper-lazy-preloader-white"></div>
12627 </div>
12628
12629 <div class="teaser__overlay js-teaser-overlay">
12630 <div class="js-teaser-series teaser__series teaser__series_landscape">
12631 <svg class="icon icon-series" role="img">
12632 <use xlink:href="#wb-series"><title>Serie</title></use>
12633 </svg>
12634 </div>
12635
12636 <div class="js-progress-bar teaser__progressbar teaser__progressbar_series"></div>
12637
12638 <div class="teaser__season-info text_genre-tag js-teaser-season-info">
12639 Staffel 1, Episode 23 </div>
12640 <div class="teaser__header text_teaser-landscape-title js-teaser-headline">
12641 Unser Weg </div>
12642 </div>
12643
12644 <div class="teaser__hover teaser__hover_landscape">
12645 <svg class="icon teaser__play" role="img">
12646 <title>Abspielen</title>
12647 <use xlink:href="#wb-play_highlighted" xlink:title="Abspielen"><title>Abspielen</title></use>
12648 </svg>
12649
12650 <div class="teaser__gradient"></div>
12651
12652 <div class="teaser__content">
12653 <div class="text_teaser-landscape-meta">
12654 22 Min. | Japan | 2008 | FSK 12 </div>
12655 <div class="teaser__description text_teaser-landscape-description">
12656 Palmtop Tiger trifft auf Highschool-Drachen - Wenn aus Gegnern Verbündete werden... </div>
12657 <div class="teaser__buttons">
12658
12659<button class="button button_small js-teaser-button-toggle-add"><div class="button-wrapper">
12660
12661 <div class="button__icon" aria-hidden="true">
12662 <svg>
12663 <use xlink:href="#wb-add"></use>
12664 </svg>
12665 </div>
12666
12667 <div class="button__text text_button-small-title">
12668 Meine Liste </div>
12669
12670</div>
12671</button> </div>
12672 </div>
12673 </div>
12674</a>
12675 </section>
12676 <section class="swiper-slide" style="width: 302px; margin-right: 10px;">
12677
12678<a class="teaserset__teaser teaser js-teaser-item teaser_season-tab teaser_landscape" onclick="tracking.tagCommanderTrackEvent('gaProductClick', 'Enhanced Ecommerce', 'Product Click', null, null,{
12679 'list':'',
12680 'productClick':{
12681 'name': 'Das\x20Gest\u00E4ndnis',
12682 'id': '15561',
12683 'category': 'Serie',
12684 'brand': 'Anime,\x20Romantik',
12685 'position': ''
12686 }
12687 },null, event)" data-asset-id="15561" data-asset-title="Das Geständnis" data-asset-list="" data-asset-type="format" data-asset-position="" data-asset-genre="Anime, Romantik" data-format-type="series" data-movie-id="417170" href="/serien/toradora-15561/staffel-1/das-gestaendnis-417170.html">
12688
12689 <div class="teaser__image js-image">
12690 <img data-src="//aiswatchbox-a.akamaihd.net/watchbox/movie/417170/495x278/das-gestaendnis.jpg" data-srcset="//aiswatchbox-a.akamaihd.net/watchbox/movie/417170/495x278/das-gestaendnis.jpg 495w, //aiswatchbox-a.akamaihd.net/watchbox/movie/417170/378x213/das-gestaendnis.jpg 378w, //aiswatchbox-a.akamaihd.net/watchbox/movie/417170/319x179/das-gestaendnis.jpg 319w, //aiswatchbox-a.akamaihd.net/watchbox/movie/417170/352x198/das-gestaendnis.jpg 352w" class=" swiper-lazy text_image-alt-tag" aria-hidden="true" alt="Das Geständnis" itemprop=""> <div class="swiper-lazy-preloader swiper-lazy-preloader-white"></div>
12691 </div>
12692
12693 <div class="teaser__overlay js-teaser-overlay">
12694 <div class="js-teaser-series teaser__series teaser__series_landscape">
12695 <svg class="icon icon-series" role="img">
12696 <use xlink:href="#wb-series"><title>Serie</title></use>
12697 </svg>
12698 </div>
12699
12700 <div class="js-progress-bar teaser__progressbar teaser__progressbar_series"></div>
12701
12702 <div class="teaser__season-info text_genre-tag js-teaser-season-info">
12703 Staffel 1, Episode 24 </div>
12704 <div class="teaser__header text_teaser-landscape-title js-teaser-headline">
12705 Das Geständnis </div>
12706 </div>
12707
12708 <div class="teaser__hover teaser__hover_landscape">
12709 <svg class="icon teaser__play" role="img">
12710 <title>Abspielen</title>
12711 <use xlink:href="#wb-play_highlighted" xlink:title="Abspielen"><title>Abspielen</title></use>
12712 </svg>
12713
12714 <div class="teaser__gradient"></div>
12715
12716 <div class="teaser__content">
12717 <div class="text_teaser-landscape-meta">
12718 22 Min. | Japan | 2008 | FSK 12 </div>
12719 <div class="teaser__description text_teaser-landscape-description">
12720 Palmtop Tiger trifft auf Highschool-Drachen - Wenn aus Gegnern Verbündete werden... </div>
12721 <div class="teaser__buttons">
12722
12723<button class="button button_small js-teaser-button-toggle-add"><div class="button-wrapper">
12724
12725 <div class="button__icon" aria-hidden="true">
12726 <svg>
12727 <use xlink:href="#wb-add"></use>
12728 </svg>
12729 </div>
12730
12731 <div class="button__text text_button-small-title">
12732 Meine Liste </div>
12733
12734</div>
12735</button> </div>
12736 </div>
12737 </div>
12738</a>
12739 </section>
12740 <section class="swiper-slide" style="width: 302px; margin-right: 10px;">
12741
12742<a class="teaserset__teaser teaser js-teaser-item teaser_season-tab teaser_landscape" onclick="tracking.tagCommanderTrackEvent('gaProductClick', 'Enhanced Ecommerce', 'Product Click', null, null,{
12743 'list':'',
12744 'productClick':{
12745 'name': 'Toradora\x21',
12746 'id': '15561',
12747 'category': 'Serie',
12748 'brand': 'Anime,\x20Romantik',
12749 'position': ''
12750 }
12751 },null, event)" data-asset-id="15561" data-asset-title="Toradora!" data-asset-list="" data-asset-type="format" data-asset-position="" data-asset-genre="Anime, Romantik" data-format-type="series" data-movie-id="417174" href="/serien/toradora-15561/staffel-1/toradora-417174.html">
12752
12753 <div class="teaser__image js-image">
12754 <img data-src="//aiswatchbox-a.akamaihd.net/watchbox/movie/417174/495x278/toradora.jpg" data-srcset="//aiswatchbox-a.akamaihd.net/watchbox/movie/417174/495x278/toradora.jpg 495w, //aiswatchbox-a.akamaihd.net/watchbox/movie/417174/378x213/toradora.jpg 378w, //aiswatchbox-a.akamaihd.net/watchbox/movie/417174/319x179/toradora.jpg 319w, //aiswatchbox-a.akamaihd.net/watchbox/movie/417174/352x198/toradora.jpg 352w" class=" swiper-lazy text_image-alt-tag" aria-hidden="true" alt="Toradora!" itemprop=""> <div class="swiper-lazy-preloader swiper-lazy-preloader-white"></div>
12755 </div>
12756
12757 <div class="teaser__overlay js-teaser-overlay">
12758 <div class="js-teaser-series teaser__series teaser__series_landscape">
12759 <svg class="icon icon-series" role="img">
12760 <use xlink:href="#wb-series"><title>Serie</title></use>
12761 </svg>
12762 </div>
12763
12764 <div class="js-progress-bar teaser__progressbar teaser__progressbar_series"></div>
12765
12766 <div class="teaser__season-info text_genre-tag js-teaser-season-info">
12767 Staffel 1, Episode 25 </div>
12768 <div class="teaser__header text_teaser-landscape-title js-teaser-headline">
12769 Toradora! </div>
12770 </div>
12771
12772 <div class="teaser__hover teaser__hover_landscape">
12773 <svg class="icon teaser__play" role="img">
12774 <title>Abspielen</title>
12775 <use xlink:href="#wb-play_highlighted" xlink:title="Abspielen"><title>Abspielen</title></use>
12776 </svg>
12777
12778 <div class="teaser__gradient"></div>
12779
12780 <div class="teaser__content">
12781 <div class="text_teaser-landscape-meta">
12782 22 Min. | Japan | 2008 | FSK 12 </div>
12783 <div class="teaser__description text_teaser-landscape-description">
12784 Palmtop Tiger trifft auf Highschool-Drachen - Wenn aus Gegnern Verbündete werden... </div>
12785 <div class="teaser__buttons">
12786
12787<button class="button button_small js-teaser-button-toggle-add"><div class="button-wrapper">
12788
12789 <div class="button__icon" aria-hidden="true">
12790 <svg>
12791 <use xlink:href="#wb-add"></use>
12792 </svg>
12793 </div>
12794
12795 <div class="button__text text_button-small-title">
12796 Meine Liste </div>
12797
12798</div>
12799</button> </div>
12800 </div>
12801 </div>
12802</a>
12803 </section>
12804 </div>
12805 </div>
12806
12807 <button class="slick-arrow slick-next" style="">
12808 <svg class="icon " aria-hidden="true">
12809 <use xlink:href="#wb-next"></use>
12810 </svg>
12811 </button>
12812</div>
12813
12814<section id="js-template-teaser" style="display: none;">
12815
12816<a class="teaserset__teaser teaser js-teaser-item teaser_season-tab teaser_landscape" onclick="tracking.tagCommanderTrackEvent('gaProductClick', 'Enhanced Ecommerce', 'Product Click', null, null,{
12817 'list':'',
12818 'productClick':{
12819 'name': 'Platzhalter',
12820 'id': '1',
12821 'category': 'Serie',
12822 'brand': '',
12823 'position': ''
12824 }
12825 },null, event)" data-asset-id="1" data-asset-title="Platzhalter" data-asset-list="" data-asset-type="format" data-asset-position="" data-asset-genre="" data-format-type="series" data-movie-id="1" href="#">
12826
12827 <div class="teaser__image js-image">
12828 <img data-src="" data-srcset=" 1599w, 1365w, 991w, 767w" class=" swiper-lazy text_image-alt-tag" aria-hidden="true" alt="Platzhalter" itemprop=""> <div class="swiper-lazy-preloader swiper-lazy-preloader-white"></div>
12829 </div>
12830
12831 <div class="teaser__overlay js-teaser-overlay">
12832 <div class="js-teaser-series teaser__series teaser__series_landscape">
12833 <svg class="icon icon-series" role="img">
12834 <use xlink:href="#wb-series"><title>Serie</title></use>
12835 </svg>
12836 </div>
12837
12838 <div class="js-progress-bar teaser__progressbar teaser__progressbar_series"></div>
12839
12840 <div class="teaser__season-info text_genre-tag js-teaser-season-info">
12841 1, Episode 1 </div>
12842 <div class="teaser__header text_teaser-landscape-title js-teaser-headline">
12843 Platzhalter </div>
12844 </div>
12845
12846 <div class="teaser__hover teaser__hover_landscape">
12847 <svg class="icon teaser__play" role="img">
12848 <title>Abspielen</title>
12849 <use xlink:href="#wb-play_highlighted" xlink:title="Abspielen"><title>Abspielen</title></use>
12850 </svg>
12851
12852 <div class="teaser__gradient"></div>
12853
12854 <div class="teaser__content">
12855 <div class="text_teaser-landscape-meta">
12856 FSK 0 </div>
12857 <div class="teaser__description text_teaser-landscape-description">
12858 Platzhalter </div>
12859 <div class="teaser__buttons">
12860
12861<button class="button button_small js-teaser-button-toggle-add"><div class="button-wrapper">
12862
12863 <div class="button__icon" aria-hidden="true">
12864 <svg>
12865 <use xlink:href="#wb-add"></use>
12866 </svg>
12867 </div>
12868
12869 <div class="button__text text_button-small-title">
12870 Meine Liste </div>
12871
12872</div>
12873</button> </div>
12874 </div>
12875 </div>
12876</a>
12877</section>
12878
12879<script type="application/javascript">
12880 var wbSeasonData = {"activeSeasonNumber":1,"1":{"1":{"movieId":387850,"title":"Tiger und Drache","subtitle":null,"link":"\/serien\/toradora-15561\/staffel-1\/tiger-und-drache-387850.html","image":{"495":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/387850\/495x278\/tiger-und-drache.jpg","378":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/387850\/378x213\/tiger-und-drache.jpg","319":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/387850\/319x179\/tiger-und-drache.jpg","352":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/387850\/352x198\/tiger-und-drache.jpg"}},"2":{"movieId":387820,"title":"Ryuuji und Taiga","subtitle":null,"link":"\/serien\/toradora-15561\/staffel-1\/ryuuji-und-taiga-387820.html","image":{"495":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/387820\/495x278\/ryuuji-und-taiga.jpg","378":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/387820\/378x213\/ryuuji-und-taiga.jpg","319":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/387820\/319x179\/ryuuji-und-taiga.jpg","352":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/387820\/352x198\/ryuuji-und-taiga.jpg"}},"3":{"movieId":387832,"title":"Dein Song","subtitle":null,"link":"\/serien\/toradora-15561\/staffel-1\/dein-song-387832.html","image":{"495":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/387832\/495x278\/dein-song.jpg","378":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/387832\/378x213\/dein-song.jpg","319":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/387832\/319x179\/dein-song.jpg","352":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/387832\/352x198\/dein-song.jpg"}},"4":{"movieId":387828,"title":"Das Gesicht von damals","subtitle":null,"link":"\/serien\/toradora-15561\/staffel-1\/das-gesicht-von-damals-387828.html","image":{"495":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/387828\/495x278\/das-gesicht-von-damals.jpg","378":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/387828\/378x213\/das-gesicht-von-damals.jpg","319":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/387828\/319x179\/das-gesicht-von-damals.jpg","352":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/387828\/352x198\/das-gesicht-von-damals.jpg"}},"5":{"movieId":387878,"title":"Ami Kawashima","subtitle":null,"link":"\/serien\/toradora-15561\/staffel-1\/ami-kawashima-387878.html","image":{"495":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/387878\/495x278\/ami-kawashima.jpg","378":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/387878\/378x213\/ami-kawashima.jpg","319":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/387878\/319x179\/ami-kawashima.jpg","352":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/387878\/352x198\/ami-kawashima.jpg"}},"6":{"movieId":387834,"title":"Wahres Gesicht","subtitle":null,"link":"\/serien\/toradora-15561\/staffel-1\/wahres-gesicht-387834.html","image":{"495":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/387834\/495x278\/wahres-gesicht.jpg","378":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/387834\/378x213\/wahres-gesicht.jpg","319":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/387834\/319x179\/wahres-gesicht.jpg","352":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/387834\/352x198\/wahres-gesicht.jpg"}},"7":{"movieId":387844,"title":"Schwimmbader\u00f6ffnung","subtitle":null,"link":"\/serien\/toradora-15561\/staffel-1\/schwimmbaderoeffnung-387844.html","image":{"495":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/387844\/495x278\/schwimmbaderoeffnung.jpg","378":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/387844\/378x213\/schwimmbaderoeffnung.jpg","319":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/387844\/319x179\/schwimmbaderoeffnung.jpg","352":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/387844\/352x198\/schwimmbaderoeffnung.jpg"}},"8":{"movieId":387846,"title":"Taiga vs. Ami","subtitle":null,"link":"\/serien\/toradora-15561\/staffel-1\/taiga-vs-ami-387846.html","image":{"495":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/387846\/495x278\/taiga-vs-ami.jpg","378":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/387846\/378x213\/taiga-vs-ami.jpg","319":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/387846\/319x179\/taiga-vs-ami.jpg","352":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/387846\/352x198\/taiga-vs-ami.jpg"}},"9":{"movieId":387882,"title":"Das Strandhaus","subtitle":null,"link":"\/serien\/toradora-15561\/staffel-1\/das-strandhaus-387882.html","image":{"495":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/387882\/495x278\/das-strandhaus.jpg","378":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/387882\/378x213\/das-strandhaus.jpg","319":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/387882\/319x179\/das-strandhaus.jpg","352":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/387882\/352x198\/das-strandhaus.jpg"}},"10":{"movieId":387848,"title":"Feuerwerk","subtitle":null,"link":"\/serien\/toradora-15561\/staffel-1\/feuerwerk-387848.html","image":{"495":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/387848\/495x278\/feuerwerk.jpg","378":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/387848\/378x213\/feuerwerk.jpg","319":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/387848\/319x179\/feuerwerk.jpg","352":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/387848\/352x198\/feuerwerk.jpg"}},"11":{"movieId":409960,"title":"Das Oohashi Kulturfest (Teil 1)","subtitle":null,"link":"\/serien\/toradora-15561\/staffel-1\/das-oohashi-kulturfest-teil-1-409960.html","image":{"495":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/409960\/495x278\/das-oohashi-kulturfest-teil-1.jpg","378":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/409960\/378x213\/das-oohashi-kulturfest-teil-1.jpg","319":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/409960\/319x179\/das-oohashi-kulturfest-teil-1.jpg","352":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/409960\/352x198\/das-oohashi-kulturfest-teil-1.jpg"}},"12":{"movieId":409966,"title":"Das Oohashi Kulturfest (Teil 2)","subtitle":null,"link":"\/serien\/toradora-15561\/staffel-1\/das-oohashi-kulturfest-teil-2-409966.html","image":{"495":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/409966\/495x278\/das-oohashi-kulturfest-teil-2.jpg","378":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/409966\/378x213\/das-oohashi-kulturfest-teil-2.jpg","319":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/409966\/319x179\/das-oohashi-kulturfest-teil-2.jpg","352":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/409966\/352x198\/das-oohashi-kulturfest-teil-2.jpg"}},"13":{"movieId":409942,"title":"Das Oohashi Kulturfest (Teil 3)","subtitle":null,"link":"\/serien\/toradora-15561\/staffel-1\/das-oohashi-kulturfest-teil-3-409942.html","image":{"495":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/409942\/495x278\/das-oohashi-kulturfest-teil-3.jpg","378":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/409942\/378x213\/das-oohashi-kulturfest-teil-3.jpg","319":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/409942\/319x179\/das-oohashi-kulturfest-teil-3.jpg","352":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/409942\/352x198\/das-oohashi-kulturfest-teil-3.jpg"}},"14":{"movieId":410714,"title":"Der Gl\u00fcckstiger","subtitle":null,"link":"\/serien\/toradora-15561\/staffel-1\/der-glueckstiger-410714.html","image":{"495":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/410714\/495x278\/der-glueckstiger.jpg","378":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/410714\/378x213\/der-glueckstiger.jpg","319":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/410714\/319x179\/der-glueckstiger.jpg","352":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/410714\/352x198\/der-glueckstiger.jpg"}},"15":{"movieId":409938,"title":"Weit entfernte Sterne","subtitle":null,"link":"\/serien\/toradora-15561\/staffel-1\/weit-entfernte-sterne-409938.html","image":{"495":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/409938\/495x278\/weit-entfernte-sterne.jpg","378":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/409938\/378x213\/weit-entfernte-sterne.jpg","319":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/409938\/319x179\/weit-entfernte-sterne.jpg","352":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/409938\/352x198\/weit-entfernte-sterne.jpg"}},"16":{"movieId":409944,"title":"Ein Schritt nach vorn","subtitle":null,"link":"\/serien\/toradora-15561\/staffel-1\/ein-schritt-nach-vorn-409944.html","image":{"495":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/409944\/495x278\/ein-schritt-nach-vorn.jpg","378":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/409944\/378x213\/ein-schritt-nach-vorn.jpg","319":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/409944\/319x179\/ein-schritt-nach-vorn.jpg","352":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/409944\/352x198\/ein-schritt-nach-vorn.jpg"}},"17":{"movieId":409946,"title":"Schrei nach Liebe","subtitle":null,"link":"\/serien\/toradora-15561\/staffel-1\/schrei-nach-liebe-409946.html","image":{"495":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/409946\/495x278\/schrei-nach-liebe.jpg","378":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/409946\/378x213\/schrei-nach-liebe.jpg","319":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/409946\/319x179\/schrei-nach-liebe.jpg","352":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/409946\/352x198\/schrei-nach-liebe.jpg"}},"18":{"movieId":409972,"title":"Unterm Tannenbaum","subtitle":null,"link":"\/serien\/toradora-15561\/staffel-1\/unterm-tannenbaum-409972.html","image":{"495":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/409972\/495x278\/unterm-tannenbaum.jpg","378":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/409972\/378x213\/unterm-tannenbaum.jpg","319":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/409972\/319x179\/unterm-tannenbaum.jpg","352":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/409972\/352x198\/unterm-tannenbaum.jpg"}},"19":{"movieId":409948,"title":"Die Weihnachtsfeier","subtitle":null,"link":"\/serien\/toradora-15561\/staffel-1\/die-weihnachtsfeier-409948.html","image":{"495":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/409948\/495x278\/die-weihnachtsfeier.jpg","378":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/409948\/378x213\/die-weihnachtsfeier.jpg","319":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/409948\/319x179\/die-weihnachtsfeier.jpg","352":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/409948\/352x198\/die-weihnachtsfeier.jpg"}},"20":{"movieId":409968,"title":"F\u00fcr immer so","subtitle":null,"link":"\/serien\/toradora-15561\/staffel-1\/fuer-immer-so-409968.html","image":{"495":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/409968\/495x278\/fuer-immer-so.jpg","378":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/409968\/378x213\/fuer-immer-so.jpg","319":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/409968\/319x179\/fuer-immer-so.jpg","352":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/409968\/352x198\/fuer-immer-so.jpg"}},"21":{"movieId":417130,"title":"Was auch geschieht","subtitle":null,"link":"\/serien\/toradora-15561\/staffel-1\/was-auch-geschieht-417130.html","image":{"495":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/417130\/495x278\/was-auch-geschieht.jpg","378":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/417130\/378x213\/was-auch-geschieht.jpg","319":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/417130\/319x179\/was-auch-geschieht.jpg","352":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/417130\/352x198\/was-auch-geschieht.jpg"}},"22":{"movieId":417172,"title":"Die Welt mit dir","subtitle":null,"link":"\/serien\/toradora-15561\/staffel-1\/die-welt-mit-dir-417172.html","image":{"495":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/417172\/495x278\/die-welt-mit-dir.jpg","378":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/417172\/378x213\/die-welt-mit-dir.jpg","319":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/417172\/319x179\/die-welt-mit-dir.jpg","352":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/417172\/352x198\/die-welt-mit-dir.jpg"}},"23":{"movieId":417178,"title":"Unser Weg","subtitle":null,"link":"\/serien\/toradora-15561\/staffel-1\/unser-weg-417178.html","image":{"495":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/417178\/495x278\/unser-weg.jpg","378":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/417178\/378x213\/unser-weg.jpg","319":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/417178\/319x179\/unser-weg.jpg","352":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/417178\/352x198\/unser-weg.jpg"}},"24":{"movieId":417170,"title":"Das Gest\u00e4ndnis","subtitle":null,"link":"\/serien\/toradora-15561\/staffel-1\/das-gestaendnis-417170.html","image":{"495":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/417170\/495x278\/das-gestaendnis.jpg","378":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/417170\/378x213\/das-gestaendnis.jpg","319":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/417170\/319x179\/das-gestaendnis.jpg","352":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/417170\/352x198\/das-gestaendnis.jpg"}},"25":{"movieId":417174,"title":"Toradora!","subtitle":null,"link":"\/serien\/toradora-15561\/staffel-1\/toradora-417174.html","image":{"495":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/417174\/495x278\/toradora.jpg","378":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/417174\/378x213\/toradora.jpg","319":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/417174\/319x179\/toradora.jpg","352":"\/\/aiswatchbox-a.akamaihd.net\/watchbox\/movie\/417174\/352x198\/toradora.jpg"}}}}</script>
12881
12882 </section>
12883</article>
12884 </main>
12885
12886 <footer>
12887 <div itemscope="" itemtype="http://schema.org/Organization" class="footer-separator text_footer-link">
12888 <a href="#top" class="footer-separator__jump-to-top js-jumptotop" aria-label="Zurück zum Anfang">
12889 <div class="scroll-top" aria-hidden="true">
12890 <div class="transform-top">
12891 <div class="arrow-top"></div>
12892 </div>
12893</div> </a>
12894 Folge uns
12895 <div class="footer-separator__social-icons">
12896 <a itemprop="sameAs" class="footer-separator__link" href="https://www.facebook.com/WATCHBOX" aria-label="Facebook">
12897 <svg class="icon icon_facebook">
12898 <use xlink:href="#wb-facebook"></use>
12899 </svg>
12900 </a>
12901 <a itemprop="sameAs" class="footer-separator__link" href="https://www.twitter.com/WATCHBOX" aria-label="Twitter">
12902 <svg class="icon icon_twitter">
12903 <use xlink:href="#wb-twitter"></use>
12904 </svg>
12905 </a>
12906 <a itemprop="sameAs" class="footer-separator__link" href="https://www.instagram.com/watchbox_de" aria-label="Instagram">
12907 <svg class="icon icon_instagram">
12908 <use xlink:href="#wb-instagram"></use>
12909 </svg>
12910 </a>
12911 </div>
12912</div>
12913
12914
12915
12916<ul class="breadcrumb text_footer-sublink" itemscope="" itemtype="http://schema.org/BreadcrumbList">
12917 <li class="breadcrumb__item" itemprop="itemListElement" itemscope="" itemtype="http://schema.org/ListItem">
12918 <a itemprop="item" class="footer-link " href="/">
12919 <span itemprop="name">Watchbox.de</span>
12920 <svg class="footer-link__icon" aria-hidden="true"><use xlink:href="#wb-next"></use></svg>
12921 </a>
12922 <meta itemprop="position" content="1">
12923 </li>
12924 <li class="breadcrumb__item" itemprop="itemListElement" itemscope="" itemtype="http://schema.org/ListItem">
12925 <a itemprop="item" class="footer-link " href="/serien">
12926 <span itemprop="name">Serien</span>
12927 <svg class="footer-link__icon" aria-hidden="true"><use xlink:href="#wb-next"></use></svg>
12928 </a>
12929 <meta itemprop="position" content="2">
12930 </li>
12931 <li class="breadcrumb__item" itemprop="itemListElement" itemscope="" itemtype="http://schema.org/ListItem">
12932 <a itemprop="item" class="footer-link " href="/serien/toradora-15561/">
12933 <span itemprop="name">Toradora! - Neue Folgen</span>
12934 <svg class="footer-link__icon" aria-hidden="true"><use xlink:href="#wb-next"></use></svg>
12935 </a>
12936 <meta itemprop="position" content="3">
12937 </li>
12938 <li class="breadcrumb__item" itemprop="itemListElement" itemscope="" itemtype="http://schema.org/ListItem">
12939 <a itemprop="item" class="footer-link " href="/serien/toradora-15561/staffel-1/">
12940 <span itemprop="name">Staffel 1</span>
12941 <svg class="footer-link__icon" aria-hidden="true"><use xlink:href="#wb-next"></use></svg>
12942 </a>
12943 <meta itemprop="position" content="4">
12944 </li>
12945 <li class="breadcrumb__item" itemprop="itemListElement" itemscope="" itemtype="http://schema.org/ListItem">
12946 <a itemprop="item" class="footer-link footer-link_active" href="/serien/toradora-15561/staffel-1/tiger-und-drache-387850.html">
12947 <span itemprop="name"><h1 class="footer-link__episode">Tiger und Drache</h1></span>
12948 </a>
12949 <meta itemprop="position" content="5">
12950 </li>
12951 </ul>
12952 <div class="footer-sitemap text_footer-sublink">
12953 <ul class="footer-sitemap__item-list">
12954 <li class="footer-sitemap__item">
12955 <span class="text_footer-link">Service</span>
12956 </li>
12957 <li class="footer-sitemap__item">
12958 <a class="footer-link" href="https://watchbox.zendesk.com" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'footer', 'hilfe', null, null, null, event);">
12959 Hilfe
12960 </a>
12961 </li>
12962 <li class="footer-sitemap__item">
12963 <a class="footer-link" href="https://watchbox.zendesk.com/hc/de/requests/new" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'footer', 'kontakt', null, null, null, event);">
12964 Kontakt
12965 </a>
12966 </li>
12967 </ul>
12968
12969 <ul class="footer-sitemap__item-list">
12970 <li class="footer-sitemap__item">
12971 <span class="text_footer-link">Über uns</span>
12972 </li>
12973 <li class="footer-sitemap__item">
12974 <a class="footer-link" href="/agb" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'footer', 'agb', null, null, null, event);" rel="nofollow">
12975 AGB
12976 </a>
12977 </li>
12978 <li class="footer-sitemap__item">
12979 <a class="footer-link" href="/datenschutzerklaerung" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'footer', 'datenschutz', null, null, null, event);" rel="nofollow">
12980 Datenschutz
12981 </a>
12982 </li>
12983 <li class="footer-sitemap__item">
12984 <a class="footer-link" href="/impressum" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'footer', 'impressum', null, null, null, event);" rel="nofollow">
12985 Impressum
12986 </a>
12987 </li>
12988 </ul>
12989
12990 <ul class="footer-sitemap__item-list">
12991 <li class="footer-sitemap__item">
12992 <span class="text_footer-link">Unsere Highlights</span>
12993 </li>
12994 <li class="footer-sitemap__item">
12995 <a class="footer-link" href="/genres/" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'footer', 'alle genres', null, null, null, event);">
12996 Alle Genres
12997 </a>
12998 </li>
12999 <li class="footer-sitemap__item">
13000 <a class="footer-link" href="/sammlungen/" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'footer', 'alle sammlungen', null, null, null, event);">
13001 Alle Sammlungen
13002 </a>
13003 </li>
13004 </ul>
13005
13006 <ul class="footer-sitemap__item-list">
13007 <li class="footer-sitemap__item">
13008 <span class="text_footer-link">Über Werbung</span>
13009 </li>
13010 <li class="footer-sitemap__item">
13011 <a class="footer-link" target="_blank" href="http://www.ip.de/loadfile.cfml?file=%3D9P%2EHPH_%23H8%2EOM%224V3AU%23NY%29%2ENLN%5CMX%5EVJT%2A%2FFYD%20%0A&type=application%2Fx-pdf&type=application/pdf" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'footer', 'werben auf watchbox', null, null, null, event);">Werben auf Watchbox</a>
13012 </li>
13013 <li class="footer-sitemap__item">
13014 <a class="footer-link" href="http://datenschutz.ip.de/nutzungsbasierte_onlinewerbung.cfm" onclick="tracking.tagCommanderTrackEvent('gaEvent', 'navigation', 'footer', 'nutzungsbasierte onlinewerbung', null, null, null, event);">
13015 Nutzungsbasierte Onlinewerbung
13016 </a>
13017 </li>
13018 </ul>
13019</div> </footer>
13020</div>
13021
13022<article class="js-show-on-search u-hidden" style="display: none;">
13023 <div class="search">
13024 <div class="page-wrapper search__wrapper">
13025 <form class="search__form js-search-form">
13026 <button type="reset" class="search__reset js-reset-search" aria-label="Suche zurücksetzen">
13027 <svg class="icon icon_search search__reset-icon"><use xlink:href="#wb-close"></use></svg>
13028 </button>
13029 <input type="text" class="form-field__input search__input js-search-input" placeholder="Film, Serie, Show">
13030 <div class="js-search-loading search__loading loading-slider">
13031 <div class="loading-slider__break loading-slider__break_dot1"></div>
13032 <div class="loading-slider__break loading-slider__break_dot2"></div>
13033 <div class="loading-slider__break loading-slider__break_dot3"></div>
13034 </div>
13035 </form>
13036 <div class="search__results">
13037 <div class="search__results-gradient"></div>
13038 <div class="grid js-search-result-grid">
13039
13040 </div>
13041 </div>
13042 </div>
13043 </div>
13044</article>
13045<div id="login-require-overlay" class="login-require-overlay js-login-require-overlay">
13046
13047 <div class="login-require-overlay__title">
13048 <div class="login-require-overlay__title__text text_flyout-link-large">Anmeldung benötigt</div>
13049 <button class="login-require-overlay__btn-close js-login-require-overlay-close">
13050 <svg class="icon" aria-hidden="true">
13051 <use xlink:href="#wb-close"></use>
13052 </svg>
13053 </button>
13054 </div>
13055
13056 <p class="text_paragraph">Melde dich an oder registriere dich, damit du dieses Funktion nutzen kannst.</p>
13057
13058
13059<button class="button login-require-overlay__login-button js-login-overlay-open" type="button"><div class="button-wrapper">
13060
13061
13062 <div class="button__text text_button-large-title">
13063 Anmelden </div>
13064
13065</div>
13066</button>
13067 <div class="separator"></div>
13068
13069 <div class="notlogin__register">
13070 <p class="text_paragraph">Bist du neu bei WATCHBOX? <br>
13071 <a href="/registrieren" class="link text_link">Dann registriere dich kostenlos HIER.</a>
13072 </p>
13073 </div>
13074</div>
13075<script type="text/javascript" src="/videoplayer/cbc-videoplayer-smartclip-5.5.2.min.js"></script>
13076<script type="text/javascript" src="/js/videoplayer-5.5.2.js"></script>
13077<script type="text/javascript" src="/js/app-5.5.2.js"></script>
13078
13079<script type="text/javascript">
13080 var continuousPlay = false;
13081 var playerConf = {
13082 source: {
13083 show: false,
13084 videoId: "387850",
13085 clipfishId: 0,
13086 title: 'Tiger\x20und\x20Drache',
13087 format: 'Toradora\x21\x20\x2D\x20Neue\x20Folgen',
13088 hls: 'https://vodwbusohls.secure.footprint.net/proxy/manifest-wb-clear/at-ch-de/387850-2-17421.ism/fairplay.m3u8',dash: 'https://vodwbusodash-a.akamaihd.net/proxy/manifest-wb-clear/at-ch-de/387850-2-17421.ism/.mpd',
13089 poster: '//aiswatchbox-a.akamaihd.net/watchbox/movie/387850/1920x1080/tiger-und-drache.jpg',
13090 length: 1443,
13091 pay: false,
13092 agof: 'dvrsowf_ten_wbtoradora',
13093 ivw: '\x2Fwatchbox\x2Fformate\x2Ftoradora\x2Fhome',
13094 },
13095 advertising: {
13096 homad: {
13097 show: true,
13098 clientConfig: '/homad-5.5.2.json'
13099 },
13100 adCall: {
13101 host: 'https://de-ipd.videoplaza.tv',
13102 category: 'rtl_watchbox/toradora',
13103 tags: ["vaa", "vpaid", "jgs=0"]
13104 },
13105 defaultMidrollOffsets: [600,1080] },
13106 playback: {
13107 autoplay: true },
13108 geoBlocking: {
13109 block: false },
13110 tracking: {
13111 videoservice: 'watchbox',
13112 heartbeat: {
13113 startType: 0 }
13114 }
13115 };
13116
13117 document.onreadystatechange = function() {
13118 var state = document.readyState;
13119 if (state === 'complete') {
13120 var videoplayer = window.WB.videoplayer();
13121 videoplayer.init();
13122
13123 videoplayer.playContent(playerConf, false);
13124
13125 var renderVideoBtns = document.getElementsByClassName('js-videoplayer-renderplayer');
13126 var i = 0;
13127 for (i = 0; i < renderVideoBtns.length; i++) {
13128 var ele = renderVideoBtns[i];
13129 ele.onclick = function(event) {
13130 var isBegin = this.className.match(/js-videoplayer-begin/);
13131 if (isBegin) {
13132 isBegin = isBegin.length > 0;
13133 } else {
13134 isBegin = false;
13135 }
13136 videoplayer.playContent(playerConf, isBegin);
13137 return false;
13138 }
13139 }
13140 }
13141 }
13142
13143</script>
13144
13145<script>window.twttr = (function (d, s, id) {
13146 var js, fjs = d.getElementsByTagName(s)[0],
13147 t = window.twttr || {};
13148 if (d.getElementById(id)) return t;
13149 js = d.createElement(s);
13150 js.id = id;
13151 js.src = "https://platform.twitter.com/widgets.js";
13152 fjs.parentNode.insertBefore(js, fjs);
13153
13154 t._e = [];
13155 t.ready = function (f) {
13156 t._e.push(f);
13157 };
13158
13159 return t;
13160 }(document, "script", "twitter-wjs"));</script>
13161
13162<script type="application/ld+json">{"@context":"http:\/\/schema.org","@type":"TVEpisode","name":"Tiger und Drache","url":"https:\/\/www.watchbox.de\/serien\/toradora-15561\/staffel-1\/tiger-und-drache-387850.html","description":"","episodeNumber":"1","releasedEvent":{"@type":"PublicationEvent","startDate":"2008-01-01","location":{"@type":"Country","name":"Japan"}},"image":{"@type":"ImageObject","url":"https:\/\/aiswatchbox-a.akamaihd.net\/watchbox\/format\/15561\/26-1\/767x400\/480\/toradora-neue-folgen.jpg"},"partOfSeries":{"@type":"TVSeries","name":"Toradora! - Neue Folgen","url":"https:\/\/www.watchbox.de\/serien\/toradora-15561\/"},"partOfSeason":{"@type":"TVSeason","seasonNumber":1},"potentialAction":{"@type":"WatchAction","target":{"@type":"EntryPoint","urlTemplate":"https:\/\/www.watchbox.de\/serien\/toradora-15561\/staffel-1\/tiger-und-drache-387850.html","inLanguage":"de","actionPlatform":["http:\/\/schema.org\/DesktopWebPlatform","http:\/\/schema.org\/MobileWebPlatform","http:\/\/schema.org\/IOSPlatform","http:\/\/schema.org\/AndroidPlatform"]},"expectsAcceptanceOf":{"@type":"Offer","category":"free","availabilityStarts":"2017-12-20 00:00:00","availabilityEnds":"2021-02-28 23:59:59","eligibleRegion":[{"@type":"Country","name":"AT"},{"@type":"Country","name":"CH"},{"@type":"Country","name":"DE"}]}},"actor":[{"@type":"Person","name":""}]}</script><div class="modal-background js-modal-background"></div>
13163
13164
13165<iframe scrolling="no" frameborder="0" allowtransparency="true" src="https://platform.twitter.com/widgets/widget_iframe.2e798283373a8137c24e277b9b9620d6.html?origin=https%3A%2F%2Fwww.watchbox.de" style="display: none;"></iframe><iframe id="rufous-sandbox" scrolling="no" frameborder="0" allowtransparency="true" allowfullscreen="true" style="position: absolute; visibility: hidden; display: none; width: 0px; height: 0px; padding: 0px; border: none;" title="Twitter analytics iframe"></iframe><img src="https://sync.search.spotxchange.com/partner?source=pub_106817" style="position: absolute; width: 1px; height: 1px; margin: 0px; padding: 0px; left: -999999px; top: -999999px; display: none; visibility: hidden;"><img src="https://ad.sxp.smartclip.net/sync?type=red&dsp=62" style="position: absolute; width: 1px; height: 1px; margin: 0px; padding: 0px; left: -999999px; top: -999999px; display: none; visibility: hidden;"><img src="https://ad.sxp.smartclip.net/sync?type=red&dsp=68" style="position: absolute; width: 1px; height: 1px; margin: 0px; padding: 0px; left: -999999px; top: -999999px; display: none; visibility: hidden;"><img src="https://c1.adform.net/serving/cookie/match?party=24&bidswitch_ssp_id=v1" style="position: absolute; width: 1px; height: 1px; margin: 0px; padding: 0px; left: -999999px; top: -999999px; display: none; visibility: hidden;"><img src="https://x.bidswitch.net/sync?dsp_id=70&user_id=42" style="position: absolute; width: 1px; height: 1px; margin: 0px; padding: 0px; left: -999999px; top: -999999px; display: none; visibility: hidden;"><img src="https://c1.adform.net/serving/cookie/match?party=30" style="position: absolute; width: 1px; height: 1px; margin: 0px; padding: 0px; left: -999999px; top: -999999px; display: none; visibility: hidden;"><div class="pub_300x250 pub_300x250m pub_728x90 text-ad textAd text_ad text_ads text-ads text-ad-links" style="width: 1px !important; height: 1px !important; position: absolute !important; left: -10000px !important; top: -1000px !important;"></div></body>
13166
13167</body>
13168</html>