More work on new preferences infrastructure

This commit is contained in:
Kovid Goyal 2010-08-25 19:15:23 -06:00
parent 6a572b9a41
commit 0916d15e8a
10 changed files with 731 additions and 13 deletions

View File

@ -5,7 +5,8 @@ __copyright__ = '2008, Kovid Goyal <kovid at kovidgoyal.net>'
import textwrap
import os
import glob
from calibre.customize import FileTypePlugin, MetadataReaderPlugin, MetadataWriterPlugin
from calibre.customize import FileTypePlugin, MetadataReaderPlugin, \
MetadataWriterPlugin, PreferencesPlugin, InterfaceActionBase
from calibre.constants import numeric_version
from calibre.ebooks.metadata.archive import ArchiveExtract, get_cbz_metadata
@ -577,7 +578,7 @@ plugins += [x for x in list(locals().values()) if isinstance(x, type) and \
x.__name__.endswith('MetadataWriter')]
plugins += input_profiles + output_profiles
from calibre.customize import InterfaceActionBase
# Interface Actions {{{
class ActionAdd(InterfaceActionBase):
name = 'Add Books'
@ -670,3 +671,20 @@ plugins += [ActionAdd, ActionFetchAnnotations, ActionGenerateCatalog,
ActionSendToDevice, ActionHelp, ActionPreferences, ActionSimilarBooks,
ActionAddToLibrary, ActionEditCollections, ActionChooseLibrary,
ActionCopyToLibrary]
# }}}
# Preferences Plugins {{{
class LookAndFeel(PreferencesPlugin):
name = 'Look & Feel'
gui_name = _('Look and Feel')
category = _('Interface')
category_order = 1
name_order = 1
config_widget = 'calibre.gui2.preferences.look_feel'
plugins += [LookAndFeel]
#}}}

View File

@ -46,6 +46,11 @@ gprefs.defaults['action-layout-context-menu-device'] = (
'View', 'Save To Disk', None, 'Remove Books', None,
'Add To Library', 'Edit Collections',
)
gprefs.defaults['show_splash_screen'] = True
gprefs.defaults['toolbar_icon_size'] = 'medium'
gprefs.defaults['toolbar_text'] = 'auto'
# }}}
NONE = QVariant() #: Null value to return from the data function of item models

View File

@ -219,11 +219,11 @@ class ToolBar(QToolBar): # {{{
self.preferred_width = self.sizeHint().width()
def apply_settings(self):
sz = gprefs.get('toolbar_icon_size', 'medium')
sz = gprefs['toolbar_icon_size']
sz = {'small':24, 'medium':48, 'large':64}[sz]
self.setIconSize(QSize(sz, sz))
style = Qt.ToolButtonTextUnderIcon
if gprefs.get('toolbar_text', 'auto') == 'never':
if gprefs['toolbar_text'] == 'never':
style = Qt.ToolButtonIconOnly
self.setToolButtonStyle(style)
self.donate_button.set_normal_icon_size(sz, sz)
@ -265,7 +265,7 @@ class ToolBar(QToolBar): # {{{
def resizeEvent(self, ev):
QToolBar.resizeEvent(self, ev)
style = Qt.ToolButtonTextUnderIcon
p = gprefs.get('toolbar_text', 'auto')
p = gprefs['toolbar_text']
if p == 'never':
style = Qt.ToolButtonIconOnly

View File

@ -241,7 +241,7 @@ class GuiRunner(QObject):
QApplication.instance().processEvents()
def initialize(self, *args):
if gprefs.get('show_splash_screen', True):
if gprefs['show_splash_screen']:
self.show_splash_screen()
self.library_path = get_library_path(parent=self.splash_screen)

View File

@ -107,6 +107,7 @@ class Setting(object):
val = None
elif self.datatype == 'choices':
idx = self.gui_obj.currentIndex()
if idx < 0: idx = 0
val = unicode(self.gui_obj.itemData(idx).toString())
return val
@ -121,8 +122,9 @@ class ConfigWidgetBase(QWidget, ConfigWidgetInterface):
self.setupUi(self)
self.settings = {}
def register(self, name, config_obj, widget, gui_name=None):
setting = Setting(name, config_obj, widget, gui_name=gui_name)
def register(self, name, config_obj, gui_name=None, choices=None, setting=Setting):
setting = setting(name, config_obj, self, gui_name=gui_name,
choices=choices)
self.register_setting(setting)
def register_setting(self, setting):
@ -165,18 +167,19 @@ def test_widget(category, name, gui=None): # {{{
bb.button(bb.Apply).setEnabled(False)
w.changed_signal.connect(lambda : bb.button(bb.Apply).setEnable(True))
l = QVBoxLayout()
pl.setLayout(l)
d.setLayout(l)
l.addWidget(w)
l.addWidget(bb)
if gui is None:
from calibre.gui2.ui import Main
from calibre.gui2.main import option_parser
from calibre.library.db import db
from calibre.library import db
parser = option_parser()
opts, args = parser.parse_args([])
actions = tuple(Main.create_application_menubar())
db = db()
gui = Main(opts)
gui.initialize(db.library_path, db, None, actions)
gui.initialize(db.library_path, db, None, actions, show_gui=False)
w.genesis(gui)
if d.exec_() == QDialog.Accepted:
w.commit()

View File

@ -0,0 +1,263 @@
<?xml version="1.0" encoding="UTF-8"?>
<ui version="4.0">
<class>Form</class>
<widget class="QWidget" name="Form">
<property name="geometry">
<rect>
<x>0</x>
<y>0</y>
<width>672</width>
<height>563</height>
</rect>
</property>
<property name="windowTitle">
<string>Form</string>
</property>
<layout class="QGridLayout" name="gridLayout">
<item row="0" column="0" colspan="2">
<widget class="QCheckBox" name="opt_overwrite_author_title_metadata">
<property name="text">
<string>&amp;Overwrite author and title by default when fetching metadata</string>
</property>
</widget>
</item>
<item row="1" column="0" colspan="2">
<widget class="QCheckBox" name="opt_get_social_metadata">
<property name="text">
<string>Download &amp;social metadata (tags/ratings/etc.) by default</string>
</property>
</widget>
</item>
<item row="2" column="0" colspan="2">
<widget class="QCheckBox" name="new_version_notification">
<property name="text">
<string>Show notification when &amp;new version is available</string>
</property>
</widget>
</item>
<item row="3" column="0" colspan="2">
<widget class="QCheckBox" name="sync_news">
<property name="text">
<string>Automatically send downloaded &amp;news to ebook reader</string>
</property>
</widget>
</item>
<item row="4" column="0" colspan="2">
<widget class="QCheckBox" name="delete_news">
<property name="text">
<string>&amp;Delete news from library when it is automatically sent to reader</string>
</property>
</widget>
</item>
<item row="5" column="0" colspan="2">
<layout class="QGridLayout" name="gridLayout_2">
<item row="1" column="0">
<widget class="QLabel" name="label_2">
<property name="text">
<string>Default network &amp;timeout:</string>
</property>
<property name="buddy">
<cstring>timeout</cstring>
</property>
</widget>
</item>
<item row="1" column="1">
<widget class="QSpinBox" name="timeout">
<property name="toolTip">
<string>Set the default timeout for network fetches (i.e. anytime we go out to the internet to get information)</string>
</property>
<property name="suffix">
<string> seconds</string>
</property>
<property name="minimum">
<number>2</number>
</property>
<property name="maximum">
<number>120</number>
</property>
<property name="value">
<number>5</number>
</property>
</widget>
</item>
<item row="2" column="1">
<widget class="QComboBox" name="priority">
<property name="sizeAdjustPolicy">
<enum>QComboBox::AdjustToMinimumContentsLengthWithIcon</enum>
</property>
<property name="minimumContentsLength">
<number>20</number>
</property>
<item>
<property name="text">
<string>Normal</string>
</property>
</item>
<item>
<property name="text">
<string>High</string>
</property>
</item>
<item>
<property name="text">
<string>Low</string>
</property>
</item>
</widget>
</item>
<item row="2" column="0">
<widget class="QLabel" name="priority_label">
<property name="text">
<string>Job &amp;priority:</string>
</property>
<property name="buddy">
<cstring>priority</cstring>
</property>
</widget>
</item>
<item row="0" column="0">
<widget class="QLabel" name="label_23">
<property name="text">
<string>Preferred &amp;output format:</string>
</property>
<property name="buddy">
<cstring>output_format</cstring>
</property>
</widget>
</item>
<item row="0" column="1">
<widget class="QComboBox" name="output_format">
<property name="sizeAdjustPolicy">
<enum>QComboBox::AdjustToMinimumContentsLengthWithIcon</enum>
</property>
<property name="minimumContentsLength">
<number>10</number>
</property>
</widget>
</item>
<item row="3" column="0">
<widget class="QLabel" name="label_170">
<property name="text">
<string>Restriction to apply when the current library is opened:</string>
</property>
<property name="buddy">
<cstring>opt_gui_restriction</cstring>
</property>
</widget>
</item>
<item row="3" column="1">
<widget class="QComboBox" name="opt_gui_restriction">
<property name="maximumSize">
<size>
<width>250</width>
<height>16777215</height>
</size>
</property>
<property name="toolTip">
<string>Apply this restriction on calibre startup if the current library is being used. Also applied when switching to this library. Note that this setting is per library. </string>
</property>
<property name="sizeAdjustPolicy">
<enum>QComboBox::AdjustToMinimumContentsLengthWithIcon</enum>
</property>
<property name="minimumContentsLength">
<number>15</number>
</property>
</widget>
</item>
</layout>
</item>
<item row="6" column="0" colspan="2">
<widget class="QPushButton" name="reset_confirmation_button">
<property name="text">
<string>Reset all disabled &amp;confirmation dialogs</string>
</property>
</widget>
</item>
<item row="7" column="0">
<widget class="QGroupBox" name="groupBox_5">
<property name="title">
<string>Preferred &amp;input format order:</string>
</property>
<layout class="QVBoxLayout" name="verticalLayout_11">
<item>
<layout class="QHBoxLayout" name="horizontalLayout_10">
<item>
<widget class="QListWidget" name="input_order">
<property name="alternatingRowColors">
<bool>true</bool>
</property>
<property name="selectionBehavior">
<enum>QAbstractItemView::SelectRows</enum>
</property>
</widget>
</item>
<item>
<layout class="QVBoxLayout" name="verticalLayout_10">
<item>
<widget class="QToolButton" name="input_up">
<property name="text">
<string>...</string>
</property>
<property name="icon">
<iconset resource="../../../../resources/images.qrc">
<normaloff>:/images/arrow-up.svg</normaloff>:/images/arrow-up.svg</iconset>
</property>
</widget>
</item>
<item>
<spacer name="verticalSpacer_5">
<property name="orientation">
<enum>Qt::Vertical</enum>
</property>
<property name="sizeHint" stdset="0">
<size>
<width>20</width>
<height>40</height>
</size>
</property>
</spacer>
</item>
<item>
<widget class="QToolButton" name="input_down">
<property name="text">
<string>...</string>
</property>
<property name="icon">
<iconset resource="../../../../resources/images.qrc">
<normaloff>:/images/arrow-down.svg</normaloff>:/images/arrow-down.svg</iconset>
</property>
</widget>
</item>
</layout>
</item>
</layout>
</item>
</layout>
</widget>
</item>
<item row="7" column="1">
<widget class="QGroupBox" name="groupBox_3">
<property name="title">
<string>Use internal &amp;viewer for:</string>
</property>
<layout class="QGridLayout" name="gridLayout_4">
<item row="0" column="0">
<widget class="QListWidget" name="viewer">
<property name="alternatingRowColors">
<bool>true</bool>
</property>
<property name="selectionMode">
<enum>QAbstractItemView::NoSelection</enum>
</property>
</widget>
</item>
</layout>
</widget>
</item>
</layout>
</widget>
<resources>
<include location="../../../../resources/images.qrc"/>
</resources>
<connections/>
</ui>

View File

@ -0,0 +1,170 @@
<?xml version="1.0" encoding="UTF-8"?>
<ui version="4.0">
<class>Form</class>
<widget class="QWidget" name="Form">
<property name="geometry">
<rect>
<x>0</x>
<y>0</y>
<width>504</width>
<height>399</height>
</rect>
</property>
<property name="windowTitle">
<string>Form</string>
</property>
<layout class="QGridLayout" name="gridLayout">
<item row="0" column="0" colspan="2">
<widget class="QLabel" name="label">
<property name="text">
<string>Here you can re-arrange the layout of the columns in the calibre library book list. You can hide columns by unchecking them. You can also create your own, custom columns.</string>
</property>
<property name="wordWrap">
<bool>true</bool>
</property>
</widget>
</item>
<item row="1" column="0">
<widget class="QListWidget" name="columns">
<property name="alternatingRowColors">
<bool>true</bool>
</property>
<property name="selectionBehavior">
<enum>QAbstractItemView::SelectRows</enum>
</property>
</widget>
</item>
<item row="1" column="1">
<layout class="QVBoxLayout" name="verticalLayout_3">
<item>
<widget class="QToolButton" name="column_up">
<property name="text">
<string>...</string>
</property>
<property name="icon">
<iconset resource="../../../../resources/images.qrc">
<normaloff>:/images/arrow-up.svg</normaloff>:/images/arrow-up.svg</iconset>
</property>
</widget>
</item>
<item>
<spacer name="verticalSpacer_2">
<property name="orientation">
<enum>Qt::Vertical</enum>
</property>
<property name="sizeHint" stdset="0">
<size>
<width>20</width>
<height>40</height>
</size>
</property>
</spacer>
</item>
<item>
<widget class="QToolButton" name="del_custcol_button">
<property name="toolTip">
<string>Remove a user-defined column</string>
</property>
<property name="text">
<string>...</string>
</property>
<property name="icon">
<iconset resource="../../../../resources/images.qrc">
<normaloff>:/images/minus.svg</normaloff>:/images/minus.svg</iconset>
</property>
</widget>
</item>
<item>
<spacer name="verticalSpacer_3">
<property name="orientation">
<enum>Qt::Vertical</enum>
</property>
<property name="sizeHint" stdset="0">
<size>
<width>20</width>
<height>40</height>
</size>
</property>
</spacer>
</item>
<item>
<widget class="QToolButton" name="add_custcol_button">
<property name="toolTip">
<string>Add a user-defined column</string>
</property>
<property name="text">
<string>...</string>
</property>
<property name="icon">
<iconset resource="../../../../resources/images.qrc">
<normaloff>:/images/plus.svg</normaloff>:/images/plus.svg</iconset>
</property>
</widget>
</item>
<item>
<spacer name="verticalSpacer_4">
<property name="orientation">
<enum>Qt::Vertical</enum>
</property>
<property name="sizeHint" stdset="0">
<size>
<width>20</width>
<height>40</height>
</size>
</property>
</spacer>
</item>
<item>
<widget class="QToolButton" name="edit_custcol_button">
<property name="toolTip">
<string>Edit settings of a user-defined column</string>
</property>
<property name="text">
<string>...</string>
</property>
<property name="icon">
<iconset resource="../../../../resources/images.qrc">
<normaloff>:/images/edit_input.svg</normaloff>:/images/edit_input.svg</iconset>
</property>
</widget>
</item>
<item>
<spacer name="verticalSpacer_5">
<property name="orientation">
<enum>Qt::Vertical</enum>
</property>
<property name="sizeHint" stdset="0">
<size>
<width>20</width>
<height>40</height>
</size>
</property>
</spacer>
</item>
<item>
<widget class="QToolButton" name="column_down">
<property name="text">
<string>...</string>
</property>
<property name="icon">
<iconset resource="../../../../resources/images.qrc">
<normaloff>:/images/arrow-down.svg</normaloff>:/images/arrow-down.svg</iconset>
</property>
</widget>
</item>
</layout>
</item>
<item row="2" column="0" colspan="2">
<widget class="QPushButton" name="pushButton">
<property name="text">
<string>Add &amp;custom column</string>
</property>
</widget>
</item>
</layout>
</widget>
<resources>
<include location="../../../../resources/images.qrc"/>
</resources>
<connections/>
</ui>

View File

@ -0,0 +1,62 @@
#!/usr/bin/env python
# vim:fileencoding=UTF-8:ts=4:sw=4:sta:et:sts=4:ai
__license__ = 'GPL v3'
__copyright__ = '2010, Kovid Goyal <kovid@kovidgoyal.net>'
__docformat__ = 'restructuredtext en'
from calibre.gui2.preferences import ConfigWidgetBase, test_widget
from calibre.gui2.preferences.look_feel_ui import Ui_Form
from calibre.gui2 import config, gprefs
from calibre.utils.localization import available_translations, \
get_language, get_lang
from calibre.utils.config import prefs
class ConfigWidget(ConfigWidgetBase, Ui_Form):
def genesis(self, gui):
self.gui = gui
r = self.register
r('gui_layout', config, choices=
[(_('Wide'), 'wide'), (_('Narrow'), 'narrow')])
r('cover_flow_queue_length', config)
lang = get_lang()
if lang is None or lang not in available_translations():
lang = 'en'
items = [(l, get_language(l)) for l in available_translations() \
if l != lang]
if lang != 'en':
items.append(('en', get_language('en')))
items.sort(cmp=lambda x, y: cmp(x[1], y[1]))
choices = [(y, x) for x, y in items]
# Default language is the autodetected one
choices = [get_language(lang), lang] + choices
r('language', prefs, choices=choices)
r('show_avg_rating', config)
r('disable_animations', config)
r('systray_icon', config)
r('show_splash_screen', gprefs)
r('disable_tray_notification', config)
r('use_roman_numerals_for_series_number', config)
r('separate_cover_flow', config)
r('search_as_you_type', config)
choices = [(_('Small'), 'small'), (_('Medium'), 'medium'),
(_('Large'), 'large')]
r('toolbar_icon_size', gprefs, choices=choices)
choices = [(_('Automatic'), 'auto'), (_('Always'), 'always'),
(_('Never'), 'never')]
r('toolbar_text', gprefs, choices=choices)
if __name__ == '__main__':
from PyQt4.Qt import QApplication
app = QApplication([])
test_widget('Interface', 'Look & Feel')

View File

@ -0,0 +1,196 @@
<?xml version="1.0" encoding="UTF-8"?>
<ui version="4.0">
<class>Form</class>
<widget class="QWidget" name="Form">
<property name="geometry">
<rect>
<x>0</x>
<y>0</y>
<width>670</width>
<height>385</height>
</rect>
</property>
<property name="windowTitle">
<string>Form</string>
</property>
<layout class="QGridLayout" name="gridLayout_2">
<item row="0" column="0">
<widget class="QLabel" name="label_17">
<property name="text">
<string>User Interface &amp;layout (needs restart):</string>
</property>
<property name="buddy">
<cstring>opt_gui_layout</cstring>
</property>
</widget>
</item>
<item row="0" column="1">
<widget class="QComboBox" name="opt_gui_layout">
<property name="maximumSize">
<size>
<width>250</width>
<height>16777215</height>
</size>
</property>
<property name="sizeAdjustPolicy">
<enum>QComboBox::AdjustToMinimumContentsLengthWithIcon</enum>
</property>
<property name="minimumContentsLength">
<number>20</number>
</property>
</widget>
</item>
<item row="1" column="0">
<widget class="QLabel" name="label_6">
<property name="text">
<string>&amp;Number of covers to show in browse mode (needs restart):</string>
</property>
<property name="buddy">
<cstring>opt_cover_flow_queue_length</cstring>
</property>
</widget>
</item>
<item row="1" column="1">
<widget class="QSpinBox" name="opt_cover_flow_queue_length"/>
</item>
<item row="2" column="0">
<widget class="QLabel" name="label_7">
<property name="text">
<string>Choose &amp;language (requires restart):</string>
</property>
<property name="buddy">
<cstring>opt_language</cstring>
</property>
</widget>
</item>
<item row="2" column="1">
<widget class="QComboBox" name="opt_language">
<property name="sizeAdjustPolicy">
<enum>QComboBox::AdjustToMinimumContentsLengthWithIcon</enum>
</property>
<property name="minimumContentsLength">
<number>20</number>
</property>
</widget>
</item>
<item row="3" column="0">
<widget class="QCheckBox" name="opt_show_avg_rating">
<property name="text">
<string>Show &amp;average ratings in the tags browser</string>
</property>
<property name="checked">
<bool>true</bool>
</property>
</widget>
</item>
<item row="3" column="1">
<widget class="QCheckBox" name="opt_disable_animations">
<property name="toolTip">
<string>Disable all animations. Useful if you have a slow/old computer.</string>
</property>
<property name="text">
<string>Disable &amp;animations</string>
</property>
</widget>
</item>
<item row="4" column="0">
<widget class="QCheckBox" name="opt_systray_icon">
<property name="text">
<string>Enable system &amp;tray icon (needs restart)</string>
</property>
</widget>
</item>
<item row="4" column="1">
<widget class="QCheckBox" name="opt_show_splash_screen">
<property name="text">
<string>Show &amp;splash screen at startup</string>
</property>
</widget>
</item>
<item row="5" column="0">
<widget class="QCheckBox" name="opt_disable_tray_notification">
<property name="text">
<string>Disable &amp;notifications in system tray</string>
</property>
</widget>
</item>
<item row="5" column="1">
<widget class="QCheckBox" name="opt_use_roman_numerals_for_series_number">
<property name="text">
<string>Use &amp;Roman numerals for series</string>
</property>
<property name="checked">
<bool>true</bool>
</property>
</widget>
</item>
<item row="6" column="0">
<widget class="QCheckBox" name="opt_separate_cover_flow">
<property name="text">
<string>Show cover &amp;browser in a separate window (needs restart)</string>
</property>
</widget>
</item>
<item row="6" column="1">
<widget class="QCheckBox" name="opt_search_as_you_type">
<property name="text">
<string>Search as you type</string>
</property>
<property name="checked">
<bool>true</bool>
</property>
</widget>
</item>
<item row="7" column="0" colspan="2">
<widget class="QGroupBox" name="groupBox_2">
<property name="title">
<string>&amp;Toolbar</string>
</property>
<layout class="QGridLayout" name="gridLayout">
<item row="0" column="1">
<widget class="QComboBox" name="opt_toolbar_icon_size"/>
</item>
<item row="0" column="0">
<widget class="QLabel" name="label">
<property name="text">
<string>&amp;Icon size:</string>
</property>
<property name="buddy">
<cstring>opt_toolbar_icon_size</cstring>
</property>
</widget>
</item>
<item row="1" column="1">
<widget class="QComboBox" name="opt_toolbar_text"/>
</item>
<item row="1" column="0">
<widget class="QLabel" name="label_4">
<property name="text">
<string>Show &amp;text under icons:</string>
</property>
<property name="buddy">
<cstring>opt_toolbar_text</cstring>
</property>
</widget>
</item>
</layout>
</widget>
</item>
<item row="8" column="0" colspan="2">
<spacer name="verticalSpacer">
<property name="orientation">
<enum>Qt::Vertical</enum>
</property>
<property name="sizeHint" stdset="0">
<size>
<width>20</width>
<height>40</height>
</size>
</property>
</spacer>
</item>
</layout>
</widget>
<resources/>
<connections/>
</ui>

View File

@ -110,7 +110,7 @@ class Main(MainWindow, MainWindowMixin, DeviceMixin, # {{{
self.iactions = acmap
def initialize(self, library_path, db, listener, actions):
def initialize(self, library_path, db, listener, actions, show_gui=True):
opts = self.opts
self.preferences_action, self.quit_action = actions
self.library_path = library_path
@ -203,7 +203,8 @@ class Main(MainWindow, MainWindowMixin, DeviceMixin, # {{{
####################### Library view ########################
LibraryViewMixin.__init__(self, db)
self.show()
if show_gui:
self.show()
if self.system_tray_icon.isVisible() and opts.start_in_tray:
self.hide_windows()