├── .gitignore ├── js ├── main.js ├── midi-utils.js ├── midi-logger.js └── WebMIDIAPI.js ├── readme.md ├── styles.css └── index.html /.gitignore: -------------------------------------------------------------------------------- 1 | .DS_Store -------------------------------------------------------------------------------- /js/main.js: -------------------------------------------------------------------------------- 1 | var midiLogger = new MidiLogger(); 2 | window.addEventListener('load', midiLogger.init); -------------------------------------------------------------------------------- /readme.md: -------------------------------------------------------------------------------- 1 | #Midi Logger 2 | 3 | Midi logger is a Web Midi tool that simply logs incoming signals to a table. There are a few options to customise how the signals appear. A short and simple little app. To run it on your own system, clone the repo or download the zip file, then simply open the `index.html` file in your browser. 4 | 5 | ###To Do List 6 | * Add a cookie system to remember settings -------------------------------------------------------------------------------- /js/midi-utils.js: -------------------------------------------------------------------------------- 1 | // Based on Midi Utils Library 2 | // https://github.com/sole/MIDIUtils/blob/master/src/MIDIUtils.js 3 | 4 | var MIDIUtils = { 5 | 6 | noteMap: {}, 7 | noteNumberMap: [], 8 | notes: [ "C", "C#", "D", "D#", "E", "F", "F#", "G", "G#", "A", "A#", "B" ], 9 | 10 | init: function(){ 11 | 12 | for (var i = 0; i < 127; i++) { 13 | 14 | var index = i, 15 | key = this.notes[index % 12], 16 | octave = ((index / 12) | 0) - 1; // MIDI scale starts at octave = -1 17 | 18 | if(key.length === 1) { 19 | key = key; 20 | } 21 | 22 | key += octave; 23 | 24 | this.noteMap[key] = i; 25 | this.noteNumberMap[i] = key; 26 | } 27 | }, 28 | 29 | getBaseLog: function(value, base) { 30 | return Math.log(value) / Math.log(base); 31 | }, 32 | 33 | frequencyFromNoteNumber: function(note) { 34 | return 440 * Math.pow(2,(note-57)/12); 35 | }, 36 | 37 | noteNumberToName: function(note) { 38 | 39 | return this.noteNumberMap[note]; 40 | }, 41 | 42 | frequencyToNoteNumber: function(f) { 43 | return Math.round(12.0 * this.getBaseLog(f / 440.0, 2) + 69); 44 | } 45 | 46 | }; 47 | 48 | MIDIUtils.init(); -------------------------------------------------------------------------------- /styles.css: -------------------------------------------------------------------------------- 1 | @import url(http://fonts.googleapis.com/css?family=Karla:400,700); 2 | body { 3 | font-family:Karla, sans-serif; 4 | } 5 | 6 | .warning { 7 | color:#F60; 8 | } 9 | 10 | h2 { 11 | font-size: 14px; 12 | margin-bottom: 5px; 13 | } 14 | 15 | table { 16 | border-collapse: collapse; 17 | margin: 0 auto; 18 | } 19 | 20 | th, td{ 21 | border:1px solid #ccc; 22 | padding:10px; 23 | text-align:center; 24 | background:#f8f8f8; 25 | } 26 | 27 | .midi-logger-page label { 28 | font-size: 13px; 29 | } 30 | 31 | .midi-log-table { 32 | border-collapse:collapse; 33 | border-spacing:0; 34 | width:100%; 35 | } 36 | 37 | .midi-log-table td { 38 | text-align:left; 39 | font-family:menlo, monospace; 40 | font-size:14px; 41 | padding:10px 5px; 42 | border-style:solid; 43 | border-width:1px; 44 | overflow:hidden; 45 | word-break:normal; 46 | background:#fff; 47 | } 48 | .midi-log-table th { 49 | text-align:left; 50 | font-family: menlo, monospace; 51 | font-size:14px; 52 | font-weight:normal; 53 | padding:10px 5px; 54 | border-style:solid; 55 | border-width:1px; 56 | overflow:hidden; 57 | word-break:normal; 58 | background:#f8f8f8; 59 | } 60 | 61 | .midi-logger-page .page-wrapper{ 62 | max-width: 90%; 63 | margin: 0 auto; 64 | width:1000px; 65 | padding: 5% 0 3%; 66 | } 67 | 68 | .midi-logger-page h1 { 69 | text-align: center; 70 | } 71 | 72 | 73 | .hide-time-column .time-column, 74 | .hide-channel-column .channel-column, 75 | .hide-channel-message-column .channel-message-column, 76 | .hide-channel-message-desc-column .channel-message-desc-column, 77 | .hide-data-byte-1-column .data-byte-1-column, 78 | .hide-data-byte-2-column .data-byte-2-column, 79 | .hide-manufacturer-column .manufacturer-column, 80 | .hide-model-column .model-column{ 81 | display: none; 82 | } 83 | 84 | .column-visibility-toggles { 85 | margin-bottom: 1em; 86 | } 87 | 88 | .column-visibility-toggles p, 89 | .number-format-choosers p { 90 | margin-bottom: 0; 91 | font-weight: bold; 92 | } 93 | 94 | .column-visibility-toggles, 95 | .number-format-choosers { 96 | padding:5px 0px 5px 18px; 97 | background:#f8f8f8; 98 | } 99 | 100 | .column-visibility-toggles label, 101 | .number-format-choosers label { 102 | padding: 10px 18px 10px 0; 103 | display: inline-block; 104 | } 105 | 106 | .midi-logger-page ul { 107 | max-width:600px; 108 | } 109 | 110 | .midi-logger-page .intro { 111 | margin-bottom: 2em; 112 | } -------------------------------------------------------------------------------- /index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | Midi Signal Logger 5 | 6 | 7 | 8 | 9 | 10 | Fork me on GitHub 11 |
12 |
13 |

Midi Logger

14 | 15 |

16 | This Midi Logger will print any midi input to your browser to the table below, with new signals appearing at the top. This is all possible because of the Web Midi API. 17 |

18 | 19 |

20 | Please note 21 |

29 |

30 | 31 |

32 | 33 |
34 |
35 |

Show/hide columns

36 |
37 | 40 | 43 | 46 | 49 | 52 | 55 | 58 | 61 |
62 |
63 | 64 |
65 | 66 |

Other settings

67 | 68 |
69 | 76 | 77 | 84 | 85 | 88 | 89 | 97 |
98 |
99 |
100 |
101 | 102 | 103 | 104 | 105 | 106 | 107 | 108 | 109 | 110 | 111 | 112 | 113 | 114 |
TimeChannelChannel messageChannel message descData byte 1Data byte 2ManufacturerModel
115 | 116 |
117 | 118 | 119 | 120 | 121 | 122 | 123 | -------------------------------------------------------------------------------- /js/midi-logger.js: -------------------------------------------------------------------------------- 1 | // Thanks to Chris Wilson for the code to get the midi signals 2 | /* Copyright 2013 Chris Wilson 3 | 4 | Licensed under the Apache License, Version 2.0 (the "License"); 5 | you may not use this file except in compliance with the License. 6 | You may obtain a copy of the License at 7 | 8 | http://www.apache.org/licenses/LICENSE-2.0 9 | 10 | Unless required by applicable law or agreed to in writing, software 11 | distributed under the License is distributed on an "AS IS" BASIS, 12 | WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | See the License for the specific language governing permissions and 14 | limitations under the License. 15 | */ 16 | 17 | 18 | var MidiLogger = function(){ 19 | 20 | this.maxRows = 100; 21 | this.rowCounter = 0; 22 | this.context = null; // the Web Audio "context" object 23 | this.midiAccess = null; // the MIDIAccess object. 24 | var _this = this; 25 | 26 | this.init = function() { 27 | 28 | if (navigator.requestMIDIAccess){ 29 | navigator.requestMIDIAccess().then( 30 | _this.onMIDIInit, 31 | _this.onMIDIReject 32 | ); 33 | } 34 | 35 | $(".js-column-toggle").change(function(e){ 36 | $(".js-midi-log-table").toggleClass($(this).data("class-to-toggle")); 37 | }); 38 | 39 | $("#row-count-switcher").change(function(){ 40 | this.maxRows = $(this).val(); 41 | this.rowCounter = $(".js-midi-log-table tr").length - 1; 42 | 43 | $(".js-midi-log-table tr").filter(":gt("+$(this).val()+")").remove(); 44 | }); 45 | 46 | } 47 | 48 | this.hookUpMIDIInput = function() { 49 | var haveAtLeastOneDevice = false; 50 | var inputs = _this.midiAccess.inputs.values(); 51 | for (var input = inputs.next(); input && !input.done; input = inputs.next()) { 52 | console.log(input); 53 | input.value.onmidimessage = _this.onMIDIMessage; 54 | haveAtLeastOneDevice = true; 55 | } 56 | 57 | 58 | if (!haveAtLeastOneDevice){ 59 | $("#js-warning").html("We weren't able to detect any MIDI devices. Please make sure at least one is connected or try restarting your browser."); 60 | } else { 61 | $("#js-warning").html(""); 62 | } 63 | 64 | } 65 | 66 | this.onMIDIInit = function(midi) { 67 | _this.midiAccess = midi; 68 | _this.hookUpMIDIInput(); 69 | _this.midiAccess.onstatechange = _this.hookUpMIDIInput; 70 | } 71 | 72 | this.onMIDIReject = function(err) { 73 | $("#js-warning").html("Sadly your browser doesn't support MIDI. Please try again with the latest version of Chrome."); 74 | } 75 | 76 | this.onMIDIMessage = function( event ) { 77 | _this.createTableRowMarkup(event); 78 | } 79 | 80 | this.startLoggingMIDIInput = function( midiAccess, indexOfPort ) { 81 | 82 | _this.midiAccess.inputs.forEach( function(entry) { 83 | entry.onmidimessage = _this.onMIDIMessage; 84 | }); 85 | } 86 | 87 | 88 | this.createTableRowMarkup = function(event){ 89 | var arrTableMarkup = new Array(); 90 | arrTableMarkup.push ( "" ); 91 | arrTableMarkup.push ( "" ); 92 | arrTableMarkup.push ( event.timeStamp ); 93 | arrTableMarkup.push ( "" ); 94 | arrTableMarkup.push ( "" ); 95 | arrTableMarkup.push ( this.printNumberinBase(((event.data[0] % 16)), $("#channel-message-format").val(), 15).toUpperCase() ); // channel 96 | arrTableMarkup.push ( "" ); 97 | arrTableMarkup.push ( "" ); 98 | arrTableMarkup.push ( this.printNumberinBase((event.data[0]), $("#channel-message-format").val(), 255).toUpperCase() ); 99 | arrTableMarkup.push ( "" ); 100 | arrTableMarkup.push ( "" ); 101 | arrTableMarkup.push ( this.calculateChannelMessageType(event.data[0]) ); 102 | arrTableMarkup.push ( "" ); 103 | arrTableMarkup.push ( "" ); 104 | if ($("#show-note-name").prop('checked')){ 105 | arrTableMarkup.push ( this.midiNumberToNoteName(event.data[1]) ); 106 | } else { 107 | arrTableMarkup.push ( this.printNumberinBase((event.data[1]), $("#data-byte-format").val(), 127).toUpperCase() ); 108 | } 109 | arrTableMarkup.push ( "" ); 110 | arrTableMarkup.push ( "" ); 111 | if (typeof event.data[2] !== "undefined"){ 112 | arrTableMarkup.push ( this.printNumberinBase((event.data[2]), $("#data-byte-format").val(), 127).toUpperCase() ); 113 | } 114 | arrTableMarkup.push ( "" ); 115 | arrTableMarkup.push ( "" ); 116 | arrTableMarkup.push ( event.currentTarget.manufacturer ); 117 | arrTableMarkup.push ( "" ); 118 | arrTableMarkup.push ( "" ); 119 | arrTableMarkup.push ( event.currentTarget.name ); 120 | arrTableMarkup.push ( "" ); 121 | arrTableMarkup.push ( "" ); 122 | 123 | if (this.rowCounter < this.maxRows){ 124 | this.rowCounter++; 125 | } else { 126 | $('.js-midi-log-table tr:last').remove(); 127 | } 128 | $(".js-table-head-row").after(arrTableMarkup.join('') ); 129 | } 130 | 131 | this.calculateChannelMessageType = function(number){ 132 | // http://www.earlevel.com/main/1996/08/14/midi-overview/ 133 | switch (Math.floor(number/16)) { 134 | case 8: 135 | return "Note off"; 136 | case 9: 137 | return "Note on"; 138 | case 10: 139 | return "Polyphonic key pressure"; 140 | case 11: 141 | return "Mode change"; 142 | case 12: 143 | return "Program change"; 144 | case 13: 145 | return "Monophonic key pressure"; 146 | case 14: 147 | return "Pitch bend"; 148 | } 149 | } 150 | 151 | 152 | 153 | this.printNumberinBase = function(decimalNumber, base, maxValue){ 154 | if (base == "dec"){ 155 | var maxLength = (maxValue + "").length; 156 | var paddedOutput = this.pad(decimalNumber, maxLength) 157 | return paddedOutput; 158 | } else if (base == "bin"){ 159 | var maxLength = maxValue.toString(2).length; 160 | var paddedOutput = this.pad(decimalNumber.toString(2), maxLength) 161 | return paddedOutput; 162 | } else if (base == "hex"){ 163 | var maxLength = maxValue.toString(16).length; 164 | var paddedOutput = this.pad(decimalNumber.toString(16), maxLength) 165 | return paddedOutput; 166 | } 167 | } 168 | 169 | this.midiNumberToNoteName = function(midiNumber){ 170 | return MIDIUtils.noteNumberToName(midiNumber); 171 | 172 | } 173 | 174 | this.pad = function(num, size) { 175 | var s = num+""; 176 | while (s.length < size) s = "0" + s; 177 | return s; 178 | } 179 | } 180 | -------------------------------------------------------------------------------- /js/WebMIDIAPI.js: -------------------------------------------------------------------------------- 1 | (function e(t,n,r){function s(o,u){if(!n[o]){if(!t[o]){var a=typeof require=="function"&&require;if(!u&&a)return a(o,!0);if(i)return i(o,!0);var f=new Error("Cannot find module '"+o+"'");throw f.code="MODULE_NOT_FOUND",f}var l=n[o]={exports:{}};t[o][0].call(l.exports,function(e){var n=t[o][1][e];return s(n?n:e)},l,l.exports,e,t,n,r)}return n[o].exports}var i=typeof require=="function"&&require;for(var o=0;o i)if(isEnum.call(it, key = symbols[i++]))keys.push(key); 361 | } 362 | return keys; 363 | }; 364 | },{"./$":30}],15:[function(require,module,exports){ 365 | module.exports = function(exec){ 366 | try { 367 | return !!exec(); 368 | } catch(e){ 369 | return true; 370 | } 371 | }; 372 | },{}],16:[function(require,module,exports){ 373 | var ctx = require('./$.ctx') 374 | , call = require('./$.iter-call') 375 | , isArrayIter = require('./$.is-array-iter') 376 | , anObject = require('./$.an-object') 377 | , toLength = require('./$.to-length') 378 | , getIterFn = require('./core.get-iterator-method'); 379 | module.exports = function(iterable, entries, fn, that){ 380 | var iterFn = getIterFn(iterable) 381 | , f = ctx(fn, that, entries ? 2 : 1) 382 | , index = 0 383 | , length, step, iterator; 384 | if(typeof iterFn != 'function')throw TypeError(iterable + ' is not iterable!'); 385 | // fast case for arrays with default iterator 386 | if(isArrayIter(iterFn))for(length = toLength(iterable.length); length > index; index++){ 387 | entries ? f(anObject(step = iterable[index])[0], step[1]) : f(iterable[index]); 388 | } else for(iterator = iterFn.call(iterable); !(step = iterator.next()).done; ){ 389 | call(iterator, f, step.value, entries); 390 | } 391 | }; 392 | },{"./$.an-object":5,"./$.ctx":11,"./$.is-array-iter":22,"./$.iter-call":24,"./$.to-length":44,"./core.get-iterator-method":48}],17:[function(require,module,exports){ 393 | // fallback for IE11 buggy Object.getOwnPropertyNames with iframe and window 394 | var toString = {}.toString 395 | , toIObject = require('./$.to-iobject') 396 | , getNames = require('./$').getNames; 397 | 398 | var windowNames = typeof window == 'object' && Object.getOwnPropertyNames 399 | ? Object.getOwnPropertyNames(window) : []; 400 | 401 | var getWindowNames = function(it){ 402 | try { 403 | return getNames(it); 404 | } catch(e){ 405 | return windowNames.slice(); 406 | } 407 | }; 408 | 409 | module.exports.get = function getOwnPropertyNames(it){ 410 | if(windowNames && toString.call(it) == '[object Window]')return getWindowNames(it); 411 | return getNames(toIObject(it)); 412 | }; 413 | },{"./$":30,"./$.to-iobject":43}],18:[function(require,module,exports){ 414 | // https://github.com/zloirock/core-js/issues/86#issuecomment-115759028 415 | var UNDEFINED = 'undefined'; 416 | var global = module.exports = typeof window != UNDEFINED && window.Math == Math 417 | ? window : typeof self != UNDEFINED && self.Math == Math ? self : Function('return this')(); 418 | if(typeof __g == 'number')__g = global; // eslint-disable-line no-undef 419 | },{}],19:[function(require,module,exports){ 420 | var hasOwnProperty = {}.hasOwnProperty; 421 | module.exports = function(it, key){ 422 | return hasOwnProperty.call(it, key); 423 | }; 424 | },{}],20:[function(require,module,exports){ 425 | var $ = require('./$') 426 | , createDesc = require('./$.property-desc'); 427 | module.exports = require('./$.support-desc') ? function(object, key, value){ 428 | return $.setDesc(object, key, createDesc(1, value)); 429 | } : function(object, key, value){ 430 | object[key] = value; 431 | return object; 432 | }; 433 | },{"./$":30,"./$.property-desc":34,"./$.support-desc":40}],21:[function(require,module,exports){ 434 | // indexed object, fallback for non-array-like ES3 strings 435 | var cof = require('./$.cof'); 436 | module.exports = 0 in Object('z') ? Object : function(it){ 437 | return cof(it) == 'String' ? it.split('') : Object(it); 438 | }; 439 | },{"./$.cof":7}],22:[function(require,module,exports){ 440 | // check on default Array iterator 441 | var Iterators = require('./$.iterators') 442 | , ITERATOR = require('./$.wks')('iterator'); 443 | module.exports = function(it){ 444 | return (Iterators.Array || Array.prototype[ITERATOR]) === it; 445 | }; 446 | },{"./$.iterators":29,"./$.wks":47}],23:[function(require,module,exports){ 447 | // http://jsperf.com/core-js-isobject 448 | module.exports = function(it){ 449 | return it !== null && (typeof it == 'object' || typeof it == 'function'); 450 | }; 451 | },{}],24:[function(require,module,exports){ 452 | // call something on iterator step with safe closing on error 453 | var anObject = require('./$.an-object'); 454 | module.exports = function(iterator, fn, value, entries){ 455 | try { 456 | return entries ? fn(anObject(value)[0], value[1]) : fn(value); 457 | // 7.4.6 IteratorClose(iterator, completion) 458 | } catch(e){ 459 | var ret = iterator['return']; 460 | if(ret !== undefined)anObject(ret.call(iterator)); 461 | throw e; 462 | } 463 | }; 464 | },{"./$.an-object":5}],25:[function(require,module,exports){ 465 | 'use strict'; 466 | var $ = require('./$') 467 | , IteratorPrototype = {}; 468 | 469 | // 25.1.2.1.1 %IteratorPrototype%[@@iterator]() 470 | require('./$.hide')(IteratorPrototype, require('./$.wks')('iterator'), function(){ return this; }); 471 | 472 | module.exports = function(Constructor, NAME, next){ 473 | Constructor.prototype = $.create(IteratorPrototype, {next: require('./$.property-desc')(1,next)}); 474 | require('./$.tag')(Constructor, NAME + ' Iterator'); 475 | }; 476 | },{"./$":30,"./$.hide":20,"./$.property-desc":34,"./$.tag":41,"./$.wks":47}],26:[function(require,module,exports){ 477 | 'use strict'; 478 | var LIBRARY = require('./$.library') 479 | , $def = require('./$.def') 480 | , $redef = require('./$.redef') 481 | , hide = require('./$.hide') 482 | , has = require('./$.has') 483 | , SYMBOL_ITERATOR = require('./$.wks')('iterator') 484 | , Iterators = require('./$.iterators') 485 | , BUGGY = !([].keys && 'next' in [].keys()) // Safari has buggy iterators w/o `next` 486 | , FF_ITERATOR = '@@iterator' 487 | , KEYS = 'keys' 488 | , VALUES = 'values'; 489 | var returnThis = function(){ return this; }; 490 | module.exports = function(Base, NAME, Constructor, next, DEFAULT, IS_SET, FORCE){ 491 | require('./$.iter-create')(Constructor, NAME, next); 492 | var createMethod = function(kind){ 493 | switch(kind){ 494 | case KEYS: return function keys(){ return new Constructor(this, kind); }; 495 | case VALUES: return function values(){ return new Constructor(this, kind); }; 496 | } return function entries(){ return new Constructor(this, kind); }; 497 | }; 498 | var TAG = NAME + ' Iterator' 499 | , proto = Base.prototype 500 | , _native = proto[SYMBOL_ITERATOR] || proto[FF_ITERATOR] || DEFAULT && proto[DEFAULT] 501 | , _default = _native || createMethod(DEFAULT) 502 | , methods, key; 503 | // Fix native 504 | if(_native){ 505 | var IteratorPrototype = require('./$').getProto(_default.call(new Base)); 506 | // Set @@toStringTag to native iterators 507 | require('./$.tag')(IteratorPrototype, TAG, true); 508 | // FF fix 509 | if(!LIBRARY && has(proto, FF_ITERATOR))hide(IteratorPrototype, SYMBOL_ITERATOR, returnThis); 510 | } 511 | // Define iterator 512 | if(!LIBRARY || FORCE)hide(proto, SYMBOL_ITERATOR, _default); 513 | // Plug for library 514 | Iterators[NAME] = _default; 515 | Iterators[TAG] = returnThis; 516 | if(DEFAULT){ 517 | methods = { 518 | keys: IS_SET ? _default : createMethod(KEYS), 519 | values: DEFAULT == VALUES ? _default : createMethod(VALUES), 520 | entries: DEFAULT != VALUES ? _default : createMethod('entries') 521 | }; 522 | if(FORCE)for(key in methods){ 523 | if(!(key in proto))$redef(proto, key, methods[key]); 524 | } else $def($def.P + $def.F * BUGGY, NAME, methods); 525 | } 526 | }; 527 | },{"./$":30,"./$.def":12,"./$.has":19,"./$.hide":20,"./$.iter-create":25,"./$.iterators":29,"./$.library":32,"./$.redef":35,"./$.tag":41,"./$.wks":47}],27:[function(require,module,exports){ 528 | var SYMBOL_ITERATOR = require('./$.wks')('iterator') 529 | , SAFE_CLOSING = false; 530 | try { 531 | var riter = [7][SYMBOL_ITERATOR](); 532 | riter['return'] = function(){ SAFE_CLOSING = true; }; 533 | Array.from(riter, function(){ throw 2; }); 534 | } catch(e){ /* empty */ } 535 | module.exports = function(exec){ 536 | if(!SAFE_CLOSING)return false; 537 | var safe = false; 538 | try { 539 | var arr = [7] 540 | , iter = arr[SYMBOL_ITERATOR](); 541 | iter.next = function(){ safe = true; }; 542 | arr[SYMBOL_ITERATOR] = function(){ return iter; }; 543 | exec(arr); 544 | } catch(e){ /* empty */ } 545 | return safe; 546 | }; 547 | },{"./$.wks":47}],28:[function(require,module,exports){ 548 | module.exports = function(done, value){ 549 | return {value: value, done: !!done}; 550 | }; 551 | },{}],29:[function(require,module,exports){ 552 | module.exports = {}; 553 | },{}],30:[function(require,module,exports){ 554 | var $Object = Object; 555 | module.exports = { 556 | create: $Object.create, 557 | getProto: $Object.getPrototypeOf, 558 | isEnum: {}.propertyIsEnumerable, 559 | getDesc: $Object.getOwnPropertyDescriptor, 560 | setDesc: $Object.defineProperty, 561 | setDescs: $Object.defineProperties, 562 | getKeys: $Object.keys, 563 | getNames: $Object.getOwnPropertyNames, 564 | getSymbols: $Object.getOwnPropertySymbols, 565 | each: [].forEach 566 | }; 567 | },{}],31:[function(require,module,exports){ 568 | var $ = require('./$') 569 | , toIObject = require('./$.to-iobject'); 570 | module.exports = function(object, el){ 571 | var O = toIObject(object) 572 | , keys = $.getKeys(O) 573 | , length = keys.length 574 | , index = 0 575 | , key; 576 | while(length > index)if(O[key = keys[index++]] === el)return key; 577 | }; 578 | },{"./$":30,"./$.to-iobject":43}],32:[function(require,module,exports){ 579 | module.exports = false; 580 | },{}],33:[function(require,module,exports){ 581 | var $redef = require('./$.redef'); 582 | module.exports = function(target, src){ 583 | for(var key in src)$redef(target, key, src[key]); 584 | return target; 585 | }; 586 | },{"./$.redef":35}],34:[function(require,module,exports){ 587 | module.exports = function(bitmap, value){ 588 | return { 589 | enumerable : !(bitmap & 1), 590 | configurable: !(bitmap & 2), 591 | writable : !(bitmap & 4), 592 | value : value 593 | }; 594 | }; 595 | },{}],35:[function(require,module,exports){ 596 | // add fake Function#toString 597 | // for correct work wrapped methods / constructors with methods like LoDash isNative 598 | var global = require('./$.global') 599 | , hide = require('./$.hide') 600 | , SRC = require('./$.uid')('src') 601 | , TO_STRING = 'toString' 602 | , $toString = Function[TO_STRING] 603 | , TPL = ('' + $toString).split(TO_STRING); 604 | 605 | require('./$.core').inspectSource = function(it){ 606 | return $toString.call(it); 607 | }; 608 | 609 | (module.exports = function(O, key, val, safe){ 610 | if(typeof val == 'function'){ 611 | hide(val, SRC, O[key] ? '' + O[key] : TPL.join(String(key))); 612 | if(!('name' in val))val.name = key; 613 | } 614 | if(O === global){ 615 | O[key] = val; 616 | } else { 617 | if(!safe)delete O[key]; 618 | hide(O, key, val); 619 | } 620 | })(Function.prototype, TO_STRING, function toString(){ 621 | return typeof this == 'function' && this[SRC] || $toString.call(this); 622 | }); 623 | },{"./$.core":10,"./$.global":18,"./$.hide":20,"./$.uid":45}],36:[function(require,module,exports){ 624 | var global = require('./$.global') 625 | , SHARED = '__core-js_shared__' 626 | , store = global[SHARED] || (global[SHARED] = {}); 627 | module.exports = function(key){ 628 | return store[key] || (store[key] = {}); 629 | }; 630 | },{"./$.global":18}],37:[function(require,module,exports){ 631 | 'use strict'; 632 | var $ = require('./$') 633 | , SPECIES = require('./$.wks')('species'); 634 | module.exports = function(C){ 635 | if(require('./$.support-desc') && !(SPECIES in C))$.setDesc(C, SPECIES, { 636 | configurable: true, 637 | get: function(){ return this; } 638 | }); 639 | }; 640 | },{"./$":30,"./$.support-desc":40,"./$.wks":47}],38:[function(require,module,exports){ 641 | module.exports = function(it, Constructor, name){ 642 | if(!(it instanceof Constructor))throw TypeError(name + ": use the 'new' operator!"); 643 | return it; 644 | }; 645 | },{}],39:[function(require,module,exports){ 646 | // true -> String#at 647 | // false -> String#codePointAt 648 | var toInteger = require('./$.to-integer') 649 | , defined = require('./$.defined'); 650 | module.exports = function(TO_STRING){ 651 | return function(that, pos){ 652 | var s = String(defined(that)) 653 | , i = toInteger(pos) 654 | , l = s.length 655 | , a, b; 656 | if(i < 0 || i >= l)return TO_STRING ? '' : undefined; 657 | a = s.charCodeAt(i); 658 | return a < 0xd800 || a > 0xdbff || i + 1 === l 659 | || (b = s.charCodeAt(i + 1)) < 0xdc00 || b > 0xdfff 660 | ? TO_STRING ? s.charAt(i) : a 661 | : TO_STRING ? s.slice(i, i + 2) : (a - 0xd800 << 10) + (b - 0xdc00) + 0x10000; 662 | }; 663 | }; 664 | },{"./$.defined":13,"./$.to-integer":42}],40:[function(require,module,exports){ 665 | // Thank's IE8 for his funny defineProperty 666 | module.exports = !require('./$.fails')(function(){ 667 | return Object.defineProperty({}, 'a', {get: function(){ return 7; }}).a != 7; 668 | }); 669 | },{"./$.fails":15}],41:[function(require,module,exports){ 670 | var has = require('./$.has') 671 | , hide = require('./$.hide') 672 | , TAG = require('./$.wks')('toStringTag'); 673 | 674 | module.exports = function(it, tag, stat){ 675 | if(it && !has(it = stat ? it : it.prototype, TAG))hide(it, TAG, tag); 676 | }; 677 | },{"./$.has":19,"./$.hide":20,"./$.wks":47}],42:[function(require,module,exports){ 678 | // 7.1.4 ToInteger 679 | var ceil = Math.ceil 680 | , floor = Math.floor; 681 | module.exports = function(it){ 682 | return isNaN(it = +it) ? 0 : (it > 0 ? floor : ceil)(it); 683 | }; 684 | },{}],43:[function(require,module,exports){ 685 | // to indexed object, toObject with fallback for non-array-like ES3 strings 686 | 687 | var IObject = require('./$.iobject') 688 | 689 | , defined = require('./$.defined'); 690 | 691 | module.exports = function(it){ 692 | 693 | return IObject(defined(it)); 694 | 695 | }; 696 | },{"./$.defined":13,"./$.iobject":21}],44:[function(require,module,exports){ 697 | // 7.1.15 ToLength 698 | var toInteger = require('./$.to-integer') 699 | , min = Math.min; 700 | module.exports = function(it){ 701 | return it > 0 ? min(toInteger(it), 0x1fffffffffffff) : 0; // pow(2, 53) - 1 == 9007199254740991 702 | }; 703 | },{"./$.to-integer":42}],45:[function(require,module,exports){ 704 | var id = 0 705 | , px = Math.random(); 706 | module.exports = function(key){ 707 | return 'Symbol('.concat(key === undefined ? '' : key, ')_', (++id + px).toString(36)); 708 | }; 709 | },{}],46:[function(require,module,exports){ 710 | // 22.1.3.31 Array.prototype[@@unscopables] 711 | var UNSCOPABLES = require('./$.wks')('unscopables'); 712 | if(!(UNSCOPABLES in []))require('./$.hide')(Array.prototype, UNSCOPABLES, {}); 713 | module.exports = function(key){ 714 | [][UNSCOPABLES][key] = true; 715 | }; 716 | },{"./$.hide":20,"./$.wks":47}],47:[function(require,module,exports){ 717 | var store = require('./$.shared')('wks') 718 | , Symbol = require('./$.global').Symbol; 719 | module.exports = function(name){ 720 | return store[name] || (store[name] = 721 | Symbol && Symbol[name] || (Symbol || require('./$.uid'))('Symbol.' + name)); 722 | }; 723 | },{"./$.global":18,"./$.shared":36,"./$.uid":45}],48:[function(require,module,exports){ 724 | var classof = require('./$.classof') 725 | , ITERATOR = require('./$.wks')('iterator') 726 | , Iterators = require('./$.iterators'); 727 | module.exports = require('./$.core').getIteratorMethod = function(it){ 728 | if(it != undefined)return it[ITERATOR] || it['@@iterator'] || Iterators[classof(it)]; 729 | }; 730 | },{"./$.classof":6,"./$.core":10,"./$.iterators":29,"./$.wks":47}],49:[function(require,module,exports){ 731 | 'use strict'; 732 | var setUnscope = require('./$.unscope') 733 | , step = require('./$.iter-step') 734 | , Iterators = require('./$.iterators') 735 | , toIObject = require('./$.to-iobject'); 736 | 737 | // 22.1.3.4 Array.prototype.entries() 738 | // 22.1.3.13 Array.prototype.keys() 739 | // 22.1.3.29 Array.prototype.values() 740 | // 22.1.3.30 Array.prototype[@@iterator]() 741 | require('./$.iter-define')(Array, 'Array', function(iterated, kind){ 742 | this._t = toIObject(iterated); // target 743 | this._i = 0; // next index 744 | this._k = kind; // kind 745 | // 22.1.5.2.1 %ArrayIteratorPrototype%.next() 746 | }, function(){ 747 | var O = this._t 748 | , kind = this._k 749 | , index = this._i++; 750 | if(!O || index >= O.length){ 751 | this._t = undefined; 752 | return step(1); 753 | } 754 | if(kind == 'keys' )return step(0, index); 755 | if(kind == 'values')return step(0, O[index]); 756 | return step(0, [index, O[index]]); 757 | }, 'values'); 758 | 759 | // argumentsList[@@iterator] is %ArrayProto_values% (9.4.4.6, 9.4.4.7) 760 | Iterators.Arguments = Iterators.Array; 761 | 762 | setUnscope('keys'); 763 | setUnscope('values'); 764 | setUnscope('entries'); 765 | },{"./$.iter-define":26,"./$.iter-step":28,"./$.iterators":29,"./$.to-iobject":43,"./$.unscope":46}],50:[function(require,module,exports){ 766 | 'use strict'; 767 | var strong = require('./$.collection-strong'); 768 | 769 | // 23.1 Map Objects 770 | require('./$.collection')('Map', function(get){ 771 | return function Map(){ return get(this, arguments[0]); }; 772 | }, { 773 | // 23.1.3.6 Map.prototype.get(key) 774 | get: function get(key){ 775 | var entry = strong.getEntry(this, key); 776 | return entry && entry.v; 777 | }, 778 | // 23.1.3.9 Map.prototype.set(key, value) 779 | set: function set(key, value){ 780 | return strong.def(this, key === 0 ? 0 : key, value); 781 | } 782 | }, strong, true); 783 | },{"./$.collection":9,"./$.collection-strong":8}],51:[function(require,module,exports){ 784 | 'use strict'; 785 | // 19.1.3.6 Object.prototype.toString() 786 | var classof = require('./$.classof') 787 | , test = {}; 788 | test[require('./$.wks')('toStringTag')] = 'z'; 789 | if(test + '' != '[object z]'){ 790 | require('./$.redef')(Object.prototype, 'toString', function toString(){ 791 | return '[object ' + classof(this) + ']'; 792 | }, true); 793 | } 794 | },{"./$.classof":6,"./$.redef":35,"./$.wks":47}],52:[function(require,module,exports){ 795 | 'use strict'; 796 | var strong = require('./$.collection-strong'); 797 | 798 | // 23.2 Set Objects 799 | require('./$.collection')('Set', function(get){ 800 | return function Set(){ return get(this, arguments[0]); }; 801 | }, { 802 | // 23.2.3.1 Set.prototype.add(value) 803 | add: function add(value){ 804 | return strong.def(this, value = value === 0 ? 0 : value, value); 805 | } 806 | }, strong); 807 | },{"./$.collection":9,"./$.collection-strong":8}],53:[function(require,module,exports){ 808 | 'use strict'; 809 | var $at = require('./$.string-at')(true); 810 | 811 | // 21.1.3.27 String.prototype[@@iterator]() 812 | require('./$.iter-define')(String, 'String', function(iterated){ 813 | this._t = String(iterated); // target 814 | this._i = 0; // next index 815 | // 21.1.5.2.1 %StringIteratorPrototype%.next() 816 | }, function(){ 817 | var O = this._t 818 | , index = this._i 819 | , point; 820 | if(index >= O.length)return {value: undefined, done: true}; 821 | point = $at(O, index); 822 | this._i += point.length; 823 | return {value: point, done: false}; 824 | }); 825 | },{"./$.iter-define":26,"./$.string-at":39}],54:[function(require,module,exports){ 826 | 'use strict'; 827 | // ECMAScript 6 symbols shim 828 | var $ = require('./$') 829 | , global = require('./$.global') 830 | , has = require('./$.has') 831 | , SUPPORT_DESC = require('./$.support-desc') 832 | , $def = require('./$.def') 833 | , $redef = require('./$.redef') 834 | , shared = require('./$.shared') 835 | , setTag = require('./$.tag') 836 | , uid = require('./$.uid') 837 | , wks = require('./$.wks') 838 | , keyOf = require('./$.keyof') 839 | , $names = require('./$.get-names') 840 | , enumKeys = require('./$.enum-keys') 841 | , isObject = require('./$.is-object') 842 | , anObject = require('./$.an-object') 843 | , toIObject = require('./$.to-iobject') 844 | , createDesc = require('./$.property-desc') 845 | , getDesc = $.getDesc 846 | , setDesc = $.setDesc 847 | , _create = $.create 848 | , getNames = $names.get 849 | , $Symbol = global.Symbol 850 | , setter = false 851 | , HIDDEN = wks('_hidden') 852 | , isEnum = $.isEnum 853 | , SymbolRegistry = shared('symbol-registry') 854 | , AllSymbols = shared('symbols') 855 | , useNative = typeof $Symbol == 'function' 856 | , ObjectProto = Object.prototype; 857 | 858 | var setSymbolDesc = SUPPORT_DESC ? function(){ // fallback for old Android 859 | try { 860 | return _create(setDesc({}, HIDDEN, { 861 | get: function(){ 862 | return setDesc(this, HIDDEN, {value: false})[HIDDEN]; 863 | } 864 | }))[HIDDEN] || setDesc; 865 | } catch(e){ 866 | return function(it, key, D){ 867 | var protoDesc = getDesc(ObjectProto, key); 868 | if(protoDesc)delete ObjectProto[key]; 869 | setDesc(it, key, D); 870 | if(protoDesc && it !== ObjectProto)setDesc(ObjectProto, key, protoDesc); 871 | }; 872 | } 873 | }() : setDesc; 874 | 875 | var wrap = function(tag){ 876 | var sym = AllSymbols[tag] = _create($Symbol.prototype); 877 | sym._k = tag; 878 | SUPPORT_DESC && setter && setSymbolDesc(ObjectProto, tag, { 879 | configurable: true, 880 | set: function(value){ 881 | if(has(this, HIDDEN) && has(this[HIDDEN], tag))this[HIDDEN][tag] = false; 882 | setSymbolDesc(this, tag, createDesc(1, value)); 883 | } 884 | }); 885 | return sym; 886 | }; 887 | 888 | var $defineProperty = function defineProperty(it, key, D){ 889 | if(D && has(AllSymbols, key)){ 890 | if(!D.enumerable){ 891 | if(!has(it, HIDDEN))setDesc(it, HIDDEN, createDesc(1, {})); 892 | it[HIDDEN][key] = true; 893 | } else { 894 | if(has(it, HIDDEN) && it[HIDDEN][key])it[HIDDEN][key] = false; 895 | D = _create(D, {enumerable: createDesc(0, false)}); 896 | } return setSymbolDesc(it, key, D); 897 | } return setDesc(it, key, D); 898 | }; 899 | var $defineProperties = function defineProperties(it, P){ 900 | anObject(it); 901 | var keys = enumKeys(P = toIObject(P)) 902 | , i = 0 903 | , l = keys.length 904 | , key; 905 | while(l > i)$defineProperty(it, key = keys[i++], P[key]); 906 | return it; 907 | }; 908 | var $create = function create(it, P){ 909 | return P === undefined ? _create(it) : $defineProperties(_create(it), P); 910 | }; 911 | var $propertyIsEnumerable = function propertyIsEnumerable(key){ 912 | var E = isEnum.call(this, key); 913 | return E || !has(this, key) || !has(AllSymbols, key) || has(this, HIDDEN) && this[HIDDEN][key] 914 | ? E : true; 915 | }; 916 | var $getOwnPropertyDescriptor = function getOwnPropertyDescriptor(it, key){ 917 | var D = getDesc(it = toIObject(it), key); 918 | if(D && has(AllSymbols, key) && !(has(it, HIDDEN) && it[HIDDEN][key]))D.enumerable = true; 919 | return D; 920 | }; 921 | var $getOwnPropertyNames = function getOwnPropertyNames(it){ 922 | var names = getNames(toIObject(it)) 923 | , result = [] 924 | , i = 0 925 | , key; 926 | while(names.length > i)if(!has(AllSymbols, key = names[i++]) && key != HIDDEN)result.push(key); 927 | return result; 928 | }; 929 | var $getOwnPropertySymbols = function getOwnPropertySymbols(it){ 930 | var names = getNames(toIObject(it)) 931 | , result = [] 932 | , i = 0 933 | , key; 934 | while(names.length > i)if(has(AllSymbols, key = names[i++]))result.push(AllSymbols[key]); 935 | return result; 936 | }; 937 | 938 | // 19.4.1.1 Symbol([description]) 939 | if(!useNative){ 940 | $Symbol = function Symbol(){ 941 | if(this instanceof $Symbol)throw TypeError('Symbol is not a constructor'); 942 | return wrap(uid(arguments[0])); 943 | }; 944 | $redef($Symbol.prototype, 'toString', function toString(){ 945 | return this._k; 946 | }); 947 | 948 | $.create = $create; 949 | $.isEnum = $propertyIsEnumerable; 950 | $.getDesc = $getOwnPropertyDescriptor; 951 | $.setDesc = $defineProperty; 952 | $.setDescs = $defineProperties; 953 | $.getNames = $names.get = $getOwnPropertyNames; 954 | $.getSymbols = $getOwnPropertySymbols; 955 | 956 | if(SUPPORT_DESC && !require('./$.library')){ 957 | $redef(ObjectProto, 'propertyIsEnumerable', $propertyIsEnumerable, true); 958 | } 959 | } 960 | 961 | // MS Edge converts symbol values to JSON as {} 962 | // WebKit converts symbol values in objects to JSON as null 963 | if(!useNative || require('./$.fails')(function(){ 964 | return JSON.stringify([{a: $Symbol()}, [$Symbol()]]) != '[{},[null]]'; 965 | }))$redef($Symbol.prototype, 'toJSON', function toJSON(){ 966 | if(useNative && isObject(this))return this; 967 | }); 968 | 969 | var symbolStatics = { 970 | // 19.4.2.1 Symbol.for(key) 971 | 'for': function(key){ 972 | return has(SymbolRegistry, key += '') 973 | ? SymbolRegistry[key] 974 | : SymbolRegistry[key] = $Symbol(key); 975 | }, 976 | // 19.4.2.5 Symbol.keyFor(sym) 977 | keyFor: function keyFor(key){ 978 | return keyOf(SymbolRegistry, key); 979 | }, 980 | useSetter: function(){ setter = true; }, 981 | useSimple: function(){ setter = false; } 982 | }; 983 | // 19.4.2.2 Symbol.hasInstance 984 | // 19.4.2.3 Symbol.isConcatSpreadable 985 | // 19.4.2.4 Symbol.iterator 986 | // 19.4.2.6 Symbol.match 987 | // 19.4.2.8 Symbol.replace 988 | // 19.4.2.9 Symbol.search 989 | // 19.4.2.10 Symbol.species 990 | // 19.4.2.11 Symbol.split 991 | // 19.4.2.12 Symbol.toPrimitive 992 | // 19.4.2.13 Symbol.toStringTag 993 | // 19.4.2.14 Symbol.unscopables 994 | $.each.call(( 995 | 'hasInstance,isConcatSpreadable,iterator,match,replace,search,' + 996 | 'species,split,toPrimitive,toStringTag,unscopables' 997 | ).split(','), function(it){ 998 | var sym = wks(it); 999 | symbolStatics[it] = useNative ? sym : wrap(sym); 1000 | } 1001 | ); 1002 | 1003 | setter = true; 1004 | 1005 | $def($def.G + $def.W, {Symbol: $Symbol}); 1006 | 1007 | $def($def.S, 'Symbol', symbolStatics); 1008 | 1009 | $def($def.S + $def.F * !useNative, 'Object', { 1010 | // 19.1.2.2 Object.create(O [, Properties]) 1011 | create: $create, 1012 | // 19.1.2.4 Object.defineProperty(O, P, Attributes) 1013 | defineProperty: $defineProperty, 1014 | // 19.1.2.3 Object.defineProperties(O, Properties) 1015 | defineProperties: $defineProperties, 1016 | // 19.1.2.6 Object.getOwnPropertyDescriptor(O, P) 1017 | getOwnPropertyDescriptor: $getOwnPropertyDescriptor, 1018 | // 19.1.2.7 Object.getOwnPropertyNames(O) 1019 | getOwnPropertyNames: $getOwnPropertyNames, 1020 | // 19.1.2.8 Object.getOwnPropertySymbols(O) 1021 | getOwnPropertySymbols: $getOwnPropertySymbols 1022 | }); 1023 | 1024 | // 19.4.3.5 Symbol.prototype[@@toStringTag] 1025 | setTag($Symbol, 'Symbol'); 1026 | // 20.2.1.9 Math[@@toStringTag] 1027 | setTag(Math, 'Math', true); 1028 | // 24.3.3 JSON[@@toStringTag] 1029 | setTag(global.JSON, 'JSON', true); 1030 | },{"./$":30,"./$.an-object":5,"./$.def":12,"./$.enum-keys":14,"./$.fails":15,"./$.get-names":17,"./$.global":18,"./$.has":19,"./$.is-object":23,"./$.keyof":31,"./$.library":32,"./$.property-desc":34,"./$.redef":35,"./$.shared":36,"./$.support-desc":40,"./$.tag":41,"./$.to-iobject":43,"./$.uid":45,"./$.wks":47}],55:[function(require,module,exports){ 1031 | require('./es6.array.iterator'); 1032 | var global = require('./$.global') 1033 | , hide = require('./$.hide') 1034 | , Iterators = require('./$.iterators') 1035 | , ITERATOR = require('./$.wks')('iterator') 1036 | , NL = global.NodeList 1037 | , HTC = global.HTMLCollection 1038 | , NLProto = NL && NL.prototype 1039 | , HTCProto = HTC && HTC.prototype 1040 | , ArrayValues = Iterators.NodeList = Iterators.HTMLCollection = Iterators.Array; 1041 | if(NL && !(ITERATOR in NLProto))hide(NLProto, ITERATOR, ArrayValues); 1042 | if(HTC && !(ITERATOR in HTCProto))hide(HTCProto, ITERATOR, ArrayValues); 1043 | },{"./$.global":18,"./$.hide":20,"./$.iterators":29,"./$.wks":47,"./es6.array.iterator":49}],56:[function(require,module,exports){ 1044 | // shim for using process in browser 1045 | 1046 | var process = module.exports = {}; 1047 | var queue = []; 1048 | var draining = false; 1049 | var currentQueue; 1050 | var queueIndex = -1; 1051 | 1052 | function cleanUpNextTick() { 1053 | draining = false; 1054 | if (currentQueue.length) { 1055 | queue = currentQueue.concat(queue); 1056 | } else { 1057 | queueIndex = -1; 1058 | } 1059 | if (queue.length) { 1060 | drainQueue(); 1061 | } 1062 | } 1063 | 1064 | function drainQueue() { 1065 | if (draining) { 1066 | return; 1067 | } 1068 | var timeout = setTimeout(cleanUpNextTick); 1069 | draining = true; 1070 | 1071 | var len = queue.length; 1072 | while(len) { 1073 | currentQueue = queue; 1074 | queue = []; 1075 | while (++queueIndex < len) { 1076 | if (currentQueue) { 1077 | currentQueue[queueIndex].run(); 1078 | } 1079 | } 1080 | queueIndex = -1; 1081 | len = queue.length; 1082 | } 1083 | currentQueue = null; 1084 | draining = false; 1085 | clearTimeout(timeout); 1086 | } 1087 | 1088 | process.nextTick = function (fun) { 1089 | var args = new Array(arguments.length - 1); 1090 | if (arguments.length > 1) { 1091 | for (var i = 1; i < arguments.length; i++) { 1092 | args[i - 1] = arguments[i]; 1093 | } 1094 | } 1095 | queue.push(new Item(fun, args)); 1096 | if (queue.length === 1 && !draining) { 1097 | setTimeout(drainQueue, 0); 1098 | } 1099 | }; 1100 | 1101 | // v8 likes predictible objects 1102 | function Item(fun, array) { 1103 | this.fun = fun; 1104 | this.array = array; 1105 | } 1106 | Item.prototype.run = function () { 1107 | this.fun.apply(null, this.array); 1108 | }; 1109 | process.title = 'browser'; 1110 | process.browser = true; 1111 | process.env = {}; 1112 | process.argv = []; 1113 | process.version = ''; // empty string to avoid regexp issues 1114 | process.versions = {}; 1115 | 1116 | function noop() {} 1117 | 1118 | process.on = noop; 1119 | process.addListener = noop; 1120 | process.once = noop; 1121 | process.off = noop; 1122 | process.removeListener = noop; 1123 | process.removeAllListeners = noop; 1124 | process.emit = noop; 1125 | 1126 | process.binding = function (name) { 1127 | throw new Error('process.binding is not supported'); 1128 | }; 1129 | 1130 | process.cwd = function () { return '/' }; 1131 | process.chdir = function (dir) { 1132 | throw new Error('process.chdir is not supported'); 1133 | }; 1134 | process.umask = function() { return 0; }; 1135 | 1136 | },{}],57:[function(require,module,exports){ 1137 | /* 1138 | Creates instances of the Jazz plugin if necessary. Initially the MIDIAccess creates one main Jazz instance that is used 1139 | to query all initially connected devices, and to track the devices that are being connected or disconnected at runtime. 1140 | 1141 | For every MIDIInput and MIDIOutput that is created, MIDIAccess queries the getJazzInstance() method for a Jazz instance 1142 | that still have an available input or output. Because Jazz only allows one input and one output per instance, we 1143 | need to create new instances if more than one MIDI input or output device gets connected. 1144 | 1145 | Note that an existing Jazz instance doesn't get deleted when both its input and output device are disconnected; instead it 1146 | will be reused if a new device gets connected. 1147 | */ 1148 | 1149 | 'use strict'; 1150 | 1151 | /* 1152 | The require statements are only needed for Internet Explorer. They have to be put here; 1153 | if you put them at the top entry point (shim.js) it doesn't work (weird quirck in IE?). 1154 | 1155 | Note that you can remove the require statements if you don't need (or want) to support Internet Explorer: 1156 | that will shrink the filesize of the WebMIDIAPIShim to about 50%. 1157 | 1158 | If you are building for Nodejs platform you can comment these lines, then run the buildscript like so: 1159 | 'npm run build-nodejs' -> the build file (approx. 15K) will be saved in the web-midi-api folder 1160 | */ 1161 | Object.defineProperty(exports, '__esModule', { 1162 | value: true 1163 | }); 1164 | exports.createJazzInstance = createJazzInstance; 1165 | exports.getJazzInstance = getJazzInstance; 1166 | 1167 | var _util = require('./util'); 1168 | 1169 | require('babelify/node_modules/babel-core/node_modules/core-js/es6/map'); 1170 | require('babelify/node_modules/babel-core/node_modules/core-js/es6/set'); 1171 | require('babelify/node_modules/babel-core/node_modules/core-js/es6/symbol'); 1172 | 1173 | var jazzPluginInitTime = 100; // milliseconds 1174 | 1175 | var jazzInstanceNumber = 0; 1176 | var jazzInstances = new Map(); 1177 | 1178 | function createJazzInstance(callback) { 1179 | 1180 | var id = 'jazz_' + jazzInstanceNumber++ + '' + Date.now(); 1181 | var instance = undefined; 1182 | var objRef = undefined, 1183 | activeX = undefined; 1184 | 1185 | if ((0, _util.getDevice)().nodejs === true) { 1186 | objRef = new jazzMidi.MIDI(); 1187 | } else { 1188 | var o1 = document.createElement('object'); 1189 | o1.id = id + 'ie'; 1190 | o1.classid = 'CLSID:1ACE1618-1C7D-4561-AEE1-34842AA85E90'; 1191 | activeX = o1; 1192 | 1193 | var o2 = document.createElement('object'); 1194 | o2.id = id; 1195 | o2.type = 'audio/x-jazz'; 1196 | o1.appendChild(o2); 1197 | objRef = o2; 1198 | 1199 | var e = document.createElement('p'); 1200 | e.appendChild(document.createTextNode('This page requires the ')); 1201 | 1202 | var a = document.createElement('a'); 1203 | a.appendChild(document.createTextNode('Jazz plugin')); 1204 | a.href = 'http://jazz-soft.net/'; 1205 | 1206 | e.appendChild(a); 1207 | e.appendChild(document.createTextNode('.')); 1208 | o2.appendChild(e); 1209 | 1210 | var insertionPoint = document.getElementById('MIDIPlugin'); 1211 | if (!insertionPoint) { 1212 | // Create hidden element 1213 | insertionPoint = document.createElement('div'); 1214 | insertionPoint.id = 'MIDIPlugin'; 1215 | insertionPoint.style.position = 'absolute'; 1216 | insertionPoint.style.visibility = 'hidden'; 1217 | insertionPoint.style.left = '-9999px'; 1218 | insertionPoint.style.top = '-9999px'; 1219 | document.body.appendChild(insertionPoint); 1220 | } 1221 | insertionPoint.appendChild(o1); 1222 | } 1223 | 1224 | setTimeout(function () { 1225 | if (objRef.isJazz === true) { 1226 | instance = objRef; 1227 | } else if (activeX.isJazz === true) { 1228 | instance = activeX; 1229 | } 1230 | if (instance !== undefined) { 1231 | instance._perfTimeZero = performance.now(); 1232 | jazzInstances.set(id, instance); 1233 | } 1234 | callback(instance); 1235 | }, jazzPluginInitTime); 1236 | } 1237 | 1238 | function getJazzInstance(type, callback) { 1239 | var instance = null; 1240 | var key = type === 'input' ? 'inputInUse' : 'outputInUse'; 1241 | 1242 | var _iteratorNormalCompletion = true; 1243 | var _didIteratorError = false; 1244 | var _iteratorError = undefined; 1245 | 1246 | try { 1247 | for (var _iterator = jazzInstances.values()[Symbol.iterator](), _step; !(_iteratorNormalCompletion = (_step = _iterator.next()).done); _iteratorNormalCompletion = true) { 1248 | var inst = _step.value; 1249 | 1250 | if (inst[key] !== true) { 1251 | instance = inst; 1252 | break; 1253 | } 1254 | } 1255 | } catch (err) { 1256 | _didIteratorError = true; 1257 | _iteratorError = err; 1258 | } finally { 1259 | try { 1260 | if (!_iteratorNormalCompletion && _iterator['return']) { 1261 | _iterator['return'](); 1262 | } 1263 | } finally { 1264 | if (_didIteratorError) { 1265 | throw _iteratorError; 1266 | } 1267 | } 1268 | } 1269 | 1270 | if (instance === null) { 1271 | createJazzInstance(callback); 1272 | } else { 1273 | callback(instance); 1274 | } 1275 | } 1276 | 1277 | },{"./util":64,"babelify/node_modules/babel-core/node_modules/core-js/es6/map":1,"babelify/node_modules/babel-core/node_modules/core-js/es6/set":2,"babelify/node_modules/babel-core/node_modules/core-js/es6/symbol":3}],58:[function(require,module,exports){ 1278 | /* 1279 | Creates a MIDIAccess instance: 1280 | - Creates MIDIInput and MIDIOutput instances for the initially connected MIDI devices. 1281 | - Keeps track of newly connected devices and creates the necessary instances of MIDIInput and MIDIOutput. 1282 | - Keeps track of disconnected devices and removes them from the inputs and/or outputs map. 1283 | - Creates a unique id for every device and stores these ids by the name of the device: 1284 | so when a device gets disconnected and reconnected again, it will still have the same id. This 1285 | is in line with the behaviour of the native MIDIAccess object. 1286 | 1287 | */ 1288 | 1289 | 'use strict'; 1290 | 1291 | Object.defineProperty(exports, '__esModule', { 1292 | value: true 1293 | }); 1294 | 1295 | var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })(); 1296 | 1297 | exports.createMIDIAccess = createMIDIAccess; 1298 | exports.dispatchEvent = dispatchEvent; 1299 | exports.closeAllMIDIInputs = closeAllMIDIInputs; 1300 | exports.getMIDIDeviceId = getMIDIDeviceId; 1301 | 1302 | function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } } 1303 | 1304 | var _jazz_instance = require('./jazz_instance'); 1305 | 1306 | var _midi_input = require('./midi_input'); 1307 | 1308 | var _midi_output = require('./midi_output'); 1309 | 1310 | var _midiconnection_event = require('./midiconnection_event'); 1311 | 1312 | var _util = require('./util'); 1313 | 1314 | var midiAccess = undefined; 1315 | var jazzInstance = undefined; 1316 | var midiInputs = new Map(); 1317 | var midiOutputs = new Map(); 1318 | var midiInputIds = new Map(); 1319 | var midiOutputIds = new Map(); 1320 | var listeners = new Set(); 1321 | 1322 | var MIDIAccess = (function () { 1323 | function MIDIAccess(midiInputs, midiOutputs) { 1324 | _classCallCheck(this, MIDIAccess); 1325 | 1326 | this.sysexEnabled = true; 1327 | this.inputs = midiInputs; 1328 | this.outputs = midiOutputs; 1329 | } 1330 | 1331 | _createClass(MIDIAccess, [{ 1332 | key: 'addEventListener', 1333 | value: function addEventListener(type, listener, useCapture) { 1334 | if (type !== 'statechange') { 1335 | return; 1336 | } 1337 | if (listeners.has(listener) === false) { 1338 | listeners.add(listener); 1339 | } 1340 | } 1341 | }, { 1342 | key: 'removeEventListener', 1343 | value: function removeEventListener(type, listener, useCapture) { 1344 | if (type !== 'statechange') { 1345 | return; 1346 | } 1347 | if (listeners.has(listener) === true) { 1348 | listeners['delete'](listener); 1349 | } 1350 | } 1351 | }]); 1352 | 1353 | return MIDIAccess; 1354 | })(); 1355 | 1356 | function createMIDIAccess() { 1357 | 1358 | return new Promise(function executor(resolve, reject) { 1359 | 1360 | if (midiAccess !== undefined) { 1361 | resolve(midiAccess); 1362 | return; 1363 | } 1364 | 1365 | if ((0, _util.getDevice)().browser === 'ie9') { 1366 | reject({ message: 'WebMIDIAPIShim supports Internet Explorer 10 and above.' }); 1367 | return; 1368 | } 1369 | 1370 | (0, _jazz_instance.createJazzInstance)(function (instance) { 1371 | if (instance === undefined) { 1372 | reject({ message: 'No access to MIDI devices: browser does not support the WebMIDI API and the Jazz plugin is not installed.' }); 1373 | return; 1374 | } 1375 | 1376 | jazzInstance = instance; 1377 | 1378 | createMIDIPorts(function () { 1379 | setupListeners(); 1380 | midiAccess = new MIDIAccess(midiInputs, midiOutputs); 1381 | resolve(midiAccess); 1382 | }); 1383 | }); 1384 | }); 1385 | } 1386 | 1387 | // create MIDIInput and MIDIOutput instances for all initially connected MIDI devices 1388 | function createMIDIPorts(callback) { 1389 | var inputs = jazzInstance.MidiInList(); 1390 | var outputs = jazzInstance.MidiOutList(); 1391 | var numInputs = inputs.length; 1392 | var numOutputs = outputs.length; 1393 | 1394 | loopCreateMIDIPort(0, numInputs, 'input', inputs, function () { 1395 | loopCreateMIDIPort(0, numOutputs, 'output', outputs, callback); 1396 | }); 1397 | } 1398 | 1399 | function loopCreateMIDIPort(index, max, type, list, callback) { 1400 | if (index < max) { 1401 | var _name = list[index++]; 1402 | createMIDIPort(type, _name, function () { 1403 | loopCreateMIDIPort(index, max, type, list, callback); 1404 | }); 1405 | } else { 1406 | callback(); 1407 | } 1408 | } 1409 | 1410 | function createMIDIPort(type, name, callback) { 1411 | (0, _jazz_instance.getJazzInstance)(type, function (instance) { 1412 | var port = undefined; 1413 | var info = [name, '', '']; 1414 | if (type === 'input') { 1415 | if (instance.Support('MidiInInfo')) { 1416 | info = instance.MidiInInfo(name); 1417 | } 1418 | port = new _midi_input.MIDIInput(info, instance); 1419 | midiInputs.set(port.id, port); 1420 | } else if (type === 'output') { 1421 | if (instance.Support('MidiOutInfo')) { 1422 | info = instance.MidiOutInfo(name); 1423 | } 1424 | port = new _midi_output.MIDIOutput(info, instance); 1425 | midiOutputs.set(port.id, port); 1426 | } 1427 | callback(port); 1428 | }); 1429 | } 1430 | 1431 | // lookup function: Jazz gives us the name of the connected/disconnected MIDI devices but we have stored them by id 1432 | function getPortByName(ports, name) { 1433 | var port = undefined; 1434 | var _iteratorNormalCompletion = true; 1435 | var _didIteratorError = false; 1436 | var _iteratorError = undefined; 1437 | 1438 | try { 1439 | for (var _iterator = ports.values()[Symbol.iterator](), _step; !(_iteratorNormalCompletion = (_step = _iterator.next()).done); _iteratorNormalCompletion = true) { 1440 | port = _step.value; 1441 | 1442 | if (port.name === name) { 1443 | break; 1444 | } 1445 | } 1446 | } catch (err) { 1447 | _didIteratorError = true; 1448 | _iteratorError = err; 1449 | } finally { 1450 | try { 1451 | if (!_iteratorNormalCompletion && _iterator['return']) { 1452 | _iterator['return'](); 1453 | } 1454 | } finally { 1455 | if (_didIteratorError) { 1456 | throw _iteratorError; 1457 | } 1458 | } 1459 | } 1460 | 1461 | return port; 1462 | } 1463 | 1464 | // keep track of connected/disconnected MIDI devices 1465 | function setupListeners() { 1466 | jazzInstance.OnDisconnectMidiIn(function (name) { 1467 | var port = getPortByName(midiInputs, name); 1468 | if (port !== undefined) { 1469 | port.state = 'disconnected'; 1470 | port.close(); 1471 | port._jazzInstance.inputInUse = false; 1472 | midiInputs['delete'](port.id); 1473 | dispatchEvent(port); 1474 | } 1475 | }); 1476 | 1477 | jazzInstance.OnDisconnectMidiOut(function (name) { 1478 | var port = getPortByName(midiOutputs, name); 1479 | if (port !== undefined) { 1480 | port.state = 'disconnected'; 1481 | port.close(); 1482 | port._jazzInstance.outputInUse = false; 1483 | midiOutputs['delete'](port.id); 1484 | dispatchEvent(port); 1485 | } 1486 | }); 1487 | 1488 | jazzInstance.OnConnectMidiIn(function (name) { 1489 | createMIDIPort('input', name, function (port) { 1490 | dispatchEvent(port); 1491 | }); 1492 | }); 1493 | 1494 | jazzInstance.OnConnectMidiOut(function (name) { 1495 | createMIDIPort('output', name, function (port) { 1496 | dispatchEvent(port); 1497 | }); 1498 | }); 1499 | } 1500 | 1501 | // when a device gets connected/disconnected both the port and MIDIAccess dispatch a MIDIConnectionEvent 1502 | // therefor we call the ports dispatchEvent function here as well 1503 | 1504 | function dispatchEvent(port) { 1505 | port.dispatchEvent(new _midiconnection_event.MIDIConnectionEvent(port, port)); 1506 | 1507 | var evt = new _midiconnection_event.MIDIConnectionEvent(midiAccess, port); 1508 | 1509 | if (typeof midiAccess.onstatechange === 'function') { 1510 | midiAccess.onstatechange(evt); 1511 | } 1512 | var _iteratorNormalCompletion2 = true; 1513 | var _didIteratorError2 = false; 1514 | var _iteratorError2 = undefined; 1515 | 1516 | try { 1517 | for (var _iterator2 = listeners[Symbol.iterator](), _step2; !(_iteratorNormalCompletion2 = (_step2 = _iterator2.next()).done); _iteratorNormalCompletion2 = true) { 1518 | var listener = _step2.value; 1519 | 1520 | listener(evt); 1521 | } 1522 | } catch (err) { 1523 | _didIteratorError2 = true; 1524 | _iteratorError2 = err; 1525 | } finally { 1526 | try { 1527 | if (!_iteratorNormalCompletion2 && _iterator2['return']) { 1528 | _iterator2['return'](); 1529 | } 1530 | } finally { 1531 | if (_didIteratorError2) { 1532 | throw _iteratorError2; 1533 | } 1534 | } 1535 | } 1536 | } 1537 | 1538 | function closeAllMIDIInputs() { 1539 | midiInputs.forEach(function (input) { 1540 | //input.close(); 1541 | input._jazzInstance.MidiInClose(); 1542 | }); 1543 | } 1544 | 1545 | // check if we have already created a unique id for this device, if so: reuse it, if not: create a new id and store it 1546 | 1547 | function getMIDIDeviceId(name, type) { 1548 | var id = undefined; 1549 | if (type === 'input') { 1550 | id = midiInputIds.get(name); 1551 | if (id === undefined) { 1552 | id = (0, _util.generateUUID)(); 1553 | midiInputIds.set(name, id); 1554 | } 1555 | } else if (type === 'output') { 1556 | id = midiOutputIds.get(name); 1557 | if (id === undefined) { 1558 | id = (0, _util.generateUUID)(); 1559 | midiOutputIds.set(name, id); 1560 | } 1561 | } 1562 | return id; 1563 | } 1564 | 1565 | },{"./jazz_instance":57,"./midi_input":59,"./midi_output":60,"./midiconnection_event":61,"./util":64}],59:[function(require,module,exports){ 1566 | /* 1567 | MIDIInput is a wrapper around an input of a Jazz instance 1568 | */ 1569 | 1570 | 'use strict'; 1571 | 1572 | Object.defineProperty(exports, '__esModule', { 1573 | value: true 1574 | }); 1575 | 1576 | var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })(); 1577 | 1578 | function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } } 1579 | 1580 | var _util = require('./util'); 1581 | 1582 | var _midimessage_event = require('./midimessage_event'); 1583 | 1584 | var _midiconnection_event = require('./midiconnection_event'); 1585 | 1586 | var _midi_access = require('./midi_access'); 1587 | 1588 | var midiProc = undefined; 1589 | var nodejs = (0, _util.getDevice)().nodejs; 1590 | 1591 | var MIDIInput = (function () { 1592 | function MIDIInput(info, instance) { 1593 | _classCallCheck(this, MIDIInput); 1594 | 1595 | this.id = (0, _midi_access.getMIDIDeviceId)(info[0], 'input'); 1596 | this.name = info[0]; 1597 | this.manufacturer = info[1]; 1598 | this.version = info[2]; 1599 | this.type = 'input'; 1600 | this.state = 'connected'; 1601 | this.connection = 'pending'; 1602 | 1603 | this.onstatechange = null; 1604 | this._onmidimessage = null; 1605 | // because we need to implicitly open the device when an onmidimessage handler gets added 1606 | // we define a setter that opens the device if the set value is a function 1607 | Object.defineProperty(this, 'onmidimessage', { 1608 | set: function set(value) { 1609 | this._onmidimessage = value; 1610 | if (typeof value === 'function') { 1611 | this.open(); 1612 | } 1613 | } 1614 | }); 1615 | 1616 | this._listeners = new Map().set('midimessage', new Set()).set('statechange', new Set()); 1617 | this._inLongSysexMessage = false; 1618 | this._sysexBuffer = new Uint8Array(); 1619 | 1620 | this._jazzInstance = instance; 1621 | this._jazzInstance.inputInUse = true; 1622 | 1623 | // on Linux opening and closing Jazz instances causes the plugin to crash a lot so we open 1624 | // the device here and don't close it when close() is called, see below 1625 | if ((0, _util.getDevice)().platform === 'linux') { 1626 | this._jazzInstance.MidiInOpen(this.name, midiProc.bind(this)); 1627 | } 1628 | } 1629 | 1630 | _createClass(MIDIInput, [{ 1631 | key: 'addEventListener', 1632 | value: function addEventListener(type, listener, useCapture) { 1633 | var listeners = this._listeners.get(type); 1634 | if (listeners === undefined) { 1635 | return; 1636 | } 1637 | 1638 | if (listeners.has(listener) === false) { 1639 | listeners.add(listener); 1640 | } 1641 | } 1642 | }, { 1643 | key: 'removeEventListener', 1644 | value: function removeEventListener(type, listener, useCapture) { 1645 | var listeners = this._listeners.get(type); 1646 | if (listeners === undefined) { 1647 | return; 1648 | } 1649 | 1650 | if (listeners.has(listener) === false) { 1651 | listeners['delete'](listener); 1652 | } 1653 | } 1654 | }, { 1655 | key: 'dispatchEvent', 1656 | value: function dispatchEvent(evt) { 1657 | var listeners = this._listeners.get(evt.type); 1658 | listeners.forEach(function (listener) { 1659 | listener(evt); 1660 | }); 1661 | 1662 | if (evt.type === 'midimessage') { 1663 | if (this._onmidimessage !== null) { 1664 | this._onmidimessage(evt); 1665 | } 1666 | } else if (evt.type === 'statechange') { 1667 | if (this.onstatechange !== null) { 1668 | this.onstatechange(evt); 1669 | } 1670 | } 1671 | } 1672 | }, { 1673 | key: 'open', 1674 | value: function open() { 1675 | if (this.connection === 'open') { 1676 | return; 1677 | } 1678 | if ((0, _util.getDevice)().platform !== 'linux') { 1679 | this._jazzInstance.MidiInOpen(this.name, midiProc.bind(this)); 1680 | } 1681 | this.connection = 'open'; 1682 | (0, _midi_access.dispatchEvent)(this); // dispatch MIDIConnectionEvent via MIDIAccess 1683 | } 1684 | }, { 1685 | key: 'close', 1686 | value: function close() { 1687 | if (this.connection === 'closed') { 1688 | return; 1689 | } 1690 | if ((0, _util.getDevice)().platform !== 'linux') { 1691 | this._jazzInstance.MidiInClose(); 1692 | } 1693 | this.connection = 'closed'; 1694 | (0, _midi_access.dispatchEvent)(this); // dispatch MIDIConnectionEvent via MIDIAccess 1695 | this._onmidimessage = null; 1696 | this.onstatechange = null; 1697 | this._listeners.get('midimessage').clear(); 1698 | this._listeners.get('statechange').clear(); 1699 | } 1700 | }, { 1701 | key: '_appendToSysexBuffer', 1702 | value: function _appendToSysexBuffer(data) { 1703 | var oldLength = this._sysexBuffer.length; 1704 | var tmpBuffer = new Uint8Array(oldLength + data.length); 1705 | tmpBuffer.set(this._sysexBuffer); 1706 | tmpBuffer.set(data, oldLength); 1707 | this._sysexBuffer = tmpBuffer; 1708 | } 1709 | }, { 1710 | key: '_bufferLongSysex', 1711 | value: function _bufferLongSysex(data, initialOffset) { 1712 | var j = initialOffset; 1713 | while (j < data.length) { 1714 | if (data[j] == 0xF7) { 1715 | // end of sysex! 1716 | j++; 1717 | this._appendToSysexBuffer(data.slice(initialOffset, j)); 1718 | return j; 1719 | } 1720 | j++; 1721 | } 1722 | // didn't reach the end; just tack it on. 1723 | this._appendToSysexBuffer(data.slice(initialOffset, j)); 1724 | this._inLongSysexMessage = true; 1725 | return j; 1726 | } 1727 | }]); 1728 | 1729 | return MIDIInput; 1730 | })(); 1731 | 1732 | exports.MIDIInput = MIDIInput; 1733 | 1734 | midiProc = function (timestamp, data) { 1735 | var length = 0; 1736 | var i = undefined; 1737 | var isSysexMessage = false; 1738 | 1739 | // Jazz sometimes passes us multiple messages at once, so we need to parse them out and pass them one at a time. 1740 | 1741 | for (i = 0; i < data.length; i += length) { 1742 | var isValidMessage = true; 1743 | if (this._inLongSysexMessage) { 1744 | i = this._bufferLongSysex(data, i); 1745 | if (data[i - 1] != 0xf7) { 1746 | // ran off the end without hitting the end of the sysex message 1747 | return; 1748 | } 1749 | isSysexMessage = true; 1750 | } else { 1751 | isSysexMessage = false; 1752 | switch (data[i] & 0xF0) { 1753 | case 0x00: 1754 | // Chew up spurious 0x00 bytes. Fixes a Windows problem. 1755 | length = 1; 1756 | isValidMessage = false; 1757 | break; 1758 | 1759 | case 0x80: // note off 1760 | case 0x90: // note on 1761 | case 0xA0: // polyphonic aftertouch 1762 | case 0xB0: // control change 1763 | case 0xE0: 1764 | // channel mode 1765 | length = 3; 1766 | break; 1767 | 1768 | case 0xC0: // program change 1769 | case 0xD0: 1770 | // channel aftertouch 1771 | length = 2; 1772 | break; 1773 | 1774 | case 0xF0: 1775 | switch (data[i]) { 1776 | case 0xf0: 1777 | // letiable-length sysex. 1778 | i = this._bufferLongSysex(data, i); 1779 | if (data[i - 1] != 0xf7) { 1780 | // ran off the end without hitting the end of the sysex message 1781 | return; 1782 | } 1783 | isSysexMessage = true; 1784 | break; 1785 | 1786 | case 0xF1: // MTC quarter frame 1787 | case 0xF3: 1788 | // song select 1789 | length = 2; 1790 | break; 1791 | 1792 | case 0xF2: 1793 | // song position pointer 1794 | length = 3; 1795 | break; 1796 | 1797 | default: 1798 | length = 1; 1799 | break; 1800 | } 1801 | break; 1802 | } 1803 | } 1804 | if (!isValidMessage) { 1805 | continue; 1806 | } 1807 | 1808 | var evt = {}; 1809 | evt.receivedTime = parseFloat(timestamp.toString()) + this._jazzInstance._perfTimeZero; 1810 | 1811 | if (isSysexMessage || this._inLongSysexMessage) { 1812 | evt.data = new Uint8Array(this._sysexBuffer); 1813 | this._sysexBuffer = new Uint8Array(0); 1814 | this._inLongSysexMessage = false; 1815 | } else { 1816 | evt.data = new Uint8Array(data.slice(i, length + i)); 1817 | } 1818 | 1819 | if (nodejs) { 1820 | if (this._onmidimessage) { 1821 | this._onmidimessage(evt); 1822 | } 1823 | } else { 1824 | var e = new _midimessage_event.MIDIMessageEvent(this, evt.data, evt.receivedTime); 1825 | this.dispatchEvent(e); 1826 | } 1827 | } 1828 | }; 1829 | 1830 | },{"./midi_access":58,"./midiconnection_event":61,"./midimessage_event":62,"./util":64}],60:[function(require,module,exports){ 1831 | /* 1832 | MIDIOutput is a wrapper around an output of a Jazz instance 1833 | */ 1834 | 1835 | 'use strict'; 1836 | 1837 | Object.defineProperty(exports, '__esModule', { 1838 | value: true 1839 | }); 1840 | 1841 | var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })(); 1842 | 1843 | function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } } 1844 | 1845 | var _util = require('./util'); 1846 | 1847 | var _midi_access = require('./midi_access'); 1848 | 1849 | var MIDIOutput = (function () { 1850 | function MIDIOutput(info, instance) { 1851 | _classCallCheck(this, MIDIOutput); 1852 | 1853 | this.id = (0, _midi_access.getMIDIDeviceId)(info[0], 'output'); 1854 | this.name = info[0]; 1855 | this.manufacturer = info[1]; 1856 | this.version = info[2]; 1857 | this.type = 'output'; 1858 | this.state = 'connected'; 1859 | this.connection = 'pending'; 1860 | this.onmidimessage = null; 1861 | this.onstatechange = null; 1862 | 1863 | this._listeners = new Set(); 1864 | this._inLongSysexMessage = false; 1865 | this._sysexBuffer = new Uint8Array(); 1866 | 1867 | this._jazzInstance = instance; 1868 | this._jazzInstance.outputInUse = true; 1869 | if ((0, _util.getDevice)().platform === 'linux') { 1870 | this._jazzInstance.MidiOutOpen(this.name); 1871 | } 1872 | } 1873 | 1874 | _createClass(MIDIOutput, [{ 1875 | key: 'open', 1876 | value: function open() { 1877 | if (this.connection === 'open') { 1878 | return; 1879 | } 1880 | if ((0, _util.getDevice)().platform !== 'linux') { 1881 | this._jazzInstance.MidiOutOpen(this.name); 1882 | } 1883 | this.connection = 'open'; 1884 | (0, _midi_access.dispatchEvent)(this); // dispatch MIDIConnectionEvent via MIDIAccess 1885 | } 1886 | }, { 1887 | key: 'close', 1888 | value: function close() { 1889 | if (this.connection === 'closed') { 1890 | return; 1891 | } 1892 | if ((0, _util.getDevice)().platform !== 'linux') { 1893 | this._jazzInstance.MidiOutClose(); 1894 | } 1895 | this.connection = 'closed'; 1896 | (0, _midi_access.dispatchEvent)(this); // dispatch MIDIConnectionEvent via MIDIAccess 1897 | this.onstatechange = null; 1898 | this._listeners.clear(); 1899 | } 1900 | }, { 1901 | key: 'send', 1902 | value: function send(data, timestamp) { 1903 | var _this = this; 1904 | 1905 | var delayBeforeSend = 0; 1906 | 1907 | if (data.length === 0) { 1908 | return false; 1909 | } 1910 | 1911 | if (timestamp) { 1912 | delayBeforeSend = Math.floor(timestamp - performance.now()); 1913 | } 1914 | 1915 | if (timestamp && delayBeforeSend > 1) { 1916 | setTimeout(function () { 1917 | _this._jazzInstance.MidiOutLong(data); 1918 | }, delayBeforeSend); 1919 | } else { 1920 | this._jazzInstance.MidiOutLong(data); 1921 | } 1922 | return true; 1923 | } 1924 | }, { 1925 | key: 'clear', 1926 | value: function clear() { 1927 | // to be implemented 1928 | } 1929 | }, { 1930 | key: 'addEventListener', 1931 | value: function addEventListener(type, listener, useCapture) { 1932 | if (type !== 'statechange') { 1933 | return; 1934 | } 1935 | 1936 | if (this._listeners.has(listener) === false) { 1937 | this._listeners.add(listener); 1938 | } 1939 | } 1940 | }, { 1941 | key: 'removeEventListener', 1942 | value: function removeEventListener(type, listener, useCapture) { 1943 | if (type !== 'statechange') { 1944 | return; 1945 | } 1946 | 1947 | if (this._listeners.has(listener) === false) { 1948 | this._listeners['delete'](listener); 1949 | } 1950 | } 1951 | }, { 1952 | key: 'dispatchEvent', 1953 | value: function dispatchEvent(evt) { 1954 | this._listeners.forEach(function (listener) { 1955 | listener(evt); 1956 | }); 1957 | 1958 | if (this.onstatechange !== null) { 1959 | this.onstatechange(evt); 1960 | } 1961 | } 1962 | }]); 1963 | 1964 | return MIDIOutput; 1965 | })(); 1966 | 1967 | exports.MIDIOutput = MIDIOutput; 1968 | 1969 | },{"./midi_access":58,"./util":64}],61:[function(require,module,exports){ 1970 | 'use strict'; 1971 | 1972 | Object.defineProperty(exports, '__esModule', { 1973 | value: true 1974 | }); 1975 | 1976 | function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } } 1977 | 1978 | var MIDIConnectionEvent = function MIDIConnectionEvent(midiAccess, port) { 1979 | _classCallCheck(this, MIDIConnectionEvent); 1980 | 1981 | this.bubbles = false; 1982 | this.cancelBubble = false; 1983 | this.cancelable = false; 1984 | this.currentTarget = midiAccess; 1985 | this.defaultPrevented = false; 1986 | this.eventPhase = 0; 1987 | this.path = []; 1988 | this.port = port; 1989 | this.returnValue = true; 1990 | this.srcElement = midiAccess; 1991 | this.target = midiAccess; 1992 | this.timeStamp = Date.now(); 1993 | this.type = 'statechange'; 1994 | }; 1995 | 1996 | exports.MIDIConnectionEvent = MIDIConnectionEvent; 1997 | 1998 | },{}],62:[function(require,module,exports){ 1999 | 'use strict'; 2000 | 2001 | Object.defineProperty(exports, '__esModule', { 2002 | value: true 2003 | }); 2004 | 2005 | function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } } 2006 | 2007 | var MIDIMessageEvent = function MIDIMessageEvent(port, data, receivedTime) { 2008 | _classCallCheck(this, MIDIMessageEvent); 2009 | 2010 | this.bubbles = false; 2011 | this.cancelBubble = false; 2012 | this.cancelable = false; 2013 | this.currentTarget = port; 2014 | this.data = data; 2015 | this.defaultPrevented = false; 2016 | this.eventPhase = 0; 2017 | this.path = []; 2018 | this.receivedTime = receivedTime; 2019 | this.returnValue = true; 2020 | this.srcElement = port; 2021 | this.target = port; 2022 | this.timeStamp = Date.now(); 2023 | this.type = 'midimessage'; 2024 | }; 2025 | 2026 | exports.MIDIMessageEvent = MIDIMessageEvent; 2027 | 2028 | },{}],63:[function(require,module,exports){ 2029 | /* 2030 | Top entry point 2031 | */ 2032 | 2033 | 'use strict'; 2034 | 2035 | var _midi_access = require('./midi_access'); 2036 | 2037 | var _util = require('./util'); 2038 | 2039 | var midiAccess = undefined; 2040 | 2041 | (function () { 2042 | if (!navigator.requestMIDIAccess) { 2043 | (0, _util.polyfill)(); 2044 | navigator.requestMIDIAccess = function () { 2045 | // singleton-ish, no need to create multiple instances of MIDIAccess 2046 | if (midiAccess === undefined) { 2047 | midiAccess = (0, _midi_access.createMIDIAccess)(); 2048 | } 2049 | return midiAccess; 2050 | }; 2051 | if ((0, _util.getDevice)().nodejs === true) { 2052 | navigator.close = function () { 2053 | // Need to close MIDI input ports, otherwise Node.js will wait for MIDI input forever. 2054 | (0, _midi_access.closeAllMIDIInputs)(); 2055 | }; 2056 | } 2057 | } 2058 | })(); 2059 | 2060 | },{"./midi_access":58,"./util":64}],64:[function(require,module,exports){ 2061 | (function (process,global){ 2062 | /* 2063 | A collection of handy util methods 2064 | */ 2065 | 2066 | 'use strict'; 2067 | 2068 | Object.defineProperty(exports, '__esModule', { 2069 | value: true 2070 | }); 2071 | exports.getDevice = getDevice; 2072 | exports.polyfillPerformance = polyfillPerformance; 2073 | exports.generateUUID = generateUUID; 2074 | exports.polyfillPromise = polyfillPromise; 2075 | exports.polyfill = polyfill; 2076 | var device = undefined; 2077 | 2078 | // check on what type of device we are running, note that in this context a device is a computer not a MIDI device 2079 | 2080 | function getDevice() { 2081 | 2082 | if (device !== undefined) { 2083 | return device; 2084 | } 2085 | 2086 | var platform = 'undetected', 2087 | browser = 'undetected', 2088 | nodejs = false; 2089 | 2090 | if (navigator.nodejs) { 2091 | platform = process.platform; 2092 | device = { 2093 | platform: platform, 2094 | nodejs: true, 2095 | mobile: platform === 'ios' || platform === 'android' 2096 | }; 2097 | return device; 2098 | } 2099 | 2100 | var ua = navigator.userAgent; 2101 | 2102 | if (ua.match(/(iPad|iPhone|iPod)/g)) { 2103 | platform = 'ios'; 2104 | } else if (ua.indexOf('Android') !== -1) { 2105 | platform = 'android'; 2106 | } else if (ua.indexOf('Linux') !== -1) { 2107 | platform = 'linux'; 2108 | } else if (ua.indexOf('Macintosh') !== -1) { 2109 | platform = 'osx'; 2110 | } else if (ua.indexOf('Windows') !== -1) { 2111 | platform = 'windows'; 2112 | } 2113 | 2114 | if (ua.indexOf('Chrome') !== -1) { 2115 | // chrome, chromium and canary 2116 | browser = 'chrome'; 2117 | 2118 | if (ua.indexOf('OPR') !== -1) { 2119 | browser = 'opera'; 2120 | } else if (ua.indexOf('Chromium') !== -1) { 2121 | browser = 'chromium'; 2122 | } 2123 | } else if (ua.indexOf('Safari') !== -1) { 2124 | browser = 'safari'; 2125 | } else if (ua.indexOf('Firefox') !== -1) { 2126 | browser = 'firefox'; 2127 | } else if (ua.indexOf('Trident') !== -1) { 2128 | browser = 'ie'; 2129 | if (ua.indexOf('MSIE 9') !== -1) { 2130 | browser = 'ie9'; 2131 | } 2132 | } 2133 | 2134 | if (platform === 'ios') { 2135 | if (ua.indexOf('CriOS') !== -1) { 2136 | browser = 'chrome'; 2137 | } 2138 | } 2139 | 2140 | device = { 2141 | platform: platform, 2142 | browser: browser, 2143 | mobile: platform === 'ios' || platform === 'android', 2144 | nodejs: false 2145 | }; 2146 | return device; 2147 | } 2148 | 2149 | function polyfillPerformance() { 2150 | if (performance === undefined) { 2151 | performance = {}; 2152 | } 2153 | Date.now = Date.now || function () { 2154 | return new Date().getTime(); 2155 | }; 2156 | 2157 | if (performance.now === undefined) { 2158 | (function () { 2159 | var nowOffset = Date.now(); 2160 | if (performance.timing !== undefined && performance.timing.navigationStart !== undefined) { 2161 | nowOffset = performance.timing.navigationStart; 2162 | } 2163 | performance.now = function now() { 2164 | return Date.now() - nowOffset; 2165 | }; 2166 | })(); 2167 | } 2168 | } 2169 | 2170 | function generateUUID() { 2171 | var d = new Date().getTime(); 2172 | var uuid = new Array(64).join('x');; //'xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx'; 2173 | uuid = uuid.replace(/[xy]/g, function (c) { 2174 | var r = (d + Math.random() * 16) % 16 | 0; 2175 | d = Math.floor(d / 16); 2176 | return (c == 'x' ? r : r & 0x3 | 0x8).toString(16).toUpperCase(); 2177 | }); 2178 | return uuid; 2179 | } 2180 | 2181 | // a very simple implementation of a Promise for Internet Explorer and Nodejs 2182 | 2183 | function polyfillPromise(scope) { 2184 | if (typeof scope.Promise !== 'function') { 2185 | 2186 | scope.Promise = function (executor) { 2187 | this.executor = executor; 2188 | }; 2189 | 2190 | scope.Promise.prototype.then = function (accept, reject) { 2191 | if (typeof accept !== 'function') { 2192 | accept = function () {}; 2193 | } 2194 | if (typeof reject !== 'function') { 2195 | reject = function () {}; 2196 | } 2197 | this.executor(accept, reject); 2198 | }; 2199 | } 2200 | } 2201 | 2202 | function polyfill() { 2203 | var device = getDevice(); 2204 | if (device.browser === 'ie') { 2205 | polyfillPromise(window); 2206 | } else if (device.nodejs === true) { 2207 | polyfillPromise(global); 2208 | } 2209 | polyfillPerformance(); 2210 | } 2211 | 2212 | }).call(this,require('_process'),typeof global !== "undefined" ? global : typeof self !== "undefined" ? self : typeof window !== "undefined" ? window : {}) 2213 | 2214 | },{"_process":56}]},{},[63]) 2215 | --------------------------------------------------------------------------------