From aba69b26f66ee1483ceb73316d412ce1f87d1744 Mon Sep 17 00:00:00 2001 From: Jon Bergli Heier Date: Wed, 10 Aug 2011 19:43:09 +0200 Subject: Implemented a client-side song queue. --- .gitignore | 1 + static/icons/sound.png | Bin 0 -> 610 bytes static/index.html | 12 ++++++++++- static/player.js | 20 ++++++++++++++++++- static/playlist.js | 53 +++++++++++++++++++++++++++++++++++++++++++++++++ static/style.css | 12 +++++++---- 6 files changed, 92 insertions(+), 6 deletions(-) create mode 100644 static/icons/sound.png create mode 100644 static/playlist.js diff --git a/.gitignore b/.gitignore index c064cc9..0d8ffc4 100644 --- a/.gitignore +++ b/.gitignore @@ -2,3 +2,4 @@ *.vim *.pyc /config +/cache diff --git a/static/icons/sound.png b/static/icons/sound.png new file mode 100644 index 0000000..6056d23 Binary files /dev/null and b/static/icons/sound.png differ diff --git a/static/index.html b/static/index.html index 15384aa..23e2db6 100644 --- a/static/index.html +++ b/static/index.html @@ -4,6 +4,7 @@ foo + @@ -14,7 +15,16 @@
- +
+ + Browse directory + + + + Song queue +
    +
    +
    none
    diff --git a/static/player.js b/static/player.js index c0cf6ff..2fa8793 100644 --- a/static/player.js +++ b/static/player.js @@ -1,4 +1,5 @@ audio = null; +playlist = null; // pre-load some icons cache_images = new Array( @@ -51,7 +52,7 @@ function MusicListing(type, path, name, cached) { if(type == 'dir') { list(path); } else if(type == 'file') { - ml.play(); + playlist.add(ml); } return false; } @@ -135,9 +136,24 @@ function event_handler(event) { case 'cached': case 'recoding': log('[' + data['type'] + '] ' + data['path']); + // update directory browser var a = get_a(data['path']); if(a) a.setAttribute('class', 'file file-' + data['type']); + // update song queue + var li = playlist.get(data['path']); + if(li) { + a = li.getElementsByTagName('a')[0]; + if(data['type'] == 'cached') { + // play the current song if we were waiting for it + if(li == playlist.current) + a.onclick(); + else + a.setAttribute('class', ''); + } else { + a.setAttribute('class', 'file-recoding'); + } + } break; case 'play': log('[play] ' + data['path']); @@ -163,5 +179,7 @@ window.onload = function() { event_open(); audio = new Audio(); + playlist = new Playlist(document.getElementById('playlist'), audio); + audio.audio.addEventListener('ended', function() { playlist.next(); }); list('/'); } diff --git a/static/playlist.js b/static/playlist.js new file mode 100644 index 0000000..5e41de5 --- /dev/null +++ b/static/playlist.js @@ -0,0 +1,53 @@ +function Playlist(pl, audio) { + this.pl = pl; + this.audio = audio; + this.current = null; + + this.get = function(path) { + var li = this.current; + while(li) { + var a = li.getElementsByTagName('a')[0]; + if(a.ml.path == path) + return li; + li = li.nextElementSibling; + } + return null; + } + + this.add = function(ml) { + var a = document.createElement('a'); + a.setAttribute('href', '#'); + a.appendChild(document.createTextNode(ml.path)); + a.ml = ml; + var li = document.createElement('li'); + var pl = this; + a.onclick = function() { + while(li.previousElementSibling) + li.previousElementSibling.parentElement.removeChild(li.previousElementSibling); + a.setAttribute('class', 'playing'); + pl.current = li; + ml.play(); + return false; + } + log(a.click); + + li.appendChild(a); + this.pl.appendChild(li); + } + + this.next = function() { + log('next'); + log('this: ' + this); + log('current: ' + this.current); + if(this.current) { + var old = this.current; + log('old: ' + old); + this.current = this.current.nextElementSibling; + old.parentElement.removeChild(old); + } + if(this.current) { + var a = this.current.getElementsByTagName('a')[0]; + a.onclick(); + } + } +} diff --git a/static/style.css b/static/style.css index d086227..3ad648c 100644 --- a/static/style.css +++ b/static/style.css @@ -1,9 +1,13 @@ -ul#song-links { list-style-type: none; } -ul#song-links a { text-decoration: none; color: inherit; } -ul#song-links a:hover { text-decoration: underline; } +ul#song-links a, ul#playlist a { text-decoration: none; color: inherit; } +ul#song-links a:hover, ul#playlist a:hover { text-decoration: underline; } a.dir { background-image: url('/static/icons/folder.png'); } a.file { background-image: url('/static/icons/music.png'); } a.file-cached { background-image: url('/static/icons/music-cached.png'); } -a.dir, a.file { background-repeat: no-repeat; padding-left: 20px; } +a.dir, a.file, ul#playlist li a { background-repeat: no-repeat; padding-left: 20px; } a.file-recoding { background-image: url('/static/icons/loading.gif'); } a.file-queued { background-image: url('/static/icons/music-queued.png'); } +div#hpanel { margin-top: 1em; } +div#hpanel span { display: inline-block; vertical-align: top; } +div#hpanel span ul { list-style-type: none; padding-left: 0; margin-top: .5em; vertical-align: top; } +ul#playlist li a.playing { background-image: url('/static/icons/sound.png'); } +span.list-header { font-size: large; } -- cgit v1.2.3