Index: st2.py ================================================================== --- st2.py +++ st2.py @@ -66,10 +66,11 @@ # standard modules import sys import os, os.path import re +from collections import namedtuple # threading or processing module try: from processing import Process as Thread except: @@ -109,10 +110,13 @@ features = {} # non-channel plugins working = [] # threads add_signals = {} # channel gtk-handler signals hooks = { "play": [favicon.download_playing], # observers queue here + "init": [], + "config_load": [], + "config_save": [], } # status variables channel_names = ["bookmarks"] # order of channel notebook tabs current_channel = "bookmarks" # currently selected channel name (as index in self.channels{}) @@ -151,12 +155,16 @@ self.channels[id].current = winstate[id]["current"] self.channels[id].shown = winlayout[id+"_list"].get("row:selected", 0) # actually just used as boolean flag (for late loading of stream list), selection bar has been positioned before already except: pass # fails for disabled/reordered plugin channels - # display current open channel/notebook tab + # late plugin initializations gui_startup(17/20.0) + [callback(self) for callback in self.hooks["init"]] + + # display current open channel/notebook tab + gui_startup(18/20.0) self.current_channel = self.current_channel_gtk() try: self.channel().first_show() except: __print__(dbg.INIT, "main.__init__: current_channel.first_show() initialization error") @@ -220,11 +228,11 @@ "streamedit_new": streamedit.new, "streamedit_cancel": streamedit.cancel, }.items() ) + list( self.add_signals.items() ) )) # actually display main window - gui_startup(99/100.0) + gui_startup(98.9/100.0) self.win_streamtuner2.show() @@ -271,12 +279,11 @@ self.current_channel = self.channel_names[page_num] # if first selected, load current category try: __print__(dbg.PROC, "channel_switch: try .first_show", self.channel().module); - __print__(self.channel().first_show) - __print__(self.channel().first_show()) + self.channel().first_show() except: __print__(dbg.INIT, "channel .first_show() initialization error") # convert ListStore iter to row number @@ -306,11 +313,11 @@ # play button def on_play_clicked(self, widget, event=None, *args): row = self.row() if row: self.channel().play(row) - [hook(row) for hook in self.hooks["play"]] + [callback(row) for callback in self.hooks["play"]] # streamripper def on_record_clicked(self, widget): row = self.row() @@ -744,10 +751,11 @@ self.combobox_theme() self.first_open = 0 self.win_config.resize(565, 625) self.load_config(conf.__dict__, "config_") self.load_config(conf.plugins, "config_plugins_") + [callback() for callback in self.hooks["config_load"]] self.win_config.show() first_open = 1 # Hide window def hide(self, *args): @@ -875,11 +883,12 @@ # save config def save(self, widget): self.save_config(conf.__dict__, "config_") self.save_config(conf.plugins, "config_plugins_") - self.apply_theme() + [callback() for callback in main.hooks["config_save"]] + config_dialog.apply_theme() conf.save(nice=1) self.hide() config_dialog = config_dialog() # instantiates itself @@ -962,22 +971,23 @@ pass def update_streams(self, cat): return self.streams.get(cat, []) - # initial display + # streams are already loaded at instantiation def first_show(self): - if not self.streams["favourite"]: - self.cache() + pass # all entries just come from "bookmarks.json" def cache(self): # stream list cache = conf.load(self.module) if (cache): + __print__(dbg.PROC, "load bookmarks.json") self.streams = cache + # save to cache file def save(self): conf.save(self.module, self.streams, nice=1)