Merge pull request #237 from rscholer/cmus-improved

Cmus improved
This commit is contained in:
enkore 2015-08-19 20:04:24 +02:00
commit f0d7e398b4

View File

@ -1,21 +1,17 @@
import os import os
from i3pystatus import IntervalModule, formatp from i3pystatus import formatp
from i3pystatus import IntervalModule
from i3pystatus.core.command import run_through_shell
from i3pystatus.core.util import TimeWrapper from i3pystatus.core.util import TimeWrapper
import subprocess
def _extract_artist_title(input): def _extract_artist_title(input):
for sep in ('-', ' - '): artist, title = (input.split('-') + [''])[:2]
split = input.split(sep) return artist.strip(), title.strip()
if len(split) == 2:
return split[0], split[1]
# fallback
return (input.split('-') + [''] * 2)[:2]
class Cmus(IntervalModule): class Cmus(IntervalModule):
""" """
Gets the status and current song info using cmus-remote Gets the status and current song info using cmus-remote
@ -34,84 +30,79 @@ class Cmus(IntervalModule):
""" """
settings = ( settings = (
('format', 'format string, available formatters: status, song_elapsed, ' ('format', 'formatp string'),
'song_length, artist, title, album, tracknumber, file, ' ('format_not_running', 'Text to show if cmus is not running'),
'stream, bitrate'), ('color', 'The color of the text'),
'color', ('color_not_running', 'The color of the text, when cmus is not running'),
('status', 'Dictionary mapping status to output'),
) )
color = "#909090"
format = "{status} {song_elapsed}/{song_length} {artist} - {title}" color = '#ffffff'
status_text = '' color_not_running = '#ffffff'
format = '{status} {song_elapsed}/{song_length} {artist} - {title}'
format_not_running = 'Not running'
interval = 1 interval = 1
status = { status = {
"paused": "", 'paused': '',
"playing": "", 'playing': '',
"stopped": "", 'stopped': '',
} }
on_leftclick = "playpause" on_leftclick = 'playpause'
on_rightclick = "next_song" on_rightclick = 'next_song'
on_upscroll = "next_song" on_upscroll = 'next_song'
on_downscroll = "previous_song" on_downscroll = 'previous_song'
def _cmus_command(self, command): def _cmus_command(self, command):
p = subprocess.Popen('cmus-remote --{command}'.format(command=command), shell=True, cmdline = 'cmus-remote --{command}'.format(command=command)
stdout=subprocess.PIPE, return run_through_shell(cmdline, enable_shell=True)
stderr=subprocess.STDOUT)
return p.communicate()
def _query_cmus(self): def _query_cmus(self):
status_dict = {} response = {}
status, error = self._cmus_command('query') cmd = self._cmus_command('query')
if status != b'cmus-remote: cmus is not running\n':
status = status.decode('utf-8').split('\n') if not cmd.rc:
for item in status: for line in cmd.out.splitlines():
split_item = item.split(' ') category, _, category_value = line.partition(' ')
if split_item[0] in ['tag', 'set']: if category in ('set', 'tag'):
key = '_'.join(split_item[:2]) key, _, value = category_value.partition(' ')
val = ' '.join([x for x in split_item[2:]]) key = '_'.join((category, key))
status_dict[key] = val response[key] = value
else: else:
status_dict[split_item[0]] = ' '.join(split_item[1:]) response[category] = category_value
return status_dict
return response
def run(self): def run(self):
status = self._query_cmus() self.output = {}
if not status: response = self._query_cmus()
self.output = {
"full_text": 'Not running', if response:
"color": self.color fdict = {
'file': response.get('file', ''),
'status': self.status[response['status']],
'title': response.get('tag_title', ''),
'stream': response.get('stream', ''),
'album': response.get('tag_album', ''),
'artist': response.get('tag_artist', ''),
'tracknumber': response.get('tag_tracknumber', 0),
'song_length': TimeWrapper(response.get('duration', 0)),
'song_elapsed': TimeWrapper(response.get('position', 0)),
'bitrate': int(response.get('bitrate', 0)),
} }
return
fdict = {
'file': status.get('file', ''),
'status': self.status[status["status"]],
'title': status.get('tag_title', ''),
'stream': status.get('stream', ''),
'album': status.get('tag_album', ''),
'artist': status.get('tag_artist', ''),
'tracknumber': status.get('tag_tracknumber', 0),
'song_length': TimeWrapper(status.get('duration', 0)),
'song_elapsed': TimeWrapper(status.get('position', 0)),
'bitrate': int(status.get("bitrate", 0)),
}
if fdict['stream']: if fdict['stream']:
fdict['artist'], fdict[ fdict['artist'], fdict['title'] = _extract_artist_title(fdict['stream'])
'title'] = _extract_artist_title(fdict['stream']) elif not fdict['title']:
filename = os.path.basename(fdict['file'])
filebase, _ = os.path.splitext(filename)
fdict['artist'], fdict['title'] = _extract_artist_title(filebase)
elif not fdict['title']: self.output['full_text'] = formatp(self.format, **fdict)
_, filename = os.path.split(fdict['file']) self.output['color'] = self.color
filebase, _ = os.path.splitext(filename) else:
fdict['artist'], fdict['title'] = _extract_artist_title(filebase) self.output['full_text'] = self.format_not_running
self.output['color'] = self.color_not_running
fdict['title'] = fdict['title'].strip()
fdict['artist'] = fdict['artist'].strip()
self.output = {
"full_text": formatp(self.format, **fdict),
"color": self.color
}
def playpause(self): def playpause(self):
status = self._query_cmus().get('status', '') status = self._query_cmus().get('status', '')
@ -123,7 +114,7 @@ class Cmus(IntervalModule):
self._cmus_command('play') self._cmus_command('play')
def next_song(self): def next_song(self):
self._cmus_command("next") self._cmus_command('next')
def previous_song(self): def previous_song(self):
self._cmus_command("prev") self._cmus_command('prev')