--- /dev/null
+#!/usr/bin/python
+
+# ADD COMMAND TO RESTART PARTY MODE
+# (probably should require confirmation)
+# also add undelete link to post-del link just in case (reinsert at old pos)
+
+# Trivial xbmc admin script to view active playlist, control volume,
+# etc.
+
+# I would not recommend putting this online, no attempt is made at
+# being even trivially secure (e.g. form values are passed directly to
+# kodi with zero verification)
+
+# todo
+# any kind of error checking
+
+from __future__ import unicode_literals
+
+# Python is being obnoxious as hell and refusing to .format() utf-8
+# strings. I have no idea. Just hack around it and deal with the
+# actual problem later instead of scattering the code with .encode
+# calls.
+
+import sys
+reload(sys)
+sys.setdefaultencoding ('utf-8')
+
+import cgi, cgitb
+import os
+import subprocess
+import random
+from xbmcjson import XBMC
+
+cgitb.enable()
+
+print ("content-type: text/html; charset=utf-8\n\n")
+
+print (u'''
+<style>
+input, select, button { font-size: 200%}
+.horiz-menu li { display: inline }
+ body { /* background-image: url("fire-under-construction-animation.gif"); */
+color: white;
+background-color: black;
+}
+</style>
+
+<ul class="horiz-menu"">
+<li><a href="admin.cgi">reload</a></li>
+<li><a href="#playlist">playlist</a></li>
+<li><a href="#controls">control</a></li>
+<li><a href="javascript:document.getElementById("quicksearch").focus()">search</a></li>
+</ul>
+''')
+
+music_dir = "/srv/archive/incoming/stolen-moosic"
+form = cgi.FieldStorage ()
+
+xbmc = XBMC ("http://localhost:8080/jsonrpc")
+
+def show_quick_search (term="",thereal=False):
+ print (u'''
+<form method="get" action="admin.cgi" style="display: inline-block">
+<input type="text" name="searchterm" value="{}" {} />
+<select name="searchfield">
+<option value="title">name</option>
+<option value="albumartist">artist</option>
+<option value="album">album</option>
+</select>
+<button type="submit" name="searchgo" value="1">Search</button>
+</form>
+ ''').format(term, 'id="quicksearch"' if thereal else '')
+
+def show_search_results (songs):
+ print (u"<h1>Results</h1>")
+ print (u"<ol>")
+ for song in songs:
+ print (u'<li>{} ({}) {}'.format (song['albumartist'][0], song['album'], song['label']))
+ print ('<form method="post" action="admin.cgi" style="display: inline-block">')
+ print ('<button type="submit" name="randomqueue" value="{}">yeh</button>'.format(song['songid']))
+ print ('</form>')
+ print ('</li>')
+ print (u"</ol>")
+
+if 'songdel' in form:
+ songid = int(form['songdel'].value)
+ print (songid)
+ (pos,name) = next ((i,s) for i,s in enumerate(xbmc.Playlist.GetItems (playlistid=0)['result']['items']) if s['id'] == songid)
+ print (u"<p>Deleted {}</p>".format(name['label']))
+ print (xbmc.Playlist.Remove (playlistid=0, position=pos))
+elif 'songup' in form:
+ songid = int(form['songup'].value)
+ print (songid)
+ (pos,name) = next ((i,s) for i,s in enumerate(xbmc.Playlist.GetItems (playlistid=0)['result']['items']) if s['id'] == songid)
+ print (u"<p>Promoted {}</p>".format(name['label']))
+ print (xbmc.Playlist.Swap (playlistid=0, position1=pos, position2=pos-1))
+elif 'songdown' in form:
+ songid = int(form['songdown'].value)
+ print (songid)
+ (pos,name) = next ((i,s) for i,s in enumerate(xbmc.Playlist.GetItems (playlistid=0)['result']['items']) if s['id'] == songid)
+ print (u"<p>Demoted {}</p>".format(name['label']))
+ print (xbmc.Playlist.Swap (playlistid=0, position1=pos, position2=pos+1))
+elif 'volchange' in form:
+ curvolume = xbmc.Application.GetProperties (properties=['volume'])['result']['volume']
+ newvolume = max (0, min (int (form['volchange'].value) + curvolume, 100))
+ print (xbmc.Application.SetVolume (volume=newvolume))
+elif 'volmute' in form:
+ print (xbmc.Application.SetMute (mute="toggle"))
+elif 'navigate' in form:
+ action = form['navigate'].value
+ if action == 'prev':
+ print xbmc.Player.GoTo (to="previous", playerid=0)
+ elif action == 'next':
+ print xbmc.Player.GoTo (to="next", playerid=0)
+ elif action == 'playpause':
+ print xbmc.Player.PlayPause (play="toggle", playerid=0)
+elif 'searchgo' in form:
+ term = form['searchterm'].value
+ field = form['searchfield'].value
+ results = xbmc.AudioLibrary.GetSongs (filter={'operator': "contains", 'field': field, 'value': term}, properties=['album', 'albumartist'], sort={'order': 'ascending', 'method': 'artist'})['result']['songs']
+ show_quick_search (term)
+ show_search_results (results)
+elif 'randomqueue' in form:
+ songid = int(form['randomqueue'].value)
+ totalitems = xbmc.Playlist.GetItems (playlistid=0)['result']['limits']['total']
+ playpos = random.randint (1, totalitems / 3 + 1)
+ print xbmc.Playlist.Insert (playlistid=0, item={"songid": songid}, position=playpos)
+ print '<p style="font-size: x-large">Your song is number {0} in the queue ({1} songs in playlist).</p>'.format (playpos, totalitems+1)
+
+
+
+
+
+playlist = xbmc.Playlist.GetItems (playlistid=0, properties=['album', 'albumartist'])['result']['items']
+#playpos = random.randint (1, totalitems / (1 if 'asap' not in form else 3))
+
+print ('<a name="controls"></a>')
+print ('<p>Volume: {}%</p>'.format(xbmc.Application.GetProperties (properties=['volume'])['result']['volume']))
+print ('''
+<form method="post" action="admin.cgi" style="display: inline-block">
+<button name="volchange" value="5" type="submit">+5</button>
+<button name="volchange" value="-5" type="submit">-5</button>
+
+<button name="volchange" value="10" type="submit">+10</button>
+<button name="volchange" value="-10" type="submit">-10</button>
+
+<button name="volmute" value="1">Toggle Mute</button>
+
+</form>
+''')
+
+print ('''
+<form method="post" action="admin.cgi" style="display: inline-block">
+<button name="navigate" value="prev" type="submit">⏮</button>
+<button name="navigate" value="next" type="submit">⏭</button>
+<button name="navigate" value="playpause" type="submit">⏯</button>
+</form>
+''')
+
+
+print ('<a name="playlist"></a><h1>Playlist</h1>')
+print ("<ol>")
+for song in playlist:
+ print (u'<li>{} {}'.format(song['albumartist'][0], song['label']).encode('UTF-8'))
+
+ print ('<form method="post" action="admin.cgi" style="display: inline-block">')
+ print ('<button name="songdel" value="{}">del</button>'.format(song['id']))
+ print ('<button name="songup" value="{}">up</button>'.format(song['id']))
+ print ('<button name="songdown" value="{}">down</button>'.format(song['id']))
+ print ('</form>' )
+ print ("</li>")
+print ("</ol>")
+
+print ('<a name="search"></a>')
+show_quick_search (thereal=True)