def load(name): """ Load the given module, may raise LoadException """ mModulesLock.acquire() module = mModules[name] mModulesLock.release() # Check dependencies unmetDeps = __checkDeps(module[MOD_INFO][MODINFO_DEPS]) if len(unmetDeps) != 0: errMsg = _('The following Python modules are not available:') errMsg += '\n * ' errMsg += '\n * '.join(unmetDeps) errMsg += '\n\n' errMsg += _('You must install them if you want to enable this module.') raise LoadException(errMsg) # Instantiate the module try: module[MOD_INSTANCE] = getattr(module[MOD_PMODULE], module[MOD_CLASSNAME])() module[MOD_INSTANCE].start() mHandlersLock.acquire() if module[MOD_INSTANCE] in mHandlers[consts.MSG_EVT_MOD_LOADED]: module[MOD_INSTANCE].postMsg(consts.MSG_EVT_MOD_LOADED) mHandlersLock.release() log.logger.info('Module loaded: %s' % module[MOD_CLASSNAME]) mEnabledModules.append(name) prefs.set(__name__, 'enabled_modules', mEnabledModules) except: raise LoadException(traceback.format_exc())
def save_track_tree(self): # Save playing track if self.tree.hasMark(): last_path = tuple(self.tree.mark.get_path()) else: last_path = None prefs.set(__name__, 'last-played-track', last_path) dump = self.getTreeDump() logging.info('Saving playlist') pickleSave(self.savedPlaylist, dump) # tell gobject to keep saving the content in regular intervals return True
def onBtnOk(self, btn): """ Save new preferences """ # Skipping tracks newSkipTrack = self.cfgWin.getWidget('chk-skipTrack').get_active() oldSkipTrack = prefs.get(__name__, 'skip-track', PREFS_DEFAULT_SKIP_TRACK) prefs.set(__name__, 'skip-track', newSkipTrack) if oldSkipTrack != newSkipTrack and self.notif is not None: if newSkipTrack: self.notif.add_action('stop', _('Skip track'), self.onSkipTrack) else: self.notif.clear_actions() # Timeout newTimeout = int(self.cfgWin.getWidget('spn-duration').get_value()) oldTimeout = prefs.get(__name__, 'timeout', PREFS_DEFAULT_TIMEOUT) prefs.set(__name__, 'timeout', newTimeout) if oldTimeout != newTimeout and self.notif is not None: self.notif.set_timeout(newTimeout * 1000) # Other preferences prefs.set(__name__, 'title', self.cfgWin.getWidget('txt-title').get_text()) (start, end) = self.cfgWin.getWidget('txt-body').get_buffer().get_bounds() prefs.set( __name__, 'body', self.cfgWin.getWidget('txt-body').get_buffer().get_text( start, end, False)) self.cfgWin.hide()
def saveTreeState(self): """ Create a dictionary representing the current state of the tree """ self.treeState = { 'tree-state': self.getTreeDump(), 'selected-paths': [tuple(path) for path in self.tree.getSelectedPaths()], 'vscrollbar-pos': self.scrolled.get_vscrollbar().get_value(), 'hscrollbar-pos': self.scrolled.get_hscrollbar().get_value(), } prefs.set(__name__, 'saved-states', self.treeState) self.music_paths = self.get_music_paths_from_tree()
def onScaleValueChanged(self, scale, idx): """ The user has moved one of the scales """ # Add a 'custom' entry to the presets if needed if self.preset is not None: self.preset = None prefs.set(__name__, 'preset', self.preset) self.combo.handler_block_by_func(self.onPresetChanged) self.comboStore.insert(0, (False, _('Custom'), None)) self.comboStore.insert(1, (True, '', None)) self.combo.set_active(0) self.combo.handler_unblock_by_func(self.onPresetChanged) self.lvls[idx] = scale.get_value() prefs.set(__name__, 'levels', self.lvls) modules.postMsg(consts.MSG_CMD_SET_EQZ_LVLS, {'lvls': self.lvls})
def onPresetChanged(self, combo): """ A preset has been selected """ idx = combo.get_active() if idx != -1: iter = self.comboStore.get_iter(idx) preset = self.comboStore.get_value(iter, ROW_PRESET_NAME) self.jumpToTargetLvls( self.comboStore.get_value(iter, ROW_PRESET_VALUES)) # Remove the 'Custom' entry if needed if self.preset is None: self.comboStore.remove(self.comboStore.get_iter((0, ))) self.comboStore.remove(self.comboStore.get_iter((0, ))) self.preset = preset prefs.set(__name__, 'preset', self.preset)
def onBtnOpen(self, btn): """ Load the levels from a file""" inFile = gui.fileChooser.openFile(self.cfgWindow, _('Load levels')) if inFile is not None: input = open(inFile, 'rt') lines = input.readlines() input.close() lvls = [0, 0, 0, 0, 0, 0, 0, 0, 0, 0] isInvalid = True if len(lines) == 10: isInvalid = False for i in range(10): elts = lines[i].split() try: if len(elts) == 1: lvls[i] = float(elts[0]) if lvls[i] >= -24 and lvls[i] <= 12: continue except: pass isInvalid = True break if isInvalid: gui.errorMsgBox(self.cfgWindow, _('Could not load the file'), _('The format of the file is incorrect.')) else: self.jumpToTargetLvls(lvls) # Add a 'custom' entry to the presets if needed if self.preset is not None: self.preset = None prefs.set(__name__, 'preset', self.preset) self.combo.handler_block_by_func(self.onPresetChanged) self.comboStore.insert(0, (False, _('Custom'), None)) self.comboStore.insert(1, (True, '', None)) self.combo.set_active(0) self.combo.handler_unblock_by_func(self.onPresetChanged)
def unload(name): """ Unload the given module """ mModulesLock.acquire() module = mModules[name] instance = module[MOD_INSTANCE] module[MOD_INSTANCE] = None mModulesLock.release() if instance is not None: mHandlersLock.acquire() instance.postMsg(consts.MSG_EVT_MOD_UNLOADED) for handlers in [ handler for handler in mHandlers.values() if instance in handler ]: handlers.remove(instance) mHandlersLock.release() mEnabledModules.remove(name) log.logger.info('Module unloaded: %s' % module[MOD_CLASSNAME]) prefs.set(__name__, 'enabled_modules', mEnabledModules)
def timerFunc(self): """ Move a bit the scales to their target value """ isFinished = True # Move the scales a bit for i in range(10): currLvl = self.scales[i].get_value() targetLvl = self.targetLvls[i] difference = targetLvl - currLvl if abs(difference) <= 0.25: newLvl = targetLvl else: newLvl = currLvl + (difference / 8.0) isFinished = False self.lvls[i] = newLvl self.scales[i].set_value(newLvl) # Set the equalizer to the new levels modules.postMsg(consts.MSG_CMD_SET_EQZ_LVLS, {'lvls': self.lvls}) if isFinished: self.timer = None prefs.set(__name__, 'levels', self.lvls) # Make sure labels are up to date (sometimes they aren't when we're done with the animation) # Also unblock the handlers for i in range(10): self.scales[i].queue_draw() self.scales[i].handler_unblock_by_func( self.onScaleValueChanged) return False return True
def load_enabled_modules(): # Find modules, instantiate those that are mandatory or that have been previously enabled by the user sys.path.append(mModDir) for file in sorted( os.path.splitext(file)[0] for file in os.listdir(mModDir) if file.endswith('.py') and file not in blacklist): try: pModule = __import__(file) modInfo = getattr(pModule, 'MOD_INFO') # Should it be instantiated? instance = None if modInfo[MODINFO_MANDATORY] or modInfo[ MODINFO_NAME] in mEnabledModules: if len(__checkDeps(modInfo[MODINFO_DEPS])) == 0: log.logger.info('Loading module: %s' % file) instance = getattr(pModule, file)() instance.start() else: log.logger.error( 'Unable to load module %s because of missing dependencies' % file) # Add it to the dictionary mModules[modInfo[MODINFO_NAME]] = [ pModule, file, instance, modInfo ] except: log.logger.error('Unable to load module %s\n\n%s' % (file, traceback.format_exc())) # Remove enabled modules that are no longer available mEnabledModules[:] = [ module for module in mEnabledModules if module in mModules ] prefs.set(__name__, 'enabled_modules', mEnabledModules)
def onResize(win, rect): """ Save the new size of the window """ maximized = win.get_state() & Gdk.WindowState.MAXIMIZED if not maximized: prefs.set(__name__, 'win-width', rect.width) prefs.set(__name__, 'win-height', rect.height) view_mode = prefs.get(__name__, 'view-mode', DEFAULT_VIEW_MODE) if view_mode in (consts.VIEW_MODE_FULL, consts.VIEW_MODE_PLAYLIST): prefs.set(__name__, 'full-win-height', rect.height)
def onBtnOk(self, btn): """ Save configuration """ downloadCovers = self.cfgWin.getWidget( 'chk-downloadCovers').get_active() preferUserCovers = self.cfgWin.getWidget( 'chk-preferUserCovers').get_active() userCoverFilenames = [ word.strip() for word in self.cfgWin.getWidget( 'txt-filenames').get_text().split(',') ] prefs.set(__name__, 'download-covers', downloadCovers) prefs.set(__name__, 'prefer-user-covers', preferUserCovers) prefs.set(__name__, 'user-cover-filenames', userCoverFilenames) self.cfgWin.hide()
def onAppQuit(self): """ The application is about to terminate """ prefs.set(__name__, 'show_thumb', self.cover_spot.show_thumb)
def onState(win, event): """ Save the new state of the window """ if event.changed_mask & Gdk.WindowState.MAXIMIZED: maximized = bool(event.new_window_state & Gdk.WindowState.MAXIMIZED) prefs.set(__name__, 'win-is-maximized', maximized)
def onPanedResize(win, rect): prefs.set(__name__, 'paned-pos', paned.get_position())
def realStartup(window, paned): """ Perform all the initialization stuff which is not mandatory to display the window. This function should be called within the GTK main loop, once the window has been displayed """ # Is the application started for the first time? first_start = prefs.get(__name__, 'first-time', True) logging.debug('First start: {}'.format(first_start)) if first_start: prefs.set(__name__, 'first-time', False) # Enable some modules by default prefs.set('modules', 'enabled_modules', ['Covers', 'Desktop Notification']) import atexit import signal import dbus.mainloop.glib from pogo import modules modules.load_enabled_modules() def onDelete(win, event): """ Use our own quit sequence, that will itself destroy the window """ win.hide() modules.postQuitMsg() return True def onResize(win, rect): """ Save the new size of the window """ maximized = win.get_state() & Gdk.WindowState.MAXIMIZED if not maximized: prefs.set(__name__, 'win-width', rect.width) prefs.set(__name__, 'win-height', rect.height) view_mode = prefs.get(__name__, 'view-mode', DEFAULT_VIEW_MODE) if view_mode in (consts.VIEW_MODE_FULL, consts.VIEW_MODE_PLAYLIST): prefs.set(__name__, 'full-win-height', rect.height) def onPanedResize(win, rect): prefs.set(__name__, 'paned-pos', paned.get_position()) def onState(win, event): """ Save the new state of the window """ if event.changed_mask & Gdk.WindowState.MAXIMIZED: maximized = bool(event.new_window_state & Gdk.WindowState.MAXIMIZED) prefs.set(__name__, 'win-is-maximized', maximized) def atExit(): """ Final function, called just before exiting the Python interpreter """ prefs.save() log.logger.info('Stopped') # D-Bus dbus.mainloop.glib.DBusGMainLoop(set_as_default=True) # Register some handlers (Signal SIGKILL cannot be caught) atexit.register(atExit) signal.signal(signal.SIGINT, lambda _sig, _frame: onDelete(window, None)) signal.signal(signal.SIGTERM, lambda _sig, _frame: onDelete(window, None)) # GTK handlers window.connect('delete-event', onDelete) window.connect('size-allocate', onResize) window.connect('window-state-event', onState) paned.connect('size-allocate', onPanedResize) # Let's go GObject.idle_add(modules.postMsg, consts.MSG_EVT_APP_STARTED)