wip
Browse files- css/chessboard-1.0.0.css +54 -0
- css/chessboard-1.0.0.min.css +2 -0
- ggml-tiny.en.bin +0 -3
- img/chesspieces/wikipedia/bB.png +0 -0
- img/chesspieces/wikipedia/bK.png +0 -0
- img/chesspieces/wikipedia/bN.png +0 -0
- img/chesspieces/wikipedia/bP.png +0 -0
- img/chesspieces/wikipedia/bQ.png +0 -0
- img/chesspieces/wikipedia/bR.png +0 -0
- img/chesspieces/wikipedia/wB.png +0 -0
- img/chesspieces/wikipedia/wK.png +0 -0
- img/chesspieces/wikipedia/wN.png +0 -0
- img/chesspieces/wikipedia/wP.png +0 -0
- img/chesspieces/wikipedia/wQ.png +0 -0
- img/chesspieces/wikipedia/wR.png +0 -0
- index.html +432 -877
- js/chess.js +0 -0
- js/chessboard-1.0.0.js +1817 -0
- js/chessboard-1.0.0.min.js +2 -0
- helpers.js → js/helpers.js +21 -9
- js/jquery-3.7.1.min.js +2 -0
- js/wchess.wasm.js +0 -0
- js/wchess.wasm.worker.js +1 -0
- libmain.worker.js +0 -1
- libwhisper.worker.js +0 -1
- models/.gitattributes +0 -51
- models/README.md +0 -24
- models/ggml-base.bin +0 -3
- models/ggml-base.en.bin +0 -3
- models/ggml-tiny.bin +0 -3
- models/ggml-tiny.en.bin +0 -3
css/chessboard-1.0.0.css
ADDED
@@ -0,0 +1,54 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
/*! chessboard.js v1.0.0 | (c) 2019 Chris Oakman | MIT License chessboardjs.com/license */
|
2 |
+
|
3 |
+
.clearfix-7da63 {
|
4 |
+
clear: both;
|
5 |
+
}
|
6 |
+
|
7 |
+
.board-b72b1 {
|
8 |
+
border: 2px solid #404040;
|
9 |
+
box-sizing: content-box;
|
10 |
+
}
|
11 |
+
|
12 |
+
.square-55d63 {
|
13 |
+
float: left;
|
14 |
+
position: relative;
|
15 |
+
|
16 |
+
/* disable any native browser highlighting */
|
17 |
+
-webkit-touch-callout: none;
|
18 |
+
-webkit-user-select: none;
|
19 |
+
-khtml-user-select: none;
|
20 |
+
-moz-user-select: none;
|
21 |
+
-ms-user-select: none;
|
22 |
+
user-select: none;
|
23 |
+
}
|
24 |
+
|
25 |
+
.white-1e1d7 {
|
26 |
+
background-color: #f0d9b5;
|
27 |
+
color: #b58863;
|
28 |
+
}
|
29 |
+
|
30 |
+
.black-3c85d {
|
31 |
+
background-color: #b58863;
|
32 |
+
color: #f0d9b5;
|
33 |
+
}
|
34 |
+
|
35 |
+
.highlight1-32417, .highlight2-9c5d2 {
|
36 |
+
box-shadow: inset 0 0 3px 3px yellow;
|
37 |
+
}
|
38 |
+
|
39 |
+
.notation-322f9 {
|
40 |
+
cursor: default;
|
41 |
+
font-family: "Helvetica Neue", Helvetica, Arial, sans-serif;
|
42 |
+
font-size: 14px;
|
43 |
+
position: absolute;
|
44 |
+
}
|
45 |
+
|
46 |
+
.alpha-d2270 {
|
47 |
+
bottom: 1px;
|
48 |
+
right: 3px;
|
49 |
+
}
|
50 |
+
|
51 |
+
.numeric-fc462 {
|
52 |
+
top: 2px;
|
53 |
+
left: 2px;
|
54 |
+
}
|
css/chessboard-1.0.0.min.css
ADDED
@@ -0,0 +1,2 @@
|
|
|
|
|
|
|
1 |
+
/*! chessboard.js v1.0.0 | (c) 2019 Chris Oakman | MIT License chessboardjs.com/license */
|
2 |
+
.clearfix-7da63{clear:both}.board-b72b1{border:2px solid #404040;box-sizing:content-box}.square-55d63{float:left;position:relative;-webkit-touch-callout:none;-webkit-user-select:none;-khtml-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none}.white-1e1d7{background-color:#f0d9b5;color:#b58863}.black-3c85d{background-color:#b58863;color:#f0d9b5}.highlight1-32417,.highlight2-9c5d2{box-shadow:inset 0 0 3px 3px #ff0}.notation-322f9{cursor:default;font-family:"Helvetica Neue",Helvetica,Arial,sans-serif;font-size:14px;position:absolute}.alpha-d2270{bottom:1px;right:3px}.numeric-fc462{top:2px;left:2px}
|
ggml-tiny.en.bin
DELETED
@@ -1,3 +0,0 @@
|
|
1 |
-
version https://git-lfs.github.com/spec/v1
|
2 |
-
oid sha256:921e4cf8686fdd993dcd081a5da5b6c365bfde1162e72b08d75ac75289920b1f
|
3 |
-
size 77704715
|
|
|
|
|
|
|
|
img/chesspieces/wikipedia/bB.png
ADDED
img/chesspieces/wikipedia/bK.png
ADDED
img/chesspieces/wikipedia/bN.png
ADDED
img/chesspieces/wikipedia/bP.png
ADDED
img/chesspieces/wikipedia/bQ.png
ADDED
img/chesspieces/wikipedia/bR.png
ADDED
img/chesspieces/wikipedia/wB.png
ADDED
img/chesspieces/wikipedia/wK.png
ADDED
img/chesspieces/wikipedia/wN.png
ADDED
img/chesspieces/wikipedia/wP.png
ADDED
img/chesspieces/wikipedia/wQ.png
ADDED
img/chesspieces/wikipedia/wR.png
ADDED
index.html
CHANGED
@@ -1,886 +1,441 @@
|
|
1 |
<!doctype html>
|
2 |
<html lang="en-us">
|
3 |
-
|
4 |
-
|
5 |
-
|
6 |
-
|
7 |
-
|
8 |
-
|
9 |
-
|
10 |
-
|
11 |
-
|
12 |
-
|
13 |
-
|
14 |
-
|
15 |
-
|
16 |
-
|
17 |
-
|
18 |
-
|
19 |
-
|
20 |
-
|
21 |
-
|
22 |
-
|
23 |
-
|
24 |
-
|
25 |
-
|
26 |
-
|
27 |
-
|
28 |
-
|
29 |
-
|
30 |
-
|
31 |
-
|
32 |
-
|
33 |
-
|
34 |
-
|
35 |
-
|
36 |
-
|
37 |
-
|
38 |
-
|
39 |
-
|
40 |
-
|
41 |
-
|
42 |
-
|
43 |
-
|
44 |
-
|
45 |
-
|
46 |
-
|
47 |
-
|
48 |
-
|
49 |
-
|
50 |
-
|
51 |
-
|
52 |
-
|
53 |
-
|
54 |
-
|
55 |
-
|
56 |
-
|
57 |
-
|
58 |
-
|
59 |
-
|
60 |
-
|
61 |
-
|
62 |
-
|
63 |
-
|
64 |
-
|
65 |
-
|
66 |
-
|
67 |
-
|
68 |
-
|
69 |
-
|
70 |
-
|
71 |
-
|
72 |
-
|
73 |
-
|
74 |
-
|
75 |
-
|
76 |
-
|
77 |
-
|
78 |
-
|
79 |
-
|
80 |
-
|
81 |
-
|
82 |
-
|
83 |
-
|
84 |
-
|
85 |
-
|
86 |
-
|
87 |
-
|
88 |
-
|
89 |
-
|
90 |
-
|
91 |
-
|
92 |
-
|
93 |
-
|
94 |
-
|
95 |
-
|
96 |
-
|
97 |
-
|
98 |
-
|
99 |
-
|
100 |
-
|
101 |
-
|
102 |
-
|
103 |
-
|
104 |
-
|
105 |
-
|
106 |
-
|
107 |
-
|
108 |
-
|
109 |
-
|
110 |
-
|
111 |
-
|
112 |
-
|
113 |
-
|
114 |
-
|
115 |
-
|
116 |
-
|
117 |
-
|
118 |
-
|
119 |
-
|
120 |
-
|
121 |
-
|
122 |
-
|
123 |
-
|
124 |
-
|
125 |
-
|
126 |
-
|
127 |
-
|
128 |
-
|
129 |
-
|
130 |
-
|
131 |
-
|
132 |
-
|
133 |
-
|
134 |
-
|
135 |
-
|
136 |
-
|
137 |
-
|
138 |
-
|
139 |
-
|
140 |
-
|
141 |
-
|
142 |
-
|
143 |
-
|
144 |
-
|
145 |
-
|
146 |
-
|
147 |
-
|
148 |
-
|
149 |
-
|
150 |
-
|
151 |
-
|
152 |
-
|
153 |
-
|
154 |
-
|
155 |
-
|
156 |
-
|
157 |
-
|
158 |
-
|
159 |
-
|
160 |
-
|
161 |
-
|
162 |
-
|
163 |
-
|
164 |
-
|
165 |
-
|
166 |
-
|
167 |
-
|
168 |
-
|
169 |
-
|
170 |
-
id="file"
|
171 |
-
name="input"
|
172 |
-
value="file"
|
173 |
-
checked="checked"
|
174 |
-
onchange="changeInput('file')"
|
175 |
-
/>
|
176 |
-
<label for="file">File</label>
|
177 |
-
<input
|
178 |
-
type="radio"
|
179 |
-
id="mic"
|
180 |
-
name="input"
|
181 |
-
value="mic"
|
182 |
-
onchange="changeInput('mic')"
|
183 |
-
/>
|
184 |
-
<label for="mic">Microphone</label>
|
185 |
-
</div>
|
186 |
-
|
187 |
-
<br />
|
188 |
-
|
189 |
-
<div id="input_file">
|
190 |
-
Audio file:
|
191 |
-
<input type="file" id="file" name="file" onchange="loadAudio(event)" />
|
192 |
-
</div>
|
193 |
-
|
194 |
-
<div id="input_mic" style="display: none">
|
195 |
-
Microphone:
|
196 |
-
<button id="start" onclick="startRecording()">Start</button>
|
197 |
-
<button id="stop" onclick="stopRecording()" disabled>Stop</button>
|
198 |
-
|
199 |
-
<!-- progress bar to show recording progress -->
|
200 |
-
<br /><br />
|
201 |
-
<div id="progress" style="display: none">
|
202 |
-
<div
|
203 |
-
id="progress-bar"
|
204 |
-
style="width: 0%; height: 10px; background-color: #4caf50"
|
205 |
-
></div>
|
206 |
-
<div id="progress-text">0%</div>
|
207 |
</div>
|
208 |
-
|
209 |
-
|
210 |
-
|
211 |
-
|
212 |
-
|
213 |
-
|
214 |
-
|
215 |
-
|
216 |
-
|
217 |
-
|
218 |
-
|
219 |
-
|
220 |
-
|
221 |
-
|
222 |
-
|
223 |
-
|
224 |
-
|
225 |
-
|
226 |
-
|
227 |
-
|
228 |
-
|
229 |
-
|
230 |
-
|
231 |
-
|
232 |
-
|
233 |
-
|
234 |
-
|
235 |
-
|
236 |
-
|
237 |
-
|
238 |
-
|
239 |
-
|
240 |
-
|
241 |
-
|
242 |
-
|
243 |
-
|
244 |
-
|
245 |
-
|
246 |
-
|
247 |
-
|
248 |
-
|
249 |
-
|
250 |
-
|
251 |
-
|
252 |
-
|
253 |
-
<option value="it">Italian</option>
|
254 |
-
<option value="ja">Japanese</option>
|
255 |
-
<option value="kn">Kannada</option>
|
256 |
-
<option value="ko">Korean</option>
|
257 |
-
<option value="la">Latin</option>
|
258 |
-
<option value="lv">Latvian</option>
|
259 |
-
<option value="lt">Lithuanian</option>
|
260 |
-
<option value="mk">Macedonian</option>
|
261 |
-
<option value="ms">Malay</option>
|
262 |
-
<option value="mt">Maltese</option>
|
263 |
-
<option value="no">Norwegian</option>
|
264 |
-
<option value="fa">Persian</option>
|
265 |
-
<option value="pl">Polish</option>
|
266 |
-
<option value="pt">Portuguese</option>
|
267 |
-
<option value="ro">Romanian</option>
|
268 |
-
<option value="ru">Russian</option>
|
269 |
-
<option value="sr">Serbian</option>
|
270 |
-
<option value="sk">Slovak</option>
|
271 |
-
<option value="sl">Slovenian</option>
|
272 |
-
<option value="es">Spanish</option>
|
273 |
-
<option value="sw">Swahili</option>
|
274 |
-
<option value="sv">Swedish</option>
|
275 |
-
<option value="ta">Tamil</option>
|
276 |
-
<option value="te">Telugu</option>
|
277 |
-
<option value="th">Thai</option>
|
278 |
-
<option value="tr">Turkish</option>
|
279 |
-
<option value="uk">Ukrainian</option>
|
280 |
-
<option value="ur">Urdu</option>
|
281 |
-
<option value="vi">Vietnamese</option>
|
282 |
-
<option value="cy">Welsh</option>
|
283 |
-
<option value="yi">Yiddish</option>
|
284 |
-
</select>
|
285 |
-
</td>
|
286 |
-
<!-- Slider to select number of threads between 1 and 16 -->
|
287 |
-
<td>
|
288 |
-
Threads:
|
289 |
-
<input
|
290 |
-
type="range"
|
291 |
-
id="threads"
|
292 |
-
name="threads"
|
293 |
-
min="1"
|
294 |
-
max="16"
|
295 |
-
value="8"
|
296 |
-
onchange="changeThreads(this.value)"
|
297 |
-
/>
|
298 |
-
<span id="threads-value">8</span>
|
299 |
-
</td>
|
300 |
-
<td>
|
301 |
-
<button onclick="onProcess(false);">Transcribe</button>
|
302 |
-
</td>
|
303 |
-
<td>
|
304 |
-
<button onclick="onProcess(true);">Translate</button>
|
305 |
-
</td>
|
306 |
-
</tr>
|
307 |
-
</table>
|
308 |
-
|
309 |
-
<br />
|
310 |
-
|
311 |
-
<!-- textarea with height filling the rest of the page -->
|
312 |
-
<textarea id="output" rows="20"></textarea>
|
313 |
-
|
314 |
-
<br /><br />
|
315 |
-
|
316 |
-
<div class="cell-version">
|
317 |
-
<span>
|
318 |
-
| Build time: <span class="nav-link">@GIT_DATE@</span> | Commit hash:
|
319 |
-
<a target="_blank"
|
320 |
-
class="nav-link"
|
321 |
-
href="https://github.com/ggerganov/whisper.cpp/commit/@GIT_SHA1@"
|
322 |
-
>@GIT_SHA1@</a
|
323 |
-
>
|
324 |
-
| Commit subject: <span class="nav-link">@GIT_COMMIT_SUBJECT@</span> |
|
325 |
-
<a target="_blank"
|
326 |
-
class="nav-link"
|
327 |
-
href="https://github.com/ggerganov/whisper.cpp/tree/master/examples/whisper.wasm"
|
328 |
-
>Source Code</a
|
329 |
-
>
|
330 |
-
|
|
331 |
-
</span>
|
332 |
-
</div>
|
333 |
-
</div>
|
334 |
-
|
335 |
-
<script type="text/javascript" src="helpers.js"></script>
|
336 |
-
<script type="text/javascript">
|
337 |
-
document.addEventListener("DOMContentLoaded", () => {
|
338 |
-
//check is shared array buffer is supported
|
339 |
-
if (!window.SharedArrayBuffer) {
|
340 |
-
document.querySelector("#warning").style.display = "block";
|
341 |
-
}
|
342 |
-
});
|
343 |
-
// TODO: convert audio buffer to WAV
|
344 |
-
function setAudio(audio) {
|
345 |
-
//if (audio) {
|
346 |
-
// // convert to 16-bit PCM
|
347 |
-
// var blob = new Blob([audio], { type: 'audio/wav' });
|
348 |
-
// var url = URL.createObjectURL(blob);
|
349 |
-
// document.getElementById('source').src = url;
|
350 |
-
// document.getElementById('audio').hidden = false;
|
351 |
-
// document.getElementById('audio').loop = false;
|
352 |
-
// document.getElementById('audio').load();
|
353 |
-
//} else {
|
354 |
-
// document.getElementById('audio').hidden = true;
|
355 |
-
//}
|
356 |
-
}
|
357 |
-
|
358 |
-
function changeInput(input) {
|
359 |
-
if (input == "file") {
|
360 |
-
document.getElementById("input_file").style.display = "block";
|
361 |
-
document.getElementById("input_mic").style.display = "none";
|
362 |
-
document.getElementById("progress").style.display = "none";
|
363 |
-
} else {
|
364 |
-
document.getElementById("input_file").style.display = "none";
|
365 |
-
document.getElementById("input_mic").style.display = "block";
|
366 |
-
document.getElementById("progress").style.display = "block";
|
367 |
-
}
|
368 |
-
}
|
369 |
-
|
370 |
-
var Module = {
|
371 |
-
print: printTextarea,
|
372 |
-
printErr: printTextarea,
|
373 |
-
setStatus: function (text) {
|
374 |
-
printTextarea("js: " + text);
|
375 |
-
},
|
376 |
-
monitorRunDependencies: function (left) {},
|
377 |
-
};
|
378 |
-
|
379 |
-
// web audio context
|
380 |
-
var context = null;
|
381 |
-
|
382 |
-
// audio data
|
383 |
-
var audio = null;
|
384 |
-
|
385 |
-
// the whisper instance
|
386 |
-
var instance = null;
|
387 |
-
var model_whisper = "";
|
388 |
-
|
389 |
-
// helper function
|
390 |
-
function convertTypedArray(src, type) {
|
391 |
-
var buffer = new ArrayBuffer(src.byteLength);
|
392 |
-
var baseView = new src.constructor(buffer).set(src);
|
393 |
-
return new type(buffer);
|
394 |
-
}
|
395 |
-
|
396 |
-
//
|
397 |
-
// load model
|
398 |
-
//
|
399 |
-
|
400 |
-
let dbVersion = 1;
|
401 |
-
let dbName = "whisper.ggerganov.com";
|
402 |
-
let indexedDB =
|
403 |
-
window.indexedDB ||
|
404 |
-
window.mozIndexedDB ||
|
405 |
-
window.webkitIndexedDB ||
|
406 |
-
window.msIndexedDB;
|
407 |
-
|
408 |
-
function storeFS(fname, buf) {
|
409 |
-
// write to WASM file using FS_createDataFile
|
410 |
-
// if the file exists, delete it
|
411 |
-
try {
|
412 |
-
Module.FS_unlink(fname);
|
413 |
-
} catch (e) {
|
414 |
-
// ignore
|
415 |
-
}
|
416 |
-
|
417 |
-
Module.FS_createDataFile("/", fname, buf, true, true);
|
418 |
-
|
419 |
-
//model_whisper = fname;
|
420 |
-
|
421 |
-
document.getElementById("model-whisper-status").innerHTML =
|
422 |
-
'loaded "' + model_whisper + '"!';
|
423 |
-
|
424 |
-
printTextarea(
|
425 |
-
"storeFS: stored model: " + fname + " size: " + buf.length
|
426 |
-
);
|
427 |
-
|
428 |
-
document.getElementById("model").innerHTML =
|
429 |
-
"Model fetched: " + model_whisper;
|
430 |
-
}
|
431 |
-
|
432 |
-
function loadFile(event, fname) {
|
433 |
-
var file = event.target.files[0] || null;
|
434 |
-
if (file == null) {
|
435 |
-
return;
|
436 |
-
}
|
437 |
-
|
438 |
-
printTextarea(
|
439 |
-
"loadFile: loading model: " +
|
440 |
-
file.name +
|
441 |
-
", size: " +
|
442 |
-
file.size +
|
443 |
-
" bytes"
|
444 |
-
);
|
445 |
-
printTextarea("loadFile: please wait ...");
|
446 |
-
|
447 |
-
var reader = new FileReader();
|
448 |
-
reader.onload = function (event) {
|
449 |
-
var buf = new Uint8Array(reader.result);
|
450 |
-
storeFS(fname, buf);
|
451 |
-
};
|
452 |
-
reader.readAsArrayBuffer(file);
|
453 |
-
|
454 |
-
document.getElementById("fetch-whisper-tiny-en").style.display = "none";
|
455 |
-
document.getElementById("fetch-whisper-base-en").style.display = "none";
|
456 |
-
document.getElementById("fetch-whisper-small-en").style.display =
|
457 |
-
"none";
|
458 |
-
document.getElementById("fetch-whisper-tiny").style.display = "none";
|
459 |
-
document.getElementById("fetch-whisper-base").style.display = "none";
|
460 |
-
document.getElementById("fetch-whisper-small").style.display = "none";
|
461 |
-
|
462 |
-
document.getElementById("fetch-whisper-tiny-en-q5_1").style.display =
|
463 |
-
"none";
|
464 |
-
document.getElementById("fetch-whisper-tiny-q5_1").style.display =
|
465 |
-
"none";
|
466 |
-
document.getElementById("fetch-whisper-base-en-q5_1").style.display =
|
467 |
-
"none";
|
468 |
-
document.getElementById("fetch-whisper-base-q5_1").style.display =
|
469 |
-
"none";
|
470 |
-
document.getElementById("fetch-whisper-small-en-q5_1").style.display =
|
471 |
-
"none";
|
472 |
-
document.getElementById("fetch-whisper-small-q5_1").style.display =
|
473 |
-
"none";
|
474 |
-
document.getElementById("fetch-whisper-medium-en-q5_0").style.display =
|
475 |
-
"none";
|
476 |
-
document.getElementById("fetch-whisper-medium-q5_0").style.display =
|
477 |
-
"none";
|
478 |
-
document.getElementById("fetch-whisper-large-q5_0").style.display =
|
479 |
-
"none";
|
480 |
-
|
481 |
-
document.getElementById("whisper-file").style.display = "none";
|
482 |
-
document.getElementById("model-whisper-status").innerHTML =
|
483 |
-
"loaded model: " + file.name;
|
484 |
-
}
|
485 |
-
|
486 |
-
function loadWhisper(model) {
|
487 |
-
const baseURL =
|
488 |
-
"https://huggingface.co/ggerganov/whisper.cpp/resolve/main";
|
489 |
-
let urls = {
|
490 |
-
"tiny.en": `${baseURL}/ggml-tiny.en.bin`,
|
491 |
-
tiny: `${baseURL}/ggml-tiny.bin`,
|
492 |
-
"base.en": `${baseURL}/ggml-base.en.bin`,
|
493 |
-
base: `${baseURL}/ggml-base.bin`,
|
494 |
-
"small.en": `${baseURL}/ggml-small.en.bin`,
|
495 |
-
small: `${baseURL}/ggml-small.bin`,
|
496 |
-
|
497 |
-
"tiny-en-q5_1": `${baseURL}/ggml-model-whisper-tiny.en-q5_1.bin`,
|
498 |
-
"tiny-q5_1": `${baseURL}/ggml-model-whisper-tiny-q5_1.bin`,
|
499 |
-
"base-en-q5_1": `${baseURL}/ggml-model-whisper-base.en-q5_1.bin`,
|
500 |
-
"base-q5_1": `${baseURL}/ggml-model-whisper-base-q5_1.bin`,
|
501 |
-
"small-en-q5_1": `${baseURL}/ggml-model-whisper-small.en-q5_1.bin`,
|
502 |
-
"small-q5_1": `${baseURL}/ggml-model-whisper-small-q5_1.bin`,
|
503 |
-
"medium-en-q5_0": `${baseURL}/ggml-model-whisper-medium.en-q5_0.bin`,
|
504 |
-
"medium-q5_0": `${baseURL}/ggml-model-whisper-medium-q5_0.bin`,
|
505 |
-
"large-q5_0": `${baseURL}/ggml-model-whisper-large-q5_0.bin`,
|
506 |
-
};
|
507 |
-
|
508 |
-
let sizes = {
|
509 |
-
"tiny.en": 75,
|
510 |
-
tiny: 75,
|
511 |
-
"base.en": 142,
|
512 |
-
base: 142,
|
513 |
-
"small.en": 466,
|
514 |
-
small: 466,
|
515 |
-
|
516 |
-
"tiny-en-q5_1": 31,
|
517 |
-
"tiny-q5_1": 31,
|
518 |
-
"base-en-q5_1": 57,
|
519 |
-
"base-q5_1": 57,
|
520 |
-
"small-en-q5_1": 182,
|
521 |
-
"small-q5_1": 182,
|
522 |
-
"medium-en-q5_0": 515,
|
523 |
-
"medium-q5_0": 515,
|
524 |
-
"large-q5_0": 1030,
|
525 |
-
};
|
526 |
-
|
527 |
-
let url = urls[model];
|
528 |
-
let dst = "whisper.bin";
|
529 |
-
let size_mb = sizes[model];
|
530 |
-
|
531 |
-
model_whisper = model;
|
532 |
-
|
533 |
-
document.getElementById("fetch-whisper-tiny-en").style.display = "none";
|
534 |
-
document.getElementById("fetch-whisper-base-en").style.display = "none";
|
535 |
-
document.getElementById("fetch-whisper-small-en").style.display =
|
536 |
-
"none";
|
537 |
-
document.getElementById("fetch-whisper-tiny").style.display = "none";
|
538 |
-
document.getElementById("fetch-whisper-base").style.display = "none";
|
539 |
-
document.getElementById("fetch-whisper-small").style.display = "none";
|
540 |
-
|
541 |
-
document.getElementById("fetch-whisper-tiny-en-q5_1").style.display =
|
542 |
-
"none";
|
543 |
-
document.getElementById("fetch-whisper-tiny-q5_1").style.display =
|
544 |
-
"none";
|
545 |
-
document.getElementById("fetch-whisper-base-en-q5_1").style.display =
|
546 |
-
"none";
|
547 |
-
document.getElementById("fetch-whisper-base-q5_1").style.display =
|
548 |
-
"none";
|
549 |
-
document.getElementById("fetch-whisper-small-en-q5_1").style.display =
|
550 |
-
"none";
|
551 |
-
document.getElementById("fetch-whisper-small-q5_1").style.display =
|
552 |
-
"none";
|
553 |
-
document.getElementById("fetch-whisper-medium-en-q5_0").style.display =
|
554 |
-
"none";
|
555 |
-
document.getElementById("fetch-whisper-medium-q5_0").style.display =
|
556 |
-
"none";
|
557 |
-
document.getElementById("fetch-whisper-large-q5_0").style.display =
|
558 |
-
"none";
|
559 |
-
|
560 |
-
document.getElementById("whisper-file").style.display = "none";
|
561 |
-
document.getElementById("model-whisper-status").innerHTML =
|
562 |
-
"loading model: " + model;
|
563 |
-
|
564 |
-
cbProgress = function (p) {
|
565 |
-
let el = document.getElementById("fetch-whisper-progress");
|
566 |
-
el.innerHTML = Math.round(100 * p) + "%";
|
567 |
-
};
|
568 |
-
|
569 |
-
cbCancel = function () {
|
570 |
-
var el;
|
571 |
-
|
572 |
-
el = document.getElementById("fetch-whisper-tiny-en");
|
573 |
-
if (el) el.style.display = "inline-block";
|
574 |
-
el = document.getElementById("fetch-whisper-base-en");
|
575 |
-
if (el) el.style.display = "inline-block";
|
576 |
-
el = document.getElementById("fetch-whisper-small-en");
|
577 |
-
if (el) el.style.display = "inline-block";
|
578 |
-
el = document.getElementById("fetch-whisper-tiny");
|
579 |
-
if (el) el.style.display = "inline-block";
|
580 |
-
el = document.getElementById("fetch-whisper-base");
|
581 |
-
if (el) el.style.display = "inline-block";
|
582 |
-
el = document.getElementById("fetch-whisper-small");
|
583 |
-
if (el) el.style.display = "inline-block";
|
584 |
-
|
585 |
-
el = document.getElementById("fetch-whisper-tiny-en-q5_1");
|
586 |
-
if (el) el.style.display = "inline-block";
|
587 |
-
el = document.getElementById("fetch-whisper-tiny-q5_1");
|
588 |
-
if (el) el.style.display = "inline-block";
|
589 |
-
el = document.getElementById("fetch-whisper-base-en-q5_1");
|
590 |
-
if (el) el.style.display = "inline-block";
|
591 |
-
el = document.getElementById("fetch-whisper-base-q5_1");
|
592 |
-
if (el) el.style.display = "inline-block";
|
593 |
-
el = document.getElementById("fetch-whisper-small-en-q5_1");
|
594 |
-
if (el) el.style.display = "inline-block";
|
595 |
-
el = document.getElementById("fetch-whisper-small-q5_1");
|
596 |
-
if (el) el.style.display = "inline-block";
|
597 |
-
el = document.getElementById("fetch-whisper-medium-en-q5_0");
|
598 |
-
if (el) el.style.display = "inline-block";
|
599 |
-
el = document.getElementById("fetch-whisper-medium-q5_0");
|
600 |
-
if (el) el.style.display = "inline-block";
|
601 |
-
el = document.getElementById("fetch-whisper-large-q5_0");
|
602 |
-
if (el) el.style.display = "inline-block";
|
603 |
-
|
604 |
-
el = document.getElementById("whisper-file");
|
605 |
-
if (el) el.style.display = "inline-block";
|
606 |
-
el = document.getElementById("model-whisper-status");
|
607 |
-
if (el) el.innerHTML = "";
|
608 |
-
};
|
609 |
-
|
610 |
-
loadRemote(
|
611 |
-
url,
|
612 |
-
dst,
|
613 |
-
size_mb,
|
614 |
-
cbProgress,
|
615 |
-
storeFS,
|
616 |
-
cbCancel,
|
617 |
-
printTextarea
|
618 |
-
);
|
619 |
-
}
|
620 |
-
|
621 |
-
//
|
622 |
-
// audio file
|
623 |
-
//
|
624 |
-
|
625 |
-
const kMaxAudio_s = 30 * 60;
|
626 |
-
const kMaxRecording_s = 2 * 60;
|
627 |
-
const kSampleRate = 16000;
|
628 |
-
|
629 |
-
window.AudioContext = window.AudioContext || window.webkitAudioContext;
|
630 |
-
window.OfflineAudioContext =
|
631 |
-
window.OfflineAudioContext || window.webkitOfflineAudioContext;
|
632 |
-
|
633 |
-
function loadAudio(event) {
|
634 |
-
if (!context) {
|
635 |
-
context = new AudioContext({
|
636 |
-
sampleRate: kSampleRate,
|
637 |
-
channelCount: 1,
|
638 |
-
echoCancellation: false,
|
639 |
-
autoGainControl: true,
|
640 |
-
noiseSuppression: true,
|
641 |
-
});
|
642 |
-
}
|
643 |
-
|
644 |
-
var file = event.target.files[0] || null;
|
645 |
-
if (file == null) {
|
646 |
-
return;
|
647 |
-
}
|
648 |
-
|
649 |
-
printTextarea(
|
650 |
-
"js: loading audio: " + file.name + ", size: " + file.size + " bytes"
|
651 |
-
);
|
652 |
-
printTextarea("js: please wait ...");
|
653 |
-
|
654 |
-
var reader = new FileReader();
|
655 |
-
reader.onload = function (event) {
|
656 |
-
var buf = new Uint8Array(reader.result);
|
657 |
-
|
658 |
-
context.decodeAudioData(
|
659 |
-
buf.buffer,
|
660 |
-
function (audioBuffer) {
|
661 |
-
var offlineContext = new OfflineAudioContext(
|
662 |
-
audioBuffer.numberOfChannels,
|
663 |
-
audioBuffer.length,
|
664 |
-
audioBuffer.sampleRate
|
665 |
-
);
|
666 |
-
var source = offlineContext.createBufferSource();
|
667 |
-
source.buffer = audioBuffer;
|
668 |
-
source.connect(offlineContext.destination);
|
669 |
-
source.start(0);
|
670 |
-
|
671 |
-
offlineContext.startRendering().then(function (renderedBuffer) {
|
672 |
-
audio = renderedBuffer.getChannelData(0);
|
673 |
-
printTextarea("js: audio loaded, size: " + audio.length);
|
674 |
-
|
675 |
-
// truncate to first 30 seconds
|
676 |
-
if (audio.length > kMaxAudio_s * kSampleRate) {
|
677 |
-
audio = audio.slice(0, kMaxAudio_s * kSampleRate);
|
678 |
-
printTextarea(
|
679 |
-
"js: truncated audio to first " + kMaxAudio_s + " seconds"
|
680 |
-
);
|
681 |
}
|
|
|
682 |
|
683 |
-
|
684 |
-
|
685 |
-
},
|
686 |
-
function (e) {
|
687 |
-
printTextarea("js: error decoding audio: " + e);
|
688 |
-
audio = null;
|
689 |
-
setAudio(audio);
|
690 |
}
|
691 |
-
|
692 |
-
|
693 |
-
|
694 |
-
|
695 |
-
|
696 |
-
|
697 |
-
|
698 |
-
|
699 |
-
|
700 |
-
|
701 |
-
|
702 |
-
|
703 |
-
|
704 |
-
|
705 |
-
|
706 |
-
|
707 |
-
|
708 |
-
|
709 |
-
|
710 |
-
|
711 |
-
|
712 |
-
|
713 |
-
|
714 |
-
|
715 |
-
|
716 |
-
|
717 |
-
|
718 |
-
|
719 |
-
|
720 |
-
|
721 |
-
|
722 |
-
|
723 |
-
|
724 |
-
|
725 |
-
|
726 |
-
|
727 |
-
|
728 |
-
|
729 |
-
|
730 |
-
|
731 |
-
|
732 |
-
|
733 |
-
|
734 |
-
|
735 |
-
|
736 |
-
|
737 |
-
|
738 |
-
|
739 |
-
|
740 |
-
|
741 |
-
}
|
742 |
-
|
743 |
-
|
744 |
-
|
745 |
-
|
746 |
-
|
747 |
-
|
748 |
-
|
749 |
-
|
750 |
-
|
751 |
-
|
752 |
-
|
753 |
-
|
754 |
-
|
755 |
-
|
756 |
-
|
757 |
-
|
758 |
-
|
759 |
-
|
760 |
-
|
761 |
-
|
762 |
-
|
763 |
-
|
764 |
-
|
765 |
-
|
766 |
-
|
767 |
-
|
768 |
-
|
769 |
-
|
770 |
-
|
771 |
-
|
772 |
-
|
773 |
-
|
774 |
-
|
775 |
-
|
776 |
-
|
777 |
-
|
778 |
-
|
779 |
-
|
780 |
-
|
781 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
782 |
}
|
783 |
-
|
784 |
-
|
785 |
-
|
786 |
-
|
787 |
-
|
788 |
-
|
789 |
-
|
790 |
-
|
791 |
-
);
|
792 |
-
};
|
793 |
-
|
794 |
-
reader.readAsArrayBuffer(blob);
|
795 |
-
};
|
796 |
-
mediaRecorder.start();
|
797 |
-
})
|
798 |
-
.catch(function (err) {
|
799 |
-
printTextarea("js: error getting audio stream: " + err);
|
800 |
-
});
|
801 |
-
|
802 |
-
var interval = setInterval(function () {
|
803 |
-
if (!doRecording) {
|
804 |
-
clearInterval(interval);
|
805 |
-
mediaRecorder.stop();
|
806 |
-
stream.getTracks().forEach(function (track) {
|
807 |
-
track.stop();
|
808 |
-
});
|
809 |
-
}
|
810 |
-
|
811 |
-
document.getElementById("progress-bar").style.width =
|
812 |
-
(100 * (Date.now() - startTime)) / 1000 / kMaxRecording_s + "%";
|
813 |
-
document.getElementById("progress-text").innerHTML =
|
814 |
-
((100 * (Date.now() - startTime)) / 1000 / kMaxRecording_s).toFixed(
|
815 |
-
0
|
816 |
-
) + "%";
|
817 |
-
}, 1000);
|
818 |
-
|
819 |
-
printTextarea("js: recording ...");
|
820 |
-
|
821 |
-
setTimeout(function () {
|
822 |
-
if (doRecording) {
|
823 |
-
printTextarea(
|
824 |
-
"js: recording stopped after " + kMaxRecording_s + " seconds"
|
825 |
-
);
|
826 |
-
stopRecording();
|
827 |
-
}
|
828 |
-
}, kMaxRecording_s * 1000);
|
829 |
-
}
|
830 |
-
|
831 |
-
//
|
832 |
-
// transcribe
|
833 |
-
//
|
834 |
-
|
835 |
-
var nthreads = 8;
|
836 |
-
|
837 |
-
function changeThreads(value) {
|
838 |
-
nthreads = value;
|
839 |
-
document.getElementById("threads-value").innerHTML = nthreads;
|
840 |
-
}
|
841 |
-
|
842 |
-
function onProcess(translate) {
|
843 |
-
if (!instance) {
|
844 |
-
instance = Module.init("whisper.bin");
|
845 |
-
|
846 |
-
if (instance) {
|
847 |
-
printTextarea("js: whisper initialized, instance: " + instance);
|
848 |
-
document.getElementById("model").innerHTML =
|
849 |
-
"Model loaded: " + model_whisper;
|
850 |
-
}
|
851 |
-
}
|
852 |
-
|
853 |
-
if (!instance) {
|
854 |
-
printTextarea("js: failed to initialize whisper");
|
855 |
-
return;
|
856 |
-
}
|
857 |
-
|
858 |
-
if (!audio) {
|
859 |
-
printTextarea("js: no audio data");
|
860 |
-
return;
|
861 |
-
}
|
862 |
-
|
863 |
-
if (instance) {
|
864 |
-
printTextarea("");
|
865 |
-
printTextarea("js: processing - this might take a while ...");
|
866 |
-
printTextarea("");
|
867 |
-
|
868 |
-
setTimeout(function () {
|
869 |
-
var ret = Module.full_default(
|
870 |
-
instance,
|
871 |
-
audio,
|
872 |
-
document.getElementById("language").value,
|
873 |
-
nthreads,
|
874 |
-
translate
|
875 |
-
);
|
876 |
-
console.log("js: full_default returned: " + ret);
|
877 |
-
if (ret) {
|
878 |
-
printTextarea("js: whisper returned: " + ret);
|
879 |
}
|
880 |
-
|
881 |
-
|
882 |
-
|
883 |
-
</
|
884 |
-
<script type="text/javascript" src="main.js"></script>
|
885 |
-
</body>
|
886 |
</html>
|
|
|
1 |
<!doctype html>
|
2 |
<html lang="en-us">
|
3 |
+
<head>
|
4 |
+
<title>wchess : voice-controlled chess using Whisper + WebAssembly</title>
|
5 |
+
<script src="https://cdnjs.cloudflare.com/ajax/libs/iframe-resizer/4.3.1/iframeResizer.contentWindow.min.js"></script>
|
6 |
+
|
7 |
+
<meta name="viewport" content="width=device-width, initial-scale=0.4, maximum-scale=1, minimum-scale=1, user-scalable=no"/>
|
8 |
+
<meta name="apple-mobile-web-app-capable" content="yes" />
|
9 |
+
|
10 |
+
<style>
|
11 |
+
#output {
|
12 |
+
width: 100%;
|
13 |
+
height: 100%;
|
14 |
+
margin: 0 auto;
|
15 |
+
margin-top: 10px;
|
16 |
+
border-left: 0px;
|
17 |
+
border-right: 0px;
|
18 |
+
padding-left: 0px;
|
19 |
+
padding-right: 0px;
|
20 |
+
display: block;
|
21 |
+
background-color: black;
|
22 |
+
color: white;
|
23 |
+
font-size: 10px;
|
24 |
+
font-family: 'Lucida Console', Monaco, monospace;
|
25 |
+
outline: none;
|
26 |
+
white-space: pre;
|
27 |
+
overflow-wrap: normal;
|
28 |
+
overflow-x: scroll;
|
29 |
+
}
|
30 |
+
.button {
|
31 |
+
background-color: #000000;
|
32 |
+
color: #FFFFFF;
|
33 |
+
padding: 20px;
|
34 |
+
border-radius: 10px;
|
35 |
+
-moz-border-radius: 10px;
|
36 |
+
-webkit-border-radius: 10px;
|
37 |
+
margin:10px;
|
38 |
+
width: 100px;
|
39 |
+
height: 50px;
|
40 |
+
-webkit-touch-callout: none; /* Safari */
|
41 |
+
-webkit-user-select: none; /* Chrome */
|
42 |
+
-moz-user-select: none; /* Firefox */
|
43 |
+
-ms-user-select: none; /* Internet Explorer/Edge */
|
44 |
+
user-select: none;
|
45 |
+
}
|
46 |
+
.center {
|
47 |
+
display: flex;
|
48 |
+
justify-content: center;
|
49 |
+
align-items: center;
|
50 |
+
width: 300px;
|
51 |
+
}
|
52 |
+
</style>
|
53 |
+
<link rel="stylesheet" href="css/chessboard-1.0.0.min.css" integrity="sha384-q94+BZtLrkL1/ohfjR8c6L+A6qzNH9R2hBLwyoAfu3i/WCvQjzL2RQJ3uNHDISdU" crossorigin="anonymous">
|
54 |
+
</head>
|
55 |
+
<body onload="loadWhisper()">
|
56 |
+
<div id="main-container">
|
57 |
+
<b>wchess : voice-controlled chess using Whisper + WebAssembly</b>
|
58 |
+
|
59 |
+
<br><br>
|
60 |
+
|
61 |
+
This is a demonstration of using Whisper to recognize voice commands in the browser.
|
62 |
+
|
63 |
+
<br><br>
|
64 |
+
|
65 |
+
Usage:<br>
|
66 |
+
|
67 |
+
<ul>
|
68 |
+
<li>Hold the button and say a chess move (e.g. "e2-e4")</li>
|
69 |
+
<li>Release the button and wait for the move to be recognized</li>
|
70 |
+
<li>Repeat</li>
|
71 |
+
</ul>
|
72 |
+
|
73 |
+
Examples:<br>
|
74 |
+
|
75 |
+
<ul>
|
76 |
+
<li><b>"d4"</b></li>
|
77 |
+
<li><b>"e2 e4"</b></li>
|
78 |
+
<li><b>"Knight to f3"</b></li>
|
79 |
+
<li><b>"Bishop to b5"</b></li>
|
80 |
+
</ul>
|
81 |
+
|
82 |
+
Note that not all chess moves are supported. For example, castling and pawn promotion<br>
|
83 |
+
currently do not work, but can be easily implemented. The main purpose of this example<br>
|
84 |
+
is to demonstrate the capabilities of Whisper and it's application in the browser.
|
85 |
+
|
86 |
+
<br><br>
|
87 |
+
|
88 |
+
Features:<br>
|
89 |
+
|
90 |
+
<ul>
|
91 |
+
<li>Model quantization for reduced memory footprint (~42MB)</li>
|
92 |
+
<li><a href="https://github.com/ggerganov/whisper.cpp/pull/1229">Grammar-based sampling</a> for improved recognition accuracy</li>
|
93 |
+
</ul>
|
94 |
+
|
95 |
+
You can find more about this project on <a href="https://github.com/ggerganov/whisper.cpp/tree/master/examples/wchess">GitHub</a>.
|
96 |
+
|
97 |
+
<br><br>
|
98 |
+
|
99 |
+
<b>More examples:</b>
|
100 |
+
<a href="https://whisper.ggerganov.com/">main</a> |
|
101 |
+
<a href="https://whisper.ggerganov.com/bench">bench</a> |
|
102 |
+
<a href="https://whisper.ggerganov.com/stream">stream</a> |
|
103 |
+
<a href="https://whisper.ggerganov.com/command">command</a> |
|
104 |
+
<a href="https://whisper.ggerganov.com/talk">talk</a> |
|
105 |
+
|
106 |
+
<br><br>
|
107 |
+
|
108 |
+
<hr>
|
109 |
+
|
110 |
+
<div id="model-whisper">
|
111 |
+
Whisper model: <span id="model-whisper-status"></span>
|
112 |
+
<span id="fetch-whisper-progress"></span>
|
113 |
+
<br><br>
|
114 |
+
<button id="clear" onclick="clearCache()">Clear Cache</button>
|
115 |
+
<!--
|
116 |
+
<input type="file" id="file" name="file" onchange="loadFile(event, 'whisper.bin')" />
|
117 |
+
-->
|
118 |
+
</div>
|
119 |
+
|
120 |
+
<br>
|
121 |
+
<div id="chessboard" style="width: 300px"></div>
|
122 |
+
<script src="js/jquery-3.7.1.min.js"></script>
|
123 |
+
<script src="js/chessboard-1.0.0.min.js"></script>
|
124 |
+
<script>
|
125 |
+
var board = Chessboard('chessboard', 'start')
|
126 |
+
var move_count = 0;
|
127 |
+
</script>
|
128 |
+
|
129 |
+
<br>
|
130 |
+
|
131 |
+
<div id="input" class="center">
|
132 |
+
<button id="toggler" class="button" onselectstart="return false" disabled>Hold</button>
|
133 |
+
</div>
|
134 |
+
|
135 |
+
<br>
|
136 |
+
|
137 |
+
<div id="state">
|
138 |
+
Status: <b><span id="state-status">not started</span></b>
|
139 |
+
|
140 |
+
<pre id="state-moves">[The moves will be displayed here]</pre>
|
141 |
+
</div>
|
142 |
+
|
143 |
+
<hr>
|
144 |
+
|
145 |
+
Debug output:
|
146 |
+
<textarea id="output" rows="20"></textarea>
|
147 |
+
|
148 |
+
<br>
|
149 |
+
|
150 |
+
<b>Troubleshooting</b>
|
151 |
+
|
152 |
+
<br><br>
|
153 |
+
|
154 |
+
The page does some heavy computations, so make sure:
|
155 |
+
|
156 |
+
<ul>
|
157 |
+
<li>To use a modern web browser (e.g. Chrome, Firefox)</li>
|
158 |
+
<li>Your browser supports WASM <a href="https://webassembly.org/roadmap/">Fixed-width SIMD</a></li>
|
159 |
+
</ul>
|
160 |
+
|
161 |
+
<div class="cell-version">
|
162 |
+
<span>
|
163 |
+
|
|
164 |
+
Build time: <span class="nav-link">Fri Dec 8 10:03:41 2023</span> |
|
165 |
+
Commit hash: <a class="nav-link" href="https://github.com/ggerganov/whisper.cpp/commit/be5cd736">be5cd736</a> |
|
166 |
+
Commit subject: <span class="nav-link">wchess: touchstart, touchend events</span> |
|
167 |
+
<a class="nav-link" href="https://github.com/ggerganov/whisper.cpp/tree/master/examples/command.wasm">Source Code</a> |
|
168 |
+
</span>
|
169 |
+
</div>
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
170 |
</div>
|
171 |
+
|
172 |
+
<script type="text/javascript" src="js/helpers.js"></script>
|
173 |
+
<script type='text/javascript'>
|
174 |
+
// web audio context
|
175 |
+
var context = null;
|
176 |
+
|
177 |
+
// the command instance
|
178 |
+
var instance = null;
|
179 |
+
|
180 |
+
// model name
|
181 |
+
var model_whisper = null;
|
182 |
+
var model_file = null;
|
183 |
+
|
184 |
+
var module_ready = null;
|
185 |
+
|
186 |
+
var Module = {
|
187 |
+
print: printTextarea,
|
188 |
+
printErr: printTextarea,
|
189 |
+
setStatus: function(text) {
|
190 |
+
printTextarea('js: ' + text);
|
191 |
+
},
|
192 |
+
monitorRunDependencies: function(left) {
|
193 |
+
},
|
194 |
+
preRun: function() {
|
195 |
+
printTextarea('js: Preparing ...');
|
196 |
+
},
|
197 |
+
postRun: function() {
|
198 |
+
printTextarea('js: Module initialized successfully!');
|
199 |
+
module_ready = true;
|
200 |
+
initInstance();
|
201 |
+
}
|
202 |
+
};
|
203 |
+
|
204 |
+
function initInstance() {
|
205 |
+
if (!module_ready || !model_file || instance) return
|
206 |
+
|
207 |
+
instance = Module.init(model_file);
|
208 |
+
|
209 |
+
if (instance) {
|
210 |
+
document.getElementById('toggler').disabled = false;
|
211 |
+
setStatus('Ready');
|
212 |
+
printTextarea("js: whisper initialized, instance: " + instance);
|
213 |
+
}
|
214 |
+
else {
|
215 |
+
printTextarea("js: failed to initialize whisper");
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
216 |
}
|
217 |
+
}
|
218 |
|
219 |
+
function setStatus(text) {
|
220 |
+
document.getElementById('state-status').innerHTML = text;
|
|
|
|
|
|
|
|
|
|
|
221 |
}
|
222 |
+
|
223 |
+
//
|
224 |
+
// fetch models
|
225 |
+
//
|
226 |
+
|
227 |
+
let dbVersion = 1
|
228 |
+
let dbName = 'whisper.ggerganov.com';
|
229 |
+
let indexedDB = window.indexedDB || window.mozIndexedDB || window.webkitIndexedDB || window.msIndexedDB
|
230 |
+
|
231 |
+
function storeFS(fname, buf) {
|
232 |
+
// write to WASM file using FS_createDataFile
|
233 |
+
// if the file exists, delete it
|
234 |
+
try {
|
235 |
+
Module.FS_unlink(fname);
|
236 |
+
} catch (e) {
|
237 |
+
// ignore
|
238 |
+
}
|
239 |
+
|
240 |
+
Module.FS_createDataFile("/", fname, buf, true, true);
|
241 |
+
|
242 |
+
printTextarea('storeFS: stored model: ' + fname + ' size: ' + buf.length);
|
243 |
+
|
244 |
+
document.getElementById('model-whisper-status').innerHTML = 'loaded "' + model_whisper + '"!';
|
245 |
+
|
246 |
+
model_file = fname;
|
247 |
+
initInstance();
|
248 |
+
}
|
249 |
+
|
250 |
+
function loadWhisper() {
|
251 |
+
setStatus('Loading')
|
252 |
+
//let url = 'https://whisper.ggerganov.com/ggml-model-whisper-tiny.en-q8_0.bin';
|
253 |
+
let url = 'https://huggingface.co/ggerganov/whisper.cpp/resolve/main/ggml-tiny.en-q8_0.bin';
|
254 |
+
let dst = 'whisper.bin';
|
255 |
+
let size_mb = 42;
|
256 |
+
|
257 |
+
model_whisper = 'tiny.en-q8_0';
|
258 |
+
|
259 |
+
document.getElementById('model-whisper-status').innerHTML = 'loading "' + model_whisper + '" ... ';
|
260 |
+
|
261 |
+
cbProgress = function(p) {
|
262 |
+
let el = document.getElementById('fetch-whisper-progress');
|
263 |
+
el.innerHTML = Math.round(100*p) + '%';
|
264 |
+
};
|
265 |
+
|
266 |
+
cbCancel = function() {
|
267 |
+
var el;
|
268 |
+
el = document.getElementById('model-whisper-status'); if (el) el.innerHTML = '';
|
269 |
+
};
|
270 |
+
|
271 |
+
loadRemote(url, dst, size_mb, cbProgress, storeFS, cbCancel, printTextarea);
|
272 |
+
}
|
273 |
+
|
274 |
+
//
|
275 |
+
// microphone
|
276 |
+
//
|
277 |
+
|
278 |
+
const kSampleRate = 16000;
|
279 |
+
const kRestartRecording_s = 120;
|
280 |
+
const kIntervalAudio_ms = 250; // pass the recorded audio to the C++ instance at this rate
|
281 |
+
|
282 |
+
var mediaRecorder = null;
|
283 |
+
var doRecording = false;
|
284 |
+
var startTime = 0;
|
285 |
+
|
286 |
+
window.AudioContext = window.AudioContext || window.webkitAudioContext;
|
287 |
+
window.OfflineAudioContext = window.OfflineAudioContext || window.webkitOfflineAudioContext;
|
288 |
+
|
289 |
+
function stopRecording() {
|
290 |
+
mediaRecorder.stop();
|
291 |
+
}
|
292 |
+
|
293 |
+
function startRecording() {
|
294 |
+
if (!context) {
|
295 |
+
context = new AudioContext({
|
296 |
+
sampleRate: kSampleRate,
|
297 |
+
channelCount: 1,
|
298 |
+
echoCancellation: false,
|
299 |
+
autoGainControl: true,
|
300 |
+
noiseSuppression: true,
|
301 |
+
});
|
302 |
+
}
|
303 |
+
|
304 |
+
startTime = Date.now();
|
305 |
+
|
306 |
+
var chunks = [];
|
307 |
+
var stream = null;
|
308 |
+
|
309 |
+
navigator.mediaDevices.getUserMedia({audio: true, video: false})
|
310 |
+
.then(function(s) {
|
311 |
+
stream = s;
|
312 |
+
mediaRecorder = new MediaRecorder(stream);
|
313 |
+
mediaRecorder.ondataavailable = function(e) {
|
314 |
+
chunks.push(e.data);
|
315 |
+
|
316 |
+
var blob = new Blob(chunks, { 'type' : 'audio/ogg; codecs=opus' });
|
317 |
+
var reader = new FileReader();
|
318 |
+
|
319 |
+
reader.onload = function(event) {
|
320 |
+
var buf = new Uint8Array(reader.result);
|
321 |
+
context.decodeAudioData(buf.buffer, function(audioBuffer) {
|
322 |
+
var offlineContext = new OfflineAudioContext(audioBuffer.numberOfChannels, audioBuffer.length, audioBuffer.sampleRate);
|
323 |
+
var source = offlineContext.createBufferSource();
|
324 |
+
source.buffer = audioBuffer;
|
325 |
+
source.connect(offlineContext.destination);
|
326 |
+
source.start(0);
|
327 |
+
|
328 |
+
offlineContext.startRendering().then(function(renderedBuffer) {
|
329 |
+
let audio = renderedBuffer.getChannelData(0);
|
330 |
+
printTextarea('js: number of samples: ' + audio.length);
|
331 |
+
Module.set_audio(instance, audio);
|
332 |
+
});
|
333 |
+
|
334 |
+
mediaRecorder = null;
|
335 |
+
context = null;
|
336 |
+
});
|
337 |
+
}
|
338 |
+
|
339 |
+
reader.readAsArrayBuffer(blob);
|
340 |
+
};
|
341 |
+
|
342 |
+
mediaRecorder.onstop = function(e) {
|
343 |
+
stream.getTracks().forEach(function(track) {
|
344 |
+
track.stop();
|
345 |
+
});
|
346 |
+
};
|
347 |
+
|
348 |
+
mediaRecorder.start();
|
349 |
+
})
|
350 |
+
.catch(function(err) {
|
351 |
+
printTextarea('js: error getting audio stream: ' + err);
|
352 |
+
});
|
353 |
+
}
|
354 |
+
|
355 |
+
//
|
356 |
+
// main
|
357 |
+
//
|
358 |
+
|
359 |
+
var nLines = 0;
|
360 |
+
var movesAll = '';
|
361 |
+
|
362 |
+
// document.body.addEventListener('keydown', function(event) {
|
363 |
+
// if (event.keyCode === 32) {
|
364 |
+
// document.getElementById('toggler').innerText = "";
|
365 |
+
// onStart();
|
366 |
+
// }
|
367 |
+
// }, true);
|
368 |
+
|
369 |
+
// document.body.addEventListener('keyup', function(event) {
|
370 |
+
// if (event.keyCode === 32) {
|
371 |
+
// document.getElementById('toggler').innerText = "Hold";
|
372 |
+
// onStop();
|
373 |
+
// }
|
374 |
+
// }, true);
|
375 |
+
|
376 |
+
document.getElementById('toggler').addEventListener("touchstart", function(event){
|
377 |
+
this.innerText = "";
|
378 |
+
onStart();
|
379 |
+
}, true);
|
380 |
+
|
381 |
+
document.getElementById('toggler').addEventListener("touchend", function(event){
|
382 |
+
this.innerText = "Hold";
|
383 |
+
onStop();
|
384 |
+
}, true)
|
385 |
+
|
386 |
+
document.getElementById('toggler').addEventListener('mousedown', function(event) {
|
387 |
+
this.innerText = "";
|
388 |
+
onStart();
|
389 |
+
}, true);
|
390 |
+
|
391 |
+
document.getElementById('toggler').addEventListener('mouseup', function(event) {
|
392 |
+
this.innerText = "Hold";
|
393 |
+
onStop();
|
394 |
+
}, true);
|
395 |
+
|
396 |
+
function onStart() {
|
397 |
+
if (!instance) return;
|
398 |
+
setStatus('Listening');
|
399 |
+
|
400 |
+
startRecording();
|
401 |
+
}
|
402 |
+
|
403 |
+
function onStop() {
|
404 |
+
setStatus('Processing');
|
405 |
+
printTextarea('js: stopping recording ...');
|
406 |
+
stopRecording();
|
407 |
+
}
|
408 |
+
|
409 |
+
function setMove(move, prob) {
|
410 |
+
if (move != null && move.length > 1) {
|
411 |
+
let gameOver = move[move.length - 1] === '#';
|
412 |
+
if (gameOver) {
|
413 |
+
move = move.substring(0, move.length - 1);
|
414 |
+
document.getElementById('toggler').disabled = true;
|
415 |
+
}
|
416 |
+
board.move(move);
|
417 |
+
|
418 |
+
movesAll += move + ', prob = ' + prob.toFixed(2) + '% <br>';
|
419 |
+
nLines++;
|
420 |
+
|
421 |
+
// if more than 10 lines, remove the first line
|
422 |
+
if (nLines > 10) {
|
423 |
+
var i = movesAll.indexOf('<br>');
|
424 |
+
if (i > 0) {
|
425 |
+
movesAll = movesAll.substring(i + 4);
|
426 |
+
nLines--;
|
427 |
}
|
428 |
+
}
|
429 |
+
++move_count;
|
430 |
+
setStatus(gameOver ? 'Done' : move_count % 2 ? 'Black\'s turn' : 'White\'s turn');
|
431 |
+
document.getElementById('state-moves').innerHTML = movesAll;
|
432 |
+
}
|
433 |
+
else {
|
434 |
+
setStatus('Failed. ' + (move_count % 2 ? 'Black\'s turn' : 'White\'s turn'));
|
435 |
+
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
436 |
}
|
437 |
+
|
438 |
+
</script>
|
439 |
+
<script type="text/javascript" src="js/chess.js"></script>
|
440 |
+
</body>
|
|
|
|
|
441 |
</html>
|
js/chess.js
ADDED
The diff for this file is too large to render.
See raw diff
|
|
js/chessboard-1.0.0.js
ADDED
@@ -0,0 +1,1817 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
// chessboard.js v1.0.0
|
2 |
+
// https://github.com/oakmac/chessboardjs/
|
3 |
+
//
|
4 |
+
// Copyright (c) 2019, Chris Oakman
|
5 |
+
// Released under the MIT license
|
6 |
+
// https://github.com/oakmac/chessboardjs/blob/master/LICENSE.md
|
7 |
+
|
8 |
+
// start anonymous scope
|
9 |
+
;(function () {
|
10 |
+
'use strict'
|
11 |
+
|
12 |
+
var $ = window['jQuery']
|
13 |
+
|
14 |
+
// ---------------------------------------------------------------------------
|
15 |
+
// Constants
|
16 |
+
// ---------------------------------------------------------------------------
|
17 |
+
|
18 |
+
var COLUMNS = 'abcdefgh'.split('')
|
19 |
+
var DEFAULT_DRAG_THROTTLE_RATE = 20
|
20 |
+
var ELLIPSIS = '…'
|
21 |
+
var MINIMUM_JQUERY_VERSION = '1.8.3'
|
22 |
+
var RUN_ASSERTS = false
|
23 |
+
var START_FEN = 'rnbqkbnr/pppppppp/8/8/8/8/PPPPPPPP/RNBQKBNR'
|
24 |
+
var START_POSITION = fenToObj(START_FEN)
|
25 |
+
|
26 |
+
// default animation speeds
|
27 |
+
var DEFAULT_APPEAR_SPEED = 200
|
28 |
+
var DEFAULT_MOVE_SPEED = 200
|
29 |
+
var DEFAULT_SNAPBACK_SPEED = 60
|
30 |
+
var DEFAULT_SNAP_SPEED = 30
|
31 |
+
var DEFAULT_TRASH_SPEED = 100
|
32 |
+
|
33 |
+
// use unique class names to prevent clashing with anything else on the page
|
34 |
+
// and simplify selectors
|
35 |
+
// NOTE: these should never change
|
36 |
+
var CSS = {}
|
37 |
+
CSS['alpha'] = 'alpha-d2270'
|
38 |
+
CSS['black'] = 'black-3c85d'
|
39 |
+
CSS['board'] = 'board-b72b1'
|
40 |
+
CSS['chessboard'] = 'chessboard-63f37'
|
41 |
+
CSS['clearfix'] = 'clearfix-7da63'
|
42 |
+
CSS['highlight1'] = 'highlight1-32417'
|
43 |
+
CSS['highlight2'] = 'highlight2-9c5d2'
|
44 |
+
CSS['notation'] = 'notation-322f9'
|
45 |
+
CSS['numeric'] = 'numeric-fc462'
|
46 |
+
CSS['piece'] = 'piece-417db'
|
47 |
+
CSS['row'] = 'row-5277c'
|
48 |
+
CSS['sparePieces'] = 'spare-pieces-7492f'
|
49 |
+
CSS['sparePiecesBottom'] = 'spare-pieces-bottom-ae20f'
|
50 |
+
CSS['sparePiecesTop'] = 'spare-pieces-top-4028b'
|
51 |
+
CSS['square'] = 'square-55d63'
|
52 |
+
CSS['white'] = 'white-1e1d7'
|
53 |
+
|
54 |
+
// ---------------------------------------------------------------------------
|
55 |
+
// Misc Util Functions
|
56 |
+
// ---------------------------------------------------------------------------
|
57 |
+
|
58 |
+
function throttle (f, interval, scope) {
|
59 |
+
var timeout = 0
|
60 |
+
var shouldFire = false
|
61 |
+
var args = []
|
62 |
+
|
63 |
+
var handleTimeout = function () {
|
64 |
+
timeout = 0
|
65 |
+
if (shouldFire) {
|
66 |
+
shouldFire = false
|
67 |
+
fire()
|
68 |
+
}
|
69 |
+
}
|
70 |
+
|
71 |
+
var fire = function () {
|
72 |
+
timeout = window.setTimeout(handleTimeout, interval)
|
73 |
+
f.apply(scope, args)
|
74 |
+
}
|
75 |
+
|
76 |
+
return function (_args) {
|
77 |
+
args = arguments
|
78 |
+
if (!timeout) {
|
79 |
+
fire()
|
80 |
+
} else {
|
81 |
+
shouldFire = true
|
82 |
+
}
|
83 |
+
}
|
84 |
+
}
|
85 |
+
|
86 |
+
// function debounce (f, interval, scope) {
|
87 |
+
// var timeout = 0
|
88 |
+
// return function (_args) {
|
89 |
+
// window.clearTimeout(timeout)
|
90 |
+
// var args = arguments
|
91 |
+
// timeout = window.setTimeout(function () {
|
92 |
+
// f.apply(scope, args)
|
93 |
+
// }, interval)
|
94 |
+
// }
|
95 |
+
// }
|
96 |
+
|
97 |
+
function uuid () {
|
98 |
+
return 'xxxx-xxxx-xxxx-xxxx-xxxx-xxxx-xxxx-xxxx'.replace(/x/g, function (c) {
|
99 |
+
var r = (Math.random() * 16) | 0
|
100 |
+
return r.toString(16)
|
101 |
+
})
|
102 |
+
}
|
103 |
+
|
104 |
+
function deepCopy (thing) {
|
105 |
+
return JSON.parse(JSON.stringify(thing))
|
106 |
+
}
|
107 |
+
|
108 |
+
function parseSemVer (version) {
|
109 |
+
var tmp = version.split('.')
|
110 |
+
return {
|
111 |
+
major: parseInt(tmp[0], 10),
|
112 |
+
minor: parseInt(tmp[1], 10),
|
113 |
+
patch: parseInt(tmp[2], 10)
|
114 |
+
}
|
115 |
+
}
|
116 |
+
|
117 |
+
// returns true if version is >= minimum
|
118 |
+
function validSemanticVersion (version, minimum) {
|
119 |
+
version = parseSemVer(version)
|
120 |
+
minimum = parseSemVer(minimum)
|
121 |
+
|
122 |
+
var versionNum = (version.major * 100000 * 100000) +
|
123 |
+
(version.minor * 100000) +
|
124 |
+
version.patch
|
125 |
+
var minimumNum = (minimum.major * 100000 * 100000) +
|
126 |
+
(minimum.minor * 100000) +
|
127 |
+
minimum.patch
|
128 |
+
|
129 |
+
return versionNum >= minimumNum
|
130 |
+
}
|
131 |
+
|
132 |
+
function interpolateTemplate (str, obj) {
|
133 |
+
for (var key in obj) {
|
134 |
+
if (!obj.hasOwnProperty(key)) continue
|
135 |
+
var keyTemplateStr = '{' + key + '}'
|
136 |
+
var value = obj[key]
|
137 |
+
while (str.indexOf(keyTemplateStr) !== -1) {
|
138 |
+
str = str.replace(keyTemplateStr, value)
|
139 |
+
}
|
140 |
+
}
|
141 |
+
return str
|
142 |
+
}
|
143 |
+
|
144 |
+
if (RUN_ASSERTS) {
|
145 |
+
console.assert(interpolateTemplate('abc', {a: 'x'}) === 'abc')
|
146 |
+
console.assert(interpolateTemplate('{a}bc', {}) === '{a}bc')
|
147 |
+
console.assert(interpolateTemplate('{a}bc', {p: 'q'}) === '{a}bc')
|
148 |
+
console.assert(interpolateTemplate('{a}bc', {a: 'x'}) === 'xbc')
|
149 |
+
console.assert(interpolateTemplate('{a}bc{a}bc', {a: 'x'}) === 'xbcxbc')
|
150 |
+
console.assert(interpolateTemplate('{a}{a}{b}', {a: 'x', b: 'y'}) === 'xxy')
|
151 |
+
}
|
152 |
+
|
153 |
+
// ---------------------------------------------------------------------------
|
154 |
+
// Predicates
|
155 |
+
// ---------------------------------------------------------------------------
|
156 |
+
|
157 |
+
function isString (s) {
|
158 |
+
return typeof s === 'string'
|
159 |
+
}
|
160 |
+
|
161 |
+
function isFunction (f) {
|
162 |
+
return typeof f === 'function'
|
163 |
+
}
|
164 |
+
|
165 |
+
function isInteger (n) {
|
166 |
+
return typeof n === 'number' &&
|
167 |
+
isFinite(n) &&
|
168 |
+
Math.floor(n) === n
|
169 |
+
}
|
170 |
+
|
171 |
+
function validAnimationSpeed (speed) {
|
172 |
+
if (speed === 'fast' || speed === 'slow') return true
|
173 |
+
if (!isInteger(speed)) return false
|
174 |
+
return speed >= 0
|
175 |
+
}
|
176 |
+
|
177 |
+
function validThrottleRate (rate) {
|
178 |
+
return isInteger(rate) &&
|
179 |
+
rate >= 1
|
180 |
+
}
|
181 |
+
|
182 |
+
function validMove (move) {
|
183 |
+
// move should be a string
|
184 |
+
if (!isString(move)) return false
|
185 |
+
|
186 |
+
// move should be in the form of "e2-e4", "f6-d5"
|
187 |
+
var squares = move.split('-')
|
188 |
+
if (squares.length !== 2) return false
|
189 |
+
|
190 |
+
return validSquare(squares[0]) && validSquare(squares[1])
|
191 |
+
}
|
192 |
+
|
193 |
+
function validSquare (square) {
|
194 |
+
return isString(square) && square.search(/^[a-h][1-8]$/) !== -1
|
195 |
+
}
|
196 |
+
|
197 |
+
if (RUN_ASSERTS) {
|
198 |
+
console.assert(validSquare('a1'))
|
199 |
+
console.assert(validSquare('e2'))
|
200 |
+
console.assert(!validSquare('D2'))
|
201 |
+
console.assert(!validSquare('g9'))
|
202 |
+
console.assert(!validSquare('a'))
|
203 |
+
console.assert(!validSquare(true))
|
204 |
+
console.assert(!validSquare(null))
|
205 |
+
console.assert(!validSquare({}))
|
206 |
+
}
|
207 |
+
|
208 |
+
function validPieceCode (code) {
|
209 |
+
return isString(code) && code.search(/^[bw][KQRNBP]$/) !== -1
|
210 |
+
}
|
211 |
+
|
212 |
+
if (RUN_ASSERTS) {
|
213 |
+
console.assert(validPieceCode('bP'))
|
214 |
+
console.assert(validPieceCode('bK'))
|
215 |
+
console.assert(validPieceCode('wK'))
|
216 |
+
console.assert(validPieceCode('wR'))
|
217 |
+
console.assert(!validPieceCode('WR'))
|
218 |
+
console.assert(!validPieceCode('Wr'))
|
219 |
+
console.assert(!validPieceCode('a'))
|
220 |
+
console.assert(!validPieceCode(true))
|
221 |
+
console.assert(!validPieceCode(null))
|
222 |
+
console.assert(!validPieceCode({}))
|
223 |
+
}
|
224 |
+
|
225 |
+
function validFen (fen) {
|
226 |
+
if (!isString(fen)) return false
|
227 |
+
|
228 |
+
// cut off any move, castling, etc info from the end
|
229 |
+
// we're only interested in position information
|
230 |
+
fen = fen.replace(/ .+$/, '')
|
231 |
+
|
232 |
+
// expand the empty square numbers to just 1s
|
233 |
+
fen = expandFenEmptySquares(fen)
|
234 |
+
|
235 |
+
// FEN should be 8 sections separated by slashes
|
236 |
+
var chunks = fen.split('/')
|
237 |
+
if (chunks.length !== 8) return false
|
238 |
+
|
239 |
+
// check each section
|
240 |
+
for (var i = 0; i < 8; i++) {
|
241 |
+
if (chunks[i].length !== 8 ||
|
242 |
+
chunks[i].search(/[^kqrnbpKQRNBP1]/) !== -1) {
|
243 |
+
return false
|
244 |
+
}
|
245 |
+
}
|
246 |
+
|
247 |
+
return true
|
248 |
+
}
|
249 |
+
|
250 |
+
if (RUN_ASSERTS) {
|
251 |
+
console.assert(validFen(START_FEN))
|
252 |
+
console.assert(validFen('8/8/8/8/8/8/8/8'))
|
253 |
+
console.assert(validFen('r1bqkbnr/pppp1ppp/2n5/1B2p3/4P3/5N2/PPPP1PPP/RNBQK2R'))
|
254 |
+
console.assert(validFen('3r3r/1p4pp/2nb1k2/pP3p2/8/PB2PN2/p4PPP/R4RK1 b - - 0 1'))
|
255 |
+
console.assert(!validFen('3r3z/1p4pp/2nb1k2/pP3p2/8/PB2PN2/p4PPP/R4RK1 b - - 0 1'))
|
256 |
+
console.assert(!validFen('anbqkbnr/8/8/8/8/8/PPPPPPPP/8'))
|
257 |
+
console.assert(!validFen('rnbqkbnr/pppppppp/8/8/8/8/PPPPPPPP/'))
|
258 |
+
console.assert(!validFen('rnbqkbnr/pppppppp/8/8/8/8/PPPPPPPP/RNBQKBN'))
|
259 |
+
console.assert(!validFen('888888/pppppppp/8/8/8/8/PPPPPPPP/RNBQKBNR'))
|
260 |
+
console.assert(!validFen('888888/pppppppp/74/8/8/8/PPPPPPPP/RNBQKBNR'))
|
261 |
+
console.assert(!validFen({}))
|
262 |
+
}
|
263 |
+
|
264 |
+
function validPositionObject (pos) {
|
265 |
+
if (!$.isPlainObject(pos)) return false
|
266 |
+
|
267 |
+
for (var i in pos) {
|
268 |
+
if (!pos.hasOwnProperty(i)) continue
|
269 |
+
|
270 |
+
if (!validSquare(i) || !validPieceCode(pos[i])) {
|
271 |
+
return false
|
272 |
+
}
|
273 |
+
}
|
274 |
+
|
275 |
+
return true
|
276 |
+
}
|
277 |
+
|
278 |
+
if (RUN_ASSERTS) {
|
279 |
+
console.assert(validPositionObject(START_POSITION))
|
280 |
+
console.assert(validPositionObject({}))
|
281 |
+
console.assert(validPositionObject({e2: 'wP'}))
|
282 |
+
console.assert(validPositionObject({e2: 'wP', d2: 'wP'}))
|
283 |
+
console.assert(!validPositionObject({e2: 'BP'}))
|
284 |
+
console.assert(!validPositionObject({y2: 'wP'}))
|
285 |
+
console.assert(!validPositionObject(null))
|
286 |
+
console.assert(!validPositionObject('start'))
|
287 |
+
console.assert(!validPositionObject(START_FEN))
|
288 |
+
}
|
289 |
+
|
290 |
+
function isTouchDevice () {
|
291 |
+
return 'ontouchstart' in document.documentElement
|
292 |
+
}
|
293 |
+
|
294 |
+
function validJQueryVersion () {
|
295 |
+
return typeof window.$ &&
|
296 |
+
$.fn &&
|
297 |
+
$.fn.jquery &&
|
298 |
+
validSemanticVersion($.fn.jquery, MINIMUM_JQUERY_VERSION)
|
299 |
+
}
|
300 |
+
|
301 |
+
// ---------------------------------------------------------------------------
|
302 |
+
// Chess Util Functions
|
303 |
+
// ---------------------------------------------------------------------------
|
304 |
+
|
305 |
+
// convert FEN piece code to bP, wK, etc
|
306 |
+
function fenToPieceCode (piece) {
|
307 |
+
// black piece
|
308 |
+
if (piece.toLowerCase() === piece) {
|
309 |
+
return 'b' + piece.toUpperCase()
|
310 |
+
}
|
311 |
+
|
312 |
+
// white piece
|
313 |
+
return 'w' + piece.toUpperCase()
|
314 |
+
}
|
315 |
+
|
316 |
+
// convert bP, wK, etc code to FEN structure
|
317 |
+
function pieceCodeToFen (piece) {
|
318 |
+
var pieceCodeLetters = piece.split('')
|
319 |
+
|
320 |
+
// white piece
|
321 |
+
if (pieceCodeLetters[0] === 'w') {
|
322 |
+
return pieceCodeLetters[1].toUpperCase()
|
323 |
+
}
|
324 |
+
|
325 |
+
// black piece
|
326 |
+
return pieceCodeLetters[1].toLowerCase()
|
327 |
+
}
|
328 |
+
|
329 |
+
// convert FEN string to position object
|
330 |
+
// returns false if the FEN string is invalid
|
331 |
+
function fenToObj (fen) {
|
332 |
+
if (!validFen(fen)) return false
|
333 |
+
|
334 |
+
// cut off any move, castling, etc info from the end
|
335 |
+
// we're only interested in position information
|
336 |
+
fen = fen.replace(/ .+$/, '')
|
337 |
+
|
338 |
+
var rows = fen.split('/')
|
339 |
+
var position = {}
|
340 |
+
|
341 |
+
var currentRow = 8
|
342 |
+
for (var i = 0; i < 8; i++) {
|
343 |
+
var row = rows[i].split('')
|
344 |
+
var colIdx = 0
|
345 |
+
|
346 |
+
// loop through each character in the FEN section
|
347 |
+
for (var j = 0; j < row.length; j++) {
|
348 |
+
// number / empty squares
|
349 |
+
if (row[j].search(/[1-8]/) !== -1) {
|
350 |
+
var numEmptySquares = parseInt(row[j], 10)
|
351 |
+
colIdx = colIdx + numEmptySquares
|
352 |
+
} else {
|
353 |
+
// piece
|
354 |
+
var square = COLUMNS[colIdx] + currentRow
|
355 |
+
position[square] = fenToPieceCode(row[j])
|
356 |
+
colIdx = colIdx + 1
|
357 |
+
}
|
358 |
+
}
|
359 |
+
|
360 |
+
currentRow = currentRow - 1
|
361 |
+
}
|
362 |
+
|
363 |
+
return position
|
364 |
+
}
|
365 |
+
|
366 |
+
// position object to FEN string
|
367 |
+
// returns false if the obj is not a valid position object
|
368 |
+
function objToFen (obj) {
|
369 |
+
if (!validPositionObject(obj)) return false
|
370 |
+
|
371 |
+
var fen = ''
|
372 |
+
|
373 |
+
var currentRow = 8
|
374 |
+
for (var i = 0; i < 8; i++) {
|
375 |
+
for (var j = 0; j < 8; j++) {
|
376 |
+
var square = COLUMNS[j] + currentRow
|
377 |
+
|
378 |
+
// piece exists
|
379 |
+
if (obj.hasOwnProperty(square)) {
|
380 |
+
fen = fen + pieceCodeToFen(obj[square])
|
381 |
+
} else {
|
382 |
+
// empty space
|
383 |
+
fen = fen + '1'
|
384 |
+
}
|
385 |
+
}
|
386 |
+
|
387 |
+
if (i !== 7) {
|
388 |
+
fen = fen + '/'
|
389 |
+
}
|
390 |
+
|
391 |
+
currentRow = currentRow - 1
|
392 |
+
}
|
393 |
+
|
394 |
+
// squeeze the empty numbers together
|
395 |
+
fen = squeezeFenEmptySquares(fen)
|
396 |
+
|
397 |
+
return fen
|
398 |
+
}
|
399 |
+
|
400 |
+
if (RUN_ASSERTS) {
|
401 |
+
console.assert(objToFen(START_POSITION) === START_FEN)
|
402 |
+
console.assert(objToFen({}) === '8/8/8/8/8/8/8/8')
|
403 |
+
console.assert(objToFen({a2: 'wP', 'b2': 'bP'}) === '8/8/8/8/8/8/Pp6/8')
|
404 |
+
}
|
405 |
+
|
406 |
+
function squeezeFenEmptySquares (fen) {
|
407 |
+
return fen.replace(/11111111/g, '8')
|
408 |
+
.replace(/1111111/g, '7')
|
409 |
+
.replace(/111111/g, '6')
|
410 |
+
.replace(/11111/g, '5')
|
411 |
+
.replace(/1111/g, '4')
|
412 |
+
.replace(/111/g, '3')
|
413 |
+
.replace(/11/g, '2')
|
414 |
+
}
|
415 |
+
|
416 |
+
function expandFenEmptySquares (fen) {
|
417 |
+
return fen.replace(/8/g, '11111111')
|
418 |
+
.replace(/7/g, '1111111')
|
419 |
+
.replace(/6/g, '111111')
|
420 |
+
.replace(/5/g, '11111')
|
421 |
+
.replace(/4/g, '1111')
|
422 |
+
.replace(/3/g, '111')
|
423 |
+
.replace(/2/g, '11')
|
424 |
+
}
|
425 |
+
|
426 |
+
// returns the distance between two squares
|
427 |
+
function squareDistance (squareA, squareB) {
|
428 |
+
var squareAArray = squareA.split('')
|
429 |
+
var squareAx = COLUMNS.indexOf(squareAArray[0]) + 1
|
430 |
+
var squareAy = parseInt(squareAArray[1], 10)
|
431 |
+
|
432 |
+
var squareBArray = squareB.split('')
|
433 |
+
var squareBx = COLUMNS.indexOf(squareBArray[0]) + 1
|
434 |
+
var squareBy = parseInt(squareBArray[1], 10)
|
435 |
+
|
436 |
+
var xDelta = Math.abs(squareAx - squareBx)
|
437 |
+
var yDelta = Math.abs(squareAy - squareBy)
|
438 |
+
|
439 |
+
if (xDelta >= yDelta) return xDelta
|
440 |
+
return yDelta
|
441 |
+
}
|
442 |
+
|
443 |
+
// returns the square of the closest instance of piece
|
444 |
+
// returns false if no instance of piece is found in position
|
445 |
+
function findClosestPiece (position, piece, square) {
|
446 |
+
// create array of closest squares from square
|
447 |
+
var closestSquares = createRadius(square)
|
448 |
+
|
449 |
+
// search through the position in order of distance for the piece
|
450 |
+
for (var i = 0; i < closestSquares.length; i++) {
|
451 |
+
var s = closestSquares[i]
|
452 |
+
|
453 |
+
if (position.hasOwnProperty(s) && position[s] === piece) {
|
454 |
+
return s
|
455 |
+
}
|
456 |
+
}
|
457 |
+
|
458 |
+
return false
|
459 |
+
}
|
460 |
+
|
461 |
+
// returns an array of closest squares from square
|
462 |
+
function createRadius (square) {
|
463 |
+
var squares = []
|
464 |
+
|
465 |
+
// calculate distance of all squares
|
466 |
+
for (var i = 0; i < 8; i++) {
|
467 |
+
for (var j = 0; j < 8; j++) {
|
468 |
+
var s = COLUMNS[i] + (j + 1)
|
469 |
+
|
470 |
+
// skip the square we're starting from
|
471 |
+
if (square === s) continue
|
472 |
+
|
473 |
+
squares.push({
|
474 |
+
square: s,
|
475 |
+
distance: squareDistance(square, s)
|
476 |
+
})
|
477 |
+
}
|
478 |
+
}
|
479 |
+
|
480 |
+
// sort by distance
|
481 |
+
squares.sort(function (a, b) {
|
482 |
+
return a.distance - b.distance
|
483 |
+
})
|
484 |
+
|
485 |
+
// just return the square code
|
486 |
+
var surroundingSquares = []
|
487 |
+
for (i = 0; i < squares.length; i++) {
|
488 |
+
surroundingSquares.push(squares[i].square)
|
489 |
+
}
|
490 |
+
|
491 |
+
return surroundingSquares
|
492 |
+
}
|
493 |
+
|
494 |
+
// given a position and a set of moves, return a new position
|
495 |
+
// with the moves executed
|
496 |
+
function calculatePositionFromMoves (position, moves) {
|
497 |
+
var newPosition = deepCopy(position)
|
498 |
+
|
499 |
+
for (var i in moves) {
|
500 |
+
if (!moves.hasOwnProperty(i)) continue
|
501 |
+
|
502 |
+
// skip the move if the position doesn't have a piece on the source square
|
503 |
+
if (!newPosition.hasOwnProperty(i)) continue
|
504 |
+
|
505 |
+
var piece = newPosition[i]
|
506 |
+
delete newPosition[i]
|
507 |
+
newPosition[moves[i]] = piece
|
508 |
+
}
|
509 |
+
|
510 |
+
return newPosition
|
511 |
+
}
|
512 |
+
|
513 |
+
// TODO: add some asserts here for calculatePositionFromMoves
|
514 |
+
|
515 |
+
// ---------------------------------------------------------------------------
|
516 |
+
// HTML
|
517 |
+
// ---------------------------------------------------------------------------
|
518 |
+
|
519 |
+
function buildContainerHTML (hasSparePieces) {
|
520 |
+
var html = '<div class="{chessboard}">'
|
521 |
+
|
522 |
+
if (hasSparePieces) {
|
523 |
+
html += '<div class="{sparePieces} {sparePiecesTop}"></div>'
|
524 |
+
}
|
525 |
+
|
526 |
+
html += '<div class="{board}"></div>'
|
527 |
+
|
528 |
+
if (hasSparePieces) {
|
529 |
+
html += '<div class="{sparePieces} {sparePiecesBottom}"></div>'
|
530 |
+
}
|
531 |
+
|
532 |
+
html += '</div>'
|
533 |
+
|
534 |
+
return interpolateTemplate(html, CSS)
|
535 |
+
}
|
536 |
+
|
537 |
+
// ---------------------------------------------------------------------------
|
538 |
+
// Config
|
539 |
+
// ---------------------------------------------------------------------------
|
540 |
+
|
541 |
+
function expandConfigArgumentShorthand (config) {
|
542 |
+
if (config === 'start') {
|
543 |
+
config = {position: deepCopy(START_POSITION)}
|
544 |
+
} else if (validFen(config)) {
|
545 |
+
config = {position: fenToObj(config)}
|
546 |
+
} else if (validPositionObject(config)) {
|
547 |
+
config = {position: deepCopy(config)}
|
548 |
+
}
|
549 |
+
|
550 |
+
// config must be an object
|
551 |
+
if (!$.isPlainObject(config)) config = {}
|
552 |
+
|
553 |
+
return config
|
554 |
+
}
|
555 |
+
|
556 |
+
// validate config / set default options
|
557 |
+
function expandConfig (config) {
|
558 |
+
// default for orientation is white
|
559 |
+
if (config.orientation !== 'black') config.orientation = 'white'
|
560 |
+
|
561 |
+
// default for showNotation is true
|
562 |
+
if (config.showNotation !== false) config.showNotation = true
|
563 |
+
|
564 |
+
// default for draggable is false
|
565 |
+
if (config.draggable !== true) config.draggable = false
|
566 |
+
|
567 |
+
// default for dropOffBoard is 'snapback'
|
568 |
+
if (config.dropOffBoard !== 'trash') config.dropOffBoard = 'snapback'
|
569 |
+
|
570 |
+
// default for sparePieces is false
|
571 |
+
if (config.sparePieces !== true) config.sparePieces = false
|
572 |
+
|
573 |
+
// draggable must be true if sparePieces is enabled
|
574 |
+
if (config.sparePieces) config.draggable = true
|
575 |
+
|
576 |
+
// default piece theme is wikipedia
|
577 |
+
if (!config.hasOwnProperty('pieceTheme') ||
|
578 |
+
(!isString(config.pieceTheme) && !isFunction(config.pieceTheme))) {
|
579 |
+
config.pieceTheme = 'img/chesspieces/wikipedia/{piece}.png'
|
580 |
+
}
|
581 |
+
|
582 |
+
// animation speeds
|
583 |
+
if (!validAnimationSpeed(config.appearSpeed)) config.appearSpeed = DEFAULT_APPEAR_SPEED
|
584 |
+
if (!validAnimationSpeed(config.moveSpeed)) config.moveSpeed = DEFAULT_MOVE_SPEED
|
585 |
+
if (!validAnimationSpeed(config.snapbackSpeed)) config.snapbackSpeed = DEFAULT_SNAPBACK_SPEED
|
586 |
+
if (!validAnimationSpeed(config.snapSpeed)) config.snapSpeed = DEFAULT_SNAP_SPEED
|
587 |
+
if (!validAnimationSpeed(config.trashSpeed)) config.trashSpeed = DEFAULT_TRASH_SPEED
|
588 |
+
|
589 |
+
// throttle rate
|
590 |
+
if (!validThrottleRate(config.dragThrottleRate)) config.dragThrottleRate = DEFAULT_DRAG_THROTTLE_RATE
|
591 |
+
|
592 |
+
return config
|
593 |
+
}
|
594 |
+
|
595 |
+
// ---------------------------------------------------------------------------
|
596 |
+
// Dependencies
|
597 |
+
// ---------------------------------------------------------------------------
|
598 |
+
|
599 |
+
// check for a compatible version of jQuery
|
600 |
+
function checkJQuery () {
|
601 |
+
if (!validJQueryVersion()) {
|
602 |
+
var errorMsg = 'Chessboard Error 1005: Unable to find a valid version of jQuery. ' +
|
603 |
+
'Please include jQuery ' + MINIMUM_JQUERY_VERSION + ' or higher on the page' +
|
604 |
+
'\n\n' +
|
605 |
+
'Exiting' + ELLIPSIS
|
606 |
+
window.alert(errorMsg)
|
607 |
+
return false
|
608 |
+
}
|
609 |
+
|
610 |
+
return true
|
611 |
+
}
|
612 |
+
|
613 |
+
// return either boolean false or the $container element
|
614 |
+
function checkContainerArg (containerElOrString) {
|
615 |
+
if (containerElOrString === '') {
|
616 |
+
var errorMsg1 = 'Chessboard Error 1001: ' +
|
617 |
+
'The first argument to Chessboard() cannot be an empty string.' +
|
618 |
+
'\n\n' +
|
619 |
+
'Exiting' + ELLIPSIS
|
620 |
+
window.alert(errorMsg1)
|
621 |
+
return false
|
622 |
+
}
|
623 |
+
|
624 |
+
// convert containerEl to query selector if it is a string
|
625 |
+
if (isString(containerElOrString) &&
|
626 |
+
containerElOrString.charAt(0) !== '#') {
|
627 |
+
containerElOrString = '#' + containerElOrString
|
628 |
+
}
|
629 |
+
|
630 |
+
// containerEl must be something that becomes a jQuery collection of size 1
|
631 |
+
var $container = $(containerElOrString)
|
632 |
+
if ($container.length !== 1) {
|
633 |
+
var errorMsg2 = 'Chessboard Error 1003: ' +
|
634 |
+
'The first argument to Chessboard() must be the ID of a DOM node, ' +
|
635 |
+
'an ID query selector, or a single DOM node.' +
|
636 |
+
'\n\n' +
|
637 |
+
'Exiting' + ELLIPSIS
|
638 |
+
window.alert(errorMsg2)
|
639 |
+
return false
|
640 |
+
}
|
641 |
+
|
642 |
+
return $container
|
643 |
+
}
|
644 |
+
|
645 |
+
// ---------------------------------------------------------------------------
|
646 |
+
// Constructor
|
647 |
+
// ---------------------------------------------------------------------------
|
648 |
+
|
649 |
+
function constructor (containerElOrString, config) {
|
650 |
+
// first things first: check basic dependencies
|
651 |
+
if (!checkJQuery()) return null
|
652 |
+
var $container = checkContainerArg(containerElOrString)
|
653 |
+
if (!$container) return null
|
654 |
+
|
655 |
+
// ensure the config object is what we expect
|
656 |
+
config = expandConfigArgumentShorthand(config)
|
657 |
+
config = expandConfig(config)
|
658 |
+
|
659 |
+
// DOM elements
|
660 |
+
var $board = null
|
661 |
+
var $draggedPiece = null
|
662 |
+
var $sparePiecesTop = null
|
663 |
+
var $sparePiecesBottom = null
|
664 |
+
|
665 |
+
// constructor return object
|
666 |
+
var widget = {}
|
667 |
+
|
668 |
+
// -------------------------------------------------------------------------
|
669 |
+
// Stateful
|
670 |
+
// -------------------------------------------------------------------------
|
671 |
+
|
672 |
+
var boardBorderSize = 2
|
673 |
+
var currentOrientation = 'white'
|
674 |
+
var currentPosition = {}
|
675 |
+
var draggedPiece = null
|
676 |
+
var draggedPieceLocation = null
|
677 |
+
var draggedPieceSource = null
|
678 |
+
var isDragging = false
|
679 |
+
var sparePiecesElsIds = {}
|
680 |
+
var squareElsIds = {}
|
681 |
+
var squareElsOffsets = {}
|
682 |
+
var squareSize = 16
|
683 |
+
|
684 |
+
// -------------------------------------------------------------------------
|
685 |
+
// Validation / Errors
|
686 |
+
// -------------------------------------------------------------------------
|
687 |
+
|
688 |
+
function error (code, msg, obj) {
|
689 |
+
// do nothing if showErrors is not set
|
690 |
+
if (
|
691 |
+
config.hasOwnProperty('showErrors') !== true ||
|
692 |
+
config.showErrors === false
|
693 |
+
) {
|
694 |
+
return
|
695 |
+
}
|
696 |
+
|
697 |
+
var errorText = 'Chessboard Error ' + code + ': ' + msg
|
698 |
+
|
699 |
+
// print to console
|
700 |
+
if (
|
701 |
+
config.showErrors === 'console' &&
|
702 |
+
typeof console === 'object' &&
|
703 |
+
typeof console.log === 'function'
|
704 |
+
) {
|
705 |
+
console.log(errorText)
|
706 |
+
if (arguments.length >= 2) {
|
707 |
+
console.log(obj)
|
708 |
+
}
|
709 |
+
return
|
710 |
+
}
|
711 |
+
|
712 |
+
// alert errors
|
713 |
+
if (config.showErrors === 'alert') {
|
714 |
+
if (obj) {
|
715 |
+
errorText += '\n\n' + JSON.stringify(obj)
|
716 |
+
}
|
717 |
+
window.alert(errorText)
|
718 |
+
return
|
719 |
+
}
|
720 |
+
|
721 |
+
// custom function
|
722 |
+
if (isFunction(config.showErrors)) {
|
723 |
+
config.showErrors(code, msg, obj)
|
724 |
+
}
|
725 |
+
}
|
726 |
+
|
727 |
+
function setInitialState () {
|
728 |
+
currentOrientation = config.orientation
|
729 |
+
|
730 |
+
// make sure position is valid
|
731 |
+
if (config.hasOwnProperty('position')) {
|
732 |
+
if (config.position === 'start') {
|
733 |
+
currentPosition = deepCopy(START_POSITION)
|
734 |
+
} else if (validFen(config.position)) {
|
735 |
+
currentPosition = fenToObj(config.position)
|
736 |
+
} else if (validPositionObject(config.position)) {
|
737 |
+
currentPosition = deepCopy(config.position)
|
738 |
+
} else {
|
739 |
+
error(
|
740 |
+
7263,
|
741 |
+
'Invalid value passed to config.position.',
|
742 |
+
config.position
|
743 |
+
)
|
744 |
+
}
|
745 |
+
}
|
746 |
+
}
|
747 |
+
|
748 |
+
// -------------------------------------------------------------------------
|
749 |
+
// DOM Misc
|
750 |
+
// -------------------------------------------------------------------------
|
751 |
+
|
752 |
+
// calculates square size based on the width of the container
|
753 |
+
// got a little CSS black magic here, so let me explain:
|
754 |
+
// get the width of the container element (could be anything), reduce by 1 for
|
755 |
+
// fudge factor, and then keep reducing until we find an exact mod 8 for
|
756 |
+
// our square size
|
757 |
+
function calculateSquareSize () {
|
758 |
+
var containerWidth = parseInt($container.width(), 10)
|
759 |
+
|
760 |
+
// defensive, prevent infinite loop
|
761 |
+
if (!containerWidth || containerWidth <= 0) {
|
762 |
+
return 0
|
763 |
+
}
|
764 |
+
|
765 |
+
// pad one pixel
|
766 |
+
var boardWidth = containerWidth - 1
|
767 |
+
|
768 |
+
while (boardWidth % 8 !== 0 && boardWidth > 0) {
|
769 |
+
boardWidth = boardWidth - 1
|
770 |
+
}
|
771 |
+
|
772 |
+
return boardWidth / 8
|
773 |
+
}
|
774 |
+
|
775 |
+
// create random IDs for elements
|
776 |
+
function createElIds () {
|
777 |
+
// squares on the board
|
778 |
+
for (var i = 0; i < COLUMNS.length; i++) {
|
779 |
+
for (var j = 1; j <= 8; j++) {
|
780 |
+
var square = COLUMNS[i] + j
|
781 |
+
squareElsIds[square] = square + '-' + uuid()
|
782 |
+
}
|
783 |
+
}
|
784 |
+
|
785 |
+
// spare pieces
|
786 |
+
var pieces = 'KQRNBP'.split('')
|
787 |
+
for (i = 0; i < pieces.length; i++) {
|
788 |
+
var whitePiece = 'w' + pieces[i]
|
789 |
+
var blackPiece = 'b' + pieces[i]
|
790 |
+
sparePiecesElsIds[whitePiece] = whitePiece + '-' + uuid()
|
791 |
+
sparePiecesElsIds[blackPiece] = blackPiece + '-' + uuid()
|
792 |
+
}
|
793 |
+
}
|
794 |
+
|
795 |
+
// -------------------------------------------------------------------------
|
796 |
+
// Markup Building
|
797 |
+
// -------------------------------------------------------------------------
|
798 |
+
|
799 |
+
function buildBoardHTML (orientation) {
|
800 |
+
if (orientation !== 'black') {
|
801 |
+
orientation = 'white'
|
802 |
+
}
|
803 |
+
|
804 |
+
var html = ''
|
805 |
+
|
806 |
+
// algebraic notation / orientation
|
807 |
+
var alpha = deepCopy(COLUMNS)
|
808 |
+
var row = 8
|
809 |
+
if (orientation === 'black') {
|
810 |
+
alpha.reverse()
|
811 |
+
row = 1
|
812 |
+
}
|
813 |
+
|
814 |
+
var squareColor = 'white'
|
815 |
+
for (var i = 0; i < 8; i++) {
|
816 |
+
html += '<div class="{row}">'
|
817 |
+
for (var j = 0; j < 8; j++) {
|
818 |
+
var square = alpha[j] + row
|
819 |
+
|
820 |
+
html += '<div class="{square} ' + CSS[squareColor] + ' ' +
|
821 |
+
'square-' + square + '" ' +
|
822 |
+
'style="width:' + squareSize + 'px;height:' + squareSize + 'px;" ' +
|
823 |
+
'id="' + squareElsIds[square] + '" ' +
|
824 |
+
'data-square="' + square + '">'
|
825 |
+
|
826 |
+
if (config.showNotation) {
|
827 |
+
// alpha notation
|
828 |
+
if ((orientation === 'white' && row === 1) ||
|
829 |
+
(orientation === 'black' && row === 8)) {
|
830 |
+
html += '<div class="{notation} {alpha}">' + alpha[j] + '</div>'
|
831 |
+
}
|
832 |
+
|
833 |
+
// numeric notation
|
834 |
+
if (j === 0) {
|
835 |
+
html += '<div class="{notation} {numeric}">' + row + '</div>'
|
836 |
+
}
|
837 |
+
}
|
838 |
+
|
839 |
+
html += '</div>' // end .square
|
840 |
+
|
841 |
+
squareColor = (squareColor === 'white') ? 'black' : 'white'
|
842 |
+
}
|
843 |
+
html += '<div class="{clearfix}"></div></div>'
|
844 |
+
|
845 |
+
squareColor = (squareColor === 'white') ? 'black' : 'white'
|
846 |
+
|
847 |
+
if (orientation === 'white') {
|
848 |
+
row = row - 1
|
849 |
+
} else {
|
850 |
+
row = row + 1
|
851 |
+
}
|
852 |
+
}
|
853 |
+
|
854 |
+
return interpolateTemplate(html, CSS)
|
855 |
+
}
|
856 |
+
|
857 |
+
function buildPieceImgSrc (piece) {
|
858 |
+
if (isFunction(config.pieceTheme)) {
|
859 |
+
return config.pieceTheme(piece)
|
860 |
+
}
|
861 |
+
|
862 |
+
if (isString(config.pieceTheme)) {
|
863 |
+
return interpolateTemplate(config.pieceTheme, {piece: piece})
|
864 |
+
}
|
865 |
+
|
866 |
+
// NOTE: this should never happen
|
867 |
+
error(8272, 'Unable to build image source for config.pieceTheme.')
|
868 |
+
return ''
|
869 |
+
}
|
870 |
+
|
871 |
+
function buildPieceHTML (piece, hidden, id) {
|
872 |
+
var html = '<img src="' + buildPieceImgSrc(piece) + '" '
|
873 |
+
if (isString(id) && id !== '') {
|
874 |
+
html += 'id="' + id + '" '
|
875 |
+
}
|
876 |
+
html += 'alt="" ' +
|
877 |
+
'class="{piece}" ' +
|
878 |
+
'data-piece="' + piece + '" ' +
|
879 |
+
'style="width:' + squareSize + 'px;' + 'height:' + squareSize + 'px;'
|
880 |
+
|
881 |
+
if (hidden) {
|
882 |
+
html += 'display:none;'
|
883 |
+
}
|
884 |
+
|
885 |
+
html += '" />'
|
886 |
+
|
887 |
+
return interpolateTemplate(html, CSS)
|
888 |
+
}
|
889 |
+
|
890 |
+
function buildSparePiecesHTML (color) {
|
891 |
+
var pieces = ['wK', 'wQ', 'wR', 'wB', 'wN', 'wP']
|
892 |
+
if (color === 'black') {
|
893 |
+
pieces = ['bK', 'bQ', 'bR', 'bB', 'bN', 'bP']
|
894 |
+
}
|
895 |
+
|
896 |
+
var html = ''
|
897 |
+
for (var i = 0; i < pieces.length; i++) {
|
898 |
+
html += buildPieceHTML(pieces[i], false, sparePiecesElsIds[pieces[i]])
|
899 |
+
}
|
900 |
+
|
901 |
+
return html
|
902 |
+
}
|
903 |
+
|
904 |
+
// -------------------------------------------------------------------------
|
905 |
+
// Animations
|
906 |
+
// -------------------------------------------------------------------------
|
907 |
+
|
908 |
+
function animateSquareToSquare (src, dest, piece, completeFn) {
|
909 |
+
// get information about the source and destination squares
|
910 |
+
var $srcSquare = $('#' + squareElsIds[src])
|
911 |
+
var srcSquarePosition = $srcSquare.offset()
|
912 |
+
var $destSquare = $('#' + squareElsIds[dest])
|
913 |
+
var destSquarePosition = $destSquare.offset()
|
914 |
+
|
915 |
+
// create the animated piece and absolutely position it
|
916 |
+
// over the source square
|
917 |
+
var animatedPieceId = uuid()
|
918 |
+
$('body').append(buildPieceHTML(piece, true, animatedPieceId))
|
919 |
+
var $animatedPiece = $('#' + animatedPieceId)
|
920 |
+
$animatedPiece.css({
|
921 |
+
display: '',
|
922 |
+
position: 'absolute',
|
923 |
+
top: srcSquarePosition.top,
|
924 |
+
left: srcSquarePosition.left
|
925 |
+
})
|
926 |
+
|
927 |
+
// remove original piece from source square
|
928 |
+
$srcSquare.find('.' + CSS.piece).remove()
|
929 |
+
|
930 |
+
function onFinishAnimation1 () {
|
931 |
+
// add the "real" piece to the destination square
|
932 |
+
$destSquare.append(buildPieceHTML(piece))
|
933 |
+
|
934 |
+
// remove the animated piece
|
935 |
+
$animatedPiece.remove()
|
936 |
+
|
937 |
+
// run complete function
|
938 |
+
if (isFunction(completeFn)) {
|
939 |
+
completeFn()
|
940 |
+
}
|
941 |
+
}
|
942 |
+
|
943 |
+
// animate the piece to the destination square
|
944 |
+
var opts = {
|
945 |
+
duration: config.moveSpeed,
|
946 |
+
complete: onFinishAnimation1
|
947 |
+
}
|
948 |
+
$animatedPiece.animate(destSquarePosition, opts)
|
949 |
+
}
|
950 |
+
|
951 |
+
function animateSparePieceToSquare (piece, dest, completeFn) {
|
952 |
+
var srcOffset = $('#' + sparePiecesElsIds[piece]).offset()
|
953 |
+
var $destSquare = $('#' + squareElsIds[dest])
|
954 |
+
var destOffset = $destSquare.offset()
|
955 |
+
|
956 |
+
// create the animate piece
|
957 |
+
var pieceId = uuid()
|
958 |
+
$('body').append(buildPieceHTML(piece, true, pieceId))
|
959 |
+
var $animatedPiece = $('#' + pieceId)
|
960 |
+
$animatedPiece.css({
|
961 |
+
display: '',
|
962 |
+
position: 'absolute',
|
963 |
+
left: srcOffset.left,
|
964 |
+
top: srcOffset.top
|
965 |
+
})
|
966 |
+
|
967 |
+
// on complete
|
968 |
+
function onFinishAnimation2 () {
|
969 |
+
// add the "real" piece to the destination square
|
970 |
+
$destSquare.find('.' + CSS.piece).remove()
|
971 |
+
$destSquare.append(buildPieceHTML(piece))
|
972 |
+
|
973 |
+
// remove the animated piece
|
974 |
+
$animatedPiece.remove()
|
975 |
+
|
976 |
+
// run complete function
|
977 |
+
if (isFunction(completeFn)) {
|
978 |
+
completeFn()
|
979 |
+
}
|
980 |
+
}
|
981 |
+
|
982 |
+
// animate the piece to the destination square
|
983 |
+
var opts = {
|
984 |
+
duration: config.moveSpeed,
|
985 |
+
complete: onFinishAnimation2
|
986 |
+
}
|
987 |
+
$animatedPiece.animate(destOffset, opts)
|
988 |
+
}
|
989 |
+
|
990 |
+
// execute an array of animations
|
991 |
+
function doAnimations (animations, oldPos, newPos) {
|
992 |
+
if (animations.length === 0) return
|
993 |
+
|
994 |
+
var numFinished = 0
|
995 |
+
function onFinishAnimation3 () {
|
996 |
+
// exit if all the animations aren't finished
|
997 |
+
numFinished = numFinished + 1
|
998 |
+
if (numFinished !== animations.length) return
|
999 |
+
|
1000 |
+
drawPositionInstant()
|
1001 |
+
|
1002 |
+
// run their onMoveEnd function
|
1003 |
+
if (isFunction(config.onMoveEnd)) {
|
1004 |
+
config.onMoveEnd(deepCopy(oldPos), deepCopy(newPos))
|
1005 |
+
}
|
1006 |
+
}
|
1007 |
+
|
1008 |
+
for (var i = 0; i < animations.length; i++) {
|
1009 |
+
var animation = animations[i]
|
1010 |
+
|
1011 |
+
// clear a piece
|
1012 |
+
if (animation.type === 'clear') {
|
1013 |
+
$('#' + squareElsIds[animation.square] + ' .' + CSS.piece)
|
1014 |
+
.fadeOut(config.trashSpeed, onFinishAnimation3)
|
1015 |
+
|
1016 |
+
// add a piece with no spare pieces - fade the piece onto the square
|
1017 |
+
} else if (animation.type === 'add' && !config.sparePieces) {
|
1018 |
+
$('#' + squareElsIds[animation.square])
|
1019 |
+
.append(buildPieceHTML(animation.piece, true))
|
1020 |
+
.find('.' + CSS.piece)
|
1021 |
+
.fadeIn(config.appearSpeed, onFinishAnimation3)
|
1022 |
+
|
1023 |
+
// add a piece with spare pieces - animate from the spares
|
1024 |
+
} else if (animation.type === 'add' && config.sparePieces) {
|
1025 |
+
animateSparePieceToSquare(animation.piece, animation.square, onFinishAnimation3)
|
1026 |
+
|
1027 |
+
// move a piece from squareA to squareB
|
1028 |
+
} else if (animation.type === 'move') {
|
1029 |
+
animateSquareToSquare(animation.source, animation.destination, animation.piece, onFinishAnimation3)
|
1030 |
+
}
|
1031 |
+
}
|
1032 |
+
}
|
1033 |
+
|
1034 |
+
// calculate an array of animations that need to happen in order to get
|
1035 |
+
// from pos1 to pos2
|
1036 |
+
function calculateAnimations (pos1, pos2) {
|
1037 |
+
// make copies of both
|
1038 |
+
pos1 = deepCopy(pos1)
|
1039 |
+
pos2 = deepCopy(pos2)
|
1040 |
+
|
1041 |
+
var animations = []
|
1042 |
+
var squaresMovedTo = {}
|
1043 |
+
|
1044 |
+
// remove pieces that are the same in both positions
|
1045 |
+
for (var i in pos2) {
|
1046 |
+
if (!pos2.hasOwnProperty(i)) continue
|
1047 |
+
|
1048 |
+
if (pos1.hasOwnProperty(i) && pos1[i] === pos2[i]) {
|
1049 |
+
delete pos1[i]
|
1050 |
+
delete pos2[i]
|
1051 |
+
}
|
1052 |
+
}
|
1053 |
+
|
1054 |
+
// find all the "move" animations
|
1055 |
+
for (i in pos2) {
|
1056 |
+
if (!pos2.hasOwnProperty(i)) continue
|
1057 |
+
|
1058 |
+
var closestPiece = findClosestPiece(pos1, pos2[i], i)
|
1059 |
+
if (closestPiece) {
|
1060 |
+
animations.push({
|
1061 |
+
type: 'move',
|
1062 |
+
source: closestPiece,
|
1063 |
+
destination: i,
|
1064 |
+
piece: pos2[i]
|
1065 |
+
})
|
1066 |
+
|
1067 |
+
delete pos1[closestPiece]
|
1068 |
+
delete pos2[i]
|
1069 |
+
squaresMovedTo[i] = true
|
1070 |
+
}
|
1071 |
+
}
|
1072 |
+
|
1073 |
+
// "add" animations
|
1074 |
+
for (i in pos2) {
|
1075 |
+
if (!pos2.hasOwnProperty(i)) continue
|
1076 |
+
|
1077 |
+
animations.push({
|
1078 |
+
type: 'add',
|
1079 |
+
square: i,
|
1080 |
+
piece: pos2[i]
|
1081 |
+
})
|
1082 |
+
|
1083 |
+
delete pos2[i]
|
1084 |
+
}
|
1085 |
+
|
1086 |
+
// "clear" animations
|
1087 |
+
for (i in pos1) {
|
1088 |
+
if (!pos1.hasOwnProperty(i)) continue
|
1089 |
+
|
1090 |
+
// do not clear a piece if it is on a square that is the result
|
1091 |
+
// of a "move", ie: a piece capture
|
1092 |
+
if (squaresMovedTo.hasOwnProperty(i)) continue
|
1093 |
+
|
1094 |
+
animations.push({
|
1095 |
+
type: 'clear',
|
1096 |
+
square: i,
|
1097 |
+
piece: pos1[i]
|
1098 |
+
})
|
1099 |
+
|
1100 |
+
delete pos1[i]
|
1101 |
+
}
|
1102 |
+
|
1103 |
+
return animations
|
1104 |
+
}
|
1105 |
+
|
1106 |
+
// -------------------------------------------------------------------------
|
1107 |
+
// Control Flow
|
1108 |
+
// -------------------------------------------------------------------------
|
1109 |
+
|
1110 |
+
function drawPositionInstant () {
|
1111 |
+
// clear the board
|
1112 |
+
$board.find('.' + CSS.piece).remove()
|
1113 |
+
|
1114 |
+
// add the pieces
|
1115 |
+
for (var i in currentPosition) {
|
1116 |
+
if (!currentPosition.hasOwnProperty(i)) continue
|
1117 |
+
|
1118 |
+
$('#' + squareElsIds[i]).append(buildPieceHTML(currentPosition[i]))
|
1119 |
+
}
|
1120 |
+
}
|
1121 |
+
|
1122 |
+
function drawBoard () {
|
1123 |
+
$board.html(buildBoardHTML(currentOrientation, squareSize, config.showNotation))
|
1124 |
+
drawPositionInstant()
|
1125 |
+
|
1126 |
+
if (config.sparePieces) {
|
1127 |
+
if (currentOrientation === 'white') {
|
1128 |
+
$sparePiecesTop.html(buildSparePiecesHTML('black'))
|
1129 |
+
$sparePiecesBottom.html(buildSparePiecesHTML('white'))
|
1130 |
+
} else {
|
1131 |
+
$sparePiecesTop.html(buildSparePiecesHTML('white'))
|
1132 |
+
$sparePiecesBottom.html(buildSparePiecesHTML('black'))
|
1133 |
+
}
|
1134 |
+
}
|
1135 |
+
}
|
1136 |
+
|
1137 |
+
function setCurrentPosition (position) {
|
1138 |
+
var oldPos = deepCopy(currentPosition)
|
1139 |
+
var newPos = deepCopy(position)
|
1140 |
+
var oldFen = objToFen(oldPos)
|
1141 |
+
var newFen = objToFen(newPos)
|
1142 |
+
|
1143 |
+
// do nothing if no change in position
|
1144 |
+
if (oldFen === newFen) return
|
1145 |
+
|
1146 |
+
// run their onChange function
|
1147 |
+
if (isFunction(config.onChange)) {
|
1148 |
+
config.onChange(oldPos, newPos)
|
1149 |
+
}
|
1150 |
+
|
1151 |
+
// update state
|
1152 |
+
currentPosition = position
|
1153 |
+
}
|
1154 |
+
|
1155 |
+
function isXYOnSquare (x, y) {
|
1156 |
+
for (var i in squareElsOffsets) {
|
1157 |
+
if (!squareElsOffsets.hasOwnProperty(i)) continue
|
1158 |
+
|
1159 |
+
var s = squareElsOffsets[i]
|
1160 |
+
if (x >= s.left &&
|
1161 |
+
x < s.left + squareSize &&
|
1162 |
+
y >= s.top &&
|
1163 |
+
y < s.top + squareSize) {
|
1164 |
+
return i
|
1165 |
+
}
|
1166 |
+
}
|
1167 |
+
|
1168 |
+
return 'offboard'
|
1169 |
+
}
|
1170 |
+
|
1171 |
+
// records the XY coords of every square into memory
|
1172 |
+
function captureSquareOffsets () {
|
1173 |
+
squareElsOffsets = {}
|
1174 |
+
|
1175 |
+
for (var i in squareElsIds) {
|
1176 |
+
if (!squareElsIds.hasOwnProperty(i)) continue
|
1177 |
+
|
1178 |
+
squareElsOffsets[i] = $('#' + squareElsIds[i]).offset()
|
1179 |
+
}
|
1180 |
+
}
|
1181 |
+
|
1182 |
+
function removeSquareHighlights () {
|
1183 |
+
$board
|
1184 |
+
.find('.' + CSS.square)
|
1185 |
+
.removeClass(CSS.highlight1 + ' ' + CSS.highlight2)
|
1186 |
+
}
|
1187 |
+
|
1188 |
+
function snapbackDraggedPiece () {
|
1189 |
+
// there is no "snapback" for spare pieces
|
1190 |
+
if (draggedPieceSource === 'spare') {
|
1191 |
+
trashDraggedPiece()
|
1192 |
+
return
|
1193 |
+
}
|
1194 |
+
|
1195 |
+
removeSquareHighlights()
|
1196 |
+
|
1197 |
+
// animation complete
|
1198 |
+
function complete () {
|
1199 |
+
drawPositionInstant()
|
1200 |
+
$draggedPiece.css('display', 'none')
|
1201 |
+
|
1202 |
+
// run their onSnapbackEnd function
|
1203 |
+
if (isFunction(config.onSnapbackEnd)) {
|
1204 |
+
config.onSnapbackEnd(
|
1205 |
+
draggedPiece,
|
1206 |
+
draggedPieceSource,
|
1207 |
+
deepCopy(currentPosition),
|
1208 |
+
currentOrientation
|
1209 |
+
)
|
1210 |
+
}
|
1211 |
+
}
|
1212 |
+
|
1213 |
+
// get source square position
|
1214 |
+
var sourceSquarePosition = $('#' + squareElsIds[draggedPieceSource]).offset()
|
1215 |
+
|
1216 |
+
// animate the piece to the target square
|
1217 |
+
var opts = {
|
1218 |
+
duration: config.snapbackSpeed,
|
1219 |
+
complete: complete
|
1220 |
+
}
|
1221 |
+
$draggedPiece.animate(sourceSquarePosition, opts)
|
1222 |
+
|
1223 |
+
// set state
|
1224 |
+
isDragging = false
|
1225 |
+
}
|
1226 |
+
|
1227 |
+
function trashDraggedPiece () {
|
1228 |
+
removeSquareHighlights()
|
1229 |
+
|
1230 |
+
// remove the source piece
|
1231 |
+
var newPosition = deepCopy(currentPosition)
|
1232 |
+
delete newPosition[draggedPieceSource]
|
1233 |
+
setCurrentPosition(newPosition)
|
1234 |
+
|
1235 |
+
// redraw the position
|
1236 |
+
drawPositionInstant()
|
1237 |
+
|
1238 |
+
// hide the dragged piece
|
1239 |
+
$draggedPiece.fadeOut(config.trashSpeed)
|
1240 |
+
|
1241 |
+
// set state
|
1242 |
+
isDragging = false
|
1243 |
+
}
|
1244 |
+
|
1245 |
+
function dropDraggedPieceOnSquare (square) {
|
1246 |
+
removeSquareHighlights()
|
1247 |
+
|
1248 |
+
// update position
|
1249 |
+
var newPosition = deepCopy(currentPosition)
|
1250 |
+
delete newPosition[draggedPieceSource]
|
1251 |
+
newPosition[square] = draggedPiece
|
1252 |
+
setCurrentPosition(newPosition)
|
1253 |
+
|
1254 |
+
// get target square information
|
1255 |
+
var targetSquarePosition = $('#' + squareElsIds[square]).offset()
|
1256 |
+
|
1257 |
+
// animation complete
|
1258 |
+
function onAnimationComplete () {
|
1259 |
+
drawPositionInstant()
|
1260 |
+
$draggedPiece.css('display', 'none')
|
1261 |
+
|
1262 |
+
// execute their onSnapEnd function
|
1263 |
+
if (isFunction(config.onSnapEnd)) {
|
1264 |
+
config.onSnapEnd(draggedPieceSource, square, draggedPiece)
|
1265 |
+
}
|
1266 |
+
}
|
1267 |
+
|
1268 |
+
// snap the piece to the target square
|
1269 |
+
var opts = {
|
1270 |
+
duration: config.snapSpeed,
|
1271 |
+
complete: onAnimationComplete
|
1272 |
+
}
|
1273 |
+
$draggedPiece.animate(targetSquarePosition, opts)
|
1274 |
+
|
1275 |
+
// set state
|
1276 |
+
isDragging = false
|
1277 |
+
}
|
1278 |
+
|
1279 |
+
function beginDraggingPiece (source, piece, x, y) {
|
1280 |
+
// run their custom onDragStart function
|
1281 |
+
// their custom onDragStart function can cancel drag start
|
1282 |
+
if (isFunction(config.onDragStart) &&
|
1283 |
+
config.onDragStart(source, piece, deepCopy(currentPosition), currentOrientation) === false) {
|
1284 |
+
return
|
1285 |
+
}
|
1286 |
+
|
1287 |
+
// set state
|
1288 |
+
isDragging = true
|
1289 |
+
draggedPiece = piece
|
1290 |
+
draggedPieceSource = source
|
1291 |
+
|
1292 |
+
// if the piece came from spare pieces, location is offboard
|
1293 |
+
if (source === 'spare') {
|
1294 |
+
draggedPieceLocation = 'offboard'
|
1295 |
+
} else {
|
1296 |
+
draggedPieceLocation = source
|
1297 |
+
}
|
1298 |
+
|
1299 |
+
// capture the x, y coords of all squares in memory
|
1300 |
+
captureSquareOffsets()
|
1301 |
+
|
1302 |
+
// create the dragged piece
|
1303 |
+
$draggedPiece.attr('src', buildPieceImgSrc(piece)).css({
|
1304 |
+
display: '',
|
1305 |
+
position: 'absolute',
|
1306 |
+
left: x - squareSize / 2,
|
1307 |
+
top: y - squareSize / 2
|
1308 |
+
})
|
1309 |
+
|
1310 |
+
if (source !== 'spare') {
|
1311 |
+
// highlight the source square and hide the piece
|
1312 |
+
$('#' + squareElsIds[source])
|
1313 |
+
.addClass(CSS.highlight1)
|
1314 |
+
.find('.' + CSS.piece)
|
1315 |
+
.css('display', 'none')
|
1316 |
+
}
|
1317 |
+
}
|
1318 |
+
|
1319 |
+
function updateDraggedPiece (x, y) {
|
1320 |
+
// put the dragged piece over the mouse cursor
|
1321 |
+
$draggedPiece.css({
|
1322 |
+
left: x - squareSize / 2,
|
1323 |
+
top: y - squareSize / 2
|
1324 |
+
})
|
1325 |
+
|
1326 |
+
// get location
|
1327 |
+
var location = isXYOnSquare(x, y)
|
1328 |
+
|
1329 |
+
// do nothing if the location has not changed
|
1330 |
+
if (location === draggedPieceLocation) return
|
1331 |
+
|
1332 |
+
// remove highlight from previous square
|
1333 |
+
if (validSquare(draggedPieceLocation)) {
|
1334 |
+
$('#' + squareElsIds[draggedPieceLocation]).removeClass(CSS.highlight2)
|
1335 |
+
}
|
1336 |
+
|
1337 |
+
// add highlight to new square
|
1338 |
+
if (validSquare(location)) {
|
1339 |
+
$('#' + squareElsIds[location]).addClass(CSS.highlight2)
|
1340 |
+
}
|
1341 |
+
|
1342 |
+
// run onDragMove
|
1343 |
+
if (isFunction(config.onDragMove)) {
|
1344 |
+
config.onDragMove(
|
1345 |
+
location,
|
1346 |
+
draggedPieceLocation,
|
1347 |
+
draggedPieceSource,
|
1348 |
+
draggedPiece,
|
1349 |
+
deepCopy(currentPosition),
|
1350 |
+
currentOrientation
|
1351 |
+
)
|
1352 |
+
}
|
1353 |
+
|
1354 |
+
// update state
|
1355 |
+
draggedPieceLocation = location
|
1356 |
+
}
|
1357 |
+
|
1358 |
+
function stopDraggedPiece (location) {
|
1359 |
+
// determine what the action should be
|
1360 |
+
var action = 'drop'
|
1361 |
+
if (location === 'offboard' && config.dropOffBoard === 'snapback') {
|
1362 |
+
action = 'snapback'
|
1363 |
+
}
|
1364 |
+
if (location === 'offboard' && config.dropOffBoard === 'trash') {
|
1365 |
+
action = 'trash'
|
1366 |
+
}
|
1367 |
+
|
1368 |
+
// run their onDrop function, which can potentially change the drop action
|
1369 |
+
if (isFunction(config.onDrop)) {
|
1370 |
+
var newPosition = deepCopy(currentPosition)
|
1371 |
+
|
1372 |
+
// source piece is a spare piece and position is off the board
|
1373 |
+
// if (draggedPieceSource === 'spare' && location === 'offboard') {...}
|
1374 |
+
// position has not changed; do nothing
|
1375 |
+
|
1376 |
+
// source piece is a spare piece and position is on the board
|
1377 |
+
if (draggedPieceSource === 'spare' && validSquare(location)) {
|
1378 |
+
// add the piece to the board
|
1379 |
+
newPosition[location] = draggedPiece
|
1380 |
+
}
|
1381 |
+
|
1382 |
+
// source piece was on the board and position is off the board
|
1383 |
+
if (validSquare(draggedPieceSource) && location === 'offboard') {
|
1384 |
+
// remove the piece from the board
|
1385 |
+
delete newPosition[draggedPieceSource]
|
1386 |
+
}
|
1387 |
+
|
1388 |
+
// source piece was on the board and position is on the board
|
1389 |
+
if (validSquare(draggedPieceSource) && validSquare(location)) {
|
1390 |
+
// move the piece
|
1391 |
+
delete newPosition[draggedPieceSource]
|
1392 |
+
newPosition[location] = draggedPiece
|
1393 |
+
}
|
1394 |
+
|
1395 |
+
var oldPosition = deepCopy(currentPosition)
|
1396 |
+
|
1397 |
+
var result = config.onDrop(
|
1398 |
+
draggedPieceSource,
|
1399 |
+
location,
|
1400 |
+
draggedPiece,
|
1401 |
+
newPosition,
|
1402 |
+
oldPosition,
|
1403 |
+
currentOrientation
|
1404 |
+
)
|
1405 |
+
if (result === 'snapback' || result === 'trash') {
|
1406 |
+
action = result
|
1407 |
+
}
|
1408 |
+
}
|
1409 |
+
|
1410 |
+
// do it!
|
1411 |
+
if (action === 'snapback') {
|
1412 |
+
snapbackDraggedPiece()
|
1413 |
+
} else if (action === 'trash') {
|
1414 |
+
trashDraggedPiece()
|
1415 |
+
} else if (action === 'drop') {
|
1416 |
+
dropDraggedPieceOnSquare(location)
|
1417 |
+
}
|
1418 |
+
}
|
1419 |
+
|
1420 |
+
// -------------------------------------------------------------------------
|
1421 |
+
// Public Methods
|
1422 |
+
// -------------------------------------------------------------------------
|
1423 |
+
|
1424 |
+
// clear the board
|
1425 |
+
widget.clear = function (useAnimation) {
|
1426 |
+
widget.position({}, useAnimation)
|
1427 |
+
}
|
1428 |
+
|
1429 |
+
// remove the widget from the page
|
1430 |
+
widget.destroy = function () {
|
1431 |
+
// remove markup
|
1432 |
+
$container.html('')
|
1433 |
+
$draggedPiece.remove()
|
1434 |
+
|
1435 |
+
// remove event handlers
|
1436 |
+
$container.unbind()
|
1437 |
+
}
|
1438 |
+
|
1439 |
+
// shorthand method to get the current FEN
|
1440 |
+
widget.fen = function () {
|
1441 |
+
return widget.position('fen')
|
1442 |
+
}
|
1443 |
+
|
1444 |
+
// flip orientation
|
1445 |
+
widget.flip = function () {
|
1446 |
+
return widget.orientation('flip')
|
1447 |
+
}
|
1448 |
+
|
1449 |
+
// move pieces
|
1450 |
+
// TODO: this method should be variadic as well as accept an array of moves
|
1451 |
+
widget.move = function () {
|
1452 |
+
// no need to throw an error here; just do nothing
|
1453 |
+
// TODO: this should return the current position
|
1454 |
+
if (arguments.length === 0) return
|
1455 |
+
|
1456 |
+
var useAnimation = true
|
1457 |
+
|
1458 |
+
// collect the moves into an object
|
1459 |
+
var moves = {}
|
1460 |
+
for (var i = 0; i < arguments.length; i++) {
|
1461 |
+
// any "false" to this function means no animations
|
1462 |
+
if (arguments[i] === false) {
|
1463 |
+
useAnimation = false
|
1464 |
+
continue
|
1465 |
+
}
|
1466 |
+
|
1467 |
+
// skip invalid arguments
|
1468 |
+
if (!validMove(arguments[i])) {
|
1469 |
+
error(2826, 'Invalid move passed to the move method.', arguments[i])
|
1470 |
+
continue
|
1471 |
+
}
|
1472 |
+
|
1473 |
+
var tmp = arguments[i].split('-')
|
1474 |
+
moves[tmp[0]] = tmp[1]
|
1475 |
+
}
|
1476 |
+
|
1477 |
+
// calculate position from moves
|
1478 |
+
var newPos = calculatePositionFromMoves(currentPosition, moves)
|
1479 |
+
|
1480 |
+
// update the board
|
1481 |
+
widget.position(newPos, useAnimation)
|
1482 |
+
|
1483 |
+
// return the new position object
|
1484 |
+
return newPos
|
1485 |
+
}
|
1486 |
+
|
1487 |
+
widget.orientation = function (arg) {
|
1488 |
+
// no arguments, return the current orientation
|
1489 |
+
if (arguments.length === 0) {
|
1490 |
+
return currentOrientation
|
1491 |
+
}
|
1492 |
+
|
1493 |
+
// set to white or black
|
1494 |
+
if (arg === 'white' || arg === 'black') {
|
1495 |
+
currentOrientation = arg
|
1496 |
+
drawBoard()
|
1497 |
+
return currentOrientation
|
1498 |
+
}
|
1499 |
+
|
1500 |
+
// flip orientation
|
1501 |
+
if (arg === 'flip') {
|
1502 |
+
currentOrientation = currentOrientation === 'white' ? 'black' : 'white'
|
1503 |
+
drawBoard()
|
1504 |
+
return currentOrientation
|
1505 |
+
}
|
1506 |
+
|
1507 |
+
error(5482, 'Invalid value passed to the orientation method.', arg)
|
1508 |
+
}
|
1509 |
+
|
1510 |
+
widget.position = function (position, useAnimation) {
|
1511 |
+
// no arguments, return the current position
|
1512 |
+
if (arguments.length === 0) {
|
1513 |
+
return deepCopy(currentPosition)
|
1514 |
+
}
|
1515 |
+
|
1516 |
+
// get position as FEN
|
1517 |
+
if (isString(position) && position.toLowerCase() === 'fen') {
|
1518 |
+
return objToFen(currentPosition)
|
1519 |
+
}
|
1520 |
+
|
1521 |
+
// start position
|
1522 |
+
if (isString(position) && position.toLowerCase() === 'start') {
|
1523 |
+
position = deepCopy(START_POSITION)
|
1524 |
+
}
|
1525 |
+
|
1526 |
+
// convert FEN to position object
|
1527 |
+
if (validFen(position)) {
|
1528 |
+
position = fenToObj(position)
|
1529 |
+
}
|
1530 |
+
|
1531 |
+
// validate position object
|
1532 |
+
if (!validPositionObject(position)) {
|
1533 |
+
error(6482, 'Invalid value passed to the position method.', position)
|
1534 |
+
return
|
1535 |
+
}
|
1536 |
+
|
1537 |
+
// default for useAnimations is true
|
1538 |
+
if (useAnimation !== false) useAnimation = true
|
1539 |
+
|
1540 |
+
if (useAnimation) {
|
1541 |
+
// start the animations
|
1542 |
+
var animations = calculateAnimations(currentPosition, position)
|
1543 |
+
doAnimations(animations, currentPosition, position)
|
1544 |
+
|
1545 |
+
// set the new position
|
1546 |
+
setCurrentPosition(position)
|
1547 |
+
} else {
|
1548 |
+
// instant update
|
1549 |
+
setCurrentPosition(position)
|
1550 |
+
drawPositionInstant()
|
1551 |
+
}
|
1552 |
+
}
|
1553 |
+
|
1554 |
+
widget.resize = function () {
|
1555 |
+
// calulate the new square size
|
1556 |
+
squareSize = calculateSquareSize()
|
1557 |
+
|
1558 |
+
// set board width
|
1559 |
+
$board.css('width', squareSize * 8 + 'px')
|
1560 |
+
|
1561 |
+
// set drag piece size
|
1562 |
+
$draggedPiece.css({
|
1563 |
+
height: squareSize,
|
1564 |
+
width: squareSize
|
1565 |
+
})
|
1566 |
+
|
1567 |
+
// spare pieces
|
1568 |
+
if (config.sparePieces) {
|
1569 |
+
$container
|
1570 |
+
.find('.' + CSS.sparePieces)
|
1571 |
+
.css('paddingLeft', squareSize + boardBorderSize + 'px')
|
1572 |
+
}
|
1573 |
+
|
1574 |
+
// redraw the board
|
1575 |
+
drawBoard()
|
1576 |
+
}
|
1577 |
+
|
1578 |
+
// set the starting position
|
1579 |
+
widget.start = function (useAnimation) {
|
1580 |
+
widget.position('start', useAnimation)
|
1581 |
+
}
|
1582 |
+
|
1583 |
+
// -------------------------------------------------------------------------
|
1584 |
+
// Browser Events
|
1585 |
+
// -------------------------------------------------------------------------
|
1586 |
+
|
1587 |
+
function stopDefault (evt) {
|
1588 |
+
evt.preventDefault()
|
1589 |
+
}
|
1590 |
+
|
1591 |
+
function mousedownSquare (evt) {
|
1592 |
+
// do nothing if we're not draggable
|
1593 |
+
if (!config.draggable) return
|
1594 |
+
|
1595 |
+
// do nothing if there is no piece on this square
|
1596 |
+
var square = $(this).attr('data-square')
|
1597 |
+
if (!validSquare(square)) return
|
1598 |
+
if (!currentPosition.hasOwnProperty(square)) return
|
1599 |
+
|
1600 |
+
beginDraggingPiece(square, currentPosition[square], evt.pageX, evt.pageY)
|
1601 |
+
}
|
1602 |
+
|
1603 |
+
function touchstartSquare (e) {
|
1604 |
+
// do nothing if we're not draggable
|
1605 |
+
if (!config.draggable) return
|
1606 |
+
|
1607 |
+
// do nothing if there is no piece on this square
|
1608 |
+
var square = $(this).attr('data-square')
|
1609 |
+
if (!validSquare(square)) return
|
1610 |
+
if (!currentPosition.hasOwnProperty(square)) return
|
1611 |
+
|
1612 |
+
e = e.originalEvent
|
1613 |
+
beginDraggingPiece(
|
1614 |
+
square,
|
1615 |
+
currentPosition[square],
|
1616 |
+
e.changedTouches[0].pageX,
|
1617 |
+
e.changedTouches[0].pageY
|
1618 |
+
)
|
1619 |
+
}
|
1620 |
+
|
1621 |
+
function mousedownSparePiece (evt) {
|
1622 |
+
// do nothing if sparePieces is not enabled
|
1623 |
+
if (!config.sparePieces) return
|
1624 |
+
|
1625 |
+
var piece = $(this).attr('data-piece')
|
1626 |
+
|
1627 |
+
beginDraggingPiece('spare', piece, evt.pageX, evt.pageY)
|
1628 |
+
}
|
1629 |
+
|
1630 |
+
function touchstartSparePiece (e) {
|
1631 |
+
// do nothing if sparePieces is not enabled
|
1632 |
+
if (!config.sparePieces) return
|
1633 |
+
|
1634 |
+
var piece = $(this).attr('data-piece')
|
1635 |
+
|
1636 |
+
e = e.originalEvent
|
1637 |
+
beginDraggingPiece(
|
1638 |
+
'spare',
|
1639 |
+
piece,
|
1640 |
+
e.changedTouches[0].pageX,
|
1641 |
+
e.changedTouches[0].pageY
|
1642 |
+
)
|
1643 |
+
}
|
1644 |
+
|
1645 |
+
function mousemoveWindow (evt) {
|
1646 |
+
if (isDragging) {
|
1647 |
+
updateDraggedPiece(evt.pageX, evt.pageY)
|
1648 |
+
}
|
1649 |
+
}
|
1650 |
+
|
1651 |
+
var throttledMousemoveWindow = throttle(mousemoveWindow, config.dragThrottleRate)
|
1652 |
+
|
1653 |
+
function touchmoveWindow (evt) {
|
1654 |
+
// do nothing if we are not dragging a piece
|
1655 |
+
if (!isDragging) return
|
1656 |
+
|
1657 |
+
// prevent screen from scrolling
|
1658 |
+
evt.preventDefault()
|
1659 |
+
|
1660 |
+
updateDraggedPiece(evt.originalEvent.changedTouches[0].pageX,
|
1661 |
+
evt.originalEvent.changedTouches[0].pageY)
|
1662 |
+
}
|
1663 |
+
|
1664 |
+
var throttledTouchmoveWindow = throttle(touchmoveWindow, config.dragThrottleRate)
|
1665 |
+
|
1666 |
+
function mouseupWindow (evt) {
|
1667 |
+
// do nothing if we are not dragging a piece
|
1668 |
+
if (!isDragging) return
|
1669 |
+
|
1670 |
+
// get the location
|
1671 |
+
var location = isXYOnSquare(evt.pageX, evt.pageY)
|
1672 |
+
|
1673 |
+
stopDraggedPiece(location)
|
1674 |
+
}
|
1675 |
+
|
1676 |
+
function touchendWindow (evt) {
|
1677 |
+
// do nothing if we are not dragging a piece
|
1678 |
+
if (!isDragging) return
|
1679 |
+
|
1680 |
+
// get the location
|
1681 |
+
var location = isXYOnSquare(evt.originalEvent.changedTouches[0].pageX,
|
1682 |
+
evt.originalEvent.changedTouches[0].pageY)
|
1683 |
+
|
1684 |
+
stopDraggedPiece(location)
|
1685 |
+
}
|
1686 |
+
|
1687 |
+
function mouseenterSquare (evt) {
|
1688 |
+
// do not fire this event if we are dragging a piece
|
1689 |
+
// NOTE: this should never happen, but it's a safeguard
|
1690 |
+
if (isDragging) return
|
1691 |
+
|
1692 |
+
// exit if they did not provide a onMouseoverSquare function
|
1693 |
+
if (!isFunction(config.onMouseoverSquare)) return
|
1694 |
+
|
1695 |
+
// get the square
|
1696 |
+
var square = $(evt.currentTarget).attr('data-square')
|
1697 |
+
|
1698 |
+
// NOTE: this should never happen; defensive
|
1699 |
+
if (!validSquare(square)) return
|
1700 |
+
|
1701 |
+
// get the piece on this square
|
1702 |
+
var piece = false
|
1703 |
+
if (currentPosition.hasOwnProperty(square)) {
|
1704 |
+
piece = currentPosition[square]
|
1705 |
+
}
|
1706 |
+
|
1707 |
+
// execute their function
|
1708 |
+
config.onMouseoverSquare(square, piece, deepCopy(currentPosition), currentOrientation)
|
1709 |
+
}
|
1710 |
+
|
1711 |
+
function mouseleaveSquare (evt) {
|
1712 |
+
// do not fire this event if we are dragging a piece
|
1713 |
+
// NOTE: this should never happen, but it's a safeguard
|
1714 |
+
if (isDragging) return
|
1715 |
+
|
1716 |
+
// exit if they did not provide an onMouseoutSquare function
|
1717 |
+
if (!isFunction(config.onMouseoutSquare)) return
|
1718 |
+
|
1719 |
+
// get the square
|
1720 |
+
var square = $(evt.currentTarget).attr('data-square')
|
1721 |
+
|
1722 |
+
// NOTE: this should never happen; defensive
|
1723 |
+
if (!validSquare(square)) return
|
1724 |
+
|
1725 |
+
// get the piece on this square
|
1726 |
+
var piece = false
|
1727 |
+
if (currentPosition.hasOwnProperty(square)) {
|
1728 |
+
piece = currentPosition[square]
|
1729 |
+
}
|
1730 |
+
|
1731 |
+
// execute their function
|
1732 |
+
config.onMouseoutSquare(square, piece, deepCopy(currentPosition), currentOrientation)
|
1733 |
+
}
|
1734 |
+
|
1735 |
+
// -------------------------------------------------------------------------
|
1736 |
+
// Initialization
|
1737 |
+
// -------------------------------------------------------------------------
|
1738 |
+
|
1739 |
+
function addEvents () {
|
1740 |
+
// prevent "image drag"
|
1741 |
+
$('body').on('mousedown mousemove', '.' + CSS.piece, stopDefault)
|
1742 |
+
|
1743 |
+
// mouse drag pieces
|
1744 |
+
$board.on('mousedown', '.' + CSS.square, mousedownSquare)
|
1745 |
+
$container.on('mousedown', '.' + CSS.sparePieces + ' .' + CSS.piece, mousedownSparePiece)
|
1746 |
+
|
1747 |
+
// mouse enter / leave square
|
1748 |
+
$board
|
1749 |
+
.on('mouseenter', '.' + CSS.square, mouseenterSquare)
|
1750 |
+
.on('mouseleave', '.' + CSS.square, mouseleaveSquare)
|
1751 |
+
|
1752 |
+
// piece drag
|
1753 |
+
var $window = $(window)
|
1754 |
+
$window
|
1755 |
+
.on('mousemove', throttledMousemoveWindow)
|
1756 |
+
.on('mouseup', mouseupWindow)
|
1757 |
+
|
1758 |
+
// touch drag pieces
|
1759 |
+
if (isTouchDevice()) {
|
1760 |
+
$board.on('touchstart', '.' + CSS.square, touchstartSquare)
|
1761 |
+
$container.on('touchstart', '.' + CSS.sparePieces + ' .' + CSS.piece, touchstartSparePiece)
|
1762 |
+
$window
|
1763 |
+
.on('touchmove', throttledTouchmoveWindow)
|
1764 |
+
.on('touchend', touchendWindow)
|
1765 |
+
}
|
1766 |
+
}
|
1767 |
+
|
1768 |
+
function initDOM () {
|
1769 |
+
// create unique IDs for all the elements we will create
|
1770 |
+
createElIds()
|
1771 |
+
|
1772 |
+
// build board and save it in memory
|
1773 |
+
$container.html(buildContainerHTML(config.sparePieces))
|
1774 |
+
$board = $container.find('.' + CSS.board)
|
1775 |
+
|
1776 |
+
if (config.sparePieces) {
|
1777 |
+
$sparePiecesTop = $container.find('.' + CSS.sparePiecesTop)
|
1778 |
+
$sparePiecesBottom = $container.find('.' + CSS.sparePiecesBottom)
|
1779 |
+
}
|
1780 |
+
|
1781 |
+
// create the drag piece
|
1782 |
+
var draggedPieceId = uuid()
|
1783 |
+
$('body').append(buildPieceHTML('wP', true, draggedPieceId))
|
1784 |
+
$draggedPiece = $('#' + draggedPieceId)
|
1785 |
+
|
1786 |
+
// TODO: need to remove this dragged piece element if the board is no
|
1787 |
+
// longer in the DOM
|
1788 |
+
|
1789 |
+
// get the border size
|
1790 |
+
boardBorderSize = parseInt($board.css('borderLeftWidth'), 10)
|
1791 |
+
|
1792 |
+
// set the size and draw the board
|
1793 |
+
widget.resize()
|
1794 |
+
}
|
1795 |
+
|
1796 |
+
// -------------------------------------------------------------------------
|
1797 |
+
// Initialization
|
1798 |
+
// -------------------------------------------------------------------------
|
1799 |
+
|
1800 |
+
setInitialState()
|
1801 |
+
initDOM()
|
1802 |
+
addEvents()
|
1803 |
+
|
1804 |
+
// return the widget object
|
1805 |
+
return widget
|
1806 |
+
} // end constructor
|
1807 |
+
|
1808 |
+
// TODO: do module exports here
|
1809 |
+
window['Chessboard'] = constructor
|
1810 |
+
|
1811 |
+
// support legacy ChessBoard name
|
1812 |
+
window['ChessBoard'] = window['Chessboard']
|
1813 |
+
|
1814 |
+
// expose util functions
|
1815 |
+
window['Chessboard']['fenToObj'] = fenToObj
|
1816 |
+
window['Chessboard']['objToFen'] = objToFen
|
1817 |
+
})() // end anonymous wrapper
|
js/chessboard-1.0.0.min.js
ADDED
@@ -0,0 +1,2 @@
|
|
|
|
|
|
|
1 |
+
/*! chessboard.js v1.0.0 | (c) 2019 Chris Oakman | MIT License chessboardjs.com/license */
|
2 |
+
!function(){"use strict";var z=window.jQuery,F="abcdefgh".split(""),r=20,A="…",W="1.8.3",e="rnbqkbnr/pppppppp/8/8/8/8/PPPPPPPP/RNBQKBNR",G=pe(e),n=200,t=200,o=60,a=30,i=100,H={};function V(e,r,n){function t(){o=0,a&&(a=!1,s())}var o=0,a=!1,i=[],s=function(){o=window.setTimeout(t,r),e.apply(n,i)};return function(e){i=arguments,o?a=!0:s()}}function Z(){return"xxxx-xxxx-xxxx-xxxx-xxxx-xxxx-xxxx-xxxx".replace(/x/g,function(e){return(16*Math.random()|0).toString(16)})}function _(e){return JSON.parse(JSON.stringify(e))}function s(e){var r=e.split(".");return{major:parseInt(r[0],10),minor:parseInt(r[1],10),patch:parseInt(r[2],10)}}function ee(e,r){for(var n in r)if(r.hasOwnProperty(n))for(var t="{"+n+"}",o=r[n];-1!==e.indexOf(t);)e=e.replace(t,o);return e}function re(e){return"string"==typeof e}function ne(e){return"function"==typeof e}function p(e){return"number"==typeof e&&isFinite(e)&&Math.floor(e)===e}function c(e){return"fast"===e||"slow"===e||!!p(e)&&0<=e}function te(e){if(!re(e))return!1;var r=e.split("-");return 2===r.length&&(oe(r[0])&&oe(r[1]))}function oe(e){return re(e)&&-1!==e.search(/^[a-h][1-8]$/)}function u(e){return re(e)&&-1!==e.search(/^[bw][KQRNBP]$/)}function ae(e){if(!re(e))return!1;var r=(e=function(e){return e.replace(/8/g,"11111111").replace(/7/g,"1111111").replace(/6/g,"111111").replace(/5/g,"11111").replace(/4/g,"1111").replace(/3/g,"111").replace(/2/g,"11")}(e=e.replace(/ .+$/,""))).split("/");if(8!==r.length)return!1;for(var n=0;n<8;n++)if(8!==r[n].length||-1!==r[n].search(/[^kqrnbpKQRNBP1]/))return!1;return!0}function ie(e){if(!z.isPlainObject(e))return!1;for(var r in e)if(e.hasOwnProperty(r)&&(!oe(r)||!u(e[r])))return!1;return!0}function se(){return typeof window.$&&z.fn&&z.fn.jquery&&function(e,r){e=s(e),r=s(r);var n=1e5*e.major*1e5+1e5*e.minor+e.patch;return 1e5*r.major*1e5+1e5*r.minor+r.patch<=n}(z.fn.jquery,W)}function pe(e){if(!ae(e))return!1;for(var r,n=(e=e.replace(/ .+$/,"")).split("/"),t={},o=8,a=0;a<8;a++){for(var i=n[a].split(""),s=0,p=0;p<i.length;p++){if(-1!==i[p].search(/[1-8]/))s+=parseInt(i[p],10);else t[F[s]+o]=(r=i[p]).toLowerCase()===r?"b"+r.toUpperCase():"w"+r.toUpperCase(),s+=1}o-=1}return t}function ce(e){if(!ie(e))return!1;for(var r,n,t="",o=8,a=0;a<8;a++){for(var i=0;i<8;i++){var s=F[i]+o;e.hasOwnProperty(s)?t+=(r=e[s],n=void 0,"w"===(n=r.split(""))[0]?n[1].toUpperCase():n[1].toLowerCase()):t+="1"}7!==a&&(t+="/"),o-=1}return t=function(e){return e.replace(/11111111/g,"8").replace(/1111111/g,"7").replace(/111111/g,"6").replace(/11111/g,"5").replace(/1111/g,"4").replace(/111/g,"3").replace(/11/g,"2")}(t)}function ue(e,r,n){for(var t=function(e){for(var r=[],n=0;n<8;n++)for(var t=0;t<8;t++){var o=F[n]+(t+1);e!==o&&r.push({square:o,distance:(a=e,i=o,void 0,void 0,void 0,void 0,void 0,void 0,void 0,void 0,s=a.split(""),p=F.indexOf(s[0])+1,c=parseInt(s[1],10),u=i.split(""),f=F.indexOf(u[0])+1,d=parseInt(u[1],10),h=Math.abs(p-f),l=Math.abs(c-d),l<=h?h:l)})}var a,i,s,p,c,u,f,d,h,l;r.sort(function(e,r){return e.distance-r.distance});var v=[];for(n=0;n<r.length;n++)v.push(r[n].square);return v}(n),o=0;o<t.length;o++){var a=t[o];if(e.hasOwnProperty(a)&&e[a]===r)return a}return!1}function fe(e){return"black"!==e.orientation&&(e.orientation="white"),!1!==e.showNotation&&(e.showNotation=!0),!0!==e.draggable&&(e.draggable=!1),"trash"!==e.dropOffBoard&&(e.dropOffBoard="snapback"),!0!==e.sparePieces&&(e.sparePieces=!1),e.sparePieces&&(e.draggable=!0),e.hasOwnProperty("pieceTheme")&&(re(e.pieceTheme)||ne(e.pieceTheme))||(e.pieceTheme="img/chesspieces/wikipedia/{piece}.png"),c(e.appearSpeed)||(e.appearSpeed=n),c(e.moveSpeed)||(e.moveSpeed=t),c(e.snapbackSpeed)||(e.snapbackSpeed=o),c(e.snapSpeed)||(e.snapSpeed=a),c(e.trashSpeed)||(e.trashSpeed=i),function(e){return p(e)&&1<=e}(e.dragThrottleRate)||(e.dragThrottleRate=r),e}H.alpha="alpha-d2270",H.black="black-3c85d",H.board="board-b72b1",H.chessboard="chessboard-63f37",H.clearfix="clearfix-7da63",H.highlight1="highlight1-32417",H.highlight2="highlight2-9c5d2",H.notation="notation-322f9",H.numeric="numeric-fc462",H.piece="piece-417db",H.row="row-5277c",H.sparePieces="spare-pieces-7492f",H.sparePiecesBottom="spare-pieces-bottom-ae20f",H.sparePiecesTop="spare-pieces-top-4028b",H.square="square-55d63",H.white="white-1e1d7",window.Chessboard=function(e,f){if(!function(){if(se())return!0;var e="Chessboard Error 1005: Unable to find a valid version of jQuery. Please include jQuery "+W+" or higher on the page\n\nExiting"+A;return window.alert(e),!1}())return null;var n=function(e){if(""===e){var r="Chessboard Error 1001: The first argument to Chessboard() cannot be an empty string.\n\nExiting"+A;return window.alert(r),!1}re(e)&&"#"!==e.charAt(0)&&(e="#"+e);var n=z(e);if(1===n.length)return n;var t="Chessboard Error 1003: The first argument to Chessboard() must be the ID of a DOM node, an ID query selector, or a single DOM node.\n\nExiting"+A;return window.alert(t),!1}(e);if(!n)return null;f=fe(f=function(e){return"start"===e?e={position:_(G)}:ae(e)?e={position:pe(e)}:ie(e)&&(e={position:_(e)}),z.isPlainObject(e)||(e={}),e}(f));var r=null,a=null,t=null,o=null,i={},s=2,p="white",c={},u=null,d=null,h=null,l=!1,v={},g={},w={},b=16;function m(e,r,n){if(!0===f.hasOwnProperty("showErrors")&&!1!==f.showErrors){var t="Chessboard Error "+e+": "+r;return"console"===f.showErrors&&"object"==typeof console&&"function"==typeof console.log?(console.log(t),void(2<=arguments.length&&console.log(n))):"alert"===f.showErrors?(n&&(t+="\n\n"+JSON.stringify(n)),void window.alert(t)):void(ne(f.showErrors)&&f.showErrors(e,r,n))}}function P(e){return ne(f.pieceTheme)?f.pieceTheme(e):re(f.pieceTheme)?ee(f.pieceTheme,{piece:e}):(m(8272,"Unable to build image source for config.pieceTheme."),"")}function y(e,r,n){var t='<img src="'+P(e)+'" ';return re(n)&&""!==n&&(t+='id="'+n+'" '),t+='alt="" class="{piece}" data-piece="'+e+'" style="width:'+b+"px;height:"+b+"px;",r&&(t+="display:none;"),ee(t+='" />',H)}function x(e){var r=["wK","wQ","wR","wB","wN","wP"];"black"===e&&(r=["bK","bQ","bR","bB","bN","bP"]);for(var n="",t=0;t<r.length;t++)n+=y(r[t],!1,v[r[t]]);return n}function O(e,r,n,t){var o=z("#"+g[e]),a=o.offset(),i=z("#"+g[r]),s=i.offset(),p=Z();z("body").append(y(n,!0,p));var c=z("#"+p);c.css({display:"",position:"absolute",top:a.top,left:a.left}),o.find("."+H.piece).remove();var u={duration:f.moveSpeed,complete:function(){i.append(y(n)),c.remove(),ne(t)&&t()}};c.animate(s,u)}function S(e,r,n){var t=z("#"+v[e]).offset(),o=z("#"+g[r]),a=o.offset(),i=Z();z("body").append(y(e,!0,i));var s=z("#"+i);s.css({display:"",position:"absolute",left:t.left,top:t.top});var p={duration:f.moveSpeed,complete:function(){o.find("."+H.piece).remove(),o.append(y(e)),s.remove(),ne(n)&&n()}};s.animate(a,p)}function T(){for(var e in r.find("."+H.piece).remove(),c)c.hasOwnProperty(e)&&z("#"+g[e]).append(y(c[e]))}function q(){r.html(function(e){"black"!==e&&(e="white");var r="",n=_(F),t=8;"black"===e&&(n.reverse(),t=1);for(var o="white",a=0;a<8;a++){r+='<div class="{row}">';for(var i=0;i<8;i++){var s=n[i]+t;r+='<div class="{square} '+H[o]+" square-"+s+'" style="width:'+b+"px;height:"+b+'px;" id="'+g[s]+'" data-square="'+s+'">',f.showNotation&&(("white"===e&&1===t||"black"===e&&8===t)&&(r+='<div class="{notation} {alpha}">'+n[i]+"</div>"),0===i&&(r+='<div class="{notation} {numeric}">'+t+"</div>")),r+="</div>",o="white"===o?"black":"white"}r+='<div class="{clearfix}"></div></div>',o="white"===o?"black":"white","white"===e?t-=1:t+=1}return ee(r,H)}(p,f.showNotation)),T(),f.sparePieces&&("white"===p?(t.html(x("black")),o.html(x("white"))):(t.html(x("white")),o.html(x("black"))))}function k(e){var r=_(c),n=_(e);ce(r)!==ce(n)&&(ne(f.onChange)&&f.onChange(r,n),c=e)}function E(e,r){for(var n in w)if(w.hasOwnProperty(n)){var t=w[n];if(e>=t.left&&e<t.left+b&&r>=t.top&&r<t.top+b)return n}return"offboard"}function C(){r.find("."+H.square).removeClass(H.highlight1+" "+H.highlight2)}function B(){C();var e=_(c);delete e[h],k(e),T(),a.fadeOut(f.trashSpeed),l=!1}function I(e,r,n,t){ne(f.onDragStart)&&!1===f.onDragStart(e,r,_(c),p)||(l=!0,u=r,d="spare"===(h=e)?"offboard":e,function(){for(var e in w={},g)g.hasOwnProperty(e)&&(w[e]=z("#"+g[e]).offset())}(),a.attr("src",P(r)).css({display:"",position:"absolute",left:n-b/2,top:t-b/2}),"spare"!==e&&z("#"+g[e]).addClass(H.highlight1).find("."+H.piece).css("display","none"))}function M(e,r){a.css({left:e-b/2,top:r-b/2});var n=E(e,r);n!==d&&(oe(d)&&z("#"+g[d]).removeClass(H.highlight2),oe(n)&&z("#"+g[n]).addClass(H.highlight2),ne(f.onDragMove)&&f.onDragMove(n,d,h,u,_(c),p),d=n)}function N(e){var r="drop";if("offboard"===e&&"snapback"===f.dropOffBoard&&(r="snapback"),"offboard"===e&&"trash"===f.dropOffBoard&&(r="trash"),ne(f.onDrop)){var n=_(c);"spare"===h&&oe(e)&&(n[e]=u),oe(h)&&"offboard"===e&&delete n[h],oe(h)&&oe(e)&&(delete n[h],n[e]=u);var t=_(c),o=f.onDrop(h,e,u,n,t,p);"snapback"!==o&&"trash"!==o||(r=o)}"snapback"===r?function(){if("spare"!==h){C();var e=z("#"+g[h]).offset(),r={duration:f.snapbackSpeed,complete:function(){T(),a.css("display","none"),ne(f.onSnapbackEnd)&&f.onSnapbackEnd(u,h,_(c),p)}};a.animate(e,r),l=!1}else B()}():"trash"===r?B():"drop"===r&&function(e){C();var r=_(c);delete r[h],r[e]=u,k(r);var n=z("#"+g[e]).offset(),t={duration:f.snapSpeed,complete:function(){T(),a.css("display","none"),ne(f.onSnapEnd)&&f.onSnapEnd(h,e,u)}};a.animate(n,t),l=!1}(e)}function j(e){e.preventDefault()}function D(e){if(f.draggable){var r=z(this).attr("data-square");oe(r)&&c.hasOwnProperty(r)&&I(r,c[r],e.pageX,e.pageY)}}function R(e){if(f.draggable){var r=z(this).attr("data-square");oe(r)&&c.hasOwnProperty(r)&&(e=e.originalEvent,I(r,c[r],e.changedTouches[0].pageX,e.changedTouches[0].pageY))}}function Q(e){f.sparePieces&&I("spare",z(this).attr("data-piece"),e.pageX,e.pageY)}function X(e){f.sparePieces&&I("spare",z(this).attr("data-piece"),(e=e.originalEvent).changedTouches[0].pageX,e.changedTouches[0].pageY)}i.clear=function(e){i.position({},e)},i.destroy=function(){n.html(""),a.remove(),n.unbind()},i.fen=function(){return i.position("fen")},i.flip=function(){return i.orientation("flip")},i.move=function(){if(0!==arguments.length){for(var e=!0,r={},n=0;n<arguments.length;n++)if(!1!==arguments[n])if(te(arguments[n])){var t=arguments[n].split("-");r[t[0]]=t[1]}else m(2826,"Invalid move passed to the move method.",arguments[n]);else e=!1;var o=function(e,r){var n=_(e);for(var t in r)if(r.hasOwnProperty(t)&&n.hasOwnProperty(t)){var o=n[t];delete n[t],n[r[t]]=o}return n}(c,r);return i.position(o,e),o}},i.orientation=function(e){return 0===arguments.length?p:"white"===e||"black"===e?(p=e,q(),p):"flip"===e?(p="white"===p?"black":"white",q(),p):void m(5482,"Invalid value passed to the orientation method.",e)},i.position=function(e,r){if(0===arguments.length)return _(c);if(re(e)&&"fen"===e.toLowerCase())return ce(c);(re(e)&&"start"===e.toLowerCase()&&(e=_(G)),ae(e)&&(e=pe(e)),ie(e))?(!1!==r&&(r=!0),r?(function(e,r,n){if(0!==e.length)for(var t=0,o=0;o<e.length;o++){var a=e[o];"clear"===a.type?z("#"+g[a.square]+" ."+H.piece).fadeOut(f.trashSpeed,i):"add"!==a.type||f.sparePieces?"add"===a.type&&f.sparePieces?S(a.piece,a.square,i):"move"===a.type&&O(a.source,a.destination,a.piece,i):z("#"+g[a.square]).append(y(a.piece,!0)).find("."+H.piece).fadeIn(f.appearSpeed,i)}function i(){(t+=1)===e.length&&(T(),ne(f.onMoveEnd)&&f.onMoveEnd(_(r),_(n)))}}(function(e,r){e=_(e),r=_(r);var n=[],t={};for(var o in r)r.hasOwnProperty(o)&&e.hasOwnProperty(o)&&e[o]===r[o]&&(delete e[o],delete r[o]);for(o in r)if(r.hasOwnProperty(o)){var a=ue(e,r[o],o);a&&(n.push({type:"move",source:a,destination:o,piece:r[o]}),delete e[a],delete r[o],t[o]=!0)}for(o in r)r.hasOwnProperty(o)&&(n.push({type:"add",square:o,piece:r[o]}),delete r[o]);for(o in e)e.hasOwnProperty(o)&&(t.hasOwnProperty(o)||(n.push({type:"clear",square:o,piece:e[o]}),delete e[o]));return n}(c,e),c,e),k(e)):(k(e),T())):m(6482,"Invalid value passed to the position method.",e)},i.resize=function(){b=function(){var e=parseInt(n.width(),10);if(!e||e<=0)return 0;for(var r=e-1;r%8!=0&&0<r;)r-=1;return r/8}(),r.css("width",8*b+"px"),a.css({height:b,width:b}),f.sparePieces&&n.find("."+H.sparePieces).css("paddingLeft",b+s+"px"),q()},i.start=function(e){i.position("start",e)};var Y=V(function(e){l&&M(e.pageX,e.pageY)},f.dragThrottleRate),K=V(function(e){l&&(e.preventDefault(),M(e.originalEvent.changedTouches[0].pageX,e.originalEvent.changedTouches[0].pageY))},f.dragThrottleRate);function L(e){l&&N(E(e.pageX,e.pageY))}function U(e){l&&N(E(e.originalEvent.changedTouches[0].pageX,e.originalEvent.changedTouches[0].pageY))}function $(e){if(!l&&ne(f.onMouseoverSquare)){var r=z(e.currentTarget).attr("data-square");if(oe(r)){var n=!1;c.hasOwnProperty(r)&&(n=c[r]),f.onMouseoverSquare(r,n,_(c),p)}}}function J(e){if(!l&&ne(f.onMouseoutSquare)){var r=z(e.currentTarget).attr("data-square");if(oe(r)){var n=!1;c.hasOwnProperty(r)&&(n=c[r]),f.onMouseoutSquare(r,n,_(c),p)}}}return p=f.orientation,f.hasOwnProperty("position")&&("start"===f.position?c=_(G):ae(f.position)?c=pe(f.position):ie(f.position)?c=_(f.position):m(7263,"Invalid value passed to config.position.",f.position)),function(){!function(){for(var e=0;e<F.length;e++)for(var r=1;r<=8;r++){var n=F[e]+r;g[n]=n+"-"+Z()}var t="KQRNBP".split("");for(e=0;e<t.length;e++){var o="w"+t[e],a="b"+t[e];v[o]=o+"-"+Z(),v[a]=a+"-"+Z()}}(),n.html(function(e){var r='<div class="{chessboard}">';return e&&(r+='<div class="{sparePieces} {sparePiecesTop}"></div>'),r+='<div class="{board}"></div>',e&&(r+='<div class="{sparePieces} {sparePiecesBottom}"></div>'),ee(r+="</div>",H)}(f.sparePieces)),r=n.find("."+H.board),f.sparePieces&&(t=n.find("."+H.sparePiecesTop),o=n.find("."+H.sparePiecesBottom));var e=Z();z("body").append(y("wP",!0,e)),a=z("#"+e),s=parseInt(r.css("borderLeftWidth"),10),i.resize()}(),function(){z("body").on("mousedown mousemove","."+H.piece,j),r.on("mousedown","."+H.square,D),n.on("mousedown","."+H.sparePieces+" ."+H.piece,Q),r.on("mouseenter","."+H.square,$).on("mouseleave","."+H.square,J);var e=z(window);e.on("mousemove",Y).on("mouseup",L),"ontouchstart"in document.documentElement&&(r.on("touchstart","."+H.square,R),n.on("touchstart","."+H.sparePieces+" ."+H.piece,X),e.on("touchmove",K).on("touchend",U))}(),i},window.ChessBoard=window.Chessboard,window.Chessboard.fenToObj=pe,window.Chessboard.objToFen=ce}();
|
helpers.js → js/helpers.js
RENAMED
@@ -8,7 +8,7 @@ function convertTypedArray(src, type) {
|
|
8 |
|
9 |
var printTextarea = (function() {
|
10 |
var element = document.getElementById('output');
|
11 |
-
if (element) element.
|
12 |
return function(text) {
|
13 |
if (arguments.length > 1) text = Array.prototype.slice.call(arguments).join(' ');
|
14 |
console.log(text);
|
@@ -22,6 +22,7 @@ var printTextarea = (function() {
|
|
22 |
async function clearCache() {
|
23 |
if (confirm('Are you sure you want to clear the cache?\nAll the models will be downloaded again.')) {
|
24 |
indexedDB.deleteDatabase(dbName);
|
|
|
25 |
}
|
26 |
}
|
27 |
|
@@ -88,11 +89,15 @@ async function fetchRemote(url, cbProgress, cbPrint) {
|
|
88 |
// - check if the data is already in the IndexedDB
|
89 |
// - if not, fetch it from the remote URL and store it in the IndexedDB
|
90 |
function loadRemote(url, dst, size_mb, cbProgress, cbReady, cbCancel, cbPrint) {
|
91 |
-
|
92 |
-
|
93 |
-
|
94 |
-
|
95 |
-
|
|
|
|
|
|
|
|
|
96 |
|
97 |
// check if the data is already in the IndexedDB
|
98 |
var rq = indexedDB.open(dbName, dbVersion);
|
@@ -141,7 +146,15 @@ function loadRemote(url, dst, size_mb, cbProgress, cbReady, cbCancel, cbPrint) {
|
|
141 |
var db = event.target.result;
|
142 |
var tx = db.transaction(['models'], 'readwrite');
|
143 |
var os = tx.objectStore('models');
|
144 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
145 |
|
146 |
rq.onsuccess = function (event) {
|
147 |
cbPrint('loadRemote: "' + url + '" stored in the IndexedDB');
|
@@ -176,7 +189,6 @@ function loadRemote(url, dst, size_mb, cbProgress, cbReady, cbCancel, cbPrint) {
|
|
176 |
|
177 |
rq.onabort = function (event) {
|
178 |
cbPrint('loadRemote: failed to open IndexedDB: abort');
|
179 |
-
|
180 |
};
|
181 |
}
|
182 |
-
|
|
|
8 |
|
9 |
var printTextarea = (function() {
|
10 |
var element = document.getElementById('output');
|
11 |
+
if (element) element.value = ''; // clear browser cache
|
12 |
return function(text) {
|
13 |
if (arguments.length > 1) text = Array.prototype.slice.call(arguments).join(' ');
|
14 |
console.log(text);
|
|
|
22 |
async function clearCache() {
|
23 |
if (confirm('Are you sure you want to clear the cache?\nAll the models will be downloaded again.')) {
|
24 |
indexedDB.deleteDatabase(dbName);
|
25 |
+
location.reload();
|
26 |
}
|
27 |
}
|
28 |
|
|
|
89 |
// - check if the data is already in the IndexedDB
|
90 |
// - if not, fetch it from the remote URL and store it in the IndexedDB
|
91 |
function loadRemote(url, dst, size_mb, cbProgress, cbReady, cbCancel, cbPrint) {
|
92 |
+
if (!navigator.storage || !navigator.storage.estimate) {
|
93 |
+
cbPrint('loadRemote: navigator.storage.estimate() is not supported');
|
94 |
+
} else {
|
95 |
+
// query the storage quota and print it
|
96 |
+
navigator.storage.estimate().then(function (estimate) {
|
97 |
+
cbPrint('loadRemote: storage quota: ' + estimate.quota + ' bytes');
|
98 |
+
cbPrint('loadRemote: storage usage: ' + estimate.usage + ' bytes');
|
99 |
+
});
|
100 |
+
}
|
101 |
|
102 |
// check if the data is already in the IndexedDB
|
103 |
var rq = indexedDB.open(dbName, dbVersion);
|
|
|
146 |
var db = event.target.result;
|
147 |
var tx = db.transaction(['models'], 'readwrite');
|
148 |
var os = tx.objectStore('models');
|
149 |
+
|
150 |
+
var rq = null;
|
151 |
+
try {
|
152 |
+
var rq = os.put(data, url);
|
153 |
+
} catch (e) {
|
154 |
+
cbPrint('loadRemote: failed to store "' + url + '" in the IndexedDB: \n' + e);
|
155 |
+
cbCancel();
|
156 |
+
return;
|
157 |
+
}
|
158 |
|
159 |
rq.onsuccess = function (event) {
|
160 |
cbPrint('loadRemote: "' + url + '" stored in the IndexedDB');
|
|
|
189 |
|
190 |
rq.onabort = function (event) {
|
191 |
cbPrint('loadRemote: failed to open IndexedDB: abort');
|
192 |
+
cbCancel();
|
193 |
};
|
194 |
}
|
|
js/jquery-3.7.1.min.js
ADDED
@@ -0,0 +1,2 @@
|
|
|
|
|
|
|
1 |
+
/*! jQuery v3.7.1 | (c) OpenJS Foundation and other contributors | jquery.org/license */
|
2 |
+
!function(e,t){"use strict";"object"==typeof module&&"object"==typeof module.exports?module.exports=e.document?t(e,!0):function(e){if(!e.document)throw new Error("jQuery requires a window with a document");return t(e)}:t(e)}("undefined"!=typeof window?window:this,function(ie,e){"use strict";var oe=[],r=Object.getPrototypeOf,ae=oe.slice,g=oe.flat?function(e){return oe.flat.call(e)}:function(e){return oe.concat.apply([],e)},s=oe.push,se=oe.indexOf,n={},i=n.toString,ue=n.hasOwnProperty,o=ue.toString,a=o.call(Object),le={},v=function(e){return"function"==typeof e&&"number"!=typeof e.nodeType&&"function"!=typeof e.item},y=function(e){return null!=e&&e===e.window},C=ie.document,u={type:!0,src:!0,nonce:!0,noModule:!0};function m(e,t,n){var r,i,o=(n=n||C).createElement("script");if(o.text=e,t)for(r in u)(i=t[r]||t.getAttribute&&t.getAttribute(r))&&o.setAttribute(r,i);n.head.appendChild(o).parentNode.removeChild(o)}function x(e){return null==e?e+"":"object"==typeof e||"function"==typeof e?n[i.call(e)]||"object":typeof e}var t="3.7.1",l=/HTML$/i,ce=function(e,t){return new ce.fn.init(e,t)};function c(e){var t=!!e&&"length"in e&&e.length,n=x(e);return!v(e)&&!y(e)&&("array"===n||0===t||"number"==typeof t&&0<t&&t-1 in e)}function fe(e,t){return e.nodeName&&e.nodeName.toLowerCase()===t.toLowerCase()}ce.fn=ce.prototype={jquery:t,constructor:ce,length:0,toArray:function(){return ae.call(this)},get:function(e){return null==e?ae.call(this):e<0?this[e+this.length]:this[e]},pushStack:function(e){var t=ce.merge(this.constructor(),e);return t.prevObject=this,t},each:function(e){return ce.each(this,e)},map:function(n){return this.pushStack(ce.map(this,function(e,t){return n.call(e,t,e)}))},slice:function(){return this.pushStack(ae.apply(this,arguments))},first:function(){return this.eq(0)},last:function(){return this.eq(-1)},even:function(){return this.pushStack(ce.grep(this,function(e,t){return(t+1)%2}))},odd:function(){return this.pushStack(ce.grep(this,function(e,t){return t%2}))},eq:function(e){var t=this.length,n=+e+(e<0?t:0);return this.pushStack(0<=n&&n<t?[this[n]]:[])},end:function(){return this.prevObject||this.constructor()},push:s,sort:oe.sort,splice:oe.splice},ce.extend=ce.fn.extend=function(){var e,t,n,r,i,o,a=arguments[0]||{},s=1,u=arguments.length,l=!1;for("boolean"==typeof a&&(l=a,a=arguments[s]||{},s++),"object"==typeof a||v(a)||(a={}),s===u&&(a=this,s--);s<u;s++)if(null!=(e=arguments[s]))for(t in e)r=e[t],"__proto__"!==t&&a!==r&&(l&&r&&(ce.isPlainObject(r)||(i=Array.isArray(r)))?(n=a[t],o=i&&!Array.isArray(n)?[]:i||ce.isPlainObject(n)?n:{},i=!1,a[t]=ce.extend(l,o,r)):void 0!==r&&(a[t]=r));return a},ce.extend({expando:"jQuery"+(t+Math.random()).replace(/\D/g,""),isReady:!0,error:function(e){throw new Error(e)},noop:function(){},isPlainObject:function(e){var t,n;return!(!e||"[object Object]"!==i.call(e))&&(!(t=r(e))||"function"==typeof(n=ue.call(t,"constructor")&&t.constructor)&&o.call(n)===a)},isEmptyObject:function(e){var t;for(t in e)return!1;return!0},globalEval:function(e,t,n){m(e,{nonce:t&&t.nonce},n)},each:function(e,t){var n,r=0;if(c(e)){for(n=e.length;r<n;r++)if(!1===t.call(e[r],r,e[r]))break}else for(r in e)if(!1===t.call(e[r],r,e[r]))break;return e},text:function(e){var t,n="",r=0,i=e.nodeType;if(!i)while(t=e[r++])n+=ce.text(t);return 1===i||11===i?e.textContent:9===i?e.documentElement.textContent:3===i||4===i?e.nodeValue:n},makeArray:function(e,t){var n=t||[];return null!=e&&(c(Object(e))?ce.merge(n,"string"==typeof e?[e]:e):s.call(n,e)),n},inArray:function(e,t,n){return null==t?-1:se.call(t,e,n)},isXMLDoc:function(e){var t=e&&e.namespaceURI,n=e&&(e.ownerDocument||e).documentElement;return!l.test(t||n&&n.nodeName||"HTML")},merge:function(e,t){for(var n=+t.length,r=0,i=e.length;r<n;r++)e[i++]=t[r];return e.length=i,e},grep:function(e,t,n){for(var r=[],i=0,o=e.length,a=!n;i<o;i++)!t(e[i],i)!==a&&r.push(e[i]);return r},map:function(e,t,n){var r,i,o=0,a=[];if(c(e))for(r=e.length;o<r;o++)null!=(i=t(e[o],o,n))&&a.push(i);else for(o in e)null!=(i=t(e[o],o,n))&&a.push(i);return g(a)},guid:1,support:le}),"function"==typeof Symbol&&(ce.fn[Symbol.iterator]=oe[Symbol.iterator]),ce.each("Boolean Number String Function Array Date RegExp Object Error Symbol".split(" "),function(e,t){n["[object "+t+"]"]=t.toLowerCase()});var pe=oe.pop,de=oe.sort,he=oe.splice,ge="[\\x20\\t\\r\\n\\f]",ve=new RegExp("^"+ge+"+|((?:^|[^\\\\])(?:\\\\.)*)"+ge+"+$","g");ce.contains=function(e,t){var n=t&&t.parentNode;return e===n||!(!n||1!==n.nodeType||!(e.contains?e.contains(n):e.compareDocumentPosition&&16&e.compareDocumentPosition(n)))};var f=/([\0-\x1f\x7f]|^-?\d)|^-$|[^\x80-\uFFFF\w-]/g;function p(e,t){return t?"\0"===e?"\ufffd":e.slice(0,-1)+"\\"+e.charCodeAt(e.length-1).toString(16)+" ":"\\"+e}ce.escapeSelector=function(e){return(e+"").replace(f,p)};var ye=C,me=s;!function(){var e,b,w,o,a,T,r,C,d,i,k=me,S=ce.expando,E=0,n=0,s=W(),c=W(),u=W(),h=W(),l=function(e,t){return e===t&&(a=!0),0},f="checked|selected|async|autofocus|autoplay|controls|defer|disabled|hidden|ismap|loop|multiple|open|readonly|required|scoped",t="(?:\\\\[\\da-fA-F]{1,6}"+ge+"?|\\\\[^\\r\\n\\f]|[\\w-]|[^\0-\\x7f])+",p="\\["+ge+"*("+t+")(?:"+ge+"*([*^$|!~]?=)"+ge+"*(?:'((?:\\\\.|[^\\\\'])*)'|\"((?:\\\\.|[^\\\\\"])*)\"|("+t+"))|)"+ge+"*\\]",g=":("+t+")(?:\\((('((?:\\\\.|[^\\\\'])*)'|\"((?:\\\\.|[^\\\\\"])*)\")|((?:\\\\.|[^\\\\()[\\]]|"+p+")*)|.*)\\)|)",v=new RegExp(ge+"+","g"),y=new RegExp("^"+ge+"*,"+ge+"*"),m=new RegExp("^"+ge+"*([>+~]|"+ge+")"+ge+"*"),x=new RegExp(ge+"|>"),j=new RegExp(g),A=new RegExp("^"+t+"$"),D={ID:new RegExp("^#("+t+")"),CLASS:new RegExp("^\\.("+t+")"),TAG:new RegExp("^("+t+"|[*])"),ATTR:new RegExp("^"+p),PSEUDO:new RegExp("^"+g),CHILD:new RegExp("^:(only|first|last|nth|nth-last)-(child|of-type)(?:\\("+ge+"*(even|odd|(([+-]|)(\\d*)n|)"+ge+"*(?:([+-]|)"+ge+"*(\\d+)|))"+ge+"*\\)|)","i"),bool:new RegExp("^(?:"+f+")$","i"),needsContext:new RegExp("^"+ge+"*[>+~]|:(even|odd|eq|gt|lt|nth|first|last)(?:\\("+ge+"*((?:-\\d)?\\d*)"+ge+"*\\)|)(?=[^-]|$)","i")},N=/^(?:input|select|textarea|button)$/i,q=/^h\d$/i,L=/^(?:#([\w-]+)|(\w+)|\.([\w-]+))$/,H=/[+~]/,O=new RegExp("\\\\[\\da-fA-F]{1,6}"+ge+"?|\\\\([^\\r\\n\\f])","g"),P=function(e,t){var n="0x"+e.slice(1)-65536;return t||(n<0?String.fromCharCode(n+65536):String.fromCharCode(n>>10|55296,1023&n|56320))},M=function(){V()},R=J(function(e){return!0===e.disabled&&fe(e,"fieldset")},{dir:"parentNode",next:"legend"});try{k.apply(oe=ae.call(ye.childNodes),ye.childNodes),oe[ye.childNodes.length].nodeType}catch(e){k={apply:function(e,t){me.apply(e,ae.call(t))},call:function(e){me.apply(e,ae.call(arguments,1))}}}function I(t,e,n,r){var i,o,a,s,u,l,c,f=e&&e.ownerDocument,p=e?e.nodeType:9;if(n=n||[],"string"!=typeof t||!t||1!==p&&9!==p&&11!==p)return n;if(!r&&(V(e),e=e||T,C)){if(11!==p&&(u=L.exec(t)))if(i=u[1]){if(9===p){if(!(a=e.getElementById(i)))return n;if(a.id===i)return k.call(n,a),n}else if(f&&(a=f.getElementById(i))&&I.contains(e,a)&&a.id===i)return k.call(n,a),n}else{if(u[2])return k.apply(n,e.getElementsByTagName(t)),n;if((i=u[3])&&e.getElementsByClassName)return k.apply(n,e.getElementsByClassName(i)),n}if(!(h[t+" "]||d&&d.test(t))){if(c=t,f=e,1===p&&(x.test(t)||m.test(t))){(f=H.test(t)&&U(e.parentNode)||e)==e&&le.scope||((s=e.getAttribute("id"))?s=ce.escapeSelector(s):e.setAttribute("id",s=S)),o=(l=Y(t)).length;while(o--)l[o]=(s?"#"+s:":scope")+" "+Q(l[o]);c=l.join(",")}try{return k.apply(n,f.querySelectorAll(c)),n}catch(e){h(t,!0)}finally{s===S&&e.removeAttribute("id")}}}return re(t.replace(ve,"$1"),e,n,r)}function W(){var r=[];return function e(t,n){return r.push(t+" ")>b.cacheLength&&delete e[r.shift()],e[t+" "]=n}}function F(e){return e[S]=!0,e}function $(e){var t=T.createElement("fieldset");try{return!!e(t)}catch(e){return!1}finally{t.parentNode&&t.parentNode.removeChild(t),t=null}}function B(t){return function(e){return fe(e,"input")&&e.type===t}}function _(t){return function(e){return(fe(e,"input")||fe(e,"button"))&&e.type===t}}function z(t){return function(e){return"form"in e?e.parentNode&&!1===e.disabled?"label"in e?"label"in e.parentNode?e.parentNode.disabled===t:e.disabled===t:e.isDisabled===t||e.isDisabled!==!t&&R(e)===t:e.disabled===t:"label"in e&&e.disabled===t}}function X(a){return F(function(o){return o=+o,F(function(e,t){var n,r=a([],e.length,o),i=r.length;while(i--)e[n=r[i]]&&(e[n]=!(t[n]=e[n]))})})}function U(e){return e&&"undefined"!=typeof e.getElementsByTagName&&e}function V(e){var t,n=e?e.ownerDocument||e:ye;return n!=T&&9===n.nodeType&&n.documentElement&&(r=(T=n).documentElement,C=!ce.isXMLDoc(T),i=r.matches||r.webkitMatchesSelector||r.msMatchesSelector,r.msMatchesSelector&&ye!=T&&(t=T.defaultView)&&t.top!==t&&t.addEventListener("unload",M),le.getById=$(function(e){return r.appendChild(e).id=ce.expando,!T.getElementsByName||!T.getElementsByName(ce.expando).length}),le.disconnectedMatch=$(function(e){return i.call(e,"*")}),le.scope=$(function(){return T.querySelectorAll(":scope")}),le.cssHas=$(function(){try{return T.querySelector(":has(*,:jqfake)"),!1}catch(e){return!0}}),le.getById?(b.filter.ID=function(e){var t=e.replace(O,P);return function(e){return e.getAttribute("id")===t}},b.find.ID=function(e,t){if("undefined"!=typeof t.getElementById&&C){var n=t.getElementById(e);return n?[n]:[]}}):(b.filter.ID=function(e){var n=e.replace(O,P);return function(e){var t="undefined"!=typeof e.getAttributeNode&&e.getAttributeNode("id");return t&&t.value===n}},b.find.ID=function(e,t){if("undefined"!=typeof t.getElementById&&C){var n,r,i,o=t.getElementById(e);if(o){if((n=o.getAttributeNode("id"))&&n.value===e)return[o];i=t.getElementsByName(e),r=0;while(o=i[r++])if((n=o.getAttributeNode("id"))&&n.value===e)return[o]}return[]}}),b.find.TAG=function(e,t){return"undefined"!=typeof t.getElementsByTagName?t.getElementsByTagName(e):t.querySelectorAll(e)},b.find.CLASS=function(e,t){if("undefined"!=typeof t.getElementsByClassName&&C)return t.getElementsByClassName(e)},d=[],$(function(e){var t;r.appendChild(e).innerHTML="<a id='"+S+"' href='' disabled='disabled'></a><select id='"+S+"-\r\\' disabled='disabled'><option selected=''></option></select>",e.querySelectorAll("[selected]").length||d.push("\\["+ge+"*(?:value|"+f+")"),e.querySelectorAll("[id~="+S+"-]").length||d.push("~="),e.querySelectorAll("a#"+S+"+*").length||d.push(".#.+[+~]"),e.querySelectorAll(":checked").length||d.push(":checked"),(t=T.createElement("input")).setAttribute("type","hidden"),e.appendChild(t).setAttribute("name","D"),r.appendChild(e).disabled=!0,2!==e.querySelectorAll(":disabled").length&&d.push(":enabled",":disabled"),(t=T.createElement("input")).setAttribute("name",""),e.appendChild(t),e.querySelectorAll("[name='']").length||d.push("\\["+ge+"*name"+ge+"*="+ge+"*(?:''|\"\")")}),le.cssHas||d.push(":has"),d=d.length&&new RegExp(d.join("|")),l=function(e,t){if(e===t)return a=!0,0;var n=!e.compareDocumentPosition-!t.compareDocumentPosition;return n||(1&(n=(e.ownerDocument||e)==(t.ownerDocument||t)?e.compareDocumentPosition(t):1)||!le.sortDetached&&t.compareDocumentPosition(e)===n?e===T||e.ownerDocument==ye&&I.contains(ye,e)?-1:t===T||t.ownerDocument==ye&&I.contains(ye,t)?1:o?se.call(o,e)-se.call(o,t):0:4&n?-1:1)}),T}for(e in I.matches=function(e,t){return I(e,null,null,t)},I.matchesSelector=function(e,t){if(V(e),C&&!h[t+" "]&&(!d||!d.test(t)))try{var n=i.call(e,t);if(n||le.disconnectedMatch||e.document&&11!==e.document.nodeType)return n}catch(e){h(t,!0)}return 0<I(t,T,null,[e]).length},I.contains=function(e,t){return(e.ownerDocument||e)!=T&&V(e),ce.contains(e,t)},I.attr=function(e,t){(e.ownerDocument||e)!=T&&V(e);var n=b.attrHandle[t.toLowerCase()],r=n&&ue.call(b.attrHandle,t.toLowerCase())?n(e,t,!C):void 0;return void 0!==r?r:e.getAttribute(t)},I.error=function(e){throw new Error("Syntax error, unrecognized expression: "+e)},ce.uniqueSort=function(e){var t,n=[],r=0,i=0;if(a=!le.sortStable,o=!le.sortStable&&ae.call(e,0),de.call(e,l),a){while(t=e[i++])t===e[i]&&(r=n.push(i));while(r--)he.call(e,n[r],1)}return o=null,e},ce.fn.uniqueSort=function(){return this.pushStack(ce.uniqueSort(ae.apply(this)))},(b=ce.expr={cacheLength:50,createPseudo:F,match:D,attrHandle:{},find:{},relative:{">":{dir:"parentNode",first:!0}," ":{dir:"parentNode"},"+":{dir:"previousSibling",first:!0},"~":{dir:"previousSibling"}},preFilter:{ATTR:function(e){return e[1]=e[1].replace(O,P),e[3]=(e[3]||e[4]||e[5]||"").replace(O,P),"~="===e[2]&&(e[3]=" "+e[3]+" "),e.slice(0,4)},CHILD:function(e){return e[1]=e[1].toLowerCase(),"nth"===e[1].slice(0,3)?(e[3]||I.error(e[0]),e[4]=+(e[4]?e[5]+(e[6]||1):2*("even"===e[3]||"odd"===e[3])),e[5]=+(e[7]+e[8]||"odd"===e[3])):e[3]&&I.error(e[0]),e},PSEUDO:function(e){var t,n=!e[6]&&e[2];return D.CHILD.test(e[0])?null:(e[3]?e[2]=e[4]||e[5]||"":n&&j.test(n)&&(t=Y(n,!0))&&(t=n.indexOf(")",n.length-t)-n.length)&&(e[0]=e[0].slice(0,t),e[2]=n.slice(0,t)),e.slice(0,3))}},filter:{TAG:function(e){var t=e.replace(O,P).toLowerCase();return"*"===e?function(){return!0}:function(e){return fe(e,t)}},CLASS:function(e){var t=s[e+" "];return t||(t=new RegExp("(^|"+ge+")"+e+"("+ge+"|$)"))&&s(e,function(e){return t.test("string"==typeof e.className&&e.className||"undefined"!=typeof e.getAttribute&&e.getAttribute("class")||"")})},ATTR:function(n,r,i){return function(e){var t=I.attr(e,n);return null==t?"!="===r:!r||(t+="","="===r?t===i:"!="===r?t!==i:"^="===r?i&&0===t.indexOf(i):"*="===r?i&&-1<t.indexOf(i):"$="===r?i&&t.slice(-i.length)===i:"~="===r?-1<(" "+t.replace(v," ")+" ").indexOf(i):"|="===r&&(t===i||t.slice(0,i.length+1)===i+"-"))}},CHILD:function(d,e,t,h,g){var v="nth"!==d.slice(0,3),y="last"!==d.slice(-4),m="of-type"===e;return 1===h&&0===g?function(e){return!!e.parentNode}:function(e,t,n){var r,i,o,a,s,u=v!==y?"nextSibling":"previousSibling",l=e.parentNode,c=m&&e.nodeName.toLowerCase(),f=!n&&!m,p=!1;if(l){if(v){while(u){o=e;while(o=o[u])if(m?fe(o,c):1===o.nodeType)return!1;s=u="only"===d&&!s&&"nextSibling"}return!0}if(s=[y?l.firstChild:l.lastChild],y&&f){p=(a=(r=(i=l[S]||(l[S]={}))[d]||[])[0]===E&&r[1])&&r[2],o=a&&l.childNodes[a];while(o=++a&&o&&o[u]||(p=a=0)||s.pop())if(1===o.nodeType&&++p&&o===e){i[d]=[E,a,p];break}}else if(f&&(p=a=(r=(i=e[S]||(e[S]={}))[d]||[])[0]===E&&r[1]),!1===p)while(o=++a&&o&&o[u]||(p=a=0)||s.pop())if((m?fe(o,c):1===o.nodeType)&&++p&&(f&&((i=o[S]||(o[S]={}))[d]=[E,p]),o===e))break;return(p-=g)===h||p%h==0&&0<=p/h}}},PSEUDO:function(e,o){var t,a=b.pseudos[e]||b.setFilters[e.toLowerCase()]||I.error("unsupported pseudo: "+e);return a[S]?a(o):1<a.length?(t=[e,e,"",o],b.setFilters.hasOwnProperty(e.toLowerCase())?F(function(e,t){var n,r=a(e,o),i=r.length;while(i--)e[n=se.call(e,r[i])]=!(t[n]=r[i])}):function(e){return a(e,0,t)}):a}},pseudos:{not:F(function(e){var r=[],i=[],s=ne(e.replace(ve,"$1"));return s[S]?F(function(e,t,n,r){var i,o=s(e,null,r,[]),a=e.length;while(a--)(i=o[a])&&(e[a]=!(t[a]=i))}):function(e,t,n){return r[0]=e,s(r,null,n,i),r[0]=null,!i.pop()}}),has:F(function(t){return function(e){return 0<I(t,e).length}}),contains:F(function(t){return t=t.replace(O,P),function(e){return-1<(e.textContent||ce.text(e)).indexOf(t)}}),lang:F(function(n){return A.test(n||"")||I.error("unsupported lang: "+n),n=n.replace(O,P).toLowerCase(),function(e){var t;do{if(t=C?e.lang:e.getAttribute("xml:lang")||e.getAttribute("lang"))return(t=t.toLowerCase())===n||0===t.indexOf(n+"-")}while((e=e.parentNode)&&1===e.nodeType);return!1}}),target:function(e){var t=ie.location&&ie.location.hash;return t&&t.slice(1)===e.id},root:function(e){return e===r},focus:function(e){return e===function(){try{return T.activeElement}catch(e){}}()&&T.hasFocus()&&!!(e.type||e.href||~e.tabIndex)},enabled:z(!1),disabled:z(!0),checked:function(e){return fe(e,"input")&&!!e.checked||fe(e,"option")&&!!e.selected},selected:function(e){return e.parentNode&&e.parentNode.selectedIndex,!0===e.selected},empty:function(e){for(e=e.firstChild;e;e=e.nextSibling)if(e.nodeType<6)return!1;return!0},parent:function(e){return!b.pseudos.empty(e)},header:function(e){return q.test(e.nodeName)},input:function(e){return N.test(e.nodeName)},button:function(e){return fe(e,"input")&&"button"===e.type||fe(e,"button")},text:function(e){var t;return fe(e,"input")&&"text"===e.type&&(null==(t=e.getAttribute("type"))||"text"===t.toLowerCase())},first:X(function(){return[0]}),last:X(function(e,t){return[t-1]}),eq:X(function(e,t,n){return[n<0?n+t:n]}),even:X(function(e,t){for(var n=0;n<t;n+=2)e.push(n);return e}),odd:X(function(e,t){for(var n=1;n<t;n+=2)e.push(n);return e}),lt:X(function(e,t,n){var r;for(r=n<0?n+t:t<n?t:n;0<=--r;)e.push(r);return e}),gt:X(function(e,t,n){for(var r=n<0?n+t:n;++r<t;)e.push(r);return e})}}).pseudos.nth=b.pseudos.eq,{radio:!0,checkbox:!0,file:!0,password:!0,image:!0})b.pseudos[e]=B(e);for(e in{submit:!0,reset:!0})b.pseudos[e]=_(e);function G(){}function Y(e,t){var n,r,i,o,a,s,u,l=c[e+" "];if(l)return t?0:l.slice(0);a=e,s=[],u=b.preFilter;while(a){for(o in n&&!(r=y.exec(a))||(r&&(a=a.slice(r[0].length)||a),s.push(i=[])),n=!1,(r=m.exec(a))&&(n=r.shift(),i.push({value:n,type:r[0].replace(ve," ")}),a=a.slice(n.length)),b.filter)!(r=D[o].exec(a))||u[o]&&!(r=u[o](r))||(n=r.shift(),i.push({value:n,type:o,matches:r}),a=a.slice(n.length));if(!n)break}return t?a.length:a?I.error(e):c(e,s).slice(0)}function Q(e){for(var t=0,n=e.length,r="";t<n;t++)r+=e[t].value;return r}function J(a,e,t){var s=e.dir,u=e.next,l=u||s,c=t&&"parentNode"===l,f=n++;return e.first?function(e,t,n){while(e=e[s])if(1===e.nodeType||c)return a(e,t,n);return!1}:function(e,t,n){var r,i,o=[E,f];if(n){while(e=e[s])if((1===e.nodeType||c)&&a(e,t,n))return!0}else while(e=e[s])if(1===e.nodeType||c)if(i=e[S]||(e[S]={}),u&&fe(e,u))e=e[s]||e;else{if((r=i[l])&&r[0]===E&&r[1]===f)return o[2]=r[2];if((i[l]=o)[2]=a(e,t,n))return!0}return!1}}function K(i){return 1<i.length?function(e,t,n){var r=i.length;while(r--)if(!i[r](e,t,n))return!1;return!0}:i[0]}function Z(e,t,n,r,i){for(var o,a=[],s=0,u=e.length,l=null!=t;s<u;s++)(o=e[s])&&(n&&!n(o,r,i)||(a.push(o),l&&t.push(s)));return a}function ee(d,h,g,v,y,e){return v&&!v[S]&&(v=ee(v)),y&&!y[S]&&(y=ee(y,e)),F(function(e,t,n,r){var i,o,a,s,u=[],l=[],c=t.length,f=e||function(e,t,n){for(var r=0,i=t.length;r<i;r++)I(e,t[r],n);return n}(h||"*",n.nodeType?[n]:n,[]),p=!d||!e&&h?f:Z(f,u,d,n,r);if(g?g(p,s=y||(e?d:c||v)?[]:t,n,r):s=p,v){i=Z(s,l),v(i,[],n,r),o=i.length;while(o--)(a=i[o])&&(s[l[o]]=!(p[l[o]]=a))}if(e){if(y||d){if(y){i=[],o=s.length;while(o--)(a=s[o])&&i.push(p[o]=a);y(null,s=[],i,r)}o=s.length;while(o--)(a=s[o])&&-1<(i=y?se.call(e,a):u[o])&&(e[i]=!(t[i]=a))}}else s=Z(s===t?s.splice(c,s.length):s),y?y(null,t,s,r):k.apply(t,s)})}function te(e){for(var i,t,n,r=e.length,o=b.relative[e[0].type],a=o||b.relative[" "],s=o?1:0,u=J(function(e){return e===i},a,!0),l=J(function(e){return-1<se.call(i,e)},a,!0),c=[function(e,t,n){var r=!o&&(n||t!=w)||((i=t).nodeType?u(e,t,n):l(e,t,n));return i=null,r}];s<r;s++)if(t=b.relative[e[s].type])c=[J(K(c),t)];else{if((t=b.filter[e[s].type].apply(null,e[s].matches))[S]){for(n=++s;n<r;n++)if(b.relative[e[n].type])break;return ee(1<s&&K(c),1<s&&Q(e.slice(0,s-1).concat({value:" "===e[s-2].type?"*":""})).replace(ve,"$1"),t,s<n&&te(e.slice(s,n)),n<r&&te(e=e.slice(n)),n<r&&Q(e))}c.push(t)}return K(c)}function ne(e,t){var n,v,y,m,x,r,i=[],o=[],a=u[e+" "];if(!a){t||(t=Y(e)),n=t.length;while(n--)(a=te(t[n]))[S]?i.push(a):o.push(a);(a=u(e,(v=o,m=0<(y=i).length,x=0<v.length,r=function(e,t,n,r,i){var o,a,s,u=0,l="0",c=e&&[],f=[],p=w,d=e||x&&b.find.TAG("*",i),h=E+=null==p?1:Math.random()||.1,g=d.length;for(i&&(w=t==T||t||i);l!==g&&null!=(o=d[l]);l++){if(x&&o){a=0,t||o.ownerDocument==T||(V(o),n=!C);while(s=v[a++])if(s(o,t||T,n)){k.call(r,o);break}i&&(E=h)}m&&((o=!s&&o)&&u--,e&&c.push(o))}if(u+=l,m&&l!==u){a=0;while(s=y[a++])s(c,f,t,n);if(e){if(0<u)while(l--)c[l]||f[l]||(f[l]=pe.call(r));f=Z(f)}k.apply(r,f),i&&!e&&0<f.length&&1<u+y.length&&ce.uniqueSort(r)}return i&&(E=h,w=p),c},m?F(r):r))).selector=e}return a}function re(e,t,n,r){var i,o,a,s,u,l="function"==typeof e&&e,c=!r&&Y(e=l.selector||e);if(n=n||[],1===c.length){if(2<(o=c[0]=c[0].slice(0)).length&&"ID"===(a=o[0]).type&&9===t.nodeType&&C&&b.relative[o[1].type]){if(!(t=(b.find.ID(a.matches[0].replace(O,P),t)||[])[0]))return n;l&&(t=t.parentNode),e=e.slice(o.shift().value.length)}i=D.needsContext.test(e)?0:o.length;while(i--){if(a=o[i],b.relative[s=a.type])break;if((u=b.find[s])&&(r=u(a.matches[0].replace(O,P),H.test(o[0].type)&&U(t.parentNode)||t))){if(o.splice(i,1),!(e=r.length&&Q(o)))return k.apply(n,r),n;break}}}return(l||ne(e,c))(r,t,!C,n,!t||H.test(e)&&U(t.parentNode)||t),n}G.prototype=b.filters=b.pseudos,b.setFilters=new G,le.sortStable=S.split("").sort(l).join("")===S,V(),le.sortDetached=$(function(e){return 1&e.compareDocumentPosition(T.createElement("fieldset"))}),ce.find=I,ce.expr[":"]=ce.expr.pseudos,ce.unique=ce.uniqueSort,I.compile=ne,I.select=re,I.setDocument=V,I.tokenize=Y,I.escape=ce.escapeSelector,I.getText=ce.text,I.isXML=ce.isXMLDoc,I.selectors=ce.expr,I.support=ce.support,I.uniqueSort=ce.uniqueSort}();var d=function(e,t,n){var r=[],i=void 0!==n;while((e=e[t])&&9!==e.nodeType)if(1===e.nodeType){if(i&&ce(e).is(n))break;r.push(e)}return r},h=function(e,t){for(var n=[];e;e=e.nextSibling)1===e.nodeType&&e!==t&&n.push(e);return n},b=ce.expr.match.needsContext,w=/^<([a-z][^\/\0>:\x20\t\r\n\f]*)[\x20\t\r\n\f]*\/?>(?:<\/\1>|)$/i;function T(e,n,r){return v(n)?ce.grep(e,function(e,t){return!!n.call(e,t,e)!==r}):n.nodeType?ce.grep(e,function(e){return e===n!==r}):"string"!=typeof n?ce.grep(e,function(e){return-1<se.call(n,e)!==r}):ce.filter(n,e,r)}ce.filter=function(e,t,n){var r=t[0];return n&&(e=":not("+e+")"),1===t.length&&1===r.nodeType?ce.find.matchesSelector(r,e)?[r]:[]:ce.find.matches(e,ce.grep(t,function(e){return 1===e.nodeType}))},ce.fn.extend({find:function(e){var t,n,r=this.length,i=this;if("string"!=typeof e)return this.pushStack(ce(e).filter(function(){for(t=0;t<r;t++)if(ce.contains(i[t],this))return!0}));for(n=this.pushStack([]),t=0;t<r;t++)ce.find(e,i[t],n);return 1<r?ce.uniqueSort(n):n},filter:function(e){return this.pushStack(T(this,e||[],!1))},not:function(e){return this.pushStack(T(this,e||[],!0))},is:function(e){return!!T(this,"string"==typeof e&&b.test(e)?ce(e):e||[],!1).length}});var k,S=/^(?:\s*(<[\w\W]+>)[^>]*|#([\w-]+))$/;(ce.fn.init=function(e,t,n){var r,i;if(!e)return this;if(n=n||k,"string"==typeof e){if(!(r="<"===e[0]&&">"===e[e.length-1]&&3<=e.length?[null,e,null]:S.exec(e))||!r[1]&&t)return!t||t.jquery?(t||n).find(e):this.constructor(t).find(e);if(r[1]){if(t=t instanceof ce?t[0]:t,ce.merge(this,ce.parseHTML(r[1],t&&t.nodeType?t.ownerDocument||t:C,!0)),w.test(r[1])&&ce.isPlainObject(t))for(r in t)v(this[r])?this[r](t[r]):this.attr(r,t[r]);return this}return(i=C.getElementById(r[2]))&&(this[0]=i,this.length=1),this}return e.nodeType?(this[0]=e,this.length=1,this):v(e)?void 0!==n.ready?n.ready(e):e(ce):ce.makeArray(e,this)}).prototype=ce.fn,k=ce(C);var E=/^(?:parents|prev(?:Until|All))/,j={children:!0,contents:!0,next:!0,prev:!0};function A(e,t){while((e=e[t])&&1!==e.nodeType);return e}ce.fn.extend({has:function(e){var t=ce(e,this),n=t.length;return this.filter(function(){for(var e=0;e<n;e++)if(ce.contains(this,t[e]))return!0})},closest:function(e,t){var n,r=0,i=this.length,o=[],a="string"!=typeof e&&ce(e);if(!b.test(e))for(;r<i;r++)for(n=this[r];n&&n!==t;n=n.parentNode)if(n.nodeType<11&&(a?-1<a.index(n):1===n.nodeType&&ce.find.matchesSelector(n,e))){o.push(n);break}return this.pushStack(1<o.length?ce.uniqueSort(o):o)},index:function(e){return e?"string"==typeof e?se.call(ce(e),this[0]):se.call(this,e.jquery?e[0]:e):this[0]&&this[0].parentNode?this.first().prevAll().length:-1},add:function(e,t){return this.pushStack(ce.uniqueSort(ce.merge(this.get(),ce(e,t))))},addBack:function(e){return this.add(null==e?this.prevObject:this.prevObject.filter(e))}}),ce.each({parent:function(e){var t=e.parentNode;return t&&11!==t.nodeType?t:null},parents:function(e){return d(e,"parentNode")},parentsUntil:function(e,t,n){return d(e,"parentNode",n)},next:function(e){return A(e,"nextSibling")},prev:function(e){return A(e,"previousSibling")},nextAll:function(e){return d(e,"nextSibling")},prevAll:function(e){return d(e,"previousSibling")},nextUntil:function(e,t,n){return d(e,"nextSibling",n)},prevUntil:function(e,t,n){return d(e,"previousSibling",n)},siblings:function(e){return h((e.parentNode||{}).firstChild,e)},children:function(e){return h(e.firstChild)},contents:function(e){return null!=e.contentDocument&&r(e.contentDocument)?e.contentDocument:(fe(e,"template")&&(e=e.content||e),ce.merge([],e.childNodes))}},function(r,i){ce.fn[r]=function(e,t){var n=ce.map(this,i,e);return"Until"!==r.slice(-5)&&(t=e),t&&"string"==typeof t&&(n=ce.filter(t,n)),1<this.length&&(j[r]||ce.uniqueSort(n),E.test(r)&&n.reverse()),this.pushStack(n)}});var D=/[^\x20\t\r\n\f]+/g;function N(e){return e}function q(e){throw e}function L(e,t,n,r){var i;try{e&&v(i=e.promise)?i.call(e).done(t).fail(n):e&&v(i=e.then)?i.call(e,t,n):t.apply(void 0,[e].slice(r))}catch(e){n.apply(void 0,[e])}}ce.Callbacks=function(r){var e,n;r="string"==typeof r?(e=r,n={},ce.each(e.match(D)||[],function(e,t){n[t]=!0}),n):ce.extend({},r);var i,t,o,a,s=[],u=[],l=-1,c=function(){for(a=a||r.once,o=i=!0;u.length;l=-1){t=u.shift();while(++l<s.length)!1===s[l].apply(t[0],t[1])&&r.stopOnFalse&&(l=s.length,t=!1)}r.memory||(t=!1),i=!1,a&&(s=t?[]:"")},f={add:function(){return s&&(t&&!i&&(l=s.length-1,u.push(t)),function n(e){ce.each(e,function(e,t){v(t)?r.unique&&f.has(t)||s.push(t):t&&t.length&&"string"!==x(t)&&n(t)})}(arguments),t&&!i&&c()),this},remove:function(){return ce.each(arguments,function(e,t){var n;while(-1<(n=ce.inArray(t,s,n)))s.splice(n,1),n<=l&&l--}),this},has:function(e){return e?-1<ce.inArray(e,s):0<s.length},empty:function(){return s&&(s=[]),this},disable:function(){return a=u=[],s=t="",this},disabled:function(){return!s},lock:function(){return a=u=[],t||i||(s=t=""),this},locked:function(){return!!a},fireWith:function(e,t){return a||(t=[e,(t=t||[]).slice?t.slice():t],u.push(t),i||c()),this},fire:function(){return f.fireWith(this,arguments),this},fired:function(){return!!o}};return f},ce.extend({Deferred:function(e){var o=[["notify","progress",ce.Callbacks("memory"),ce.Callbacks("memory"),2],["resolve","done",ce.Callbacks("once memory"),ce.Callbacks("once memory"),0,"resolved"],["reject","fail",ce.Callbacks("once memory"),ce.Callbacks("once memory"),1,"rejected"]],i="pending",a={state:function(){return i},always:function(){return s.done(arguments).fail(arguments),this},"catch":function(e){return a.then(null,e)},pipe:function(){var i=arguments;return ce.Deferred(function(r){ce.each(o,function(e,t){var n=v(i[t[4]])&&i[t[4]];s[t[1]](function(){var e=n&&n.apply(this,arguments);e&&v(e.promise)?e.promise().progress(r.notify).done(r.resolve).fail(r.reject):r[t[0]+"With"](this,n?[e]:arguments)})}),i=null}).promise()},then:function(t,n,r){var u=0;function l(i,o,a,s){return function(){var n=this,r=arguments,e=function(){var e,t;if(!(i<u)){if((e=a.apply(n,r))===o.promise())throw new TypeError("Thenable self-resolution");t=e&&("object"==typeof e||"function"==typeof e)&&e.then,v(t)?s?t.call(e,l(u,o,N,s),l(u,o,q,s)):(u++,t.call(e,l(u,o,N,s),l(u,o,q,s),l(u,o,N,o.notifyWith))):(a!==N&&(n=void 0,r=[e]),(s||o.resolveWith)(n,r))}},t=s?e:function(){try{e()}catch(e){ce.Deferred.exceptionHook&&ce.Deferred.exceptionHook(e,t.error),u<=i+1&&(a!==q&&(n=void 0,r=[e]),o.rejectWith(n,r))}};i?t():(ce.Deferred.getErrorHook?t.error=ce.Deferred.getErrorHook():ce.Deferred.getStackHook&&(t.error=ce.Deferred.getStackHook()),ie.setTimeout(t))}}return ce.Deferred(function(e){o[0][3].add(l(0,e,v(r)?r:N,e.notifyWith)),o[1][3].add(l(0,e,v(t)?t:N)),o[2][3].add(l(0,e,v(n)?n:q))}).promise()},promise:function(e){return null!=e?ce.extend(e,a):a}},s={};return ce.each(o,function(e,t){var n=t[2],r=t[5];a[t[1]]=n.add,r&&n.add(function(){i=r},o[3-e][2].disable,o[3-e][3].disable,o[0][2].lock,o[0][3].lock),n.add(t[3].fire),s[t[0]]=function(){return s[t[0]+"With"](this===s?void 0:this,arguments),this},s[t[0]+"With"]=n.fireWith}),a.promise(s),e&&e.call(s,s),s},when:function(e){var n=arguments.length,t=n,r=Array(t),i=ae.call(arguments),o=ce.Deferred(),a=function(t){return function(e){r[t]=this,i[t]=1<arguments.length?ae.call(arguments):e,--n||o.resolveWith(r,i)}};if(n<=1&&(L(e,o.done(a(t)).resolve,o.reject,!n),"pending"===o.state()||v(i[t]&&i[t].then)))return o.then();while(t--)L(i[t],a(t),o.reject);return o.promise()}});var H=/^(Eval|Internal|Range|Reference|Syntax|Type|URI)Error$/;ce.Deferred.exceptionHook=function(e,t){ie.console&&ie.console.warn&&e&&H.test(e.name)&&ie.console.warn("jQuery.Deferred exception: "+e.message,e.stack,t)},ce.readyException=function(e){ie.setTimeout(function(){throw e})};var O=ce.Deferred();function P(){C.removeEventListener("DOMContentLoaded",P),ie.removeEventListener("load",P),ce.ready()}ce.fn.ready=function(e){return O.then(e)["catch"](function(e){ce.readyException(e)}),this},ce.extend({isReady:!1,readyWait:1,ready:function(e){(!0===e?--ce.readyWait:ce.isReady)||(ce.isReady=!0)!==e&&0<--ce.readyWait||O.resolveWith(C,[ce])}}),ce.ready.then=O.then,"complete"===C.readyState||"loading"!==C.readyState&&!C.documentElement.doScroll?ie.setTimeout(ce.ready):(C.addEventListener("DOMContentLoaded",P),ie.addEventListener("load",P));var M=function(e,t,n,r,i,o,a){var s=0,u=e.length,l=null==n;if("object"===x(n))for(s in i=!0,n)M(e,t,s,n[s],!0,o,a);else if(void 0!==r&&(i=!0,v(r)||(a=!0),l&&(a?(t.call(e,r),t=null):(l=t,t=function(e,t,n){return l.call(ce(e),n)})),t))for(;s<u;s++)t(e[s],n,a?r:r.call(e[s],s,t(e[s],n)));return i?e:l?t.call(e):u?t(e[0],n):o},R=/^-ms-/,I=/-([a-z])/g;function W(e,t){return t.toUpperCase()}function F(e){return e.replace(R,"ms-").replace(I,W)}var $=function(e){return 1===e.nodeType||9===e.nodeType||!+e.nodeType};function B(){this.expando=ce.expando+B.uid++}B.uid=1,B.prototype={cache:function(e){var t=e[this.expando];return t||(t={},$(e)&&(e.nodeType?e[this.expando]=t:Object.defineProperty(e,this.expando,{value:t,configurable:!0}))),t},set:function(e,t,n){var r,i=this.cache(e);if("string"==typeof t)i[F(t)]=n;else for(r in t)i[F(r)]=t[r];return i},get:function(e,t){return void 0===t?this.cache(e):e[this.expando]&&e[this.expando][F(t)]},access:function(e,t,n){return void 0===t||t&&"string"==typeof t&&void 0===n?this.get(e,t):(this.set(e,t,n),void 0!==n?n:t)},remove:function(e,t){var n,r=e[this.expando];if(void 0!==r){if(void 0!==t){n=(t=Array.isArray(t)?t.map(F):(t=F(t))in r?[t]:t.match(D)||[]).length;while(n--)delete r[t[n]]}(void 0===t||ce.isEmptyObject(r))&&(e.nodeType?e[this.expando]=void 0:delete e[this.expando])}},hasData:function(e){var t=e[this.expando];return void 0!==t&&!ce.isEmptyObject(t)}};var _=new B,z=new B,X=/^(?:\{[\w\W]*\}|\[[\w\W]*\])$/,U=/[A-Z]/g;function V(e,t,n){var r,i;if(void 0===n&&1===e.nodeType)if(r="data-"+t.replace(U,"-$&").toLowerCase(),"string"==typeof(n=e.getAttribute(r))){try{n="true"===(i=n)||"false"!==i&&("null"===i?null:i===+i+""?+i:X.test(i)?JSON.parse(i):i)}catch(e){}z.set(e,t,n)}else n=void 0;return n}ce.extend({hasData:function(e){return z.hasData(e)||_.hasData(e)},data:function(e,t,n){return z.access(e,t,n)},removeData:function(e,t){z.remove(e,t)},_data:function(e,t,n){return _.access(e,t,n)},_removeData:function(e,t){_.remove(e,t)}}),ce.fn.extend({data:function(n,e){var t,r,i,o=this[0],a=o&&o.attributes;if(void 0===n){if(this.length&&(i=z.get(o),1===o.nodeType&&!_.get(o,"hasDataAttrs"))){t=a.length;while(t--)a[t]&&0===(r=a[t].name).indexOf("data-")&&(r=F(r.slice(5)),V(o,r,i[r]));_.set(o,"hasDataAttrs",!0)}return i}return"object"==typeof n?this.each(function(){z.set(this,n)}):M(this,function(e){var t;if(o&&void 0===e)return void 0!==(t=z.get(o,n))?t:void 0!==(t=V(o,n))?t:void 0;this.each(function(){z.set(this,n,e)})},null,e,1<arguments.length,null,!0)},removeData:function(e){return this.each(function(){z.remove(this,e)})}}),ce.extend({queue:function(e,t,n){var r;if(e)return t=(t||"fx")+"queue",r=_.get(e,t),n&&(!r||Array.isArray(n)?r=_.access(e,t,ce.makeArray(n)):r.push(n)),r||[]},dequeue:function(e,t){t=t||"fx";var n=ce.queue(e,t),r=n.length,i=n.shift(),o=ce._queueHooks(e,t);"inprogress"===i&&(i=n.shift(),r--),i&&("fx"===t&&n.unshift("inprogress"),delete o.stop,i.call(e,function(){ce.dequeue(e,t)},o)),!r&&o&&o.empty.fire()},_queueHooks:function(e,t){var n=t+"queueHooks";return _.get(e,n)||_.access(e,n,{empty:ce.Callbacks("once memory").add(function(){_.remove(e,[t+"queue",n])})})}}),ce.fn.extend({queue:function(t,n){var e=2;return"string"!=typeof t&&(n=t,t="fx",e--),arguments.length<e?ce.queue(this[0],t):void 0===n?this:this.each(function(){var e=ce.queue(this,t,n);ce._queueHooks(this,t),"fx"===t&&"inprogress"!==e[0]&&ce.dequeue(this,t)})},dequeue:function(e){return this.each(function(){ce.dequeue(this,e)})},clearQueue:function(e){return this.queue(e||"fx",[])},promise:function(e,t){var n,r=1,i=ce.Deferred(),o=this,a=this.length,s=function(){--r||i.resolveWith(o,[o])};"string"!=typeof e&&(t=e,e=void 0),e=e||"fx";while(a--)(n=_.get(o[a],e+"queueHooks"))&&n.empty&&(r++,n.empty.add(s));return s(),i.promise(t)}});var G=/[+-]?(?:\d*\.|)\d+(?:[eE][+-]?\d+|)/.source,Y=new RegExp("^(?:([+-])=|)("+G+")([a-z%]*)$","i"),Q=["Top","Right","Bottom","Left"],J=C.documentElement,K=function(e){return ce.contains(e.ownerDocument,e)},Z={composed:!0};J.getRootNode&&(K=function(e){return ce.contains(e.ownerDocument,e)||e.getRootNode(Z)===e.ownerDocument});var ee=function(e,t){return"none"===(e=t||e).style.display||""===e.style.display&&K(e)&&"none"===ce.css(e,"display")};function te(e,t,n,r){var i,o,a=20,s=r?function(){return r.cur()}:function(){return ce.css(e,t,"")},u=s(),l=n&&n[3]||(ce.cssNumber[t]?"":"px"),c=e.nodeType&&(ce.cssNumber[t]||"px"!==l&&+u)&&Y.exec(ce.css(e,t));if(c&&c[3]!==l){u/=2,l=l||c[3],c=+u||1;while(a--)ce.style(e,t,c+l),(1-o)*(1-(o=s()/u||.5))<=0&&(a=0),c/=o;c*=2,ce.style(e,t,c+l),n=n||[]}return n&&(c=+c||+u||0,i=n[1]?c+(n[1]+1)*n[2]:+n[2],r&&(r.unit=l,r.start=c,r.end=i)),i}var ne={};function re(e,t){for(var n,r,i,o,a,s,u,l=[],c=0,f=e.length;c<f;c++)(r=e[c]).style&&(n=r.style.display,t?("none"===n&&(l[c]=_.get(r,"display")||null,l[c]||(r.style.display="")),""===r.style.display&&ee(r)&&(l[c]=(u=a=o=void 0,a=(i=r).ownerDocument,s=i.nodeName,(u=ne[s])||(o=a.body.appendChild(a.createElement(s)),u=ce.css(o,"display"),o.parentNode.removeChild(o),"none"===u&&(u="block"),ne[s]=u)))):"none"!==n&&(l[c]="none",_.set(r,"display",n)));for(c=0;c<f;c++)null!=l[c]&&(e[c].style.display=l[c]);return e}ce.fn.extend({show:function(){return re(this,!0)},hide:function(){return re(this)},toggle:function(e){return"boolean"==typeof e?e?this.show():this.hide():this.each(function(){ee(this)?ce(this).show():ce(this).hide()})}});var xe,be,we=/^(?:checkbox|radio)$/i,Te=/<([a-z][^\/\0>\x20\t\r\n\f]*)/i,Ce=/^$|^module$|\/(?:java|ecma)script/i;xe=C.createDocumentFragment().appendChild(C.createElement("div")),(be=C.createElement("input")).setAttribute("type","radio"),be.setAttribute("checked","checked"),be.setAttribute("name","t"),xe.appendChild(be),le.checkClone=xe.cloneNode(!0).cloneNode(!0).lastChild.checked,xe.innerHTML="<textarea>x</textarea>",le.noCloneChecked=!!xe.cloneNode(!0).lastChild.defaultValue,xe.innerHTML="<option></option>",le.option=!!xe.lastChild;var ke={thead:[1,"<table>","</table>"],col:[2,"<table><colgroup>","</colgroup></table>"],tr:[2,"<table><tbody>","</tbody></table>"],td:[3,"<table><tbody><tr>","</tr></tbody></table>"],_default:[0,"",""]};function Se(e,t){var n;return n="undefined"!=typeof e.getElementsByTagName?e.getElementsByTagName(t||"*"):"undefined"!=typeof e.querySelectorAll?e.querySelectorAll(t||"*"):[],void 0===t||t&&fe(e,t)?ce.merge([e],n):n}function Ee(e,t){for(var n=0,r=e.length;n<r;n++)_.set(e[n],"globalEval",!t||_.get(t[n],"globalEval"))}ke.tbody=ke.tfoot=ke.colgroup=ke.caption=ke.thead,ke.th=ke.td,le.option||(ke.optgroup=ke.option=[1,"<select multiple='multiple'>","</select>"]);var je=/<|&#?\w+;/;function Ae(e,t,n,r,i){for(var o,a,s,u,l,c,f=t.createDocumentFragment(),p=[],d=0,h=e.length;d<h;d++)if((o=e[d])||0===o)if("object"===x(o))ce.merge(p,o.nodeType?[o]:o);else if(je.test(o)){a=a||f.appendChild(t.createElement("div")),s=(Te.exec(o)||["",""])[1].toLowerCase(),u=ke[s]||ke._default,a.innerHTML=u[1]+ce.htmlPrefilter(o)+u[2],c=u[0];while(c--)a=a.lastChild;ce.merge(p,a.childNodes),(a=f.firstChild).textContent=""}else p.push(t.createTextNode(o));f.textContent="",d=0;while(o=p[d++])if(r&&-1<ce.inArray(o,r))i&&i.push(o);else if(l=K(o),a=Se(f.appendChild(o),"script"),l&&Ee(a),n){c=0;while(o=a[c++])Ce.test(o.type||"")&&n.push(o)}return f}var De=/^([^.]*)(?:\.(.+)|)/;function Ne(){return!0}function qe(){return!1}function Le(e,t,n,r,i,o){var a,s;if("object"==typeof t){for(s in"string"!=typeof n&&(r=r||n,n=void 0),t)Le(e,s,n,r,t[s],o);return e}if(null==r&&null==i?(i=n,r=n=void 0):null==i&&("string"==typeof n?(i=r,r=void 0):(i=r,r=n,n=void 0)),!1===i)i=qe;else if(!i)return e;return 1===o&&(a=i,(i=function(e){return ce().off(e),a.apply(this,arguments)}).guid=a.guid||(a.guid=ce.guid++)),e.each(function(){ce.event.add(this,t,i,r,n)})}function He(e,r,t){t?(_.set(e,r,!1),ce.event.add(e,r,{namespace:!1,handler:function(e){var t,n=_.get(this,r);if(1&e.isTrigger&&this[r]){if(n)(ce.event.special[r]||{}).delegateType&&e.stopPropagation();else if(n=ae.call(arguments),_.set(this,r,n),this[r](),t=_.get(this,r),_.set(this,r,!1),n!==t)return e.stopImmediatePropagation(),e.preventDefault(),t}else n&&(_.set(this,r,ce.event.trigger(n[0],n.slice(1),this)),e.stopPropagation(),e.isImmediatePropagationStopped=Ne)}})):void 0===_.get(e,r)&&ce.event.add(e,r,Ne)}ce.event={global:{},add:function(t,e,n,r,i){var o,a,s,u,l,c,f,p,d,h,g,v=_.get(t);if($(t)){n.handler&&(n=(o=n).handler,i=o.selector),i&&ce.find.matchesSelector(J,i),n.guid||(n.guid=ce.guid++),(u=v.events)||(u=v.events=Object.create(null)),(a=v.handle)||(a=v.handle=function(e){return"undefined"!=typeof ce&&ce.event.triggered!==e.type?ce.event.dispatch.apply(t,arguments):void 0}),l=(e=(e||"").match(D)||[""]).length;while(l--)d=g=(s=De.exec(e[l])||[])[1],h=(s[2]||"").split(".").sort(),d&&(f=ce.event.special[d]||{},d=(i?f.delegateType:f.bindType)||d,f=ce.event.special[d]||{},c=ce.extend({type:d,origType:g,data:r,handler:n,guid:n.guid,selector:i,needsContext:i&&ce.expr.match.needsContext.test(i),namespace:h.join(".")},o),(p=u[d])||((p=u[d]=[]).delegateCount=0,f.setup&&!1!==f.setup.call(t,r,h,a)||t.addEventListener&&t.addEventListener(d,a)),f.add&&(f.add.call(t,c),c.handler.guid||(c.handler.guid=n.guid)),i?p.splice(p.delegateCount++,0,c):p.push(c),ce.event.global[d]=!0)}},remove:function(e,t,n,r,i){var o,a,s,u,l,c,f,p,d,h,g,v=_.hasData(e)&&_.get(e);if(v&&(u=v.events)){l=(t=(t||"").match(D)||[""]).length;while(l--)if(d=g=(s=De.exec(t[l])||[])[1],h=(s[2]||"").split(".").sort(),d){f=ce.event.special[d]||{},p=u[d=(r?f.delegateType:f.bindType)||d]||[],s=s[2]&&new RegExp("(^|\\.)"+h.join("\\.(?:.*\\.|)")+"(\\.|$)"),a=o=p.length;while(o--)c=p[o],!i&&g!==c.origType||n&&n.guid!==c.guid||s&&!s.test(c.namespace)||r&&r!==c.selector&&("**"!==r||!c.selector)||(p.splice(o,1),c.selector&&p.delegateCount--,f.remove&&f.remove.call(e,c));a&&!p.length&&(f.teardown&&!1!==f.teardown.call(e,h,v.handle)||ce.removeEvent(e,d,v.handle),delete u[d])}else for(d in u)ce.event.remove(e,d+t[l],n,r,!0);ce.isEmptyObject(u)&&_.remove(e,"handle events")}},dispatch:function(e){var t,n,r,i,o,a,s=new Array(arguments.length),u=ce.event.fix(e),l=(_.get(this,"events")||Object.create(null))[u.type]||[],c=ce.event.special[u.type]||{};for(s[0]=u,t=1;t<arguments.length;t++)s[t]=arguments[t];if(u.delegateTarget=this,!c.preDispatch||!1!==c.preDispatch.call(this,u)){a=ce.event.handlers.call(this,u,l),t=0;while((i=a[t++])&&!u.isPropagationStopped()){u.currentTarget=i.elem,n=0;while((o=i.handlers[n++])&&!u.isImmediatePropagationStopped())u.rnamespace&&!1!==o.namespace&&!u.rnamespace.test(o.namespace)||(u.handleObj=o,u.data=o.data,void 0!==(r=((ce.event.special[o.origType]||{}).handle||o.handler).apply(i.elem,s))&&!1===(u.result=r)&&(u.preventDefault(),u.stopPropagation()))}return c.postDispatch&&c.postDispatch.call(this,u),u.result}},handlers:function(e,t){var n,r,i,o,a,s=[],u=t.delegateCount,l=e.target;if(u&&l.nodeType&&!("click"===e.type&&1<=e.button))for(;l!==this;l=l.parentNode||this)if(1===l.nodeType&&("click"!==e.type||!0!==l.disabled)){for(o=[],a={},n=0;n<u;n++)void 0===a[i=(r=t[n]).selector+" "]&&(a[i]=r.needsContext?-1<ce(i,this).index(l):ce.find(i,this,null,[l]).length),a[i]&&o.push(r);o.length&&s.push({elem:l,handlers:o})}return l=this,u<t.length&&s.push({elem:l,handlers:t.slice(u)}),s},addProp:function(t,e){Object.defineProperty(ce.Event.prototype,t,{enumerable:!0,configurable:!0,get:v(e)?function(){if(this.originalEvent)return e(this.originalEvent)}:function(){if(this.originalEvent)return this.originalEvent[t]},set:function(e){Object.defineProperty(this,t,{enumerable:!0,configurable:!0,writable:!0,value:e})}})},fix:function(e){return e[ce.expando]?e:new ce.Event(e)},special:{load:{noBubble:!0},click:{setup:function(e){var t=this||e;return we.test(t.type)&&t.click&&fe(t,"input")&&He(t,"click",!0),!1},trigger:function(e){var t=this||e;return we.test(t.type)&&t.click&&fe(t,"input")&&He(t,"click"),!0},_default:function(e){var t=e.target;return we.test(t.type)&&t.click&&fe(t,"input")&&_.get(t,"click")||fe(t,"a")}},beforeunload:{postDispatch:function(e){void 0!==e.result&&e.originalEvent&&(e.originalEvent.returnValue=e.result)}}}},ce.removeEvent=function(e,t,n){e.removeEventListener&&e.removeEventListener(t,n)},ce.Event=function(e,t){if(!(this instanceof ce.Event))return new ce.Event(e,t);e&&e.type?(this.originalEvent=e,this.type=e.type,this.isDefaultPrevented=e.defaultPrevented||void 0===e.defaultPrevented&&!1===e.returnValue?Ne:qe,this.target=e.target&&3===e.target.nodeType?e.target.parentNode:e.target,this.currentTarget=e.currentTarget,this.relatedTarget=e.relatedTarget):this.type=e,t&&ce.extend(this,t),this.timeStamp=e&&e.timeStamp||Date.now(),this[ce.expando]=!0},ce.Event.prototype={constructor:ce.Event,isDefaultPrevented:qe,isPropagationStopped:qe,isImmediatePropagationStopped:qe,isSimulated:!1,preventDefault:function(){var e=this.originalEvent;this.isDefaultPrevented=Ne,e&&!this.isSimulated&&e.preventDefault()},stopPropagation:function(){var e=this.originalEvent;this.isPropagationStopped=Ne,e&&!this.isSimulated&&e.stopPropagation()},stopImmediatePropagation:function(){var e=this.originalEvent;this.isImmediatePropagationStopped=Ne,e&&!this.isSimulated&&e.stopImmediatePropagation(),this.stopPropagation()}},ce.each({altKey:!0,bubbles:!0,cancelable:!0,changedTouches:!0,ctrlKey:!0,detail:!0,eventPhase:!0,metaKey:!0,pageX:!0,pageY:!0,shiftKey:!0,view:!0,"char":!0,code:!0,charCode:!0,key:!0,keyCode:!0,button:!0,buttons:!0,clientX:!0,clientY:!0,offsetX:!0,offsetY:!0,pointerId:!0,pointerType:!0,screenX:!0,screenY:!0,targetTouches:!0,toElement:!0,touches:!0,which:!0},ce.event.addProp),ce.each({focus:"focusin",blur:"focusout"},function(r,i){function o(e){if(C.documentMode){var t=_.get(this,"handle"),n=ce.event.fix(e);n.type="focusin"===e.type?"focus":"blur",n.isSimulated=!0,t(e),n.target===n.currentTarget&&t(n)}else ce.event.simulate(i,e.target,ce.event.fix(e))}ce.event.special[r]={setup:function(){var e;if(He(this,r,!0),!C.documentMode)return!1;(e=_.get(this,i))||this.addEventListener(i,o),_.set(this,i,(e||0)+1)},trigger:function(){return He(this,r),!0},teardown:function(){var e;if(!C.documentMode)return!1;(e=_.get(this,i)-1)?_.set(this,i,e):(this.removeEventListener(i,o),_.remove(this,i))},_default:function(e){return _.get(e.target,r)},delegateType:i},ce.event.special[i]={setup:function(){var e=this.ownerDocument||this.document||this,t=C.documentMode?this:e,n=_.get(t,i);n||(C.documentMode?this.addEventListener(i,o):e.addEventListener(r,o,!0)),_.set(t,i,(n||0)+1)},teardown:function(){var e=this.ownerDocument||this.document||this,t=C.documentMode?this:e,n=_.get(t,i)-1;n?_.set(t,i,n):(C.documentMode?this.removeEventListener(i,o):e.removeEventListener(r,o,!0),_.remove(t,i))}}}),ce.each({mouseenter:"mouseover",mouseleave:"mouseout",pointerenter:"pointerover",pointerleave:"pointerout"},function(e,i){ce.event.special[e]={delegateType:i,bindType:i,handle:function(e){var t,n=e.relatedTarget,r=e.handleObj;return n&&(n===this||ce.contains(this,n))||(e.type=r.origType,t=r.handler.apply(this,arguments),e.type=i),t}}}),ce.fn.extend({on:function(e,t,n,r){return Le(this,e,t,n,r)},one:function(e,t,n,r){return Le(this,e,t,n,r,1)},off:function(e,t,n){var r,i;if(e&&e.preventDefault&&e.handleObj)return r=e.handleObj,ce(e.delegateTarget).off(r.namespace?r.origType+"."+r.namespace:r.origType,r.selector,r.handler),this;if("object"==typeof e){for(i in e)this.off(i,t,e[i]);return this}return!1!==t&&"function"!=typeof t||(n=t,t=void 0),!1===n&&(n=qe),this.each(function(){ce.event.remove(this,e,n,t)})}});var Oe=/<script|<style|<link/i,Pe=/checked\s*(?:[^=]|=\s*.checked.)/i,Me=/^\s*<!\[CDATA\[|\]\]>\s*$/g;function Re(e,t){return fe(e,"table")&&fe(11!==t.nodeType?t:t.firstChild,"tr")&&ce(e).children("tbody")[0]||e}function Ie(e){return e.type=(null!==e.getAttribute("type"))+"/"+e.type,e}function We(e){return"true/"===(e.type||"").slice(0,5)?e.type=e.type.slice(5):e.removeAttribute("type"),e}function Fe(e,t){var n,r,i,o,a,s;if(1===t.nodeType){if(_.hasData(e)&&(s=_.get(e).events))for(i in _.remove(t,"handle events"),s)for(n=0,r=s[i].length;n<r;n++)ce.event.add(t,i,s[i][n]);z.hasData(e)&&(o=z.access(e),a=ce.extend({},o),z.set(t,a))}}function $e(n,r,i,o){r=g(r);var e,t,a,s,u,l,c=0,f=n.length,p=f-1,d=r[0],h=v(d);if(h||1<f&&"string"==typeof d&&!le.checkClone&&Pe.test(d))return n.each(function(e){var t=n.eq(e);h&&(r[0]=d.call(this,e,t.html())),$e(t,r,i,o)});if(f&&(t=(e=Ae(r,n[0].ownerDocument,!1,n,o)).firstChild,1===e.childNodes.length&&(e=t),t||o)){for(s=(a=ce.map(Se(e,"script"),Ie)).length;c<f;c++)u=e,c!==p&&(u=ce.clone(u,!0,!0),s&&ce.merge(a,Se(u,"script"))),i.call(n[c],u,c);if(s)for(l=a[a.length-1].ownerDocument,ce.map(a,We),c=0;c<s;c++)u=a[c],Ce.test(u.type||"")&&!_.access(u,"globalEval")&&ce.contains(l,u)&&(u.src&&"module"!==(u.type||"").toLowerCase()?ce._evalUrl&&!u.noModule&&ce._evalUrl(u.src,{nonce:u.nonce||u.getAttribute("nonce")},l):m(u.textContent.replace(Me,""),u,l))}return n}function Be(e,t,n){for(var r,i=t?ce.filter(t,e):e,o=0;null!=(r=i[o]);o++)n||1!==r.nodeType||ce.cleanData(Se(r)),r.parentNode&&(n&&K(r)&&Ee(Se(r,"script")),r.parentNode.removeChild(r));return e}ce.extend({htmlPrefilter:function(e){return e},clone:function(e,t,n){var r,i,o,a,s,u,l,c=e.cloneNode(!0),f=K(e);if(!(le.noCloneChecked||1!==e.nodeType&&11!==e.nodeType||ce.isXMLDoc(e)))for(a=Se(c),r=0,i=(o=Se(e)).length;r<i;r++)s=o[r],u=a[r],void 0,"input"===(l=u.nodeName.toLowerCase())&&we.test(s.type)?u.checked=s.checked:"input"!==l&&"textarea"!==l||(u.defaultValue=s.defaultValue);if(t)if(n)for(o=o||Se(e),a=a||Se(c),r=0,i=o.length;r<i;r++)Fe(o[r],a[r]);else Fe(e,c);return 0<(a=Se(c,"script")).length&&Ee(a,!f&&Se(e,"script")),c},cleanData:function(e){for(var t,n,r,i=ce.event.special,o=0;void 0!==(n=e[o]);o++)if($(n)){if(t=n[_.expando]){if(t.events)for(r in t.events)i[r]?ce.event.remove(n,r):ce.removeEvent(n,r,t.handle);n[_.expando]=void 0}n[z.expando]&&(n[z.expando]=void 0)}}}),ce.fn.extend({detach:function(e){return Be(this,e,!0)},remove:function(e){return Be(this,e)},text:function(e){return M(this,function(e){return void 0===e?ce.text(this):this.empty().each(function(){1!==this.nodeType&&11!==this.nodeType&&9!==this.nodeType||(this.textContent=e)})},null,e,arguments.length)},append:function(){return $e(this,arguments,function(e){1!==this.nodeType&&11!==this.nodeType&&9!==this.nodeType||Re(this,e).appendChild(e)})},prepend:function(){return $e(this,arguments,function(e){if(1===this.nodeType||11===this.nodeType||9===this.nodeType){var t=Re(this,e);t.insertBefore(e,t.firstChild)}})},before:function(){return $e(this,arguments,function(e){this.parentNode&&this.parentNode.insertBefore(e,this)})},after:function(){return $e(this,arguments,function(e){this.parentNode&&this.parentNode.insertBefore(e,this.nextSibling)})},empty:function(){for(var e,t=0;null!=(e=this[t]);t++)1===e.nodeType&&(ce.cleanData(Se(e,!1)),e.textContent="");return this},clone:function(e,t){return e=null!=e&&e,t=null==t?e:t,this.map(function(){return ce.clone(this,e,t)})},html:function(e){return M(this,function(e){var t=this[0]||{},n=0,r=this.length;if(void 0===e&&1===t.nodeType)return t.innerHTML;if("string"==typeof e&&!Oe.test(e)&&!ke[(Te.exec(e)||["",""])[1].toLowerCase()]){e=ce.htmlPrefilter(e);try{for(;n<r;n++)1===(t=this[n]||{}).nodeType&&(ce.cleanData(Se(t,!1)),t.innerHTML=e);t=0}catch(e){}}t&&this.empty().append(e)},null,e,arguments.length)},replaceWith:function(){var n=[];return $e(this,arguments,function(e){var t=this.parentNode;ce.inArray(this,n)<0&&(ce.cleanData(Se(this)),t&&t.replaceChild(e,this))},n)}}),ce.each({appendTo:"append",prependTo:"prepend",insertBefore:"before",insertAfter:"after",replaceAll:"replaceWith"},function(e,a){ce.fn[e]=function(e){for(var t,n=[],r=ce(e),i=r.length-1,o=0;o<=i;o++)t=o===i?this:this.clone(!0),ce(r[o])[a](t),s.apply(n,t.get());return this.pushStack(n)}});var _e=new RegExp("^("+G+")(?!px)[a-z%]+$","i"),ze=/^--/,Xe=function(e){var t=e.ownerDocument.defaultView;return t&&t.opener||(t=ie),t.getComputedStyle(e)},Ue=function(e,t,n){var r,i,o={};for(i in t)o[i]=e.style[i],e.style[i]=t[i];for(i in r=n.call(e),t)e.style[i]=o[i];return r},Ve=new RegExp(Q.join("|"),"i");function Ge(e,t,n){var r,i,o,a,s=ze.test(t),u=e.style;return(n=n||Xe(e))&&(a=n.getPropertyValue(t)||n[t],s&&a&&(a=a.replace(ve,"$1")||void 0),""!==a||K(e)||(a=ce.style(e,t)),!le.pixelBoxStyles()&&_e.test(a)&&Ve.test(t)&&(r=u.width,i=u.minWidth,o=u.maxWidth,u.minWidth=u.maxWidth=u.width=a,a=n.width,u.width=r,u.minWidth=i,u.maxWidth=o)),void 0!==a?a+"":a}function Ye(e,t){return{get:function(){if(!e())return(this.get=t).apply(this,arguments);delete this.get}}}!function(){function e(){if(l){u.style.cssText="position:absolute;left:-11111px;width:60px;margin-top:1px;padding:0;border:0",l.style.cssText="position:relative;display:block;box-sizing:border-box;overflow:scroll;margin:auto;border:1px;padding:1px;width:60%;top:1%",J.appendChild(u).appendChild(l);var e=ie.getComputedStyle(l);n="1%"!==e.top,s=12===t(e.marginLeft),l.style.right="60%",o=36===t(e.right),r=36===t(e.width),l.style.position="absolute",i=12===t(l.offsetWidth/3),J.removeChild(u),l=null}}function t(e){return Math.round(parseFloat(e))}var n,r,i,o,a,s,u=C.createElement("div"),l=C.createElement("div");l.style&&(l.style.backgroundClip="content-box",l.cloneNode(!0).style.backgroundClip="",le.clearCloneStyle="content-box"===l.style.backgroundClip,ce.extend(le,{boxSizingReliable:function(){return e(),r},pixelBoxStyles:function(){return e(),o},pixelPosition:function(){return e(),n},reliableMarginLeft:function(){return e(),s},scrollboxSize:function(){return e(),i},reliableTrDimensions:function(){var e,t,n,r;return null==a&&(e=C.createElement("table"),t=C.createElement("tr"),n=C.createElement("div"),e.style.cssText="position:absolute;left:-11111px;border-collapse:separate",t.style.cssText="box-sizing:content-box;border:1px solid",t.style.height="1px",n.style.height="9px",n.style.display="block",J.appendChild(e).appendChild(t).appendChild(n),r=ie.getComputedStyle(t),a=parseInt(r.height,10)+parseInt(r.borderTopWidth,10)+parseInt(r.borderBottomWidth,10)===t.offsetHeight,J.removeChild(e)),a}}))}();var Qe=["Webkit","Moz","ms"],Je=C.createElement("div").style,Ke={};function Ze(e){var t=ce.cssProps[e]||Ke[e];return t||(e in Je?e:Ke[e]=function(e){var t=e[0].toUpperCase()+e.slice(1),n=Qe.length;while(n--)if((e=Qe[n]+t)in Je)return e}(e)||e)}var et=/^(none|table(?!-c[ea]).+)/,tt={position:"absolute",visibility:"hidden",display:"block"},nt={letterSpacing:"0",fontWeight:"400"};function rt(e,t,n){var r=Y.exec(t);return r?Math.max(0,r[2]-(n||0))+(r[3]||"px"):t}function it(e,t,n,r,i,o){var a="width"===t?1:0,s=0,u=0,l=0;if(n===(r?"border":"content"))return 0;for(;a<4;a+=2)"margin"===n&&(l+=ce.css(e,n+Q[a],!0,i)),r?("content"===n&&(u-=ce.css(e,"padding"+Q[a],!0,i)),"margin"!==n&&(u-=ce.css(e,"border"+Q[a]+"Width",!0,i))):(u+=ce.css(e,"padding"+Q[a],!0,i),"padding"!==n?u+=ce.css(e,"border"+Q[a]+"Width",!0,i):s+=ce.css(e,"border"+Q[a]+"Width",!0,i));return!r&&0<=o&&(u+=Math.max(0,Math.ceil(e["offset"+t[0].toUpperCase()+t.slice(1)]-o-u-s-.5))||0),u+l}function ot(e,t,n){var r=Xe(e),i=(!le.boxSizingReliable()||n)&&"border-box"===ce.css(e,"boxSizing",!1,r),o=i,a=Ge(e,t,r),s="offset"+t[0].toUpperCase()+t.slice(1);if(_e.test(a)){if(!n)return a;a="auto"}return(!le.boxSizingReliable()&&i||!le.reliableTrDimensions()&&fe(e,"tr")||"auto"===a||!parseFloat(a)&&"inline"===ce.css(e,"display",!1,r))&&e.getClientRects().length&&(i="border-box"===ce.css(e,"boxSizing",!1,r),(o=s in e)&&(a=e[s])),(a=parseFloat(a)||0)+it(e,t,n||(i?"border":"content"),o,r,a)+"px"}function at(e,t,n,r,i){return new at.prototype.init(e,t,n,r,i)}ce.extend({cssHooks:{opacity:{get:function(e,t){if(t){var n=Ge(e,"opacity");return""===n?"1":n}}}},cssNumber:{animationIterationCount:!0,aspectRatio:!0,borderImageSlice:!0,columnCount:!0,flexGrow:!0,flexShrink:!0,fontWeight:!0,gridArea:!0,gridColumn:!0,gridColumnEnd:!0,gridColumnStart:!0,gridRow:!0,gridRowEnd:!0,gridRowStart:!0,lineHeight:!0,opacity:!0,order:!0,orphans:!0,scale:!0,widows:!0,zIndex:!0,zoom:!0,fillOpacity:!0,floodOpacity:!0,stopOpacity:!0,strokeMiterlimit:!0,strokeOpacity:!0},cssProps:{},style:function(e,t,n,r){if(e&&3!==e.nodeType&&8!==e.nodeType&&e.style){var i,o,a,s=F(t),u=ze.test(t),l=e.style;if(u||(t=Ze(s)),a=ce.cssHooks[t]||ce.cssHooks[s],void 0===n)return a&&"get"in a&&void 0!==(i=a.get(e,!1,r))?i:l[t];"string"===(o=typeof n)&&(i=Y.exec(n))&&i[1]&&(n=te(e,t,i),o="number"),null!=n&&n==n&&("number"!==o||u||(n+=i&&i[3]||(ce.cssNumber[s]?"":"px")),le.clearCloneStyle||""!==n||0!==t.indexOf("background")||(l[t]="inherit"),a&&"set"in a&&void 0===(n=a.set(e,n,r))||(u?l.setProperty(t,n):l[t]=n))}},css:function(e,t,n,r){var i,o,a,s=F(t);return ze.test(t)||(t=Ze(s)),(a=ce.cssHooks[t]||ce.cssHooks[s])&&"get"in a&&(i=a.get(e,!0,n)),void 0===i&&(i=Ge(e,t,r)),"normal"===i&&t in nt&&(i=nt[t]),""===n||n?(o=parseFloat(i),!0===n||isFinite(o)?o||0:i):i}}),ce.each(["height","width"],function(e,u){ce.cssHooks[u]={get:function(e,t,n){if(t)return!et.test(ce.css(e,"display"))||e.getClientRects().length&&e.getBoundingClientRect().width?ot(e,u,n):Ue(e,tt,function(){return ot(e,u,n)})},set:function(e,t,n){var r,i=Xe(e),o=!le.scrollboxSize()&&"absolute"===i.position,a=(o||n)&&"border-box"===ce.css(e,"boxSizing",!1,i),s=n?it(e,u,n,a,i):0;return a&&o&&(s-=Math.ceil(e["offset"+u[0].toUpperCase()+u.slice(1)]-parseFloat(i[u])-it(e,u,"border",!1,i)-.5)),s&&(r=Y.exec(t))&&"px"!==(r[3]||"px")&&(e.style[u]=t,t=ce.css(e,u)),rt(0,t,s)}}}),ce.cssHooks.marginLeft=Ye(le.reliableMarginLeft,function(e,t){if(t)return(parseFloat(Ge(e,"marginLeft"))||e.getBoundingClientRect().left-Ue(e,{marginLeft:0},function(){return e.getBoundingClientRect().left}))+"px"}),ce.each({margin:"",padding:"",border:"Width"},function(i,o){ce.cssHooks[i+o]={expand:function(e){for(var t=0,n={},r="string"==typeof e?e.split(" "):[e];t<4;t++)n[i+Q[t]+o]=r[t]||r[t-2]||r[0];return n}},"margin"!==i&&(ce.cssHooks[i+o].set=rt)}),ce.fn.extend({css:function(e,t){return M(this,function(e,t,n){var r,i,o={},a=0;if(Array.isArray(t)){for(r=Xe(e),i=t.length;a<i;a++)o[t[a]]=ce.css(e,t[a],!1,r);return o}return void 0!==n?ce.style(e,t,n):ce.css(e,t)},e,t,1<arguments.length)}}),((ce.Tween=at).prototype={constructor:at,init:function(e,t,n,r,i,o){this.elem=e,this.prop=n,this.easing=i||ce.easing._default,this.options=t,this.start=this.now=this.cur(),this.end=r,this.unit=o||(ce.cssNumber[n]?"":"px")},cur:function(){var e=at.propHooks[this.prop];return e&&e.get?e.get(this):at.propHooks._default.get(this)},run:function(e){var t,n=at.propHooks[this.prop];return this.options.duration?this.pos=t=ce.easing[this.easing](e,this.options.duration*e,0,1,this.options.duration):this.pos=t=e,this.now=(this.end-this.start)*t+this.start,this.options.step&&this.options.step.call(this.elem,this.now,this),n&&n.set?n.set(this):at.propHooks._default.set(this),this}}).init.prototype=at.prototype,(at.propHooks={_default:{get:function(e){var t;return 1!==e.elem.nodeType||null!=e.elem[e.prop]&&null==e.elem.style[e.prop]?e.elem[e.prop]:(t=ce.css(e.elem,e.prop,""))&&"auto"!==t?t:0},set:function(e){ce.fx.step[e.prop]?ce.fx.step[e.prop](e):1!==e.elem.nodeType||!ce.cssHooks[e.prop]&&null==e.elem.style[Ze(e.prop)]?e.elem[e.prop]=e.now:ce.style(e.elem,e.prop,e.now+e.unit)}}}).scrollTop=at.propHooks.scrollLeft={set:function(e){e.elem.nodeType&&e.elem.parentNode&&(e.elem[e.prop]=e.now)}},ce.easing={linear:function(e){return e},swing:function(e){return.5-Math.cos(e*Math.PI)/2},_default:"swing"},ce.fx=at.prototype.init,ce.fx.step={};var st,ut,lt,ct,ft=/^(?:toggle|show|hide)$/,pt=/queueHooks$/;function dt(){ut&&(!1===C.hidden&&ie.requestAnimationFrame?ie.requestAnimationFrame(dt):ie.setTimeout(dt,ce.fx.interval),ce.fx.tick())}function ht(){return ie.setTimeout(function(){st=void 0}),st=Date.now()}function gt(e,t){var n,r=0,i={height:e};for(t=t?1:0;r<4;r+=2-t)i["margin"+(n=Q[r])]=i["padding"+n]=e;return t&&(i.opacity=i.width=e),i}function vt(e,t,n){for(var r,i=(yt.tweeners[t]||[]).concat(yt.tweeners["*"]),o=0,a=i.length;o<a;o++)if(r=i[o].call(n,t,e))return r}function yt(o,e,t){var n,a,r=0,i=yt.prefilters.length,s=ce.Deferred().always(function(){delete u.elem}),u=function(){if(a)return!1;for(var e=st||ht(),t=Math.max(0,l.startTime+l.duration-e),n=1-(t/l.duration||0),r=0,i=l.tweens.length;r<i;r++)l.tweens[r].run(n);return s.notifyWith(o,[l,n,t]),n<1&&i?t:(i||s.notifyWith(o,[l,1,0]),s.resolveWith(o,[l]),!1)},l=s.promise({elem:o,props:ce.extend({},e),opts:ce.extend(!0,{specialEasing:{},easing:ce.easing._default},t),originalProperties:e,originalOptions:t,startTime:st||ht(),duration:t.duration,tweens:[],createTween:function(e,t){var n=ce.Tween(o,l.opts,e,t,l.opts.specialEasing[e]||l.opts.easing);return l.tweens.push(n),n},stop:function(e){var t=0,n=e?l.tweens.length:0;if(a)return this;for(a=!0;t<n;t++)l.tweens[t].run(1);return e?(s.notifyWith(o,[l,1,0]),s.resolveWith(o,[l,e])):s.rejectWith(o,[l,e]),this}}),c=l.props;for(!function(e,t){var n,r,i,o,a;for(n in e)if(i=t[r=F(n)],o=e[n],Array.isArray(o)&&(i=o[1],o=e[n]=o[0]),n!==r&&(e[r]=o,delete e[n]),(a=ce.cssHooks[r])&&"expand"in a)for(n in o=a.expand(o),delete e[r],o)n in e||(e[n]=o[n],t[n]=i);else t[r]=i}(c,l.opts.specialEasing);r<i;r++)if(n=yt.prefilters[r].call(l,o,c,l.opts))return v(n.stop)&&(ce._queueHooks(l.elem,l.opts.queue).stop=n.stop.bind(n)),n;return ce.map(c,vt,l),v(l.opts.start)&&l.opts.start.call(o,l),l.progress(l.opts.progress).done(l.opts.done,l.opts.complete).fail(l.opts.fail).always(l.opts.always),ce.fx.timer(ce.extend(u,{elem:o,anim:l,queue:l.opts.queue})),l}ce.Animation=ce.extend(yt,{tweeners:{"*":[function(e,t){var n=this.createTween(e,t);return te(n.elem,e,Y.exec(t),n),n}]},tweener:function(e,t){v(e)?(t=e,e=["*"]):e=e.match(D);for(var n,r=0,i=e.length;r<i;r++)n=e[r],yt.tweeners[n]=yt.tweeners[n]||[],yt.tweeners[n].unshift(t)},prefilters:[function(e,t,n){var r,i,o,a,s,u,l,c,f="width"in t||"height"in t,p=this,d={},h=e.style,g=e.nodeType&&ee(e),v=_.get(e,"fxshow");for(r in n.queue||(null==(a=ce._queueHooks(e,"fx")).unqueued&&(a.unqueued=0,s=a.empty.fire,a.empty.fire=function(){a.unqueued||s()}),a.unqueued++,p.always(function(){p.always(function(){a.unqueued--,ce.queue(e,"fx").length||a.empty.fire()})})),t)if(i=t[r],ft.test(i)){if(delete t[r],o=o||"toggle"===i,i===(g?"hide":"show")){if("show"!==i||!v||void 0===v[r])continue;g=!0}d[r]=v&&v[r]||ce.style(e,r)}if((u=!ce.isEmptyObject(t))||!ce.isEmptyObject(d))for(r in f&&1===e.nodeType&&(n.overflow=[h.overflow,h.overflowX,h.overflowY],null==(l=v&&v.display)&&(l=_.get(e,"display")),"none"===(c=ce.css(e,"display"))&&(l?c=l:(re([e],!0),l=e.style.display||l,c=ce.css(e,"display"),re([e]))),("inline"===c||"inline-block"===c&&null!=l)&&"none"===ce.css(e,"float")&&(u||(p.done(function(){h.display=l}),null==l&&(c=h.display,l="none"===c?"":c)),h.display="inline-block")),n.overflow&&(h.overflow="hidden",p.always(function(){h.overflow=n.overflow[0],h.overflowX=n.overflow[1],h.overflowY=n.overflow[2]})),u=!1,d)u||(v?"hidden"in v&&(g=v.hidden):v=_.access(e,"fxshow",{display:l}),o&&(v.hidden=!g),g&&re([e],!0),p.done(function(){for(r in g||re([e]),_.remove(e,"fxshow"),d)ce.style(e,r,d[r])})),u=vt(g?v[r]:0,r,p),r in v||(v[r]=u.start,g&&(u.end=u.start,u.start=0))}],prefilter:function(e,t){t?yt.prefilters.unshift(e):yt.prefilters.push(e)}}),ce.speed=function(e,t,n){var r=e&&"object"==typeof e?ce.extend({},e):{complete:n||!n&&t||v(e)&&e,duration:e,easing:n&&t||t&&!v(t)&&t};return ce.fx.off?r.duration=0:"number"!=typeof r.duration&&(r.duration in ce.fx.speeds?r.duration=ce.fx.speeds[r.duration]:r.duration=ce.fx.speeds._default),null!=r.queue&&!0!==r.queue||(r.queue="fx"),r.old=r.complete,r.complete=function(){v(r.old)&&r.old.call(this),r.queue&&ce.dequeue(this,r.queue)},r},ce.fn.extend({fadeTo:function(e,t,n,r){return this.filter(ee).css("opacity",0).show().end().animate({opacity:t},e,n,r)},animate:function(t,e,n,r){var i=ce.isEmptyObject(t),o=ce.speed(e,n,r),a=function(){var e=yt(this,ce.extend({},t),o);(i||_.get(this,"finish"))&&e.stop(!0)};return a.finish=a,i||!1===o.queue?this.each(a):this.queue(o.queue,a)},stop:function(i,e,o){var a=function(e){var t=e.stop;delete e.stop,t(o)};return"string"!=typeof i&&(o=e,e=i,i=void 0),e&&this.queue(i||"fx",[]),this.each(function(){var e=!0,t=null!=i&&i+"queueHooks",n=ce.timers,r=_.get(this);if(t)r[t]&&r[t].stop&&a(r[t]);else for(t in r)r[t]&&r[t].stop&&pt.test(t)&&a(r[t]);for(t=n.length;t--;)n[t].elem!==this||null!=i&&n[t].queue!==i||(n[t].anim.stop(o),e=!1,n.splice(t,1));!e&&o||ce.dequeue(this,i)})},finish:function(a){return!1!==a&&(a=a||"fx"),this.each(function(){var e,t=_.get(this),n=t[a+"queue"],r=t[a+"queueHooks"],i=ce.timers,o=n?n.length:0;for(t.finish=!0,ce.queue(this,a,[]),r&&r.stop&&r.stop.call(this,!0),e=i.length;e--;)i[e].elem===this&&i[e].queue===a&&(i[e].anim.stop(!0),i.splice(e,1));for(e=0;e<o;e++)n[e]&&n[e].finish&&n[e].finish.call(this);delete t.finish})}}),ce.each(["toggle","show","hide"],function(e,r){var i=ce.fn[r];ce.fn[r]=function(e,t,n){return null==e||"boolean"==typeof e?i.apply(this,arguments):this.animate(gt(r,!0),e,t,n)}}),ce.each({slideDown:gt("show"),slideUp:gt("hide"),slideToggle:gt("toggle"),fadeIn:{opacity:"show"},fadeOut:{opacity:"hide"},fadeToggle:{opacity:"toggle"}},function(e,r){ce.fn[e]=function(e,t,n){return this.animate(r,e,t,n)}}),ce.timers=[],ce.fx.tick=function(){var e,t=0,n=ce.timers;for(st=Date.now();t<n.length;t++)(e=n[t])()||n[t]!==e||n.splice(t--,1);n.length||ce.fx.stop(),st=void 0},ce.fx.timer=function(e){ce.timers.push(e),ce.fx.start()},ce.fx.interval=13,ce.fx.start=function(){ut||(ut=!0,dt())},ce.fx.stop=function(){ut=null},ce.fx.speeds={slow:600,fast:200,_default:400},ce.fn.delay=function(r,e){return r=ce.fx&&ce.fx.speeds[r]||r,e=e||"fx",this.queue(e,function(e,t){var n=ie.setTimeout(e,r);t.stop=function(){ie.clearTimeout(n)}})},lt=C.createElement("input"),ct=C.createElement("select").appendChild(C.createElement("option")),lt.type="checkbox",le.checkOn=""!==lt.value,le.optSelected=ct.selected,(lt=C.createElement("input")).value="t",lt.type="radio",le.radioValue="t"===lt.value;var mt,xt=ce.expr.attrHandle;ce.fn.extend({attr:function(e,t){return M(this,ce.attr,e,t,1<arguments.length)},removeAttr:function(e){return this.each(function(){ce.removeAttr(this,e)})}}),ce.extend({attr:function(e,t,n){var r,i,o=e.nodeType;if(3!==o&&8!==o&&2!==o)return"undefined"==typeof e.getAttribute?ce.prop(e,t,n):(1===o&&ce.isXMLDoc(e)||(i=ce.attrHooks[t.toLowerCase()]||(ce.expr.match.bool.test(t)?mt:void 0)),void 0!==n?null===n?void ce.removeAttr(e,t):i&&"set"in i&&void 0!==(r=i.set(e,n,t))?r:(e.setAttribute(t,n+""),n):i&&"get"in i&&null!==(r=i.get(e,t))?r:null==(r=ce.find.attr(e,t))?void 0:r)},attrHooks:{type:{set:function(e,t){if(!le.radioValue&&"radio"===t&&fe(e,"input")){var n=e.value;return e.setAttribute("type",t),n&&(e.value=n),t}}}},removeAttr:function(e,t){var n,r=0,i=t&&t.match(D);if(i&&1===e.nodeType)while(n=i[r++])e.removeAttribute(n)}}),mt={set:function(e,t,n){return!1===t?ce.removeAttr(e,n):e.setAttribute(n,n),n}},ce.each(ce.expr.match.bool.source.match(/\w+/g),function(e,t){var a=xt[t]||ce.find.attr;xt[t]=function(e,t,n){var r,i,o=t.toLowerCase();return n||(i=xt[o],xt[o]=r,r=null!=a(e,t,n)?o:null,xt[o]=i),r}});var bt=/^(?:input|select|textarea|button)$/i,wt=/^(?:a|area)$/i;function Tt(e){return(e.match(D)||[]).join(" ")}function Ct(e){return e.getAttribute&&e.getAttribute("class")||""}function kt(e){return Array.isArray(e)?e:"string"==typeof e&&e.match(D)||[]}ce.fn.extend({prop:function(e,t){return M(this,ce.prop,e,t,1<arguments.length)},removeProp:function(e){return this.each(function(){delete this[ce.propFix[e]||e]})}}),ce.extend({prop:function(e,t,n){var r,i,o=e.nodeType;if(3!==o&&8!==o&&2!==o)return 1===o&&ce.isXMLDoc(e)||(t=ce.propFix[t]||t,i=ce.propHooks[t]),void 0!==n?i&&"set"in i&&void 0!==(r=i.set(e,n,t))?r:e[t]=n:i&&"get"in i&&null!==(r=i.get(e,t))?r:e[t]},propHooks:{tabIndex:{get:function(e){var t=ce.find.attr(e,"tabindex");return t?parseInt(t,10):bt.test(e.nodeName)||wt.test(e.nodeName)&&e.href?0:-1}}},propFix:{"for":"htmlFor","class":"className"}}),le.optSelected||(ce.propHooks.selected={get:function(e){var t=e.parentNode;return t&&t.parentNode&&t.parentNode.selectedIndex,null},set:function(e){var t=e.parentNode;t&&(t.selectedIndex,t.parentNode&&t.parentNode.selectedIndex)}}),ce.each(["tabIndex","readOnly","maxLength","cellSpacing","cellPadding","rowSpan","colSpan","useMap","frameBorder","contentEditable"],function(){ce.propFix[this.toLowerCase()]=this}),ce.fn.extend({addClass:function(t){var e,n,r,i,o,a;return v(t)?this.each(function(e){ce(this).addClass(t.call(this,e,Ct(this)))}):(e=kt(t)).length?this.each(function(){if(r=Ct(this),n=1===this.nodeType&&" "+Tt(r)+" "){for(o=0;o<e.length;o++)i=e[o],n.indexOf(" "+i+" ")<0&&(n+=i+" ");a=Tt(n),r!==a&&this.setAttribute("class",a)}}):this},removeClass:function(t){var e,n,r,i,o,a;return v(t)?this.each(function(e){ce(this).removeClass(t.call(this,e,Ct(this)))}):arguments.length?(e=kt(t)).length?this.each(function(){if(r=Ct(this),n=1===this.nodeType&&" "+Tt(r)+" "){for(o=0;o<e.length;o++){i=e[o];while(-1<n.indexOf(" "+i+" "))n=n.replace(" "+i+" "," ")}a=Tt(n),r!==a&&this.setAttribute("class",a)}}):this:this.attr("class","")},toggleClass:function(t,n){var e,r,i,o,a=typeof t,s="string"===a||Array.isArray(t);return v(t)?this.each(function(e){ce(this).toggleClass(t.call(this,e,Ct(this),n),n)}):"boolean"==typeof n&&s?n?this.addClass(t):this.removeClass(t):(e=kt(t),this.each(function(){if(s)for(o=ce(this),i=0;i<e.length;i++)r=e[i],o.hasClass(r)?o.removeClass(r):o.addClass(r);else void 0!==t&&"boolean"!==a||((r=Ct(this))&&_.set(this,"__className__",r),this.setAttribute&&this.setAttribute("class",r||!1===t?"":_.get(this,"__className__")||""))}))},hasClass:function(e){var t,n,r=0;t=" "+e+" ";while(n=this[r++])if(1===n.nodeType&&-1<(" "+Tt(Ct(n))+" ").indexOf(t))return!0;return!1}});var St=/\r/g;ce.fn.extend({val:function(n){var r,e,i,t=this[0];return arguments.length?(i=v(n),this.each(function(e){var t;1===this.nodeType&&(null==(t=i?n.call(this,e,ce(this).val()):n)?t="":"number"==typeof t?t+="":Array.isArray(t)&&(t=ce.map(t,function(e){return null==e?"":e+""})),(r=ce.valHooks[this.type]||ce.valHooks[this.nodeName.toLowerCase()])&&"set"in r&&void 0!==r.set(this,t,"value")||(this.value=t))})):t?(r=ce.valHooks[t.type]||ce.valHooks[t.nodeName.toLowerCase()])&&"get"in r&&void 0!==(e=r.get(t,"value"))?e:"string"==typeof(e=t.value)?e.replace(St,""):null==e?"":e:void 0}}),ce.extend({valHooks:{option:{get:function(e){var t=ce.find.attr(e,"value");return null!=t?t:Tt(ce.text(e))}},select:{get:function(e){var t,n,r,i=e.options,o=e.selectedIndex,a="select-one"===e.type,s=a?null:[],u=a?o+1:i.length;for(r=o<0?u:a?o:0;r<u;r++)if(((n=i[r]).selected||r===o)&&!n.disabled&&(!n.parentNode.disabled||!fe(n.parentNode,"optgroup"))){if(t=ce(n).val(),a)return t;s.push(t)}return s},set:function(e,t){var n,r,i=e.options,o=ce.makeArray(t),a=i.length;while(a--)((r=i[a]).selected=-1<ce.inArray(ce.valHooks.option.get(r),o))&&(n=!0);return n||(e.selectedIndex=-1),o}}}}),ce.each(["radio","checkbox"],function(){ce.valHooks[this]={set:function(e,t){if(Array.isArray(t))return e.checked=-1<ce.inArray(ce(e).val(),t)}},le.checkOn||(ce.valHooks[this].get=function(e){return null===e.getAttribute("value")?"on":e.value})});var Et=ie.location,jt={guid:Date.now()},At=/\?/;ce.parseXML=function(e){var t,n;if(!e||"string"!=typeof e)return null;try{t=(new ie.DOMParser).parseFromString(e,"text/xml")}catch(e){}return n=t&&t.getElementsByTagName("parsererror")[0],t&&!n||ce.error("Invalid XML: "+(n?ce.map(n.childNodes,function(e){return e.textContent}).join("\n"):e)),t};var Dt=/^(?:focusinfocus|focusoutblur)$/,Nt=function(e){e.stopPropagation()};ce.extend(ce.event,{trigger:function(e,t,n,r){var i,o,a,s,u,l,c,f,p=[n||C],d=ue.call(e,"type")?e.type:e,h=ue.call(e,"namespace")?e.namespace.split("."):[];if(o=f=a=n=n||C,3!==n.nodeType&&8!==n.nodeType&&!Dt.test(d+ce.event.triggered)&&(-1<d.indexOf(".")&&(d=(h=d.split(".")).shift(),h.sort()),u=d.indexOf(":")<0&&"on"+d,(e=e[ce.expando]?e:new ce.Event(d,"object"==typeof e&&e)).isTrigger=r?2:3,e.namespace=h.join("."),e.rnamespace=e.namespace?new RegExp("(^|\\.)"+h.join("\\.(?:.*\\.|)")+"(\\.|$)"):null,e.result=void 0,e.target||(e.target=n),t=null==t?[e]:ce.makeArray(t,[e]),c=ce.event.special[d]||{},r||!c.trigger||!1!==c.trigger.apply(n,t))){if(!r&&!c.noBubble&&!y(n)){for(s=c.delegateType||d,Dt.test(s+d)||(o=o.parentNode);o;o=o.parentNode)p.push(o),a=o;a===(n.ownerDocument||C)&&p.push(a.defaultView||a.parentWindow||ie)}i=0;while((o=p[i++])&&!e.isPropagationStopped())f=o,e.type=1<i?s:c.bindType||d,(l=(_.get(o,"events")||Object.create(null))[e.type]&&_.get(o,"handle"))&&l.apply(o,t),(l=u&&o[u])&&l.apply&&$(o)&&(e.result=l.apply(o,t),!1===e.result&&e.preventDefault());return e.type=d,r||e.isDefaultPrevented()||c._default&&!1!==c._default.apply(p.pop(),t)||!$(n)||u&&v(n[d])&&!y(n)&&((a=n[u])&&(n[u]=null),ce.event.triggered=d,e.isPropagationStopped()&&f.addEventListener(d,Nt),n[d](),e.isPropagationStopped()&&f.removeEventListener(d,Nt),ce.event.triggered=void 0,a&&(n[u]=a)),e.result}},simulate:function(e,t,n){var r=ce.extend(new ce.Event,n,{type:e,isSimulated:!0});ce.event.trigger(r,null,t)}}),ce.fn.extend({trigger:function(e,t){return this.each(function(){ce.event.trigger(e,t,this)})},triggerHandler:function(e,t){var n=this[0];if(n)return ce.event.trigger(e,t,n,!0)}});var qt=/\[\]$/,Lt=/\r?\n/g,Ht=/^(?:submit|button|image|reset|file)$/i,Ot=/^(?:input|select|textarea|keygen)/i;function Pt(n,e,r,i){var t;if(Array.isArray(e))ce.each(e,function(e,t){r||qt.test(n)?i(n,t):Pt(n+"["+("object"==typeof t&&null!=t?e:"")+"]",t,r,i)});else if(r||"object"!==x(e))i(n,e);else for(t in e)Pt(n+"["+t+"]",e[t],r,i)}ce.param=function(e,t){var n,r=[],i=function(e,t){var n=v(t)?t():t;r[r.length]=encodeURIComponent(e)+"="+encodeURIComponent(null==n?"":n)};if(null==e)return"";if(Array.isArray(e)||e.jquery&&!ce.isPlainObject(e))ce.each(e,function(){i(this.name,this.value)});else for(n in e)Pt(n,e[n],t,i);return r.join("&")},ce.fn.extend({serialize:function(){return ce.param(this.serializeArray())},serializeArray:function(){return this.map(function(){var e=ce.prop(this,"elements");return e?ce.makeArray(e):this}).filter(function(){var e=this.type;return this.name&&!ce(this).is(":disabled")&&Ot.test(this.nodeName)&&!Ht.test(e)&&(this.checked||!we.test(e))}).map(function(e,t){var n=ce(this).val();return null==n?null:Array.isArray(n)?ce.map(n,function(e){return{name:t.name,value:e.replace(Lt,"\r\n")}}):{name:t.name,value:n.replace(Lt,"\r\n")}}).get()}});var Mt=/%20/g,Rt=/#.*$/,It=/([?&])_=[^&]*/,Wt=/^(.*?):[ \t]*([^\r\n]*)$/gm,Ft=/^(?:GET|HEAD)$/,$t=/^\/\//,Bt={},_t={},zt="*/".concat("*"),Xt=C.createElement("a");function Ut(o){return function(e,t){"string"!=typeof e&&(t=e,e="*");var n,r=0,i=e.toLowerCase().match(D)||[];if(v(t))while(n=i[r++])"+"===n[0]?(n=n.slice(1)||"*",(o[n]=o[n]||[]).unshift(t)):(o[n]=o[n]||[]).push(t)}}function Vt(t,i,o,a){var s={},u=t===_t;function l(e){var r;return s[e]=!0,ce.each(t[e]||[],function(e,t){var n=t(i,o,a);return"string"!=typeof n||u||s[n]?u?!(r=n):void 0:(i.dataTypes.unshift(n),l(n),!1)}),r}return l(i.dataTypes[0])||!s["*"]&&l("*")}function Gt(e,t){var n,r,i=ce.ajaxSettings.flatOptions||{};for(n in t)void 0!==t[n]&&((i[n]?e:r||(r={}))[n]=t[n]);return r&&ce.extend(!0,e,r),e}Xt.href=Et.href,ce.extend({active:0,lastModified:{},etag:{},ajaxSettings:{url:Et.href,type:"GET",isLocal:/^(?:about|app|app-storage|.+-extension|file|res|widget):$/.test(Et.protocol),global:!0,processData:!0,async:!0,contentType:"application/x-www-form-urlencoded; charset=UTF-8",accepts:{"*":zt,text:"text/plain",html:"text/html",xml:"application/xml, text/xml",json:"application/json, text/javascript"},contents:{xml:/\bxml\b/,html:/\bhtml/,json:/\bjson\b/},responseFields:{xml:"responseXML",text:"responseText",json:"responseJSON"},converters:{"* text":String,"text html":!0,"text json":JSON.parse,"text xml":ce.parseXML},flatOptions:{url:!0,context:!0}},ajaxSetup:function(e,t){return t?Gt(Gt(e,ce.ajaxSettings),t):Gt(ce.ajaxSettings,e)},ajaxPrefilter:Ut(Bt),ajaxTransport:Ut(_t),ajax:function(e,t){"object"==typeof e&&(t=e,e=void 0),t=t||{};var c,f,p,n,d,r,h,g,i,o,v=ce.ajaxSetup({},t),y=v.context||v,m=v.context&&(y.nodeType||y.jquery)?ce(y):ce.event,x=ce.Deferred(),b=ce.Callbacks("once memory"),w=v.statusCode||{},a={},s={},u="canceled",T={readyState:0,getResponseHeader:function(e){var t;if(h){if(!n){n={};while(t=Wt.exec(p))n[t[1].toLowerCase()+" "]=(n[t[1].toLowerCase()+" "]||[]).concat(t[2])}t=n[e.toLowerCase()+" "]}return null==t?null:t.join(", ")},getAllResponseHeaders:function(){return h?p:null},setRequestHeader:function(e,t){return null==h&&(e=s[e.toLowerCase()]=s[e.toLowerCase()]||e,a[e]=t),this},overrideMimeType:function(e){return null==h&&(v.mimeType=e),this},statusCode:function(e){var t;if(e)if(h)T.always(e[T.status]);else for(t in e)w[t]=[w[t],e[t]];return this},abort:function(e){var t=e||u;return c&&c.abort(t),l(0,t),this}};if(x.promise(T),v.url=((e||v.url||Et.href)+"").replace($t,Et.protocol+"//"),v.type=t.method||t.type||v.method||v.type,v.dataTypes=(v.dataType||"*").toLowerCase().match(D)||[""],null==v.crossDomain){r=C.createElement("a");try{r.href=v.url,r.href=r.href,v.crossDomain=Xt.protocol+"//"+Xt.host!=r.protocol+"//"+r.host}catch(e){v.crossDomain=!0}}if(v.data&&v.processData&&"string"!=typeof v.data&&(v.data=ce.param(v.data,v.traditional)),Vt(Bt,v,t,T),h)return T;for(i in(g=ce.event&&v.global)&&0==ce.active++&&ce.event.trigger("ajaxStart"),v.type=v.type.toUpperCase(),v.hasContent=!Ft.test(v.type),f=v.url.replace(Rt,""),v.hasContent?v.data&&v.processData&&0===(v.contentType||"").indexOf("application/x-www-form-urlencoded")&&(v.data=v.data.replace(Mt,"+")):(o=v.url.slice(f.length),v.data&&(v.processData||"string"==typeof v.data)&&(f+=(At.test(f)?"&":"?")+v.data,delete v.data),!1===v.cache&&(f=f.replace(It,"$1"),o=(At.test(f)?"&":"?")+"_="+jt.guid+++o),v.url=f+o),v.ifModified&&(ce.lastModified[f]&&T.setRequestHeader("If-Modified-Since",ce.lastModified[f]),ce.etag[f]&&T.setRequestHeader("If-None-Match",ce.etag[f])),(v.data&&v.hasContent&&!1!==v.contentType||t.contentType)&&T.setRequestHeader("Content-Type",v.contentType),T.setRequestHeader("Accept",v.dataTypes[0]&&v.accepts[v.dataTypes[0]]?v.accepts[v.dataTypes[0]]+("*"!==v.dataTypes[0]?", "+zt+"; q=0.01":""):v.accepts["*"]),v.headers)T.setRequestHeader(i,v.headers[i]);if(v.beforeSend&&(!1===v.beforeSend.call(y,T,v)||h))return T.abort();if(u="abort",b.add(v.complete),T.done(v.success),T.fail(v.error),c=Vt(_t,v,t,T)){if(T.readyState=1,g&&m.trigger("ajaxSend",[T,v]),h)return T;v.async&&0<v.timeout&&(d=ie.setTimeout(function(){T.abort("timeout")},v.timeout));try{h=!1,c.send(a,l)}catch(e){if(h)throw e;l(-1,e)}}else l(-1,"No Transport");function l(e,t,n,r){var i,o,a,s,u,l=t;h||(h=!0,d&&ie.clearTimeout(d),c=void 0,p=r||"",T.readyState=0<e?4:0,i=200<=e&&e<300||304===e,n&&(s=function(e,t,n){var r,i,o,a,s=e.contents,u=e.dataTypes;while("*"===u[0])u.shift(),void 0===r&&(r=e.mimeType||t.getResponseHeader("Content-Type"));if(r)for(i in s)if(s[i]&&s[i].test(r)){u.unshift(i);break}if(u[0]in n)o=u[0];else{for(i in n){if(!u[0]||e.converters[i+" "+u[0]]){o=i;break}a||(a=i)}o=o||a}if(o)return o!==u[0]&&u.unshift(o),n[o]}(v,T,n)),!i&&-1<ce.inArray("script",v.dataTypes)&&ce.inArray("json",v.dataTypes)<0&&(v.converters["text script"]=function(){}),s=function(e,t,n,r){var i,o,a,s,u,l={},c=e.dataTypes.slice();if(c[1])for(a in e.converters)l[a.toLowerCase()]=e.converters[a];o=c.shift();while(o)if(e.responseFields[o]&&(n[e.responseFields[o]]=t),!u&&r&&e.dataFilter&&(t=e.dataFilter(t,e.dataType)),u=o,o=c.shift())if("*"===o)o=u;else if("*"!==u&&u!==o){if(!(a=l[u+" "+o]||l["* "+o]))for(i in l)if((s=i.split(" "))[1]===o&&(a=l[u+" "+s[0]]||l["* "+s[0]])){!0===a?a=l[i]:!0!==l[i]&&(o=s[0],c.unshift(s[1]));break}if(!0!==a)if(a&&e["throws"])t=a(t);else try{t=a(t)}catch(e){return{state:"parsererror",error:a?e:"No conversion from "+u+" to "+o}}}return{state:"success",data:t}}(v,s,T,i),i?(v.ifModified&&((u=T.getResponseHeader("Last-Modified"))&&(ce.lastModified[f]=u),(u=T.getResponseHeader("etag"))&&(ce.etag[f]=u)),204===e||"HEAD"===v.type?l="nocontent":304===e?l="notmodified":(l=s.state,o=s.data,i=!(a=s.error))):(a=l,!e&&l||(l="error",e<0&&(e=0))),T.status=e,T.statusText=(t||l)+"",i?x.resolveWith(y,[o,l,T]):x.rejectWith(y,[T,l,a]),T.statusCode(w),w=void 0,g&&m.trigger(i?"ajaxSuccess":"ajaxError",[T,v,i?o:a]),b.fireWith(y,[T,l]),g&&(m.trigger("ajaxComplete",[T,v]),--ce.active||ce.event.trigger("ajaxStop")))}return T},getJSON:function(e,t,n){return ce.get(e,t,n,"json")},getScript:function(e,t){return ce.get(e,void 0,t,"script")}}),ce.each(["get","post"],function(e,i){ce[i]=function(e,t,n,r){return v(t)&&(r=r||n,n=t,t=void 0),ce.ajax(ce.extend({url:e,type:i,dataType:r,data:t,success:n},ce.isPlainObject(e)&&e))}}),ce.ajaxPrefilter(function(e){var t;for(t in e.headers)"content-type"===t.toLowerCase()&&(e.contentType=e.headers[t]||"")}),ce._evalUrl=function(e,t,n){return ce.ajax({url:e,type:"GET",dataType:"script",cache:!0,async:!1,global:!1,converters:{"text script":function(){}},dataFilter:function(e){ce.globalEval(e,t,n)}})},ce.fn.extend({wrapAll:function(e){var t;return this[0]&&(v(e)&&(e=e.call(this[0])),t=ce(e,this[0].ownerDocument).eq(0).clone(!0),this[0].parentNode&&t.insertBefore(this[0]),t.map(function(){var e=this;while(e.firstElementChild)e=e.firstElementChild;return e}).append(this)),this},wrapInner:function(n){return v(n)?this.each(function(e){ce(this).wrapInner(n.call(this,e))}):this.each(function(){var e=ce(this),t=e.contents();t.length?t.wrapAll(n):e.append(n)})},wrap:function(t){var n=v(t);return this.each(function(e){ce(this).wrapAll(n?t.call(this,e):t)})},unwrap:function(e){return this.parent(e).not("body").each(function(){ce(this).replaceWith(this.childNodes)}),this}}),ce.expr.pseudos.hidden=function(e){return!ce.expr.pseudos.visible(e)},ce.expr.pseudos.visible=function(e){return!!(e.offsetWidth||e.offsetHeight||e.getClientRects().length)},ce.ajaxSettings.xhr=function(){try{return new ie.XMLHttpRequest}catch(e){}};var Yt={0:200,1223:204},Qt=ce.ajaxSettings.xhr();le.cors=!!Qt&&"withCredentials"in Qt,le.ajax=Qt=!!Qt,ce.ajaxTransport(function(i){var o,a;if(le.cors||Qt&&!i.crossDomain)return{send:function(e,t){var n,r=i.xhr();if(r.open(i.type,i.url,i.async,i.username,i.password),i.xhrFields)for(n in i.xhrFields)r[n]=i.xhrFields[n];for(n in i.mimeType&&r.overrideMimeType&&r.overrideMimeType(i.mimeType),i.crossDomain||e["X-Requested-With"]||(e["X-Requested-With"]="XMLHttpRequest"),e)r.setRequestHeader(n,e[n]);o=function(e){return function(){o&&(o=a=r.onload=r.onerror=r.onabort=r.ontimeout=r.onreadystatechange=null,"abort"===e?r.abort():"error"===e?"number"!=typeof r.status?t(0,"error"):t(r.status,r.statusText):t(Yt[r.status]||r.status,r.statusText,"text"!==(r.responseType||"text")||"string"!=typeof r.responseText?{binary:r.response}:{text:r.responseText},r.getAllResponseHeaders()))}},r.onload=o(),a=r.onerror=r.ontimeout=o("error"),void 0!==r.onabort?r.onabort=a:r.onreadystatechange=function(){4===r.readyState&&ie.setTimeout(function(){o&&a()})},o=o("abort");try{r.send(i.hasContent&&i.data||null)}catch(e){if(o)throw e}},abort:function(){o&&o()}}}),ce.ajaxPrefilter(function(e){e.crossDomain&&(e.contents.script=!1)}),ce.ajaxSetup({accepts:{script:"text/javascript, application/javascript, application/ecmascript, application/x-ecmascript"},contents:{script:/\b(?:java|ecma)script\b/},converters:{"text script":function(e){return ce.globalEval(e),e}}}),ce.ajaxPrefilter("script",function(e){void 0===e.cache&&(e.cache=!1),e.crossDomain&&(e.type="GET")}),ce.ajaxTransport("script",function(n){var r,i;if(n.crossDomain||n.scriptAttrs)return{send:function(e,t){r=ce("<script>").attr(n.scriptAttrs||{}).prop({charset:n.scriptCharset,src:n.url}).on("load error",i=function(e){r.remove(),i=null,e&&t("error"===e.type?404:200,e.type)}),C.head.appendChild(r[0])},abort:function(){i&&i()}}});var Jt,Kt=[],Zt=/(=)\?(?=&|$)|\?\?/;ce.ajaxSetup({jsonp:"callback",jsonpCallback:function(){var e=Kt.pop()||ce.expando+"_"+jt.guid++;return this[e]=!0,e}}),ce.ajaxPrefilter("json jsonp",function(e,t,n){var r,i,o,a=!1!==e.jsonp&&(Zt.test(e.url)?"url":"string"==typeof e.data&&0===(e.contentType||"").indexOf("application/x-www-form-urlencoded")&&Zt.test(e.data)&&"data");if(a||"jsonp"===e.dataTypes[0])return r=e.jsonpCallback=v(e.jsonpCallback)?e.jsonpCallback():e.jsonpCallback,a?e[a]=e[a].replace(Zt,"$1"+r):!1!==e.jsonp&&(e.url+=(At.test(e.url)?"&":"?")+e.jsonp+"="+r),e.converters["script json"]=function(){return o||ce.error(r+" was not called"),o[0]},e.dataTypes[0]="json",i=ie[r],ie[r]=function(){o=arguments},n.always(function(){void 0===i?ce(ie).removeProp(r):ie[r]=i,e[r]&&(e.jsonpCallback=t.jsonpCallback,Kt.push(r)),o&&v(i)&&i(o[0]),o=i=void 0}),"script"}),le.createHTMLDocument=((Jt=C.implementation.createHTMLDocument("").body).innerHTML="<form></form><form></form>",2===Jt.childNodes.length),ce.parseHTML=function(e,t,n){return"string"!=typeof e?[]:("boolean"==typeof t&&(n=t,t=!1),t||(le.createHTMLDocument?((r=(t=C.implementation.createHTMLDocument("")).createElement("base")).href=C.location.href,t.head.appendChild(r)):t=C),o=!n&&[],(i=w.exec(e))?[t.createElement(i[1])]:(i=Ae([e],t,o),o&&o.length&&ce(o).remove(),ce.merge([],i.childNodes)));var r,i,o},ce.fn.load=function(e,t,n){var r,i,o,a=this,s=e.indexOf(" ");return-1<s&&(r=Tt(e.slice(s)),e=e.slice(0,s)),v(t)?(n=t,t=void 0):t&&"object"==typeof t&&(i="POST"),0<a.length&&ce.ajax({url:e,type:i||"GET",dataType:"html",data:t}).done(function(e){o=arguments,a.html(r?ce("<div>").append(ce.parseHTML(e)).find(r):e)}).always(n&&function(e,t){a.each(function(){n.apply(this,o||[e.responseText,t,e])})}),this},ce.expr.pseudos.animated=function(t){return ce.grep(ce.timers,function(e){return t===e.elem}).length},ce.offset={setOffset:function(e,t,n){var r,i,o,a,s,u,l=ce.css(e,"position"),c=ce(e),f={};"static"===l&&(e.style.position="relative"),s=c.offset(),o=ce.css(e,"top"),u=ce.css(e,"left"),("absolute"===l||"fixed"===l)&&-1<(o+u).indexOf("auto")?(a=(r=c.position()).top,i=r.left):(a=parseFloat(o)||0,i=parseFloat(u)||0),v(t)&&(t=t.call(e,n,ce.extend({},s))),null!=t.top&&(f.top=t.top-s.top+a),null!=t.left&&(f.left=t.left-s.left+i),"using"in t?t.using.call(e,f):c.css(f)}},ce.fn.extend({offset:function(t){if(arguments.length)return void 0===t?this:this.each(function(e){ce.offset.setOffset(this,t,e)});var e,n,r=this[0];return r?r.getClientRects().length?(e=r.getBoundingClientRect(),n=r.ownerDocument.defaultView,{top:e.top+n.pageYOffset,left:e.left+n.pageXOffset}):{top:0,left:0}:void 0},position:function(){if(this[0]){var e,t,n,r=this[0],i={top:0,left:0};if("fixed"===ce.css(r,"position"))t=r.getBoundingClientRect();else{t=this.offset(),n=r.ownerDocument,e=r.offsetParent||n.documentElement;while(e&&(e===n.body||e===n.documentElement)&&"static"===ce.css(e,"position"))e=e.parentNode;e&&e!==r&&1===e.nodeType&&((i=ce(e).offset()).top+=ce.css(e,"borderTopWidth",!0),i.left+=ce.css(e,"borderLeftWidth",!0))}return{top:t.top-i.top-ce.css(r,"marginTop",!0),left:t.left-i.left-ce.css(r,"marginLeft",!0)}}},offsetParent:function(){return this.map(function(){var e=this.offsetParent;while(e&&"static"===ce.css(e,"position"))e=e.offsetParent;return e||J})}}),ce.each({scrollLeft:"pageXOffset",scrollTop:"pageYOffset"},function(t,i){var o="pageYOffset"===i;ce.fn[t]=function(e){return M(this,function(e,t,n){var r;if(y(e)?r=e:9===e.nodeType&&(r=e.defaultView),void 0===n)return r?r[i]:e[t];r?r.scrollTo(o?r.pageXOffset:n,o?n:r.pageYOffset):e[t]=n},t,e,arguments.length)}}),ce.each(["top","left"],function(e,n){ce.cssHooks[n]=Ye(le.pixelPosition,function(e,t){if(t)return t=Ge(e,n),_e.test(t)?ce(e).position()[n]+"px":t})}),ce.each({Height:"height",Width:"width"},function(a,s){ce.each({padding:"inner"+a,content:s,"":"outer"+a},function(r,o){ce.fn[o]=function(e,t){var n=arguments.length&&(r||"boolean"!=typeof e),i=r||(!0===e||!0===t?"margin":"border");return M(this,function(e,t,n){var r;return y(e)?0===o.indexOf("outer")?e["inner"+a]:e.document.documentElement["client"+a]:9===e.nodeType?(r=e.documentElement,Math.max(e.body["scroll"+a],r["scroll"+a],e.body["offset"+a],r["offset"+a],r["client"+a])):void 0===n?ce.css(e,t,i):ce.style(e,t,n,i)},s,n?e:void 0,n)}})}),ce.each(["ajaxStart","ajaxStop","ajaxComplete","ajaxError","ajaxSuccess","ajaxSend"],function(e,t){ce.fn[t]=function(e){return this.on(t,e)}}),ce.fn.extend({bind:function(e,t,n){return this.on(e,null,t,n)},unbind:function(e,t){return this.off(e,null,t)},delegate:function(e,t,n,r){return this.on(t,e,n,r)},undelegate:function(e,t,n){return 1===arguments.length?this.off(e,"**"):this.off(t,e||"**",n)},hover:function(e,t){return this.on("mouseenter",e).on("mouseleave",t||e)}}),ce.each("blur focus focusin focusout resize scroll click dblclick mousedown mouseup mousemove mouseover mouseout mouseenter mouseleave change select submit keydown keypress keyup contextmenu".split(" "),function(e,n){ce.fn[n]=function(e,t){return 0<arguments.length?this.on(n,null,e,t):this.trigger(n)}});var en=/^[\s\uFEFF\xA0]+|([^\s\uFEFF\xA0])[\s\uFEFF\xA0]+$/g;ce.proxy=function(e,t){var n,r,i;if("string"==typeof t&&(n=e[t],t=e,e=n),v(e))return r=ae.call(arguments,2),(i=function(){return e.apply(t||this,r.concat(ae.call(arguments)))}).guid=e.guid=e.guid||ce.guid++,i},ce.holdReady=function(e){e?ce.readyWait++:ce.ready(!0)},ce.isArray=Array.isArray,ce.parseJSON=JSON.parse,ce.nodeName=fe,ce.isFunction=v,ce.isWindow=y,ce.camelCase=F,ce.type=x,ce.now=Date.now,ce.isNumeric=function(e){var t=ce.type(e);return("number"===t||"string"===t)&&!isNaN(e-parseFloat(e))},ce.trim=function(e){return null==e?"":(e+"").replace(en,"$1")},"function"==typeof define&&define.amd&&define("jquery",[],function(){return ce});var tn=ie.jQuery,nn=ie.$;return ce.noConflict=function(e){return ie.$===ce&&(ie.$=nn),e&&ie.jQuery===ce&&(ie.jQuery=tn),ce},"undefined"==typeof e&&(ie.jQuery=ie.$=ce),ce});
|
js/wchess.wasm.js
ADDED
The diff for this file is too large to render.
See raw diff
|
|
js/wchess.wasm.worker.js
ADDED
@@ -0,0 +1 @@
|
|
|
|
|
1 |
+
"use strict";var Module={};var ENVIRONMENT_IS_NODE=typeof process=="object"&&typeof process.versions=="object"&&typeof process.versions.node=="string";if(ENVIRONMENT_IS_NODE){var nodeWorkerThreads=require("worker_threads");var parentPort=nodeWorkerThreads.parentPort;parentPort.on("message",data=>onmessage({data:data}));var fs=require("fs");Object.assign(global,{self:global,require:require,Module:Module,location:{href:__filename},Worker:nodeWorkerThreads.Worker,importScripts:f=>(0,eval)(fs.readFileSync(f,"utf8")+"//# sourceURL="+f),postMessage:msg=>parentPort.postMessage(msg),performance:global.performance||{now:Date.now}})}var initializedJS=false;function threadPrintErr(){var text=Array.prototype.slice.call(arguments).join(" ");if(ENVIRONMENT_IS_NODE){fs.writeSync(2,text+"\n");return}console.error(text)}function threadAlert(){var text=Array.prototype.slice.call(arguments).join(" ");postMessage({cmd:"alert",text:text,threadId:Module["_pthread_self"]()})}var err=threadPrintErr;self.alert=threadAlert;Module["instantiateWasm"]=(info,receiveInstance)=>{var module=Module["wasmModule"];Module["wasmModule"]=null;var instance=new WebAssembly.Instance(module,info);return receiveInstance(instance)};self.onunhandledrejection=e=>{throw e.reason||e};function handleMessage(e){try{if(e.data.cmd==="load"){let messageQueue=[];self.onmessage=e=>messageQueue.push(e);self.startWorker=instance=>{postMessage({"cmd":"loaded"});for(let msg of messageQueue){handleMessage(msg)}self.onmessage=handleMessage};Module["wasmModule"]=e.data.wasmModule;for(const handler of e.data.handlers){Module[handler]=(...args)=>{postMessage({cmd:"callHandler",handler:handler,args:args})}}Module["wasmMemory"]=e.data.wasmMemory;Module["buffer"]=Module["wasmMemory"].buffer;Module["ENVIRONMENT_IS_PTHREAD"]=true;if(typeof e.data.urlOrBlob=="string"){importScripts(e.data.urlOrBlob)}else{var objectUrl=URL.createObjectURL(e.data.urlOrBlob);importScripts(objectUrl);URL.revokeObjectURL(objectUrl)}}else if(e.data.cmd==="run"){Module["__emscripten_thread_init"](e.data.pthread_ptr,0,0,1);Module["__emscripten_thread_mailbox_await"](e.data.pthread_ptr);Module["establishStackSpace"]();Module["PThread"].receiveObjectTransfer(e.data);Module["PThread"].threadInitTLS();if(!initializedJS){Module["__embind_initialize_bindings"]();initializedJS=true}try{Module["invokeEntryPoint"](e.data.start_routine,e.data.arg)}catch(ex){if(ex!="unwind"){throw ex}}}else if(e.data.cmd==="cancel"){if(Module["_pthread_self"]()){Module["__emscripten_thread_exit"](-1)}}else if(e.data.target==="setimmediate"){}else if(e.data.cmd==="checkMailbox"){if(initializedJS){Module["checkMailbox"]()}}else if(e.data.cmd){err(`worker.js received unknown command ${e.data.cmd}`);err(e.data)}}catch(ex){if(Module["__emscripten_thread_crashed"]){Module["__emscripten_thread_crashed"]()}throw ex}}self.onmessage=handleMessage;
|
libmain.worker.js
DELETED
@@ -1 +0,0 @@
|
|
1 |
-
"use strict";var Module={};var ENVIRONMENT_IS_NODE=typeof process=="object"&&typeof process.versions=="object"&&typeof process.versions.node=="string";if(ENVIRONMENT_IS_NODE){var nodeWorkerThreads=require("worker_threads");var parentPort=nodeWorkerThreads.parentPort;parentPort.on("message",data=>onmessage({data:data}));var fs=require("fs");Object.assign(global,{self:global,require:require,Module:Module,location:{href:__filename},Worker:nodeWorkerThreads.Worker,importScripts:function(f){(0,eval)(fs.readFileSync(f,"utf8")+"//# sourceURL="+f)},postMessage:function(msg){parentPort.postMessage(msg)},performance:global.performance||{now:function(){return Date.now()}}})}var initializedJS=false;var pendingNotifiedProxyingQueues=[];function threadPrintErr(){var text=Array.prototype.slice.call(arguments).join(" ");if(ENVIRONMENT_IS_NODE){fs.writeSync(2,text+"\n");return}console.error(text)}function threadAlert(){var text=Array.prototype.slice.call(arguments).join(" ");postMessage({cmd:"alert",text:text,threadId:Module["_pthread_self"]()})}var err=threadPrintErr;self.alert=threadAlert;Module["instantiateWasm"]=(info,receiveInstance)=>{var instance=new WebAssembly.Instance(Module["wasmModule"],info);receiveInstance(instance);Module["wasmModule"]=null;return instance.exports};self.onunhandledrejection=e=>{throw e.reason??e};function handleMessage(e){try{if(e.data.cmd==="load"){let messageQueue=[];self.onmessage=e=>messageQueue.push(e);self.startWorker=instance=>{postMessage({"cmd":"loaded"});for(let msg of messageQueue){handleMessage(msg)}self.onmessage=handleMessage};Module["wasmModule"]=e.data.wasmModule;for(const handler of e.data.handlers){Module[handler]=function(){postMessage({cmd:"callHandler",handler:handler,args:[...arguments]})}}Module["wasmMemory"]=e.data.wasmMemory;Module["buffer"]=Module["wasmMemory"].buffer;Module["ENVIRONMENT_IS_PTHREAD"]=true;if(typeof e.data.urlOrBlob=="string"){importScripts(e.data.urlOrBlob)}else{var objectUrl=URL.createObjectURL(e.data.urlOrBlob);importScripts(objectUrl);URL.revokeObjectURL(objectUrl)}}else if(e.data.cmd==="run"){Module["__emscripten_thread_init"](e.data.pthread_ptr,0,0,1);Module["establishStackSpace"]();Module["PThread"].receiveObjectTransfer(e.data);Module["PThread"].threadInitTLS();if(!initializedJS){Module["__embind_initialize_bindings"]();pendingNotifiedProxyingQueues.forEach(queue=>{Module["executeNotifiedProxyingQueue"](queue)});pendingNotifiedProxyingQueues=[];initializedJS=true}try{Module["invokeEntryPoint"](e.data.start_routine,e.data.arg)}catch(ex){if(ex!="unwind"){if(ex instanceof Module["ExitStatus"]){if(Module["keepRuntimeAlive"]()){}else{Module["__emscripten_thread_exit"](ex.status)}}else{throw ex}}}}else if(e.data.cmd==="cancel"){if(Module["_pthread_self"]()){Module["__emscripten_thread_exit"](-1)}}else if(e.data.target==="setimmediate"){}else if(e.data.cmd==="processProxyingQueue"){if(initializedJS){Module["executeNotifiedProxyingQueue"](e.data.queue)}else{pendingNotifiedProxyingQueues.push(e.data.queue)}}else if(e.data.cmd){err("worker.js received unknown command "+e.data.cmd);err(e.data)}}catch(ex){if(Module["__emscripten_thread_crashed"]){Module["__emscripten_thread_crashed"]()}throw ex}}self.onmessage=handleMessage;
|
|
|
|
libwhisper.worker.js
DELETED
@@ -1 +0,0 @@
|
|
1 |
-
"use strict";var Module={};var ENVIRONMENT_IS_NODE=typeof process=="object"&&typeof process.versions=="object"&&typeof process.versions.node=="string";if(ENVIRONMENT_IS_NODE){var nodeWorkerThreads=require("worker_threads");var parentPort=nodeWorkerThreads.parentPort;parentPort.on("message",data=>onmessage({data:data}));var fs=require("fs");Object.assign(global,{self:global,require:require,Module:Module,location:{href:__filename},Worker:nodeWorkerThreads.Worker,importScripts:function(f){(0,eval)(fs.readFileSync(f,"utf8")+"//# sourceURL="+f)},postMessage:function(msg){parentPort.postMessage(msg)},performance:global.performance||{now:function(){return Date.now()}}})}var initializedJS=false;var pendingNotifiedProxyingQueues=[];function threadPrintErr(){var text=Array.prototype.slice.call(arguments).join(" ");if(ENVIRONMENT_IS_NODE){fs.writeSync(2,text+"\n");return}console.error(text)}function threadAlert(){var text=Array.prototype.slice.call(arguments).join(" ");postMessage({cmd:"alert",text:text,threadId:Module["_pthread_self"]()})}var err=threadPrintErr;self.alert=threadAlert;Module["instantiateWasm"]=(info,receiveInstance)=>{var instance=new WebAssembly.Instance(Module["wasmModule"],info);receiveInstance(instance);Module["wasmModule"]=null;return instance.exports};self.onunhandledrejection=e=>{throw e.reason??e};function handleMessage(e){try{if(e.data.cmd==="load"){let messageQueue=[];self.onmessage=e=>messageQueue.push(e);self.startWorker=instance=>{Module=instance;postMessage({"cmd":"loaded"});for(let msg of messageQueue){handleMessage(msg)}self.onmessage=handleMessage};Module["wasmModule"]=e.data.wasmModule;for(const handler of e.data.handlers){Module[handler]=function(){postMessage({cmd:"callHandler",handler:handler,args:[...arguments]})}}Module["wasmMemory"]=e.data.wasmMemory;Module["buffer"]=Module["wasmMemory"].buffer;Module["ENVIRONMENT_IS_PTHREAD"]=true;if(typeof e.data.urlOrBlob=="string"){importScripts(e.data.urlOrBlob)}else{var objectUrl=URL.createObjectURL(e.data.urlOrBlob);importScripts(objectUrl);URL.revokeObjectURL(objectUrl)}whisper_factory(Module)}else if(e.data.cmd==="run"){Module["__emscripten_thread_init"](e.data.pthread_ptr,0,0,1);Module["establishStackSpace"]();Module["PThread"].receiveObjectTransfer(e.data);Module["PThread"].threadInitTLS();if(!initializedJS){Module["__embind_initialize_bindings"]();pendingNotifiedProxyingQueues.forEach(queue=>{Module["executeNotifiedProxyingQueue"](queue)});pendingNotifiedProxyingQueues=[];initializedJS=true}try{Module["invokeEntryPoint"](e.data.start_routine,e.data.arg)}catch(ex){if(ex!="unwind"){if(ex instanceof Module["ExitStatus"]){if(Module["keepRuntimeAlive"]()){}else{Module["__emscripten_thread_exit"](ex.status)}}else{throw ex}}}}else if(e.data.cmd==="cancel"){if(Module["_pthread_self"]()){Module["__emscripten_thread_exit"](-1)}}else if(e.data.target==="setimmediate"){}else if(e.data.cmd==="processProxyingQueue"){if(initializedJS){Module["executeNotifiedProxyingQueue"](e.data.queue)}else{pendingNotifiedProxyingQueues.push(e.data.queue)}}else if(e.data.cmd){err("worker.js received unknown command "+e.data.cmd);err(e.data)}}catch(ex){if(Module["__emscripten_thread_crashed"]){Module["__emscripten_thread_crashed"]()}throw ex}}self.onmessage=handleMessage;
|
|
|
|
models/.gitattributes
DELETED
@@ -1,51 +0,0 @@
|
|
1 |
-
*.7z filter=lfs diff=lfs merge=lfs -text
|
2 |
-
*.arrow filter=lfs diff=lfs merge=lfs -text
|
3 |
-
*.bin filter=lfs diff=lfs merge=lfs -text
|
4 |
-
*.bz2 filter=lfs diff=lfs merge=lfs -text
|
5 |
-
*.ftz filter=lfs diff=lfs merge=lfs -text
|
6 |
-
*.gz filter=lfs diff=lfs merge=lfs -text
|
7 |
-
*.h5 filter=lfs diff=lfs merge=lfs -text
|
8 |
-
*.joblib filter=lfs diff=lfs merge=lfs -text
|
9 |
-
*.lfs.* filter=lfs diff=lfs merge=lfs -text
|
10 |
-
*.lz4 filter=lfs diff=lfs merge=lfs -text
|
11 |
-
*.model filter=lfs diff=lfs merge=lfs -text
|
12 |
-
*.msgpack filter=lfs diff=lfs merge=lfs -text
|
13 |
-
*.npy filter=lfs diff=lfs merge=lfs -text
|
14 |
-
*.npz filter=lfs diff=lfs merge=lfs -text
|
15 |
-
*.onnx filter=lfs diff=lfs merge=lfs -text
|
16 |
-
*.ot filter=lfs diff=lfs merge=lfs -text
|
17 |
-
*.parquet filter=lfs diff=lfs merge=lfs -text
|
18 |
-
*.pb filter=lfs diff=lfs merge=lfs -text
|
19 |
-
*.pickle filter=lfs diff=lfs merge=lfs -text
|
20 |
-
*.pkl filter=lfs diff=lfs merge=lfs -text
|
21 |
-
*.pt filter=lfs diff=lfs merge=lfs -text
|
22 |
-
*.pth filter=lfs diff=lfs merge=lfs -text
|
23 |
-
*.rar filter=lfs diff=lfs merge=lfs -text
|
24 |
-
saved_model/**/* filter=lfs diff=lfs merge=lfs -text
|
25 |
-
*.tar.* filter=lfs diff=lfs merge=lfs -text
|
26 |
-
*.tflite filter=lfs diff=lfs merge=lfs -text
|
27 |
-
*.tgz filter=lfs diff=lfs merge=lfs -text
|
28 |
-
*.wasm filter=lfs diff=lfs merge=lfs -text
|
29 |
-
*.xz filter=lfs diff=lfs merge=lfs -text
|
30 |
-
*.zip filter=lfs diff=lfs merge=lfs -text
|
31 |
-
*.zst filter=lfs diff=lfs merge=lfs -text
|
32 |
-
*tfevents* filter=lfs diff=lfs merge=lfs -text
|
33 |
-
# Audio files - uncompressed
|
34 |
-
*.pcm filter=lfs diff=lfs merge=lfs -text
|
35 |
-
*.sam filter=lfs diff=lfs merge=lfs -text
|
36 |
-
*.raw filter=lfs diff=lfs merge=lfs -text
|
37 |
-
# Audio files - compressed
|
38 |
-
*.aac filter=lfs diff=lfs merge=lfs -text
|
39 |
-
*.flac filter=lfs diff=lfs merge=lfs -text
|
40 |
-
*.mp3 filter=lfs diff=lfs merge=lfs -text
|
41 |
-
*.ogg filter=lfs diff=lfs merge=lfs -text
|
42 |
-
*.wav filter=lfs diff=lfs merge=lfs -text
|
43 |
-
# Image files - uncompressed
|
44 |
-
*.bmp filter=lfs diff=lfs merge=lfs -text
|
45 |
-
*.gif filter=lfs diff=lfs merge=lfs -text
|
46 |
-
*.png filter=lfs diff=lfs merge=lfs -text
|
47 |
-
*.tiff filter=lfs diff=lfs merge=lfs -text
|
48 |
-
# Image files - compressed
|
49 |
-
*.jpg filter=lfs diff=lfs merge=lfs -text
|
50 |
-
*.jpeg filter=lfs diff=lfs merge=lfs -text
|
51 |
-
*.webp filter=lfs diff=lfs merge=lfs -text
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
models/README.md
DELETED
@@ -1,24 +0,0 @@
|
|
1 |
-
---
|
2 |
-
license: mit
|
3 |
-
---
|
4 |
-
|
5 |
-
# OpenAI's Whisper models converted to ggml format
|
6 |
-
|
7 |
-
[Available models](https://huggingface.co/datasets/ggerganov/whisper.cpp/tree/main)
|
8 |
-
|
9 |
-
| Model | Disk | Mem | SHA |
|
10 |
-
| --- | --- | --- | --- |
|
11 |
-
| tiny | 75 MB | ~390 MB | `bd577a113a864445d4c299885e0cb97d4ba92b5f` |
|
12 |
-
| tiny.en | 75 MB | ~390 MB | `c78c86eb1a8faa21b369bcd33207cc90d64ae9df` |
|
13 |
-
| base | 142 MB | ~500 MB | `465707469ff3a37a2b9b8d8f89f2f99de7299dac` |
|
14 |
-
| base.en | 142 MB | ~500 MB | `137c40403d78fd54d454da0f9bd998f78703390c` |
|
15 |
-
| small | 466 MB | ~1.0 GB | `55356645c2b361a969dfd0ef2c5a50d530afd8d5` |
|
16 |
-
| small.en | 466 MB | ~1.0 GB | `db8a495a91d927739e50b3fc1cc4c6b8f6c2d022` |
|
17 |
-
| medium | 1.5 GB | ~2.6 GB | `fd9727b6e1217c2f614f9b698455c4ffd82463b4` |
|
18 |
-
| medium.en | 1.5 GB | ~2.6 GB | `8c30f0e44ce9560643ebd10bbe50cd20eafd3723` |
|
19 |
-
| large-v1 | 2.9 GB | ~4.7 GB | `b1caaf735c4cc1429223d5a74f0f4d0b9b59a299` |
|
20 |
-
| large | 2.9 GB | ~4.7 GB | `0f4c8e34f21cf1a914c59d8b3ce882345ad349d6` |
|
21 |
-
|
22 |
-
For more information, visit:
|
23 |
-
|
24 |
-
https://github.com/ggerganov/whisper.cpp/tree/master/models
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
models/ggml-base.bin
DELETED
@@ -1,3 +0,0 @@
|
|
1 |
-
version https://git-lfs.github.com/spec/v1
|
2 |
-
oid sha256:60ed5bc3dd14eea856493d334349b405782ddcaf0028d4b5df4088345fba2efe
|
3 |
-
size 147951465
|
|
|
|
|
|
|
|
models/ggml-base.en.bin
DELETED
@@ -1,3 +0,0 @@
|
|
1 |
-
version https://git-lfs.github.com/spec/v1
|
2 |
-
oid sha256:a03779c86df3323075f5e796cb2ce5029f00ec8869eee3fdfb897afe36c6d002
|
3 |
-
size 147964211
|
|
|
|
|
|
|
|
models/ggml-tiny.bin
DELETED
@@ -1,3 +0,0 @@
|
|
1 |
-
version https://git-lfs.github.com/spec/v1
|
2 |
-
oid sha256:be07e048e1e599ad46341c8d2a135645097a538221678b7acdd1b1919c6e1b21
|
3 |
-
size 77691713
|
|
|
|
|
|
|
|
models/ggml-tiny.en.bin
DELETED
@@ -1,3 +0,0 @@
|
|
1 |
-
version https://git-lfs.github.com/spec/v1
|
2 |
-
oid sha256:921e4cf8686fdd993dcd081a5da5b6c365bfde1162e72b08d75ac75289920b1f
|
3 |
-
size 77704715
|
|
|
|
|
|
|
|