{"type":"rich","version":"1.0","provider_name":"phorkie","provider_url":"https:\/\/p.cweiske.de\/","title":"rhythmbox lyrics WIP","author_name":"Anonymous","cache_age":86400,"width":900,"height":900,"html":"<!-- embedding all files of https:\/\/p.cweiske.de\/456 -->\n<link rel=\"stylesheet\" href=\"https:\/\/p.cweiske.de\/css\/embed.css\"\/>\n<div class=\"phork\" id=\"456\">\n    <div class=\"phork-file\">\n <div class=\"phork-content\">\n  <style type=\"text\/css\">\/**\n * GeSHi (C) 2004 - 2007 Nigel McNie, 2007 - 2014 Benny Baumann\n * (http:\/\/qbnz.com\/highlighter\/ and http:\/\/geshi.org\/)\n *\/\n.diff .de1, .diff .de2 {font: normal normal 1em\/1.2em monospace; margin:0; padding:0; background:none; vertical-align:top;}\n.diff  {font-family:monospace;}\n.diff .imp {font-weight: bold; color: red;}\n.diff li, .diff .li1 {color: #DDD;}\n.diff .ln {width:1px;text-align:right;margin:0;padding:0 2px;vertical-align:top;}\n.diff .kw1 {color: #aaaaaa; font-style: italic;}\n.diff .re0 {color: #440088;}\n.diff .re1 {color: #991111;}\n.diff .re2 {color: #00b000;}\n.diff .re3 {color: #888822;}\n.diff .re4 {color: #888822;}\n.diff .re5 {color: #0011dd;}\n.diff .re6 {color: #440088;}\n.diff .re7 {color: #991111;}\n.diff .re8 {color: #00b000;}\n.diff .re9 {color: #888822;}\n.diff span.xtra { display:block; }\n<\/style><div class=\"code\"><table class=\"diff\"><tbody><tr class=\"li1\"><td class=\"ln\"><pre class=\"de1\">1\n2\n3\n4\n5\n6\n7\n8\n9\n10\n11\n12\n13\n14\n15\n16\n17\n18\n19\n20\n21\n22\n23\n24\n25\n26\n27\n28\n29\n30\n31\n32\n33\n34\n35\n36\n37\n38\n39\n40\n41\n42\n43\n44\n45\n46\n47\n48\n49\n50\n51\n52\n53\n54\n55\n56\n57\n58\n59\n60\n61\n62\n63\n64\n65\n66\n67\n68\n69\n70\n71\n72\n73\n74\n75\n76\n77\n78\n79\n80\n81\n82\n83\n84\n85\n86\n87\n88\n89\n90\n91\n92\n93\n94\n95\n96\n97\n98\n99\n100\n101\n102\n103\n104\n105\n106\n107\n108\n109\n110\n111\n112\n113\n114\n115\n116\n117\n118\n119\n120\n121\n122\n123\n124\n125\n126\n127\n128\n129\n130\n131\n132\n133\n134\n135\n136\n<\/pre><\/td><td class=\"de1\"><pre class=\"de1\">diff --git a\/plugins\/lyrics\/lyrics.py b\/plugins\/lyrics\/lyrics.py\nindex 13124b3..c0f8de1 <span class=\"nu0\">100644<\/span>\n<span class=\"re3\">--- a\/plugins\/lyrics\/lyrics.py<\/span>\n<span class=\"re4\">+++ b\/plugins\/lyrics\/lyrics.py<\/span>\n<span class=\"re6\">@@ -32,6 +32,7 @@ import urllib.request<\/span>\n&#160;import rb\n&#160;from gi.repository import Gtk, Gio, GObject, Peas\n&#160;from gi.repository import RB\n<span class=\"re8\">+from gi.repository import Gst, GstPbutils<\/span>\n&#160;\n&#160;import LyricsParse\n&#160;from LyricsConfigureDialog import LyricsConfigureDialog\n<span class=\"re6\">@@ -132,22 +133,33 @@ def build_cache_path<span class=\"br0\">&#40;<\/span>artist, title<span class=\"br0\">&#41;<\/span>:<\/span>\n&#160; &#160; &#160; &#160; return os.path.join<span class=\"br0\">&#40;<\/span>artist_folder, title<span class=\"br0\">&#91;<\/span>:<span class=\"nu0\">128<\/span><span class=\"br0\">&#93;<\/span> + '.lyric'<span class=\"br0\">&#41;<\/span>\n&#160;\n&#160;class LyricGrabber<span class=\"br0\">&#40;<\/span>object<span class=\"br0\">&#41;<\/span>:\n<span class=\"re8\">+ &#160; &#160; &#160; &quot;&quot;&quot;<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; Fetch lyrics from several sources.<\/span>\n<span class=\"re8\">+<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; 1. Local cache file<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; 2. Lyric tags in file meta data<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; 3. Online services<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &quot;&quot;&quot;<\/span>\n&#160; &#160; &#160; &#160; def __init__<span class=\"br0\">&#40;<\/span>self, db, entry<span class=\"br0\">&#41;<\/span>:\n&#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; self.db = db\n&#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; self.entry = entry\n<span class=\"re7\">- &#160; &#160; &#160; &#160; &#160; &#160; &#160; <\/span>\n<span class=\"re8\">+<\/span>\n&#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; <span class=\"br0\">&#40;<\/span>self.artist, self.title<span class=\"br0\">&#41;<\/span> = parse_song_data<span class=\"br0\">&#40;<\/span>self.db, self.entry<span class=\"br0\">&#41;<\/span>\n&#160;\n&#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; self.cache_path = build_cache_path<span class=\"br0\">&#40;<\/span>self.artist, self.title<span class=\"br0\">&#41;<\/span>\n&#160;\n&#160; &#160; &#160; &#160; def verify_lyric<span class=\"br0\">&#40;<\/span>self<span class=\"br0\">&#41;<\/span>:\n&#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; return os.path.exists<span class=\"br0\">&#40;<\/span>self.cache_path<span class=\"br0\">&#41;<\/span>\n<span class=\"re7\">- &#160; &#160; &#160; &#160; <\/span>\n<span class=\"re8\">+<\/span>\n&#160; &#160; &#160; &#160; def search_lyrics<span class=\"br0\">&#40;<\/span>self, callback, cache_only=False<span class=\"br0\">&#41;<\/span>:\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; &quot;&quot;&quot;<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; Fetch lyrics from cache.<\/span>\n<span class=\"re8\">+<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; If no cache file exist, tag extraction is tried next.<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; &quot;&quot;&quot;<\/span>\n&#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; self.callback = callback\n<span class=\"re7\">- &#160; &#160; &#160; &#160; &#160; &#160; &#160; <\/span>\n<span class=\"re8\">+<\/span>\n&#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; status = self.verify_lyric<span class=\"br0\">&#40;<\/span><span class=\"br0\">&#41;<\/span>\n<span class=\"re7\">- &#160; &#160; &#160; &#160; &#160; &#160; &#160; <\/span>\n&#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; if status:\n&#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; f = open<span class=\"br0\">&#40;<\/span>self.cache_path, 'rt'<span class=\"br0\">&#41;<\/span>\n&#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; text = f.read<span class=\"br0\">&#40;<\/span><span class=\"br0\">&#41;<\/span>\n<span class=\"re6\">@@ -155,20 +167,73 @@ class LyricGrabber<span class=\"br0\">&#40;<\/span>object<span class=\"br0\">&#41;<\/span>:<\/span>\n&#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; self.callback<span class=\"br0\">&#40;<\/span>text<span class=\"br0\">&#41;<\/span>\n&#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; elif cache_only:\n&#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; self.callback<span class=\"br0\">&#40;<\/span>_<span class=\"br0\">&#40;<\/span>&quot;No lyrics found&quot;<span class=\"br0\">&#41;<\/span><span class=\"br0\">&#41;<\/span>\n<span class=\"re7\">- &#160; &#160; &#160; &#160; &#160; &#160; &#160; elif self.artist == &quot;&quot; and self.title == &quot;&quot;:<\/span>\n<span class=\"re7\">- &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; self.callback<span class=\"br0\">&#40;<\/span>_<span class=\"br0\">&#40;<\/span>&quot;No lyrics found&quot;<span class=\"br0\">&#41;<\/span><span class=\"br0\">&#41;<\/span><\/span>\n&#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; else:\n<span class=\"re7\">- &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; def lyric_callback <span class=\"br0\">&#40;<\/span>text<span class=\"br0\">&#41;<\/span>:<\/span>\n<span class=\"re7\">- &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; if text is not None:<\/span>\n<span class=\"re7\">- &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; f = open<span class=\"br0\">&#40;<\/span>self.cache_path, 'wt'<span class=\"br0\">&#41;<\/span><\/span>\n<span class=\"re7\">- &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; f.write <span class=\"br0\">&#40;<\/span>text<span class=\"br0\">&#41;<\/span><\/span>\n<span class=\"re7\">- &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; f.close <span class=\"br0\">&#40;<\/span><span class=\"br0\">&#41;<\/span><\/span>\n<span class=\"re7\">- &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; self.callback<span class=\"br0\">&#40;<\/span>text<span class=\"br0\">&#41;<\/span><\/span>\n<span class=\"re7\">- &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; else:<\/span>\n<span class=\"re7\">- &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; self.callback<span class=\"br0\">&#40;<\/span>_<span class=\"br0\">&#40;<\/span>&quot;No lyrics found&quot;<span class=\"br0\">&#41;<\/span><span class=\"br0\">&#41;<\/span><\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; self.search_tags<span class=\"br0\">&#40;<\/span><span class=\"br0\">&#41;<\/span><\/span>\n<span class=\"re8\">+<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; def search_tags<span class=\"br0\">&#40;<\/span>self<span class=\"br0\">&#41;<\/span>:<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; &quot;&quot;&quot;<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; Initiate fetching meta tags.<\/span>\n<span class=\"re8\">+<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; Result will be handled in search_tags_result<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; &quot;&quot;&quot;<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; location = self.entry.get_playback_uri<span class=\"br0\">&#40;<\/span><span class=\"br0\">&#41;<\/span><\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; self.discoverer = GstPbutils.Discoverer<span class=\"br0\">&#40;<\/span>timeout=Gst.SECOND*3<span class=\"br0\">&#41;<\/span><\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; self.discoverer.connect<span class=\"br0\">&#40;<\/span>'discovered', self.search_tags_result<span class=\"br0\">&#41;<\/span><\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; self.discoverer.start<span class=\"br0\">&#40;<\/span><span class=\"br0\">&#41;<\/span><\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; self.discoverer.discover_uri_async<span class=\"br0\">&#40;<\/span>location<span class=\"br0\">&#41;<\/span><\/span>\n<span class=\"re8\">+<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; def search_tags_result<span class=\"br0\">&#40;<\/span>self, discoverer, info, error<span class=\"br0\">&#41;<\/span>:<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; &quot;&quot;&quot;<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; Extract lyrics from the file meta data <span class=\"br0\">&#40;<\/span>tags<span class=\"br0\">&#41;<\/span>.<\/span>\n<span class=\"re8\">+<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; If no lyrics tags are found, online services are tried next.<\/span>\n<span class=\"re8\">+<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; Supported file formats and lyrics tags:<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; - ogg\/vorbis files with &quot;LYRICS&quot; and &quot;SYNCLYRICS&quot; tag<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; &quot;&quot;&quot;<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; tags = info.get_tags<span class=\"br0\">&#40;<\/span><span class=\"br0\">&#41;<\/span><\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; if tags is None:<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; self.search_online<span class=\"br0\">&#40;<\/span><span class=\"br0\">&#41;<\/span><\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; return<\/span>\n&#160;\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; for i in range<span class=\"br0\">&#40;<\/span>tags.get_tag_size<span class=\"br0\">&#40;<\/span>&quot;extended-comment&quot;<span class=\"br0\">&#41;<\/span><span class=\"br0\">&#41;<\/span>:<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; <span class=\"br0\">&#40;<\/span>exists, value<span class=\"br0\">&#41;<\/span> = tags.get_string_index<span class=\"br0\">&#40;<\/span>&quot;extended-comment&quot;, i<span class=\"br0\">&#41;<\/span><\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; #ogg\/vorbis unsynchronized lyrics<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; if exists and value.startswith<span class=\"br0\">&#40;<\/span>&quot;LYRICS&quot;<span class=\"br0\">&#41;<\/span>:<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; text = value.replace<span class=\"br0\">&#40;<\/span>&quot;LYRICS=&quot;, &quot;&quot;<span class=\"br0\">&#41;<\/span><\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; self.lyrics_found<span class=\"br0\">&#40;<\/span>text<span class=\"br0\">&#41;<\/span><\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; return<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; #ogg\/vorbis synchronized lyrics<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; elif exists and value.startswith<span class=\"br0\">&#40;<\/span>&quot;SYNCLYRICS&quot;<span class=\"br0\">&#41;<\/span>:<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; text = value.replace<span class=\"br0\">&#40;<\/span>&quot;SYNCLYRICS=&quot;, &quot;&quot;<span class=\"br0\">&#41;<\/span><\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; self.lyrics_found<span class=\"br0\">&#40;<\/span>text<span class=\"br0\">&#41;<\/span><\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; return<\/span>\n<span class=\"re8\">+<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; self.search_online<span class=\"br0\">&#40;<\/span><span class=\"br0\">&#41;<\/span><\/span>\n<span class=\"re8\">+<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; def search_online<span class=\"br0\">&#40;<\/span>self<span class=\"br0\">&#41;<\/span>:<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; &quot;&quot;&quot;Initiate searching the online lyrics services&quot;&quot;&quot;<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; if self.artist == &quot;&quot; and self.title == &quot;&quot;:<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; self.callback<span class=\"br0\">&#40;<\/span>_<span class=\"br0\">&#40;<\/span>&quot;No lyrics found&quot;<span class=\"br0\">&#41;<\/span><span class=\"br0\">&#41;<\/span><\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; else:<\/span>\n&#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; parser = LyricsParse.Parser<span class=\"br0\">&#40;<\/span>self.artist, self.title<span class=\"br0\">&#41;<\/span>\n<span class=\"re7\">- &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; parser.get_lyrics<span class=\"br0\">&#40;<\/span>lyric_callback<span class=\"br0\">&#41;<\/span><\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; parser.get_lyrics<span class=\"br0\">&#40;<\/span>self.search_online_result<span class=\"br0\">&#41;<\/span><\/span>\n<span class=\"re8\">+<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; def search_online_result<span class=\"br0\">&#40;<\/span>self, text<span class=\"br0\">&#41;<\/span>:<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; &quot;&quot;&quot;Handle the result of searching online lyrics services&quot;&quot;&quot;<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; if text is not None:<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; self.lyrics_found<span class=\"br0\">&#40;<\/span>text<span class=\"br0\">&#41;<\/span><\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; else:<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; self.callback<span class=\"br0\">&#40;<\/span>_<span class=\"br0\">&#40;<\/span>&quot;No lyrics found&quot;<span class=\"br0\">&#41;<\/span><span class=\"br0\">&#41;<\/span><\/span>\n<span class=\"re8\">+<\/span>\n<span class=\"re8\">+<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; def lyrics_found<span class=\"br0\">&#40;<\/span>self, text<span class=\"br0\">&#41;<\/span>:<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; f = open<span class=\"br0\">&#40;<\/span>self.cache_path, 'wt'<span class=\"br0\">&#41;<\/span><\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; f.write<span class=\"br0\">&#40;<\/span>text<span class=\"br0\">&#41;<\/span><\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; f.close<span class=\"br0\">&#40;<\/span><span class=\"br0\">&#41;<\/span><\/span>\n<span class=\"re8\">+<\/span>\n<span class=\"re8\">+ &#160; &#160; &#160; &#160; &#160; &#160; &#160; self.callback<span class=\"br0\">&#40;<\/span>text<span class=\"br0\">&#41;<\/span><\/span>\n<span class=\"re8\">+<\/span>\n&#160;\n&#160;class LyricPane<span class=\"br0\">&#40;<\/span>object<span class=\"br0\">&#41;<\/span>:\n&#160; &#160; &#160; &#160; def __init__<span class=\"br0\">&#40;<\/span>self, db, song_info<span class=\"br0\">&#41;<\/span>:\n&#160;<\/pre><\/td><\/tr><\/tbody><\/table><\/div>\n <\/div>\n <div class=\"phork-meta\">\n  <a href=\"https:\/\/p.cweiske.de\/456\/rev-raw\/9e2bf8c2e22f3b70c888a0f519db6056d59c544a\/0-patch.diff\" style=\"float: right\">view raw source<\/a>\n  <a href=\"https:\/\/p.cweiske.de\/456#0-patch.diff\">0-patch.diff<\/a>\n <\/div>\n<\/div>\n    <div class=\"phork-file\">\n <div class=\"phork-content\">\n  <style type=\"text\/css\">\/**\n * GeSHi (C) 2004 - 2007 Nigel McNie, 2007 - 2014 Benny Baumann\n * (http:\/\/qbnz.com\/highlighter\/ and http:\/\/geshi.org\/)\n *\/\n.bash .de1, .bash .de2 {font: normal normal 1em\/1.2em monospace; margin:0; padding:0; background:none; vertical-align:top;}\n.bash  {font-family:monospace;}\n.bash .imp {font-weight: bold; color: red;}\n.bash li, .bash .li1 {color: #DDD;}\n.bash .ln {width:1px;text-align:right;margin:0;padding:0 2px;vertical-align:top;}\n.bash .kw1 {color: #000000; font-weight: bold;}\n.bash .kw2 {color: #c20cb9; font-weight: bold;}\n.bash .kw3 {color: #7a0874; font-weight: bold;}\n.bash .co0 {color: #666666; font-style: italic;}\n.bash .co1 {color: #800000;}\n.bash .co2 {color: #cc0000; font-style: italic;}\n.bash .co3 {color: #000000; font-weight: bold;}\n.bash .co4 {color: #666666;}\n.bash .es1 {color: #000099; font-weight: bold;}\n.bash .es2 {color: #007800;}\n.bash .es3 {color: #007800;}\n.bash .es4 {color: #007800;}\n.bash .es5 {color: #780078;}\n.bash .es_h {color: #000099; font-weight: bold;}\n.bash .br0 {color: #7a0874; font-weight: bold;}\n.bash .sy0 {color: #000000; font-weight: bold;}\n.bash .st0 {color: #ff0000;}\n.bash .st_h {color: #ff0000;}\n.bash .nu0 {color: #000000;}\n.bash .re0 {color: #007800;}\n.bash .re1 {color: #007800;}\n.bash .re2 {color: #007800;}\n.bash .re4 {color: #007800;}\n.bash .re5 {color: #660033;}\n.bash span.xtra { display:block; }\n<\/style><div class=\"code\"><table class=\"bash\"><tbody><tr class=\"li1\"><td class=\"ln\"><pre class=\"de1\">1\n<\/pre><\/td><td class=\"de1\"><pre class=\"de1\">&#160;.<span class=\"sy0\">\/<\/span>shell<span class=\"sy0\">\/<\/span>rhythmbox <span class=\"re5\">--debug-match<\/span> lyrics filename.ogg<\/pre><\/td><\/tr><\/tbody><\/table><\/div>\n <\/div>\n <div class=\"phork-meta\">\n  <a href=\"https:\/\/p.cweiske.de\/456\/rev-raw\/9e2bf8c2e22f3b70c888a0f519db6056d59c544a\/1-command.sh\" style=\"float: right\">view raw source<\/a>\n  <a href=\"https:\/\/p.cweiske.de\/456#1-command.sh\">1-command.sh<\/a>\n <\/div>\n<\/div>\n    <div class=\"phork-file\">\n <div class=\"phork-content\">\n  <div class=\"code\"><pre class=\"txt\">(14:13:55) [0x1c7bb20] [LyricGrabber.search_lyrics] \/home\/cweiske\/php\/rhythmbox\/rhythmbox\/data\/..\/plugins\/lyrics\/lyrics.py:299: discovering file:\/\/\/home\/cweiske\/Musik\/neu\/Britney%20Spears\/Femme%20Fatale\/Britney%20Spears%20-%20Femme%20Fatale%20-%2003%20-%20Inside%20Out.ogg\r\n(14:13:55) [0x1c7bb20] [LyricGrabber.search_lyrics] \/home\/cweiske\/php\/rhythmbox\/rhythmbox\/data\/..\/plugins\/lyrics\/lyrics.py:303: abc\r\n(14:13:55) [0x1c7bb20] [fetags] \/home\/cweiske\/php\/rhythmbox\/rhythmbox\/data\/..\/plugins\/lyrics\/lyrics.py:317: tag: title\r\n(14:13:55) [0x1c7bb20] [fetags] \/home\/cweiske\/php\/rhythmbox\/rhythmbox\/data\/..\/plugins\/lyrics\/lyrics.py:317: tag: artist\r\n(14:13:55) [0x1c7bb20] [fetags] \/home\/cweiske\/php\/rhythmbox\/rhythmbox\/data\/..\/plugins\/lyrics\/lyrics.py:317: tag: album\r\n(14:13:55) [0x1c7bb20] [fetags] \/home\/cweiske\/php\/rhythmbox\/rhythmbox\/data\/..\/plugins\/lyrics\/lyrics.py:317: tag: datetime\r\n(14:13:55) [0x1c7bb20] [fetags] \/home\/cweiske\/php\/rhythmbox\/rhythmbox\/data\/..\/plugins\/lyrics\/lyrics.py:317: tag: track-number\r\n(14:13:55) [0x1c7bb20] [fetags] \/home\/cweiske\/php\/rhythmbox\/rhythmbox\/data\/..\/plugins\/lyrics\/lyrics.py:317: tag: track-count\r\n(14:13:55) [0x1c7bb20] [fetags] \/home\/cweiske\/php\/rhythmbox\/rhythmbox\/data\/..\/plugins\/lyrics\/lyrics.py:317: tag: genre\r\n(14:13:55) [0x1c7bb20] [fetags] \/home\/cweiske\/php\/rhythmbox\/rhythmbox\/data\/..\/plugins\/lyrics\/lyrics.py:317: tag: image\r\n(14:13:55) [0x1c7bb20] [fetags] \/home\/cweiske\/php\/rhythmbox\/rhythmbox\/data\/..\/plugins\/lyrics\/lyrics.py:317: tag: extended-comment\r\n(14:13:55) [0x1c7bb20] [fetags] \/home\/cweiske\/php\/rhythmbox\/rhythmbox\/data\/..\/plugins\/lyrics\/lyrics.py:317: tag: encoder\r\n(14:13:55) [0x1c7bb20] [fetags] \/home\/cweiske\/php\/rhythmbox\/rhythmbox\/data\/..\/plugins\/lyrics\/lyrics.py:317: tag: encoder-version\r\n(14:13:55) [0x1c7bb20] [fetags] \/home\/cweiske\/php\/rhythmbox\/rhythmbox\/data\/..\/plugins\/lyrics\/lyrics.py:317: tag: audio-codec\r\n(14:13:55) [0x1c7bb20] [fetags] \/home\/cweiske\/php\/rhythmbox\/rhythmbox\/data\/..\/plugins\/lyrics\/lyrics.py:317: tag: nominal-bitrate\r\n(14:13:55) [0x1c7bb20] [fetags] \/home\/cweiske\/php\/rhythmbox\/rhythmbox\/data\/..\/plugins\/lyrics\/lyrics.py:317: tag: bitrate\r\n(14:13:55) [0x1c7bb20] [fetags] \/home\/cweiske\/php\/rhythmbox\/rhythmbox\/data\/..\/plugins\/lyrics\/lyrics.py:317: tag: container-format\r\n(14:13:55) [0x1c7bb20] [LyricGrabber.search_lyrics] \/home\/cweiske\/php\/rhythmbox\/rhythmbox\/data\/..\/plugins\/lyrics\/lyrics.py:311: found lyrics tag:\r\nLYRICS=Said you're gonna be here in a minute\r\nSitting in the mirror getting pretty\r\nGotta look my best if we're gonna break up\r\nGotta look my best if we're gonna break up\r\n<\/pre><\/div>\n\n <\/div>\n <div class=\"phork-meta\">\n  <a href=\"https:\/\/p.cweiske.de\/456\/rev-raw\/9e2bf8c2e22f3b70c888a0f519db6056d59c544a\/2-output.txt\" style=\"float: right\">view raw source<\/a>\n  <a href=\"https:\/\/p.cweiske.de\/456#2-output.txt\">2-output.txt<\/a>\n <\/div>\n<\/div>\n    <div class=\"phork-file\">\n <div class=\"phork-content\">\n  \n<div class=\"document\">\n\n\n<pre class=\"literal-block\">\n$ gst-discoverer-1.0 file.ogg\n<\/pre>\n<p><a class=\"reference external\" href=\"https:\/\/lazka.github.io\/pgi-docs\/GstPbutils-1.0\/classes\/DiscovererInfo.html#GstPbutils.DiscovererInfo\">https:\/\/lazka.github.io\/pgi-docs\/GstPbutils-1.0\/classes\/DiscovererInfo.html#GstPbutils.DiscovererInfo<\/a><\/p>\n<p><a class=\"reference external\" href=\"https:\/\/bugzilla.gnome.org\/show_bug.cgi?id=463978\">https:\/\/bugzilla.gnome.org\/show_bug.cgi?id=463978<\/a><\/p>\n<\/div>\n\n <\/div>\n <div class=\"phork-meta\">\n  <a href=\"https:\/\/p.cweiske.de\/456\/rev-raw\/9e2bf8c2e22f3b70c888a0f519db6056d59c544a\/4-other.rst\" style=\"float: right\">view raw source<\/a>\n  <a href=\"https:\/\/p.cweiske.de\/456#4-other.rst\">4-other.rst<\/a>\n <\/div>\n<\/div>\n    <div class=\"phork-file\">\n <div class=\"phork-content\">\n  <style type=\"text\/css\"><\/style><div class=\"code\"><table class=\"py\"><tbody><tr class=\"li1\"><td class=\"ln\"><pre class=\"de1\">1\n2\n3\n4\n5\n6\n7\n<\/pre><\/td><td class=\"de1\"><pre class=\"de1\">&#160; &#160; &#160; &#160; for i in range(tags.get_tag_size(&quot;extended-comment&quot;)):\r\n&#160; &#160; &#160; &#160; &#160; &#160; (exists, read) = tags.get_string_index(&quot;extended-comment&quot;, i)\r\n&#160; &#160; &#160; &#160; &#160; &#160; if exists and read.startswith(&quot;DISCSUBTITLE&quot;):\r\n&#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; discname = read.replace(&quot;DISCSUBTITLE=&quot;, &quot;&quot;)\r\n&#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; break\r\n&#160; &#160; &#160; &#160; return discname\r\n&#160;<\/pre><\/td><\/tr><\/tbody><\/table><\/div>\n <\/div>\n <div class=\"phork-meta\">\n  <a href=\"https:\/\/p.cweiske.de\/456\/rev-raw\/9e2bf8c2e22f3b70c888a0f519db6056d59c544a\/5-copiedcode.py\" style=\"float: right\">view raw source<\/a>\n  <a href=\"https:\/\/p.cweiske.de\/456#5-copiedcode.py\">5-copiedcode.py<\/a>\n <\/div>\n<\/div>\n    <div class=\"phork-file\">\n <div class=\"phork-content\">\n  <style type=\"text\/css\"><\/style><div class=\"code\"><table class=\"py\"><tbody><tr class=\"li1\"><td class=\"ln\"><pre class=\"de1\">1\n2\n3\n<\/pre><\/td><td class=\"de1\"><pre class=\"de1\">&#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160;def fetags (list, tag):\r\n&#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160;print(&quot;tag: %s&quot; % tag)\r\n&#160; &#160; &#160; &#160; &#160; &#160; &#160; &#160;tags.foreach(fetags)<\/pre><\/td><\/tr><\/tbody><\/table><\/div>\n <\/div>\n <div class=\"phork-meta\">\n  <a href=\"https:\/\/p.cweiske.de\/456\/rev-raw\/9e2bf8c2e22f3b70c888a0f519db6056d59c544a\/6-printalltags.py\" style=\"float: right\">view raw source<\/a>\n  <a href=\"https:\/\/p.cweiske.de\/456#6-printalltags.py\">6-printalltags.py<\/a>\n <\/div>\n<\/div>\n<\/div>\n"}
