Changeset 298
- Timestamp:
- 06/10/06 21:08:58 (3 years ago)
- Files:
-
- trunk/src/audio_control.py (modified) (4 diffs)
- trunk/src/mesk/audio_source.py (modified) (7 diffs)
- trunk/src/mesk/playlist.py (modified) (3 diffs)
- trunk/src/mesk/utils.py (modified) (1 diff)
- trunk/src/playlist_control.py (modified) (3 diffs)
- trunk/src/plugins/audioscrobbler.py (modified) (1 diff)
Legend:
- Unmodified
- Added
- Removed
- Modified
- Copied
- Moved
trunk/src/audio_control.py
r289 r298 94 94 gobject.signal_new('prev', AudioControl, gobject.SIGNAL_RUN_LAST, 95 95 gobject.TYPE_NONE, []) 96 # Callback takes: widget, old_index, new_index 97 gobject.signal_new("source-changed", AudioControl, 96 gobject.signal_new('source-changed', AudioControl, 98 97 gobject.SIGNAL_RUN_LAST, 99 98 gobject.TYPE_NONE, 100 99 [gobject.TYPE_PYOBJECT, gobject.TYPE_PYOBJECT]) 101 # Callback takes: widget, error_message, audio_source 102 gobject.signal_new("error", AudioControl, gobject.SIGNAL_RUN_LAST, 100 gobject.signal_new('error', AudioControl, gobject.SIGNAL_RUN_LAST, 103 101 gobject.TYPE_NONE, [gobject.TYPE_STRING, 104 102 gobject.TYPE_PYOBJECT]) 105 gobject.signal_new("playlist-reset", AudioControl, 103 # Callback takes: widget, audio_src 104 gobject.signal_new('tag-update', AudioControl, gobject.SIGNAL_RUN_LAST, 105 gobject.TYPE_NONE, [gobject.TYPE_PYOBJECT]) 106 gobject.signal_new('playlist-reset', AudioControl, 106 107 gobject.SIGNAL_RUN_LAST, gobject.TYPE_NONE, []) 107 108 … … 351 352 def _set_source(self, src): 352 353 self._set_track_scale(0.0) 353 354 if src.uri.scheme == 'file': 355 self._gst_bin.set_property('uri', src.uri.to_string()) 356 else: 357 raise RuntimeError("Unsupported URI scheme: " + src.uri.scheme) 354 self._gst_bin.set_property('uri', src.uri.to_string()) 358 355 self._current_audio_src = src 359 356 … … 428 425 {'next': True, 'start_playing': True}) 429 426 elif message.type == gst.MESSAGE_TAG: 430 # TODO: Read tags from streams 431 pass 427 if not self._current_audio_src.meta_data.frozen: 428 self._update_meta_data(self._current_audio_src, 429 message.parse_tag()) 432 430 elif message.type == gst.MESSAGE_ERROR: 433 431 self._gst_error_set = True … … 438 436 self.emit('error', error, self._current_audio_src) 439 437 438 def _update_meta_data(self, src, taglist): 439 '''Possible keys: 440 ['title', 'artist', 'album', 'date', 'track-count', 'track-number', 441 'genre', 'duration'] 442 ['layer', 'mode', 'emphasis', 'audio-codec', 'bitrate'] 443 ''' 444 changed = False 445 keys = taglist.keys() 446 if 'title' in keys: 447 src.meta_data.title = unicode(taglist['title'], 'utf-8') 448 if 'artist' in keys: 449 src.meta_data.artist = unicode(taglist['artist'], 'utf-8') 450 if 'album' in keys: 451 src.meta_data.album = unicode(taglist['album'], 'utf-8') 452 if 'date' in keys: 453 src.meta_data.year = unicode(str(taglist['date'].year), 'utf-8') 454 if 'track-number' in keys: 455 src.meta_data.track_num = taglist['track-number'] 456 if 'track-count' in keys: 457 src.meta_data.track_total = taglist['track-count'] 458 if 'duration' in keys: 459 src.audio_info.time_secs = taglist['duration'] / gst.SECOND 460 self.emit('tag-update', src) 440 461 441 462 ### Timer methods ### trunk/src/mesk/audio_source.py
r178 r298 42 42 year = None 43 43 track_num = track_total = None 44 frozen = False 44 45 45 46 def __init__(self, native_tag = None): … … 50 51 self.album = native_tag.getAlbum() or EMPTY_METADATA 51 52 self.year = native_tag.getYear() 52 (self.track_num, self.track_total) = native_tag.getTrackNum() or 053 (self.track_num, self.track_total) = native_tag.getTrackNum() 53 54 54 55 class AudioSource: … … 56 57 if not isinstance(uri, Uri): 57 58 self.uri = Uri(uri) 59 else: 60 self.uri = uri 58 61 self.meta_data = None 59 62 self.audio_info = AudioInfo() … … 67 70 self.audio_info.time_secs = audio_file.getPlayTime() 68 71 self.audio_info.size_bytes = audio_file.getSize() 69 70 72 self.meta_data = AudioMetaData(audio_file.tag) 71 73 except eyeD3.TagException, ex: … … 75 77 76 78 if not self.meta_data: 79 self.metadata = AudioMetaData() 77 80 mesk.log.warning(_('No metadata for file \'%s\'') % self.uri.path) 78 pass 81 else: 82 self.meta_data.frozen = True 79 83 80 # FIXME: Rename HttpAudioSource 81 class UrlAudioSource(AudioSource): 82 # TODO 83 def __init__(self, url): 84 AudioSource.__init__(self, url) 84 class HttpAudioSource(AudioSource): 85 def __init__(self, http_uri): 86 AudioSource.__init__(self, http_uri) 87 88 self.audio_info.time_secs = None 89 self.audio_info.size_bytes = None 90 self.meta_data = AudioMetaData() 91 # FIXME: Make use of extended m3u data if possible 92 self.meta_data.title = unicode(self.uri.to_string()) 85 93 86 94 class UnsupportedScheme(Exception): … … 96 104 if uri.scheme == 'file': 97 105 path = os.path.realpath(os.path.abspath(uri.path)) 98 ext = os.path.splitext(path) 99 if not ext or ext[1 ][1:] not in SUPPORTED_AUDIO:106 ext = os.path.splitext(path)[1] 107 if not ext or ext[1:] not in SUPPORTED_AUDIO: 100 108 mt = mimetypes.guess_type(path)[0] 101 109 if not mt: … … 107 115 mesk.log.error(_('Error loading source file %s') % path) 108 116 src = None 117 elif uri.scheme == 'http' or uri.scheme == 'https': 118 # FIXME: Pass any extended m3u info 119 src = HttpAudioSource(uri) 109 120 else: 110 121 raise UnsupportedScheme(_('Unsupported audio URI scheme: %s') % \ trunk/src/mesk/playlist.py
r285 r298 23 23 import audio_source 24 24 import utils 25 import log 25 26 import common.uri 26 27 … … 42 43 line = line.strip() 43 44 if line[0] == '#': 44 # TODO: meta data can be extracted here (e.g. stream info)45 # FIXME: meta data can be extracted here (e.g. stream info) 45 46 continue 46 src = audio_source.load(line) 47 if src: 48 pl.append(src) 47 try: 48 src = audio_source.load(line) 49 except Exception, ex: 50 log.warn(str(ex)) 51 else: 52 if src: 53 pl.append(src) 49 54 fp.close() 50 55 … … 52 57 fp = file(pl_file, 'w') 53 58 for src in pl: 54 fp.write(src.uri.path) 59 if src.uri.scheme == 'file': 60 fp.write(src.uri.path) 61 else: 62 fp.write(src.uri.to_string()) 55 63 fp.write('\n') 56 64 fp.close() trunk/src/mesk/utils.py
r286 r298 27 27 def format_track_time(curr, total = None): 28 28 def time_tuple(ts): 29 if ts is None or ts < 0: 30 ts = 0 29 31 hours = ts / 3600 30 32 mins = (ts % 3600) / 60 trunk/src/playlist_control.py
r273 r298 175 175 self._audio_control.connect('error', self._on_audio_error) 176 176 self._audio_control.connect('playlist-reset', self._on_playlist_reset) 177 self._audio_control.connect('tag-update', self._on_audio_tag_update) 177 178 178 179 self.widget.show() … … 195 196 self._save_playlist() 196 197 197 def _new_model_row(self, src): 198 filename = os.path.basename(src.uri.path) 199 filename = gtk_utils.escape_pango_markup(filename) 200 title = gtk_utils.escape_pango_markup(src.meta_data.title) 201 artist = gtk_utils.escape_pango_markup(src.meta_data.artist) 202 album = gtk_utils.escape_pango_markup(src.meta_data.album) 203 year = unicode(src.meta_data.year) 198 def _get_model_metadata(self, src): 199 row_data = {} 200 row_data[MODEL_TITLE] = \ 201 gtk_utils.escape_pango_markup(src.meta_data.title) 202 row_data[MODEL_ARTIST] = \ 203 gtk_utils.escape_pango_markup(src.meta_data.artist) 204 row_data[MODEL_ALBUM] = \ 205 gtk_utils.escape_pango_markup(src.meta_data.album) 206 207 if src.meta_data.year: 208 year = unicode(src.meta_data.year) 209 else: 210 year = u'' 211 row_data[MODEL_YEAR] = year 212 204 213 track_num = src.meta_data.track_num 205 214 if track_num is None: 206 215 track_num = 0 207 208 return [MODEL_STATE_ACTIVE, None, None, filename, 209 track_num, 210 title, 211 artist, 212 album, 213 mesk.utils.format_track_time(src.audio_info.time_secs), 214 year, 216 row_data[MODEL_NUM] = track_num 217 218 duration = mesk.utils.format_track_time(src.audio_info.time_secs) 219 row_data[MODEL_TIME] = duration 220 221 return row_data 222 223 def _new_model_row(self, src): 224 model_data = self._get_model_metadata(src) 225 return [MODEL_STATE_ACTIVE, None, None, src.uri.to_string(), 226 model_data[MODEL_NUM], 227 model_data[MODEL_TITLE], 228 model_data[MODEL_ARTIST], 229 model_data[MODEL_ALBUM], 230 model_data[MODEL_TIME], 231 model_data[MODEL_YEAR], 215 232 ] 216 233 … … 369 386 if src_index != len(self._playlist) - 1: 370 387 gobject.idle_add(self._audio_control.next, True) 388 389 def _on_audio_tag_update(self, audio_control, audio_src): 390 row = self._playlist.index(audio_src) 391 model_iter = self._pl_model.get_iter(row) 392 393 model_data = self._get_model_metadata(audio_src) 394 for key in model_data: 395 self._pl_model.set_value(model_iter, key, model_data[key]) 371 396 372 397 def _on_dialog_close(self, dialog, response): trunk/src/plugins/audioscrobbler.py
r257 r298 395 395 src_len = audio_src.audio_info.time_secs 396 396 if src_len < 30: 397 self.log.info(_('Source length %d < 30s, skipping') % src_len) 397 self.log.info(_('Source length %s < 30s, skipping') % \ 398 str(src_len)) 398 399 return 399 400 interval = min(src_len / 2, 240)
