This site has been retired. For up to date information, see handbook.gnome.org or gitlab.gnome.org.


[Home] [TitleIndex] [WordIndex

Some example bits of code on how to various things for Python Plugins.

These have all been updated for Rhythmbox 2.99, so they mostly won't work with older versions.

Adding a context menu to a source

How to add a context menu to a given browser source: define do_impl_show_entry_popup in the source.

class DuplicateSource(RB.BrowserSource):

        def __init__(self):
                RB.BrowserSource.__init__(self, name=_("Duplicates"))

                app = Gio.Application.get_default()
                action = Gio.SimpleAction(name="duplicate-mark-non-duplicate")
                action.connect("activate", self.mark_non_duplicate)
                app.add_action(action)

                # you can also do this bit with GtkBuilder xml if you like
                self.__popup = Gio.Menu()
                section = Gio.Menu()
                section.append("Mark Non-duplicate", "app.duplicate-mark-non-duplicate")
                self.__popup.append_section(None, section)

                section = Gio.Menu()
                section.append("Move to Trash", "app.clipboard-move-to-trash")
                section.append("Remove", "app.clipboard-delete")
                self.__popup.append_section(None, section)

                section = Gio.Menu()
                section.append("Properties", "app.clipboard-properties")
                self.__popup.append_section(None, section)

        def do_impl_show_entry_popup(self):
                menu = Gtk.Menu.new_from_model(self.__popup)
                menu.attach_to_widget(self, None)
                menu.popup(None, None, None, None, 3, Gtk.get_current_event_time())

GObject.type_register(DuplicateSource)

User Interface

1. Add Menu Items

Plugins can add items to menus and toolbars in specific locations by calling RBApplication.add_plugin_menu_item(menu_name, item_id, item) where item_id uniquely identifies the item being added and item is a Gio.MenuItem instance. menu_name here is the name of a plugin menu location. Some plugin menu locations:

You can find plugin menu locations by searching for 'rb-plugin-menu-link' in the GtkBuilder UI files defining menus and toolbars.

An example:

        def do_activate(self):

                app = Gio.Application.get_default()

                # create action
                action = Gio.SimpleAction(name="smart-playlist-create")
                action.connect("activate", self.generate_playlist)
                app.add_action(action)

                # add plugin menu item (note the "app." prefix here)
                item = Gio.MenuItem(label=("Create Smart Playlist"), detailed_action="app.smart-playlist-create")                
                app.add_plugin_menu_item('browser-popup', 'create-smart-playlist', item)      

        def do_deactivate(self):

                Gio.Application.get_default().remove_plugin_menu_item('browser-popup', 'create-smart-playlist')

Exploring the music library

1. How do I get a list of the user's playlists?

Playlists are stored in the display page model, the Gtk.TreeModel in the left hand pane. Get a reference to the display page model with (shell.props.display_page_model.props.model. The "Playlists" header item is therefore playlist_mode_header = [x for x in list(shell.props.display_page_model.props.model) if list(x)[2] == "Playlists"][0], and you can get a list of playlist TreeModelRows with playlist_model_header.iterchildren(), so

playlist_model_entries = [x for x in 
   list(shell.props.display_page_model.props.model)
   if list(x)[2] == "Playlists"]
if playlist_model_entries:
    playlist_iter = playlist_model_entries[0].iterchildren()
    for playlist_item in playlist_iter:
        print "Playlist image: %s, name: %s, source: %s" % (playlist_item[1], playlist_item[2], playlist_item[3])

2. How do I get a list of the user's podcast feeds?

You can interrogate the rhythmdb object to find out a number of things to do with the users library. The following example will print out the users podcast feed:

db = shell.get_property("db")

def print_podcast_info(entry):
    """Takes a podcast entry and prints out its info"""
    name = entry.get_string(RB.RhythmDBPropType.ARTIST)
    uri = entry.get_string(RB.RhythmDBPropType.LOCATION)
    print "%s: %s" % (name, uri)

db.entry_foreach_by_type(db.entry_type_get_by_name("podcast-feed"), print_podcast_info)

3. How do I create a new "Page Group"?

First, we need to create a new "page group" type and register it with RB.

page_group = RB.DisplayPageGroup(shell=shell, id='lastfm-playlist', name="Last.Fm Playlist", category=RB.DisplayPageGroupCategory.TRANSIENT)
shell.append_display_page(page_group, None)

Next, we can add a "source" to this new group.

## Dummy Source Class
class lfmbs(RB.BrowserSource):
  def __init__(self):
    RB.BrowserSource.__init__(self)

GObject.type_register(lfmbs)

## Insert the a new "source"
s1=GObject.new(lfmbs, shell=shell, entry_type=shell.db.entry_register_type("lfm"))
shell.append_display_page(s1, page_group)

4. How do I jump to the playing song?

# get the library's Source
src = shell.props.library_source
# get the gtk widget that views the contents of that source
lst = src.get_entry_view()
# jump to a particular entry
lst.scroll_to_entry(entry)

5. How do I get the list of songs in a source?

A source's songs are stored in source.props.base_query_model, a Gtk.TreeModel. Each item in that model is a Gtk.TreeModelRow with two columns, a RhythmDBEntry and a path. So, to print all songs in a source:

for treerow in source.props.base_query_model:
  entry, path = list(treerow)
  print entry

6. How do I switch to a source?

If you've got a source, and want to switch Rhythmbox over to playing it:

player = shell.player.get_player()
player.stop()
shell.props.display_page_tree.select(your_source)
# start playing from the beginning
player.play()
# or, if you've got a specific RhythmDBEntry that you want to play
player.play_entry(entry)

7. How do I get the metadata details of a song?

If you have a RhythmDBEntry for a song, then you can get the metadata by querying the database with special properties. Access to the database is from shell.props.db. So, expanding the above example:

for treerow in source.props.base_query_model:
  entry, path = list(treerow)
  artist = entry.get_string(RB.RhythmDBPropType.ARTIST)
  album = entry.get_string(RB.RhythmDBPropType.ALBUM)
  title = entry.get_string(RB.RhythmDBPropType.TITLE)
  duration = entry.get_ulong(RB.RhythmDBPropType.DURATION)
  print "%s - %s" % (title, artist)

There are lots and lots of defined properties: dir(RB.RhythmDBPropType) in the python console will list them all.


2024-10-23 10:58