UNPKG

jzz-gui-player

Version:
821 lines (781 loc) 29.3 kB
(function(global, factory) { /* istanbul ignore next */ if (typeof exports === 'object' && typeof module !== 'undefined') { factory.Player = factory; module.exports = factory; } else if (typeof define === 'function' && define.amd) { define('JZZ.gui.Player', ['JZZ', 'JZZ.midi.SMF'], factory); } else { factory(JZZ); } })(this, function(JZZ) { if (!JZZ.gui) JZZ.gui = {}; if (JZZ.gui.Player) return; /* istanbul ignore next */ function nop() {} var _noBtn = { on: nop, off: nop, disable: nop, title: nop, div: {} }; var theme = { container: { backgroundColor: '#888', borderRadius: '0px', borderWidth: '1px' }, lbl: { color: '#aaa', fontSize: '12px', fontFamily: 'Arial, Helvetica, sans-serif' }, btn: { borderRadius: '0px', backgroundColor: { on: '#ddd', off: '#aaa', disable: '#888' }, borderColor: { on: '#ccc', off: '#ccc', disable: '#aaa' }, svgFill: { on: '#000', off: '#000', disable: '#555' }, close: { borderRadius: '0px', backgroundColor: '#f44' } }, rail: { borderRadius: '2px', borderWidth: '1px', backgroundColor: { enable: '#ccc', disable: '#888' }, borderColor: { enable: '#ccc', disable: '#aaa' } }, caret: { borderRadius: '6px', borderWidth: '1px', backgroundColor: { mouseDown: '#ddd', mouseUp: '#aaa', enable: '#aaa', disable: '#888' }, borderColor: { enable: '#ccc', disable: '#aaa' } }, svg: { play: '<svg fill="#555" height="18" viewBox="0 0 24 24" width="18" xmlns="http://www.w3.org/2000/svg"><path d="M8 5v14l11-7z"/><path d="M0 0h24v24H0z" fill="none"/></svg>', pause: '<svg fill="#555" height="18" viewBox="0 0 24 24" width="18" xmlns="http://www.w3.org/2000/svg"><path d="M6 19h4V5H6v14zm8-14v14h4V5h-4z"/><path d="M0 0h24v24H0z" fill="none"/></svg>', stop: '<svg fill="#555" height="18" viewBox="0 0 24 24" width="18" xmlns="http://www.w3.org/2000/svg"><path d="M0 0h24v24H0z" fill="none"/><path d="M6 6h12v12H6z"/></svg>', loop: '<svg fill="#555" height="18" viewBox="0 0 24 24" width="18" xmlns="http://www.w3.org/2000/svg"><path d="M0 0h24v24H0z" fill="none"/><path d="M12 5V1L7 6l5 5V7c3.31 0 6 2.69 6 6s-2.69 6-6 6-6-2.69-6-6H4c0 4.42 3.58 8 8 8s8-3.58 8-8-3.58-8-8-8z"/></svg>', more: '<svg fill="#555" height="18" viewBox="0 0 24 24" width="18" xmlns="http://www.w3.org/2000/svg"><path d="M0 0h24v24H0z" fill="none"/><path d="M12 3v9.28c-.47-.17-.97-.28-1.5-.28C8.01 12 6 14.01 6 16.5S8.01 21 10.5 21c2.31 0 4.2-1.75 4.45-4H15V6h4V3h-7z"/></svg>', open: '<svg fill="#555" xmlns="http://www.w3.org/2000/svg" width="18" height="18" viewBox="0 0 24 24"><path fill="none" d="M0 0h24v24H0V0z"/><path d="M10 4H2v16h20V6H12l-2-2z"/></svg>', link: '<svg fill="#555" xmlns="http://www.w3.org/2000/svg" width="18" height="18" viewBox="0 0 24 24"><path d="M19 12v7H5v-7H3v7c0 1.1.9 2 2 2h14c1.1 0 2-.9 2-2v-7h-2zm-6 .67l2.59-2.58L17 11.5l-5 5-5-5 1.41-1.41L11 12.67V3h2z"/><path fill="none" d="M0 0h24v24H0z"/></svg>', close: '<svg stroke="#ff8" xmlns="http://www.w3.org/2000/svg" width="7" height="7" viewBox="0 0 7 7"><line x1="1" y1="1" x2="6" y2="6"/><line x1="1" y1="6" x2="6" y2="1"/></svg>' } }; function Btn(html) { this.div = document.createElement('div'); this.div.style.display = 'inline-block'; this.div.style.position = 'absolute'; this.div.style.boxSizing = 'content-box'; this.div.style.top = '8px'; this.div.style.margin = '0'; this.div.style.padding = '2px'; this.div.style.borderRadius = theme.btn.borderRadius; this.div.style.borderStyle = 'solid'; this.div.style.borderWidth = theme.container.borderWidth; this.div.style.borderColor = theme.btn.borderColor.disable; this.div.style.backgroundColor = theme.btn.backgroundColor.disable; this.div.style.lineHeight = '0'; this.div.style.lineSpasing = '0'; this.div.style.width = '18px'; this.div.style.height = '18px'; this.div.innerHTML = html; } Btn.prototype.on = function() { this.div.style.backgroundColor = theme.btn.backgroundColor.on; this.div.style.borderColor = theme.btn.borderColor.on; this.div.firstChild.style.fill = theme.btn.svgFill.on; }; Btn.prototype.off = function() { this.div.style.backgroundColor = theme.btn.backgroundColor.off; this.div.style.borderColor = theme.btn.borderColor.off; this.div.firstChild.style.fill = theme.btn.svgFill.off; }; Btn.prototype.disable = function() { this.div.style.backgroundColor = theme.btn.backgroundColor.disable; this.div.style.borderColor = theme.btn.borderColor.disable; this.div.firstChild.style.fill = theme.btn.svgFill.disable; }; Btn.prototype.title = function(s) { this.div.title = s; }; function _stopProp(e) { e.stopPropagation(); e.preventDefault(); } function _createGUI(self, arg) { self.gui = document.createElement('div'); self.gui.style.display = 'inline-block'; self.gui.style.position = 'relative'; self.gui.style.boxSizing = 'content-box'; self.gui.style.margin = '0px'; self.gui.style.padding = '0px'; self.gui.style.borderRadius = theme.container.borderRadius; self.gui.style.borderStyle = 'none'; self.gui.style.backgroundColor = theme.container.backgroundColor; self.gui.style.width = '270px'; self.gui.style.height = '40px'; var left = 8; var right = 238; var step = 28; if (arg.play) { self.playBtn = new Btn(theme.svg.play); self.playBtn.div.style.left = left + 'px'; left += step; self.playBtn.div.title = 'play'; self.playBtn.div.addEventListener('click', function() { self.play(); }); self.gui.appendChild(self.playBtn.div); } else self.playBtn = _noBtn; if (arg.pause) { self.pauseBtn = new Btn(theme.svg.pause); self.pauseBtn.div.style.left = left + 'px'; left += step; self.pauseBtn.div.title = 'pause'; self.pauseBtn.div.addEventListener('click', function() { self.pause(); }); self.gui.appendChild(self.pauseBtn.div); } else self.pauseBtn = _noBtn; if (arg.stop) { self.stopBtn = new Btn(theme.svg.stop); self.stopBtn.div.style.left = left + 'px'; left += step; self.stopBtn.div.title = 'stop'; self.stopBtn.div.addEventListener('click', function() { self.stop(); }); self.gui.appendChild(self.stopBtn.div); } else self.stopBtn = _noBtn; if (arg.loop) { self.loopBtn = new Btn(theme.svg.loop); self.loopBtn.div.style.left = left + 'px'; left += step; self.loopBtn.div.title = 'loop'; self.loopBtn.div.addEventListener('click', function() { self.loop(); }); self.gui.appendChild(self.loopBtn.div); } else self.loopBtn = _noBtn; if (arg.midi) { self.midiBtn = new Btn(theme.svg.more); self.midiBtn.div.style.left = right + 'px'; right -= step; self.midiBtn.div.title = 'midi'; self.midiBtn.div.addEventListener('click', function() { self.settings(); }); self.gui.appendChild(self.midiBtn.div); self.sel = document.createElement('select'); self.sel.style.position = 'absolute'; self.sel.style.top = '30px'; self.sel.style.left = '40px'; self.sel.style.width = '230px'; self.sel.style.display = 'none'; self.sel.style.zIndex = 1; self.sel.addEventListener('click', function() { self._selected(); }); self.sel.addEventListener('keydown', function(e) { self._keydown(e); }); self.sel.addEventListener('focusout', function() { self._closeselect(); }); self.gui.appendChild(self.sel); } else self.midiBtn = _noBtn; if (arg.link) { self.linkBtn = new Btn(theme.svg.link); self.linkBtn.div.style.left = right + 'px'; right -= step; self.linkBtn.div.title = 'link'; self.gui.appendChild(self.linkBtn.div); } if (arg.file) { self.fileBtn = new Btn(theme.svg.open); self.fileBtn.div.style.left = right + 'px'; right -= step; self.fileBtn.div.title = 'file'; self.gui.appendChild(self.fileBtn.div); self.fileInput = document.createElement('input'); self.fileInput.type = 'file'; self.fileInput.style.position = 'fixed'; self.fileInput.style.visibility = 'hidden'; self.fileInput.accept = '.mid, .midi, .midi2, .kar, .rmi, .syx'; self.gui.appendChild(self.fileInput); if (window.FileReader) { self.fileBtn.off(); self.fileBtn.div.addEventListener('click', function() { self.fileInput.click(); }); self.fileInput.addEventListener('change', function(e) { _stopProp(e); if (e.target.files[0]) self.readFile(e.target.files[0]); }); self.gui.addEventListener('drop', function(e) { _stopProp(e); self.fileBtn.off(); self.readFile(e.dataTransfer.files[0]); }); self.gui.addEventListener('dragover', function(e) { _stopProp(e); self.fileBtn.on(); e.dataTransfer.dropEffect = 'copy'; }); self.gui.addEventListener('dragexit', function(e) { _stopProp(e); self.fileBtn.off(); }); } } else self.fileBtn = _noBtn; if (arg.close) { self.closeBtn = document.createElement('div'); self.closeBtn.style.display = 'inline-block'; self.closeBtn.style.position = 'absolute'; self.closeBtn.style.boxSizing = 'content-box'; self.closeBtn.style.top = '1px'; self.closeBtn.style.left = '262px'; self.closeBtn.style.margin = '0'; self.closeBtn.style.padding = '0'; self.closeBtn.style.borderRadius = theme.btn.close.borderRadius; self.closeBtn.style.backgroundColor = theme.btn.close.backgroundColor; self.closeBtn.style.width = '7px'; self.closeBtn.style.height = '7px'; self.closeBtn.style.lineHeight = '0'; self.closeBtn.style.lineSpasing = '0'; self.closeBtn.innerHTML = theme.svg.close; self.closeBtn.title = 'close'; self.closeBtn.addEventListener('click', function() { self.destroy(); }); self.gui.appendChild(self.closeBtn); } self.rlen = right - left + 10; self.lbl = document.createElement('div'); self.lbl.style.display = 'inline-block'; self.lbl.style.position = 'absolute'; self.lbl.style.top = '26px'; self.lbl.style.left = left + 'px'; self.lbl.style.width = (self.rlen + 10) + 'px'; self.lbl.style.height = '12px'; self.lbl.style.padding = '0'; self.lbl.style.textAlign = 'center'; self.lbl.style.color = theme.lbl.color; self.lbl.style.fontSize = theme.lbl.fontSize; self.lbl.style.fontFamily = theme.lbl.fontFamily; self.gui.appendChild(self.lbl); self.rail = document.createElement('div'); self.rail.style.display = 'inline-block'; self.rail.style.position = 'absolute'; self.rail.style.boxSizing = 'content-box'; self.rail.style.top = '19px'; self.rail.style.left = (left + 5) + 'px'; self.rail.style.width = self.rlen + 'px'; self.rail.style.height = '0'; self.rail.style.padding = '1px'; self.rail.style.borderStyle = 'solid'; self.rail.style.borderWidth = theme.rail.borderWidth; self.rail.style.borderRadius = theme.rail.borderRadius; self.rail.style.borderColor = theme.rail.borderColor.disable; self.rail.style.backgroundColor = theme.rail.backgroundColor.disable; self.gui.appendChild(self.rail); self.caret = document.createElement('div'); self.caret.style.display = 'inline-block'; self.caret.style.position = 'absolute'; self.caret.style.boxSizing = 'content-box'; self.caret.style.width = '2px'; self.caret.style.height = '2px'; self.caret.style.top = '-5px'; self.caret.style.left = '-5px'; self.caret.style.padding = '4px'; self.caret.style.borderStyle = 'solid'; self.caret.style.borderWidth = theme.caret.borderWidth; self.caret.style.borderRadius = theme.caret.borderRadius; self.caret.style.borderColor = theme.caret.borderColor.disable; self.caret.style.backgroundColor = theme.caret.backgroundColor.disable; self.caret.addEventListener('mousedown', function(e) { self._mousedown(e); }); self.rail.appendChild(self.caret); window.addEventListener('mousemove', function(e) { self._mousemove(e); }); window.addEventListener('mouseup', function(e) { self._mouseup(e); }); } var _floating = 0; function Player(x, y) { if (!(this instanceof Player)) return new Player(x, y); this._m2m1 = new JZZ.M2M1(); this._connect(this._m2m1); var arg = { at: undefined, x: undefined, y: undefined, play: true, record: false, pause: true, stop: true, loop: true, file: false, link: false, midi: true, close: false, sndoff: true, ports: [undefined, /MIDI Through/i], connect: true }; if (typeof x == 'object') for (var k in arg) if (arg.hasOwnProperty(k) && typeof x[k] != 'undefined') arg[k] = x[k]; if (typeof arg.at == 'undefined') arg.at = x; if (typeof arg.x == 'undefined') arg.x = x; if (typeof arg.y == 'undefined') arg.y = y; _createGUI(this, arg); if (!(arg.ports instanceof Array)) arg.ports = [arg.ports]; arg.ports.push(undefined); this._ports = arg.ports; this._conn = arg.connect; this._sndoff = arg.sndoff; this.disable(); if (typeof arg.at == 'string') { try { document.getElementById(arg.at).appendChild(this.gui); return this; } catch(e) {} } try { arg.at.appendChild(this.gui); return this; } catch(e) {} if (arg.x != parseInt(arg.x) || arg.y != parseInt(arg.y)) { arg.x = _floating * 15 + 5; arg.y = _floating * 45 + 5; _floating++; } this.gui.style.position = 'fixed'; this.gui.style.top = arg.y + 'px'; this.gui.style.left = arg.x + 'px'; this.gui.style.opacity = 0.9; var self = this; this.gui.addEventListener('mousedown', function(e) { self._startmove(e); }); document.body.appendChild(this.gui); } Player.prototype = new JZZ.Widget(); Player.prototype.constructor = Player; Player.prototype.label = function(html) { this.lbl.innerHTML = html; }; Player.prototype.disable = function() { this.playBtn.disable(); this.pauseBtn.disable(); this.stopBtn.disable(); this.loopBtn.disable(); this.midiBtn.disable(); if (this._conn) this.midiBtn.off(); this.fileBtn.off(); this.rail.style.borderColor = theme.rail.borderColor.disable; this.rail.style.backgroundColor = theme.rail.backgroundColor.disable; this.caret.style.borderColor = theme.caret.borderColor.disable; this.caret.style.backgroundColor = theme.caret.backgroundColor.disable; }; Player.prototype.enable = function() { this.playBtn.off(); this.pauseBtn.off(); this.stopBtn.off(); this.loopBtn.off(); if (this._conn) this.midiBtn.off(); this.rail.style.borderColor = theme.rail.borderColor.enable; this.caret.style.backgroundColor = theme.caret.backgroundColor.enable; this.caret.style.borderColor = theme.caret.borderColor.enable; }; Player.prototype.load = function(smf) { var self = this; this._player = smf.player(); this._player.trim(); this._player.connect(this); this._player.onEnd = function() { self._onEnd(); }; this._player.filter(this._setfilter); if (!this._sndoff) this._player.sndOff = nop; this.enable(); this.onLoad(smf); }; Player.prototype.filter = function(f) { this._setfilter = f instanceof Function ? f : undefined; if (this._player) this._player.filter(this._setfilter); }; Player.prototype.onSelect = nop; Player.prototype.onEnd = nop; Player.prototype.onLoad = nop; Player.prototype._onEnd = function() { this.onEnd(); if (this._loop && this._loop != -1) this._loop--; if (!this._loop) { if (this._moving) clearInterval(this._moving); this._move(); this._playing = false; this.playBtn.off(); } else { if (this._loop == 1) { this._loop = 0; this.loopBtn.off(); this.loopBtn.title('loop'); } else this.loopBtn.title('loop: ' + (this._loop == -1 ? '\u221e' : this._loop)); } }; Player.prototype._move = function() { var off = Math.round(this._player.positionMS() * this.rlen / this._player.durationMS()) - 5; this.caret.style.left = off + 'px'; }; Player.prototype.onPlay = nop; Player.prototype.onResume = nop; Player.prototype._resume = function() { var self = this; this._player.resume(); this._moving = setInterval(function() { self._move(); }, 100); }; Player.prototype.play = function() { if (this._player) { var self = this; this.playBtn.on(); this.pauseBtn.off(); if (this._playing) return; if (this._paused) this.onResume(); else this.onPlay(); this._playing = true; this._paused = false; if (this._out || !this._conn) { this._resume(); } else if (!this._waiting) { this._waiting = true; JZZ().openMidiOut(self._ports).and(function() { self._out = this; self._outname = this.name(); self.midiBtn.title(self._outname); self._m2m1.connect(this); self._waiting = false; self.onSelect(self._outname); if (self._playing) { self._resume(); } }).or(function() { self._waiting = false; self._resume(); }); } } }; Player.prototype.onStop = nop; Player.prototype.stop = function() { if (this._player) { var self = this; this._player.stop(); JZZ.lib.schedule(function() { self.onStop(); }); if (this._moving) clearInterval(this._moving); this._playing = false; this._paused = false; this.playBtn.off(); this.pauseBtn.off(); this._move(); } }; Player.prototype.onPause = nop; Player.prototype.pause = function(p) { if (this._player) { var self = this; if (this._paused) { if (typeof p == 'undefined' || p) { if (this._out) { this._resume(); this.onResume(); this._playing = true; this._paused = false; this.playBtn.on(); this.pauseBtn.off(); } else this.play(); } } else if (this._playing) { if (typeof p == 'undefined' || !p) { this._player.pause(); JZZ.lib.schedule(function() { self.onPause(); }); if (this._moving) clearInterval(this._moving); this._playing = false; this._paused = true; this.playBtn.off(); this.pauseBtn.on(); } } } }; Player.prototype.onLoop = nop; Player.prototype.loop = function(n) { if (this._player) { var self = this; if (typeof n == 'undefined') n = !this._loop; if (n == parseInt(n) && n > 0) this._loop = n; else this._loop = n ? -1 : 0; if (this._loop == 1) this._loop = 0; this._player.loop(this._loop); JZZ.lib.schedule(function() { self.onLoop(n); }); if (this._loop) { this.loopBtn.on(); this.loopBtn.title('loop: ' + (this._loop == -1 ? '\u221e' : this._loop)); } else { this.loopBtn.off(); this.loopBtn.title('loop'); } } }; Player.prototype.onClose = nop; Player.prototype.destroy = function() { this.stop(); if (this._out) { var out = this._out; JZZ.lib.schedule(function() { out.close(); }); } this.gui.parentNode.removeChild(this.gui); this.onClose(); }; Player.prototype.setUrl = function(url, name) { if (this.linkBtn) { if (this._url) { this.linkBtn.div.appendChild(this._url.firstChild); this.linkBtn.div.removeChild(this._url); this._url = undefined; } if (typeof url == 'undefined') this.linkBtn.disable(); else { this.linkBtn.off(); this._url = document.createElement('a'); this._url.target = '_blank'; this._url.appendChild(this.linkBtn.div.firstChild); this.linkBtn.div.appendChild(this._url); this._url.href = url; if (!this._url.dataset) this._url.dataset = {}; this._url.dataset.jzzGuiPlayer = true; if (typeof name != 'undefined') this._url.download = name; } } }; Player.prototype.readFile = function(f) { var self = this; var reader = new FileReader(); reader.onload = function(e) { var data = ''; var bytes = new Uint8Array(e.target.result); for (var i = 0; i < bytes.length; i++) data += String.fromCharCode(bytes[i]); var smf; var mime = 'audio/midi'; try { smf = new JZZ.MIDI.Clip(data); mime = 'audio/midi-clip'; } catch (err) {} try { if (!smf) { smf = new JZZ.MIDI.SYX(data); mime = 'application/octet-stream'; } } catch (err) {} try { if (!smf) smf = new JZZ.MIDI.SMF(data); self.stop(); JZZ.lib.schedule(function() { self.load(smf); }); if (self.linkBtn) self.setUrl('data:' + mime + ';base64,' + JZZ.lib.toBase64(data), f.name); } catch (err) { console.log(err.message); } }; reader.readAsArrayBuffer(f); }; // selecting MIDI Player.prototype.onSelect = nop; Player.prototype._closeselect = function() { this.midiBtn.off(); this.sel.style.display = 'none'; this._more = false; }; Player.prototype.settings = function() { if (this._more || !this._conn) return; var self = this; this._more = true; this.midiBtn.on(); this.sel.style.display = 'inline-block'; JZZ().refresh().and(function() { var outs = this.info().outputs; var i; for (i = 0; i < self.sel.options.length; i++) self.sel.remove(i); for (i = 0; i < outs.length; i++) self.sel[i] = new Option(outs[i].name, outs[i].name, outs[i].name == self._outname, outs[i].name == self._outname); self.sel.size = outs.length < 2 ? 2 : outs.length; self.sel.focus(); }); }; Player.prototype._selectMidi = function() { var self = this; JZZ().openMidiOut(this._newname).or(function() { self._newname = undefined; self._closeselect(); }).and(function() { self._newname = undefined; if (self._outname != this.name()) { self._outname = this.name(); self._closeselect(); if (self._out) { if (self._playing) for (var c = 0; c < 16; c++) self._out._receive(JZZ.MIDI.allSoundOff(c)); self._m2m1.disconnect(self._out); self._out.close(); } self._out = this; self._m2m1.connect(this); self.midiBtn.title(self._outname); self.onSelect(self._outname); setTimeout(function() { self.onSelect(self._outname); }, 0); } }); }; Player.prototype.select = function(name) { var self = this; this._newname = name || 0; if (this._newname == this._outname) { this._newname = undefined; this._closeselect(); } else { setTimeout(function() { self._selectMidi(); }, 0); } }; Player.prototype._selected = function() { var selected = this.sel.options[this.sel.selectedIndex]; if (selected) this.select(selected.value); }; Player.prototype._keydown = function(e) { if (e.keyCode == 13 || e.keyCode == 32) this._selected(); }; Player.prototype.type = function() { return this._player ? this._player.type() : 0; }; Player.prototype.tracks = function() { return this._player ? this._player.tracks() : 0; }; Player.prototype.duration = function() { return this._player ? this._player.duration() : 0; }; Player.prototype.durationMS = function() { return this._player ? this._player.durationMS() : 0; }; Player.prototype.position = function() { return this._player ? this._player.position() : 0; }; Player.prototype.positionMS = function() { return this._player ? this._player.positionMS() : 0; }; Player.prototype.tick2ms = function() { return this._player ? this._player.tick2ms() : 0; }; Player.prototype.ms2tick = function() { return this._player ? this._player.ms2tick() : 0; }; Player.prototype.onJump = nop; Player.prototype.jump = function(pos) { if (this._player) { this._player.jump(pos); this._move(); if (!this._playing) { if (pos) { this._paused = true; this.playBtn.off(); this.pauseBtn.on(); } else { this._paused = false; this.playBtn.off(); this.pauseBtn.off(); } } this.onJump(this._player.position()); } }; Player.prototype.jumpMS = function(pos) { if (this._player) { this._player.jumpMS(pos); this._move(); if (!this._playing) { if (pos) { this._paused = true; this.playBtn.off(); this.pauseBtn.on(); } else { this._paused = false; this.playBtn.off(); this.pauseBtn.off(); } } this.onJump(this._player.position()); } }; Player.prototype.speed = function(x) { return this._player ? this._player.speed(x) : 1; }; // mouse dragging function _lftBtnDn(e) { return typeof e.buttons == 'undefined' ? !e.button : e.buttons & 1; } Player.prototype._mousedown = function(e) { if (_lftBtnDn(e) && this._player) { if (!this._more) e.preventDefault(); this.caret.style.backgroundColor = theme.caret.backgroundColor.mouseDown; this._wasPlaying = this._playing; this._player.pause(); this._caretX = e.clientX; this._caretPos = parseInt(this.caret.style.left) + 5; } }; Player.prototype._startmove = function(e) { if (_lftBtnDn(e)) { if (!this._more) e.preventDefault(); this._startX = parseInt(this.gui.style.left); this._startY = parseInt(this.gui.style.top); this._clickX = e.clientX; this._clickY = e.clientY; } }; Player.prototype._mouseup = function() { if (this._player) { if (typeof this._caretX != 'undefined') { if (this._wasPlaying) { this._wasPlaying = undefined; this._player.resume(); } this.caret.style.backgroundColor = theme.caret.backgroundColor.mouseUp; this._caretX = undefined; } } if (typeof this._startX != 'undefined') { this._startX = undefined; this._startY = undefined; this._clickX = undefined; this._clickY = undefined; } }; Player.prototype._mousemove = function(e) { if (this._more) { this._startX = undefined; this._startY = undefined; this._clickX = undefined; this._clickY = undefined; } if (this._player && typeof this._caretX != 'undefined') { e.preventDefault(); var to = this._caretPos + e.clientX - this._caretX; if (to < 0) to = 0; if (to > this.rlen) to = this.rlen; this.jumpMS(this.durationMS() * to * 1.0 / this.rlen); } else if (typeof this._startX != 'undefined') { e.preventDefault(); this.gui.style.left = this._startX - this._clickX + e.clientX + 'px'; this.gui.style.top = this._startY - this._clickY + e.clientY + 'px'; } }; Player.prototype._connect = Player.prototype.connect; Player.prototype._disconnect = Player.prototype.disconnect; Player.prototype.connect = function(port) { if (port == this) { this._conn = true; this.midiBtn.off(); } else { this._connect(port); } }; Player.prototype.disconnect = function(port) { if (port == this) { this._conn = false; if (this._out) this._m2m1.disconnect(this._out); this._outname = undefined; this.midiBtn.disable(); } else { this._disconnect(port); this._connect(this._m2m1); } }; Player.prototype.connected = function() { return this._outname; }; JZZ.gui.Player = Player; JZZ.gui.Player.Btn = Btn; JZZ.gui.Player.theme = theme; });