def _people(self, songs, box): tags_ = PEOPLE people = defaultdict(set) for song in songs: for t in tags_: if t in song: people[t] |= set(song.list(t)) data = [] # Preserve order of people for tag_ in tags_: values = people.get(tag_) if values: name = readable(tag_, plural=len(values) > 1) data.append((name, "\n".join(values))) table = Table(len(data)) for i, (key, text) in enumerate(data): key = util.capitalize(util.escape(key) + ":") table.attach(Label(markup=key), 0, 1, i, i + 1, xoptions=Gtk.AttachOptions.FILL) label = Label(text, ellipsize=True) table.attach(label, 1, 2, i, i + 1) box.pack_start(Frame(tag("~people"), table), False, False, 0)
def _additional(self, song, box): if "website" not in song and "comment" not in song: return data = [] if "comment" in song: comments = song.list("comment") markups = ["<i>%s</i>" % c for c in comments] data.append(("comment", markups)) if "website" in song: markups = [ "<a href=\"%(url)s\">%(text)s</a>" % { "text": util.escape(website), "url": util.escape(website) } for website in song.list("website") ] data.append(("website", markups)) table = Table(1) for i, (key, markups) in enumerate(data): title = readable(key, plural=len(markups) > 1) lab = Label(markup=util.capitalize(util.escape(title) + ":")) table.attach(lab, 0, 1, i, i + 1, xoptions=Gtk.AttachOptions.FILL) lab = Label(markup="\n".join(markups), ellipsize=True) table.attach(lab, 1, 2, i, i + 1) box.pack_start(Frame(_("Additional"), table), False, False, 0)
def _additional(self, song, box): if "website" not in song and "comment" not in song: return data = [] if "comment" in song: comments = song.list("comment") markups = ["<i>%s</i>" % c for c in comments] data.append(("comment", markups)) if "website" in song: markups = ["<a href=\"%(url)s\">%(text)s</a>" % {"text": util.escape(website), "url": util.escape(website)} for website in song.list("website")] data.append(("website", markups)) table = Table(1) for i, (key, markups) in enumerate(data): title = readable(key, plural=len(markups) > 1) lab = Label(markup=util.capitalize(util.escape(title) + ":")) table.attach(lab, 0, 1, i, i + 1, xoptions=Gtk.AttachOptions.FILL) lab = Label(markup="\n".join(markups), ellipsize=True) table.attach(lab, 1, 2, i, i + 1) box.pack_start(Frame(_("Additional"), table), False, False, 0)
def _people(self, song, box): vb = Gtk.VBox() if "artist" in song: if len(song.list("artist")) == 1: title = _("artist") else: title = _("artists") title = util.capitalize(title) l = Label(song["artist"]) l.set_ellipsize(Pango.EllipsizeMode.END) vb.pack_start(l, False, True, 0) else: title = tag("~people") for tag_ in [ "performer", "lyricist", "arranger", "composer", "conductor", "author" ]: if tag_ in song: l = Label(song[tag_]) l.set_ellipsize(Pango.EllipsizeMode.END) if len(song.list(tag_)) == 1: name = tag(tag_) else: name = readable(tag_, plural=True) vb.pack_start(Frame(util.capitalize(name), l), False, False, 0) performers = {} for tag_ in song: if "performer:" in tag_: for person in song[tag_].split('\n'): try: performers[str(person)] except: performers[str(person)] = [] performers[str(person)].append( util.title(tag_[tag_.find(":") + 1:])) if len(performers) > 0: performerstr = '' for performer in performers: performerstr += performer + ' (' i = 0 for part in performers[performer]: if i != 0: performerstr += ', ' performerstr += part i += 1 performerstr += ')\n' l = Label(performerstr) l.set_ellipsize(Pango.EllipsizeMode.END) if len(performers) == 1: name = tag("performer") else: name = _("performers") vb.pack_start(Frame(util.capitalize(name), l), False, False, 0) if not vb.get_children(): vb.destroy() else: box.pack_start(Frame(title, vb), False, False, 0)
def _people(self, song, box): vb = Gtk.VBox() if "artist" in song: if len(song.list("artist")) == 1: title = _("artist") else: title = _("artists") title = util.capitalize(title) l = Label(song["artist"]) l.set_ellipsize(Pango.EllipsizeMode.END) vb.pack_start(l, False, True, 0) else: title = tag("~people") for tag_ in ["performer", "lyricist", "arranger", "composer", "conductor", "author"]: if tag_ in song: l = Label(song[tag_]) l.set_ellipsize(Pango.EllipsizeMode.END) if len(song.list(tag_)) == 1: name = tag(tag_) else: name = readable(tag_, plural=True) vb.pack_start(Frame(util.capitalize(name), l), False, False, 0) performers = {} for tag_ in song: if "performer:" in tag_: for person in song[tag_].split('\n'): try: performers[str(person)] except: performers[str(person)] = [] performers[str(person)].append( util.title(tag_[tag_.find(":") + 1:])) if len(performers) > 0: performerstr = '' for performer in performers: performerstr += performer + ' (' i = 0 for part in performers[performer]: if i != 0: performerstr += ', ' performerstr += part i += 1 performerstr += ')\n' l = Label(performerstr) l.set_ellipsize(Pango.EllipsizeMode.END) if len(performers) == 1: name = tag("performer") else: name = _("performers") vb.pack_start(Frame(util.capitalize(name), l), False, False, 0) if not vb.get_children(): vb.destroy() else: box.pack_start(Frame(title, vb), False, False, 0)
def test_readable(self): self.assertEqual(readable("artistsort"), "artist (sort)") self.assertEqual(readable("~people:roles"), "people (roles)") self.assertEqual(readable("~peoplesort:roles"), "people (sort, roles)") self.assertEqual(readable("artist", plural=True), "artists") self.assertEqual(readable("artistsort", plural=True), "artists (sort)") self.assertEqual(readable("~"), "Invalid tag")
def _people(self, song, box): data = [] if "artist" in song: title = (_("artist") if len(song.list("artist")) == 1 else _("artists")) title = util.capitalize(title) data.append((title, song["artist"])) for tag_ in [ "performer", "lyricist", "arranger", "composer", "conductor", "author" ]: if tag_ in song: name = (tag(tag_) if len(song.list(tag_)) == 1 else readable( tag_, plural=True)) data.append((name, song[tag_])) performers = defaultdict(list) for tag_ in song: if "performer:" in tag_: for person in song.list(tag_): role = util.title(tag_.split(':', 1)[1]) performers[role].append(person) if performers: text = '\n'.join("%s (%s)" % (', '.join(names), part) for part, names in performers.iteritems()) name = (tag("performer") if len(performers) == 1 else _("performers")) data.append((name, text)) table = Table(len(data)) for i, (key, text) in enumerate(data): key = util.capitalize(util.escape(key) + ":") table.attach(Label(markup=key), 0, 1, i, i + 1, xoptions=Gtk.AttachOptions.FILL) label = Label(text, ellipsize=True) table.attach(label, 1, 2, i, i + 1) box.pack_start(Frame(tag("~people"), table), False, False, 0)
def _people(self, song, box): data = [] if "artist" in song: title = (_("artist") if len(song.list("artist")) == 1 else _("artists")) title = util.capitalize(title) data.append((title, song["artist"])) for tag_ in ["performer", "lyricist", "arranger", "composer", "conductor", "author"]: if tag_ in song: name = (tag(tag_) if len(song.list(tag_)) == 1 else readable(tag_, plural=True)) data.append((name, song[tag_])) performers = defaultdict(list) for tag_ in song: if "performer:" in tag_: for person in song.list(tag_): role = util.title(tag_.split(':', 1)[1]) performers[role].append(person) if performers: text = '\n'.join("%s (%s)" % (', '.join(names), part) for part, names in performers.iteritems()) name = (tag("performer") if len(performers) == 1 else _("performers")) data.append((name, text)) table = Table(len(data)) for i, (key, text) in enumerate(data): key = util.capitalize(util.escape(key) + ":") table.attach(Label(markup=key), 0, 1, i, i + 1, xoptions=Gtk.AttachOptions.FILL) label = Label(text, ellipsize=True) table.attach(label, 1, 2, i, i + 1) box.pack_start(Frame(tag("~people"), table), False, False, 0)
def plugin_songs(self, songs): global songinfo # Create a dialog. dlg = Dialog(title=_("Migrate Metadata"), transient_for=self.plugin_window, flags=(Gtk.DialogFlags.MODAL | Gtk.DialogFlags.DESTROY_WITH_PARENT)) dlg.set_border_width(4) dlg.vbox.set_spacing(4) dlg.add_icon_button(_("_Copy"), Icons.EDIT_COPY, Gtk.ResponseType.OK) dlg.add_icon_button( _("_Paste"), Icons.EDIT_PASTE, Gtk.ResponseType.APPLY) # Default to the "Copy" button when the songsinfo # list is empty, default to "Paste" button otherwise. if len(songinfo) == 0: dlg.set_default_response(Gtk.ResponseType.OK) else: dlg.set_default_response(Gtk.ResponseType.APPLY) # Create the tag table. frame = Gtk.Frame(label=_("Information to copy/paste")) # Try to make a nice even square-ish table. bias = 3 # Columns count for 3 rows, due to label text using space. columns = int(max(1, math.ceil(math.sqrt(len(MIGRATE) / bias)))) rows = int(max(1, math.ceil(len(MIGRATE) / columns))) table = Gtk.Table(rows=rows, columns=columns, homogeneous=True) table.set_border_width(4) table.set_row_spacings(4) table.set_col_spacings(4) # Create check boxes. tags = {} for ctr, tag in enumerate(sorted(MIGRATE)): tags[tag] = Gtk.CheckButton(label=readable(tag).capitalize()) tags[tag].set_active(True) # These floors and casts make sure we don't get floats. col = int(math.floor(ctr % columns)) row = int(math.floor(ctr / columns)) table.attach(tags[tag], col, col + 1, row, row + 1) # Create the indexing box. index = Gtk.CheckButton(label=_("Map tracks by disc and track number")) index.set_tooltip_markup(_("Enable this when you want to migrate " "metadata from one album to another while " "matching the disc and track numbers." "\n\n" "<b>Note:</b> this must be enabled when " "metadata is copied for track information " "to be stored.")) # Automatically check when there is more # than one song in the songs or songinfo lists. if len(songs) > 1 or len(songinfo) > 1: index.set_active(True) # Assemble the window. frame.add(table) dlg.vbox.add(frame) dlg.vbox.add(index) dlg.vbox.add(Gtk.Label(ngettext("There is %d stored track.", "There are %d stored tracks.", len(songinfo)) % len(songinfo))) dlg.show_all() response = dlg.run() # Only accept expected responses. if response not in [Gtk.ResponseType.OK, Gtk.ResponseType.APPLY]: dlg.destroy() return # If copying, erase the currently stored metadata. if response == Gtk.ResponseType.OK: songinfo = {} # Go through the songs list and process it. for tid, song in enumerate(songs): # This tid will be what we index all of our tracks by, # so they will be easier to find when pasting metadata. if index.get_active() is True: tid = "%d-%d" % (self.get_number(song, 'discnumber'), self.get_number(song, 'tracknumber')) # Erase track info if copying. if response == Gtk.ResponseType.OK: songinfo[tid] = {} for tag in tags.keys(): if tags[tag].get_active() is False: continue # Skip unchecked tags. try: if response == Gtk.ResponseType.OK: # Copy information. songinfo[tid][tag] = song[tag] elif response == Gtk.ResponseType.APPLY: # Paste information. song[tag] = songinfo[tid][tag] except KeyError: continue # Just leave out tags that aren't present. # Erase songinfo after pasting. if response == Gtk.ResponseType.APPLY: songinfo = {} # Aaaaaand we're done. dlg.destroy() return